diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index c86507c7fc..baf0fbbe8e 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -25,12 +25,12 @@ /packages/cli/src/cmds/m365 @swatDong @kuojianlu @kimizhu /packages/cli/src/cmds/preview @swatDong @kuojianlu @qinezh @a1exwang /packages/cli/src/commands @jayzhang @Alive-Fish -/packages/cli/src/commands/models/account.ts @swatDong @xiaolang124 @kimizhu -/packages/cli/src/commands/models/accountLogin.ts @swatDong @xiaolang124 @kimizhu -/packages/cli/src/commands/models/accountLoginAzure.ts @swatDong @xiaolang124 @kimizhu -/packages/cli/src/commands/models/accountLoginM365.ts @swatDong @xiaolang124 @kimizhu -/packages/cli/src/commands/models/accountLogout.ts @swatDong @xiaolang124 @kimizhu -/packages/cli/src/commands/models/accountShow.ts @swatDong @xiaolang124 @kimizhu +/packages/cli/src/commands/models/account.ts @swatDong @xiaolang124 @kimizhu @HuihuiWu-Microsoft @jayzhang +/packages/cli/src/commands/models/accountLogin.ts @swatDong @xiaolang124 @kimizhu @HuihuiWu-Microsoft @jayzhang +/packages/cli/src/commands/models/accountLoginAzure.ts @swatDong @xiaolang124 @kimizhu @HuihuiWu-Microsoft @jayzhang +/packages/cli/src/commands/models/accountLoginM365.ts @swatDong @xiaolang124 @kimizhu @HuihuiWu-Microsoft @jayzhang +/packages/cli/src/commands/models/accountLogout.ts @swatDong @xiaolang124 @kimizhu @HuihuiWu-Microsoft @jayzhang +/packages/cli/src/commands/models/accountShow.ts @swatDong @xiaolang124 @kimizhu @HuihuiWu-Microsoft @jayzhang /packages/cli/src/commands/models/add.ts @HuihuiWu-Microsoft @nliu-ms @jayzhang /packages/cli/src/commands/models/addSPFxWebpart.ts @HuihuiWu-Microsoft @yuqizhou77 @nliu-ms @jayzhang /packages/cli/src/commands/models/doctor.ts @swatDong @jayzhang @@ -47,7 +47,7 @@ /packages/cli/src/commands/models/teamsapp @nliu-ms @jayzhang @anchenyi /packages/cli/src/commands/models/upgrade.ts @xzf0587 @blackchoey /packages/cli/src/commands/models/validate.ts @nliu-ms @jayzhang @anchenyi -/packages/cli/src/commonlib @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya +/packages/cli/src/commonlib @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya @HuihuiWu-Microsoft @jayzhang /packages/cli/src/commonlib/appStudioLoginUserPassword.ts @chagong @Alive-Fish /packages/cli/src/commonlib/azureLoginUserPassword.ts @chagong @Alive-Fish /packages/cli/src/commonlib/common/userPasswordConfig.ts @chagong @Alive-Fish @@ -56,7 +56,7 @@ /packages/cli/src/resource/errors.json @timngmsft @sffamily @therealjohn @supkasar /packages/cli/src/resource/strings.json @timngmsft @sffamily @therealjohn @supkasar /packages/cli/tests/unit/cmds/preview @swatDong @kuojianlu @qinezh @a1exwang -/packages/cli/tests/unit/commonlib @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya +/packages/cli/tests/unit/commonlib @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya @HuihuiWu-Microsoft @jayzhang /packages/dotnet-sdk @tecton @JerryYangKai @yiqing-zhao /packages/dotnet-sdk/src/TeamsFx.Test/Conversation @swatDong @dooriya @kimizhu @@ -247,7 +247,7 @@ /packages/simpleauth @blackchoey @wenytang-ms -/packages/spec-parser/ @KennethBWSong @SLdragon +/packages/spec-parser/ @KennethBWSong @SLdragon @adashen /packages/tests/src/e2e/bot @JerryYangKai @eriolchan @Siglud @Yukun-dong /packages/tests/src/e2e/bot/tdpIntegrationTemplates @yuqizhou77 @nliu-ms @@ -271,16 +271,16 @@ /packages/vscode-extension/WHATISNEW.md @therealjohn @sffamily /packages/vscode-extension/package.nls.json @timngmsft @sffamily @therealjohn @supkasar /packages/vscode-extension/src/chat @tecton @Alive-Fish @lijie-lee @1openwindow -/packages/vscode-extension/src/commonlib @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya +/packages/vscode-extension/src/commonlib @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya @HuihuiWu-Microsoft @jayzhang /packages/vscode-extension/src/controls @tecton @yiqing-zhao /packages/vscode-extension/src/debug @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya /packages/vscode-extension/src/debug/officeTaskHandler.ts @swatDong @jayzhang @tecton /packages/vscode-extension/src/debug/taskTerminal/officeDevTerminal.ts @tecton @swatDong /packages/vscode-extension/src/handlers @tecton @jayzhang @yiqing-zhao -/packages/vscode-extension/src/handlers/accounts @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya +/packages/vscode-extension/src/handlers/accounts @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya @HuihuiWu-Microsoft @jayzhang /packages/vscode-extension/src/handlers/aadManifestHandlers.ts @blackchoey @wenytang-ms @KennethBWSong /packages/vscode-extension/src/handlers/collaboratorHandlers.ts @KennethBWSong @SLdragon -/packages/vscode-extension/src/handlers/copilotChatHandlers.ts @yuqizhou77 +/packages/vscode-extension/src/handlers/copilotChatHandlers.ts @yuqizhou77 @Alive-Fish @tecton /packages/vscode-extension/src/handlers/manifestHandlers.ts @nliu-ms @yuqizhou77 @anchenyi /packages/vscode-extension/src/migration @kimizhu @swatDong @kuojianlu @a1exwang @qinezh @XiaofuHuang @xiaolang124 @dooriya /packages/vscode-extension/src/officeChat @1openwindow @MSFT-yiz @@ -329,7 +329,7 @@ /templates/**/non-sso-tab-ssr @Yimin-Jin @eriolchan @hund030 /templates/**/notification-http-timer-trigger @kimizhu @dooriya @swatDong /templates/**/notification-http-trigger @kimizhu @dooriya @swatDong -/templates/**/notification-restify @kimizhu @dooriya @swatDong +/templates/**/notification-express @kimizhu @dooriya @swatDong /templates/**/notification-timer-trigger @kimizhu @dooriya @swatDong /templates/**/notification-webapi @kimizhu @dooriya @swatDong /templates/**/office-addin @jayzhang @tecton diff --git a/.github/workflows/templates-ci.yml b/.github/workflows/templates-ci.yml deleted file mode 100644 index 8ce6ff2718..0000000000 --- a/.github/workflows/templates-ci.yml +++ /dev/null @@ -1,43 +0,0 @@ -name: Template CI - -on: - pull_request: - branches: - - main - - dev - - hotfix/**/* - paths: - - templates/** - push: - branches: - - main - - dev - - hotfix/**/* - paths: - - templates/** - workflow_dispatch: - -jobs: - verify-constraints: - name: verify-constraints - runs-on: ubuntu-latest - - steps: - - name: Checkout - uses: actions/checkout@v3 - - - name: Setup node - uses: actions/setup-node@v3 - with: - node-version: 18 - - - uses: pnpm/action-setup@v4 - - - name: Setup project - run: | - pnpm --filter=templates install - - - name: Verify - run: | - npm run verify - working-directory: ./templates \ No newline at end of file diff --git a/.github/workflows/ui-test.yml b/.github/workflows/ui-test.yml index 838dcdb0c0..93e1651fc9 100644 --- a/.github/workflows/ui-test.yml +++ b/.github/workflows/ui-test.yml @@ -201,6 +201,7 @@ jobs: AZURE_SUBSCRIPTION_NAME: ${{ secrets.TEST_SUBSCRIPTION_NAME }} AZURE_ACCOUNT_NAME: ${{ secrets.TEST_USER_NAME }} AZURE_ACCOUNT_PASSWORD: ${{ secrets.TEST_USER_PASSWORD }} + STORAGE_ACCOUNT_KEY: ${{ secrets.TEST_STORAGE_ACCOUNT_KEY }} AZURE_OPENAI_DEPLOYMENT_NAME: "gpt-4-32k" AZURE_OPENAI_ENDPOINT: "https://aoai-jasozdr.openai.azure.com/" @@ -340,40 +341,13 @@ jobs: name: ttk path: ./packages/tests - - name: Install teamsfx cli (for migration use latest) - if: contains(matrix.test-case, 'upgrade') && contains(matrix.test-case, '4.0.0') == false && contains(matrix.test-case, '3.x') == false - working-directory: packages/tests - run: | - npm install @microsoft/teamsfx-cli@1.2.6 - - - name: Install teamsfx cli (for migration use 1.0.0) - if: contains(matrix.test-case, '4.0.0') - working-directory: packages/tests - run: | - npm install @microsoft/teamsfx-cli@1.0.0 - - - name: Install teamsfx cli (for migration use 0.2.0) - if: contains(matrix.test-case, '3.x') - working-directory: packages/tests - run: | - npm install @microsoft/teamsfx-cli@0.2.0 - - name: Install teamsfx cli - if: contains(matrix.test-case, 'upgrade') == false working-directory: packages/tests run: | npm install @microsoft/teamsapp-cli@${{ needs.setup.outputs.npm-tag }} - - name: Download samples (migration use v1.1.0) - if: contains(matrix.test-case, 'sample-') && contains(matrix.test-case, 'upgrade') - uses: actions/checkout@v3 - with: - repository: OfficeDev/TeamsFx-Samples - ref: v1.1.0 - path: ./packages/tests/resource - - name: Download samples - if: startsWith(matrix.test-case, 'sample-') && contains(matrix.test-case, 'proactive-message') == false && contains(matrix.test-case, 'reddit-link') == false && contains(matrix.test-case, 'upgrade') == false && contains(matrix.test-case, 'chef-bot') == false && contains(matrix.test-case, 'food-catalog') == false && contains(matrix.test-case, 'outlook-signature') == false + if: startsWith(matrix.test-case, 'sample-') && contains(matrix.test-case, 'proactive-message') == false && contains(matrix.test-case, 'reddit-link') == false && contains(matrix.test-case, 'chef-bot') == false && contains(matrix.test-case, 'food-catalog') == false && contains(matrix.test-case, 'outlook-signature') == false uses: actions/checkout@v3 with: repository: OfficeDev/TeamsFx-Samples @@ -381,7 +355,7 @@ jobs: path: ./packages/tests/resource - name: Download samples from another repo - if: (contains(matrix.test-case, 'proactive-message') || contains(matrix.test-case, 'reddit-link')) && contains(matrix.test-case, 'upgrade') == false + if: contains(matrix.test-case, 'proactive-message') || contains(matrix.test-case, 'reddit-link') uses: actions/checkout@v3 with: repository: OfficeDev/Microsoft-Teams-Samples diff --git a/packages/api/src/utils/login.ts b/packages/api/src/utils/login.ts index 0094a273fa..90b64a79ef 100644 --- a/packages/api/src/utils/login.ts +++ b/packages/api/src/utils/login.ts @@ -76,7 +76,11 @@ export interface AzureAccountProvider { * Azure sign out */ signout(): Promise; - + /** + * Switch to specified tenant for current user account + * @param tenantId id of tenant that user wants to switch to + */ + switchTenant(tenantId: string): Promise>; /** * Add update account info callback * @param name callback name @@ -172,6 +176,11 @@ export interface M365TokenProvider { * @param tokenRequest permission scopes or show user interactive UX */ getStatus(tokenRequest: TokenRequest): Promise>; + /** + * Switch to specified tenant for current user account + * @param tenantId id of tenant that user wants to switch to + */ + switchTenant(tenantId: string): Promise>; /** * Add update account info callback * @param name callback name diff --git a/packages/api/tests/login.test.ts b/packages/api/tests/login.test.ts index 2cb6db06d0..3254a3172c 100644 --- a/packages/api/tests/login.test.ts +++ b/packages/api/tests/login.test.ts @@ -20,6 +20,10 @@ class M365Provider extends BasicLogin implements M365TokenProvider { async getStatus(tokenRequest: TokenRequest): Promise> { return ok({ status: "SignedIn" }); } + + async switchTenant(tenantId: string): Promise> { + return ok("fakeToken"); + } } describe("m365Login", function () { diff --git a/packages/cli/package.json b/packages/cli/package.json index 050a941dc3..14b75bf237 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -50,7 +50,7 @@ "@microsoft/metrics-ts": "workspace:*", "@types/chai": "^4.2.14", "@types/chai-as-promised": "^7.1.3", - "@types/express": "^4.17.14", + "@types/express": "^4.17.21", "@types/fs-extra": "^8.0.1", "@types/keytar": "^4.4.2", "@types/lodash": "^4.14.170", @@ -87,20 +87,20 @@ "ts-loader": "^9.2.2", "ts-node": "^9.1.1", "tslib": "^2.3.1", - "typescript": "^4.3.2", + "typescript": "^4.5.5", "umd-compat-loader": "^2.1.2", "url-loader": "^4.1.1", "uuid": "^8.3.2", - "webpack": "^5.38.1", - "webpack-cli": "^4.7.2" + "webpack": "^5.95.0", + "webpack-cli": "^5.1.4" }, "dependencies": { "@azure/arm-subscriptions": "^5.0.0", "@azure/core-auth": "^1.4.0", "@azure/identity": "^4.1.0", "@azure/msal-node": "^2.6.6", - "@inquirer/core": "^5.1.1", - "@inquirer/prompts": "^3.3.0", + "@inquirer/core": "^5.1.2", + "@inquirer/prompts": "^6.0.0", "@inquirer/type": "^1.1.5", "@microsoft/teamsfx-api": "workspace:*", "@microsoft/teamsfx-core": "workspace:*", @@ -110,7 +110,7 @@ "chalk": "^4.1.0", "cli-table3": "^0.6.3", "dotenv": "^8.2.0", - "express": "^4.19.2", + "express": "^4.21.1", "figures": "^3.2.0", "fs-extra": "^9.1.0", "lodash": "^4.17.21", diff --git a/packages/cli/pnpm-lock.yaml b/packages/cli/pnpm-lock.yaml index e3d4afd659..7e32948431 100644 --- a/packages/cli/pnpm-lock.yaml +++ b/packages/cli/pnpm-lock.yaml @@ -18,14 +18,14 @@ dependencies: specifier: ^2.6.6 version: 2.6.6 '@inquirer/core': - specifier: ^5.1.1 - version: 5.1.1 + specifier: ^5.1.2 + version: 5.1.2 '@inquirer/prompts': - specifier: ^3.3.0 - version: 3.3.2 + specifier: ^6.0.0 + version: 6.0.1 '@inquirer/type': specifier: ^1.1.5 - version: 1.1.5 + version: 1.5.5 '@microsoft/teamsfx-api': specifier: workspace:* version: link:../api @@ -51,8 +51,8 @@ dependencies: specifier: ^8.2.0 version: 8.2.0 express: - specifier: ^4.19.2 - version: 4.19.2 + specifier: ^4.21.1 + version: 4.21.1 figures: specifier: ^3.2.0 version: 3.2.0 @@ -95,13 +95,13 @@ devDependencies: version: link:../metrics-ts '@types/chai': specifier: ^4.2.14 - version: 4.2.22 + version: 4.2.14 '@types/chai-as-promised': specifier: ^7.1.3 version: 7.1.3 '@types/express': - specifier: ^4.17.14 - version: 4.17.14 + specifier: ^4.17.21 + version: 4.17.21 '@types/fs-extra': specifier: ^8.0.1 version: 8.0.1 @@ -137,19 +137,19 @@ devDependencies: version: 4.19.0(eslint@7.29.0)(typescript@4.5.5) chai: specifier: ^4.2.0 - version: 4.3.4 + version: 4.2.0 chai-as-promised: specifier: ^7.1.1 - version: 7.1.1(chai@4.3.4) + version: 7.1.1(chai@4.2.0) copy-webpack-plugin: specifier: ^9.0.0 - version: 9.0.0(webpack@5.62.1) + version: 9.0.0(webpack@5.95.0) copyfiles: specifier: ^2.4.1 version: 2.4.1 css-loader: specifier: ^5.2.5 - version: 5.2.5(webpack@5.62.1) + version: 5.2.5(webpack@5.95.0) eslint: specifier: ^7.29.0 version: 7.29.0 @@ -167,7 +167,7 @@ devDependencies: version: 4.0.0(eslint@7.29.0)(prettier@2.4.1) html-webpack-plugin: specifier: ^5.3.1 - version: 5.3.1(webpack@5.62.1) + version: 5.3.1(webpack@5.95.0) lint-staged: specifier: ^10.5.4 version: 10.5.4 @@ -188,7 +188,7 @@ devDependencies: version: 5.0.1 sass-loader: specifier: ^11.1.1 - version: 11.1.1(webpack@5.62.1) + version: 11.1.1(webpack@5.95.0) sinon: specifier: ^9.2.2 version: 9.2.2 @@ -197,13 +197,13 @@ devDependencies: version: 0.5.19 style-loader: specifier: ^2.0.0 - version: 2.0.0(webpack@5.62.1) + version: 2.0.0(webpack@5.95.0) terser-webpack-plugin: specifier: ^5.1.2 - version: 5.1.2(webpack@5.62.1) + version: 5.1.2(webpack@5.95.0) ts-loader: specifier: ^9.2.2 - version: 9.2.2(typescript@4.5.5)(webpack@5.62.1) + version: 9.2.2(typescript@4.5.5)(webpack@5.95.0) ts-node: specifier: ^9.1.1 version: 9.1.1(typescript@4.5.5) @@ -211,37 +211,32 @@ devDependencies: specifier: ^2.3.1 version: 2.3.1 typescript: - specifier: ^4.3.2 + specifier: ^4.5.5 version: 4.5.5 umd-compat-loader: specifier: ^2.1.2 version: 2.1.2 url-loader: specifier: ^4.1.1 - version: 4.1.1(webpack@5.62.1) + version: 4.1.1(webpack@5.95.0) uuid: specifier: ^8.3.2 version: 8.3.2 webpack: - specifier: ^5.38.1 - version: 5.62.1(webpack-cli@4.7.2) + specifier: ^5.95.0 + version: 5.95.0(webpack-cli@5.1.4) webpack-cli: - specifier: ^4.7.2 - version: 4.7.2(webpack@5.62.1) + specifier: ^5.1.4 + version: 5.1.4(webpack@5.95.0) packages: - /@aashutoshrathi/word-wrap@1.2.6: - resolution: {integrity: sha512-1Yjs2SvM8TflER/OD3cOjhWWOZb58A2t7wpE2S9XfBYTiIl+XFhQG2bjy4Pu1I+EAlCNUzRDYDdFwFYUKvXcIA==} - engines: {node: '>=0.10.0'} - dev: true - - /@ampproject/remapping@2.2.1: - resolution: {integrity: sha512-lFMjJTrFL3j7L9yBxwYfCq2k6qqwHyzuUl/XBnif78PWTJYyL/dfowQHWE3sp6U6ZzqWiiIZnpTMO96zhkjwtg==} + /@ampproject/remapping@2.3.0: + resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==} engines: {node: '>=6.0.0'} dependencies: - '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.22 + '@jridgewell/gen-mapping': 0.3.5 + '@jridgewell/trace-mapping': 0.3.25 dev: true /@azure/abort-controller@1.1.0: @@ -255,7 +250,7 @@ packages: resolution: {integrity: sha512-nBrLsEWm4J2u5LpAPjxADTlq3trDgVZZXHNKabeXZtpq3d3AbN/KGO82R87rdDz5/lYB024rtEf10/q0urNgsA==} engines: {node: '>=18.0.0'} dependencies: - tslib: 2.6.2 + tslib: 2.8.0 dev: false /@azure/arm-subscriptions@5.0.0: @@ -264,10 +259,10 @@ packages: dependencies: '@azure/abort-controller': 1.1.0 '@azure/core-auth': 1.4.0 - '@azure/core-client': 1.7.3 - '@azure/core-lro': 2.5.4 - '@azure/core-paging': 1.5.0 - '@azure/core-rest-pipeline': 1.13.0 + '@azure/core-client': 1.9.2 + '@azure/core-lro': 2.7.2 + '@azure/core-paging': 1.6.2 + '@azure/core-rest-pipeline': 1.17.0 tslib: 2.3.1 transitivePeerDependencies: - supports-color @@ -281,76 +276,76 @@ packages: tslib: 2.3.1 dev: false - /@azure/core-auth@1.7.2: - resolution: {integrity: sha512-Igm/S3fDYmnMq1uKS38Ae1/m37B3zigdlZw+kocwEhh5GjyKjPrXKO2J6rzpC1wAxrNil/jX9BJRqBshyjnF3g==} + /@azure/core-auth@1.9.0: + resolution: {integrity: sha512-FPwHpZywuyasDSLMqJ6fhbOK3TqUdviZNF8OqRGA4W5Ewib2lEEZ+pBsYcBa88B2NGO/SEnYPGhyBqNlE8ilSw==} engines: {node: '>=18.0.0'} dependencies: '@azure/abort-controller': 2.1.2 - '@azure/core-util': 1.6.1 - tslib: 2.6.2 + '@azure/core-util': 1.11.0 + tslib: 2.8.0 dev: false - /@azure/core-client@1.7.3: - resolution: {integrity: sha512-kleJ1iUTxcO32Y06dH9Pfi9K4U+Tlb111WXEnbt7R/ne+NLRwppZiTGJuTD5VVoxTMK5NTbEtm5t2vcdNCFe2g==} - engines: {node: '>=14.0.0'} + /@azure/core-client@1.9.2: + resolution: {integrity: sha512-kRdry/rav3fUKHl/aDLd/pDLcB+4pOFwPPTVEExuMyaI5r+JBbMWqRbCY1pn5BniDaU3lRxO9eaQ1AmSMehl/w==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 + '@azure/abort-controller': 2.1.2 '@azure/core-auth': 1.4.0 - '@azure/core-rest-pipeline': 1.13.0 - '@azure/core-tracing': 1.0.1 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - tslib: 2.3.1 + '@azure/core-rest-pipeline': 1.17.0 + '@azure/core-tracing': 1.2.0 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + tslib: 2.8.0 transitivePeerDependencies: - supports-color dev: false - /@azure/core-lro@2.5.4: - resolution: {integrity: sha512-3GJiMVH7/10bulzOKGrrLeG/uCBH/9VtxqaMcB9lIqAeamI/xYQSHJL/KcsLDuH+yTjYpro/u6D/MuRe4dN70Q==} - engines: {node: '>=14.0.0'} + /@azure/core-lro@2.7.2: + resolution: {integrity: sha512-0YIpccoX8m/k00O7mDDMdJpbr6mf1yWo2dfmxt5A8XVZVVMz2SSKaEbMCeJRvgQ0IaSlqhjT47p4hVIRRy90xw==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - tslib: 2.3.1 + '@azure/abort-controller': 2.1.2 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + tslib: 2.8.0 dev: false - /@azure/core-paging@1.5.0: - resolution: {integrity: sha512-zqWdVIt+2Z+3wqxEOGzR5hXFZ8MGKK52x4vFLw8n58pR6ZfKRx3EXYTxTaYxYHc/PexPUTyimcTWFJbji9Z6Iw==} - engines: {node: '>=14.0.0'} + /@azure/core-paging@1.6.2: + resolution: {integrity: sha512-YKWi9YuCU04B55h25cnOYZHxXYtEvQEbKST5vqRga7hWY9ydd3FZHdeQF8pyh+acWZvppw13M/LMGx0LABUVMA==} + engines: {node: '>=18.0.0'} dependencies: - tslib: 2.3.1 + tslib: 2.8.0 dev: false - /@azure/core-rest-pipeline@1.13.0: - resolution: {integrity: sha512-a62aP/wppgmnfIkJLfcB4ssPBcH94WzrzPVJ3tlJt050zX4lfmtnvy95D3igDo3f31StO+9BgPrzvkj4aOxnoA==} + /@azure/core-rest-pipeline@1.17.0: + resolution: {integrity: sha512-62Vv8nC+uPId3j86XJ0WI+sBf0jlqTqPUFCBNrGtlaUeQUIXWV/D8GE5A1d+Qx8H7OQojn2WguC8kChD6v0shA==} engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - '@azure/core-auth': 1.4.0 - '@azure/core-tracing': 1.0.1 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - http-proxy-agent: 5.0.0 - https-proxy-agent: 5.0.1 - tslib: 2.3.1 + '@azure/abort-controller': 2.1.2 + '@azure/core-auth': 1.9.0 + '@azure/core-tracing': 1.2.0 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + http-proxy-agent: 7.0.2 + https-proxy-agent: 7.0.5 + tslib: 2.8.0 transitivePeerDependencies: - supports-color dev: false - /@azure/core-tracing@1.0.1: - resolution: {integrity: sha512-I5CGMoLtX+pI17ZdiFJZgxMJApsK6jjfm85hpgp3oazCdq5Wxgh4wMr7ge/TTWW1B5WBuvIOI1fMU/FrOAMKrw==} - engines: {node: '>=12.0.0'} + /@azure/core-tracing@1.2.0: + resolution: {integrity: sha512-UKTiEJPkWcESPYJz3X5uKRYyOcJD+4nYph+KpfdPRnQJVrZfk0KJgdnaAWKfhsBBtAf/D58Az4AvCJEmWgIBAg==} + engines: {node: '>=18.0.0'} dependencies: - tslib: 2.3.1 + tslib: 2.8.0 dev: false - /@azure/core-util@1.6.1: - resolution: {integrity: sha512-h5taHeySlsV9qxuK64KZxy4iln1BtMYlNt5jbuEFN3UFSAd1EwKg/Gjl5a6tZ/W8t6li3xPnutOx7zbDyXnPmQ==} - engines: {node: '>=16.0.0'} + /@azure/core-util@1.11.0: + resolution: {integrity: sha512-DxOSLua+NdpWoSqULhjDyAZTXFdP/LKkqtYuxxz1SCN289zk3OG8UOpnCQAz/tygyACBtWp/BoO72ptK7msY8g==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - tslib: 2.3.1 + '@azure/abort-controller': 2.1.2 + tslib: 2.8.0 dev: false /@azure/identity@4.1.0: @@ -358,13 +353,13 @@ packages: engines: {node: '>=18.0.0'} dependencies: '@azure/abort-controller': 1.1.0 - '@azure/core-auth': 1.7.2 - '@azure/core-client': 1.7.3 - '@azure/core-rest-pipeline': 1.13.0 - '@azure/core-tracing': 1.0.1 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - '@azure/msal-browser': 3.13.0 + '@azure/core-auth': 1.9.0 + '@azure/core-client': 1.9.2 + '@azure/core-rest-pipeline': 1.17.0 + '@azure/core-tracing': 1.2.0 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + '@azure/msal-browser': 3.26.1 '@azure/msal-node': 2.6.6 events: 3.3.0 jws: 4.0.0 @@ -375,27 +370,27 @@ packages: - supports-color dev: false - /@azure/logger@1.0.4: - resolution: {integrity: sha512-ustrPY8MryhloQj7OWGe+HrYx+aoiOxzbXTtgblbV3xwCqpzUK36phH3XNHQKj3EPonyFUuDTfR3qFhTEAuZEg==} - engines: {node: '>=14.0.0'} + /@azure/logger@1.1.4: + resolution: {integrity: sha512-4IXXzcCdLdlXuCG+8UKEwLA1T1NHqUfanhXYHiQTn+6sfWCZXduqbtXDGceg3Ce5QxTGo7EqmbV6Bi+aqKuClQ==} + engines: {node: '>=18.0.0'} dependencies: - tslib: 2.3.1 + tslib: 2.8.0 dev: false - /@azure/msal-browser@3.13.0: - resolution: {integrity: sha512-fD906nmJei3yE7la6DZTdUtXKvpwzJURkfsiz9747Icv4pit77cegSm6prJTKLQ1fw4iiZzrrWwxnhMLrTf5gQ==} + /@azure/msal-browser@3.26.1: + resolution: {integrity: sha512-y78sr9g61aCAH9fcLO1um+oHFXc1/5Ap88RIsUSuzkm0BHzFnN+PXGaQeuM1h5Qf5dTnWNOd6JqkskkMPAhh7Q==} engines: {node: '>=0.8.0'} dependencies: - '@azure/msal-common': 14.9.0 + '@azure/msal-common': 14.15.0 dev: false - /@azure/msal-common@14.8.1: - resolution: {integrity: sha512-9HfBMDTIgtFFkils+o6gO/aGEoLLuc4z+QLLfhy/T1bTNPiVsX/9CjaBPMZGnMltN/IlMkU5SGGNggGh55p5xA==} + /@azure/msal-common@14.15.0: + resolution: {integrity: sha512-ImAQHxmpMneJ/4S8BRFhjt1MZ3bppmpRPYYNyzeQPeFN288YKbb8TmmISQEbtfkQ1BPASvYZU5doIZOPBAqENQ==} engines: {node: '>=0.8.0'} dev: false - /@azure/msal-common@14.9.0: - resolution: {integrity: sha512-yzBPRlWPnTBeixxLNI3BBIgF5/bHpbhoRVuuDBnYjCyWRavaPUsKAHUDYLqpGkBLDciA6TCc6GOxN4/S3WiSxg==} + /@azure/msal-common@14.8.1: + resolution: {integrity: sha512-9HfBMDTIgtFFkils+o6gO/aGEoLLuc4z+QLLfhy/T1bTNPiVsX/9CjaBPMZGnMltN/IlMkU5SGGNggGh55p5xA==} engines: {node: '>=0.8.0'} dev: false @@ -411,38 +406,39 @@ packages: /@babel/code-frame@7.12.11: resolution: {integrity: sha512-Zt1yodBx1UcyiePMSkWnU4hPqhwq7hGi2nFL1LeA3EUl+q2LQx16MISgJ0+z7dnmgvP9QtIleuETGOiOH1RcIw==} dependencies: - '@babel/highlight': 7.23.4 + '@babel/highlight': 7.25.9 dev: true - /@babel/code-frame@7.23.5: - resolution: {integrity: sha512-CgH3s1a96LipHCmSUmYFPwY7MNx8C3avkq7i4Wl3cfa662ldtUe4VM1TPXX70pfmrlWTb6jLqTYrZyT2ZTJBgA==} + /@babel/code-frame@7.26.0: + resolution: {integrity: sha512-INCKxTtbXtcNbUZ3YXutwMpEleqttcswhAdee7dhuoVrD2cnuc3PqtERBtxkX5nziX9vnBL8WXmSGwv8CuPV6g==} engines: {node: '>=6.9.0'} dependencies: - '@babel/highlight': 7.23.4 - chalk: 2.4.2 + '@babel/helper-validator-identifier': 7.25.9 + js-tokens: 4.0.0 + picocolors: 1.1.1 dev: true - /@babel/compat-data@7.23.5: - resolution: {integrity: sha512-uU27kfDRlhfKl+w1U6vp16IuvSLtjAxdArVXPa9BvLkrr7CYIsxH5adpHObeAGY/41+syctUWOZ140a2Rvkgjw==} + /@babel/compat-data@7.26.0: + resolution: {integrity: sha512-qETICbZSLe7uXv9VE8T/RWOdIE5qqyTucOt4zLYMafj2MRO271VGgLd4RACJMeBO37UPWhXiKMBk7YlJ0fOzQA==} engines: {node: '>=6.9.0'} dev: true - /@babel/core@7.23.7: - resolution: {integrity: sha512-+UpDgowcmqe36d4NwqvKsyPMlOLNGMsfMmQ5WGCu+siCe3t3dfe9njrzGfdN4qq+bcNUt0+Vw6haRxBOycs4dw==} + /@babel/core@7.26.0: + resolution: {integrity: sha512-i1SLeK+DzNnQ3LL/CswPCa/E5u4lh1k6IAEphON8F+cXt0t9euTshDru0q7/IqMa1PMPz5RnHuHscF8/ZJsStg==} engines: {node: '>=6.9.0'} dependencies: - '@ampproject/remapping': 2.2.1 - '@babel/code-frame': 7.23.5 - '@babel/generator': 7.23.6 - '@babel/helper-compilation-targets': 7.23.6 - '@babel/helper-module-transforms': 7.23.3(@babel/core@7.23.7) - '@babel/helpers': 7.23.8 - '@babel/parser': 7.23.6 - '@babel/template': 7.22.15 - '@babel/traverse': 7.23.7 - '@babel/types': 7.23.6 + '@ampproject/remapping': 2.3.0 + '@babel/code-frame': 7.26.0 + '@babel/generator': 7.26.0 + '@babel/helper-compilation-targets': 7.25.9 + '@babel/helper-module-transforms': 7.26.0(@babel/core@7.26.0) + '@babel/helpers': 7.26.0 + '@babel/parser': 7.26.1 + '@babel/template': 7.25.9 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 convert-source-map: 2.0.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 gensync: 1.0.0-beta.2 json5: 2.2.3 semver: 6.3.1 @@ -450,159 +446,123 @@ packages: - supports-color dev: true - /@babel/generator@7.23.6: - resolution: {integrity: sha512-qrSfCYxYQB5owCmGLbl8XRpX1ytXlpueOb0N0UmQwA073KZxejgQTzAmJezxvpwQD9uGtK2shHdi55QT+MbjIw==} + /@babel/generator@7.26.0: + resolution: {integrity: sha512-/AIkAmInnWwgEAJGQr9vY0c66Mj6kjkE2ZPB1PurTRaRAh3U+J45sAQMjQDJdh4WbR3l0x5xkimXBKyBXXAu2w==} engines: {node: '>=6.9.0'} dependencies: - '@babel/types': 7.23.6 - '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.22 - jsesc: 2.5.2 + '@babel/parser': 7.26.1 + '@babel/types': 7.26.0 + '@jridgewell/gen-mapping': 0.3.5 + '@jridgewell/trace-mapping': 0.3.25 + jsesc: 3.0.2 dev: true - /@babel/helper-compilation-targets@7.23.6: - resolution: {integrity: sha512-9JB548GZoQVmzrFgp8o7KxdgkTGm6xs9DW0o/Pim72UDjzr5ObUQ6ZzYPqA+g9OTS2bBQoctLJrky0RDCAWRgQ==} + /@babel/helper-compilation-targets@7.25.9: + resolution: {integrity: sha512-j9Db8Suy6yV/VHa4qzrj9yZfZxhLWQdVnRlXxmKLYlhWUVB1sB2G5sxuWYXk/whHD9iW76PmNzxZ4UCnTQTVEQ==} engines: {node: '>=6.9.0'} dependencies: - '@babel/compat-data': 7.23.5 - '@babel/helper-validator-option': 7.23.5 - browserslist: 4.22.2 + '@babel/compat-data': 7.26.0 + '@babel/helper-validator-option': 7.25.9 + browserslist: 4.24.2 lru-cache: 5.1.1 semver: 6.3.1 dev: true - /@babel/helper-environment-visitor@7.22.20: - resolution: {integrity: sha512-zfedSIzFhat/gFhWfHtgWvlec0nqB9YEIVrpuwjruLlXfUSnA8cJB0miHKwqDnQ7d32aKo2xt88/xZptwxbfhA==} - engines: {node: '>=6.9.0'} - dev: true - - /@babel/helper-function-name@7.23.0: - resolution: {integrity: sha512-OErEqsrxjZTJciZ4Oo+eoZqeW9UIiOcuYKRJA4ZAgV9myA+pOXhhmpfNCKjEH/auVfEYVFJ6y1Tc4r0eIApqiw==} + /@babel/helper-module-imports@7.25.9: + resolution: {integrity: sha512-tnUA4RsrmflIM6W6RFTLFSXITtl0wKjgpnLgXyowocVPrbYrLUXSBXDgTs8BlbmIzIdlBySRQjINYs2BAkiLtw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/template': 7.22.15 - '@babel/types': 7.23.6 - dev: true - - /@babel/helper-hoist-variables@7.22.5: - resolution: {integrity: sha512-wGjk9QZVzvknA6yKIUURb8zY3grXCcOZt+/7Wcy8O2uctxhplmUPkOdlgoNhmdVee2c92JXbf1xpMtVNbfoxRw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 - dev: true - - /@babel/helper-module-imports@7.22.15: - resolution: {integrity: sha512-0pYVBnDKZO2fnSPCrgM/6WMc7eS20Fbok+0r88fp+YtWVLZrp4CkafFGIp+W0VKw4a22sgebPT99y+FDNMdP4w==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 + transitivePeerDependencies: + - supports-color dev: true - /@babel/helper-module-transforms@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-7bBs4ED9OmswdfDzpz4MpWgSrV7FXlc3zIagvLFjS5H+Mk7Snr21vQ6QwrsoCGMfNC4e4LQPdoULEt4ykz0SRQ==} + /@babel/helper-module-transforms@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-xO+xu6B5K2czEnQye6BHA7DolFFmS3LB7stHZFaOLb1pAwO1HWLS8fXA+eh0A2yIvltPVmx3eNNDBJA2SLHXFw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-module-imports': 7.22.15 - '@babel/helper-simple-access': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/helper-validator-identifier': 7.22.20 - dev: true - - /@babel/helper-simple-access@7.22.5: - resolution: {integrity: sha512-n0H99E/K+Bika3++WNL17POvo4rKWZ7lZEp1Q+fStVbUi8nxPQEBOlTmCOxW/0JsS56SKKQ+ojAe2pHKJHN35w==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 - dev: true - - /@babel/helper-split-export-declaration@7.22.6: - resolution: {integrity: sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 + '@babel/core': 7.26.0 + '@babel/helper-module-imports': 7.25.9 + '@babel/helper-validator-identifier': 7.25.9 + '@babel/traverse': 7.25.9 + transitivePeerDependencies: + - supports-color dev: true - /@babel/helper-string-parser@7.23.4: - resolution: {integrity: sha512-803gmbQdqwdf4olxrX4AJyFBV/RTr3rSmOj0rKwesmzlfhYNDEs+/iOcznzpNWlJlIlTJC2QfPFcHB6DlzdVLQ==} + /@babel/helper-string-parser@7.25.9: + resolution: {integrity: sha512-4A/SCr/2KLd5jrtOMFzaKjVtAei3+2r/NChoBNoZ3EyP/+GlhoaEGoWOZUmFmoITP7zOJyHIMm+DYRd8o3PvHA==} engines: {node: '>=6.9.0'} dev: true - /@babel/helper-validator-identifier@7.22.20: - resolution: {integrity: sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A==} + /@babel/helper-validator-identifier@7.25.9: + resolution: {integrity: sha512-Ed61U6XJc3CVRfkERJWDz4dJwKe7iLmmJsbOGu9wSloNSFttHV0I8g6UAgb7qnK5ly5bGLPd4oXZlxCdANBOWQ==} engines: {node: '>=6.9.0'} dev: true - /@babel/helper-validator-option@7.23.5: - resolution: {integrity: sha512-85ttAOMLsr53VgXkTbkx8oA6YTfT4q7/HzXSLEYmjcSTJPMPQtvq1BD79Byep5xMUYbGRzEpDsjUf3dyp54IKw==} + /@babel/helper-validator-option@7.25.9: + resolution: {integrity: sha512-e/zv1co8pp55dNdEcCynfj9X7nyUKUXoUEwfXqaZt0omVOmDe9oOTdKStH4GmAw6zxMFs50ZayuMfHDKlO7Tfw==} engines: {node: '>=6.9.0'} dev: true - /@babel/helpers@7.23.8: - resolution: {integrity: sha512-KDqYz4PiOWvDFrdHLPhKtCThtIcKVy6avWD2oG4GEvyQ+XDZwHD4YQd+H2vNMnq2rkdxsDkU82T+Vk8U/WXHRQ==} + /@babel/helpers@7.26.0: + resolution: {integrity: sha512-tbhNuIxNcVb21pInl3ZSjksLCvgdZy9KwJ8brv993QtIVKJBBkYXz4q4ZbAv31GdnC+R90np23L5FbEBlthAEw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/template': 7.22.15 - '@babel/traverse': 7.23.7 - '@babel/types': 7.23.6 - transitivePeerDependencies: - - supports-color + '@babel/template': 7.25.9 + '@babel/types': 7.26.0 dev: true - /@babel/highlight@7.23.4: - resolution: {integrity: sha512-acGdbYSfp2WheJoJm/EBBBLh/ID8KDc64ISZ9DYtBmC8/Q204PZJLHyzeB5qMzJ5trcOkybd78M4x2KWsUq++A==} + /@babel/highlight@7.25.9: + resolution: {integrity: sha512-llL88JShoCsth8fF8R4SJnIn+WLvR6ccFxu1H3FlMhDontdcmZWf2HgIZ7AIqV3Xcck1idlohrN4EUBQz6klbw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/helper-validator-identifier': 7.22.20 + '@babel/helper-validator-identifier': 7.25.9 chalk: 2.4.2 js-tokens: 4.0.0 + picocolors: 1.1.1 dev: true - /@babel/parser@7.23.6: - resolution: {integrity: sha512-Z2uID7YJ7oNvAI20O9X0bblw7Qqs8Q2hFy0R9tAfnfLkp5MW0UH9eUvnDSnFwKZ0AvgS1ucqR4KzvVHgnke1VQ==} + /@babel/parser@7.26.1: + resolution: {integrity: sha512-reoQYNiAJreZNsJzyrDNzFQ+IQ5JFiIzAHJg9bn94S3l+4++J7RsIhNMoB+lgP/9tpmiAQqspv+xfdxTSzREOw==} engines: {node: '>=6.0.0'} hasBin: true dependencies: - '@babel/types': 7.23.6 + '@babel/types': 7.26.0 dev: true - /@babel/template@7.22.15: - resolution: {integrity: sha512-QPErUVm4uyJa60rkI73qneDacvdvzxshT3kksGqlGWYdOTIUOwJ7RDUL8sGqslY1uXWSL6xMFKEXDS3ox2uF0w==} + /@babel/template@7.25.9: + resolution: {integrity: sha512-9DGttpmPvIxBb/2uwpVo3dqJ+O6RooAFOS+lB+xDqoE2PVCE8nfoHMdZLpfCQRLwvohzXISPZcgxt80xLfsuwg==} engines: {node: '>=6.9.0'} dependencies: - '@babel/code-frame': 7.23.5 - '@babel/parser': 7.23.6 - '@babel/types': 7.23.6 + '@babel/code-frame': 7.26.0 + '@babel/parser': 7.26.1 + '@babel/types': 7.26.0 dev: true - /@babel/traverse@7.23.7: - resolution: {integrity: sha512-tY3mM8rH9jM0YHFGyfC0/xf+SB5eKUu7HPj7/k3fpi9dAlsMc5YbQvDi0Sh2QTPXqMhyaAtzAr807TIyfQrmyg==} + /@babel/traverse@7.25.9: + resolution: {integrity: sha512-ZCuvfwOwlz/bawvAuvcj8rrithP2/N55Tzz342AkTvq4qaWbGfmCk/tKhNaV2cthijKrPAA8SRJV5WWe7IBMJw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/code-frame': 7.23.5 - '@babel/generator': 7.23.6 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-function-name': 7.23.0 - '@babel/helper-hoist-variables': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/parser': 7.23.6 - '@babel/types': 7.23.6 - debug: 4.3.4(supports-color@8.1.1) + '@babel/code-frame': 7.26.0 + '@babel/generator': 7.26.0 + '@babel/parser': 7.26.1 + '@babel/template': 7.25.9 + '@babel/types': 7.26.0 + debug: 4.3.7 globals: 11.12.0 transitivePeerDependencies: - supports-color dev: true - /@babel/types@7.23.6: - resolution: {integrity: sha512-+uarb83brBzPKN38NX1MkB6vb6+mwvR6amUulqAE7ccQw1pEl+bCia9TbdG1lsnFP7lZySvUn37CHyXQdfTwzg==} + /@babel/types@7.26.0: + resolution: {integrity: sha512-Z/yiTPj+lDVnF7lWeKCIJzaIkI0vYO87dMpZ4bg4TDrFe4XXLFWL1TbXU27gBP3QccxV9mZICCrnjnYlJjXHOA==} engines: {node: '>=6.9.0'} dependencies: - '@babel/helper-string-parser': 7.23.4 - '@babel/helper-validator-identifier': 7.22.20 - to-fast-properties: 2.0.0 + '@babel/helper-string-parser': 7.25.9 + '@babel/helper-validator-identifier': 7.25.9 dev: true /@colors/colors@1.5.0: @@ -622,7 +582,7 @@ packages: engines: {node: ^10.12.0 || >=12.0.0} dependencies: ajv: 6.12.6 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 espree: 7.3.1 globals: 13.24.0 ignore: 4.0.6 @@ -634,33 +594,32 @@ packages: - supports-color dev: true - /@inquirer/checkbox@1.5.2: - resolution: {integrity: sha512-CifrkgQjDkUkWexmgYYNyB5603HhTHI91vLFeQXh6qrTKiCMVASol01Rs1cv6LP/A2WccZSRlJKZhbaBIs/9ZA==} - engines: {node: '>=14.18.0'} + /@inquirer/checkbox@3.0.1: + resolution: {integrity: sha512-0hm2nrToWUdD6/UHnel/UKGdk1//ke5zGUpHIvk5ZWmaKezlGxZkOJXNSWsdxO/rEqTkbB3lNC2J6nBElV2aAQ==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 + '@inquirer/core': 9.2.1 + '@inquirer/figures': 1.0.7 + '@inquirer/type': 2.0.0 ansi-escapes: 4.3.2 - chalk: 4.1.2 - figures: 3.2.0 + yoctocolors-cjs: 2.1.2 dev: false - /@inquirer/confirm@2.0.17: - resolution: {integrity: sha512-EqzhGryzmGpy2aJf6LxJVhndxYmFs+m8cxXzf8nejb1DE3sabf6mUgBcp4J0jAUEiAcYzqmkqRr7LPFh/WdnXA==} - engines: {node: '>=14.18.0'} + /@inquirer/confirm@4.0.1: + resolution: {integrity: sha512-46yL28o2NJ9doViqOy0VDcoTzng7rAb6yPQKU7VDLqkmbCaH4JqK4yk4XqlzNWy9PVC5pG1ZUXPBQv+VqnYs2w==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 - chalk: 4.1.2 + '@inquirer/core': 9.2.1 + '@inquirer/type': 2.0.0 dev: false - /@inquirer/core@5.1.1: - resolution: {integrity: sha512-IuJyZQUg75+L5AmopgnzxYrgcU6PJKL0hoIs332G1Gv55CnmZrhG6BzNOeZ5sOsTi1YCGOopw4rYICv74ejMFg==} + /@inquirer/core@5.1.2: + resolution: {integrity: sha512-w3PMZH5rahrukn8/I7P9Ihil+twgLTUHDZtJlJyBbUKyPaOSSQjLZkb0PpncVhin1gCaMgOFXy6iNPgcZUoo2w==} engines: {node: '>=14.18.0'} dependencies: - '@inquirer/type': 1.1.5 + '@inquirer/type': 1.5.5 '@types/mute-stream': 0.0.4 - '@types/node': 20.11.6 + '@types/node': 20.17.2 '@types/wrap-ansi': 3.0.0 ansi-escapes: 4.3.2 chalk: 4.1.2 @@ -674,119 +633,141 @@ packages: wrap-ansi: 6.2.0 dev: false - /@inquirer/core@6.0.0: - resolution: {integrity: sha512-fKi63Khkisgda3ohnskNf5uZJj+zXOaBvOllHsOkdsXRA/ubQLJQrZchFFi57NKbZzkTunXiBMdvWOv71alonw==} - engines: {node: '>=14.18.0'} + /@inquirer/core@9.2.1: + resolution: {integrity: sha512-F2VBt7W/mwqEU4bL0RnHNZmC/OxzNx9cOYxHqnXX3MP6ruYvZUZAW9imgN9+h/uBT/oP8Gh888J2OZSbjSeWcg==} + engines: {node: '>=18'} dependencies: - '@inquirer/type': 1.2.1 + '@inquirer/figures': 1.0.7 + '@inquirer/type': 2.0.0 '@types/mute-stream': 0.0.4 - '@types/node': 20.11.28 + '@types/node': 20.17.2 '@types/wrap-ansi': 3.0.0 ansi-escapes: 4.3.2 - chalk: 4.1.2 - cli-spinners: 2.9.2 cli-width: 4.1.0 - figures: 3.2.0 mute-stream: 1.0.0 - run-async: 3.0.0 signal-exit: 4.1.0 strip-ansi: 6.0.1 wrap-ansi: 6.2.0 + yoctocolors-cjs: 2.1.2 dev: false - /@inquirer/editor@1.2.15: - resolution: {integrity: sha512-gQ77Ls09x5vKLVNMH9q/7xvYPT6sIs5f7URksw+a2iJZ0j48tVS6crLqm2ugG33tgXHIwiEqkytY60Zyh5GkJQ==} - engines: {node: '>=14.18.0'} + /@inquirer/editor@3.0.1: + resolution: {integrity: sha512-VA96GPFaSOVudjKFraokEEmUQg/Lub6OXvbIEZU1SDCmBzRkHGhxoFAVaF30nyiB4m5cEbDgiI2QRacXZ2hw9Q==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 - chalk: 4.1.2 + '@inquirer/core': 9.2.1 + '@inquirer/type': 2.0.0 external-editor: 3.1.0 dev: false - /@inquirer/expand@1.1.16: - resolution: {integrity: sha512-TGLU9egcuo+s7PxphKUCnJnpCIVY32/EwPCLLuu+gTvYiD8hZgx8Z2niNQD36sa6xcfpdLY6xXDBiL/+g1r2XQ==} - engines: {node: '>=14.18.0'} + /@inquirer/expand@3.0.1: + resolution: {integrity: sha512-ToG8d6RIbnVpbdPdiN7BCxZGiHOTomOX94C2FaT5KOHupV40tKEDozp12res6cMIfRKrXLJyexAZhWVHgbALSQ==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 - chalk: 4.1.2 - figures: 3.2.0 + '@inquirer/core': 9.2.1 + '@inquirer/type': 2.0.0 + yoctocolors-cjs: 2.1.2 dev: false - /@inquirer/input@1.2.16: - resolution: {integrity: sha512-Ou0LaSWvj1ni+egnyQ+NBtfM1885UwhRCMtsRt2bBO47DoC1dwtCa+ZUNgrxlnCHHF0IXsbQHYtIIjFGAavI4g==} - engines: {node: '>=14.18.0'} + /@inquirer/figures@1.0.7: + resolution: {integrity: sha512-m+Trk77mp54Zma6xLkLuY+mvanPxlE4A7yNKs2HBiyZ4UkVs28Mv5c/pgWrHeInx+USHeX/WEPzjrWrcJiQgjw==} + engines: {node: '>=18'} + dev: false + + /@inquirer/input@3.0.1: + resolution: {integrity: sha512-BDuPBmpvi8eMCxqC5iacloWqv+5tQSJlUafYWUe31ow1BVXjW2a5qe3dh4X/Z25Wp22RwvcaLCc2siHobEOfzg==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 - chalk: 4.1.2 + '@inquirer/core': 9.2.1 + '@inquirer/type': 2.0.0 dev: false - /@inquirer/password@1.1.16: - resolution: {integrity: sha512-aZYZVHLUXZ2gbBot+i+zOJrks1WaiI95lvZCn1sKfcw6MtSSlYC8uDX8sTzQvAsQ8epHoP84UNvAIT0KVGOGqw==} - engines: {node: '>=14.18.0'} + /@inquirer/number@2.0.1: + resolution: {integrity: sha512-QpR8jPhRjSmlr/mD2cw3IR8HRO7lSVOnqUvQa8scv1Lsr3xoAMMworcYW3J13z3ppjBFBD2ef1Ci6AE5Qn8goQ==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 + '@inquirer/core': 9.2.1 + '@inquirer/type': 2.0.0 + dev: false + + /@inquirer/password@3.0.1: + resolution: {integrity: sha512-haoeEPUisD1NeE2IanLOiFr4wcTXGWrBOyAyPZi1FfLJuXOzNmxCJPgUrGYKVh+Y8hfGJenIfz5Wb/DkE9KkMQ==} + engines: {node: '>=18'} + dependencies: + '@inquirer/core': 9.2.1 + '@inquirer/type': 2.0.0 ansi-escapes: 4.3.2 - chalk: 4.1.2 dev: false - /@inquirer/prompts@3.3.2: - resolution: {integrity: sha512-k52mOMRvTUejrqyF1h8Z07chC+sbaoaUYzzr1KrJXyj7yaX7Nrh0a9vktv8TuocRwIJOQMaj5oZEmkspEcJFYQ==} - engines: {node: '>=14.18.0'} + /@inquirer/prompts@6.0.1: + resolution: {integrity: sha512-yl43JD/86CIj3Mz5mvvLJqAOfIup7ncxfJ0Btnl0/v5TouVUyeEdcpknfgc+yMevS/48oH9WAkkw93m7otLb/A==} + engines: {node: '>=18'} dependencies: - '@inquirer/checkbox': 1.5.2 - '@inquirer/confirm': 2.0.17 - '@inquirer/core': 6.0.0 - '@inquirer/editor': 1.2.15 - '@inquirer/expand': 1.1.16 - '@inquirer/input': 1.2.16 - '@inquirer/password': 1.1.16 - '@inquirer/rawlist': 1.2.16 - '@inquirer/select': 1.3.3 + '@inquirer/checkbox': 3.0.1 + '@inquirer/confirm': 4.0.1 + '@inquirer/editor': 3.0.1 + '@inquirer/expand': 3.0.1 + '@inquirer/input': 3.0.1 + '@inquirer/number': 2.0.1 + '@inquirer/password': 3.0.1 + '@inquirer/rawlist': 3.0.1 + '@inquirer/search': 2.0.1 + '@inquirer/select': 3.0.1 dev: false - /@inquirer/rawlist@1.2.16: - resolution: {integrity: sha512-pZ6TRg2qMwZAOZAV6TvghCtkr53dGnK29GMNQ3vMZXSNguvGqtOVc4j/h1T8kqGJFagjyfBZhUPGwNS55O5qPQ==} - engines: {node: '>=14.18.0'} + /@inquirer/rawlist@3.0.1: + resolution: {integrity: sha512-VgRtFIwZInUzTiPLSfDXK5jLrnpkuSOh1ctfaoygKAdPqjcjKYmGh6sCY1pb0aGnCGsmhUxoqLDUAU0ud+lGXQ==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 - chalk: 4.1.2 + '@inquirer/core': 9.2.1 + '@inquirer/type': 2.0.0 + yoctocolors-cjs: 2.1.2 dev: false - /@inquirer/select@1.3.3: - resolution: {integrity: sha512-RzlRISXWqIKEf83FDC9ZtJ3JvuK1l7aGpretf41BCWYrvla2wU8W8MTRNMiPrPJ+1SIqrRC1nZdZ60hD9hRXLg==} - engines: {node: '>=14.18.0'} + /@inquirer/search@2.0.1: + resolution: {integrity: sha512-r5hBKZk3g5MkIzLVoSgE4evypGqtOannnB3PKTG9NRZxyFRKcfzrdxXXPcoJQsxJPzvdSU2Rn7pB7lw0GCmGAg==} + engines: {node: '>=18'} dependencies: - '@inquirer/core': 6.0.0 - '@inquirer/type': 1.2.1 + '@inquirer/core': 9.2.1 + '@inquirer/figures': 1.0.7 + '@inquirer/type': 2.0.0 + yoctocolors-cjs: 2.1.2 + dev: false + + /@inquirer/select@3.0.1: + resolution: {integrity: sha512-lUDGUxPhdWMkN/fHy1Lk7pF3nK1fh/gqeyWXmctefhxLYxlDsc7vsPBEpxrfVGDsVdyYJsiJoD4bJ1b623cV1Q==} + engines: {node: '>=18'} + dependencies: + '@inquirer/core': 9.2.1 + '@inquirer/figures': 1.0.7 + '@inquirer/type': 2.0.0 ansi-escapes: 4.3.2 - chalk: 4.1.2 - figures: 3.2.0 + yoctocolors-cjs: 2.1.2 dev: false /@inquirer/testing@2.1.2: resolution: {integrity: sha512-k9SXDwfvlYvU2jFC77R8ZoA+/pRQsDUKZ0DCrXMEnPUFe92qwQ9pkGkd5gGh5Kt0hS5+fcjZ6Q38vFrCYQAVHg==} engines: {node: '>=14.18.0'} dependencies: - '@inquirer/type': 1.1.5 + '@inquirer/type': 1.5.5 '@types/mute-stream': 0.0.1 - '@types/node': 20.11.6 + '@types/node': 20.17.2 ansi-escapes: 4.3.2 mute-stream: 1.0.0 strip-ansi: 6.0.1 dev: true - /@inquirer/type@1.1.5: - resolution: {integrity: sha512-wmwHvHozpPo4IZkkNtbYenem/0wnfI6hvOcGKmPEa0DwuaH5XUQzFqy6OpEpjEegZMhYIk8HDYITI16BPLtrRA==} - engines: {node: '>=14.18.0'} + /@inquirer/type@1.5.5: + resolution: {integrity: sha512-MzICLu4yS7V8AA61sANROZ9vT1H3ooca5dSmI1FjZkzq7o/koMsRfQSzRtFo+F3Ao4Sf1C0bpLKejpKB/+j6MA==} + engines: {node: '>=18'} + dependencies: + mute-stream: 1.0.0 - /@inquirer/type@1.2.1: - resolution: {integrity: sha512-xwMfkPAxeo8Ji/IxfUSqzRi0/+F2GIqJmpc5/thelgMGsjNZcjDDRBO9TLXT1s/hdx/mK5QbVIvgoLIFgXhTMQ==} + /@inquirer/type@2.0.0: + resolution: {integrity: sha512-XvJRx+2KR3YXyYtPUUy+qd9i7p+GO9Ko6VIIpWlBrpWwXDv8WLFeHTxz35CfQFUiBMLXlGHhGzys7lqit9gWag==} engines: {node: '>=18'} + dependencies: + mute-stream: 1.0.0 dev: false /@isaacs/cliui@8.0.2: @@ -831,41 +812,41 @@ packages: engines: {node: '>=8'} dev: true - /@jridgewell/gen-mapping@0.3.3: - resolution: {integrity: sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==} + /@jridgewell/gen-mapping@0.3.5: + resolution: {integrity: sha512-IzL8ZoEDIBRWEzlCcRhOaCupYyN5gdIK+Q6fbFdPDg6HqX6jpkItn7DFIpW9LQzXG6Df9sA7+OKnq0qlz/GaQg==} engines: {node: '>=6.0.0'} dependencies: - '@jridgewell/set-array': 1.1.2 - '@jridgewell/sourcemap-codec': 1.4.15 - '@jridgewell/trace-mapping': 0.3.22 + '@jridgewell/set-array': 1.2.1 + '@jridgewell/sourcemap-codec': 1.5.0 + '@jridgewell/trace-mapping': 0.3.25 dev: true - /@jridgewell/resolve-uri@3.1.1: - resolution: {integrity: sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA==} + /@jridgewell/resolve-uri@3.1.2: + resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} engines: {node: '>=6.0.0'} dev: true - /@jridgewell/set-array@1.1.2: - resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==} + /@jridgewell/set-array@1.2.1: + resolution: {integrity: sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==} engines: {node: '>=6.0.0'} dev: true - /@jridgewell/source-map@0.3.5: - resolution: {integrity: sha512-UTYAUj/wviwdsMfzoSJspJxbkH5o1snzwX0//0ENX1u/55kkZZkcTZP6u9bwKGkv+dkk9at4m1Cpt0uY80kcpQ==} + /@jridgewell/source-map@0.3.6: + resolution: {integrity: sha512-1ZJTZebgqllO79ue2bm3rIGud/bOe0pP5BjSRCRxxYkEZS8STV7zN84UBbiYu7jy+eCKSnVIUgoWWE/tt+shMQ==} dependencies: - '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.22 + '@jridgewell/gen-mapping': 0.3.5 + '@jridgewell/trace-mapping': 0.3.25 dev: true - /@jridgewell/sourcemap-codec@1.4.15: - resolution: {integrity: sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==} + /@jridgewell/sourcemap-codec@1.5.0: + resolution: {integrity: sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==} dev: true - /@jridgewell/trace-mapping@0.3.22: - resolution: {integrity: sha512-Wf963MzWtA2sjrNt+g18IAln9lKnlRp+K2eH4jjIoF1wYeq3aMREpG09xhlhdzS0EjwU7qmUJYangWa+151vZw==} + /@jridgewell/trace-mapping@0.3.25: + resolution: {integrity: sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==} dependencies: - '@jridgewell/resolve-uri': 3.1.1 - '@jridgewell/sourcemap-codec': 1.4.15 + '@jridgewell/resolve-uri': 3.1.2 + '@jridgewell/sourcemap-codec': 1.5.0 dev: true /@nodelib/fs.scandir@2.1.5: @@ -886,7 +867,7 @@ packages: engines: {node: '>= 8'} dependencies: '@nodelib/fs.scandir': 2.1.5 - fastq: 1.16.0 + fastq: 1.17.1 dev: true /@pkgjs/parseargs@0.11.0: @@ -920,18 +901,13 @@ packages: dependencies: '@sinonjs/commons': 1.8.6 lodash.get: 4.4.2 - type-detect: 4.0.8 + type-detect: 4.1.0 dev: true - /@sinonjs/text-encoding@0.7.2: - resolution: {integrity: sha512-sXXKG+uL9IrKqViTtao2Ws6dy0znu9sOaP1di/jKGW1M6VssO8vlpXCQcpZ+jisQ1tTFAC5Jo/EOzFbggBagFQ==} + /@sinonjs/text-encoding@0.7.3: + resolution: {integrity: sha512-DE427ROAphMQzU4ENbliGYrBSYPXF+TtLg9S8vzeA+OF4ZKzoDdzfL8sxuMUGS/lgRhM6j1URSk9ghf7Xo1tyA==} dev: true - /@tootallnate/once@2.0.0: - resolution: {integrity: sha512-XCuKFP5PS55gnMVu3dty8KPatLqUoy/ZYzDzAGCQ8JNFCkLXzmI7vNHCR+XpbZaMWQK/vQubr7PkYq8g470J/A==} - engines: {node: '>= 10'} - dev: false - /@types/body-parser@1.19.5: resolution: {integrity: sha512-fB3Zu92ucau0iQ0JMCFQE7b/dv8Ot07NI3KaZIkIUNXq82k4eBAqUaneXfleGY9JWskeS9y+u0nXMyspcuQrCg==} dependencies: @@ -942,11 +918,11 @@ packages: /@types/chai-as-promised@7.1.3: resolution: {integrity: sha512-FQnh1ohPXJELpKhzjuDkPLR2BZCAqed+a6xV4MI/T3XzHfd2FlarfUGUdZYgqYe8oxkYn0fchHEeHfHqdZ96sg==} dependencies: - '@types/chai': 4.2.22 + '@types/chai': 4.2.14 dev: true - /@types/chai@4.2.22: - resolution: {integrity: sha512-tFfcE+DSTzWAgifkjik9AySNqIyNoYwmR+uecPwwD/XRNfvOjmC/FjCxpiUGDkDVDphPfCUecSQVFw+lN3M3kQ==} + /@types/chai@4.2.14: + resolution: {integrity: sha512-G+ITQPXkwTrslfG5L/BksmbLUA0M1iybEsmCWPqzSxsRRhJZimBKJkoMi8fr/CPygPTj4zO5pJH7I2/cm9M7SQ==} dev: true /@types/connect@3.4.38: @@ -955,40 +931,26 @@ packages: '@types/node': 14.14.21 dev: true - /@types/eslint-scope@3.7.7: - resolution: {integrity: sha512-MzMFlSLBqNF2gcHWO0G1vP/YQyfvrxZ0bF+u7mzUdZ1/xK4A4sru+nraZz5i3iEIk1l1uyicaDVTB4QbbEkAYg==} - dependencies: - '@types/eslint': 8.56.2 - '@types/estree': 0.0.50 - dev: true - - /@types/eslint@8.56.2: - resolution: {integrity: sha512-uQDwm1wFHmbBbCZCqAlq6Do9LYwByNZHWzXppSnay9SuwJ+VRbjkbLABer54kcPnMSlG6Fdiy2yaFXm/z9Z5gw==} - dependencies: - '@types/estree': 0.0.50 - '@types/json-schema': 7.0.15 - dev: true - - /@types/estree@0.0.50: - resolution: {integrity: sha512-C6N5s2ZFtuZRj54k2/zyRhNDjJwwcViAM3Nbm8zjBpbqAdZ00mr0CFxvSKeO8Y/e03WVFLpQMdHYVfUd6SB+Hw==} + /@types/estree@1.0.6: + resolution: {integrity: sha512-AYnb1nQyY49te+VRAVgmzfcgjYS91mY5P0TKUDCLEM+gNnA+3T6rWITXRLYCpahpqSQbN5cE+gHpnPyXjHWxcw==} dev: true - /@types/express-serve-static-core@4.17.41: - resolution: {integrity: sha512-OaJ7XLaelTgrvlZD8/aa0vvvxZdUmlCn6MtWeB7TkiKW70BQLc9XEPpDLPdbo52ZhXUCrznlWdCHWxJWtdyajA==} + /@types/express-serve-static-core@4.19.6: + resolution: {integrity: sha512-N4LZ2xG7DatVqhCZzOGb1Yi5lMbXSZcmdLDe9EzSndPV2HpWYWzRbaerl2n27irrm94EPpprqa8KpskPT085+A==} dependencies: '@types/node': 14.14.21 - '@types/qs': 6.9.11 + '@types/qs': 6.9.16 '@types/range-parser': 1.2.7 '@types/send': 0.17.4 dev: true - /@types/express@4.17.14: - resolution: {integrity: sha512-TEbt+vaPFQ+xpxFLFssxUDXj5cWCxZJjIcB7Yg0k0GMHGtgtQgpvx/MUQUeAkNbA9AAGrwkAsoeItdTgS7FMyg==} + /@types/express@4.17.21: + resolution: {integrity: sha512-ejlPM315qwLpaQlQDTjPdsUFSc6ZsP4AN6AlWnogPjQ7CVi7PYF3YVz+CY3jE2pwYf7E/7HlDAN0rV2GxTG0HQ==} dependencies: '@types/body-parser': 1.19.5 - '@types/express-serve-static-core': 4.17.41 - '@types/qs': 6.9.11 - '@types/serve-static': 1.15.5 + '@types/express-serve-static-core': 4.19.6 + '@types/qs': 6.9.16 + '@types/serve-static': 1.15.7 dev: true /@types/fs-extra@8.0.1: @@ -1028,10 +990,6 @@ packages: resolution: {integrity: sha512-/pyBZWSLD2n0dcHE3hq8s8ZvcETHtEuF+3E7XVt0Ig2nvsVQXdghHVcEkIWjy9A0wKfTn97a/PSDYohKIlnP/w==} dev: true - /@types/mime@3.0.4: - resolution: {integrity: sha512-iJt33IQnVRkqeqC7PzBHPTC6fDlRNRW8vjrgqtScAhrmMwe8c4Eo7+fUGTa+XdWrpEgpyKWMYmi2dIwMAYRzPw==} - dev: true - /@types/mocha@8.0.4: resolution: {integrity: sha512-M4BwiTJjHmLq6kjON7ZoI2JMlBvpY3BYSdiP6s/qCT3jb1s9/DeJF0JELpAxiVSIxXDzfNKe+r7yedMIoLbknQ==} dev: true @@ -1051,23 +1009,23 @@ packages: /@types/node@14.14.21: resolution: {integrity: sha512-cHYfKsnwllYhjOzuC5q1VpguABBeecUp24yFluHpn/BQaVxB1CuQ1FSRZCzrPxrkIfWISXV2LbeoBthLWg0+0A==} - /@types/node@20.11.28: - resolution: {integrity: sha512-M/GPWVS2wLkSkNHVeLkrF2fD5Lx5UC4PxA0uZcKc6QqbIQUJyW1jVjueJYi1z8n0I5PxYrtpnPnWglE+y9A0KA==} + /@types/node@20.17.2: + resolution: {integrity: sha512-OOHK4sjXqkL7yQ7VEEHcf6+0jSvKjWqwnaCtY7AKD/VLEvRHMsxxu7eI8ErnjxHS8VwmekD4PeVCpu4qZEZSxg==} dependencies: - undici-types: 5.26.5 - dev: false + undici-types: 6.19.8 - /@types/node@20.11.6: - resolution: {integrity: sha512-+EOokTnksGVgip2PbYbr3xnR7kZigh4LbybAfBAw5BpnQ+FqBYUsvCEjYd70IXKlbohQ64mzEYmMtlWUY8q//Q==} + /@types/node@22.8.2: + resolution: {integrity: sha512-NzaRNFV+FZkvK/KLCsNdTvID0SThyrs5SHB6tsD/lajr22FGC73N2QeDPM2wHtVde8mgcXuSsHQkH5cX1pbPLw==} dependencies: - undici-types: 5.26.5 + undici-types: 6.19.8 + dev: false /@types/parse-json@4.0.2: resolution: {integrity: sha512-dISoDXWWQwUquiKsyZ4Ng+HX2KsPL7LyHKHQwgGFEA3IaKac4Obd+h2a/a6waisAoepJlBcx9paWqjA8/HVjCw==} dev: true - /@types/qs@6.9.11: - resolution: {integrity: sha512-oGk0gmhnEJK4Yyk+oI7EfXsLayXatCWPHary1MtcmbAifkobT9cM9yutG/hZKIseOU0MqbIwQ/u2nn/Gb+ltuQ==} + /@types/qs@6.9.16: + resolution: {integrity: sha512-7i+zxXdPD0T4cKDuxCUXJ4wHcsJLwENa6Z3dCu8cfCK743OGy5Nu1RmAGqDPsoTDINVEcdXKRvR/zre+P2Ku1A==} dev: true /@types/range-parser@1.2.7: @@ -1085,12 +1043,12 @@ packages: '@types/node': 14.14.21 dev: true - /@types/serve-static@1.15.5: - resolution: {integrity: sha512-PDRk21MnK70hja/YF8AHfC7yIsiQHn1rcXx7ijCFBX/k+XQJhQT/gw3xekXKJvx+5SXaMMS8oqQy09Mzvz2TuQ==} + /@types/serve-static@1.15.7: + resolution: {integrity: sha512-W8Ym+h8nhuRwaKPaDw34QUkwsGi6Rc4yYqvKFo5rm2FUEhCFbzVWrxXUxuKK8TASjWsysJY0nsmNCGhCOIsrOw==} dependencies: '@types/http-errors': 2.0.4 - '@types/mime': 3.0.4 '@types/node': 14.14.21 + '@types/send': 0.17.4 dev: true /@types/sinon@9.0.10: @@ -1129,7 +1087,7 @@ packages: '@typescript-eslint/experimental-utils': 4.19.0(eslint@7.29.0)(typescript@4.5.5) '@typescript-eslint/parser': 4.19.0(eslint@7.29.0)(typescript@4.5.5) '@typescript-eslint/scope-manager': 4.19.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 eslint: 7.29.0 functional-red-black-tree: 1.0.1 lodash: 4.17.21 @@ -1172,7 +1130,7 @@ packages: '@typescript-eslint/scope-manager': 4.19.0 '@typescript-eslint/types': 4.19.0 '@typescript-eslint/typescript-estree': 4.19.0(typescript@4.5.5) - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 eslint: 7.29.0 typescript: 4.5.5 transitivePeerDependencies: @@ -1203,7 +1161,7 @@ packages: dependencies: '@typescript-eslint/types': 4.19.0 '@typescript-eslint/visitor-keys': 4.19.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 globby: 11.1.0 is-glob: 4.0.3 semver: 7.5.4 @@ -1221,141 +1179,147 @@ packages: eslint-visitor-keys: 2.1.0 dev: true - /@webassemblyjs/ast@1.11.1: - resolution: {integrity: sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw==} + /@webassemblyjs/ast@1.12.1: + resolution: {integrity: sha512-EKfMUOPRRUTy5UII4qJDGPpqfwjOmZ5jeGFwid9mnoqIFK+e0vqoi1qH56JpmZSzEL53jKnNzScdmftJyG5xWg==} dependencies: - '@webassemblyjs/helper-numbers': 1.11.1 - '@webassemblyjs/helper-wasm-bytecode': 1.11.1 + '@webassemblyjs/helper-numbers': 1.11.6 + '@webassemblyjs/helper-wasm-bytecode': 1.11.6 dev: true - /@webassemblyjs/floating-point-hex-parser@1.11.1: - resolution: {integrity: sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ==} + /@webassemblyjs/floating-point-hex-parser@1.11.6: + resolution: {integrity: sha512-ejAj9hfRJ2XMsNHk/v6Fu2dGS+i4UaXBXGemOfQ/JfQ6mdQg/WXtwleQRLLS4OvfDhv8rYnVwH27YJLMyYsxhw==} dev: true - /@webassemblyjs/helper-api-error@1.11.1: - resolution: {integrity: sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg==} + /@webassemblyjs/helper-api-error@1.11.6: + resolution: {integrity: sha512-o0YkoP4pVu4rN8aTJgAyj9hC2Sv5UlkzCHhxqWj8butaLvnpdc2jOwh4ewE6CX0txSfLn/UYaV/pheS2Txg//Q==} dev: true - /@webassemblyjs/helper-buffer@1.11.1: - resolution: {integrity: sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA==} + /@webassemblyjs/helper-buffer@1.12.1: + resolution: {integrity: sha512-nzJwQw99DNDKr9BVCOZcLuJJUlqkJh+kVzVl6Fmq/tI5ZtEyWT1KZMyOXltXLZJmDtvLCDgwsyrkohEtopTXCw==} dev: true - /@webassemblyjs/helper-numbers@1.11.1: - resolution: {integrity: sha512-vDkbxiB8zfnPdNK9Rajcey5C0w+QJugEglN0of+kmO8l7lDb77AnlKYQF7aarZuCrv+l0UvqL+68gSDr3k9LPQ==} + /@webassemblyjs/helper-numbers@1.11.6: + resolution: {integrity: sha512-vUIhZ8LZoIWHBohiEObxVm6hwP034jwmc9kuq5GdHZH0wiLVLIPcMCdpJzG4C11cHoQ25TFIQj9kaVADVX7N3g==} dependencies: - '@webassemblyjs/floating-point-hex-parser': 1.11.1 - '@webassemblyjs/helper-api-error': 1.11.1 + '@webassemblyjs/floating-point-hex-parser': 1.11.6 + '@webassemblyjs/helper-api-error': 1.11.6 '@xtuc/long': 4.2.2 dev: true - /@webassemblyjs/helper-wasm-bytecode@1.11.1: - resolution: {integrity: sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q==} + /@webassemblyjs/helper-wasm-bytecode@1.11.6: + resolution: {integrity: sha512-sFFHKwcmBprO9e7Icf0+gddyWYDViL8bpPjJJl0WHxCdETktXdmtWLGVzoHbqUcY4Be1LkNfwTmXOJUFZYSJdA==} dev: true - /@webassemblyjs/helper-wasm-section@1.11.1: - resolution: {integrity: sha512-10P9No29rYX1j7F3EVPX3JvGPQPae+AomuSTPiF9eBQeChHI6iqjMIwR9JmOJXwpnn/oVGDk7I5IlskuMwU/pg==} + /@webassemblyjs/helper-wasm-section@1.12.1: + resolution: {integrity: sha512-Jif4vfB6FJlUlSbgEMHUyk1j234GTNG9dBJ4XJdOySoj518Xj0oGsNi59cUQF4RRMS9ouBUxDDdyBVfPTypa5g==} dependencies: - '@webassemblyjs/ast': 1.11.1 - '@webassemblyjs/helper-buffer': 1.11.1 - '@webassemblyjs/helper-wasm-bytecode': 1.11.1 - '@webassemblyjs/wasm-gen': 1.11.1 + '@webassemblyjs/ast': 1.12.1 + '@webassemblyjs/helper-buffer': 1.12.1 + '@webassemblyjs/helper-wasm-bytecode': 1.11.6 + '@webassemblyjs/wasm-gen': 1.12.1 dev: true - /@webassemblyjs/ieee754@1.11.1: - resolution: {integrity: sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ==} + /@webassemblyjs/ieee754@1.11.6: + resolution: {integrity: sha512-LM4p2csPNvbij6U1f19v6WR56QZ8JcHg3QIJTlSwzFcmx6WSORicYj6I63f9yU1kEUtrpG+kjkiIAkevHpDXrg==} dependencies: '@xtuc/ieee754': 1.2.0 dev: true - /@webassemblyjs/leb128@1.11.1: - resolution: {integrity: sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw==} + /@webassemblyjs/leb128@1.11.6: + resolution: {integrity: sha512-m7a0FhE67DQXgouf1tbN5XQcdWoNgaAuoULHIfGFIEVKA6tu/edls6XnIlkmS6FrXAquJRPni3ZZKjw6FSPjPQ==} dependencies: '@xtuc/long': 4.2.2 dev: true - /@webassemblyjs/utf8@1.11.1: - resolution: {integrity: sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==} + /@webassemblyjs/utf8@1.11.6: + resolution: {integrity: sha512-vtXf2wTQ3+up9Zsg8sa2yWiQpzSsMyXj0qViVP6xKGCUT8p8YJ6HqI7l5eCnWx1T/FYdsv07HQs2wTFbbof/RA==} dev: true - /@webassemblyjs/wasm-edit@1.11.1: - resolution: {integrity: sha512-g+RsupUC1aTHfR8CDgnsVRVZFJqdkFHpsHMfJuWQzWU3tvnLC07UqHICfP+4XyL2tnr1amvl1Sdp06TnYCmVkA==} + /@webassemblyjs/wasm-edit@1.12.1: + resolution: {integrity: sha512-1DuwbVvADvS5mGnXbE+c9NfA8QRcZ6iKquqjjmR10k6o+zzsRVesil54DKexiowcFCPdr/Q0qaMgB01+SQ1u6g==} dependencies: - '@webassemblyjs/ast': 1.11.1 - '@webassemblyjs/helper-buffer': 1.11.1 - '@webassemblyjs/helper-wasm-bytecode': 1.11.1 - '@webassemblyjs/helper-wasm-section': 1.11.1 - '@webassemblyjs/wasm-gen': 1.11.1 - '@webassemblyjs/wasm-opt': 1.11.1 - '@webassemblyjs/wasm-parser': 1.11.1 - '@webassemblyjs/wast-printer': 1.11.1 + '@webassemblyjs/ast': 1.12.1 + '@webassemblyjs/helper-buffer': 1.12.1 + '@webassemblyjs/helper-wasm-bytecode': 1.11.6 + '@webassemblyjs/helper-wasm-section': 1.12.1 + '@webassemblyjs/wasm-gen': 1.12.1 + '@webassemblyjs/wasm-opt': 1.12.1 + '@webassemblyjs/wasm-parser': 1.12.1 + '@webassemblyjs/wast-printer': 1.12.1 dev: true - /@webassemblyjs/wasm-gen@1.11.1: - resolution: {integrity: sha512-F7QqKXwwNlMmsulj6+O7r4mmtAlCWfO/0HdgOxSklZfQcDu0TpLiD1mRt/zF25Bk59FIjEuGAIyn5ei4yMfLhA==} + /@webassemblyjs/wasm-gen@1.12.1: + resolution: {integrity: sha512-TDq4Ojh9fcohAw6OIMXqiIcTq5KUXTGRkVxbSo1hQnSy6lAM5GSdfwWeSxpAo0YzgsgF182E/U0mDNhuA0tW7w==} dependencies: - '@webassemblyjs/ast': 1.11.1 - '@webassemblyjs/helper-wasm-bytecode': 1.11.1 - '@webassemblyjs/ieee754': 1.11.1 - '@webassemblyjs/leb128': 1.11.1 - '@webassemblyjs/utf8': 1.11.1 + '@webassemblyjs/ast': 1.12.1 + '@webassemblyjs/helper-wasm-bytecode': 1.11.6 + '@webassemblyjs/ieee754': 1.11.6 + '@webassemblyjs/leb128': 1.11.6 + '@webassemblyjs/utf8': 1.11.6 dev: true - /@webassemblyjs/wasm-opt@1.11.1: - resolution: {integrity: sha512-VqnkNqnZlU5EB64pp1l7hdm3hmQw7Vgqa0KF/KCNO9sIpI6Fk6brDEiX+iCOYrvMuBWDws0NkTOxYEb85XQHHw==} + /@webassemblyjs/wasm-opt@1.12.1: + resolution: {integrity: sha512-Jg99j/2gG2iaz3hijw857AVYekZe2SAskcqlWIZXjji5WStnOpVoat3gQfT/Q5tb2djnCjBtMocY/Su1GfxPBg==} dependencies: - '@webassemblyjs/ast': 1.11.1 - '@webassemblyjs/helper-buffer': 1.11.1 - '@webassemblyjs/wasm-gen': 1.11.1 - '@webassemblyjs/wasm-parser': 1.11.1 + '@webassemblyjs/ast': 1.12.1 + '@webassemblyjs/helper-buffer': 1.12.1 + '@webassemblyjs/wasm-gen': 1.12.1 + '@webassemblyjs/wasm-parser': 1.12.1 dev: true - /@webassemblyjs/wasm-parser@1.11.1: - resolution: {integrity: sha512-rrBujw+dJu32gYB7/Lup6UhdkPx9S9SnobZzRVL7VcBH9Bt9bCBLEuX/YXOOtBsOZ4NQrRykKhffRWHvigQvOA==} + /@webassemblyjs/wasm-parser@1.12.1: + resolution: {integrity: sha512-xikIi7c2FHXysxXe3COrVUPSheuBtpcfhbpFj4gmu7KRLYOzANztwUU0IbsqvMqzuNK2+glRGWCEqZo1WCLyAQ==} dependencies: - '@webassemblyjs/ast': 1.11.1 - '@webassemblyjs/helper-api-error': 1.11.1 - '@webassemblyjs/helper-wasm-bytecode': 1.11.1 - '@webassemblyjs/ieee754': 1.11.1 - '@webassemblyjs/leb128': 1.11.1 - '@webassemblyjs/utf8': 1.11.1 + '@webassemblyjs/ast': 1.12.1 + '@webassemblyjs/helper-api-error': 1.11.6 + '@webassemblyjs/helper-wasm-bytecode': 1.11.6 + '@webassemblyjs/ieee754': 1.11.6 + '@webassemblyjs/leb128': 1.11.6 + '@webassemblyjs/utf8': 1.11.6 dev: true - /@webassemblyjs/wast-printer@1.11.1: - resolution: {integrity: sha512-IQboUWM4eKzWW+N/jij2sRatKMh99QEelo3Eb2q0qXkvPRISAj8Qxtmw5itwqK+TTkBuUIE45AxYPToqPtL5gg==} + /@webassemblyjs/wast-printer@1.12.1: + resolution: {integrity: sha512-+X4WAlOisVWQMikjbcvY2e0rwPsKQ9F688lksZhBcPycBBuii3O7m8FACbDMWDojpAqvjIncrG8J0XHKyQfVeA==} dependencies: - '@webassemblyjs/ast': 1.11.1 + '@webassemblyjs/ast': 1.12.1 '@xtuc/long': 4.2.2 dev: true - /@webpack-cli/configtest@1.2.0(webpack-cli@4.7.2)(webpack@5.62.1): - resolution: {integrity: sha512-4FB8Tj6xyVkyqjj1OaTqCjXYULB9FMkqQ8yGrZjRDrYh0nOE+7Lhs45WioWQQMV+ceFlE368Ukhe6xdvJM9Egg==} + /@webpack-cli/configtest@2.1.1(webpack-cli@5.1.4)(webpack@5.95.0): + resolution: {integrity: sha512-wy0mglZpDSiSS0XHrVR+BAdId2+yxPSoJW8fsna3ZpYSlufjvxnP4YbKTCBZnNIcGN4r6ZPXV55X4mYExOfLmw==} + engines: {node: '>=14.15.0'} peerDependencies: - webpack: 4.x.x || 5.x.x - webpack-cli: 4.x.x + webpack: 5.x.x + webpack-cli: 5.x.x dependencies: - webpack: 5.62.1(webpack-cli@4.7.2) - webpack-cli: 4.7.2(webpack@5.62.1) + webpack: 5.95.0(webpack-cli@5.1.4) + webpack-cli: 5.1.4(webpack@5.95.0) dev: true - /@webpack-cli/info@1.5.0(webpack-cli@4.7.2): - resolution: {integrity: sha512-e8tSXZpw2hPl2uMJY6fsMswaok5FdlGNRTktvFk2sD8RjH0hE2+XistawJx1vmKteh4NmGmNUrp+Tb2w+udPcQ==} + /@webpack-cli/info@2.0.2(webpack-cli@5.1.4)(webpack@5.95.0): + resolution: {integrity: sha512-zLHQdI/Qs1UyT5UBdWNqsARasIA+AaF8t+4u2aS2nEpBQh2mWIVb8qAklq0eUENnC5mOItrIB4LiS9xMtph18A==} + engines: {node: '>=14.15.0'} peerDependencies: - webpack-cli: 4.x.x + webpack: 5.x.x + webpack-cli: 5.x.x dependencies: - envinfo: 7.11.0 - webpack-cli: 4.7.2(webpack@5.62.1) + webpack: 5.95.0(webpack-cli@5.1.4) + webpack-cli: 5.1.4(webpack@5.95.0) dev: true - /@webpack-cli/serve@1.7.0(webpack-cli@4.7.2): - resolution: {integrity: sha512-oxnCNGj88fL+xzV+dacXs44HcDwf1ovs3AuEzvP7mqXw7fQntqIhQ1BRmynh4qEKQSSSRSWVyXRjmTbZIX9V2Q==} + /@webpack-cli/serve@2.0.5(webpack-cli@5.1.4)(webpack@5.95.0): + resolution: {integrity: sha512-lqaoKnRYBdo1UgDX8uF24AfGMifWK19TxPmM5FHc2vAGxrJ/qtyUyFBWoY1tISZdelsQ5fBcOusifo5o5wSJxQ==} + engines: {node: '>=14.15.0'} peerDependencies: - webpack-cli: 4.x.x + webpack: 5.x.x + webpack-cli: 5.x.x webpack-dev-server: '*' peerDependenciesMeta: webpack-dev-server: optional: true dependencies: - webpack-cli: 4.7.2(webpack@5.62.1) + webpack: 5.95.0(webpack-cli@5.1.4) + webpack-cli: 5.1.4(webpack@5.95.0) dev: true /@xtuc/ieee754@1.2.0: @@ -1374,12 +1338,12 @@ packages: negotiator: 0.6.3 dev: false - /acorn-import-assertions@1.9.0(acorn@8.11.3): - resolution: {integrity: sha512-cmMwop9x+8KFhxvKrKfPYmN6/pKTYYHBqLa0DfvVZcKMJWNyWLnaqND7dx/qn66R7ewM1UX5XMaDVP5wlVTaVA==} + /acorn-import-attributes@1.9.5(acorn@8.14.0): + resolution: {integrity: sha512-n02Vykv5uA3eHGM/Z2dQrcD56kL8TyDb2p1+0P83PClMnC/nc+anbQRhIOWnSq4Ke/KvDPrY3C9hDtC/A3eHnQ==} peerDependencies: acorn: ^8 dependencies: - acorn: 8.11.3 + acorn: 8.14.0 dev: true /acorn-jsx@5.3.2(acorn@7.4.1): @@ -1396,17 +1360,17 @@ packages: hasBin: true dev: true - /acorn@8.11.3: - resolution: {integrity: sha512-Y9rRfJG5jcKOE0CLisYbojUjIrIEE7AGMzA/Sm4BslANhbS+cDMpgBdcPT91oJ7OuJ9hYJBx59RjbhxVnrF8Xg==} + /acorn@8.14.0: + resolution: {integrity: sha512-cl669nCJTZBsL97OF4kUQm5g5hC2uihk0NxY3WENAC0TYdILVkAyHymAntgxGkl7K+t0cXIrH5siy5S4XkFycA==} engines: {node: '>=0.4.0'} hasBin: true dev: true - /agent-base@6.0.2: - resolution: {integrity: sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==} - engines: {node: '>= 6.0.0'} + /agent-base@7.1.1: + resolution: {integrity: sha512-H0TSyFNDMomMNJQBn8wFV5YC/2eJ+VXECwOadZJT554xP6cODZHPX3H9QMQECxvrgiSOP1pHjy1sMWQVYJOUOA==} + engines: {node: '>= 14'} dependencies: - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 transitivePeerDependencies: - supports-color dev: false @@ -1436,13 +1400,13 @@ packages: uri-js: 4.4.1 dev: true - /ajv@8.12.0: - resolution: {integrity: sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==} + /ajv@8.17.1: + resolution: {integrity: sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==} dependencies: fast-deep-equal: 3.1.3 + fast-uri: 3.0.3 json-schema-traverse: 1.0.0 require-from-string: 2.0.2 - uri-js: 4.4.1 dev: true /ansi-colors@4.1.1: @@ -1469,8 +1433,8 @@ packages: resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} engines: {node: '>=8'} - /ansi-regex@6.0.1: - resolution: {integrity: sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==} + /ansi-regex@6.1.0: + resolution: {integrity: sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==} engines: {node: '>=12'} dev: true @@ -1526,6 +1490,7 @@ packages: /are-we-there-yet@1.1.7: resolution: {integrity: sha512-nxwy40TuMiUGqMyRHgCSWZ9FM4VAoRP4xUYSTv5ImRog+h9yISPbVH7H8fASCIzYn9wlEv4zvFL7uKDMCFQm3g==} + deprecated: This package is no longer supported. requiresBuild: true dependencies: delegates: 1.0.0 @@ -1545,25 +1510,27 @@ packages: resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} dev: true - /array-buffer-byte-length@1.0.0: - resolution: {integrity: sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A==} + /array-buffer-byte-length@1.0.1: + resolution: {integrity: sha512-ahC5W1xgou+KTXix4sAO8Ki12Q+jf4i0+tmk3sC+zgcynshkHxzpXdImBehiUYKKKDwvfFiJl1tZt6ewscS1Mg==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - is-array-buffer: 3.0.2 + call-bind: 1.0.7 + is-array-buffer: 3.0.4 dev: true /array-flatten@1.1.1: resolution: {integrity: sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==} dev: false - /array-includes@3.1.7: - resolution: {integrity: sha512-dlcsNBIiWhPkHdOEEKnehA+RNUWDc4UqFtnIXU4uuYDPtA4LDkr7qip2p0VvFAEXNDr0yWZ9PJyIRiGjRLQzwQ==} + /array-includes@3.1.8: + resolution: {integrity: sha512-itaWrbYbqpGXkGhZPGUulwnhVf5Hpy1xiCFsGqyIGglbBxmG5vSjxQen3/WGOjPpNEv1RtBLKxbmVXm8HpJStQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 - get-intrinsic: 1.2.2 + es-abstract: 1.23.3 + es-object-atoms: 1.0.0 + get-intrinsic: 1.2.4 is-string: 1.0.7 dev: true @@ -1576,23 +1543,24 @@ packages: resolution: {integrity: sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-abstract: 1.23.3 es-shim-unscopables: 1.0.2 dev: true - /arraybuffer.prototype.slice@1.0.2: - resolution: {integrity: sha512-yMBKppFur/fbHu9/6USUe03bZ4knMYiwFBcyiaXB8Go0qNehwX6inYPzK9U0NeQvGxKthcmHcaR8P5MStSRBAw==} + /arraybuffer.prototype.slice@1.0.3: + resolution: {integrity: sha512-bMxMKAjg13EBSVscxTaYA4mRc5t1UAXa2kXiGTNfZ079HIWXEkKmkgFrh/nJqamaLSrXO5H4WFFkPEaLJWbs3A==} engines: {node: '>= 0.4'} dependencies: - array-buffer-byte-length: 1.0.0 - call-bind: 1.0.5 + array-buffer-byte-length: 1.0.1 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 - get-intrinsic: 1.2.2 - is-array-buffer: 3.0.2 - is-shared-array-buffer: 1.0.2 + es-abstract: 1.23.3 + es-errors: 1.3.0 + get-intrinsic: 1.2.4 + is-array-buffer: 3.0.4 + is-shared-array-buffer: 1.0.3 dev: true /assertion-error@1.1.0: @@ -1640,9 +1608,11 @@ packages: engines: {node: '>= 4.0.0'} dev: false - /available-typed-arrays@1.0.5: - resolution: {integrity: sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==} + /available-typed-arrays@1.0.7: + resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} engines: {node: '>= 0.4'} + dependencies: + possible-typed-array-names: 1.0.0 dev: true /balanced-match@1.0.2: @@ -1657,8 +1627,8 @@ packages: resolution: {integrity: sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==} dev: true - /binary-extensions@2.2.0: - resolution: {integrity: sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==} + /binary-extensions@2.3.0: + resolution: {integrity: sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==} engines: {node: '>=8'} dev: true @@ -1670,8 +1640,8 @@ packages: inherits: 2.0.4 readable-stream: 3.6.2 - /body-parser@1.20.2: - resolution: {integrity: sha512-ml9pReCu3M61kGlqoTm2umSXTlRTuGTx0bfYj+uIUKKYycG5NtSbeetV3faSU6R7ajOPw0g/J1PvK4qNy7s5bA==} + /body-parser@1.20.3: + resolution: {integrity: sha512-7rAxByjUMqQ3/bHJy7D6OGXvx/MMc4IqBn/X0fcM1QUcAItpZrBEYhWGem+tzXH90c+G01ypMcYJBO9Y30203g==} engines: {node: '>= 0.8', npm: 1.2.8000 || >= 1.4.16} dependencies: bytes: 3.1.2 @@ -1682,7 +1652,7 @@ packages: http-errors: 2.0.0 iconv-lite: 0.4.24 on-finished: 2.4.1 - qs: 6.11.0 + qs: 6.13.0 raw-body: 2.5.2 type-is: 1.6.18 unpipe: 1.0.0 @@ -1707,26 +1677,26 @@ packages: balanced-match: 1.0.2 dev: true - /braces@3.0.2: - resolution: {integrity: sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==} + /braces@3.0.3: + resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} engines: {node: '>=8'} dependencies: - fill-range: 7.0.1 + fill-range: 7.1.1 dev: true /browser-stdout@1.3.1: resolution: {integrity: sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw==} dev: true - /browserslist@4.22.2: - resolution: {integrity: sha512-0UgcrvQmBDvZHFGdYUehrCNIazki7/lUP3kkoi/r3YB2amZbFM9J43ZRkJTXBUZK4gmx56+Sqk9+Vs9mwZx9+A==} + /browserslist@4.24.2: + resolution: {integrity: sha512-ZIc+Q62revdMcqC6aChtW4jz3My3klmCO1fEmINZY/8J3EpBg5/A/D0AKmBveUh6pgoeycoMkVMko84tuYS+Gg==} engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} hasBin: true dependencies: - caniuse-lite: 1.0.30001579 - electron-to-chromium: 1.4.645 - node-releases: 2.0.14 - update-browserslist-db: 1.0.13(browserslist@4.22.2) + caniuse-lite: 1.0.30001674 + electron-to-chromium: 1.5.49 + node-releases: 2.0.18 + update-browserslist-db: 1.1.1(browserslist@4.24.2) dev: true /buffer-equal-constant-time@1.0.1: @@ -1759,12 +1729,15 @@ packages: write-file-atomic: 3.0.3 dev: true - /call-bind@1.0.5: - resolution: {integrity: sha512-C3nQxfFZxFRVoJoGKKI8y3MOEo129NQ+FgQ08iye+Mk4zNZZGdjfs06bVTr+DBSlA66Q2VEcMki/cUCP4SercQ==} + /call-bind@1.0.7: + resolution: {integrity: sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==} + engines: {node: '>= 0.4'} dependencies: + es-define-property: 1.0.0 + es-errors: 1.3.0 function-bind: 1.1.2 - get-intrinsic: 1.2.2 - set-function-length: 1.2.0 + get-intrinsic: 1.2.4 + set-function-length: 1.2.2 /callsites@3.1.0: resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} @@ -1788,21 +1761,21 @@ packages: engines: {node: '>=10'} dev: true - /caniuse-lite@1.0.30001579: - resolution: {integrity: sha512-u5AUVkixruKHJjw/pj9wISlcMpgFWzSrczLZbrqBSxukQixmg0SJ5sZTpvaFvxU0HoQKd4yoyAogyrAz9pzJnA==} + /caniuse-lite@1.0.30001674: + resolution: {integrity: sha512-jOsKlZVRnzfhLojb+Ykb+gyUSp9Xb57So+fAiFlLzzTKpqg8xxSav0e40c8/4F/v9N8QSvrRRaLeVzQbLqomYw==} dev: true - /chai-as-promised@7.1.1(chai@4.3.4): + /chai-as-promised@7.1.1(chai@4.2.0): resolution: {integrity: sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA==} peerDependencies: chai: '>= 2.1.2 < 5' dependencies: - chai: 4.3.4 + chai: 4.2.0 check-error: 1.0.3 dev: true - /chai@4.3.4: - resolution: {integrity: sha512-yS5H68VYOCtN1cjfwumDSuzn/9c+yza4f3reKXlE5rUg7SFcCEy90gJvydNgOYtblyf4Zi6jIWRnXOgErta0KA==} + /chai@4.2.0: + resolution: {integrity: sha512-XQU3bhBukrOsQCuwZndwGcCVQHyZi53fQ6Ys1Fym7E4olpIqqZZhhoFJoaKVvV17lWQoXYwgWN2nF5crA8J2jw==} engines: {node: '>=4'} dependencies: assertion-error: 1.1.0 @@ -1810,7 +1783,7 @@ packages: deep-eql: 3.0.1 get-func-name: 2.0.2 pathval: 1.1.1 - type-detect: 4.0.8 + type-detect: 4.1.0 dev: true /chalk@2.4.2: @@ -1835,6 +1808,7 @@ packages: dependencies: ansi-styles: 4.3.0 supports-color: 7.2.0 + dev: false /chardet@0.7.0: resolution: {integrity: sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==} @@ -1856,7 +1830,7 @@ packages: engines: {node: '>= 8.10.0'} dependencies: anymatch: 3.1.3 - braces: 3.0.2 + braces: 3.0.3 glob-parent: 5.1.2 is-binary-path: 2.1.0 is-glob: 4.0.3 @@ -1870,8 +1844,8 @@ packages: resolution: {integrity: sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==} requiresBuild: true - /chrome-trace-event@1.0.3: - resolution: {integrity: sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg==} + /chrome-trace-event@1.0.4: + resolution: {integrity: sha512-rNjApaLzuwaOTjCiT8lSDdGN1APCiqkChLMJxJPWLunPAt5fy8xgU9/jNOchV84wfIxrA0lRQB7oCT8jrn/wrQ==} engines: {node: '>=6.0'} dev: true @@ -1979,14 +1953,15 @@ packages: /color-name@1.1.4: resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==} - /colorette@1.4.0: - resolution: {integrity: sha512-Y2oEozpomLn7Q3HFP7dpww7AtMJplbM9lGZP6RDfHqmbeRjiwRg4n6VM6j4KLmRke85uWEI7JqF17f3pqdRA0g==} - dev: true - /colorette@2.0.20: resolution: {integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==} dev: true + /commander@10.0.1: + resolution: {integrity: sha512-y4Mg2tXshplEbSGzx7amzPwKKOCGuoSRP/CjEdwwk0FOGlUbq6lKuoyDZTNZkmxHdJtp54hdfY/JUrdL7Xfdug==} + engines: {node: '>=14'} + dev: true + /commander@2.20.3: resolution: {integrity: sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==} dev: true @@ -2001,11 +1976,6 @@ packages: engines: {node: '>= 6'} dev: true - /commander@7.2.0: - resolution: {integrity: sha512-QrWXB+ZQSVPmIWIhtEO9H+gwHaMGYiF5ChvoJ+K9ZGHG/sVsa6yiesAD1GC/x46sET00Xlwo1u49RVVVzvcSkw==} - engines: {node: '>= 10'} - dev: true - /commondir@1.0.1: resolution: {integrity: sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==} dev: true @@ -2049,12 +2019,12 @@ packages: resolution: {integrity: sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==} dev: false - /cookie@0.6.0: - resolution: {integrity: sha512-U71cyTamuh1CRNCfpGY6to28lxvNwPG4Guz/EVjgf3Jmzv0vlDp1atT9eS5dDjMYHucpHbWns6Lwf3BKz6svdw==} + /cookie@0.7.1: + resolution: {integrity: sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w==} engines: {node: '>= 0.6'} dev: false - /copy-webpack-plugin@9.0.0(webpack@5.62.1): + /copy-webpack-plugin@9.0.0(webpack@5.95.0): resolution: {integrity: sha512-k8UB2jLIb1Jip2nZbCz83T/XfhfjX6mB1yLJNYKrpYi7FQimfOoFv/0//iT6HV1K8FwUB5yUbCcnpLebJXJTug==} engines: {node: '>= 12.13.0'} peerDependencies: @@ -2067,7 +2037,7 @@ packages: p-limit: 3.1.0 schema-utils: 3.3.0 serialize-javascript: 5.0.1 - webpack: 5.62.1(webpack-cli@4.7.2) + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /copyfiles@2.4.1: @@ -2110,23 +2080,23 @@ packages: which: 2.0.2 dev: true - /css-loader@5.2.5(webpack@5.62.1): + /css-loader@5.2.5(webpack@5.95.0): resolution: {integrity: sha512-bH6QQacvSRtLX0lycAOs43S173n+lfXxB5cx4FjVkTLw5tAEwk5bxNLbkt5K1iETd5KxazRx70GpqOxsuwKiFA==} engines: {node: '>= 10.13.0'} peerDependencies: webpack: ^4.27.0 || ^5.0.0 dependencies: - icss-utils: 5.1.0(postcss@8.4.33) + icss-utils: 5.1.0(postcss@8.4.47) loader-utils: 2.0.4 - postcss: 8.4.33 - postcss-modules-extract-imports: 3.0.0(postcss@8.4.33) - postcss-modules-local-by-default: 4.0.4(postcss@8.4.33) - postcss-modules-scope: 3.1.1(postcss@8.4.33) - postcss-modules-values: 4.0.0(postcss@8.4.33) + postcss: 8.4.47 + postcss-modules-extract-imports: 3.1.0(postcss@8.4.47) + postcss-modules-local-by-default: 4.0.5(postcss@8.4.47) + postcss-modules-scope: 3.2.0(postcss@8.4.47) + postcss-modules-values: 4.0.0(postcss@8.4.47) postcss-value-parser: 4.2.0 schema-utils: 3.3.0 semver: 7.5.4 - webpack: 5.62.1(webpack-cli@4.7.2) + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /css-select@4.3.0: @@ -2150,6 +2120,33 @@ packages: hasBin: true dev: true + /data-view-buffer@1.0.1: + resolution: {integrity: sha512-0lht7OugA5x3iJLOWFhWK/5ehONdprk0ISXqVFn/NFrDu+cuc8iADFrGQz5BnRK7LLU3JmkbXSxaqX+/mXYtUA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.7 + es-errors: 1.3.0 + is-data-view: 1.0.1 + dev: true + + /data-view-byte-length@1.0.1: + resolution: {integrity: sha512-4J7wRJD3ABAzr8wP+OcIcqq2dlUKp4DVflx++hs5h5ZKydWMI6/D/fAot+yh6g2tHh8fLFTvNOaVN357NvSrOQ==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.7 + es-errors: 1.3.0 + is-data-view: 1.0.1 + dev: true + + /data-view-byte-offset@1.0.0: + resolution: {integrity: sha512-t/Ygsytq+R995EJ5PZlD4Cu56sWa8InXySaViRzw9apusqsOO2bQP+SbYzAhR0pFKoB+43lYy8rWban9JSuXnA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.7 + es-errors: 1.3.0 + is-data-view: 1.0.1 + dev: true + /debug@2.6.9: resolution: {integrity: sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==} peerDependencies: @@ -2194,6 +2191,18 @@ packages: dependencies: ms: 2.1.2 supports-color: 8.1.1 + dev: true + + /debug@4.3.7: + resolution: {integrity: sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ==} + engines: {node: '>=6.0'} + peerDependencies: + supports-color: '*' + peerDependenciesMeta: + supports-color: + optional: true + dependencies: + ms: 2.1.3 /decamelize@1.2.0: resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==} @@ -2220,7 +2229,7 @@ packages: resolution: {integrity: sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==} engines: {node: '>=0.12'} dependencies: - type-detect: 4.0.8 + type-detect: 4.1.0 dev: true /deep-extend@0.6.0: @@ -2239,13 +2248,13 @@ packages: strip-bom: 4.0.0 dev: true - /define-data-property@1.1.1: - resolution: {integrity: sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ==} + /define-data-property@1.1.4: + resolution: {integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==} engines: {node: '>= 0.4'} dependencies: - get-intrinsic: 1.2.2 + es-define-property: 1.0.0 + es-errors: 1.3.0 gopd: 1.0.1 - has-property-descriptors: 1.0.1 /define-lazy-prop@2.0.0: resolution: {integrity: sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==} @@ -2256,8 +2265,8 @@ packages: resolution: {integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==} engines: {node: '>= 0.4'} dependencies: - define-data-property: 1.1.1 - has-property-descriptors: 1.0.1 + define-data-property: 1.1.4 + has-property-descriptors: 1.0.2 object-keys: 1.1.1 dev: true @@ -2385,8 +2394,8 @@ packages: resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} dev: false - /electron-to-chromium@1.4.645: - resolution: {integrity: sha512-EeS1oQDCmnYsRDRy2zTeC336a/4LZ6WKqvSaM1jLocEk5ZuyszkQtCpsqvuvaIXGOUjwtvF6LTcS8WueibXvSw==} + /electron-to-chromium@1.5.49: + resolution: {integrity: sha512-ZXfs1Of8fDb6z7WEYZjXpgIRF6MEu8JdeGA0A40aZq6OQbS+eJpnnV49epZRna2DU/YsEjSQuGtQPPtvt6J65A==} dev: true /emitter-listener@1.1.2: @@ -2412,14 +2421,19 @@ packages: engines: {node: '>= 0.8'} dev: false + /encodeurl@2.0.0: + resolution: {integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==} + engines: {node: '>= 0.8'} + dev: false + /end-of-stream@1.4.4: resolution: {integrity: sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==} requiresBuild: true dependencies: once: 1.4.0 - /enhanced-resolve@5.15.0: - resolution: {integrity: sha512-LXYT42KJ7lpIKECr2mAXIaMldcNCh/7E0KBKOu4KSfkHmP+mZmSs+8V5gBAqisWBy0OO4W5Oyys0GO1Y8KtdKg==} + /enhanced-resolve@5.17.1: + resolution: {integrity: sha512-LMHl3dXhTcfv8gM4kEzIUeTQ+7fpdA0l2tUf34BddXPkz2A5xJ5L/Pchd5BL6rdccM9QGvu0sWZzK1Z1t4wwyg==} engines: {node: '>=10.13.0'} dependencies: graceful-fs: 4.2.11 @@ -2438,8 +2452,8 @@ packages: resolution: {integrity: sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==} dev: true - /envinfo@7.11.0: - resolution: {integrity: sha512-G9/6xF1FPbIw0TtalAMaVPpiq2aDEuKLXM314jPVAO9r2fo2a4BLqMNkmRS7O/xPPZ+COAhGIz3ETvHEV3eUcg==} + /envinfo@7.14.0: + resolution: {integrity: sha512-CO40UI41xDQzhLB1hWyqUKgFhs250pNcGbyGKe1l/e4FSaI/+YE4IMG76GDt0In67WLPACIITC+sOi08x4wIvg==} engines: {node: '>=4'} hasBin: true dev: true @@ -2450,68 +2464,92 @@ packages: is-arrayish: 0.2.1 dev: true - /es-abstract@1.22.3: - resolution: {integrity: sha512-eiiY8HQeYfYH2Con2berK+To6GrK2RxbPawDkGq4UiCQQfZHb6wX9qQqkbpPqaxQFcl8d9QzZqo0tGE0VcrdwA==} + /es-abstract@1.23.3: + resolution: {integrity: sha512-e+HfNH61Bj1X9/jLc5v1owaLYuHdeHHSQlkhCBiTK8rBvKaULl/beGMxwrMXjpYrv4pz22BlY570vVePA2ho4A==} engines: {node: '>= 0.4'} dependencies: - array-buffer-byte-length: 1.0.0 - arraybuffer.prototype.slice: 1.0.2 - available-typed-arrays: 1.0.5 - call-bind: 1.0.5 - es-set-tostringtag: 2.0.2 + array-buffer-byte-length: 1.0.1 + arraybuffer.prototype.slice: 1.0.3 + available-typed-arrays: 1.0.7 + call-bind: 1.0.7 + data-view-buffer: 1.0.1 + data-view-byte-length: 1.0.1 + data-view-byte-offset: 1.0.0 + es-define-property: 1.0.0 + es-errors: 1.3.0 + es-object-atoms: 1.0.0 + es-set-tostringtag: 2.0.3 es-to-primitive: 1.2.1 function.prototype.name: 1.1.6 - get-intrinsic: 1.2.2 - get-symbol-description: 1.0.0 - globalthis: 1.0.3 + get-intrinsic: 1.2.4 + get-symbol-description: 1.0.2 + globalthis: 1.0.4 gopd: 1.0.1 - has-property-descriptors: 1.0.1 - has-proto: 1.0.1 + has-property-descriptors: 1.0.2 + has-proto: 1.0.3 has-symbols: 1.0.3 - hasown: 2.0.0 - internal-slot: 1.0.6 - is-array-buffer: 3.0.2 + hasown: 2.0.2 + internal-slot: 1.0.7 + is-array-buffer: 3.0.4 is-callable: 1.2.7 - is-negative-zero: 2.0.2 + is-data-view: 1.0.1 + is-negative-zero: 2.0.3 is-regex: 1.1.4 - is-shared-array-buffer: 1.0.2 + is-shared-array-buffer: 1.0.3 is-string: 1.0.7 - is-typed-array: 1.1.12 + is-typed-array: 1.1.13 is-weakref: 1.0.2 - object-inspect: 1.13.1 + object-inspect: 1.13.2 object-keys: 1.1.1 object.assign: 4.1.5 - regexp.prototype.flags: 1.5.1 - safe-array-concat: 1.1.0 - safe-regex-test: 1.0.2 - string.prototype.trim: 1.2.8 - string.prototype.trimend: 1.0.7 - string.prototype.trimstart: 1.0.7 - typed-array-buffer: 1.0.0 - typed-array-byte-length: 1.0.0 - typed-array-byte-offset: 1.0.0 - typed-array-length: 1.0.4 + regexp.prototype.flags: 1.5.3 + safe-array-concat: 1.1.2 + safe-regex-test: 1.0.3 + string.prototype.trim: 1.2.9 + string.prototype.trimend: 1.0.8 + string.prototype.trimstart: 1.0.8 + typed-array-buffer: 1.0.2 + typed-array-byte-length: 1.0.1 + typed-array-byte-offset: 1.0.2 + typed-array-length: 1.0.6 unbox-primitive: 1.0.2 - which-typed-array: 1.1.13 + which-typed-array: 1.1.15 dev: true - /es-module-lexer@0.9.3: - resolution: {integrity: sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==} + /es-define-property@1.0.0: + resolution: {integrity: sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==} + engines: {node: '>= 0.4'} + dependencies: + get-intrinsic: 1.2.4 + + /es-errors@1.3.0: + resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} + engines: {node: '>= 0.4'} + + /es-module-lexer@1.5.4: + resolution: {integrity: sha512-MVNK56NiMrOwitFB7cqDwq0CQutbw+0BvLshJSse0MUNU+y1FC3bUS/AQg7oUng+/wKrrki7JfmwtVHkVfPLlw==} + dev: true + + /es-object-atoms@1.0.0: + resolution: {integrity: sha512-MZ4iQ6JwHOBQjahnjwaC1ZtIBH+2ohjamzAO3oaHcXYup7qxjF2fixyH+Q71voWHeOkI2q/TnJao/KfXYIZWbw==} + engines: {node: '>= 0.4'} + dependencies: + es-errors: 1.3.0 dev: true - /es-set-tostringtag@2.0.2: - resolution: {integrity: sha512-BuDyupZt65P9D2D2vA/zqcI3G5xRsklm5N3xCwuiy+/vKy8i0ifdsQP1sLgO4tZDSCaQUSnmC48khknGMV3D2Q==} + /es-set-tostringtag@2.0.3: + resolution: {integrity: sha512-3T8uNMC3OQTHkFUsFq8r/BwAXLHvU/9O9mE0fBc/MY5iq/8H7ncvO947LmYA6ldWw9Uh8Yhf25zu6n7nML5QWQ==} engines: {node: '>= 0.4'} dependencies: - get-intrinsic: 1.2.2 - has-tostringtag: 1.0.0 - hasown: 2.0.0 + get-intrinsic: 1.2.4 + has-tostringtag: 1.0.2 + hasown: 2.0.2 dev: true /es-shim-unscopables@1.0.2: resolution: {integrity: sha512-J3yBRXCzDu4ULnQwxyToo/OjdMx6akgVC7K6few0a7F/0wLtmKKN7I73AH5T2836UuXRqN7Qg+IIUw/+YJksRw==} dependencies: - hasown: 2.0.0 + hasown: 2.0.2 dev: true /es-to-primitive@1.2.1: @@ -2527,8 +2565,8 @@ packages: resolution: {integrity: sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==} dev: true - /escalade@3.1.1: - resolution: {integrity: sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==} + /escalade@3.2.0: + resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} engines: {node: '>=6'} dev: true @@ -2549,14 +2587,14 @@ packages: resolution: {integrity: sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==} dependencies: debug: 3.2.7 - is-core-module: 2.13.1 + is-core-module: 2.15.1 resolve: 1.22.8 transitivePeerDependencies: - supports-color dev: true - /eslint-module-utils@2.8.0(@typescript-eslint/parser@4.19.0)(eslint-import-resolver-node@0.3.9)(eslint@7.29.0): - resolution: {integrity: sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw==} + /eslint-module-utils@2.12.0(@typescript-eslint/parser@4.19.0)(eslint-import-resolver-node@0.3.9)(eslint@7.29.0): + resolution: {integrity: sha512-wALZ0HFoytlyh/1+4wuZ9FJCD/leWHQzzrxJ8+rebyReSLk7LApMyd3WJaLVoN+D5+WIdJyDK1c6JnE65V4Zyg==} engines: {node: '>=4'} peerDependencies: '@typescript-eslint/parser': '*' @@ -2603,18 +2641,18 @@ packages: optional: true dependencies: '@typescript-eslint/parser': 4.19.0(eslint@7.29.0)(typescript@4.5.5) - array-includes: 3.1.7 + array-includes: 3.1.8 array.prototype.flat: 1.3.2 debug: 2.6.9 doctrine: 2.1.0 eslint: 7.29.0 eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.8.0(@typescript-eslint/parser@4.19.0)(eslint-import-resolver-node@0.3.9)(eslint@7.29.0) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@4.19.0)(eslint-import-resolver-node@0.3.9)(eslint@7.29.0) has: 1.0.4 - is-core-module: 2.13.1 + is-core-module: 2.15.1 is-glob: 4.0.3 minimatch: 3.1.2 - object.values: 1.1.7 + object.values: 1.2.0 resolve: 1.22.8 tsconfig-paths: 3.15.0 transitivePeerDependencies: @@ -2681,9 +2719,9 @@ packages: '@babel/code-frame': 7.12.11 '@eslint/eslintrc': 0.4.3 ajv: 6.12.6 - chalk: 4.1.2 + chalk: 4.1.0 cross-spawn: 7.0.3 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 doctrine: 3.0.0 enquirer: 2.4.1 escape-string-regexp: 4.0.0 @@ -2691,7 +2729,7 @@ packages: eslint-utils: 2.1.0 eslint-visitor-keys: 2.1.0 espree: 7.3.1 - esquery: 1.5.0 + esquery: 1.6.0 esutils: 2.0.3 fast-deep-equal: 3.1.3 file-entry-cache: 6.0.1 @@ -2708,13 +2746,13 @@ packages: lodash.merge: 4.6.2 minimatch: 3.1.2 natural-compare: 1.4.0 - optionator: 0.9.3 + optionator: 0.9.4 progress: 2.0.3 regexpp: 3.2.0 semver: 7.5.4 strip-ansi: 6.0.1 strip-json-comments: 3.1.1 - table: 6.8.1 + table: 6.8.2 text-table: 0.2.0 v8-compile-cache: 2.4.0 transitivePeerDependencies: @@ -2742,8 +2780,8 @@ packages: hasBin: true dev: true - /esquery@1.5.0: - resolution: {integrity: sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg==} + /esquery@1.6.0: + resolution: {integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==} engines: {node: '>=0.10'} dependencies: estraverse: 5.3.0 @@ -2795,56 +2833,41 @@ packages: strip-final-newline: 2.0.0 dev: true - /execa@5.1.1: - resolution: {integrity: sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==} - engines: {node: '>=10'} - dependencies: - cross-spawn: 7.0.3 - get-stream: 6.0.1 - human-signals: 2.1.0 - is-stream: 2.0.1 - merge-stream: 2.0.0 - npm-run-path: 4.0.1 - onetime: 5.1.2 - signal-exit: 3.0.7 - strip-final-newline: 2.0.0 - dev: true - /expand-template@2.0.3: resolution: {integrity: sha512-XYfuKMvj4O35f/pOXLObndIRvyQ+/+6AhODh+OKWj9S9498pHHn/IMszH+gt0fBCRWMNfk1ZSp5x3AifmnI2vg==} engines: {node: '>=6'} requiresBuild: true - /express@4.19.2: - resolution: {integrity: sha512-5T6nhjsT+EOMzuck8JjBHARTHfMht0POzlA60WV2pMD3gyXw2LZnZ+ueGdNxG+0calOJcWKbpFcuzLZ91YWq9Q==} + /express@4.21.1: + resolution: {integrity: sha512-YSFlK1Ee0/GC8QaO91tHcDxJiE/X4FbpAyQWkxAvG6AXCuR65YzK8ua6D9hvi/TzUfZMpc+BwuM1IPw8fmQBiQ==} engines: {node: '>= 0.10.0'} dependencies: accepts: 1.3.8 array-flatten: 1.1.1 - body-parser: 1.20.2 + body-parser: 1.20.3 content-disposition: 0.5.4 content-type: 1.0.5 - cookie: 0.6.0 + cookie: 0.7.1 cookie-signature: 1.0.6 debug: 2.6.9 depd: 2.0.0 - encodeurl: 1.0.2 + encodeurl: 2.0.0 escape-html: 1.0.3 etag: 1.8.1 - finalhandler: 1.2.0 + finalhandler: 1.3.1 fresh: 0.5.2 http-errors: 2.0.0 - merge-descriptors: 1.0.1 + merge-descriptors: 1.0.3 methods: 1.1.2 on-finished: 2.4.1 parseurl: 1.3.3 - path-to-regexp: 0.1.7 + path-to-regexp: 0.1.10 proxy-addr: 2.0.7 - qs: 6.11.0 + qs: 6.13.0 range-parser: 1.2.1 safe-buffer: 5.2.1 - send: 0.18.0 - serve-static: 1.15.0 + send: 0.19.0 + serve-static: 1.16.2 setprototypeof: 1.2.0 statuses: 2.0.1 type-is: 1.6.18 @@ -2879,7 +2902,7 @@ packages: '@nodelib/fs.walk': 1.2.8 glob-parent: 5.1.2 merge2: 1.4.1 - micromatch: 4.0.5 + micromatch: 4.0.8 dev: true /fast-json-stable-stringify@2.1.0: @@ -2890,13 +2913,17 @@ packages: resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} dev: true + /fast-uri@3.0.3: + resolution: {integrity: sha512-aLrHthzCjH5He4Z2H9YZ+v6Ujb9ocRuW6ZzkJQOrTxleEijANq4v1TsaPaVG1PZcuurEzrLcWRyYBYXD5cEiaw==} + dev: true + /fastest-levenshtein@1.0.16: resolution: {integrity: sha512-eRnCtTTtGZFpQCwhJiUOuxPQWRXVKYDn0b2PeHfXL6/Zi53SLAzAHfVhVWK2AryC/WH05kGfxhFIPvTF0SXQzg==} engines: {node: '>= 4.9.1'} dev: true - /fastq@1.16.0: - resolution: {integrity: sha512-ifCoaXsDrsdkWTtiNJX5uzHDsrck5TzfKKDcuFFTIrrc/BS076qgEIfoIy1VeZqViznfKiysPYTh/QeHtnIsYA==} + /fastq@1.17.1: + resolution: {integrity: sha512-sRVD3lWVIXWg6By68ZN7vho9a1pQcN/WBFaAAsDDFzlJjvoGx0P8z7V1t72grFJfJhu3YPZBuu25f7Kaw2jN1w==} dependencies: reusify: 1.0.4 dev: true @@ -2915,19 +2942,19 @@ packages: flat-cache: 3.2.0 dev: true - /fill-range@7.0.1: - resolution: {integrity: sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==} + /fill-range@7.1.1: + resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} engines: {node: '>=8'} dependencies: to-regex-range: 5.0.1 dev: true - /finalhandler@1.2.0: - resolution: {integrity: sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==} + /finalhandler@1.3.1: + resolution: {integrity: sha512-6BN9trH7bp3qvnrRyzsBz+g3lZxTNZTbVO2EV1CS0WIcDbawYVdYvGflME/9QP0h0pYlCDBCTjYa9nZzMDpyxQ==} engines: {node: '>= 0.8'} dependencies: debug: 2.6.9 - encodeurl: 1.0.2 + encodeurl: 2.0.0 escape-html: 1.0.3 on-finished: 2.4.1 parseurl: 1.3.3 @@ -2966,7 +2993,7 @@ packages: resolution: {integrity: sha512-CYcENa+FtcUKLmhhqyctpclsq7QF38pKjZHsGNiSQF5r4FtoKDWabFDl3hzaEQMvT1LHEysw5twgLvpYYb4vbw==} engines: {node: ^10.12.0 || >=12.0.0} dependencies: - flatted: 3.2.9 + flatted: 3.3.1 keyv: 4.5.4 rimraf: 3.0.2 dev: true @@ -2976,8 +3003,8 @@ packages: hasBin: true dev: true - /flatted@3.2.9: - resolution: {integrity: sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ==} + /flatted@3.3.1: + resolution: {integrity: sha512-X8cqMLLie7KsNUDSdzeN8FYK9rEt4Dt67OsG/DNGnYTSDBG4uFAJFBnUeiV+zCVAvwFy56IjM9sH51jVaEhNxw==} dev: true /for-each@0.3.3: @@ -2994,8 +3021,8 @@ packages: signal-exit: 3.0.7 dev: true - /foreground-child@3.1.1: - resolution: {integrity: sha512-TMKDUnIte6bfb5nWv7V/caI169OHgvwjb7V4WkeUvbQQdjr5rWKqHFiKWb/fcOwB+CzBT+qbWjvj+DVwRskpIg==} + /foreground-child@3.3.0: + resolution: {integrity: sha512-Ld2g8rrAyMYFXBhEqMz8ZAHBi4J4uS1i/CxGMDnjyFWddMXLVcDp051DZfu+t7+ab7Wv6SMqpWmyFIj5UbfFvg==} engines: {node: '>=14'} dependencies: cross-spawn: 7.0.3 @@ -3049,9 +3076,9 @@ packages: resolution: {integrity: sha512-Z5kx79swU5P27WEayXM1tBi5Ze/lbIyiNgU3qyXUOf9b2rgXYyF9Dy9Cx+IQv/Lc8WCG6L82zwUPpSS9hGehIg==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-abstract: 1.23.3 functions-have-names: 1.2.3 dev: true @@ -3065,6 +3092,7 @@ packages: /gauge@2.7.4: resolution: {integrity: sha512-14x4kjc6lkD3ltw589k0NrPD6cCNTD6CWoVUNpB85+DrtONoZn+Rug6xZU5RvSC4+TZPxA5AnBibQYAvZn41Hg==} + deprecated: This package is no longer supported. requiresBuild: true dependencies: aproba: 1.2.0 @@ -3090,13 +3118,15 @@ packages: resolution: {integrity: sha512-8vXOvuE167CtIc3OyItco7N/dpRtBbYOsPsXCz7X/PMnlGjYjSGuZJgM1Y7mmew7BKf9BqvLX2tnOVy1BBUsxQ==} dev: true - /get-intrinsic@1.2.2: - resolution: {integrity: sha512-0gSo4ml/0j98Y3lngkFEot/zhiCeWsbYIlZ+uZOVgzLyLaUw7wxUL+nCTP0XJvJg1AXulJRI3UJi8GsbDuxdGA==} + /get-intrinsic@1.2.4: + resolution: {integrity: sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==} + engines: {node: '>= 0.4'} dependencies: + es-errors: 1.3.0 function-bind: 1.1.2 - has-proto: 1.0.1 + has-proto: 1.0.3 has-symbols: 1.0.3 - hasown: 2.0.0 + hasown: 2.0.2 /get-own-enumerable-property-symbols@3.0.2: resolution: {integrity: sha512-I0UBV/XOz1XkIJHEUDMZAbzCThU/H8DxmSfmdGcKPnVhu2VfFqr34jr9777IyaTYvxjedWhqVIilEDsCdP5G6g==} @@ -3111,20 +3141,16 @@ packages: resolution: {integrity: sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==} engines: {node: '>=8'} dependencies: - pump: 3.0.0 + pump: 3.0.2 dev: true - /get-stream@6.0.1: - resolution: {integrity: sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==} - engines: {node: '>=10'} - dev: true - - /get-symbol-description@1.0.0: - resolution: {integrity: sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==} + /get-symbol-description@1.0.2: + resolution: {integrity: sha512-g0QYk1dZBxGwk+Ngc+ltRH2IBp2f7zBkBMBJZCDerh6EhlhSR6+9irMCuT/09zD6qkarHUSn529sK/yL4S27mg==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 + call-bind: 1.0.7 + es-errors: 1.3.0 + get-intrinsic: 1.2.4 dev: true /github-from-package@0.0.0: @@ -3149,20 +3175,21 @@ packages: resolution: {integrity: sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==} dev: true - /glob@10.3.10: - resolution: {integrity: sha512-fa46+tv1Ak0UPK1TOy/pZrIybNNt4HCv7SDzwyfiOZkvZLEbjsZkJBPtDHVshZjbecAoAGSC20MjLDG/qr679g==} - engines: {node: '>=16 || 14 >=14.17'} + /glob@10.4.5: + resolution: {integrity: sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg==} hasBin: true dependencies: - foreground-child: 3.1.1 - jackspeak: 2.3.6 - minimatch: 9.0.3 - minipass: 7.0.4 - path-scurry: 1.10.1 + foreground-child: 3.3.0 + jackspeak: 3.4.3 + minimatch: 9.0.5 + minipass: 7.1.2 + package-json-from-dist: 1.0.1 + path-scurry: 1.11.1 dev: true /glob@7.2.0: resolution: {integrity: sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q==} + deprecated: Glob versions prior to v9 are no longer supported dependencies: fs.realpath: 1.0.0 inflight: 1.0.6 @@ -3174,6 +3201,7 @@ packages: /glob@7.2.3: resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} + deprecated: Glob versions prior to v9 are no longer supported dependencies: fs.realpath: 1.0.0 inflight: 1.0.6 @@ -3195,11 +3223,12 @@ packages: type-fest: 0.20.2 dev: true - /globalthis@1.0.3: - resolution: {integrity: sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA==} + /globalthis@1.0.4: + resolution: {integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==} engines: {node: '>= 0.4'} dependencies: define-properties: 1.2.1 + gopd: 1.0.1 dev: true /globby@11.1.0: @@ -3209,7 +3238,7 @@ packages: array-union: 2.1.0 dir-glob: 3.0.1 fast-glob: 3.3.2 - ignore: 5.3.0 + ignore: 5.3.2 merge2: 1.4.1 slash: 3.0.0 dev: true @@ -3217,7 +3246,7 @@ packages: /gopd@1.0.1: resolution: {integrity: sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==} dependencies: - get-intrinsic: 1.2.2 + get-intrinsic: 1.2.4 /graceful-fs@4.2.11: resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==} @@ -3235,21 +3264,21 @@ packages: resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} engines: {node: '>=8'} - /has-property-descriptors@1.0.1: - resolution: {integrity: sha512-VsX8eaIewvas0xnvinAe9bw4WfIeODpGYikiWYLH+dma0Jw6KHYqWiWfhQlgOVK8D6PvjubK5Uc4P0iIhIcNVg==} + /has-property-descriptors@1.0.2: + resolution: {integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==} dependencies: - get-intrinsic: 1.2.2 + es-define-property: 1.0.0 - /has-proto@1.0.1: - resolution: {integrity: sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==} + /has-proto@1.0.3: + resolution: {integrity: sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==} engines: {node: '>= 0.4'} /has-symbols@1.0.3: resolution: {integrity: sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==} engines: {node: '>= 0.4'} - /has-tostringtag@1.0.0: - resolution: {integrity: sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==} + /has-tostringtag@1.0.2: + resolution: {integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==} engines: {node: '>= 0.4'} dependencies: has-symbols: 1.0.3 @@ -3272,8 +3301,8 @@ packages: type-fest: 0.8.1 dev: true - /hasown@2.0.0: - resolution: {integrity: sha512-vUptKVTpIJhcczKBbgnS+RtcuYMB8+oNzPK2/Hp3hanz8JmpATdmmgLgSaadVREkDm+e2giHwY3ZRkyjSIDDFA==} + /hasown@2.0.2: + resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} engines: {node: '>= 0.4'} dependencies: function-bind: 1.1.2 @@ -3301,7 +3330,7 @@ packages: terser: 4.8.1 dev: true - /html-webpack-plugin@5.3.1(webpack@5.62.1): + /html-webpack-plugin@5.3.1(webpack@5.95.0): resolution: {integrity: sha512-rZsVvPXUYFyME0cuGkyOHfx9hmkFa4pWfxY/mdY38PsBEaVNsRoA+Id+8z6DBDgyv3zaw6XQszdF8HLwfQvcdQ==} engines: {node: '>=10.13.0'} peerDependencies: @@ -3312,7 +3341,7 @@ packages: lodash: 4.17.21 pretty-error: 2.1.2 tapable: 2.2.1 - webpack: 5.62.1(webpack-cli@4.7.2) + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /htmlparser2@6.1.0: @@ -3335,23 +3364,22 @@ packages: toidentifier: 1.0.1 dev: false - /http-proxy-agent@5.0.0: - resolution: {integrity: sha512-n2hY8YdoRE1i7r6M0w9DIw5GgZN0G25P8zLCRQ8rjXtTU3vsNFBI/vWK/UIeE6g5MUUz6avwAPXmL6Fy9D/90w==} - engines: {node: '>= 6'} + /http-proxy-agent@7.0.2: + resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==} + engines: {node: '>= 14'} dependencies: - '@tootallnate/once': 2.0.0 - agent-base: 6.0.2 - debug: 4.3.4(supports-color@8.1.1) + agent-base: 7.1.1 + debug: 4.3.7 transitivePeerDependencies: - supports-color dev: false - /https-proxy-agent@5.0.1: - resolution: {integrity: sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==} - engines: {node: '>= 6'} + /https-proxy-agent@7.0.5: + resolution: {integrity: sha512-1e4Wqeblerz+tMKPIq2EMGiiWW1dIjZOksyHWSUm1rmuvw/how9hBHZ38lAGj5ID4Ik6EdkOw7NmWPy6LAwalw==} + engines: {node: '>= 14'} dependencies: - agent-base: 6.0.2 - debug: 4.3.4(supports-color@8.1.1) + agent-base: 7.1.1 + debug: 4.3.7 transitivePeerDependencies: - supports-color dev: false @@ -3361,11 +3389,6 @@ packages: engines: {node: '>=8.12.0'} dev: true - /human-signals@2.1.0: - resolution: {integrity: sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==} - engines: {node: '>=10.17.0'} - dev: true - /iconv-lite@0.4.24: resolution: {integrity: sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==} engines: {node: '>=0.10.0'} @@ -3373,13 +3396,13 @@ packages: safer-buffer: 2.1.2 dev: false - /icss-utils@5.1.0(postcss@8.4.33): + /icss-utils@5.1.0(postcss@8.4.47): resolution: {integrity: sha512-soFhflCVWLfRNOPU3iv5Z9VUdT44xFRbzjLsEzSr5AQmgqPMTHdU3PMT1Cf1ssx8fLNJDA1juftYl+PUcv3MqA==} engines: {node: ^10 || ^12 || >= 14} peerDependencies: postcss: ^8.1.0 dependencies: - postcss: 8.4.33 + postcss: 8.4.47 dev: true /ieee754@1.2.1: @@ -3391,8 +3414,8 @@ packages: engines: {node: '>= 4'} dev: true - /ignore@5.3.0: - resolution: {integrity: sha512-g7dmpshy+gD7mh88OC9NwSGTKoc3kyLAZQRU1mt53Aw/vnvfXnbC+F/7F7QoYVKbV+KNvJx8wArewKy1vXMtlg==} + /ignore@5.3.2: + resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==} engines: {node: '>= 4'} dev: true @@ -3404,8 +3427,8 @@ packages: resolve-from: 4.0.0 dev: true - /import-local@3.1.0: - resolution: {integrity: sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg==} + /import-local@3.2.0: + resolution: {integrity: sha512-2SPlun1JUPWoM6t3F0dw0FkCF/jWY8kttcY4f599GLTSjh2OCuuhdTkJQsEcZzBqbXZGKMK2OqW1oZsjtf/gQA==} engines: {node: '>=8'} hasBin: true dependencies: @@ -3425,6 +3448,7 @@ packages: /inflight@1.0.6: resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==} + deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful. dependencies: once: 1.4.0 wrappy: 1.0.2 @@ -3437,18 +3461,18 @@ packages: resolution: {integrity: sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==} requiresBuild: true - /internal-slot@1.0.6: - resolution: {integrity: sha512-Xj6dv+PsbtwyPpEflsejS+oIZxmMlV44zAhG479uYu89MsjcYOhCFnNyKrkJrihbsiasQyY0afoCl/9BLR65bg==} + /internal-slot@1.0.7: + resolution: {integrity: sha512-NGnrKwXzSms2qUUih/ILZ5JBqNTSa1+ZmP6flaIp6KmSElgE9qdndzS3cqjrDovwFdmwsGsLdeFgB6suw+1e9g==} engines: {node: '>= 0.4'} dependencies: - get-intrinsic: 1.2.2 - hasown: 2.0.0 - side-channel: 1.0.4 + es-errors: 1.3.0 + hasown: 2.0.2 + side-channel: 1.0.6 dev: true - /interpret@2.2.0: - resolution: {integrity: sha512-Ju0Bz/cEia55xDwUWEa8+olFpCiQoypjnQySseKtmjNrnps3P+xfpUmGr90T7yjlVJmOtybRvPXhKMbHr+fWnw==} - engines: {node: '>= 0.10'} + /interpret@3.1.1: + resolution: {integrity: sha512-6xwYfHbajpoF0xLW+iwLkhwgvLoZDfjYfoFNu8ftMoXINzwuymNLd9u/KmwtdT2GbR+/Cz66otEGEVVUHX9QLQ==} + engines: {node: '>=10.13.0'} dev: true /ipaddr.js@1.9.1: @@ -3456,12 +3480,12 @@ packages: engines: {node: '>= 0.10'} dev: false - /is-array-buffer@3.0.2: - resolution: {integrity: sha512-y+FyyR/w8vfIRq4eQcM1EYgSTnmHXPqaF+IgzgraytCFq5Xh8lllDVmAZolPJiZttZLeFSINPYMaEJ7/vWUa1w==} + /is-array-buffer@3.0.4: + resolution: {integrity: sha512-wcjaerHw0ydZwfhiKbXJWLDY8A7yV7KhjQOpb83hGgGfId/aQa4TOvwyzn2PuswW2gPCYEL/nEAiSVpdOj1lXw==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 - is-typed-array: 1.1.12 + call-bind: 1.0.7 + get-intrinsic: 1.2.4 dev: true /is-arrayish@0.2.1: @@ -3478,15 +3502,15 @@ packages: resolution: {integrity: sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==} engines: {node: '>=8'} dependencies: - binary-extensions: 2.2.0 + binary-extensions: 2.3.0 dev: true /is-boolean-object@1.1.2: resolution: {integrity: sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - has-tostringtag: 1.0.0 + call-bind: 1.0.7 + has-tostringtag: 1.0.2 dev: true /is-callable@1.2.7: @@ -3494,17 +3518,25 @@ packages: engines: {node: '>= 0.4'} dev: true - /is-core-module@2.13.1: - resolution: {integrity: sha512-hHrIjvZsftOsvKSn2TRYl63zvxsgE0K+0mYMoH6gD4omR5IWB2KynivBQczo3+wF1cCkjzvptnI9Q0sPU66ilw==} + /is-core-module@2.15.1: + resolution: {integrity: sha512-z0vtXSwucUJtANQWldhbtbt7BnL0vxiFjIdDLAatwhDYty2bad6s+rijD6Ri4YuYJubLzIJLUidCh09e1djEVQ==} + engines: {node: '>= 0.4'} dependencies: - hasown: 2.0.0 + hasown: 2.0.2 + dev: true + + /is-data-view@1.0.1: + resolution: {integrity: sha512-AHkaJrsUVW6wq6JS8y3JnM/GJF/9cf+k20+iDzlSaJrinEo5+7vRiteOSwBhHRiAyQATN1AmY4hwzxJKPmYf+w==} + engines: {node: '>= 0.4'} + dependencies: + is-typed-array: 1.1.13 dev: true /is-date-object@1.0.5: resolution: {integrity: sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==} engines: {node: '>= 0.4'} dependencies: - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /is-docker@2.2.1: @@ -3536,8 +3568,8 @@ packages: is-extglob: 2.1.1 dev: true - /is-negative-zero@2.0.2: - resolution: {integrity: sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==} + /is-negative-zero@2.0.3: + resolution: {integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==} engines: {node: '>= 0.4'} dev: true @@ -3545,7 +3577,7 @@ packages: resolution: {integrity: sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==} engines: {node: '>= 0.4'} dependencies: - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /is-number@7.0.0: @@ -3574,8 +3606,8 @@ packages: resolution: {integrity: sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - has-tostringtag: 1.0.0 + call-bind: 1.0.7 + has-tostringtag: 1.0.2 dev: true /is-regexp@1.0.0: @@ -3583,10 +3615,11 @@ packages: engines: {node: '>=0.10.0'} dev: true - /is-shared-array-buffer@1.0.2: - resolution: {integrity: sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==} + /is-shared-array-buffer@1.0.3: + resolution: {integrity: sha512-nA2hv5XIhLR3uVzDDfCIknerhx8XUKnstuOERPNNIinXG7v9u+ohXF67vxm4TPTEPU6lm61ZkwP3c9PCB97rhg==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 dev: true /is-stream@2.0.1: @@ -3598,7 +3631,7 @@ packages: resolution: {integrity: sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==} engines: {node: '>= 0.4'} dependencies: - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /is-symbol@1.0.4: @@ -3608,11 +3641,11 @@ packages: has-symbols: 1.0.3 dev: true - /is-typed-array@1.1.12: - resolution: {integrity: sha512-Z14TF2JNG8Lss5/HMqt0//T9JeHXttXy5pH/DBU4vi98ozO2btxzq9MwYDZYnKwU8nRsz/+GVFVRDq3DkVuSPg==} + /is-typed-array@1.1.13: + resolution: {integrity: sha512-uZ25/bUAlUY5fR4OKT4rZQEBrzQWYV9ZJYGGsUmEJ6thodVJ1HX64ePQ6Z0qPWP+m+Uq6e9UugrE38jeYsDSMw==} engines: {node: '>= 0.4'} dependencies: - which-typed-array: 1.1.13 + which-typed-array: 1.1.15 dev: true /is-typedarray@1.0.0: @@ -3627,7 +3660,7 @@ packages: /is-weakref@1.0.2: resolution: {integrity: sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 dev: true /is-windows@1.0.2: @@ -3678,7 +3711,7 @@ packages: resolution: {integrity: sha512-BXgQl9kf4WTCPCCpmFGoJkz/+uhvm7h7PFKUYxh7qarQd3ER33vHG//qaE8eN25l07YqZPpHXU9I09l/RD5aGQ==} engines: {node: '>=8'} dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 '@istanbuljs/schema': 0.1.3 istanbul-lib-coverage: 3.2.2 semver: 6.3.1 @@ -3711,24 +3744,23 @@ packages: resolution: {integrity: sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==} engines: {node: '>=10'} dependencies: - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 istanbul-lib-coverage: 3.2.2 source-map: 0.6.1 transitivePeerDependencies: - supports-color dev: true - /istanbul-reports@3.1.6: - resolution: {integrity: sha512-TLgnMkKg3iTDsQ9PbPTdpfAK2DzjF9mqUG7RMgcQl8oFjad8ob4laGxv5XV5U9MAfx8D6tSJiUyuAwzLicaxlg==} + /istanbul-reports@3.1.7: + resolution: {integrity: sha512-BewmUXImeuRk2YY0PVbxgKAysvhRPUQE0h5QRM++nVWyubKGV0l8qQ5op8+B2DOmwSe63Jivj0BjkPQVf8fP5g==} engines: {node: '>=8'} dependencies: html-escaper: 2.0.2 istanbul-lib-report: 3.0.1 dev: true - /jackspeak@2.3.6: - resolution: {integrity: sha512-N3yCS/NegsOBokc8GAdM8UcmfsKiSS8cipheD/nivzr700H+nsMOxJjQnvwOcRYVuFkdH0wGUvW2WbXGmrZGbQ==} - engines: {node: '>=14'} + /jackspeak@3.4.3: + resolution: {integrity: sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw==} dependencies: '@isaacs/cliui': 8.0.2 optionalDependencies: @@ -3772,9 +3804,9 @@ packages: argparse: 2.0.1 dev: true - /jsesc@2.5.2: - resolution: {integrity: sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==} - engines: {node: '>=4'} + /jsesc@3.0.2: + resolution: {integrity: sha512-xKqzzWXDttJuOcawBt4KnKHHIf5oQ/Cxax+0PWFG+DFDgHNAdi+TXECADI+RYiFUMmx8792xsMbbgXj4CwnP4g==} + engines: {node: '>=6'} hasBin: true dev: true @@ -3782,10 +3814,6 @@ packages: resolution: {integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==} dev: true - /json-parse-better-errors@1.0.2: - resolution: {integrity: sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==} - dev: true - /json-parse-even-better-errors@2.3.1: resolution: {integrity: sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==} dev: true @@ -3921,13 +3949,13 @@ packages: cli-truncate: 2.1.0 commander: 6.2.1 cosmiconfig: 7.1.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7 dedent: 0.7.0 enquirer: 2.4.1 execa: 4.1.0 listr2: 3.14.0(enquirer@2.4.1) log-symbols: 4.1.0 - micromatch: 4.0.5 + micromatch: 4.0.8 normalize-path: 3.0.0 please-upgrade-node: 3.2.0 string-argv: 0.3.1 @@ -3950,7 +3978,7 @@ packages: enquirer: 2.4.1 log-update: 4.0.0 p-map: 4.0.0 - rfdc: 1.3.1 + rfdc: 1.4.1 rxjs: 7.8.1 through: 2.3.8 wrap-ansi: 7.0.0 @@ -4044,7 +4072,7 @@ packages: resolution: {integrity: sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg==} engines: {node: '>=10'} dependencies: - chalk: 4.1.2 + chalk: 4.1.0 is-unicode-supported: 0.1.0 dev: true @@ -4064,9 +4092,8 @@ packages: tslib: 2.3.1 dev: true - /lru-cache@10.1.0: - resolution: {integrity: sha512-/1clY/ui8CzjKFyjdvwPWJUYKiFVXG2I2cY0ssG7h4+hwk+XOIX7ZSG9Q7TW8TW3Kp3BUSqgFWBLgL4PJ+Blag==} - engines: {node: 14 || >=16.14} + /lru-cache@10.4.3: + resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==} dev: true /lru-cache@5.1.1: @@ -4104,8 +4131,8 @@ packages: engines: {node: '>= 0.6'} dev: false - /merge-descriptors@1.0.1: - resolution: {integrity: sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==} + /merge-descriptors@1.0.3: + resolution: {integrity: sha512-gaNvAS7TZ897/rVaZ0nMtAyxNyi/pdbjbAwUpFQpN70GqnVfOiXpeUUMKRBmzXaSQ8DdTX4/0ms62r2K+hE6mQ==} dev: false /merge-stream@2.0.0: @@ -4122,11 +4149,11 @@ packages: engines: {node: '>= 0.6'} dev: false - /micromatch@4.0.5: - resolution: {integrity: sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==} + /micromatch@4.0.8: + resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} engines: {node: '>=8.6'} dependencies: - braces: 3.0.2 + braces: 3.0.3 picomatch: 2.3.1 dev: true @@ -4169,8 +4196,8 @@ packages: brace-expansion: 2.0.1 dev: true - /minimatch@9.0.3: - resolution: {integrity: sha512-RHiac9mvaRw0x3AYRgDC1CxAP7HTcNrrECeA8YYJeWnpo+2Q5CegtZjaotWTWxDG3UeGA1coE05iH1mPjT/2mg==} + /minimatch@9.0.5: + resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} engines: {node: '>=16 || 14 >=14.17'} dependencies: brace-expansion: 2.0.1 @@ -4179,8 +4206,8 @@ packages: /minimist@1.2.8: resolution: {integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==} - /minipass@7.0.4: - resolution: {integrity: sha512-jYofLM5Dam9279rdkWzqHozUo4ybjdZmCsDHePy5V/PbBcVMiSZR97gmAy45aqi8CK1lG2ECd356FU86avfwUQ==} + /minipass@7.1.2: + resolution: {integrity: sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw==} engines: {node: '>=16 || 14 >=14.17'} dev: true @@ -4239,6 +4266,7 @@ packages: /ms@2.1.2: resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==} + dev: true /ms@2.1.3: resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} @@ -4281,9 +4309,9 @@ packages: dependencies: '@sinonjs/commons': 1.8.6 '@sinonjs/fake-timers': 6.0.1 - '@sinonjs/text-encoding': 0.7.2 + '@sinonjs/text-encoding': 0.7.3 just-extend: 4.2.1 - path-to-regexp: 1.8.0 + path-to-regexp: 1.9.0 dev: true /no-case@3.0.4: @@ -4314,8 +4342,8 @@ packages: process-on-spawn: 1.0.0 dev: true - /node-releases@2.0.14: - resolution: {integrity: sha512-y10wOWt8yZpqXmOgRo77WaHEmhYQYGNA6y421PKsKYWEK8aW+cqAphborZDhqfyKrbZEN92CN1X2KbafY2s7Yw==} + /node-releases@2.0.18: + resolution: {integrity: sha512-d9VeXT4SJ7ZeOqGX6R5EM022wpL+eWPooLI+5UpWn2jCT1aosUQEhQP214x33Wkwx3JQMvIm+tIoVOdodFS40g==} dev: true /noms@0.0.0: @@ -4339,6 +4367,7 @@ packages: /npmlog@4.1.2: resolution: {integrity: sha512-2uUqazuKlTaSI/dC8AzicUck7+IrEaOnN/e0jd3Xtt1KcGpwx30v50mL7oPyr/h9bL3E4aZccVwpwP+5W9Vjkg==} + deprecated: This package is no longer supported. requiresBuild: true dependencies: are-we-there-yet: 1.1.7 @@ -4378,7 +4407,7 @@ packages: istanbul-lib-processinfo: 2.0.3 istanbul-lib-report: 3.0.1 istanbul-lib-source-maps: 4.0.1 - istanbul-reports: 3.1.6 + istanbul-reports: 3.1.7 make-dir: 3.1.0 node-preload: 0.2.1 p-map: 3.0.0 @@ -4398,8 +4427,9 @@ packages: engines: {node: '>=0.10.0'} requiresBuild: true - /object-inspect@1.13.1: - resolution: {integrity: sha512-5qoj1RUiKOMsCCNLV1CBiPYE10sziTsnmNxkAI/rZhiD63CF7IqdFGC/XzjWjpSgLf0LxXX3bDFIh0E18f6UhQ==} + /object-inspect@1.13.2: + resolution: {integrity: sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==} + engines: {node: '>= 0.4'} /object-keys@1.1.1: resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} @@ -4410,19 +4440,19 @@ packages: resolution: {integrity: sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 has-symbols: 1.0.3 object-keys: 1.1.1 dev: true - /object.values@1.1.7: - resolution: {integrity: sha512-aU6xnDFYT3x17e/f0IiiwlGPTy2jzMySGfUB4fq6z7CV8l85CWHDk5ErhyhpfDHhrOMwGFhSQkhMGHaIotA6Ng==} + /object.values@1.2.0: + resolution: {integrity: sha512-yBYjY9QX2hnRmZHAjG/f13MzmBzxzYgQhFrke06TTyKY5zSTEqkOeukBzIdVA3j3ulu8Qa3MbVFShV7T2RmGtQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-object-atoms: 1.0.0 dev: true /on-finished@2.4.1: @@ -4453,16 +4483,16 @@ packages: is-wsl: 2.2.0 dev: false - /optionator@0.9.3: - resolution: {integrity: sha512-JjCoypp+jKn1ttEFExxhetCKeJt9zhAgAve5FXHixTvFDW/5aEktX9bufBKLRRMdU7bNtpLfcGu94B3cdEJgjg==} + /optionator@0.9.4: + resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} engines: {node: '>= 0.8.0'} dependencies: - '@aashutoshrathi/word-wrap': 1.2.6 deep-is: 0.1.4 fast-levenshtein: 2.0.6 levn: 0.4.1 prelude-ls: 1.2.1 type-check: 0.4.0 + word-wrap: 1.2.5 dev: true /os-tmpdir@1.0.2: @@ -4527,6 +4557,10 @@ packages: release-zalgo: 1.0.0 dev: true + /package-json-from-dist@1.0.1: + resolution: {integrity: sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw==} + dev: true + /param-case@3.0.4: resolution: {integrity: sha512-RXlj7zCYokReqWpOPH9oYivUzLYZ5vAPIfEmCTNViosC78F8F0H9y7T7gG2M39ymgutxF5gcFEsyZQSph9Bp3A==} dependencies: @@ -4545,7 +4579,7 @@ packages: resolution: {integrity: sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==} engines: {node: '>=8'} dependencies: - '@babel/code-frame': 7.23.5 + '@babel/code-frame': 7.26.0 error-ex: 1.3.2 json-parse-even-better-errors: 2.3.1 lines-and-columns: 1.2.4 @@ -4582,20 +4616,20 @@ packages: resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} dev: true - /path-scurry@1.10.1: - resolution: {integrity: sha512-MkhCqzzBEpPvxxQ71Md0b1Kk51W01lrYvlMzSUaIzNsODdd7mqhiimSZlr+VegAz5Z6Vzt9Xg2ttE//XBhH3EQ==} - engines: {node: '>=16 || 14 >=14.17'} + /path-scurry@1.11.1: + resolution: {integrity: sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==} + engines: {node: '>=16 || 14 >=14.18'} dependencies: - lru-cache: 10.1.0 - minipass: 7.0.4 + lru-cache: 10.4.3 + minipass: 7.1.2 dev: true - /path-to-regexp@0.1.7: - resolution: {integrity: sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==} + /path-to-regexp@0.1.10: + resolution: {integrity: sha512-7lf7qcQidTku0Gu3YDPc8DJ1q7OOucfa/BSsIwjuh56VU7katFvuM8hULfkwB3Fns/rsVF7PwPKVw1sl5KQS9w==} dev: false - /path-to-regexp@1.8.0: - resolution: {integrity: sha512-n43JRhlUKUAlibEJhPeir1ncUID16QnEjNpwzNdO3Lm4ywrBpBZ5oLD0I6br9evr1Y9JTqwRtAh7JLoOzAQdVA==} + /path-to-regexp@1.9.0: + resolution: {integrity: sha512-xIp7/apCFJuUHdDLWe8O1HIkb0kQrOMb/0u6FXQjemHn/ii5LrIzU6bdECnsiTF/GjZkMEKg1xdiZwNqDYlZ6g==} dependencies: isarray: 0.0.1 dev: true @@ -4609,8 +4643,8 @@ packages: resolution: {integrity: sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ==} dev: true - /picocolors@1.0.0: - resolution: {integrity: sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==} + /picocolors@1.1.1: + resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} dev: true /picomatch@2.3.1: @@ -4631,49 +4665,54 @@ packages: semver-compare: 1.0.0 dev: true - /postcss-modules-extract-imports@3.0.0(postcss@8.4.33): - resolution: {integrity: sha512-bdHleFnP3kZ4NYDhuGlVK+CMrQ/pqUm8bx/oGL93K6gVwiclvX5x0n76fYMKuIGKzlABOy13zsvqjb0f92TEXw==} + /possible-typed-array-names@1.0.0: + resolution: {integrity: sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==} + engines: {node: '>= 0.4'} + dev: true + + /postcss-modules-extract-imports@3.1.0(postcss@8.4.47): + resolution: {integrity: sha512-k3kNe0aNFQDAZGbin48pL2VNidTF0w4/eASDsxlyspobzU3wZQLOGj7L9gfRe0Jo9/4uud09DsjFNH7winGv8Q==} engines: {node: ^10 || ^12 || >= 14} peerDependencies: postcss: ^8.1.0 dependencies: - postcss: 8.4.33 + postcss: 8.4.47 dev: true - /postcss-modules-local-by-default@4.0.4(postcss@8.4.33): - resolution: {integrity: sha512-L4QzMnOdVwRm1Qb8m4x8jsZzKAaPAgrUF1r/hjDR2Xj7R+8Zsf97jAlSQzWtKx5YNiNGN8QxmPFIc/sh+RQl+Q==} + /postcss-modules-local-by-default@4.0.5(postcss@8.4.47): + resolution: {integrity: sha512-6MieY7sIfTK0hYfafw1OMEG+2bg8Q1ocHCpoWLqOKj3JXlKu4G7btkmM/B7lFubYkYWmRSPLZi5chid63ZaZYw==} engines: {node: ^10 || ^12 || >= 14} peerDependencies: postcss: ^8.1.0 dependencies: - icss-utils: 5.1.0(postcss@8.4.33) - postcss: 8.4.33 - postcss-selector-parser: 6.0.15 + icss-utils: 5.1.0(postcss@8.4.47) + postcss: 8.4.47 + postcss-selector-parser: 6.1.2 postcss-value-parser: 4.2.0 dev: true - /postcss-modules-scope@3.1.1(postcss@8.4.33): - resolution: {integrity: sha512-uZgqzdTleelWjzJY+Fhti6F3C9iF1JR/dODLs/JDefozYcKTBCdD8BIl6nNPbTbcLnGrk56hzwZC2DaGNvYjzA==} + /postcss-modules-scope@3.2.0(postcss@8.4.47): + resolution: {integrity: sha512-oq+g1ssrsZOsx9M96c5w8laRmvEu9C3adDSjI8oTcbfkrTE8hx/zfyobUoWIxaKPO8bt6S62kxpw5GqypEw1QQ==} engines: {node: ^10 || ^12 || >= 14} peerDependencies: postcss: ^8.1.0 dependencies: - postcss: 8.4.33 - postcss-selector-parser: 6.0.15 + postcss: 8.4.47 + postcss-selector-parser: 6.1.2 dev: true - /postcss-modules-values@4.0.0(postcss@8.4.33): + /postcss-modules-values@4.0.0(postcss@8.4.47): resolution: {integrity: sha512-RDxHkAiEGI78gS2ofyvCsu7iycRv7oqw5xMWn9iMoR0N/7mf9D50ecQqUo5BZ9Zh2vH4bCUR/ktCqbB9m8vJjQ==} engines: {node: ^10 || ^12 || >= 14} peerDependencies: postcss: ^8.1.0 dependencies: - icss-utils: 5.1.0(postcss@8.4.33) - postcss: 8.4.33 + icss-utils: 5.1.0(postcss@8.4.47) + postcss: 8.4.47 dev: true - /postcss-selector-parser@6.0.15: - resolution: {integrity: sha512-rEYkQOMUCEMhsKbK66tbEU9QVIxbhN18YiniAwA7XQYTVBqrBy+P2p5JcdqsHgKM2zWylp8d7J6eszocfds5Sw==} + /postcss-selector-parser@6.1.2: + resolution: {integrity: sha512-Q8qQfPiZ+THO/3ZrOrO0cJJKfpYCagtMUkXbnEfmgUjwXg6z/WBeOyS9APBBPCTSiDV+s4SwQGu8yFsiMRIudg==} engines: {node: '>=4'} dependencies: cssesc: 3.0.0 @@ -4684,13 +4723,13 @@ packages: resolution: {integrity: sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==} dev: true - /postcss@8.4.33: - resolution: {integrity: sha512-Kkpbhhdjw2qQs2O2DGX+8m5OVqEcbB9HRBvuYM9pgrjEFUg30A9LmXNlTAUj4S9kgtGyrMbTzVjH7E+s5Re2yg==} + /postcss@8.4.47: + resolution: {integrity: sha512-56rxCq7G/XfB4EkXq9Egn5GCqugWvDFjafDOThIdMBsI15iqPqR5r15TfSr1YPYeEI19YeaXMCbY6u88Y76GLQ==} engines: {node: ^10 || ^12 || >=14} dependencies: nanoid: 3.3.7 - picocolors: 1.0.0 - source-map-js: 1.0.2 + picocolors: 1.1.1 + source-map-js: 1.2.1 dev: true /prebuild-install@6.1.4: @@ -4707,7 +4746,7 @@ packages: napi-build-utils: 1.0.2 node-abi: 2.30.1 npmlog: 4.1.2 - pump: 3.0.0 + pump: 3.0.2 rc: 1.2.8 simple-get: 3.1.1 tar-fs: 2.1.1 @@ -4766,8 +4805,8 @@ packages: ipaddr.js: 1.9.1 dev: false - /pump@3.0.0: - resolution: {integrity: sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==} + /pump@3.0.2: + resolution: {integrity: sha512-tUPXtzlGM8FE3P0ZL6DVs/3P58k9nk8/jZeQCurTJylQA8qFYzHFfhBJkuqyE0FifOsQ0uKWekiZ5g8wtr28cw==} dependencies: end-of-stream: 1.4.4 once: 1.4.0 @@ -4777,11 +4816,11 @@ packages: engines: {node: '>=6'} dev: true - /qs@6.11.0: - resolution: {integrity: sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==} + /qs@6.13.0: + resolution: {integrity: sha512-+38qI9SOr8tfZ4QmJNplMUxqjbe7LKvvZgWdExBOmd+egZTtjLB67Gu0HRX3u/XOq7UU2Nx6nsjvS16Z9uwfpg==} engines: {node: '>=0.6'} dependencies: - side-channel: 1.0.4 + side-channel: 1.0.6 dev: false /queue-microtask@1.2.3: @@ -4869,20 +4908,21 @@ packages: source-map: 0.5.7 dev: true - /rechoir@0.7.1: - resolution: {integrity: sha512-/njmZ8s1wVeR6pjTZ+0nCnv8SpZNRMT2D1RLOJQESlYFDBvwpTA4KWJpZ+sBJ4+vhjILRcK7JIFdGCdxEAAitg==} - engines: {node: '>= 0.10'} + /rechoir@0.8.0: + resolution: {integrity: sha512-/vxpCXddiX8NGfGO/mTafwjq4aFa/71pvamip0++IQk3zG8cbCj0fifNPrjjF1XMXUne91jL9OoxmdykoEtifQ==} + engines: {node: '>= 10.13.0'} dependencies: resolve: 1.22.8 dev: true - /regexp.prototype.flags@1.5.1: - resolution: {integrity: sha512-sy6TXMN+hnP/wMy+ISxg3krXx7BAtWVO4UouuCN/ziM9UEne0euamVNafDfvC83bRNr95y0V5iijeDQFUNpvrg==} + /regexp.prototype.flags@1.5.3: + resolution: {integrity: sha512-vqlC04+RQoFalODCbCumG2xIOvapzVMHwsyIGM/SIE8fRhFFsXeH8/QQ+s0T0kDAhKc4k30s73/0ydkHQz6HlQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - set-function-name: 2.0.1 + es-errors: 1.3.0 + set-function-name: 2.0.2 dev: true /regexpp@3.2.0: @@ -4947,7 +4987,7 @@ packages: resolution: {integrity: sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==} hasBin: true dependencies: - is-core-module: 2.13.1 + is-core-module: 2.15.1 path-parse: 1.0.7 supports-preserve-symlinks-flag: 1.0.0 dev: true @@ -4965,12 +5005,13 @@ packages: engines: {iojs: '>=1.0.0', node: '>=0.10.0'} dev: true - /rfdc@1.3.1: - resolution: {integrity: sha512-r5a3l5HzYlIC68TpmYKlxWjmOP6wiPJ1vWv2HeLhNsRZMrCkxeqxiHlQ21oXmQ4F3SiryXBHhAD7JZqvOJjFmg==} + /rfdc@1.4.1: + resolution: {integrity: sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==} dev: true /rimraf@3.0.2: resolution: {integrity: sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==} + deprecated: Rimraf versions prior to v4 are no longer supported hasBin: true dependencies: glob: 7.2.3 @@ -4981,7 +5022,7 @@ packages: engines: {node: '>=14'} hasBin: true dependencies: - glob: 10.3.10 + glob: 10.4.5 dev: true /run-async@3.0.0: @@ -5001,12 +5042,12 @@ packages: tslib: 2.3.1 dev: true - /safe-array-concat@1.1.0: - resolution: {integrity: sha512-ZdQ0Jeb9Ofti4hbt5lX3T2JcAamT9hfzYU1MNB+z/jaEbB6wfFfPIR/zEORmZqobkCCJhSjodobH6WHNmJ97dg==} + /safe-array-concat@1.1.2: + resolution: {integrity: sha512-vj6RsCsWBCf19jIeHEfkRMw8DPiBb+DMXklQ/1SGDHOMlHdPUkZXFQ2YdplS23zESTijAcurb1aSgJA3AgMu1Q==} engines: {node: '>=0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 + call-bind: 1.0.7 + get-intrinsic: 1.2.4 has-symbols: 1.0.3 isarray: 2.0.5 dev: true @@ -5017,12 +5058,12 @@ packages: /safe-buffer@5.2.1: resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} - /safe-regex-test@1.0.2: - resolution: {integrity: sha512-83S9w6eFq12BBIJYvjMux6/dkirb8+4zJRA9cxNBVb7Wq5fJBW+Xze48WqR8pxua7bDuAaaAxtVVd4Idjp1dBQ==} + /safe-regex-test@1.0.3: + resolution: {integrity: sha512-CdASjNJPvRa7roO6Ra/gLYBTzYzzPyyBXxIMdGW3USQLyjWEls2RgW5UBTXaQVp+OrpeCK3bLem8smtmheoRuw==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 + call-bind: 1.0.7 + es-errors: 1.3.0 is-regex: 1.1.4 dev: true @@ -5030,7 +5071,7 @@ packages: resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} dev: false - /sass-loader@11.1.1(webpack@5.62.1): + /sass-loader@11.1.1(webpack@5.95.0): resolution: {integrity: sha512-fOCp/zLmj1V1WHDZbUbPgrZhA7HKXHEqkslzB+05U5K9SbSbcmH91C7QLW31AsXikxUMaxXRhhcqWZAxUMLDyA==} engines: {node: '>= 10.13.0'} peerDependencies: @@ -5048,7 +5089,7 @@ packages: dependencies: klona: 2.0.6 neo-async: 2.6.2 - webpack: 5.62.1(webpack-cli@4.7.2) + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /schema-utils@3.3.0: @@ -5080,8 +5121,8 @@ packages: dependencies: lru-cache: 6.0.0 - /send@0.18.0: - resolution: {integrity: sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==} + /send@0.19.0: + resolution: {integrity: sha512-dW41u5VfLXu8SJh5bwRmyYUbAoSB3c9uQh6L8h/KtsFREPWpbX1lrljJo186Jc4nmci/sGUZ9a0a0J2zgfq2hw==} engines: {node: '>= 0.8.0'} dependencies: debug: 2.6.9 @@ -5119,14 +5160,14 @@ packages: randombytes: 2.1.0 dev: true - /serve-static@1.15.0: - resolution: {integrity: sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==} + /serve-static@1.16.2: + resolution: {integrity: sha512-VqpjJZKadQB/PEbEwvFdO43Ax5dFBZ2UECszz8bQ7pi7wt//PWe1P6MN7eCnjsatYtBT6EuiClbjSWP2WrIoTw==} engines: {node: '>= 0.8.0'} dependencies: - encodeurl: 1.0.2 + encodeurl: 2.0.0 escape-html: 1.0.3 parseurl: 1.3.3 - send: 0.18.0 + send: 0.19.0 transitivePeerDependencies: - supports-color dev: false @@ -5134,23 +5175,25 @@ packages: /set-blocking@2.0.0: resolution: {integrity: sha512-KiKBS8AnWGEyLzofFfmvKwpdPzqiy16LvQfK3yv/fVH7Bj13/wl3JSR1J+rfgRE9q7xUJK4qvgS8raSOeLUehw==} - /set-function-length@1.2.0: - resolution: {integrity: sha512-4DBHDoyHlM1IRPGYcoxexgh67y4ueR53FKV1yyxwFMY7aCqcN/38M1+SwZ/qJQ8iLv7+ck385ot4CcisOAPT9w==} + /set-function-length@1.2.2: + resolution: {integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==} engines: {node: '>= 0.4'} dependencies: - define-data-property: 1.1.1 + define-data-property: 1.1.4 + es-errors: 1.3.0 function-bind: 1.1.2 - get-intrinsic: 1.2.2 + get-intrinsic: 1.2.4 gopd: 1.0.1 - has-property-descriptors: 1.0.1 + has-property-descriptors: 1.0.2 - /set-function-name@2.0.1: - resolution: {integrity: sha512-tMNCiqYVkXIZgc2Hnoy2IvC/f8ezc5koaRFkCjrpWzGpCd3qbZXPzVy9MAZzK1ch/X0jvSkojys3oqJN0qCmdA==} + /set-function-name@2.0.2: + resolution: {integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==} engines: {node: '>= 0.4'} dependencies: - define-data-property: 1.1.1 + define-data-property: 1.1.4 + es-errors: 1.3.0 functions-have-names: 1.2.3 - has-property-descriptors: 1.0.1 + has-property-descriptors: 1.0.2 dev: true /setprototypeof@1.2.0: @@ -5180,12 +5223,14 @@ packages: resolution: {integrity: sha512-sQTKC1Re/rM6XyFM6fIAGHRPVGvyXfgzIDvzoq608vM+jeyVD0Tu1E6Np0Kc2zAIFWIj963V2800iF/9LPieQw==} dev: false - /side-channel@1.0.4: - resolution: {integrity: sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==} + /side-channel@1.0.6: + resolution: {integrity: sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 - object-inspect: 1.13.1 + call-bind: 1.0.7 + es-errors: 1.3.0 + get-intrinsic: 1.2.4 + object-inspect: 1.13.2 /signal-exit@3.0.7: resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==} @@ -5242,8 +5287,8 @@ packages: is-fullwidth-code-point: 3.0.0 dev: true - /source-map-js@1.0.2: - resolution: {integrity: sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw==} + /source-map-js@1.2.1: + resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} engines: {node: '>=0.10.0'} dev: true @@ -5332,29 +5377,31 @@ packages: strip-ansi: 7.1.0 dev: true - /string.prototype.trim@1.2.8: - resolution: {integrity: sha512-lfjY4HcixfQXOfaqCvcBuOIapyaroTXhbkfJN3gcB1OtyupngWK4sEET9Knd0cXd28kTUqu/kHoV4HKSJdnjiQ==} + /string.prototype.trim@1.2.9: + resolution: {integrity: sha512-klHuCNxiMZ8MlsOihJhJEBJAiMVqU3Z2nEXWfWnIqjN0gEFS9J9+IxKozWWtQGcgoa1WUZzLjKPTr4ZHNFTFxw==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-abstract: 1.23.3 + es-object-atoms: 1.0.0 dev: true - /string.prototype.trimend@1.0.7: - resolution: {integrity: sha512-Ni79DqeB72ZFq1uH/L6zJ+DKZTkOtPIHovb3YZHQViE+HDouuU4mBrLOLDn5Dde3RF8qw5qVETEjhu9locMLvA==} + /string.prototype.trimend@1.0.8: + resolution: {integrity: sha512-p73uL5VCHCO2BZZ6krwwQE3kCzM7NKmis8S//xEC6fQonchbum4eP6kR4DLEjQFO3Wnj3Fuo8NM0kOSjVdHjZQ==} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-object-atoms: 1.0.0 dev: true - /string.prototype.trimstart@1.0.7: - resolution: {integrity: sha512-NGhtDFu3jCEm7B4Fy0DpLewdJQOZcQ0rGbwQ/+stjnrp2i+rlKeCvos9hOIeCmqwratM47OBxY7uFZzjxHXmrg==} + /string.prototype.trimstart@1.0.8: + resolution: {integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-object-atoms: 1.0.0 dev: true /string_decoder@0.10.31: @@ -5397,7 +5444,7 @@ packages: resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==} engines: {node: '>=12'} dependencies: - ansi-regex: 6.0.1 + ansi-regex: 6.1.0 dev: true /strip-bom@3.0.0: @@ -5425,7 +5472,7 @@ packages: engines: {node: '>=8'} dev: true - /style-loader@2.0.0(webpack@5.62.1): + /style-loader@2.0.0(webpack@5.95.0): resolution: {integrity: sha512-Z0gYUJmzZ6ZdRUqpg1r8GsaFKypE+3xAzuFeMuoHgjc9KZv3wMyCRjQIWEbhoFSq7+7yoHXySDJyyWQaPajeiQ==} engines: {node: '>= 10.13.0'} peerDependencies: @@ -5433,7 +5480,7 @@ packages: dependencies: loader-utils: 2.0.4 schema-utils: 3.3.0 - webpack: 5.62.1(webpack-cli@4.7.2) + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /supports-color@5.5.0: @@ -5454,17 +5501,18 @@ packages: engines: {node: '>=10'} dependencies: has-flag: 4.0.0 + dev: true /supports-preserve-symlinks-flag@1.0.0: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} dev: true - /table@6.8.1: - resolution: {integrity: sha512-Y4X9zqrCftUhMeH2EptSSERdVKt/nEdijTOacGD/97EKjhQ/Qs8RTlEGABSJNNN8lac9kheH+af7yAkEWlgneA==} + /table@6.8.2: + resolution: {integrity: sha512-w2sfv80nrAh2VCbqR5AK27wswXhqcck2AhfnNW76beQXskGZ1V12GwS//yYVa3d3fcvAip2OUnbDAjW2k3v9fA==} engines: {node: '>=10.0.0'} dependencies: - ajv: 8.12.0 + ajv: 8.17.1 lodash.truncate: 4.4.2 slice-ansi: 4.0.0 string-width: 4.2.3 @@ -5482,7 +5530,7 @@ packages: dependencies: chownr: 1.1.4 mkdirp-classic: 0.5.3 - pump: 3.0.0 + pump: 3.0.2 tar-stream: 2.2.0 /tar-stream@2.2.0: @@ -5496,7 +5544,7 @@ packages: inherits: 2.0.4 readable-stream: 3.6.2 - /terser-webpack-plugin@5.1.2(webpack@5.62.1): + /terser-webpack-plugin@5.1.2(webpack@5.95.0): resolution: {integrity: sha512-6QhDaAiVHIQr5Ab3XUWZyDmrIPCHMiqJVljMF91YKyqwKkL5QHnYMkrMBy96v9Z7ev1hGhSEw1HQZc2p/s5Z8Q==} engines: {node: '>= 10.13.0'} peerDependencies: @@ -5507,11 +5555,11 @@ packages: schema-utils: 3.3.0 serialize-javascript: 5.0.1 source-map: 0.6.1 - terser: 5.27.0 - webpack: 5.62.1(webpack-cli@4.7.2) + terser: 5.36.0 + webpack: 5.95.0(webpack-cli@5.1.4) dev: true - /terser-webpack-plugin@5.3.10(webpack@5.62.1): + /terser-webpack-plugin@5.3.10(webpack@5.95.0): resolution: {integrity: sha512-BKFPWlPDndPs+NGGCr1U59t0XScL5317Y0UReNrHaw9/FwhPENlq6bfgs+4yPfyP51vqC1bQ4rp1EfXW5ZSH9w==} engines: {node: '>= 10.13.0'} peerDependencies: @@ -5527,12 +5575,12 @@ packages: uglify-js: optional: true dependencies: - '@jridgewell/trace-mapping': 0.3.22 + '@jridgewell/trace-mapping': 0.3.25 jest-worker: 27.5.1 schema-utils: 3.3.0 serialize-javascript: 6.0.2 - terser: 5.27.0 - webpack: 5.62.1(webpack-cli@4.7.2) + terser: 5.36.0 + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /terser@4.8.1: @@ -5540,19 +5588,19 @@ packages: engines: {node: '>=6.0.0'} hasBin: true dependencies: - acorn: 8.11.3 + acorn: 8.14.0 commander: 2.20.3 source-map: 0.6.1 source-map-support: 0.5.19 dev: true - /terser@5.27.0: - resolution: {integrity: sha512-bi1HRwVRskAjheeYl291n3JC4GgO/Ty4z1nVs5AAsmonJulGxpSektecnNedrwK9C7vpvVtcX3cw00VSLt7U2A==} + /terser@5.36.0: + resolution: {integrity: sha512-IYV9eNMuFAV4THUspIRXkLakHnV6XO7FEdtKjf/mDyrnqUg9LnlOn6/RwRvM9SZjR4GUq8Nk8zj67FzVARr74w==} engines: {node: '>=10'} hasBin: true dependencies: - '@jridgewell/source-map': 0.3.5 - acorn: 8.11.3 + '@jridgewell/source-map': 0.3.6 + acorn: 8.14.0 commander: 2.20.3 source-map-support: 0.5.21 dev: true @@ -5588,11 +5636,6 @@ packages: os-tmpdir: 1.0.2 dev: false - /to-fast-properties@2.0.0: - resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==} - engines: {node: '>=4'} - dev: true - /to-regex-range@5.0.1: resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} engines: {node: '>=8.0'} @@ -5610,7 +5653,7 @@ packages: hasBin: true dev: false - /ts-loader@9.2.2(typescript@4.5.5)(webpack@5.62.1): + /ts-loader@9.2.2(typescript@4.5.5)(webpack@5.95.0): resolution: {integrity: sha512-hNIhGTQHtNKjOzR2ZtQ2OSVbXPykOae+zostf1IlHCf61Mt41GMJurKNqrYUbzHgpmj6UWRu8eBfb7q0XliV0g==} engines: {node: '>=12.0.0'} peerDependencies: @@ -5618,11 +5661,11 @@ packages: webpack: ^5.0.0 dependencies: chalk: 4.1.0 - enhanced-resolve: 5.15.0 - micromatch: 4.0.5 + enhanced-resolve: 5.17.1 + micromatch: 4.0.8 semver: 7.5.4 typescript: 4.5.5 - webpack: 5.62.1(webpack-cli@4.7.2) + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /ts-node@9.1.1(typescript@4.5.5): @@ -5657,8 +5700,8 @@ packages: /tslib@2.3.1: resolution: {integrity: sha512-77EbyPPpMz+FRFRuAFlWMtmgUWGe9UOG2Z25NqCwiIjRhOf5iKGuzSe5P2w1laq+FkRy4p+PCuVkJSGkzTEKVw==} - /tslib@2.6.2: - resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==} + /tslib@2.8.0: + resolution: {integrity: sha512-jWVzBLplnCmoaTr13V9dYbiQ99wvZRd0vNWaDRg+aVYRcjDF3nDksxFDE/+fkXnKhpnUUkmx5pK/v8mCtLVqZA==} dev: false /tsutils@3.21.0(typescript@4.5.5): @@ -5689,6 +5732,11 @@ packages: engines: {node: '>=4'} dev: true + /type-detect@4.1.0: + resolution: {integrity: sha512-Acylog8/luQ8L7il+geoSxhEkazvkslg7PSNKOX59mbB9cOveP5aq9h74Y7YU8yDpJwetzQQrfIwtf4Wp4LKcw==} + engines: {node: '>=4'} + dev: true + /type-fest@0.20.2: resolution: {integrity: sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==} engines: {node: '>=10'} @@ -5711,42 +5759,48 @@ packages: mime-types: 2.1.35 dev: false - /typed-array-buffer@1.0.0: - resolution: {integrity: sha512-Y8KTSIglk9OZEr8zywiIHG/kmQ7KWyjseXs1CbSo8vC42w7hg2HgYTxSWwP0+is7bWDc1H+Fo026CpHFwm8tkw==} + /typed-array-buffer@1.0.2: + resolution: {integrity: sha512-gEymJYKZtKXzzBzM4jqa9w6Q1Jjm7x2d+sh19AdsD4wqnMPDYyvwpsIc2Q/835kHuo3BEQ7CjelGhfTsoBb2MQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 - is-typed-array: 1.1.12 + call-bind: 1.0.7 + es-errors: 1.3.0 + is-typed-array: 1.1.13 dev: true - /typed-array-byte-length@1.0.0: - resolution: {integrity: sha512-Or/+kvLxNpeQ9DtSydonMxCx+9ZXOswtwJn17SNLvhptaXYDJvkFFP5zbfU/uLmvnBJlI4yrnXRxpdWH/M5tNA==} + /typed-array-byte-length@1.0.1: + resolution: {integrity: sha512-3iMJ9q0ao7WE9tWcaYKIptkNBuOIcZCCT0d4MRvuuH88fEoEH62IuQe0OtraD3ebQEoTRk8XCBoknUNc1Y67pw==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 for-each: 0.3.3 - has-proto: 1.0.1 - is-typed-array: 1.1.12 + gopd: 1.0.1 + has-proto: 1.0.3 + is-typed-array: 1.1.13 dev: true - /typed-array-byte-offset@1.0.0: - resolution: {integrity: sha512-RD97prjEt9EL8YgAgpOkf3O4IF9lhJFr9g0htQkm0rchFp/Vx7LW5Q8fSXXub7BXAODyUQohRMyOc3faCPd0hg==} + /typed-array-byte-offset@1.0.2: + resolution: {integrity: sha512-Ous0vodHa56FviZucS2E63zkgtgrACj7omjwd/8lTEMEPFFyjfixMZ1ZXenpgCFBBt4EC1J2XsyVS2gkG0eTFA==} engines: {node: '>= 0.4'} dependencies: - available-typed-arrays: 1.0.5 - call-bind: 1.0.5 + available-typed-arrays: 1.0.7 + call-bind: 1.0.7 for-each: 0.3.3 - has-proto: 1.0.1 - is-typed-array: 1.1.12 + gopd: 1.0.1 + has-proto: 1.0.3 + is-typed-array: 1.1.13 dev: true - /typed-array-length@1.0.4: - resolution: {integrity: sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng==} + /typed-array-length@1.0.6: + resolution: {integrity: sha512-/OxDN6OtAk5KBpGb28T+HZc2M+ADtvRxXrKKbUwtsLgdoxgX13hyy7ek6bFRl5+aBs2yZzB0c4CnQfAtVypW/g==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 for-each: 0.3.3 - is-typed-array: 1.1.12 + gopd: 1.0.1 + has-proto: 1.0.3 + is-typed-array: 1.1.13 + possible-typed-array-names: 1.0.0 dev: true /typedarray-to-buffer@3.1.5: @@ -5772,7 +5826,7 @@ packages: /unbox-primitive@1.0.2: resolution: {integrity: sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 has-bigints: 1.0.2 has-symbols: 1.0.3 which-boxed-primitive: 1.0.2 @@ -5782,8 +5836,8 @@ packages: resolution: {integrity: sha512-hEQt0+ZLDVUMhebKxL4x1BTtDY7bavVofhZ9KZ4aI26X9SRaE+Y3m83XUL1UP2jn8ynjndwCCpEHdUG+9pP1Tw==} dev: false - /undici-types@5.26.5: - resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} + /undici-types@6.19.8: + resolution: {integrity: sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw==} /universalify@2.0.1: resolution: {integrity: sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==} @@ -5800,15 +5854,15 @@ packages: engines: {node: '>=8'} dev: true - /update-browserslist-db@1.0.13(browserslist@4.22.2): - resolution: {integrity: sha512-xebP81SNcPuNpPP3uzeW1NYXxI3rxyJzF3pD6sH4jE7o/IX+WtSpwnVU+qIsDPyk0d3hmFQ7mjqc6AtV604hbg==} + /update-browserslist-db@1.1.1(browserslist@4.24.2): + resolution: {integrity: sha512-R8UzCaa9Az+38REPiJ1tXlImTJXlVfgHZsglwBD/k6nj76ctsH1E3q4doGrukiLQd3sGQYu56r5+lo5r94l29A==} hasBin: true peerDependencies: browserslist: '>= 4.21.0' dependencies: - browserslist: 4.22.2 - escalade: 3.1.1 - picocolors: 1.0.0 + browserslist: 4.24.2 + escalade: 3.2.0 + picocolors: 1.1.1 dev: true /uri-js@4.4.1: @@ -5817,7 +5871,7 @@ packages: punycode: 2.3.1 dev: true - /url-loader@4.1.1(webpack@5.62.1): + /url-loader@4.1.1(webpack@5.95.0): resolution: {integrity: sha512-3BTV812+AVHHOJQO8O5MkWgZ5aosP7GnROJwvzLS9hWDj00lZ6Z0wNak423Lp9PBZN05N+Jk/N5Si8jRAlGyWA==} engines: {node: '>= 10.13.0'} peerDependencies: @@ -5830,7 +5884,7 @@ packages: loader-utils: 2.0.4 mime-types: 2.1.35 schema-utils: 3.3.0 - webpack: 5.62.1(webpack-cli@4.7.2) + webpack: 5.95.0(webpack-cli@5.1.4) dev: true /util-deprecate@1.0.2: @@ -5858,47 +5912,44 @@ packages: engines: {node: '>= 0.8'} dev: false - /watchpack@2.4.0: - resolution: {integrity: sha512-Lcvm7MGST/4fup+ifyKi2hjyIAwcdI4HRgtvTpIUxBRhB+RFtUh8XtDOxUfctVCnhVi+QQj49i91OyvzkJl6cg==} + /watchpack@2.4.2: + resolution: {integrity: sha512-TnbFSbcOCcDgjZ4piURLCbJ3nJhznVh9kw6F6iokjiFPl8ONxe9A6nMDVXDiNbrSfLILs6vB07F7wLBrwPYzJw==} engines: {node: '>=10.13.0'} dependencies: glob-to-regexp: 0.4.1 graceful-fs: 4.2.11 dev: true - /webpack-cli@4.7.2(webpack@5.62.1): - resolution: {integrity: sha512-mEoLmnmOIZQNiRl0ebnjzQ74Hk0iKS5SiEEnpq3dRezoyR3yPaeQZCMCe+db4524pj1Pd5ghZXjT41KLzIhSLw==} - engines: {node: '>=10.13.0'} + /webpack-cli@5.1.4(webpack@5.95.0): + resolution: {integrity: sha512-pIDJHIEI9LR0yxHXQ+Qh95k2EvXpWzZ5l+d+jIo+RdSm9MiHfzazIxwwni/p7+x4eJZuvG1AJwgC4TNQ7NRgsg==} + engines: {node: '>=14.15.0'} hasBin: true peerDependencies: '@webpack-cli/generators': '*' - '@webpack-cli/migrate': '*' - webpack: 4.x.x || 5.x.x + webpack: 5.x.x webpack-bundle-analyzer: '*' webpack-dev-server: '*' peerDependenciesMeta: '@webpack-cli/generators': optional: true - '@webpack-cli/migrate': - optional: true webpack-bundle-analyzer: optional: true webpack-dev-server: optional: true dependencies: '@discoveryjs/json-ext': 0.5.7 - '@webpack-cli/configtest': 1.2.0(webpack-cli@4.7.2)(webpack@5.62.1) - '@webpack-cli/info': 1.5.0(webpack-cli@4.7.2) - '@webpack-cli/serve': 1.7.0(webpack-cli@4.7.2) - colorette: 1.4.0 - commander: 7.2.0 - execa: 5.1.1 + '@webpack-cli/configtest': 2.1.1(webpack-cli@5.1.4)(webpack@5.95.0) + '@webpack-cli/info': 2.0.2(webpack-cli@5.1.4)(webpack@5.95.0) + '@webpack-cli/serve': 2.0.5(webpack-cli@5.1.4)(webpack@5.95.0) + colorette: 2.0.20 + commander: 10.0.1 + cross-spawn: 7.0.3 + envinfo: 7.14.0 fastest-levenshtein: 1.0.16 - import-local: 3.1.0 - interpret: 2.2.0 - rechoir: 0.7.1 - v8-compile-cache: 2.4.0 - webpack: 5.62.1(webpack-cli@4.7.2) + import-local: 3.2.0 + interpret: 3.1.1 + rechoir: 0.8.0 + webpack: 5.95.0(webpack-cli@5.1.4) webpack-merge: 5.10.0 dev: true @@ -5916,8 +5967,8 @@ packages: engines: {node: '>=10.13.0'} dev: true - /webpack@5.62.1(webpack-cli@4.7.2): - resolution: {integrity: sha512-jNLtnWChS2CMZ7vqWtztv0G6fYB5hz11Zsadp5tE7e4/66zVDj7/KUeQZOsOl8Hz5KrLJH1h2eIDl6AnlyE12Q==} + /webpack@5.95.0(webpack-cli@5.1.4): + resolution: {integrity: sha512-2t3XstrKULz41MNMBF+cJ97TyHdyQ8HCt//pqErqDvNjU9YQBnZxIHa11VXsi7F3mb5/aO2tuDxdeTPdU7xu9Q==} engines: {node: '>=10.13.0'} hasBin: true peerDependencies: @@ -5926,30 +5977,29 @@ packages: webpack-cli: optional: true dependencies: - '@types/eslint-scope': 3.7.7 - '@types/estree': 0.0.50 - '@webassemblyjs/ast': 1.11.1 - '@webassemblyjs/wasm-edit': 1.11.1 - '@webassemblyjs/wasm-parser': 1.11.1 - acorn: 8.11.3 - acorn-import-assertions: 1.9.0(acorn@8.11.3) - browserslist: 4.22.2 - chrome-trace-event: 1.0.3 - enhanced-resolve: 5.15.0 - es-module-lexer: 0.9.3 + '@types/estree': 1.0.6 + '@webassemblyjs/ast': 1.12.1 + '@webassemblyjs/wasm-edit': 1.12.1 + '@webassemblyjs/wasm-parser': 1.12.1 + acorn: 8.14.0 + acorn-import-attributes: 1.9.5(acorn@8.14.0) + browserslist: 4.24.2 + chrome-trace-event: 1.0.4 + enhanced-resolve: 5.17.1 + es-module-lexer: 1.5.4 eslint-scope: 5.1.1 events: 3.3.0 glob-to-regexp: 0.4.1 graceful-fs: 4.2.11 - json-parse-better-errors: 1.0.2 + json-parse-even-better-errors: 2.3.1 loader-runner: 4.3.0 mime-types: 2.1.35 neo-async: 2.6.2 schema-utils: 3.3.0 tapable: 2.2.1 - terser-webpack-plugin: 5.3.10(webpack@5.62.1) - watchpack: 2.4.0 - webpack-cli: 4.7.2(webpack@5.62.1) + terser-webpack-plugin: 5.3.10(webpack@5.95.0) + watchpack: 2.4.2 + webpack-cli: 5.1.4(webpack@5.95.0) webpack-sources: 3.2.3 transitivePeerDependencies: - '@swc/core' @@ -5971,15 +6021,15 @@ packages: resolution: {integrity: sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==} dev: true - /which-typed-array@1.1.13: - resolution: {integrity: sha512-P5Nra0qjSncduVPEAr7xhoF5guty49ArDTwzJ/yNuPIbZppyRxFQsRCWrocxIY+CnMVG+qfbU2FmDKyvSGClow==} + /which-typed-array@1.1.15: + resolution: {integrity: sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA==} engines: {node: '>= 0.4'} dependencies: - available-typed-arrays: 1.0.5 - call-bind: 1.0.5 + available-typed-arrays: 1.0.7 + call-bind: 1.0.7 for-each: 0.3.3 gopd: 1.0.1 - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /which@2.0.2: @@ -6000,6 +6050,11 @@ packages: resolution: {integrity: sha512-CC1bOL87PIWSBhDcTrdeLo6eGT7mCFtrg0uIJtqJUFyK+eJnzl8A1niH56uu7KMa5XFrtiV+AQuHO3n7DsHnLQ==} dev: true + /word-wrap@1.2.5: + resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} + engines: {node: '>=0.10.0'} + dev: true + /workerpool@6.2.1: resolution: {integrity: sha512-ILEIE97kDZvF9Wb9f6h5aXK4swSlKGUcOEGiIYb2OOu/IrDU9iwj0fD//SsA6E5ibwJxpEvhullJY4Sl4GcpAw==} dev: true @@ -6118,7 +6173,7 @@ packages: engines: {node: '>=10'} dependencies: cliui: 7.0.4 - escalade: 3.1.1 + escalade: 3.2.0 get-caller-file: 2.0.5 require-directory: 2.1.1 string-width: 4.2.3 @@ -6135,3 +6190,8 @@ packages: resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} engines: {node: '>=10'} dev: true + + /yoctocolors-cjs@2.1.2: + resolution: {integrity: sha512-cYVsTjKl8b+FrnidjibDWskAv7UKOfcwaVZdp/it9n1s9fU3IkgDbhdIRKCW4JDsAlECJY0ytoVPT3sK6kideA==} + engines: {node: '>=18'} + dev: false diff --git a/packages/cli/src/commonlib/azureLogin.ts b/packages/cli/src/commonlib/azureLogin.ts index 46e0b926d0..b787fbbddb 100644 --- a/packages/cli/src/commonlib/azureLogin.ts +++ b/packages/cli/src/commonlib/azureLogin.ts @@ -180,6 +180,10 @@ export class AzureAccountManager extends login implements AzureAccountProvider { return Promise.resolve(AzureAccountManager.teamsFxTokenCredential); } + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } + private async updateLoginStatus(): Promise { const checkCodeFlow = AzureAccountManager.codeFlowInstance !== undefined && diff --git a/packages/cli/src/commonlib/azureLoginCI.ts b/packages/cli/src/commonlib/azureLoginCI.ts index 6adb2414b6..808a699ca8 100644 --- a/packages/cli/src/commonlib/azureLoginCI.ts +++ b/packages/cli/src/commonlib/azureLoginCI.ts @@ -8,7 +8,13 @@ import * as identity from "@azure/identity"; import * as fs from "fs-extra"; import * as path from "path"; -import { AzureAccountProvider, ConfigFolderName, SubscriptionInfo } from "@microsoft/teamsfx-api"; +import { + AzureAccountProvider, + ConfigFolderName, + FxError, + Result, + SubscriptionInfo, +} from "@microsoft/teamsfx-api"; import { LoginStatus, login } from "./common/login"; import { LogLevel as LLevel } from "@microsoft/teamsfx-api"; @@ -115,6 +121,11 @@ export class AzureAccountManager extends login implements AzureAccountProvider { await AzureSpCrypto.clearAzureSP(); return true; } + + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } + async getStatus(): Promise { await this.load(); if ( diff --git a/packages/cli/src/commonlib/azureLoginUserPassword.ts b/packages/cli/src/commonlib/azureLoginUserPassword.ts index f7c93a9caa..b7abb2098e 100644 --- a/packages/cli/src/commonlib/azureLoginUserPassword.ts +++ b/packages/cli/src/commonlib/azureLoginUserPassword.ts @@ -8,7 +8,13 @@ import { TokenCredential } from "@azure/core-auth"; import * as identity from "@azure/identity"; import dotenv from "dotenv"; -import { AzureAccountProvider, SubscriptionInfo, UserError } from "@microsoft/teamsfx-api"; +import { + AzureAccountProvider, + FxError, + Result, + SubscriptionInfo, + UserError, +} from "@microsoft/teamsfx-api"; import * as cfg from "./common/userPasswordConfig"; import { AzureScopes } from "@microsoft/teamsfx-core"; @@ -65,6 +71,10 @@ export class AzureAccountProviderUserPassword implements AzureAccountProvider { }); } + public switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } + public async getStatus(): Promise { return Promise.resolve({ status: "SignedIn", diff --git a/packages/cli/src/commonlib/m365Login.ts b/packages/cli/src/commonlib/m365Login.ts index c08d3fc538..e43227712c 100644 --- a/packages/cli/src/commonlib/m365Login.ts +++ b/packages/cli/src/commonlib/m365Login.ts @@ -117,6 +117,10 @@ export class M365Login extends BasicLogin implements M365TokenProvider { return true; } + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } + async getStatus(tokenRequest: TokenRequest): Promise> { if (!M365Login.codeFlowInstance.account) { await M365Login.codeFlowInstance.reloadCache(); @@ -185,6 +189,9 @@ class MM365TokenProviderWrapper implements M365TokenProvider { async signout(): Promise { return await (this.getProvider() as any).signout(); } + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } } export default new MM365TokenProviderWrapper(); diff --git a/packages/cli/src/commonlib/m365LoginUserPassword.ts b/packages/cli/src/commonlib/m365LoginUserPassword.ts index 43ff01cf13..ca958faa5b 100644 --- a/packages/cli/src/commonlib/m365LoginUserPassword.ts +++ b/packages/cli/src/commonlib/m365LoginUserPassword.ts @@ -135,6 +135,10 @@ export class M365ProviderUserPassword extends BasicLogin implements M365TokenPro signout(): boolean { return true; } + + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } } export default M365ProviderUserPassword.getInstance(); diff --git a/packages/cli/src/userInteraction.ts b/packages/cli/src/userInteraction.ts index 5a25bc2952..c34cec4efd 100644 --- a/packages/cli/src/userInteraction.ts +++ b/packages/cli/src/userInteraction.ts @@ -46,6 +46,12 @@ import { CheckboxChoice, SelectChoice, checkbox, select } from "./prompts"; import { errors } from "./resource"; import { getColorizedString } from "./utils"; +export const inquirerPrompts = { + confirm, + password, + input, +}; + /// TODO: input can be undefined type ValidationType = (input: T) => string | boolean | Promise; @@ -113,10 +119,16 @@ class CLIUserInteraction implements UserInteraction { return ok(defaultValue || ""); } ScreenManager.pause(); - const answer = await input({ + const answer = await inquirerPrompts.input({ message, default: defaultValue, validate, + theme: { + prefix: { + idle: "\x1b[32m?\x1b[0m", // Green question mark displayed when input is in progress + done: "\x1b[32m?\x1b[0m", // Green question mark displayed when input is completed + }, + }, }); ScreenManager.continue(); return ok(answer); @@ -132,7 +144,7 @@ class CLIUserInteraction implements UserInteraction { return ok(defaultValue || ""); } ScreenManager.pause(); - const answer = await password({ + const answer = await inquirerPrompts.password({ message, mask: "*", validate, @@ -165,7 +177,7 @@ class CLIUserInteraction implements UserInteraction { return ok(defaultValue !== undefined ? defaultValue : true); } ScreenManager.pause(); - const answer = await confirm({ + const answer = await inquirerPrompts.confirm({ message, default: defaultValue ?? true, transformer, diff --git a/packages/cli/tests/unit/cmds/preview/previewEnv.tests.ts b/packages/cli/tests/unit/cmds/preview/previewEnv.tests.ts index cd399ea923..b4fa6a5c44 100644 --- a/packages/cli/tests/unit/cmds/preview/previewEnv.tests.ts +++ b/packages/cli/tests/unit/cmds/preview/previewEnv.tests.ts @@ -85,7 +85,7 @@ describe("Preview --env", () => { sandbox.stub(PreviewEnv.prototype, "launchBrowser").resolves(ok(null)); const cmd = new PreviewEnv(); await cmd.runCommand(defaultOptions); - expect(logs.length).greaterThanOrEqual(1); + expect(logs.length >= 1).to.be.true; expect(logs[0]).satisfy((l: string) => l.includes("run-command")); }); @@ -104,7 +104,7 @@ describe("Preview --env", () => { ["browser-arg"]: ["--guest"], ["open-only"]: true, }); - expect(logs.length).greaterThanOrEqual(0); + expect(logs.length >= 0).to.be.true; }); it("Preview Command Running - office", async () => { @@ -124,7 +124,7 @@ describe("Preview --env", () => { ["browser-arg"]: ["--guest"], }); - expect(logs.length).greaterThanOrEqual(0); + expect(logs.length >= 0).to.be.true; }); it("Preview Command Running - workspace not supported error", async () => { diff --git a/packages/cli/tests/unit/ui.tests.ts b/packages/cli/tests/unit/ui.tests.ts index 8860299a25..6215fcd340 100644 --- a/packages/cli/tests/unit/ui.tests.ts +++ b/packages/cli/tests/unit/ui.tests.ts @@ -1,7 +1,7 @@ +/* eslint-disable import/no-duplicates */ // Copyright (c) Microsoft Corporation. // Licensed under the MIT license. -import * as prompts from "@inquirer/prompts"; import { Colors, InputTextConfig, @@ -20,6 +20,7 @@ import sinon from "sinon"; import { logger } from "../../src/commonlib/logger"; import * as customizedPrompts from "../../src/prompts"; import UI from "../../src/userInteraction"; +import { inquirerPrompts } from "../../src/userInteraction"; import { expect } from "./utils"; import mockedEnv from "mocked-env"; @@ -345,7 +346,7 @@ describe("User Interaction Tests", function () { }); it("interactive", async () => { sandbox.stub(UI, "interactive").value(true); - sandbox.stub(prompts, "confirm").resolves(false); + sandbox.stub(inquirerPrompts, "confirm").resolves(false); const result = await UI._confirm("Select a string", false); expect(result.isOk() ? result.value : result.error).to.be.equals(false); }); @@ -404,7 +405,7 @@ describe("User Interaction Tests", function () { }); it("interactive", async () => { sandbox.stub(UI, "interactive").value(true); - sandbox.stub(prompts, "input").resolves("abc"); + sandbox.stub(inquirerPrompts, "input").resolves("abc"); const result = await UI.input("test", "Input the password", "default string"); expect(result.isOk() ? result.value : result.error).equals("abc"); }); @@ -425,7 +426,7 @@ describe("User Interaction Tests", function () { }); it("interactive", async () => { sandbox.stub(UI, "interactive").value(true); - sandbox.stub(prompts, "password").resolves("Password Result"); + sandbox.stub(inquirerPrompts, "password").resolves("Password Result"); const result = await UI.password("test", "Input the password"); expect(result.isOk() ? result.value : result.error).equals("Password Result"); }); @@ -496,7 +497,7 @@ describe("User Interaction Tests", function () { expect(result.isOk() ? result.value.result : result.error).deep.equals("./"); }); it("Input text", async () => { - sandbox.stub(prompts, "input").resolves("abc"); + sandbox.stub(inquirerPrompts, "input").resolves("abc"); sandbox.stub(UI, "interactive").value(true); const config: InputTextConfig = { name: "folder", diff --git a/packages/fx-core/package.json b/packages/fx-core/package.json index 3ac12bb287..1de08a82bd 100644 --- a/packages/fx-core/package.json +++ b/packages/fx-core/package.json @@ -93,7 +93,7 @@ "@azure/core-auth": "^1.4.0", "@azure/identity": "^4.1.0", "@azure/msal-node": "^2.6.6", - "@azure/storage-blob": "^12.7.0", + "@azure/storage-blob": "^12.25.0", "@feathersjs/hooks": "^0.6.5", "@microsoft/dev-tunnels-contracts": "1.1.9", "@microsoft/dev-tunnels-management": "1.1.9", @@ -123,8 +123,8 @@ "mustache": "^4.1.0", "node-fetch": "2.7.0", "node-forge": "^1.3.1", - "office-addin-manifest": "^1.13.1", - "office-addin-project": "^0.8.1", + "office-addin-manifest": "^1.13.5", + "office-addin-project": "^1.0.0", "openapi-types": "^7.2.3", "proper-lockfile": "^4.1.2", "read-package-json-fast": "^2.0.3", diff --git a/packages/fx-core/pnpm-lock.yaml b/packages/fx-core/pnpm-lock.yaml index 3a500f2bdf..e348a0f414 100644 --- a/packages/fx-core/pnpm-lock.yaml +++ b/packages/fx-core/pnpm-lock.yaml @@ -30,8 +30,8 @@ dependencies: specifier: ^2.6.6 version: 2.6.6 '@azure/storage-blob': - specifier: ^12.7.0 - version: 12.7.0 + specifier: ^12.25.0 + version: 12.25.0 '@feathersjs/hooks': specifier: ^0.6.5 version: 0.6.5 @@ -120,11 +120,11 @@ dependencies: specifier: ^1.3.1 version: 1.3.1 office-addin-manifest: - specifier: ^1.13.1 - version: 1.13.1 + specifier: ^1.13.5 + version: 1.13.5 office-addin-project: - specifier: ^0.8.1 - version: 0.8.1 + specifier: ^1.0.0 + version: 1.0.0 openapi-types: specifier: ^7.2.3 version: 7.2.3 @@ -420,7 +420,7 @@ packages: resolution: {integrity: sha512-TrRLIoSQVzfAJX9H1JeFjzAoDGcoK1IYX1UImfceTZpsyYfWr09Ss1aHW1y5TrrR3iq6RZLBwJ3E24uwPhwahw==} engines: {node: '>=12.0.0'} dependencies: - tslib: 2.3.1 + tslib: 2.7.0 dev: false /@azure/abort-controller@2.1.2: @@ -512,7 +512,7 @@ packages: engines: {node: '>=18.0.0'} dependencies: '@azure/abort-controller': 2.1.2 - '@azure/core-auth': 1.4.0 + '@azure/core-auth': 1.7.2 '@azure/core-rest-pipeline': 1.16.3 '@azure/core-tracing': 1.1.2 '@azure/core-util': 1.9.2 @@ -522,27 +522,15 @@ packages: - supports-color dev: false - /@azure/core-http@2.3.2: - resolution: {integrity: sha512-Z4dfbglV9kNZO177CNx4bo5ekFuYwwsvjLiKdZI4r84bYGv3irrbQz7JC3/rUfFH2l4T/W6OFleJaa2X0IaQqw==} - engines: {node: '>=14.0.0'} + /@azure/core-http-compat@2.1.2: + resolution: {integrity: sha512-5MnV1yqzZwgNLLjlizsU3QqOeQChkIXw781Fwh1xdAqJR5AA32IUaq6xv1BICJvfbHoa+JYcaij2HFkhLbNTJQ==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - '@azure/core-auth': 1.4.0 - '@azure/core-tracing': 1.0.0-preview.13 - '@azure/core-util': 1.9.2 - '@azure/logger': 1.1.4 - '@types/node-fetch': 2.6.9 - '@types/tunnel': 0.0.3 - form-data: 4.0.0 - node-fetch: 2.7.0 - process: 0.11.10 - tough-cookie: 4.1.4 - tslib: 2.3.1 - tunnel: 0.0.6 - uuid: 8.3.2 - xml2js: 0.5.0 + '@azure/abort-controller': 2.1.2 + '@azure/core-client': 1.9.2 + '@azure/core-rest-pipeline': 1.16.3 transitivePeerDependencies: - - encoding + - supports-color dev: false /@azure/core-lro@2.7.2: @@ -567,7 +555,7 @@ packages: engines: {node: '>=18.0.0'} dependencies: '@azure/abort-controller': 2.1.2 - '@azure/core-auth': 1.4.0 + '@azure/core-auth': 1.7.2 '@azure/core-tracing': 1.1.2 '@azure/core-util': 1.9.2 '@azure/logger': 1.1.4 @@ -578,14 +566,6 @@ packages: - supports-color dev: false - /@azure/core-tracing@1.0.0-preview.13: - resolution: {integrity: sha512-KxDlhXyMlh2Jhj2ykX6vNEU0Vou4nHr025KoSEiz7cS3BNiHNaZcdECk/DmLkEB0as5T7b/TpRcehJ5yV6NeXQ==} - engines: {node: '>=12.0.0'} - dependencies: - '@opentelemetry/api': 1.9.0 - tslib: 2.3.1 - dev: false - /@azure/core-tracing@1.1.2: resolution: {integrity: sha512-dawW9ifvWAWmUm9/h+/UQ2jrdvjCJ7VJEuCJ6XVNudzcOwm53BFZH4Q845vjfgoUAM8ZxokvVNxNxAITc502YA==} engines: {node: '>=18.0.0'} @@ -601,6 +581,14 @@ packages: tslib: 2.7.0 dev: false + /@azure/core-xml@1.4.4: + resolution: {integrity: sha512-J4FYAqakGXcbfeZjwjMzjNcpcH4E+JtEBv+xcV1yL0Ydn/6wbQfeFKTCHh9wttAi0lmajHw7yBbHPRG+YHckZQ==} + engines: {node: '>=18.0.0'} + dependencies: + fast-xml-parser: 4.5.0 + tslib: 2.7.0 + dev: false + /@azure/identity@4.1.0: resolution: {integrity: sha512-BhYkF8Xr2gXjyDxocm0pc9RI5J5a1jw8iW0dw6Bx95OGdYbuMyFZrrwNw4eYSqQ2BB6FZOqpJP3vjsAqRcvDhw==} engines: {node: '>=18.0.0'} @@ -656,20 +644,25 @@ packages: uuid: 8.3.2 dev: false - /@azure/storage-blob@12.7.0: - resolution: {integrity: sha512-7YEWEx03Us/YBxthzBv788R7jokwpCD5KcIsvtE5xRaijNX9o80KXpabhEwLR9DD9nmt/AlU/c1R+aXydgCduQ==} - engines: {node: '>=8.0.0'} + /@azure/storage-blob@12.25.0: + resolution: {integrity: sha512-oodouhA3nCCIh843tMMbxty3WqfNT+Vgzj3Xo5jqR9UPnzq3d7mzLjlHAYz7lW+b4km3SIgz+NAgztvhm7Z6kQ==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - '@azure/core-http': 2.3.2 + '@azure/abort-controller': 2.1.2 + '@azure/core-auth': 1.7.2 + '@azure/core-client': 1.9.2 + '@azure/core-http-compat': 2.1.2 '@azure/core-lro': 2.7.2 '@azure/core-paging': 1.6.2 - '@azure/core-tracing': 1.0.0-preview.13 + '@azure/core-rest-pipeline': 1.16.3 + '@azure/core-tracing': 1.1.2 + '@azure/core-util': 1.9.2 + '@azure/core-xml': 1.4.4 '@azure/logger': 1.1.4 events: 3.3.0 - tslib: 2.3.1 + tslib: 2.7.0 transitivePeerDependencies: - - encoding + - supports-color dev: false /@babel/code-frame@7.12.11: @@ -1016,9 +1009,9 @@ packages: dependencies: '@types/fs-extra': 11.0.4 '@types/node-fetch': 2.6.9 - ajv: 8.5.0 - ajv-draft-04: 1.0.0(ajv@8.5.0) - ajv-formats: 3.0.1(ajv@8.5.0) + ajv: 8.17.1 + ajv-draft-04: 1.0.0(ajv@8.17.1) + ajv-formats: 3.0.1(ajv@8.17.1) fs-extra: 9.1.0 node-fetch: 2.7.0 transitivePeerDependencies: @@ -1050,7 +1043,7 @@ packages: resolution: {integrity: sha512-8KG5RD0GVP4ydEzRn/I4BNDuxDtqVbOdm8675T49OIG/NGhaK0pjPX7ZcDlvKYbA+ulvVK3ztfcF4uBdOxuJbQ==} dependencies: '@gar/promisify': 1.1.3 - semver: 7.5.2 + semver: 7.6.3 dev: true /@npmcli/move-file@1.1.2: @@ -1062,11 +1055,6 @@ packages: rimraf: 3.0.2 dev: true - /@opentelemetry/api@1.9.0: - resolution: {integrity: sha512-3giAOQvZiH5F9bMlMiv8+GSPMeqg0dbaeo58/0SlA9sxSqZhnUtxzX9/2FzyhS9sWQf5S0GJE0AKBrFqjpeYcg==} - engines: {node: '>=8.0.0'} - dev: false - /@pkgjs/parseargs@0.11.0: resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==} engines: {node: '>=14'} @@ -1328,12 +1316,6 @@ packages: resolution: {integrity: sha512-flgpHJjntpBAdJD43ShRosQvNC0ME97DCfGvZEDlAThQmnerRXrLbX6YgzRBQCZTthET9eAWFAMaYP0m0Y4HzQ==} dev: true - /@types/tunnel@0.0.3: - resolution: {integrity: sha512-sOUTGn6h1SfQ+gbgqC364jLFBw2lnFqkgF3q0WovEHRLMrVD1sd5aufqi/aJObLekJO+Aq5z646U4Oxy6shXMA==} - dependencies: - '@types/node': 14.14.21 - dev: false - /@types/unzipper@0.10.5: resolution: {integrity: sha512-NrLJb29AdnBARpg9S/4ktfPEisbJ0AvaaAr3j7Q1tg8AgcEUsq2HqbNzvgLRoWyRtjzeLEv7vuL39u1mrNIyNA==} dependencies: @@ -1627,6 +1609,11 @@ packages: engines: {node: '>=6.0'} dev: false + /adm-zip@0.5.12: + resolution: {integrity: sha512-6TVU49mK6KZb4qG6xWaaM4C7sA/sgUMLy/JYMOzkcp3BvVLpW0fXDFQiIzAuxFCt/2+xD7fNIiPFAoLZPhVNLQ==} + engines: {node: '>=6.0'} + dev: false + /agent-base@7.1.1: resolution: {integrity: sha512-H0TSyFNDMomMNJQBn8wFV5YC/2eJ+VXECwOadZJT554xP6cODZHPX3H9QMQECxvrgiSOP1pHjy1sMWQVYJOUOA==} engines: {node: '>= 14'} @@ -1659,18 +1646,7 @@ packages: ajv: 8.17.1 dev: false - /ajv-draft-04@1.0.0(ajv@8.5.0): - resolution: {integrity: sha512-mv00Te6nmYbRp5DCwclxtt7yV/joXJPGS7nM+97GdxvuttCOfgI3K4U25zboyeX0O+myI8ERluxQe5wljMmVIw==} - peerDependencies: - ajv: ^8.5.0 - peerDependenciesMeta: - ajv: - optional: true - dependencies: - ajv: 8.5.0 - dev: false - - /ajv-formats@3.0.1(ajv@8.5.0): + /ajv-formats@3.0.1(ajv@8.17.1): resolution: {integrity: sha512-8iUql50EUR+uUcdRQ3HDqa6EVyo3docL8g5WJ3FNcWmu62IbkGUue/pEyLBW8VGKKucTPgqeks4fIU1DA4yowQ==} peerDependencies: ajv: ^8.0.0 @@ -1678,7 +1654,7 @@ packages: ajv: optional: true dependencies: - ajv: 8.5.0 + ajv: 8.17.1 dev: false /ajv-keywords@3.5.2(ajv@6.12.6): @@ -1705,7 +1681,6 @@ packages: fast-uri: 3.0.1 json-schema-traverse: 1.0.0 require-from-string: 2.0.2 - dev: false /ajv@8.5.0: resolution: {integrity: sha512-Y2l399Tt1AguU3BPRP9Fn4eN+Or+StUGWCUpbnFyXSo8NZ9S4uj+AG2pjs5apK+ZMOwYOz1+a+VKvKH7CudXgQ==} @@ -1714,6 +1689,7 @@ packages: json-schema-traverse: 1.0.0 require-from-string: 2.0.2 uri-js: 4.4.1 + dev: false /ansi-colors@4.1.1: resolution: {integrity: sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA==} @@ -2954,7 +2930,7 @@ packages: optionator: 0.9.4 progress: 2.0.3 regexpp: 3.2.0 - semver: 7.5.2 + semver: 7.6.3 strip-ansi: 6.0.1 strip-json-comments: 3.1.1 table: 6.8.2 @@ -3071,6 +3047,12 @@ packages: /fast-uri@3.0.1: resolution: {integrity: sha512-MWipKbbYiYI0UC7cl8m/i/IWTqfC8YXsqjzybjddLsFjStroQzsHXkc73JutMvBiXmOvapk+axIl79ig5t55Bw==} + + /fast-xml-parser@4.5.0: + resolution: {integrity: sha512-/PlTQCI96+fZMAOLMZK4CWG1ItCbfZ/0jx7UIJFChPNrx7tcEgerUgWbeieCM9MfHInUDyK8DWYZ+YrywDJuTg==} + hasBin: true + dependencies: + strnum: 1.0.5 dev: false /fastq@1.17.1: @@ -4655,8 +4637,8 @@ packages: es-object-atoms: 1.0.0 dev: true - /office-addin-manifest-converter@0.3.1: - resolution: {integrity: sha512-b0KumPkwfFqNTQ66Wjjbw5FU+wFMds6zvnGQit5yhHksv01aqQ/abBoI6T7hE5QV4Zx0wZrFGLntYMSShWFi0Q==} + /office-addin-manifest-converter@0.4.1: + resolution: {integrity: sha512-2eOdCCYJ5bhCe2p9KKETdg1UNshsKaT0lDU/jNopAg3t7zC1WxwvofTSO/+4Log5L4Re+wUdV8MqrQikZBa7+Q==} hasBin: true dependencies: '@xmldom/xmldom': 0.8.10 @@ -4664,17 +4646,17 @@ packages: terser: 5.31.6 dev: false - /office-addin-manifest@1.13.1: - resolution: {integrity: sha512-uIYpEE3tLr3grchqx9GOIHl3P+/4EqQ/Mrx4u5y7EsFzB5YqSIjwsvw6/x6OLrEhD5+0qtEh4fcAJVtfMPSpmw==} + /office-addin-manifest@1.13.5: + resolution: {integrity: sha512-CPCwmLqYG875Ro6TT/gNMR81QXJM4aAdto1QSzNsEOBSv4oTlvKe+089NlERImdWgocBSnMy5Q8cW39y1MbvrA==} hasBin: true dependencies: '@microsoft/teams-manifest': 0.1.5 - adm-zip: 0.5.10 + adm-zip: 0.5.12 chalk: 2.4.2 commander: 6.2.1 fs-extra: 7.0.1 node-fetch: 2.7.0 - office-addin-usage-data: 1.6.12 + office-addin-usage-data: 1.6.13 path: 0.12.7 uuid: 8.3.2 xml2js: 0.5.0 @@ -4682,24 +4664,50 @@ packages: - encoding dev: false - /office-addin-project@0.8.1: - resolution: {integrity: sha512-1fOmGHFZSHj9gvWaaO11UtnCkqpsmEXz5ZYhAs8bsv/aBgsw/+oSmO0yTqCFPrcKwDV7b4a+f8TuwKt3K0Atvw==} + /office-addin-manifest@2.0.0: + resolution: {integrity: sha512-Hz4rZ5iBGj30OR1nn87Csdnz4B2XxVQTjXpFErdXX9Y6B8Dz9mVLvhsv/6q75tXnPlSk9ksrSNvPE8o9PtAh6A==} hasBin: true dependencies: - adm-zip: 0.5.10 + '@microsoft/teams-manifest': 0.1.5 + adm-zip: 0.5.12 + chalk: 2.4.2 + commander: 6.2.1 + fs-extra: 7.0.1 + node-fetch: 2.7.0 + office-addin-usage-data: 2.0.0 + uuid: 8.3.2 + xml2js: 0.5.0 + transitivePeerDependencies: + - encoding + dev: false + + /office-addin-project@1.0.0: + resolution: {integrity: sha512-QGgy2Y3U54/50Zn48+229YHzWYK0cahsgnvjsoPd7L8A9rurlR6yXqfiksOv2gGmz84VMJPtg7Pk49X6tHoj7w==} + hasBin: true + dependencies: + adm-zip: 0.5.12 commander: 6.2.1 fs-extra: 7.0.1 inquirer: 7.3.3 - office-addin-manifest: 1.13.1 - office-addin-manifest-converter: 0.3.1 - office-addin-usage-data: 1.6.12 - path: 0.12.7 + office-addin-manifest: 2.0.0 + office-addin-manifest-converter: 0.4.1 + office-addin-usage-data: 2.0.0 transitivePeerDependencies: - encoding dev: false - /office-addin-usage-data@1.6.12: - resolution: {integrity: sha512-K9Ii5Jsc6Vuf6LrBvo5BycMzTmDwTkk3g5W2zS4PLffvvQYeI/RO3oYpGpOT6z7Pa8oh5gQ2QMDUgmjQGQZ7PA==} + /office-addin-usage-data@1.6.13: + resolution: {integrity: sha512-onAcOnTfGIr7T9mTn4nVLFc6PGd1qRCPsX4XDDG1/CLxXZq9/5QnZO60eKMox4m2IZpgt9anZNe6Fgn2mdt/ZQ==} + hasBin: true + dependencies: + applicationinsights: 1.8.10 + commander: 6.2.1 + readline-sync: 1.4.10 + uuid: 8.3.2 + dev: false + + /office-addin-usage-data@2.0.0: + resolution: {integrity: sha512-cwtDLII2S6raE0OucU+MZOhWdiNLmARDaFxus/6so0KQawQiMEVo2lPhacPOTYypeBKZAK7o5AIcE2NWT6VFfQ==} hasBin: true dependencies: applicationinsights: 1.8.10 @@ -4981,10 +4989,6 @@ packages: resolution: {integrity: sha512-yPw4Sng1gWghHQWj0B3ZggWUm4qVbPwPFcRG8KyxiU7J2OHFSoEHKS+EZ3fv5l1t9CyCiop6l/ZYeWbrgoQejw==} dev: true - /psl@1.9.0: - resolution: {integrity: sha512-E/ZsdU4HLs/68gYzgGTkMicWTLPdAftJLfJFlLUAAKZGkStNU72sZjT66SnMDVOfOWY/YAoiD7Jxa9iHvngcag==} - dev: false - /pump@3.0.0: resolution: {integrity: sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==} dependencies: @@ -4996,10 +5000,6 @@ packages: resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} engines: {node: '>=6'} - /querystringify@2.2.0: - resolution: {integrity: sha512-FIqgj2EUvTa7R50u0rGsyTftzjYmv/a3hO345bZNrqabNqjtgiDMgmo4mkUjd+nzU5oF3dClKqFIPUKybUyqoQ==} - dev: false - /queue-microtask@1.2.3: resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} dev: true @@ -5097,10 +5097,6 @@ packages: resolution: {integrity: sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==} dev: true - /requires-port@1.0.0: - resolution: {integrity: sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==} - dev: false - /resolve-from@4.0.0: resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} engines: {node: '>=4'} @@ -5186,7 +5182,7 @@ packages: /rxjs@7.8.1: resolution: {integrity: sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==} dependencies: - tslib: 2.3.1 + tslib: 2.7.0 dev: true /safe-array-concat@1.1.2: @@ -5562,6 +5558,10 @@ packages: engines: {node: '>=8'} dev: true + /strnum@1.0.5: + resolution: {integrity: sha512-J8bbNyKKXl5qYcR36TIO8W3mVGVHrmmxsd5PAItGkmyzwJvybiw2IVq5nqd0i4LSNSkB/sx9VHllbfFdr9k1JA==} + dev: false + /supports-color@5.5.0: resolution: {integrity: sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==} engines: {node: '>=4'} @@ -5609,7 +5609,7 @@ packages: resolution: {integrity: sha512-w2sfv80nrAh2VCbqR5AK27wswXhqcck2AhfnNW76beQXskGZ1V12GwS//yYVa3d3fcvAip2OUnbDAjW2k3v9fA==} engines: {node: '>=10.0.0'} dependencies: - ajv: 8.5.0 + ajv: 8.17.1 lodash.truncate: 4.4.2 slice-ansi: 4.0.0 string-width: 4.2.3 @@ -5714,16 +5714,6 @@ packages: is-number: 7.0.0 dev: true - /tough-cookie@4.1.4: - resolution: {integrity: sha512-Loo5UUvLD9ScZ6jh8beX1T6sO1w2/MpCRpEP7V280GKMVUQ0Jzar2U3UJPsrdbziLEMMhu3Ujnq//rhiFuIeag==} - engines: {node: '>=6'} - dependencies: - psl: 1.9.0 - punycode: 2.3.1 - universalify: 0.2.0 - url-parse: 1.5.10 - dev: false - /tr46@0.0.3: resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} dev: false @@ -5797,7 +5787,6 @@ packages: /tslib@2.7.0: resolution: {integrity: sha512-gLXCKdN1/j47AiHiOkJN69hJmcbGTHI0ImLmbYLHykhgeN0jVGola9yVjFgzCUklsZQMW55o+dW7IXv3RCXDzA==} - dev: false /tsutils@3.21.0(typescript@4.7.4): resolution: {integrity: sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==} @@ -5809,11 +5798,6 @@ packages: typescript: 4.7.4 dev: true - /tunnel@0.0.6: - resolution: {integrity: sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==} - engines: {node: '>=0.6.11 <=0.7.0 || >=0.7.3'} - dev: false - /type-check@0.4.0: resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} engines: {node: '>= 0.8.0'} @@ -5939,11 +5923,6 @@ packages: engines: {node: '>= 4.0.0'} dev: false - /universalify@0.2.0: - resolution: {integrity: sha512-CJ1QgKmNg3CwvAv/kOFmtnEN05f0D/cn9QntgNOQlQF9dgvVTHj3t+8JPdjqawCHk7V/KA+fbUqzZ9XWhcqPUg==} - engines: {node: '>= 4.0.0'} - dev: false - /universalify@2.0.1: resolution: {integrity: sha512-gptHNQghINnc/vTGIk0SOFGFNXw7JVrlRUtConJRlvaw6DuX0wO5Jeko9sWrMBhh+PsYAZ7oXAiOnf/UKogyiw==} engines: {node: '>= 10.0.0'} @@ -5965,13 +5944,6 @@ packages: dependencies: punycode: 2.3.1 - /url-parse@1.5.10: - resolution: {integrity: sha512-WypcfiRhfeUP9vvF0j6rw0J3hrWrw6iZv3+22h6iRMJ/8z1Tj6XfLP4DsUix5MhMPnXpiHDoKyoZ/bdCkwBCiQ==} - dependencies: - querystringify: 2.2.0 - requires-port: 1.0.0 - dev: false - /util-deprecate@1.0.2: resolution: {integrity: sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==} dev: true diff --git a/packages/fx-core/resource/package.nls.json b/packages/fx-core/resource/package.nls.json index f5813bd243..cf9c1f3a28 100644 --- a/packages/fx-core/resource/package.nls.json +++ b/packages/fx-core/resource/package.nls.json @@ -1,5 +1,7 @@ { "core.addApi.confirm": "Teams Toolkit will modify files in your \"%s\" folder based on the new OpenAPI document you provided. To avoid losing unexpected changes, back up your files or use git for change tracking before proceeding.", + "core.addApi.confirm.teamsYaml": "Teams Toolkit will modify files in your \"%s\" folder and \"%s\" based on the new OpenAPI document you provided. To avoid losing unexpected changes, back up your files or use git for change tracking before proceeding.", + "core.addApi.confirm.localTeamsYaml": "Teams Toolkit will modify files in your \"%s\" folder, \"%s\" and \"%s\" based on the new OpenAPI document you provided. To avoid losing unexpected changes, back up your files or use git for change tracking before proceeding.", "core.addApi.continue": "Add", "core.provision.provision": "Provision", "core.provision.learnMore": "More info", @@ -160,9 +162,9 @@ "plugins.bot.triggers.http-and-timer-functions.description": "Azure Functions", "plugins.bot.triggers.http-and-timer-functions.detail": "A function running on Azure Functions can respond to HTTP requests based on a specific schedule.", "plugins.bot.triggers.http-and-timer-functions.label": "HTTP and Timer Trigger", - "plugins.bot.triggers.http-restify.description": "Restify Server", - "plugins.bot.triggers.http-restify.detail": "A restify server running on Azure App Service can respond to HTTP requests.", - "plugins.bot.triggers.http-restify.label": "HTTP Trigger", + "plugins.bot.triggers.http-express.description": "Express Server", + "plugins.bot.triggers.http-express.detail": "An express server running on Azure App Service can respond to HTTP requests.", + "plugins.bot.triggers.http-express.label": "HTTP Trigger", "plugins.bot.triggers.http-webapi.description": "Web API Server", "plugins.bot.triggers.http-webapi.detail": "A Web API server running on Azure App Service can respond to HTTP requests.", "plugins.bot.triggers.http-webapi.label": "HTTP Trigger", @@ -212,6 +214,8 @@ "_error.appstudio.BotProvisionReturnsForbiddenResult.comment": "This is to describe API call, no need to translate 'Botframework'.", "error.appstudio.BotProvisionReturnsConflictResult": "Botframework provisioning returns conflict result when attempting to create bot registration.", "_error.appstudio.BotProvisionReturnsConflictResult.comment": "This is to describe API call, no need to translate 'Botframework'.", + "error.appstudio.localizationFile.pathNotDefined": "Localization file not found. Path: %s.", + "error.appstudio.localizationFile.validationException": "Unable to validate localization file due to errors. File: %s. Error: %s", "error.generator.ScaffoldLocalTemplateError": "Unable to scaffold template based on local zip package.", "error.generator.TemplateNotFoundError": "Unable to find template: %s.", "error.generator.SampleNotFoundError": "Unable to find sample: %s.", @@ -235,7 +239,6 @@ "core.option.github": "Open a GitHub guide", "core.option.inProduct": "Open an in-product guide", "core.TabOption.label": "Tab", - "core.generator.officeAddin.importProject.title": "Importing Existing Outlook Add-in Project", "core.generator.officeAddin.importProject.copyFiles": "Copying files...", "core.generator.officeAddin.importProject.convertProject": "Converting project...", "core.generator.officeAddin.importProject.updateManifest": "Modifying manifest...", @@ -271,6 +274,7 @@ "core.copilotPlugin.list.unsupportedBecause": "is unsupported because:", "core.copilotPlugin.scaffold.summary": "We have detected the following issues for your OpenAPI description document:\n%s", "core.copilotPlugin.scaffold.summary.warning.operationId": "%s Mitigation: Not required, operationId has been automatically generated and added into \"%s\" file.", + "core.copilotPlugin.scaffold.summary.warning.operationIdContainsSpecialCharacters": "Operation id '%s' in OpenAPI description document contained special characters and was renamed to '%s'.", "core.copilotPlugin.scaffold.summary.warning.swaggerVersion": "The OpenAPI description document is on Swagger version 2.0. Mitigation: Not required. The content has been converted to OpenAPI 3.0 and saved in \"%s\".", "core.copilotPlugin.scaffold.summary.warning.teamsManifest.lengthExceeding": "\"%s\" must not have more than %s characters. ", "core.copilotPlugin.scaffold.summary.warning.teamsManifest.missingFullDescription": "Missing full description. ", @@ -283,6 +287,7 @@ "core.copilotPlugin.scaffold.summary.warning.pluginManifest.missingFunctionDescription.mitigation": " Mitigation: Update description for \"%s\" in \"%s\"", "core.copilotPlugin.scaffold.summary.warning.pluginManifest.functionDescription.lengthExceeding": "Description for function \"%s\" shortened to %s characters to meet the length requirement.", "core.copilotPlugin.scaffold.summary.warning.pluginManifest.functionDescription.lengthExceeding.mitigation": " Mitigation: Update description for \"%s\" in \"%s\" so that Copilot can trigger the function.", + "core.copilotPlugin.scaffold.summary.warning.generate.ac.failed": "Failed to create the adaptive card for API '%s': %s. Mitigation: Not required but you can manually add it to the adaptiveCards folder.", "core.createCapabilityQuestion.titleNew": "Capabilities", "core.createCapabilityQuestion.placeholder": "Select a capability", "core.createProjectQuestion.option.description.preview": "Preview", @@ -899,6 +904,7 @@ "driver.apiKey.error.clientSecretInvalid": "Invalid client secret. It should be 10 to 512 characters long.", "driver.apiKey.error.domainInvalid": "Invalid domain. Please follow these rules: 1. Max %d domain(s) per API key. 2. Use comma to separate domains.", "driver.apiKey.error.failedToGetDomain": "Unable to get domain from API specification. Make sure your API specification is valid.", + "driver.apiKey.error.authMissingInSpec": "No API in the OpenAPI specification file matches the API key authentication name '%s'. Please verify the name in the specification.", "driver.apiKey.error.clientSecretFromScratchInvalid": "Invalid client secret. If you start with a new API, refer to the README file for details.", "driver.apiKey.log.successCreateApiKey": "Created API key with id %s", "driver.apiKey.log.failedExecuteDriver": "Unable to execute action %s. Error message: %s", @@ -911,7 +917,8 @@ "driver.oauth.error.OauthIdentityProviderInvalid": "Invalid identity provider 'MicrosoftEntra'. Ensure the OAuth authorization endpoint in the OpenAPI specification file is for Microsoft Entra.", "driver.oauth.log.successCreateOauth": "OAuth registration created successfully with id %s!", "driver.oauth.error.domainInvalid": "Maximum %d domains allowed per OAuth registration.", - "driver.apiKey.error.oauthAuthInfoInvalid": "Unable to parse OAuth2 authScheme from spec. Make sure your API specification is valid.", + "driver.oauth.error.oauthAuthInfoInvalid": "Unable to parse OAuth2 authScheme from spec. Make sure your API specification is valid.", + "driver.oauth.error.oauthAuthMissingInSpec": "No API in the OpenAPI specification file matches the OAuth authentication name '%s'. Please verify the name in the specification.", "driver.oauth.log.skipUpdateOauth": "Skip updating OAuth registration as the same property exists.", "driver.oauth.confirm.update": "The following parameters will be updated:\n%s\nDo you want to continue?", "driver.oauth.log.successUpdateOauth": "OAuth registration updated successfully!", diff --git a/packages/fx-core/src/client/teamsDevPortalClient.ts b/packages/fx-core/src/client/teamsDevPortalClient.ts index ac72ba1148..8fa50aa64f 100644 --- a/packages/fx-core/src/client/teamsDevPortalClient.ts +++ b/packages/fx-core/src/client/teamsDevPortalClient.ts @@ -971,7 +971,7 @@ export class TeamsDevPortalClient { } wrapResponse(e?: Error, response?: AxiosResponse): any { const error = new Error( - e?.message || response?.data.error.message || response?.data.errorMessage + e?.message || response?.data.error?.message || response?.data.errorMessage ); (error as any).response = response; (error as any).request = response?.request; diff --git a/packages/fx-core/src/common/featureFlags.ts b/packages/fx-core/src/common/featureFlags.ts index 3811f782ee..14a8ed7a2c 100644 --- a/packages/fx-core/src/common/featureFlags.ts +++ b/packages/fx-core/src/common/featureFlags.ts @@ -34,6 +34,7 @@ export class FeatureFlagName { static readonly KiotaIntegration = "TEAMSFX_KIOTA_INTEGRATION"; static readonly ApiPluginAAD = "TEAMSFX_API_PLUGIN_AAD"; static readonly CEAEnabled = "TEAMSFX_CEA_ENABLED"; + static readonly MultiTenant = "TEAMSFX_MULTI_TENANT"; } export interface FeatureFlag { @@ -109,6 +110,10 @@ export class FeatureFlags { name: FeatureFlagName.CEAEnabled, defaultValue: "false", }; + static readonly MultiTenant = { + name: FeatureFlagName.MultiTenant, + defaultValue: "false", + }; } export function isCopilotExtensionEnabled(): boolean { diff --git a/packages/fx-core/src/common/tools.ts b/packages/fx-core/src/common/tools.ts index 36f539a66d..e2bf88dd8a 100644 --- a/packages/fx-core/src/common/tools.ts +++ b/packages/fx-core/src/common/tools.ts @@ -14,6 +14,22 @@ export async function getSideloadingStatus(token: string): Promise[]> { + const RM_ENDPOINT = "https://management.azure.com/tenants?api-version=2022-06-01"; + if (token.length > 0) { + try { + const response = await axios.get(RM_ENDPOINT, { + headers: { Authorization: `Bearer ${token}` }, + }); + return response.data.value; + } catch (error) { + return []; + } + } + + return []; +} + export async function getSPFxTenant(graphToken: string): Promise { const GRAPH_TENANT_ENDPT = "https://graph.microsoft.com/v1.0/sites/root?$select=webUrl"; if (graphToken.length > 0) { diff --git a/packages/fx-core/src/component/configManager/actionInjector.ts b/packages/fx-core/src/component/configManager/actionInjector.ts index c8d1d1fee2..5ee3db522e 100644 --- a/packages/fx-core/src/component/configManager/actionInjector.ts +++ b/packages/fx-core/src/component/configManager/actionInjector.ts @@ -58,8 +58,9 @@ export class ActionInjector { static async injectCreateOAuthAction( ymlPath: string, authName: string, - specRelativePath: string - ): Promise { + specRelativePath: string, + forceToAddNew: boolean // If it from add plugin, then we will add another CreateOAuthAction + ): Promise { const ymlContent = await fs.readFile(ymlPath, "utf-8"); const actionName = "oauth/register"; @@ -67,23 +68,42 @@ export class ActionInjector { const provisionNode = document.get("provision") as any; if (provisionNode) { const hasOAuthAction = ActionInjector.hasActionWithName(provisionNode, actionName, authName); - if (!hasOAuthAction) { - provisionNode.items = provisionNode.items.filter( - (item: any) => item.get("uses") !== actionName && item.get("uses") !== "apiKey/register" + if (!hasOAuthAction || forceToAddNew) { + provisionNode.items = provisionNode.items.filter((item: any) => { + const uses = item.get("uses"); + if (forceToAddNew) { + return uses; + } else { + return uses !== actionName && uses !== "apiKey/register"; + } + }); + const existingConfigurationIdEnvNames: string[] = provisionNode.items + .filter((item: any) => { + const uses = item.get("uses"); + return uses == actionName; + }) + .map((item: any) => item.get("writeToEnvironmentFile")?.get("configurationId")) + .filter((item: string | undefined) => { + return !!item; + }); + const defaultEnvName = Utils.getSafeRegistrationIdEnvName(`${authName}_CONFIGURATION_ID`); + const registrationIdEnvName = this.findNextAvailableEnvName( + defaultEnvName, + existingConfigurationIdEnvNames ); const teamsAppIdEnvName = ActionInjector.getTeamsAppIdEnvName(provisionNode); if (teamsAppIdEnvName) { const index: number = provisionNode.items.findIndex( (item: any) => item.get("uses") === "teamsApp/create" ); - const envName = Utils.getSafeRegistrationIdEnvName(`${authName}_CONFIGURATION_ID`); + const flow = "authorizationCode"; const action = ActionInjector.generateAuthAction( actionName, authName, teamsAppIdEnvName, specRelativePath, - envName, + registrationIdEnvName, flow ); provisionNode.items.splice(index + 1, 0, action); @@ -92,17 +112,24 @@ export class ActionInjector { } await fs.writeFile(ymlPath, document.toString(), "utf8"); + return { + defaultRegistrationIdEnvName: defaultEnvName, + registrationIdEnvName: registrationIdEnvName, + }; } } else { throw new InjectOAuthActionFailedError(); } + + return undefined; } static async injectCreateAPIKeyAction( ymlPath: string, authName: string, - specRelativePath: string - ): Promise { + specRelativePath: string, + forceToAddNew: boolean // If it from add plugin, then we will add another CreateApiKeyAction + ): Promise { const ymlContent = await fs.readFile(ymlPath, "utf-8"); const actionName = "apiKey/register"; @@ -112,22 +139,40 @@ export class ActionInjector { if (provisionNode) { const hasApiKeyAction = ActionInjector.hasActionWithName(provisionNode, actionName, authName); - if (!hasApiKeyAction) { - provisionNode.items = provisionNode.items.filter( - (item: any) => item.get("uses") !== actionName && item.get("uses") !== "oauth/register" - ); + if (!hasApiKeyAction || forceToAddNew) { + provisionNode.items = provisionNode.items.filter((item: any) => { + const uses = item.get("uses"); + if (forceToAddNew) { + return uses; + } else { + return uses !== actionName && uses !== "oauth/register"; + } + }); + const existingRegistrationIdEnvNames: string[] = provisionNode.items + .filter((item: any) => { + const uses = item.get("uses"); + return uses == actionName; + }) + .map((item: any) => item.get("writeToEnvironmentFile")?.get("registrationId")) + .filter((item: string | undefined) => { + return !!item; + }); const teamsAppIdEnvName = ActionInjector.getTeamsAppIdEnvName(provisionNode); + const defaultEnvName = Utils.getSafeRegistrationIdEnvName(`${authName}_REGISTRATION_ID`); + const registrationIdEnvName = this.findNextAvailableEnvName( + defaultEnvName, + existingRegistrationIdEnvNames + ); if (teamsAppIdEnvName) { const index: number = provisionNode.items.findIndex( (item: any) => item.get("uses") === "teamsApp/create" ); - const envName = Utils.getSafeRegistrationIdEnvName(`${authName}_REGISTRATION_ID`); const action = ActionInjector.generateAuthAction( actionName, authName, teamsAppIdEnvName, specRelativePath, - envName + registrationIdEnvName ); provisionNode.items.splice(index + 1, 0, action); } else { @@ -135,9 +180,29 @@ export class ActionInjector { } await fs.writeFile(ymlPath, document.toString(), "utf8"); + return { + defaultRegistrationIdEnvName: defaultEnvName, + registrationIdEnvName: registrationIdEnvName, + }; } } else { throw new InjectAPIKeyActionFailedError(); } + return undefined; + } + + static findNextAvailableEnvName(baseEnvName: string, existingEnvNames: string[]): string { + let suffix = 1; + let envName = baseEnvName; + while (existingEnvNames.includes(envName)) { + envName = `${baseEnvName}${suffix}`; + suffix++; + } + return envName; } } + +export interface AuthActionInjectResult { + defaultRegistrationIdEnvName: string | undefined; // The default registration id env name without suffix + registrationIdEnvName: string | undefined; // The real env name of registration id we write in the yaml file +} diff --git a/packages/fx-core/src/component/constants.ts b/packages/fx-core/src/component/constants.ts index 2439ec8bb8..df05aeaa83 100644 --- a/packages/fx-core/src/component/constants.ts +++ b/packages/fx-core/src/component/constants.ts @@ -114,4 +114,5 @@ export const AadConstants = { export const KiotaLastCommands = { createPluginWithManifest: "createPluginWithManifest", createDeclarativeCopilotWithManifest: "createDeclarativeCopilotWithManifest", + addPlugin: "addPlugin", }; diff --git a/packages/fx-core/src/component/deps-checker/internal/nodeChecker.ts b/packages/fx-core/src/component/deps-checker/internal/nodeChecker.ts index ecd4d969d7..e71cdc93de 100644 --- a/packages/fx-core/src/component/deps-checker/internal/nodeChecker.ts +++ b/packages/fx-core/src/component/deps-checker/internal/nodeChecker.ts @@ -194,7 +194,7 @@ export class LtsNodeChecker extends NodeChecker { protected readonly _maxErrorVersion = Number.MAX_SAFE_INTEGER; protected getSupportedVersions(): Promise { - return Promise.resolve(["16", "18"]); + return Promise.resolve(["16", "18", "20"]); } protected isVersionSupported(supportedVersions: string[], version: NodeVersion): boolean { diff --git a/packages/fx-core/src/component/driver/apiKey/create.ts b/packages/fx-core/src/component/driver/apiKey/create.ts index c189bd24a4..652e2d3f58 100644 --- a/packages/fx-core/src/component/driver/apiKey/create.ts +++ b/packages/fx-core/src/component/driver/apiKey/create.ts @@ -90,7 +90,7 @@ export class CreateApiKeyDriver implements StepDriver { this.validateArgs(args); - const domains = await getDomain(args, context); + const domains = await getDomain(args, context, actionName); validateDomain(domains, actionName); const apiKey = await this.mapArgsToApiSecretRegistration( diff --git a/packages/fx-core/src/component/driver/apiKey/error/apiKeyAuthMissingInSpec.ts b/packages/fx-core/src/component/driver/apiKey/error/apiKeyAuthMissingInSpec.ts new file mode 100644 index 0000000000..99bd2397bf --- /dev/null +++ b/packages/fx-core/src/component/driver/apiKey/error/apiKeyAuthMissingInSpec.ts @@ -0,0 +1,21 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. + +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. +import { UserError } from "@microsoft/teamsfx-api"; +import { getDefaultString, getLocalizedString } from "../../../../common/localizeUtils"; + +const errorCode = "ApiKeyAuthMissingInSpec"; +const messageKey = "driver.apiKey.error.authMissingInSpec"; + +export class ApiKeyAuthMissingInSpecError extends UserError { + constructor(actionName: string, authName: string) { + super({ + source: actionName, + name: errorCode, + message: getDefaultString(messageKey, authName), + displayMessage: getLocalizedString(messageKey, authName), + }); + } +} diff --git a/packages/fx-core/src/component/driver/apiKey/update.ts b/packages/fx-core/src/component/driver/apiKey/update.ts index fcedddc2a6..864f2ce79b 100644 --- a/packages/fx-core/src/component/driver/apiKey/update.ts +++ b/packages/fx-core/src/component/driver/apiKey/update.ts @@ -39,7 +39,7 @@ export class UpdateApiKeyDriver implements StepDriver { context.logProvider?.info(getLocalizedString(logMessageKeys.startExecuteDriver, actionName)); this.validateArgs(args); - const domain = await getDomain(args, context); + const domain = await getDomain(args, context, actionName); validateDomain(domain, actionName); const appStudioTokenRes = await context.m365TokenProvider.getAccessToken({ diff --git a/packages/fx-core/src/component/driver/apiKey/utility/utility.ts b/packages/fx-core/src/component/driver/apiKey/utility/utility.ts index 2b304f3e6a..53a01fc537 100644 --- a/packages/fx-core/src/component/driver/apiKey/utility/utility.ts +++ b/packages/fx-core/src/component/driver/apiKey/utility/utility.ts @@ -9,6 +9,7 @@ import { UpdateApiKeyArgs } from "../interface/updateApiKeyArgs"; import { maxDomainPerApiKey } from "./constants"; import { ApiKeyDomainInvalidError } from "../error/apiKeyDomainInvalid"; import { ApiKeyFailedToGetDomainError } from "../error/apiKeyFailedToGetDomain"; +import { ApiKeyAuthMissingInSpecError } from "../error/apiKeyAuthMissingInSpec"; // Needs to validate the parameters outside of the function export function loadStateFromEnv( @@ -24,7 +25,8 @@ export function loadStateFromEnv( // TODO: need to add logic to read domain from env if need to support non-lifecycle commands export async function getDomain( args: CreateApiKeyArgs | UpdateApiKeyArgs, - context: DriverContext + context: DriverContext, + actionName: string ): Promise { const absolutePath = getAbsolutePath(args.apiSpecPath, context.projectPath); const parser = new SpecParser(absolutePath, { @@ -33,23 +35,26 @@ export async function getDomain( }); const listResult = await parser.list(); const operations = listResult.APIs; - const domains = operations - .filter((value) => { - const auth = value.auth; - return ( - auth && - auth.authScheme.type === "http" && - auth.authScheme.scheme === "bearer" && - auth.name === args.name - ); - }) - .map((value) => { - return value.server; - }) - .filter((value, index, self) => { - return self.indexOf(value) === index; - }); - return domains; + + const filteredOperations = operations.filter((value) => { + const auth = value.auth; + return ( + auth && + auth.authScheme.type === "http" && + auth.authScheme.scheme === "bearer" && + auth.name === args.name + ); + }); + + if (filteredOperations.length === 0) { + throw new ApiKeyAuthMissingInSpecError(actionName, args.name); + } + + const servers = filteredOperations.map((value) => value.server); + + const uniqueServerUrls = servers.filter((value, index, self) => self.indexOf(value) === index); + + return uniqueServerUrls; } export function validateDomain(domain: string[], actionName: string): void { @@ -57,7 +62,7 @@ export function validateDomain(domain: string[], actionName: string): void { throw new ApiKeyDomainInvalidError(actionName); } - if (domain.length === 0) { + if (domain.length === 0 || domain.includes("")) { throw new ApiKeyFailedToGetDomainError(actionName); } } diff --git a/packages/fx-core/src/component/driver/oauth/error/oauthAuthInfoInvalid.ts b/packages/fx-core/src/component/driver/oauth/error/oauthAuthInfoInvalid.ts index d675b003c5..b1dd7ab3ba 100644 --- a/packages/fx-core/src/component/driver/oauth/error/oauthAuthInfoInvalid.ts +++ b/packages/fx-core/src/component/driver/oauth/error/oauthAuthInfoInvalid.ts @@ -5,7 +5,7 @@ import { UserError } from "@microsoft/teamsfx-api"; import { getDefaultString, getLocalizedString } from "../../../../common/localizeUtils"; const errorCode = "OauthAuthInfoInvalid"; -const messageKey = "driver.apiKey.error.oauthAuthInfoInvalid"; +const messageKey = "driver.oauth.error.oauthAuthInfoInvalid"; export class OauthAuthInfoInvalid extends UserError { constructor(actionName: string) { diff --git a/packages/fx-core/src/component/driver/oauth/error/oauthAuthMissingInSpec.ts b/packages/fx-core/src/component/driver/oauth/error/oauthAuthMissingInSpec.ts new file mode 100644 index 0000000000..692f01f39c --- /dev/null +++ b/packages/fx-core/src/component/driver/oauth/error/oauthAuthMissingInSpec.ts @@ -0,0 +1,19 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. + +import { UserError } from "@microsoft/teamsfx-api"; +import { getDefaultString, getLocalizedString } from "../../../../common/localizeUtils"; + +const errorCode = "OauthAuthMissingInSpec"; +const messageKey = "driver.oauth.error.oauthAuthMissingInSpec"; + +export class OauthAuthMissingInSpec extends UserError { + constructor(actionName: string, authName: string) { + super({ + source: actionName, + name: errorCode, + message: getDefaultString(messageKey, authName), + displayMessage: getLocalizedString(messageKey, authName), + }); + } +} diff --git a/packages/fx-core/src/component/driver/oauth/utility/utility.ts b/packages/fx-core/src/component/driver/oauth/utility/utility.ts index 8c62346b44..b46364524d 100644 --- a/packages/fx-core/src/component/driver/oauth/utility/utility.ts +++ b/packages/fx-core/src/component/driver/oauth/utility/utility.ts @@ -13,6 +13,7 @@ import { OauthDomainInvalidError } from "../error/oauthDomainInvalid"; import { OauthFailedToGetDomainError } from "../error/oauthFailedToGetDomain"; import { OauthAuthInfoInvalid } from "../error/oauthAuthInfoInvalid"; import { UpdateOauthArgs } from "../interface/updateOauthArgs"; +import { OauthAuthMissingInSpec } from "../error/oauthAuthMissingInSpec"; export interface OauthInfo { domain: string[]; @@ -51,6 +52,10 @@ export async function getandValidateOauthInfoFromSpec( return auth && auth.authScheme.type === "oauth2" && auth.name === args.name; }); + if (operations.length === 0) { + throw new OauthAuthMissingInSpec(actionName, args.name); + } + const domains = operations .map((value) => { return value.server; @@ -103,7 +108,7 @@ function validateDomain(domain: string[], actionName: string): void { throw new OauthDomainInvalidError(actionName); } - if (domain.length === 0) { + if (domain.length === 0 || domain.includes("")) { throw new OauthFailedToGetDomainError(actionName); } } diff --git a/packages/fx-core/src/component/driver/script/scriptDriver.ts b/packages/fx-core/src/component/driver/script/scriptDriver.ts index 66353b2dff..4f51b25410 100644 --- a/packages/fx-core/src/component/driver/script/scriptDriver.ts +++ b/packages/fx-core/src/component/driver/script/scriptDriver.ts @@ -102,14 +102,14 @@ export async function executeCommand( timeout?: number, redirectTo?: string ): Promise> { - const systemEncoding = await getSystemEncoding(command); + let systemEncoding = await getSystemEncoding(command); + if (command.startsWith("dotnet ")) { + systemEncoding = "utf-8"; + } const dshell = await defaultShell(); return new Promise((resolve) => { const finalShell = shell || dshell; const finalCmd = command; - // if (typeof finalShell === "string" && finalShell.includes("cmd")) { - // finalCmd = `%ComSpec% /D /E:ON /V:OFF /S /C "CALL ${command}"`; - // } const platform = os.platform(); let workingDir = workingDirectory || "."; workingDir = path.isAbsolute(workingDir) ? workingDir : path.join(projectPath, workingDir); diff --git a/packages/fx-core/src/component/driver/teamsApp/utils/CopilotGptManifestUtils.ts b/packages/fx-core/src/component/driver/teamsApp/utils/CopilotGptManifestUtils.ts index 21e109f74c..a43ea6dc4c 100644 --- a/packages/fx-core/src/component/driver/teamsApp/utils/CopilotGptManifestUtils.ts +++ b/packages/fx-core/src/component/driver/teamsApp/utils/CopilotGptManifestUtils.ts @@ -187,6 +187,30 @@ export class CopilotGptManifestUtils { id, file: pluginFile, }); + + const actionPath = path.join(path.dirname(copilotGptPath), pluginFile); + const actionManifest = await fs.readJson(actionPath); + const conversationStarters = actionManifest.capabilities?.conversation_starters; + + if (conversationStarters) { + if (!gptManifest.conversation_starters) { + gptManifest.conversation_starters = []; + } + + for (const starter of conversationStarters) { + if (gptManifest.conversation_starters.length >= 6) { + break; + } + if ( + !gptManifest.conversation_starters.some( + (existingStarter) => existingStarter.text === starter.text + ) + ) { + gptManifest.conversation_starters.push(starter); + } + } + } + const updateGptManifestRes = await copilotGptManifestUtils.writeCopilotGptManifestFile( gptManifest, copilotGptPath @@ -288,15 +312,46 @@ export class CopilotGptManifestUtils { } } - public async getDefaultNextAvailablePluginManifestPath(folder: string) { - const pluginManifestNamePrefix = DefaultPluginManifestFileName.split(".")[0]; + public async getDefaultNextAvailablePluginManifestPath( + folder: string, + pluginManifestFileName = DefaultPluginManifestFileName, + isKiotaIntegration = false + ) { + if (!(await fs.pathExists(path.join(folder, pluginManifestFileName)))) { + return path.join(folder, pluginManifestFileName); + } + const pluginManifestNamePrefix = pluginManifestFileName.split(".")[0]; let pluginFileNameSuffix = 1; - let pluginManifestName = `${pluginManifestNamePrefix}_${pluginFileNameSuffix}.json`; + let pluginManifestName = this.getPluginManifestFileName( + pluginManifestNamePrefix, + pluginFileNameSuffix, + isKiotaIntegration + ); while (await fs.pathExists(path.join(folder, pluginManifestName))) { - pluginManifestName = `${pluginManifestNamePrefix}_${++pluginFileNameSuffix}.json`; + pluginFileNameSuffix++; + pluginManifestName = this.getPluginManifestFileName( + pluginManifestNamePrefix, + pluginFileNameSuffix, + isKiotaIntegration + ); } return path.join(folder, pluginManifestName); } + + getPluginManifestFileName( + pluginManifestNamePrefix: string, + pluginFileNameSuffix: number, + isKiotaIntegration: boolean + ) { + let pluginManifestName; + if (isKiotaIntegration) { + const pluginManifestNameSplit = pluginManifestNamePrefix.split("-"); + pluginManifestName = `${pluginManifestNameSplit[0]}_${pluginFileNameSuffix}-${pluginManifestNameSplit[1]}.json`; + } else { + pluginManifestName = `${pluginManifestNamePrefix}_${pluginFileNameSuffix}.json`; + } + return pluginManifestName; + } } export const copilotGptManifestUtils = new CopilotGptManifestUtils(); diff --git a/packages/fx-core/src/component/driver/teamsApp/utils/ManifestUtils.ts b/packages/fx-core/src/component/driver/teamsApp/utils/ManifestUtils.ts index 57d60d2bf2..c6f9d11fc5 100644 --- a/packages/fx-core/src/component/driver/teamsApp/utils/ManifestUtils.ts +++ b/packages/fx-core/src/component/driver/teamsApp/utils/ManifestUtils.ts @@ -112,6 +112,13 @@ export class ManifestUtils { if (fs.existsSync(filePath)) { return filePath; } + + // Samples from https://github.com/OfficeDev/Office-Add-in-samples/tree/main/Samples/outlook-set-signature have the manifest in root folder + const officeAddinManifestPath = path.join(projectPath, "manifest.json"); + if (fs.existsSync(officeAddinManifestPath)) { + return officeAddinManifestPath; + } + return path.join(projectPath, "appPackage", "manifest.json"); } @@ -406,21 +413,23 @@ export class ManifestUtils { maxLength = 25 ): Promise> { const manifestPath = this.getTeamsAppManifestPath(projectPath); - const manifest = (await fs.readJson(manifestPath)) as TeamsAppManifest; - const shortName = manifest.name.short; - let hasSuffix = false; - let trimmedName = shortName; - if (shortName.includes("${{APP_NAME_SUFFIX}}")) { - hasSuffix = true; - trimmedName = shortName.replace("${{APP_NAME_SUFFIX}}", ""); - } - if (trimmedName.length <= maxLength) return ok(undefined); - let newShortName = trimmedName.replace(/\s/g, "").slice(0, maxLength); - if (hasSuffix) { - newShortName += "${{APP_NAME_SUFFIX}}"; + if (fs.pathExistsSync(manifestPath)) { + const manifest = (await fs.readJson(manifestPath)) as TeamsAppManifest; + const shortName = manifest.name.short; + let hasSuffix = false; + let trimmedName = shortName; + if (shortName.includes("${{APP_NAME_SUFFIX}}")) { + hasSuffix = true; + trimmedName = shortName.replace("${{APP_NAME_SUFFIX}}", ""); + } + if (trimmedName.length <= maxLength) return ok(undefined); + let newShortName = trimmedName.replace(/\s/g, "").slice(0, maxLength); + if (hasSuffix) { + newShortName += "${{APP_NAME_SUFFIX}}"; + } + manifest.name.short = newShortName; + await fs.writeFile(manifestPath, JSON.stringify(manifest, null, 2)); } - manifest.name.short = newShortName; - await fs.writeFile(manifestPath, JSON.stringify(manifest, null, 2)); return ok(undefined); } } diff --git a/packages/fx-core/src/component/driver/teamsApp/utils/PluginManifestUtils.ts b/packages/fx-core/src/component/driver/teamsApp/utils/PluginManifestUtils.ts index 85694a90d8..3205a87546 100644 --- a/packages/fx-core/src/component/driver/teamsApp/utils/PluginManifestUtils.ts +++ b/packages/fx-core/src/component/driver/teamsApp/utils/PluginManifestUtils.ts @@ -173,26 +173,64 @@ export class PluginManifestUtils { } } - public async getDefaultNextAvailableApiSpecPath(apiSpecPath: string, apiSpecFolder: string) { + public async getDefaultNextAvailableApiSpecPath( + apiSpecPath: string, + apiSpecFolder: string, + apiSpecFileName?: string, + isKiotaIntegration = false + ) { let isYaml = false; try { isYaml = !(await isJsonSpecFile(apiSpecPath)); } catch (e) {} - let openApiSpecFileName = isYaml ? DefaultApiSpecYamlFileName : DefaultApiSpecJsonFileName; + let openApiSpecFileName = + apiSpecFileName ?? (isYaml ? DefaultApiSpecYamlFileName : DefaultApiSpecJsonFileName); + // Check if the default file name already exists + if (!(await fs.pathExists(path.join(apiSpecFolder, openApiSpecFileName)))) { + return path.join(apiSpecFolder, openApiSpecFileName); + } + const openApiSpecFileNamePrefix = openApiSpecFileName.split(".")[0]; const openApiSpecFileType = openApiSpecFileName.split(".")[1]; let apiSpecFileNameSuffix = 1; - openApiSpecFileName = `${openApiSpecFileNamePrefix}_${apiSpecFileNameSuffix}.${openApiSpecFileType}`; + openApiSpecFileName = this.getApiSpecFileName( + openApiSpecFileNamePrefix, + openApiSpecFileType, + apiSpecFileNameSuffix, + isKiotaIntegration + ); while (await fs.pathExists(path.join(apiSpecFolder, openApiSpecFileName))) { - openApiSpecFileName = `${openApiSpecFileNamePrefix}_${++apiSpecFileNameSuffix}.${openApiSpecFileType}`; + apiSpecFileNameSuffix++; + openApiSpecFileName = this.getApiSpecFileName( + openApiSpecFileNamePrefix, + openApiSpecFileType, + apiSpecFileNameSuffix, + isKiotaIntegration + ); } const openApiSpecFilePath = path.join(apiSpecFolder, openApiSpecFileName); return openApiSpecFilePath; } + getApiSpecFileName( + openApiSpecFileNamePrefix: string, + openApiSpecFileType: string, + apiSpecFileNameSuffix: number, + isKiotaIntegration: boolean + ): string { + let openApiSpecFileName; + if (isKiotaIntegration) { + const apiSpecNameSplit = openApiSpecFileNamePrefix.split("-"); + openApiSpecFileName = `${apiSpecNameSplit[0]}_${apiSpecFileNameSuffix}-${apiSpecNameSplit[1]}.${openApiSpecFileType}`; + } else { + openApiSpecFileName = `${openApiSpecFileNamePrefix}_${apiSpecFileNameSuffix}.${openApiSpecFileType}`; + } + return openApiSpecFileName; + } + async getApiSpecFilePathFromPlugin( plugin: PluginManifestSchema, pluginPath: string diff --git a/packages/fx-core/src/component/driver/teamsApp/utils/telemetry.ts b/packages/fx-core/src/component/driver/teamsApp/utils/telemetry.ts index 1318415757..879c0a8b71 100644 --- a/packages/fx-core/src/component/driver/teamsApp/utils/telemetry.ts +++ b/packages/fx-core/src/component/driver/teamsApp/utils/telemetry.ts @@ -15,6 +15,7 @@ export enum TelemetryPropertyKey { pluginValidationErrors = "plugin-validation-errors", gptValidationErrors = "gpt-validation-errors", gptActionValidationErrors = "gpt-action-validation-errors", + localizationValidationErrors = "localization-validation-errors", } export enum TelemetryPropertyValue { diff --git a/packages/fx-core/src/component/driver/teamsApp/validate.ts b/packages/fx-core/src/component/driver/teamsApp/validate.ts index 1d26c57f53..a87deb2c8a 100644 --- a/packages/fx-core/src/component/driver/teamsApp/validate.ts +++ b/packages/fx-core/src/component/driver/teamsApp/validate.ts @@ -1,7 +1,16 @@ // Copyright (c) Microsoft Corporation. // Licensed under the MIT license. -import { Result, FxError, ok, err, Platform, ManifestUtil, Colors } from "@microsoft/teamsfx-api"; +import { + Result, + FxError, + ok, + err, + Platform, + ManifestUtil, + Colors, + TeamsAppManifest, +} from "@microsoft/teamsfx-api"; import { hooks } from "@feathersjs/hooks/lib"; import { Service } from "typedi"; import { EOL } from "os"; @@ -96,6 +105,18 @@ export class ValidateManifestDriver implements StepDriver { ); } + // validate localization files + const localizationFilesValidationRes = await this.validateLocalizatoinFiles( + args, + context, + manifest + ); + if (localizationFilesValidationRes.isErr()) { + return err(localizationFilesValidationRes.error); + } + telemetryProperties[TelemetryPropertyKey.localizationValidationErrors] = + localizationFilesValidationRes.value.error.map((r: string) => r.replace(/\//g, "")).join(";"); + let declarativeCopilotValidationResult; let pluginValidationResult; let pluginPath = ""; @@ -175,6 +196,7 @@ export class ValidateManifestDriver implements StepDriver { const allErrorCount = manifestValidationResult.length + + localizationFilesValidationRes.value.error.length + (declarativeCopilotValidationResult?.validationResult.length ?? 0) + (pluginValidationResult?.validationResult.length ?? 0) + actionErrorCount; @@ -215,6 +237,23 @@ export class ValidateManifestDriver implements StepDriver { }); }); } + if (localizationFilesValidationRes.value.error.length > 0) { + outputMessage.push({ + content: + getDefaultString( + "driver.teamsApp.summary.validateTeamsManifest.checkPath", + localizationFilesValidationRes.value.filePath + ) + "\n", + color: Colors.BRIGHT_WHITE, + }); + localizationFilesValidationRes.value.error.map((error: string) => { + outputMessage.push({ content: `${SummaryConstant.Failed} `, color: Colors.BRIGHT_RED }); + outputMessage.push({ + content: `${error}\n`, + color: Colors.BRIGHT_WHITE, + }); + }); + } if (declarativeCopilotValidationResult) { const validationMessage = copilotGptManifestUtils.logValidationErrors( declarativeCopilotValidationResult, @@ -258,6 +297,21 @@ export class ValidateManifestDriver implements StepDriver { teamsManifestErrors; } + if (localizationFilesValidationRes.value.error.length > 0) { + const localizationErrors = localizationFilesValidationRes.value.error + .map((error: string) => { + return `${SummaryConstant.Failed} ${error}`; + }) + .join(EOL); + outputMessage += + EOL + + getLocalizedString( + "driver.teamsApp.summary.validateTeamsManifest.checkPath", + localizationFilesValidationRes.value.filePath + ) + + EOL + + localizationErrors; + } if (declarativeCopilotValidationResult) { const validationMessage = copilotGptManifestUtils.logValidationErrors( declarativeCopilotValidationResult, @@ -341,4 +395,91 @@ export class ValidateManifestDriver implements StepDriver { } return ok(undefined); } + + public async validateLocalizatoinFiles( + args: ValidateManifestArgs, + context: WrapDriverContext, + manifest: TeamsAppManifest + ): Promise> { + if ( + manifest.localizationInfo?.additionalLanguages?.length == 0 && + !manifest.localizationInfo?.defaultLanguageFile + ) { + return ok({ error: [] }); + } + const languageList = manifest.localizationInfo?.additionalLanguages || []; + if (manifest.localizationInfo?.defaultLanguageFile) { + languageList.push({ + languageTag: manifest.localizationInfo.defaultLanguageTag, + file: manifest.localizationInfo.defaultLanguageFile, + }); + } + for (const language of languageList) { + const filePath = language?.file; + if (!filePath) { + return err( + AppStudioResultFactory.UserError( + AppStudioError.ValidationFailedError.name, + AppStudioError.ValidationFailedError.message([ + getLocalizedString("error.appstudio.localizationFile.pathNotDefined", filePath), + ]) + ) + ); + } + const localizationFileDir = path.dirname( + getAbsolutePath(args.manifestPath, context.projectPath) + ); + const localizationFilePath = getAbsolutePath(filePath, localizationFileDir); + + const manifestRes = await manifestUtils._readAppManifest(localizationFilePath); + if (manifestRes.isErr()) { + return err(manifestRes.error); + } + const localizationFile = manifestRes.value; + try { + const schema = await ManifestUtil.fetchSchema(localizationFile); + // the current localization schema has invalid regex sytax, we need to manually fix the properties temporarily + const activityDespString = + "^activities.activityTypes\\[\\b([0-9]|[1-8][0-9]|9[0-9]|1[01][0-9]|12[0-7])\\b]\\.description$"; + const fixedActivityDespString = + "^activities.activityTypes\\[\\b([0-9]|[1-8][0-9]|9[0-9]|1[01][0-9]|12[0-7])\\b\\]\\.description$"; + if (schema.patternProperties?.[activityDespString]) { + schema.patternProperties[fixedActivityDespString] = + schema.patternProperties[activityDespString]; + delete schema.patternProperties[activityDespString]; + } + const activityTemplateString = + "^activities.activityTypes\\[\\b([0-9]|[1-8][0-9]|9[0-9]|1[01][0-9]|12[0-7])\\b]\\.templateText$"; + const fixedActivityTemplateString = + "^activities.activityTypes\\[\\b([0-9]|[1-8][0-9]|9[0-9]|1[01][0-9]|12[0-7])\\b\\]\\.templateText$"; + if (schema.patternProperties?.[activityTemplateString]) { + schema.patternProperties[fixedActivityTemplateString] = + schema.patternProperties[activityTemplateString]; + delete schema.patternProperties[activityTemplateString]; + } + + const validationRes = await ManifestUtil.validateManifestAgainstSchema( + localizationFile, + schema + ); + if (validationRes.length > 0) { + return ok({ error: validationRes, filePath: localizationFilePath }); + } + } catch (e: any) { + return err( + AppStudioResultFactory.UserError( + AppStudioError.ValidationFailedError.name, + AppStudioError.ValidationFailedError.message([ + getLocalizedString( + "error.appstudio.localizationFile.validationException", + filePath, + e.message + ), + ]) + ) + ); + } + } + return ok({ error: [] }); + } } diff --git a/packages/fx-core/src/component/generator/apiSpec/generator.ts b/packages/fx-core/src/component/generator/apiSpec/generator.ts index e2b0dbb73a..de6f3991dd 100644 --- a/packages/fx-core/src/component/generator/apiSpec/generator.ts +++ b/packages/fx-core/src/component/generator/apiSpec/generator.ts @@ -299,6 +299,9 @@ export class SpecGenerator extends DefaultTemplateGenerator { const getTemplateInfosState = inputs.getTemplateInfosState as TemplateInfosState; const isDeclarativeCopilot = inputs[QuestionNames.Capabilities] === CapabilityOptions.declarativeCopilot().id; + const isKiotaIntegration = + featureFlagManager.getBooleanValue(FeatureFlags.KiotaIntegration) && + !!inputs[QuestionNames.ApiPluginManifestPath]; const manifestPath = path.join( destinationPath, AppPackageFolderName, @@ -307,9 +310,11 @@ export class SpecGenerator extends DefaultTemplateGenerator { const apiSpecFolderPath = path.join( destinationPath, AppPackageFolderName, - DefaultApiSpecFolderName + isKiotaIntegration ? "" : DefaultApiSpecFolderName ); - const openapiSpecFileName = getTemplateInfosState.isYaml + const openapiSpecFileName = isKiotaIntegration + ? path.basename(inputs[QuestionNames.ApiSpecLocation]) + : getTemplateInfosState.isYaml ? DefaultApiSpecYamlFileName : DefaultApiSpecJsonFileName; @@ -331,7 +336,13 @@ export class SpecGenerator extends DefaultTemplateGenerator { let warnings: WarningResult[]; const pluginManifestPath = getTemplateInfosState.type === ProjectType.Copilot - ? path.join(destinationPath, AppPackageFolderName, DefaultPluginManifestFileName) + ? path.join( + destinationPath, + AppPackageFolderName, + isKiotaIntegration + ? path.basename(inputs[QuestionNames.ApiPluginManifestPath]) + : DefaultPluginManifestFileName + ) : undefined; const responseTemplateFolder = getTemplateInfosState.type === ProjectType.SME @@ -367,7 +378,7 @@ export class SpecGenerator extends DefaultTemplateGenerator { const addAcionResult = await copilotGptManifestUtils.addAction( gptManifestPath, defaultDeclarativeCopilotActionId, - DefaultPluginManifestFileName + path.basename(pluginManifestPath!) ); if (addAcionResult.isErr()) { return err(addAcionResult.error); @@ -379,7 +390,13 @@ export class SpecGenerator extends DefaultTemplateGenerator { const spec = specs[1]; try { const language = inputs[QuestionNames.ProgrammingLanguage] as ProgrammingLanguage; - await updateForCustomApi(spec, language, destinationPath, openapiSpecFileName); + const updateWarnings = await updateForCustomApi( + spec, + language, + destinationPath, + openapiSpecFileName + ); + warnings.push(...updateWarnings); } catch (error: any) { throw new SystemError( this.componentName, diff --git a/packages/fx-core/src/component/generator/apiSpec/helper.ts b/packages/fx-core/src/component/generator/apiSpec/helper.ts index ac23d879c7..2932057a8b 100644 --- a/packages/fx-core/src/component/generator/apiSpec/helper.ts +++ b/packages/fx-core/src/component/generator/apiSpec/helper.ts @@ -21,7 +21,7 @@ import { WarningResult, WarningType, } from "@microsoft/m365-spec-parser"; -import { ListAPIInfo } from "@microsoft/m365-spec-parser/dist/src/interfaces"; +import { AuthType, ListAPIInfo } from "@microsoft/m365-spec-parser/dist/src/interfaces"; import { ApiOperation, AppPackageFolderName, @@ -62,6 +62,8 @@ import { } from "../../../common/telemetry"; import * as util from "util"; import { SpecParserSource } from "../../../common/constants"; +import { MetadataV3 } from "../../../common/versionMetadata"; +import { ActionInjector, AuthActionInjectResult } from "../../configManager/actionInjector"; const enum telemetryProperties { validationStatus = "validation-status", @@ -594,6 +596,55 @@ export function logValidationResults( void context.logProvider.info(outputMessage); } +export async function injectAuthAction( + projectPath: string, + authName: string, + authScheme: AuthType, + outputApiSpecPath: string, + forceToAddNew: boolean +): Promise { + const ymlPath = path.join(projectPath, MetadataV3.configFile); + const localYamlPath = path.join(projectPath, MetadataV3.localConfigFile); + + const relativeSpecPath = "./" + path.relative(projectPath, outputApiSpecPath).replace(/\\/g, "/"); + + if (Utils.isBearerTokenAuth(authScheme)) { + const res = await ActionInjector.injectCreateAPIKeyAction( + ymlPath, + authName, + relativeSpecPath, + forceToAddNew + ); + + if (await fs.pathExists(localYamlPath)) { + await ActionInjector.injectCreateAPIKeyAction( + localYamlPath, + authName, + relativeSpecPath, + forceToAddNew + ); + } + return res; + } else if (Utils.isOAuthWithAuthCodeFlow(authScheme)) { + const res = await ActionInjector.injectCreateOAuthAction( + ymlPath, + authName, + relativeSpecPath, + forceToAddNew + ); + + if (await fs.pathExists(localYamlPath)) { + await ActionInjector.injectCreateOAuthAction( + localYamlPath, + authName, + relativeSpecPath, + forceToAddNew + ); + } + return res; + } +} + /** * Generate scaffolding warning summary. * @param warnings warnings returned from spec-parser. @@ -687,6 +738,20 @@ function formatApiSpecValidationWarningMessage( ); } + const specialCharactersWarnings = specWarnings.filter( + (w) => w.type === WarningType.OperationIdContainsSpecialCharacters + ); + + specialCharactersWarnings.forEach((warning) => { + resultWarnings.push( + getLocalizedString( + "core.copilotPlugin.scaffold.summary.warning.operationIdContainsSpecialCharacters", + warning.data.operationId, + warning.data.operationId.replace(/[^a-zA-Z0-9]/g, "_") + ) + ); + }); + return resultWarnings; } @@ -1061,7 +1126,8 @@ async function updateAdaptiveCardForCustomApi( specItems: SpecObject[], language: string, destinationPath: string -): Promise { +): Promise { + const warnings: WarningResult[] = []; if (commonLanguages.includes(language as ProgrammingLanguage)) { let adaptiveCardsFolderPath = path.join(destinationPath, "src", "adaptiveCards"); if (language === ProgrammingLanguage.CSharp) { @@ -1071,14 +1137,43 @@ async function updateAdaptiveCardForCustomApi( for (const item of specItems) { const name = item.item.operationId!.replace(/[^a-zA-Z0-9]/g, "_"); - const [card, jsonPath] = AdaptiveCardGenerator.generateAdaptiveCard(item.item, true); - if (jsonPath !== "$" && card.body && card.body[0] && (card.body[0] as any).$data) { - (card.body[0] as any).$data = `\${${jsonPath}}`; + try { + const [card, jsonPath, jsonData, generateWarnings] = + AdaptiveCardGenerator.generateAdaptiveCard(item.item, true, 5); + if (jsonPath !== "$" && card.body && card.body[0] && (card.body[0] as any).$data) { + (card.body[0] as any).$data = `\${${jsonPath}}`; + } + const cardFilePath = path.join(adaptiveCardsFolderPath, `${name}.json`); + const jsonDataPath = path.join(adaptiveCardsFolderPath, `${name}.data.json`); + await fs.writeFile(cardFilePath, JSON.stringify(card, null, 2)); + await fs.writeFile(jsonDataPath, JSON.stringify(jsonData, null, 2)); + + generateWarnings.forEach((w) => { + warnings.push({ + type: WarningType.GenerateJsonDataFailed, + // TODO: move message to package.nls.json file + content: util.format( + "Failed to create the adaptive card mock data for API '%s': %s. Mitigation: Not required but you can manually add it to the adaptiveCards folder.", + item.item.operationId, + w.content + ), + data: item.item.operationId, + }); + }); + } catch (err) { + warnings.push({ + type: WarningType.GenerateCardFailed, + content: getLocalizedString( + "core.copilotPlugin.scaffold.summary.warning.generate.ac.failed", + item.item.operationId, + err.message + ), + data: item.item.operationId, + }); } - const cardFilePath = path.join(adaptiveCardsFolderPath, `${name}.json`); - await fs.writeFile(cardFilePath, JSON.stringify(card, null, 2)); } } + return warnings; } function filterSchema(schema: OpenAPIV3.SchemaObject): OpenAPIV3.SchemaObject { @@ -1189,14 +1284,23 @@ const ActionCode = { app.ai.action("{{operationId}}", async (context, state, parameter) => { const client = await api.getClient(); // Add authentication configuration for the client - const path = client.paths["{{pathUrl}}"]; - if (path && path.{{method}}) { - const result = await path.{{method}}(parameter.path, parameter.body, { + const apiPath = client.paths["{{pathUrl}}"]; + if (apiPath && apiPath.{{method}}) { + const result = await apiPath.{{method}}(parameter.path, parameter.body, { params: parameter.query, }); + if (!result || !result.data) { + throw new Error("Get empty result from api call."); + } const cardName = "{{operationId}}".replace(/[^a-zA-Z0-9]/g, "_"); - const card = generateAdaptiveCard("../adaptiveCards/" + cardName + ".json", result); - await context.sendActivity({ attachments: [card] }); + const cardTemplatePath = path.join(__dirname, '../adaptiveCards', cardName + '.json'); + if (await fs.exists(cardTemplatePath)){ + const card = generateAdaptiveCard(cardTemplatePath, result); + await context.sendActivity({ attachments: [card] }); + } + else { + await context.sendActivity(JSON.stringify(result.data)); + } } else { await context.sendActivity("no result"); } @@ -1207,14 +1311,23 @@ app.ai.action("{{operationId}}", async (context, state, parameter) => { app.ai.action("{{operationId}}", async (context: TurnContext, state: ApplicationTurnState, parameter: any) => { const client = await api.getClient(); // Add authentication configuration for the client - const path = client.paths["{{pathUrl}}"]; - if (path && path.{{method}}) { - const result = await path.{{method}}(parameter.path, parameter.body, { + const apiPath = client.paths["{{pathUrl}}"]; + if (apiPath && apiPath.{{method}}) { + const result = await apiPath.{{method}}(parameter.path, parameter.body, { params: parameter.query, }); + if (!result || !result.data) { + throw new Error("Get empty result from api call."); + } const cardName = "{{operationId}}".replace(/[^a-zA-Z0-9]/g, "_"); - const card = generateAdaptiveCard("../adaptiveCards/" + cardName + ".json", result); - await context.sendActivity({ attachments: [card] }); + const cardTemplatePath = path.join(__dirname, '../adaptiveCards', cardName + '.json'); + if (await fs.exists(cardTemplatePath)){ + const card = generateAdaptiveCard(cardTemplatePath, result); + await context.sendActivity({ attachments: [card] }); + } + else { + await context.sendActivity(JSON.stringify(result.data)); + } } else { await context.sendActivity("no result"); } @@ -1237,18 +1350,22 @@ async def {{operationId}}( await context.send_activity(resp.reason) else: card_template_path = os.path.join(current_dir, 'adaptiveCards/{{operationId}}.json') - with open(card_template_path) as card_template_file: + if not os.path.exists(card_template_path): + json_resoponse_str = resp.text + await context.send_activity(json_resoponse_str) + else: + with open(card_template_path) as card_template_file: adaptive_card_template = card_template_file.read() - renderer = AdaptiveCardRenderer(adaptive_card_template) + renderer = AdaptiveCardRenderer(adaptive_card_template) - json_resoponse_str = resp.text - rendered_card_str = renderer.render(json_resoponse_str) - rendered_card_json = json.loads(rendered_card_str) - card = CardFactory.adaptive_card(rendered_card_json) - message = MessageFactory.attachment(card) - - await context.send_activity(message) + json_resoponse_str = resp.text + rendered_card_str = renderer.render(json_resoponse_str) + rendered_card_json = json.loads(rendered_card_str) + card = CardFactory.adaptive_card(rendered_card_json) + message = MessageFactory.attachment(card) + + await context.send_activity(message) return "success" `, cs: ` @@ -1263,9 +1380,14 @@ async def {{operationId}}( var data = response.Content; var cardTemplatePath = "./adaptiveCards/{{operationId}}.json"; - var message = RenderCardToMessage(cardTemplatePath, data); - - await turnContext.SendActivityAsync(message); + if (File.Exists(cardTemplatePath)) { + var message = RenderCardToMessage(cardTemplatePath, data); + await turnContext.SendActivityAsync(message); + } + else + { + await turnContext.SendActivityAsync(data); + } } catch (Exception ex) { await turnContext.SendActivityAsync("Failed to call API with error: " + ex.Message); @@ -1375,7 +1497,8 @@ export async function updateForCustomApi( language: string, destinationPath: string, openapiSpecFileName: string -): Promise { +): Promise { + const warnings: WarningResult[] = []; let chatFolder = path.join(destinationPath, "src", "prompts", "chat"); if (language === ProgrammingLanguage.CSharp) { chatFolder = path.join(destinationPath, "prompts", "Chat"); @@ -1388,13 +1511,21 @@ export async function updateForCustomApi( const [specItems, needAuth] = parseSpec(spec); // 2. update adaptive card folder - await updateAdaptiveCardForCustomApi(specItems, language, destinationPath); + const generateWarnings = await updateAdaptiveCardForCustomApi( + specItems, + language, + destinationPath + ); + + warnings.push(...generateWarnings); // 3. update actions file await updateActionForCustomApi(specItems, language, chatFolder); // 4. update code await updateCodeForCustomApi(specItems, language, destinationPath, openapiSpecFileName, needAuth); + + return warnings; } const EnvNameMapping: { [authType: string]: string } = { diff --git a/packages/fx-core/src/component/generator/generator.ts b/packages/fx-core/src/component/generator/generator.ts index 9f5089ee68..66b44186f8 100644 --- a/packages/fx-core/src/component/generator/generator.ts +++ b/packages/fx-core/src/component/generator/generator.ts @@ -93,6 +93,7 @@ export class Generator { : "", NewProjectTypeName: process.env.TEAMSFX_NEW_PROJECT_TYPE_NAME ?? "TeamsApp", NewProjectTypeExt: process.env.TEAMSFX_NEW_PROJECT_TYPE_EXTENSION ?? "ttkproj", + CEAEnabled: featureFlagManager.getBooleanValue(FeatureFlags.CEAEnabled) ? "true" : "", }; } @hooks([ diff --git a/packages/fx-core/src/component/generator/officeAddin/generator.ts b/packages/fx-core/src/component/generator/officeAddin/generator.ts index cab2fb3a50..c8f1eb6e75 100644 --- a/packages/fx-core/src/component/generator/officeAddin/generator.ts +++ b/packages/fx-core/src/component/generator/officeAddin/generator.ts @@ -105,10 +105,9 @@ export class OfficeAddinGenerator { const capability = inputs[QuestionNames.Capabilities]; const inputHost = inputs[QuestionNames.OfficeAddinHost]; const workingDir = process.cwd(); - const importProgressStr = - projectType === ProjectTypeOptions.officeAddin().id - ? getLocalizedString("core.generator.officeAddin.importOfficeProject.title") - : getLocalizedString("core.generator.officeAddin.importProject.title"); + const importProgressStr = getLocalizedString( + "core.generator.officeAddin.importOfficeProject.title" + ); const importProgress = context.userInteraction.createProgressBar(importProgressStr, 3); process.chdir(addinRoot); @@ -178,7 +177,7 @@ export class OfficeAddinGenerator { ); if (manifestFile.endsWith(".xml")) { // Need to convert to json project first - await convertProject(manifestFile); + await convertProject(manifestFile, "./backup.zip", "", true); manifestFile = manifestFile.replace(/\.xml$/, ".json"); } inputs[QuestionNames.OfficeAddinHost] = await getHost(manifestFile); diff --git a/packages/fx-core/src/component/generator/officeAddin/helperMethods.ts b/packages/fx-core/src/component/generator/officeAddin/helperMethods.ts index 782bcaccba..215f1cfea4 100644 --- a/packages/fx-core/src/component/generator/officeAddin/helperMethods.ts +++ b/packages/fx-core/src/component/generator/officeAddin/helperMethods.ts @@ -57,8 +57,8 @@ export class HelperMethods { const packageJsonPath = path.join(projectRoot, "package.json"); if (await fse.pathExists(packageJsonPath)) { const content = (await fse.readFile(packageJsonPath)).toString(); - const reg = /\smanifest\.json\"/g; - const data = content.replace(reg, ` appPackage/manifest.json"`); + const reg = /\smanifest\.json/g; + const data = content.replace(reg, ` appPackage/manifest.json`); await fse.writeFile(packageJsonPath, data); } diff --git a/packages/fx-core/src/component/generator/spfx/utils/constants.ts b/packages/fx-core/src/component/generator/spfx/utils/constants.ts index c3f275a84b..be56900cf3 100644 --- a/packages/fx-core/src/component/generator/spfx/utils/constants.ts +++ b/packages/fx-core/src/component/generator/spfx/utils/constants.ts @@ -24,7 +24,7 @@ export class Constants { public static readonly TEAMS_APP_NAME_MAX_LENGTH = 30; public static readonly YO_RC_VERSION = "version"; public static readonly YO_RC_FILE = ".yo-rc.json"; - public static readonly DEFAULT_NODE_VERSION = "16 || 18"; + public static readonly DEFAULT_NODE_VERSION = "18"; public static readonly PACKAGE_JSON_FILE = "package.json"; } diff --git a/packages/fx-core/src/component/generator/templates/templateNames.ts b/packages/fx-core/src/component/generator/templates/templateNames.ts index 8b906f41e5..45ebcbed33 100644 --- a/packages/fx-core/src/component/generator/templates/templateNames.ts +++ b/packages/fx-core/src/component/generator/templates/templateNames.ts @@ -22,7 +22,7 @@ export enum TemplateNames { TabSSR = "non-sso-tab-ssr", SsoTabSSR = "sso-tab-ssr", DashboardTab = "dashboard-tab", - NotificationRestify = "notification-restify", + NotificationExpress = "notification-express", NotificationWebApi = "notification-webapi", NotificationHttpTriggerIsolated = "notification-http-trigger-isolated", NotificationHttpTrigger = "notification-http-trigger", @@ -70,7 +70,7 @@ export const Feature2TemplateName = { [`${CapabilityOptions.tab().id}:ssr`]: TemplateNames.SsoTabSSR, [`${CapabilityOptions.dashboardTab().id}:undefined`]: TemplateNames.DashboardTab, [`${CapabilityOptions.notificationBot().id}:${NotificationTriggerOptions.appService().id}`]: - TemplateNames.NotificationRestify, + TemplateNames.NotificationExpress, [`${CapabilityOptions.notificationBot().id}:${NotificationTriggerOptions.appServiceForVS().id}`]: TemplateNames.NotificationWebApi, [`${CapabilityOptions.notificationBot().id}:${ @@ -170,7 +170,7 @@ export const inputsToTemplateName: Map<{ [key: string]: any }, TemplateNames> = [QuestionNames.Capabilities]: CapabilityOptions.notificationBot().id, [QuestionNames.BotTrigger]: NotificationTriggerOptions.appService().id, }, - TemplateNames.NotificationRestify, + TemplateNames.NotificationExpress, ], [ { diff --git a/packages/fx-core/src/component/generator/templates/templateReplaceMap.ts b/packages/fx-core/src/component/generator/templates/templateReplaceMap.ts index 05f6a6405c..36b8302a36 100644 --- a/packages/fx-core/src/component/generator/templates/templateReplaceMap.ts +++ b/packages/fx-core/src/component/generator/templates/templateReplaceMap.ts @@ -71,5 +71,6 @@ export function getTemplateReplaceMap(inputs: Inputs): { [key: string]: string } : "", NewProjectTypeName: process.env.TEAMSFX_NEW_PROJECT_TYPE_NAME ?? "TeamsApp", NewProjectTypeExt: process.env.TEAMSFX_NEW_PROJECT_TYPE_EXTENSION ?? "ttkproj", + CEAEnabled: featureFlagManager.getBooleanValue(FeatureFlags.CEAEnabled) ? "true" : "", }; } diff --git a/packages/fx-core/src/component/utils/ResourceGroupHelper.ts b/packages/fx-core/src/component/utils/ResourceGroupHelper.ts index f44c87c1a1..5b53a1503d 100644 --- a/packages/fx-core/src/component/utils/ResourceGroupHelper.ts +++ b/packages/fx-core/src/component/utils/ResourceGroupHelper.ts @@ -241,7 +241,6 @@ class ResourceGroupHelper { const checkRes = await rmClient.resourceGroups.checkExistence(resourceGroupName); return ok(!!checkRes.body); } catch (e: any) { - delete e["request"]; return err( new CheckResourceGroupExistenceError( resourceGroupName, diff --git a/packages/fx-core/src/component/utils/envFunctionUtils.ts b/packages/fx-core/src/component/utils/envFunctionUtils.ts index cadf18d179..ee6946331b 100644 --- a/packages/fx-core/src/component/utils/envFunctionUtils.ts +++ b/packages/fx-core/src/component/utils/envFunctionUtils.ts @@ -138,7 +138,7 @@ async function readFileContent( fromPath: string ): Promise> { const ext = path.extname(filePath); - if (ext.toLowerCase() !== ".txt") { + if (ext.toLowerCase() !== ".txt" && ext.toLowerCase() !== ".md") { ctx.logProvider.error( getLocalizedString("core.envFunc.unsupportedFile.errorLog", filePath, "txt") ); @@ -150,7 +150,8 @@ async function readFileContent( try { let fileContent = await fs.readFile(absolutePath, "utf8"); fileContent = stripBom(fileContent); - const processedFileContent = expandEnvironmentVariable(fileContent, envs); + let processedFileContent = expandEnvironmentVariable(fileContent, envs); + processedFileContent = processedFileContent.replace(/\r\n/g, "\n"); return ok(processedFileContent); } catch (e) { ctx.logProvider.error( diff --git a/packages/fx-core/src/core/FxCore.ts b/packages/fx-core/src/core/FxCore.ts index a12dd458f6..2c6fb9cc58 100644 --- a/packages/fx-core/src/core/FxCore.ts +++ b/packages/fx-core/src/core/FxCore.ts @@ -65,7 +65,12 @@ import { MetadataV3, VersionSource, VersionState } from "../common/versionMetada import { ActionInjector } from "../component/configManager/actionInjector"; import { ILifecycle, LifecycleName } from "../component/configManager/interface"; import { YamlParser } from "../component/configManager/parser"; -import { AadConstants, SingleSignOnOptionItem, ViewAadAppHelpLinkV5 } from "../component/constants"; +import { + AadConstants, + KiotaLastCommands, + SingleSignOnOptionItem, + ViewAadAppHelpLinkV5, +} from "../component/constants"; import { coordinator } from "../component/coordinator"; import { UpdateAadAppArgs } from "../component/driver/aad/interface/updateAadAppArgs"; import { UpdateAadAppDriver } from "../component/driver/aad/update"; @@ -103,6 +108,7 @@ import { generateFromApiSpec, generateScaffoldingSummary, getParserOptions, + injectAuthAction, listOperations, listPluginExistingOperations, } from "../component/generator/apiSpec/helper"; @@ -167,6 +173,7 @@ import { SyncManifestArgs } from "../component/driver/teamsApp/interfaces/SyncMa import { SyncManifestDriver } from "../component/driver/teamsApp/syncManifest"; import { generateDriverContext } from "../common/utils"; import { addExistingPlugin } from "../component/generator/copilotExtension/helper"; +import { featureFlagManager, FeatureFlags } from "../common/featureFlags"; export class FxCore { constructor(tools: Tools) { @@ -1694,30 +1701,13 @@ export class FxCore { } if (authNames.size === 1 && authScheme) { - const ymlPath = path.join(inputs.projectPath!, MetadataV3.configFile); - const localYamlPath = path.join(inputs.projectPath!, MetadataV3.localConfigFile); - const authName = [...authNames][0]; - - const relativeSpecPath = - "./" + path.relative(inputs.projectPath!, outputApiSpecPath).replace(/\\/g, "/"); - - if (Utils.isBearerTokenAuth(authScheme)) { - await ActionInjector.injectCreateAPIKeyAction(ymlPath, authName, relativeSpecPath); - - if (await fs.pathExists(localYamlPath)) { - await ActionInjector.injectCreateAPIKeyAction( - localYamlPath, - authName, - relativeSpecPath - ); - } - } else if (Utils.isOAuthWithAuthCodeFlow(authScheme)) { - await ActionInjector.injectCreateOAuthAction(ymlPath, authName, relativeSpecPath); - - if (await fs.pathExists(localYamlPath)) { - await ActionInjector.injectCreateOAuthAction(localYamlPath, authName, relativeSpecPath); - } - } + await injectAuthAction( + inputs.projectPath!, + [...authNames][0], + authScheme, + outputApiSpecPath, + false + ); } let pluginPath: string | undefined; @@ -1850,15 +1840,32 @@ export class FxCore { QuestionMW("addPlugin"), ConcurrentLockerMW, ]) - async addPlugin(inputs: Inputs): Promise> { + async addPlugin(inputs: Inputs): Promise> { if (!inputs.projectPath) { throw new Error("projectPath is undefined"); // should never happen } + + // Call Kiota to select the OpenAPI spec file + if ( + inputs.platform === Platform.VSCode && + featureFlagManager.getBooleanValue(FeatureFlags.KiotaIntegration) && + inputs[QuestionNames.ApiPluginType] === ApiPluginStartOptions.apiSpec().id && + !!!inputs[QuestionNames.ApiPluginManifestPath] + ) { + return ok({ + lastCommand: KiotaLastCommands.addPlugin, + manifestPath: inputs[QuestionNames.ManifestPath], + }); + } + const context = createContext(); const teamsManifestPath = inputs[QuestionNames.ManifestPath]; const appPackageFolder = path.dirname(teamsManifestPath); const isGenerateFromApiSpec = inputs[QuestionNames.ApiPluginType] === ApiPluginStartOptions.apiSpec().id; + const isKiotaIntegration = + featureFlagManager.getBooleanValue(FeatureFlags.KiotaIntegration) && + !!inputs[QuestionNames.ApiPluginManifestPath]; // validate the project is valid for adding plugin const manifestRes = await manifestUtils._readAppManifest(teamsManifestPath); @@ -1896,14 +1903,71 @@ export class FxCore { } const declarativeCopilotManifest = declarativeCopilotManifesRes.value; + let confirmMessage = getLocalizedString( + "core.addApi.confirm", + path.relative(inputs.projectPath, appPackageFolder) + ); + + // Will be used if generating from API spec + let specParser: SpecParser | undefined = undefined; + let authName: string | undefined = undefined; + let authScheme: AuthType | undefined = undefined; + + if (isGenerateFromApiSpec) { + specParser = new SpecParser( + inputs[QuestionNames.ApiSpecLocation].trim(), + getParserOptions(ProjectType.Copilot, true) + ); + const listResult = await specParser.list(); + const authApis = listResult.APIs.filter((value) => value.isValid && !!value.auth); + if ( + inputs.platform === Platform.VSCode && + featureFlagManager.getBooleanValue(FeatureFlags.KiotaIntegration) && + inputs[QuestionNames.ApiPluginType] === ApiPluginStartOptions.apiSpec().id && + !!inputs[QuestionNames.ApiPluginManifestPath] + ) { + inputs[QuestionNames.ApiOperation] = listResult.APIs.filter((value) => value.isValid).map( + (value) => value.api + ); + } + for (const api of inputs[QuestionNames.ApiOperation] as string[]) { + const operation = authApis.find((op) => op.api === api); + if ( + operation && + operation.auth && + (Utils.isBearerTokenAuth(operation.auth.authScheme) || + Utils.isOAuthWithAuthCodeFlow(operation.auth.authScheme)) + ) { + authName = operation.auth.name; + authScheme = operation.auth.authScheme; + break; // Only one auth is supported for one plugin for now. + } + } + + if (authName && authScheme) { + const doesLocalYamlPathExists = await fs.pathExists( + path.join(inputs.projectPath, MetadataV3.localConfigFile) + ); + confirmMessage = doesLocalYamlPathExists + ? getLocalizedString( + "core.addApi.confirm.localTeamsYaml", + path.relative(inputs.projectPath, appPackageFolder), + MetadataV3.localConfigFile, + MetadataV3.configFile + ) + : getLocalizedString( + "core.addApi.confirm.teamsYaml", + path.relative(inputs.projectPath, appPackageFolder), + MetadataV3.configFile + ); + } + } // confirm + const confirmRes = await context.userInteraction.showMessage( "warn", - getLocalizedString( - "core.addApi.confirm", - path.relative(inputs.projectPath, appPackageFolder) - ), + confirmMessage, true, getLocalizedString("core.addApi.continue") ); @@ -1926,16 +1990,22 @@ export class FxCore { let destinationPluginManifestPath: string; // generate files - if (isGenerateFromApiSpec) { - const url = inputs[QuestionNames.ApiSpecLocation].trim(); - + if (isGenerateFromApiSpec && specParser) { destinationPluginManifestPath = - await copilotGptManifestUtils.getDefaultNextAvailablePluginManifestPath(appPackageFolder); + await copilotGptManifestUtils.getDefaultNextAvailablePluginManifestPath( + appPackageFolder, + isKiotaIntegration + ? path.basename(inputs[QuestionNames.ApiPluginManifestPath]) + : undefined, + isKiotaIntegration + ); const destinationApiSpecPath = await pluginManifestUtils.getDefaultNextAvailableApiSpecPath( - url, - path.join(appPackageFolder, DefaultApiSpecFolderName) + inputs[QuestionNames.ApiSpecLocation].trim(), + path.join(appPackageFolder, isKiotaIntegration ? "" : DefaultApiSpecFolderName), + isKiotaIntegration ? path.basename(inputs[QuestionNames.ApiSpecLocation]) : undefined, + isKiotaIntegration ); - const specParser = new SpecParser(url, getParserOptions(ProjectType.Copilot, true)); + const generateRes = await generateFromApiSpec( specParser, teamsManifestPath, @@ -1972,6 +2042,29 @@ export class FxCore { if (addActionRes.isErr()) { return err(addActionRes.error); } + + // update teamspp.local.yaml and teamsapp.yaml if auth action is needed + if (authName && authScheme) { + const authInjectRes = await injectAuthAction( + inputs.projectPath, + authName, + authScheme, + destinationApiSpecPath, + true + ); + if ( + authInjectRes?.defaultRegistrationIdEnvName && + authInjectRes?.registrationIdEnvName && + authInjectRes.defaultRegistrationIdEnvName !== authInjectRes.registrationIdEnvName + ) { + const pluginManifestContent = await fs.readFile(destinationPluginManifestPath, "utf-8"); + const updatedPluginManifestContext = pluginManifestContent.replace( + authInjectRes.defaultRegistrationIdEnvName, + authInjectRes.registrationIdEnvName + ); + await fs.writeFile(destinationPluginManifestPath, updatedPluginManifestContext); + } + } } else { const addPluginRes = await addExistingPlugin( declarativeCopilotManifestPath, diff --git a/packages/fx-core/src/question/constants.ts b/packages/fx-core/src/question/constants.ts index 5ed262e277..1e7b5753eb 100644 --- a/packages/fx-core/src/question/constants.ts +++ b/packages/fx-core/src/question/constants.ts @@ -771,6 +771,9 @@ export class CapabilityOptions { // custom copilot static customCopilotBasic(): OptionItem { + const description = featureFlagManager.getBooleanValue(FeatureFlags.CEAEnabled) + ? getLocalizedString("core.createProjectQuestion.capability.customEngineAgent.description") + : undefined; return { id: "custom-copilot-basic", label: getLocalizedString( @@ -779,13 +782,14 @@ export class CapabilityOptions { detail: getLocalizedString( "core.createProjectQuestion.capability.customCopilotBasicOption.detail" ), - description: getLocalizedString( - "core.createProjectQuestion.capability.customEngineAgent.description" - ), + description: description, }; } static customCopilotRag(): OptionItem { + const description = featureFlagManager.getBooleanValue(FeatureFlags.CEAEnabled) + ? getLocalizedString("core.createProjectQuestion.capability.customEngineAgent.description") + : undefined; return { id: "custom-copilot-rag", label: getLocalizedString( @@ -794,10 +798,14 @@ export class CapabilityOptions { detail: getLocalizedString( "core.createProjectQuestion.capability.customCopilotRagOption.detail" ), + description: description, }; } static customCopilotAssistant(): OptionItem { + const description = featureFlagManager.getBooleanValue(FeatureFlags.CEAEnabled) + ? getLocalizedString("core.createProjectQuestion.capability.customEngineAgent.description") + : undefined; return { id: "custom-copilot-agent", label: getLocalizedString( @@ -806,6 +814,7 @@ export class CapabilityOptions { detail: getLocalizedString( "core.createProjectQuestion.capability.customCopilotAssistantOption.detail" ), + description: description, }; } } @@ -939,11 +948,11 @@ interface HostTypeTriggerOptionItem extends OptionItem { export class NotificationTriggerOptions { static appService(): HostTypeTriggerOptionItem { return { - id: "http-restify", + id: "http-express", hostType: HostType.AppService, - label: getLocalizedString("plugins.bot.triggers.http-restify.label"), - description: getLocalizedString("plugins.bot.triggers.http-restify.description"), - detail: getLocalizedString("plugins.bot.triggers.http-restify.detail"), + label: getLocalizedString("plugins.bot.triggers.http-express.label"), + description: getLocalizedString("plugins.bot.triggers.http-express.description"), + detail: getLocalizedString("plugins.bot.triggers.http-express.detail"), }; } static appServiceForVS(): HostTypeTriggerOptionItem { diff --git a/packages/fx-core/src/question/inputs/CreateProjectInputs.ts b/packages/fx-core/src/question/inputs/CreateProjectInputs.ts index 5c7e494c2c..2b0d6fa830 100644 --- a/packages/fx-core/src/question/inputs/CreateProjectInputs.ts +++ b/packages/fx-core/src/question/inputs/CreateProjectInputs.ts @@ -42,7 +42,7 @@ export interface CreateProjectInputs extends Inputs { | "office-content-addin"; /** @description Select triggers */ "bot-host-type-trigger"?: - | "http-restify" + | "http-express" | "http-webapi" | "http-and-timer-functions" | "http-functions" diff --git a/packages/fx-core/src/question/options/CreateProjectOptions.ts b/packages/fx-core/src/question/options/CreateProjectOptions.ts index 3d56ccab0e..f6a4ca802b 100644 --- a/packages/fx-core/src/question/options/CreateProjectOptions.ts +++ b/packages/fx-core/src/question/options/CreateProjectOptions.ts @@ -58,9 +58,9 @@ export const CreateProjectOptions: CLICommandOption[] = [ type: "string", shortName: "t", description: "Specifies the trigger for `Chat Notification Message` app template.", - default: "http-restify", + default: "http-express", choices: [ - "http-restify", + "http-express", "http-webapi", "http-and-timer-functions", "http-functions", diff --git a/packages/fx-core/src/question/other.ts b/packages/fx-core/src/question/other.ts index cac14898f2..af271df663 100644 --- a/packages/fx-core/src/question/other.ts +++ b/packages/fx-core/src/question/other.ts @@ -758,14 +758,20 @@ export function addPluginQuestionNode(): IQTreeNode { }, { data: apiSpecLocationQuestion(), - condition: { - equals: ApiPluginStartOptions.apiSpec().id, + condition: (inputs: Inputs) => { + return ( + !featureFlagManager.getBooleanValue(FeatureFlags.KiotaIntegration) && + inputs[QuestionNames.ApiPluginType] === ApiPluginStartOptions.apiSpec().id + ); }, }, { data: apiOperationQuestion(true, true), - condition: { - equals: ApiPluginStartOptions.apiSpec().id, + condition: (inputs: Inputs) => { + return ( + !featureFlagManager.getBooleanValue(FeatureFlags.KiotaIntegration) && + inputs[QuestionNames.ApiPluginType] === ApiPluginStartOptions.apiSpec().id + ); }, }, { diff --git a/packages/fx-core/templates/plugins/resource/aad/auth/bot/README.md b/packages/fx-core/templates/plugins/resource/aad/auth/bot/README.md index c53d4d78e5..45e0101563 100644 --- a/packages/fx-core/templates/plugins/resource/aad/auth/bot/README.md +++ b/packages/fx-core/templates/plugins/resource/aad/auth/bot/README.md @@ -29,7 +29,7 @@ After you successfully added SSO into your project, Teams Toolkit will create an | Modify | `azureWebAppBotConfig.bicep` under `templates/azure/teamsFx` and `azure.parameters.dev.json` under `.fx/configs` | Insert environment variables used for bot web app to enable SSO feature | | Modify | `manifest.template.json` under `templates/appPackage` | An `webApplicationInfo` object will be added into your Teams app manifest template. This field is required by Teams when enabling SSO. | | Modify | `projectSettings.json` under `.fx/configs` | Add bot sso capability, which will be used internally by Teams Toolkit. | -| Create | `aad.template.json` under `templates/appPackage` | The Microsoft Entra application manifest that is used to register the application with Microsoft Entra. | +| Create | `aad.template.json` under `templates/appPackage` | The Microsoft Entra application manifest that is used to register the application with Microsoft Entra. | | Create | `auth/bot` | Reference code, redirect pages and a `README.md` file. These files are provided for reference. See below for more information. |

Update your code to Use SSO for Bot

@@ -41,17 +41,22 @@ As described above, the Teams Toolkit generated some configuration to set up you

Set up the Microsoft Entra redirects

1. Move the `auth/bot/public` folder to `bot/src`. This folder contains HTML pages that the bot application hosts. When single sign-on flows are initiated with Microsoft Entra, Microsoft Entra will redirect the user to these pages. -1. Modify your `bot/src/index` to add the appropriate `restify` routes to these pages. +1. Modify your `bot/src/index` to add the appropriate `express` routes to these pages. ```ts const path = require("path"); - - server.get( - "/auth-:name(start|end).html", - restify.plugins.serveStatic({ - directory: path.join(__dirname, "public"), - }) - ); + const send = require("send"); + + expressApp.get(["/auth-start.html", "/auth-end.html"], async (req, res) => { + send( + req, + path.join( + __dirname, + "public", + req.url.includes("auth-start.html") ? "auth-start.html" : "auth-end.html" + ) + ).pipe(res); + }); ```

Update your business logic

@@ -337,13 +342,14 @@ You can update the query logic in the `handleMessageExtensionQueryWithSSO` with To make this work in your application: 1. Move the `auth/bot/public` folder to `bot`. This folder contains HTML pages that the bot application hosts. When single sign-on flows are initiated with Microsoft Entra, Microsoft Entra will redirect the user to these pages. -1. Modify your `bot/index` to add the appropriate `restify` routes to these pages. +1. Modify your `bot/index` to add the appropriate `express` routes to these pages. ```ts const path = require("path"); + const send = require("send"); // Listen for incoming requests. - server.post("/api/messages", async (req, res) => { + expressApp.post("/api/messages", async (req, res) => { await adapter .process(req, res, async (context) => { await bot.run(context); @@ -356,12 +362,16 @@ To make this work in your application: }); }); - server.get( - "/auth-:name(start|end).html", - restify.plugins.serveStatic({ - directory: path.join(__dirname, "public"), - }) - ); + expressApp.get(["/auth-start.html", "/auth-end.html"], async (req, res) => { + send( + req, + path.join( + __dirname, + "public", + req.url.includes("auth-start.html") ? "auth-start.html" : "auth-end.html" + ) + ).pipe(res); + }); ``` 1. Override `handleTeamsMessagingExtensionQuery` interface under `bot/teamsBot`. You can follow the sample code in the `handleMessageExtensionQueryWithSSO` to do your own query logic. diff --git a/packages/fx-core/tests/client/tdpClient.test.ts b/packages/fx-core/tests/client/tdpClient.test.ts index 15a32326fe..55c4248842 100644 --- a/packages/fx-core/tests/client/tdpClient.test.ts +++ b/packages/fx-core/tests/client/tdpClient.test.ts @@ -40,6 +40,7 @@ import { Messages } from "../component/resource/botService/messages"; import { MockTools } from "../core/utils"; import { getDefaultString } from "../../src/common/localizeUtils"; import { HelpLinks } from "../../src/common/constants"; +import { expect } from "chai"; describe("TeamsDevPortalClient Test", () => { const tools = new MockTools(); @@ -854,7 +855,6 @@ describe("TeamsDevPortalClient Test", () => { chai.assert.include(error.message, xCorrelationId); } }); - it("API Failure", async () => { const fakeAxiosInstance = axios.create(); sandbox.stub(axios, "create").returns(fakeAxiosInstance); @@ -889,6 +889,93 @@ describe("TeamsDevPortalClient Test", () => { chai.assert.equal(error.name, DeveloperPortalAPIFailedSystemError.name); } }); + it("Bad Request", async () => { + const fakeAxiosInstance = axios.create(); + sandbox.stub(axios, "create").returns(fakeAxiosInstance); + + const xCorrelationId = "fakeCorrelationId"; + const postResponse = { + data: { + errorMessage: "BadRequest", + }, + message: "fake message", + headers: { + "x-correlation-id": xCorrelationId, + }, + }; + + sandbox.stub(fakeAxiosInstance, "post").resolves(postResponse); + + const getResponse = { + data: { + value: [ + { + appDefinitions: [ + { + publishingState: PublishingState.submitted, + teamsAppId: "xx", + displayName: "xx", + lastModifiedDateTime: null, + }, + ], + }, + ], + }, + }; + sandbox.stub(fakeAxiosInstance, "get").resolves(getResponse); + + try { + await teamsDevPortalClient.publishTeamsAppUpdate(token, "", Buffer.from("")); + } catch (error) { + chai.assert.include(error.message, xCorrelationId); + chai.assert.include(error.message, "BadRequest"); + } + }); + }); + + describe("wrapResponse", () => { + it("should return an error with e.message if it exists", () => { + const e = new Error("Error from e"); + const error = teamsDevPortalClient.wrapResponse(e, undefined); + expect(error.message).to.equal("Error from e"); + }); + + it("should return an error with e.message and response are missing", () => { + const e = new Error(""); + const error = teamsDevPortalClient.wrapResponse(e, undefined); + expect(error.message).to.equal(""); + }); + + it("should return an error with response.data.error.message if e.message is missing and response.data.error.message exists", () => { + const e = new Error(""); + const response = { + data: { error: { message: "Error from response.data.error" }, errorMessage: "" }, + } as any; + const error = teamsDevPortalClient.wrapResponse(e, response); + expect(error.message).to.equal("Error from response.data.error"); + expect(error.response).to.equal(response); + expect(error.request).to.equal(response.request); + }); + + it("should return an error with response.data.errorMessage if both e.message and response.data.error.message are missing", () => { + const e = new Error(""); + const response = { + data: { error: { message: "" }, errorMessage: "Error from response.data.errorMessage" }, + } as any; + const error = teamsDevPortalClient.wrapResponse(e, response); + expect(error.message).to.equal("Error from response.data.errorMessage"); + expect(error.response).to.equal(response); + expect(error.request).to.equal(response.request); + }); + + it("should return an error with empty message if all messages are missing", () => { + const e = new Error(""); + const response = { data: { error: { message: "" }, errorMessage: "" } } as any; + const error = teamsDevPortalClient.wrapResponse(e, response); + expect(error.message).to.equal(""); + expect(error.response).to.equal(response); + expect(error.request).to.equal(response.request); + }); }); describe("grantPermission", () => { diff --git a/packages/fx-core/tests/common/tools.test.ts b/packages/fx-core/tests/common/tools.test.ts index d8a9559c39..7ab110a5fb 100644 --- a/packages/fx-core/tests/common/tools.test.ts +++ b/packages/fx-core/tests/common/tools.test.ts @@ -12,7 +12,12 @@ import * as path from "path"; import Sinon, * as sinon from "sinon"; import { getProjectMetadata } from "../../src/common/projectSettingsHelper"; import * as telemetry from "../../src/common/telemetry"; -import { getSPFxToken, getSideloadingStatus, listDevTunnels } from "../../src/common/tools"; +import { + getSPFxToken, + getSideloadingStatus, + listAllTenants, + listDevTunnels, +} from "../../src/common/tools"; import { PackageService } from "../../src/component/m365/packageService"; import { isVideoFilterProject } from "../../src/core/middleware/videoFilterAppBlocker"; import { isUserCancelError } from "../../src/error/common"; @@ -124,6 +129,52 @@ describe("tools", () => { }); }); + describe("listAllTenants", () => { + const sandbox = sinon.createSandbox(); + + afterEach(() => { + sandbox.restore(); + }); + + it("returns empty for invalid token", async () => { + const tenants = await listAllTenants(""); + + chai.assert.equal(tenants.length, 0); + }); + + it("returns empty when API call failure", async () => { + sandbox.stub(axios, "get").throws({ name: 404, message: "failed" }); + + const tenants = await listAllTenants("faked token"); + + chai.assert.equal(tenants.length, 0); + }); + + it("returns tenant list", async () => { + const fakedTenants = { + data: { + value: [ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + countryCode: "SG", + displayName: "MSFT", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + countryCode: "CN", + displayName: "Cisco", + }, + ], + }, + }; + sandbox.stub(axios, "get").resolves(fakedTenants); + + const tenants = await listAllTenants("faked token"); + + chai.assert.equal(tenants, fakedTenants.data.value); + }); + }); + describe("getCopilotStatus", () => { let mockGet: () => AxiosResponse; let errors: number; diff --git a/packages/fx-core/tests/component/configManager/actionInjector.test.ts b/packages/fx-core/tests/component/configManager/actionInjector.test.ts new file mode 100644 index 0000000000..69d9547325 --- /dev/null +++ b/packages/fx-core/tests/component/configManager/actionInjector.test.ts @@ -0,0 +1,350 @@ +import { assert } from "chai"; +import sinon from "sinon"; +import fs from "fs-extra"; +import { Utils } from "@microsoft/m365-spec-parser"; +import { ActionInjector } from "../../../src/component/configManager/actionInjector"; +import { + InjectAPIKeyActionFailedError, + InjectOAuthActionFailedError, +} from "../../../src/error/common"; + +describe("ActionInjector", () => { + function countOccurrences(str: string, substring: string): number { + let count = 0; + let pos = str.indexOf(substring); + + while (pos !== -1) { + count++; + pos = str.indexOf(substring, pos + 1); + } + + return count; + } + describe("injectCreateOAuthAction", () => { + const sandbox = sinon.createSandbox(); + const sampleAuthAction = { + uses: "oauth/register", + with: { + name: "testAuth", + appId: "${{TEAMS_APP_ID}}", + apiSpecPath: "path/to/spec", + flow: "authorizationCode", + }, + writeToEnvironmentFile: { + configurationId: "TEST_AUTH_CONFIGURATION_ID", + }, + }; + let writeStub: sinon.SinonStub; + + beforeEach(() => { + writeStub = sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(ActionInjector, "generateAuthAction").returns(sampleAuthAction); + }); + afterEach(() => { + sandbox.restore(); + }); + + it("should inject OAuth action successfully if no existing env names for configuration id exists", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = false; + + const ymlContent = ` + provision: + - uses: teamsApp/create + with: + # Teams app name + name: test + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + teamsAppId: TEAMS_APP_ID + - uses: apiKey/register + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + sandbox.stub(Utils, "getSafeRegistrationIdEnvName").returns("TEST_AUTH_CONFIGURATION_ID"); + sandbox.stub(ActionInjector, "getTeamsAppIdEnvName").returns("TEAMS_APP_ID"); + + const result = await ActionInjector.injectCreateOAuthAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + + assert.deepEqual(result, { + defaultRegistrationIdEnvName: "TEST_AUTH_CONFIGURATION_ID", + registrationIdEnvName: "TEST_AUTH_CONFIGURATION_ID", + }); + assert.isTrue(writeStub.args[0][1].includes("oauth/register")); + assert.isFalse(writeStub.args[0][1].includes("apiKey/register")); + }); + + it("should throw InjectOAuthActionFailedError if provision node is missing", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = false; + + const ymlContent = ` + otherNode: + - uses: teamsApp/create + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + + try { + await ActionInjector.injectCreateOAuthAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + assert.fail("Expected InjectOAuthActionFailedError to be thrown"); + } catch (error) { + assert.instanceOf(error, InjectOAuthActionFailedError); + } + }); + + it("should throw InjectOAuthActionFailedError if teamsApp/create action is missing", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = false; + + const ymlContent = ` + provision: + - uses: otherAction + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + sandbox.stub(ActionInjector, "hasActionWithName").returns(false); + sandbox.stub(ActionInjector, "getTeamsAppIdEnvName").returns(undefined); + + try { + await ActionInjector.injectCreateOAuthAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + assert.fail("Expected InjectOAuthActionFailedError to be thrown"); + } catch (error) { + assert.instanceOf(error, InjectOAuthActionFailedError); + } + }); + + it("should handle existing OAuth action if env names for configuration id exists", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = true; + + const ymlContent = ` + provision: + - uses: teamsApp/create + with: + # Teams app name + name: test + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + teamsAppId: TEAMS_APP_ID + - uses: oauth/register + with: + name: oAuth2AuthCode + appId: appId + apiSpecPath: ./appPackage/apiSpecificationFile/openapi_3.yaml + flow: authorizationCode + writeToEnvironmentFile: + configurationId: OAUTH2AUTHCODE_CONFIGURATION_ID + - uses: apiKey/register + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + sandbox + .stub(Utils, "getSafeRegistrationIdEnvName") + .returns("OAUTH2AUTHCODE_CONFIGURATION_ID"); + sandbox.stub(ActionInjector, "getTeamsAppIdEnvName").returns("TEAMS_APP_ID"); + + const result = await ActionInjector.injectCreateOAuthAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + + assert.deepEqual(result, { + defaultRegistrationIdEnvName: "OAUTH2AUTHCODE_CONFIGURATION_ID", + registrationIdEnvName: "OAUTH2AUTHCODE_CONFIGURATION_ID1", + }); + assert.isTrue(writeStub.args[0][1].includes("apiKey/register")); + + assert.equal(countOccurrences(writeStub.args[0][1], "oauth/register"), 2); + }); + }); + + describe("injectCreateAPIKeyAction", () => { + const sandbox = sinon.createSandbox(); + const sampleAPIKeyAction = { + uses: "apiKey/register", + with: { + name: "testAuth", + appId: "${{TEAMS_APP_ID}}", + apiSpecPath: "path/to/spec", + }, + writeToEnvironmentFile: { + registrationId: "TEST_AUTH_CONFIGURATION_ID", + }, + }; + let writeStub: sinon.SinonStub; + + beforeEach(() => { + writeStub = sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(ActionInjector, "generateAuthAction").returns(sampleAPIKeyAction); + }); + + afterEach(() => { + sandbox.restore(); + }); + + it("should inject APIKey action successfully if no existing env names for configuration id exists", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = false; + + const ymlContent = ` + provision: + - uses: teamsApp/create + with: + # Teams app name + name: test + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + teamsAppId: TEAMS_APP_ID + - uses: oauth/register + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + sandbox.stub(ActionInjector, "hasActionWithName").returns(false); + sandbox.stub(Utils, "getSafeRegistrationIdEnvName").returns("TEST_AUTH_CONFIGURATION_ID"); + sandbox.stub(ActionInjector, "getTeamsAppIdEnvName").returns("TEAMS_APP_ID"); + + const result = await ActionInjector.injectCreateAPIKeyAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + + assert.deepEqual(result, { + defaultRegistrationIdEnvName: "TEST_AUTH_CONFIGURATION_ID", + registrationIdEnvName: "TEST_AUTH_CONFIGURATION_ID", + }); + assert.isFalse(writeStub.args[0][1].includes("oauth/register")); + assert.isTrue(writeStub.args[0][1].includes("apiKey/register")); + }); + + it("should throw InjectAPIKeyActionFailedError if provision node is missing", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = false; + + const ymlContent = ` + otherNode: + - uses: teamsApp/create + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + + try { + await ActionInjector.injectCreateAPIKeyAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + assert.fail("Expected InjectAPIKeyActionFailedError to be thrown"); + } catch (error) { + assert.instanceOf(error, InjectAPIKeyActionFailedError); + } + }); + + it("should throw InjectAPIKeyActionFailedError if teamsApp/create action is missing", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = false; + + const ymlContent = ` + provision: + - uses: otherAction + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + sandbox.stub(ActionInjector, "hasActionWithName").returns(false); + sandbox.stub(ActionInjector, "getTeamsAppIdEnvName").returns(undefined); + + try { + await ActionInjector.injectCreateAPIKeyAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + assert.fail("Expected InjectAPIKeyActionFailedError to be thrown"); + } catch (error) { + assert.instanceOf(error, InjectAPIKeyActionFailedError); + } + }); + + it("should handle existing OAuth action if env names for configuration id exists", async () => { + const ymlPath = "path/to/yml"; + const authName = "testAuth"; + const specRelativePath = "path/to/spec"; + const forceToAddNew = true; + + const ymlContent = ` + provision: + - uses: teamsApp/create + with: + # Teams app name + name: test + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + teamsAppId: TEAMS_APP_ID + - uses: apiKey/register + with: + name: bearerAuth + appId: appId + apiSpecPath: ./appPackage/apiSpecificationFile/openapi_1.yaml + writeToEnvironmentFile: + registrationId: BEARERAUTH_REGISTRATION_ID + `; + + sandbox.stub(fs, "readFile").resolves(ymlContent as any); + sandbox.stub(Utils, "getSafeRegistrationIdEnvName").returns("BEARERAUTH_REGISTRATION_ID"); + sandbox.stub(ActionInjector, "getTeamsAppIdEnvName").returns("TEAMS_APP_ID"); + + const result = await ActionInjector.injectCreateAPIKeyAction( + ymlPath, + authName, + specRelativePath, + forceToAddNew + ); + + assert.deepEqual(result, { + defaultRegistrationIdEnvName: "BEARERAUTH_REGISTRATION_ID", + registrationIdEnvName: "BEARERAUTH_REGISTRATION_ID1", + }); + + assert.equal(countOccurrences(writeStub.args[0][1], "apiKey/register"), 2); + }); + }); +}); diff --git a/packages/fx-core/tests/component/configManager/lifecycle.test.ts b/packages/fx-core/tests/component/configManager/lifecycle.test.ts index c3a57634fe..f2c889fe58 100644 --- a/packages/fx-core/tests/component/configManager/lifecycle.test.ts +++ b/packages/fx-core/tests/component/configManager/lifecycle.test.ts @@ -13,9 +13,7 @@ import { Lifecycle } from "../../../src/component/configManager/lifecycle"; import Container from "typedi"; import { DriverDefinition } from "../../../src/component/configManager/interface"; import { - MockedAzureAccountProvider, MockedLogProvider, - MockedM365Provider, MockedTelemetryReporter, MockedUserInteraction, } from "../../plugins/solution/util"; @@ -31,6 +29,7 @@ import { } from "@microsoft/teamsfx-api"; import { ExecutionResult, StepDriver } from "../../../src/component/driver/interface/stepDriver"; import { SummaryConstant } from "../../../src/component/configManager/constant"; +import { MockedAzureAccountProvider, MockedM365Provider } from "../../core/utils"; const mockedDriverContext: DriverContext = { m365TokenProvider: new MockedM365Provider(), diff --git a/packages/fx-core/tests/component/coordinator/coordinator.test.ts b/packages/fx-core/tests/component/coordinator/coordinator.test.ts index 380c376d91..83054ed4c5 100644 --- a/packages/fx-core/tests/component/coordinator/coordinator.test.ts +++ b/packages/fx-core/tests/component/coordinator/coordinator.test.ts @@ -42,7 +42,7 @@ import { FxCore } from "../../../src/core/FxCore"; import * as v3MigrationUtils from "../../../src/core/middleware/utils/v3MigrationUtils"; import { MissingEnvironmentVariablesError } from "../../../src/error/common"; import { QuestionNames } from "../../../src/question"; -import { MockAzureAccountProvider, MockM365TokenProvider, MockTools } from "../../core/utils"; +import { MockedAzureAccountProvider, MockedM365Provider, MockTools } from "../../core/utils"; export function mockedResolveDriverInstances(log: LogProvider): Result { return ok([ @@ -425,8 +425,8 @@ describe("component coordinator test", () => { it("missing appPackagePath", async () => { const context = createContext(); context.tokenProvider = { - m365TokenProvider: new MockM365TokenProvider(), - azureAccountProvider: new MockAzureAccountProvider(), + m365TokenProvider: new MockedM365Provider(), + azureAccountProvider: new MockedAzureAccountProvider(), }; const inputs: InputsWithProjectPath = { platform: Platform.VSCode, @@ -439,8 +439,8 @@ describe("component coordinator test", () => { it("success", async () => { const context = createContext(); context.tokenProvider = { - m365TokenProvider: new MockM365TokenProvider(), - azureAccountProvider: new MockAzureAccountProvider(), + m365TokenProvider: new MockedM365Provider(), + azureAccountProvider: new MockedAzureAccountProvider(), }; sandbox .stub(context.tokenProvider.m365TokenProvider, "getJsonObject") @@ -461,8 +461,8 @@ describe("component coordinator test", () => { it("update manifest error", async () => { const context = createContext(); context.tokenProvider = { - m365TokenProvider: new MockM365TokenProvider(), - azureAccountProvider: new MockAzureAccountProvider(), + m365TokenProvider: new MockedM365Provider(), + azureAccountProvider: new MockedAzureAccountProvider(), }; sandbox .stub(appStudio, "updateTeamsAppV3ForPublish") diff --git a/packages/fx-core/tests/component/deps-checker/cases/funcTool.it.ts b/packages/fx-core/tests/component/deps-checker/cases/funcTool.it.ts index 382696f7cf..38b3eab8cb 100644 --- a/packages/fx-core/tests/component/deps-checker/cases/funcTool.it.ts +++ b/packages/fx-core/tests/component/deps-checker/cases/funcTool.it.ts @@ -130,8 +130,8 @@ describe("FuncToolChecker E2E Test", async () => { expect(depsInfo.command).to.be.equal("func"); expect(depsInfo.details.binFolders).to.be.equal(undefined); expect(depsInfo.error?.message).to.contains( - "Unable to find Azure Functions Core Tools.", - `Expect error message contains 'Unable to find Azure Functions Core Tools.'. Actual error message: ${depsInfo.error?.message}` + "Unable to install https://aka.ms/teamsfx-actions/devtool-install.", + `Expect error message contains 'Unable to install https://aka.ms/teamsfx-actions/devtool-install.'. Actual error message: ${depsInfo.error?.message}` ); }); diff --git a/packages/fx-core/tests/component/deps-checker/cases/node.it.ts b/packages/fx-core/tests/component/deps-checker/cases/node.it.ts index 1b74cb3341..8e82d57ddb 100644 --- a/packages/fx-core/tests/component/deps-checker/cases/node.it.ts +++ b/packages/fx-core/tests/component/deps-checker/cases/node.it.ts @@ -15,7 +15,7 @@ import { import { TestLogger } from "../adapters/testLogger"; import { TestTelemetry } from "../adapters/testTelemetry"; -const ltsNodeRange = "16 || 18"; +const ltsNodeRange = "16 || 18 || 20"; describe("NodeChecker E2E Test", async () => { let baseFolder: string | undefined = undefined; diff --git a/packages/fx-core/tests/component/developerPortalScaffoldUtils.test.ts b/packages/fx-core/tests/component/developerPortalScaffoldUtils.test.ts index 0ef6174744..55849b414a 100644 --- a/packages/fx-core/tests/component/developerPortalScaffoldUtils.test.ts +++ b/packages/fx-core/tests/component/developerPortalScaffoldUtils.test.ts @@ -30,8 +30,7 @@ import { CommandScope, MeetingsContext } from "../../src/component/driver/teamsA import { DotenvOutput, envUtil } from "../../src/component/utils/envUtil"; import { CapabilityOptions, QuestionNames } from "../../src/question/constants"; import { getProjectTypeAndCapability } from "../../src/question/create"; -import { MockTools } from "../core/utils"; -import { MockedAzureAccountProvider, MockedM365Provider } from "../plugins/solution/util"; +import { MockedAzureAccountProvider, MockedM365Provider, MockTools } from "../core/utils"; import { InputValidationError } from "../../src/error"; describe("developPortalScaffoldUtils", () => { diff --git a/packages/fx-core/tests/component/driver/aad/aadAppClient.test.ts b/packages/fx-core/tests/component/driver/aad/aadAppClient.test.ts index 9cde0568c3..2d61359930 100644 --- a/packages/fx-core/tests/component/driver/aad/aadAppClient.test.ts +++ b/packages/fx-core/tests/component/driver/aad/aadAppClient.test.ts @@ -7,7 +7,7 @@ import { AadAppClient } from "../../../../src/component/driver/aad/utility/aadAp import chai from "chai"; import chaiAsPromised from "chai-as-promised"; import axios, { AxiosInstance, isAxiosError } from "axios"; -import { MockedLogProvider, MockedM365Provider } from "../../../plugins/solution/util"; +import { MockedLogProvider } from "../../../plugins/solution/util"; import axiosRetry from "axios-retry"; import MockAdapter from "axios-mock-adapter"; import { SystemError, err } from "@microsoft/teamsfx-api"; @@ -19,6 +19,7 @@ import { } from "../../../../src/component/driver/aad/error/aadManifestError"; import { CredentialInvalidLifetimeError } from "../../../../src/component/driver/aad/error/credentialInvalidLifetimeError"; import { ClientSecretNotAllowedError } from "../../../../src/component/driver/aad/error/clientSecretNotAllowedError"; +import { MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/driver/aad/create.test.ts b/packages/fx-core/tests/component/driver/aad/create.test.ts index 82e79eb814..ae4e1c5a4b 100644 --- a/packages/fx-core/tests/component/driver/aad/create.test.ts +++ b/packages/fx-core/tests/component/driver/aad/create.test.ts @@ -5,11 +5,7 @@ import "mocha"; import * as sinon from "sinon"; import mockedEnv, { RestoreFn } from "mocked-env"; import { CreateAadAppDriver } from "../../../../src/component/driver/aad/create"; -import { - MockedM365Provider, - MockedTelemetryReporter, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedTelemetryReporter, MockedUserInteraction } from "../../../plugins/solution/util"; import * as chai from "chai"; import chaiAsPromised from "chai-as-promised"; import { AadAppClient } from "../../../../src/component/driver/aad/utility/aadAppClient"; @@ -25,6 +21,7 @@ import { OutputEnvironmentVariableUndefinedError } from "../../../../src/compone import { AadAppNameTooLongError } from "../../../../src/component/driver/aad/error/aadAppNameTooLongError"; import { SignInAudience } from "../../../../src/component/driver/aad/interface/signInAudience"; import { MissingServiceManagementReferenceError } from "../../../../src/component/driver/aad/error/missingServiceManagamentReferenceError"; +import { MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/driver/aad/update.test.ts b/packages/fx-core/tests/component/driver/aad/update.test.ts index 0ef0153a0c..31fb0ef45b 100644 --- a/packages/fx-core/tests/component/driver/aad/update.test.ts +++ b/packages/fx-core/tests/component/driver/aad/update.test.ts @@ -9,7 +9,6 @@ import chaiAsPromised from "chai-as-promised"; import { UpdateAadAppDriver } from "../../../../src/component/driver/aad/update"; import { MockedLogProvider, - MockedM365Provider, MockedTelemetryReporter, MockedUserInteraction, } from "../../../plugins/solution/util"; @@ -28,6 +27,7 @@ import { UnhandledError, } from "../../../../src/error/common"; import { Platform, ok, err } from "@microsoft/teamsfx-api"; +import { MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/driver/add/AddWebpart.test.ts b/packages/fx-core/tests/component/driver/add/AddWebpart.test.ts index b102d3fdf9..98fa6685d5 100644 --- a/packages/fx-core/tests/component/driver/add/AddWebpart.test.ts +++ b/packages/fx-core/tests/component/driver/add/AddWebpart.test.ts @@ -9,12 +9,7 @@ import sinon from "sinon"; import * as path from "path"; import * as uuid from "uuid"; -import { - MockedAzureAccountProvider, - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; import { AddWebPartDriver } from "../../../../src/component/driver/add/addWebPart"; import { AddWebPartArgs } from "../../../../src/component/driver/add/interface/AddWebPartArgs"; import { Constants } from "../../../../src/component/driver/add/utility/constants"; @@ -24,6 +19,7 @@ import { ManifestUtils } from "../../../../src/component/driver/teamsApp/utils/M import { AppStudioResultFactory } from "../../../../src/component/driver/teamsApp/results"; import { setTools } from "../../../../src/common/globalVars"; import { InstallSoftwareError } from "../../../../src/error/common"; +import { MockedAzureAccountProvider, MockedM365Provider } from "../../../core/utils"; describe("Add web part driver", async () => { const args: AddWebPartArgs = { diff --git a/packages/fx-core/tests/component/driver/apiKey/create.test.ts b/packages/fx-core/tests/component/driver/apiKey/create.test.ts index 93ac86b154..e0a0b38a32 100644 --- a/packages/fx-core/tests/component/driver/apiKey/create.test.ts +++ b/packages/fx-core/tests/component/driver/apiKey/create.test.ts @@ -17,12 +17,8 @@ import { } from "../../../../src/component/driver/teamsApp/interfaces/ApiSecretRegistration"; import { UserCancelError } from "../../../../src/error"; import * as visitor from "../../../../src/ui/visitor"; -import { - MockedAzureAccountProvider, - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; +import { MockedAzureAccountProvider, MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; @@ -522,7 +518,7 @@ describe("CreateApiKeyDriver", () => { const result = await createApiKeyDriver.execute(args, mockedDriverContext, outputEnvVarNames); expect(result.result.isErr()).to.be.true; if (result.result.isErr()) { - expect(result.result.error.name).to.equal("ApiKeyFailedToGetDomain"); + expect(result.result.error.name).to.equal("ApiKeyAuthMissingInSpec"); } }); @@ -549,7 +545,7 @@ describe("CreateApiKeyDriver", () => { const result = await createApiKeyDriver.execute(args, mockedDriverContext, outputEnvVarNames); expect(result.result.isErr()).to.be.true; if (result.result.isErr()) { - expect(result.result.error.name).to.equal("ApiKeyFailedToGetDomain"); + expect(result.result.error.name).to.equal("ApiKeyAuthMissingInSpec"); } }); @@ -611,6 +607,69 @@ describe("CreateApiKeyDriver", () => { }); const result = await createApiKeyDriver.execute(args, mockedDriverContext, outputEnvVarNames); expect(result.result.isErr()).to.be.true; + if (result.result.isErr()) { + expect(result.result.error.name).to.equal("ApiKeyAuthMissingInSpec"); + } + }); + + it("should throw error if list api contains auth but server info is null", async () => { + const args: any = { + name: "test", + appId: "mockedAppId", + primaryClientSecret: "mockedSecret", + apiSpecPath: "mockedPath", + }; + sinon.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "api1", + server: "https://test", + operationId: "get1", + auth: { + name: "test1", + authScheme: { + type: "http", + scheme: "bearer", + }, + }, + isValid: true, + reason: [], + }, + { + api: "api2", + server: "", + operationId: "get2", + auth: { + name: "test", + authScheme: { + type: "http", + scheme: "bearer", + }, + }, + isValid: true, + reason: [], + }, + { + api: "api3", + server: "https://test", + operationId: "get3", + auth: { + name: "test1", + authScheme: { + type: "apiKey", + in: "header", + name: "test1", + }, + }, + isValid: true, + reason: [], + }, + ], + validAPICount: 3, + allAPICount: 3, + }); + const result = await createApiKeyDriver.execute(args, mockedDriverContext, outputEnvVarNames); + expect(result.result.isErr()).to.be.true; if (result.result.isErr()) { expect(result.result.error.name).to.equal("ApiKeyFailedToGetDomain"); } diff --git a/packages/fx-core/tests/component/driver/apiKey/update.test.ts b/packages/fx-core/tests/component/driver/apiKey/update.test.ts index 916ccd8e9b..eb0e1c9dd8 100644 --- a/packages/fx-core/tests/component/driver/apiKey/update.test.ts +++ b/packages/fx-core/tests/component/driver/apiKey/update.test.ts @@ -16,12 +16,8 @@ import { ApiSecretRegistrationAppType, ApiSecretRegistrationTargetAudience, } from "../../../../src/component/driver/teamsApp/interfaces/ApiSecretRegistration"; -import { - MockedAzureAccountProvider, - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; +import { MockedAzureAccountProvider, MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/driver/arm/deploy.test.ts b/packages/fx-core/tests/component/driver/arm/deploy.test.ts index acc7dff04f..ceac406cc0 100644 --- a/packages/fx-core/tests/component/driver/arm/deploy.test.ts +++ b/packages/fx-core/tests/component/driver/arm/deploy.test.ts @@ -6,13 +6,13 @@ import "mocha"; import { createSandbox } from "sinon"; import { setTools } from "../../../../src/common/globalVars"; import { - MockAzureAccountProvider, + MockedAzureAccountProvider, + MockedM365Provider, MockLogProvider, MockTelemetryReporter, MockTools, MockUserInteraction, } from "../../../core/utils"; -import { MockedM365Provider } from "../../../plugins/solution/util"; import { ArmDeployDriver } from "../../../../src/component/driver/arm/deploy"; import fs from "fs-extra"; import { ArmDeployImpl } from "../../../../src/component/driver/arm/deployImpl"; @@ -27,7 +27,7 @@ describe("Arm driver deploy", () => { setTools(tools); const mockedDriverContext: any = { m365TokenProvider: new MockedM365Provider(), - azureAccountProvider: new MockAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), telemetryReporter: new MockTelemetryReporter(), ui: new MockUserInteraction(), logProvider: new MockLogProvider(), diff --git a/packages/fx-core/tests/component/driver/arm/utils.test.ts b/packages/fx-core/tests/component/driver/arm/utils.test.ts index ae30214b13..79adbacac5 100644 --- a/packages/fx-core/tests/component/driver/arm/utils.test.ts +++ b/packages/fx-core/tests/component/driver/arm/utils.test.ts @@ -6,13 +6,14 @@ import "mocha"; import { createSandbox } from "sinon"; import { setTools } from "../../../../src/common/globalVars"; import { - MockAzureAccountProvider, + MockedAzureAccountProvider, + MockedM365Provider, MockLogProvider, MockTelemetryReporter, MockTools, MockUserInteraction, + MyTokenCredential, } from "../../../core/utils"; -import { MockedM365Provider, MyTokenCredential } from "../../../plugins/solution/util"; import { ArmDeployImpl } from "../../../../src/component/driver/arm/deployImpl"; import { ok } from "@microsoft/teamsfx-api"; import { getAbsolutePath, getEnvironmentVariables } from "../../../../src/component/utils/common"; @@ -104,7 +105,7 @@ describe("arm deploy error handle test", () => { setTools(tools); const mockedDriverContext: any = { m365TokenProvider: new MockedM365Provider(), - azureAccountProvider: new MockAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), telemetryReporter: new MockTelemetryReporter(), ui: new MockUserInteraction(), logProvider: new MockLogProvider(), diff --git a/packages/fx-core/tests/component/driver/botAadApp/create.test.ts b/packages/fx-core/tests/component/driver/botAadApp/create.test.ts index 028be18e98..3a490d8411 100644 --- a/packages/fx-core/tests/component/driver/botAadApp/create.test.ts +++ b/packages/fx-core/tests/component/driver/botAadApp/create.test.ts @@ -5,11 +5,7 @@ import "mocha"; import * as sinon from "sinon"; import mockedEnv, { RestoreFn } from "mocked-env"; import { CreateBotAadAppDriver } from "../../../../src/component/driver/botAadApp/create"; -import { - MockedLogProvider, - MockedM365Provider, - MockedTelemetryReporter, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedTelemetryReporter } from "../../../plugins/solution/util"; import * as chai from "chai"; import chaiAsPromised from "chai-as-promised"; import { err, ok, UserError } from "@microsoft/teamsfx-api"; @@ -25,6 +21,7 @@ import { AADApplication } from "../../../../src/component/driver/aad/interface/A import { OutputEnvironmentVariableUndefinedError } from "../../../../src/component/driver/error/outputEnvironmentVariableUndefinedError"; import { AadAppNameTooLongError } from "../../../../src/component/driver/aad/error/aadAppNameTooLongError"; import { MissingServiceManagementReferenceError } from "../../../../src/component/driver/aad/error/missingServiceManagamentReferenceError"; +import { MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/driver/botFramework/createOrUpdateBot.test.ts b/packages/fx-core/tests/component/driver/botFramework/createOrUpdateBot.test.ts index 8c9aa8ae1a..5f3276b9f0 100644 --- a/packages/fx-core/tests/component/driver/botFramework/createOrUpdateBot.test.ts +++ b/packages/fx-core/tests/component/driver/botFramework/createOrUpdateBot.test.ts @@ -10,7 +10,8 @@ import * as localizeUtils from "../../../../src/common/localizeUtils"; import { CreateOrUpdateBotFrameworkBotDriver } from "../../../../src/component/driver/botFramework/createOrUpdateBot"; import { IBotRegistration } from "../../../../src/component/resource/botService/appStudio/interfaces/IBotRegistration"; import { InvalidActionInputError, UnhandledError } from "../../../../src/error/common"; -import { MockedLogProvider, MockedM365Provider } from "../../../plugins/solution/util"; +import { MockedLogProvider } from "../../../plugins/solution/util"; +import { MockedM365Provider } from "../../../core/utils"; describe("CreateOrUpdateM365BotDriver", () => { const mockedDriverContext: any = { diff --git a/packages/fx-core/tests/component/driver/deploy/azure/AzureDeployImpl.test.ts b/packages/fx-core/tests/component/driver/deploy/azure/AzureDeployImpl.test.ts index e085e2d1e0..1ccdf9f363 100644 --- a/packages/fx-core/tests/component/driver/deploy/azure/AzureDeployImpl.test.ts +++ b/packages/fx-core/tests/component/driver/deploy/azure/AzureDeployImpl.test.ts @@ -6,9 +6,13 @@ import "mocha"; import { DeployArgs } from "../../../../../src/component/driver/interface/buildAndDeployArgs"; -import { TestAzureAccountProvider } from "../../../util/azureAccountMock"; import { TestLogProvider } from "../../../util/logProviderMock"; -import { MockTelemetryReporter, MockUserInteraction } from "../../../../core/utils"; +import { + MockedAzureAccountProvider, + MockTelemetryReporter, + MockUserInteraction, + MyTokenCredential, +} from "../../../../core/utils"; import { AzureZipDeployImpl } from "../../../../../src/component/driver/deploy/azure/impl/AzureZipDeployImpl"; import * as tools from "../../../../../src/common/utils"; import * as sinon from "sinon"; @@ -20,7 +24,6 @@ import { GetPublishingCredentialsError, } from "../../../../../src/error/deploy"; import * as chai from "chai"; -import { MyTokenCredential } from "../../../../plugins/solution/util"; import chaiAsPromised = require("chai-as-promised"); chai.use(chaiAsPromised); import * as appService from "@azure/arm-appservice"; @@ -64,7 +67,7 @@ describe("AzureDeployImpl zip deploy acceleration", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: new MockUserInteraction(), } as any; @@ -341,7 +344,7 @@ describe("AzureDeployImpl zip deploy acceleration", () => { resourceGroupName: string, name: string ): Promise { - throw new RestError("test message", "111", 500); + throw new RestError("test message", { statusCode: 500 }); }, }; const mockWebSiteManagementClient = new WebSiteManagementClient(new MyTokenCredential(), "sub"); @@ -545,7 +548,7 @@ describe("AzureDeployImpl zip deploy acceleration", () => { resourceGroupName: string, name: string ): Promise { - throw new RestError("test message", "111", 500); + throw new RestError("test message", { statusCode: 500 }); }, }; const mockWebSiteManagementClient = new WebSiteManagementClient(new MyTokenCredential(), "sub"); diff --git a/packages/fx-core/tests/component/driver/deploy/azure/azureAppServiceDeployDriver.test.ts b/packages/fx-core/tests/component/driver/deploy/azure/azureAppServiceDeployDriver.test.ts index 1eb1a2d4bb..e7f14d02f9 100644 --- a/packages/fx-core/tests/component/driver/deploy/azure/azureAppServiceDeployDriver.test.ts +++ b/packages/fx-core/tests/component/driver/deploy/azure/azureAppServiceDeployDriver.test.ts @@ -8,7 +8,6 @@ import "mocha"; import * as sinon from "sinon"; import * as tools from "../../../../../src/common/utils"; import { DeployArgs } from "../../../../../src/component/driver/interface/buildAndDeployArgs"; -import { TestAzureAccountProvider } from "../../../util/azureAccountMock"; import { TestLogProvider } from "../../../util/logProviderMock"; import * as appService from "@azure/arm-appservice"; import * as Models from "@azure/arm-appservice/src/models"; @@ -18,8 +17,12 @@ import { expect, assert } from "chai"; import fs from "fs-extra"; import { AzureAppServiceDeployDriver } from "../../../../../src/component/driver/deploy/azure/azureAppServiceDeployDriver"; import { DeployConstant } from "../../../../../src/component/constant/deployConstant"; -import { MyTokenCredential } from "../../../../plugins/solution/util"; -import { MockTelemetryReporter, MockUserInteraction } from "../../../../core/utils"; +import { + MockedAzureAccountProvider, + MockTelemetryReporter, + MockUserInteraction, + MyTokenCredential, +} from "../../../../core/utils"; import * as os from "os"; import * as path from "path"; import * as uuid from "uuid"; @@ -95,7 +98,7 @@ describe("Azure App Service Deploy Driver test", () => { const progressNextCaller = sandbox.stub(progressHandler, "next").resolves(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: ui, telemetryReporter: new MockTelemetryReporter(), @@ -171,7 +174,7 @@ describe("Azure App Service Deploy Driver test", () => { const progressNextCaller = sandbox.stub(progressHandler, "next").resolves(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: ui, telemetryReporter: new MockTelemetryReporter(), @@ -250,7 +253,7 @@ describe("Azure App Service Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), telemetryReporter: new MockTelemetryReporter(), } as any; @@ -297,7 +300,7 @@ describe("Azure App Service Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; sandbox @@ -339,7 +342,7 @@ describe("Azure App Service Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; sandbox @@ -386,7 +389,7 @@ describe("Azure App Service Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; sandbox @@ -433,7 +436,7 @@ describe("Azure App Service Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; const res = await deploy.execute(args, context); @@ -466,7 +469,7 @@ describe("Azure App Service Deploy Driver test", () => { const progressNextCaller = sandbox.stub(progressHandler, "next").resolves(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: ui, progressBar: progressHandler, @@ -529,7 +532,7 @@ describe("Azure App Service Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: new MockUserInteraction(), } as any; diff --git a/packages/fx-core/tests/component/driver/deploy/azure/azureFunctionDeployDriver.test.ts b/packages/fx-core/tests/component/driver/deploy/azure/azureFunctionDeployDriver.test.ts index 350632338b..b77f4aa676 100644 --- a/packages/fx-core/tests/component/driver/deploy/azure/azureFunctionDeployDriver.test.ts +++ b/packages/fx-core/tests/component/driver/deploy/azure/azureFunctionDeployDriver.test.ts @@ -8,7 +8,6 @@ import "mocha"; import * as sinon from "sinon"; import * as tools from "../../../../../src/common/utils"; import { DeployArgs } from "../../../../../src/component/driver/interface/buildAndDeployArgs"; -import { TestAzureAccountProvider } from "../../../util/azureAccountMock"; import { TestLogProvider } from "../../../util/logProviderMock"; import * as appService from "@azure/arm-appservice"; import * as Models from "@azure/arm-appservice/src/models"; @@ -17,8 +16,12 @@ import { AzureDeployImpl } from "../../../../../src/component/driver/deploy/azur import { assert, expect } from "chai"; import fs from "fs-extra"; import { AzureFunctionDeployDriver } from "../../../../../src/component/driver/deploy/azure/azureFunctionDeployDriver"; -import { MyTokenCredential } from "../../../../plugins/solution/util"; -import { MockTelemetryReporter, MockUserInteraction } from "../../../../core/utils"; +import { + MockedAzureAccountProvider, + MockTelemetryReporter, + MockUserInteraction, + MyTokenCredential, +} from "../../../../core/utils"; import * as os from "os"; import * as uuid from "uuid"; import * as path from "path"; @@ -72,7 +75,7 @@ describe("Azure Function Deploy Driver test", () => { zipFilePath: path.join(testFolder, "test.zip"), } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), telemetryReporter: new MockTelemetryReporter(), @@ -121,7 +124,7 @@ describe("Azure Function Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), telemetryReporter: new MockTelemetryReporter(), } as any; @@ -171,7 +174,7 @@ describe("Azure Function Deploy Driver test", () => { const logger = new TestLogProvider(); const caller = sandbox.stub(logger, "warning").resolves(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: logger, telemetryReporter: new MockTelemetryReporter(), } as any; @@ -221,7 +224,7 @@ describe("Azure Function Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; sandbox @@ -268,7 +271,7 @@ describe("Azure Function Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; sandbox @@ -315,7 +318,7 @@ describe("Azure Function Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), telemetryReporter: new MockTelemetryReporter(), } as any; @@ -364,7 +367,7 @@ describe("Azure Function Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Web/sites/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; sandbox @@ -413,7 +416,7 @@ describe("Azure Function Deploy Driver test", () => { dryRun: true, } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; diff --git a/packages/fx-core/tests/component/driver/deploy/azure/azureStorageDeployDriver.test.ts b/packages/fx-core/tests/component/driver/deploy/azure/azureStorageDeployDriver.test.ts index 70b6a38562..6bd33f5af8 100644 --- a/packages/fx-core/tests/component/driver/deploy/azure/azureStorageDeployDriver.test.ts +++ b/packages/fx-core/tests/component/driver/deploy/azure/azureStorageDeployDriver.test.ts @@ -9,7 +9,6 @@ import * as sinon from "sinon"; import * as tools from "../../../../../src/common/utils"; import { AzureStorageDeployDriver } from "../../../../../src/component/driver/deploy/azure/azureStorageDeployDriver"; import { DeployArgs } from "../../../../../src/component/driver/interface/buildAndDeployArgs"; -import { TestAzureAccountProvider } from "../../../util/azureAccountMock"; import { TestLogProvider } from "../../../util/logProviderMock"; import { assert } from "chai"; import { @@ -23,9 +22,12 @@ import { BlockBlobParallelUploadOptions, ContainerClient, } from "@azure/storage-blob"; -import { MyTokenCredential } from "../../../../plugins/solution/util"; import * as armStorage from "@azure/arm-storage"; -import { MockUserInteraction } from "../../../../core/utils"; +import { + MockedAzureAccountProvider, + MockUserInteraction, + MyTokenCredential, +} from "../../../../core/utils"; import * as os from "os"; import * as uuid from "uuid"; import * as path from "path"; @@ -75,7 +77,7 @@ describe("Azure Storage Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Storage/storageAccounts/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), progressBar: { @@ -126,7 +128,7 @@ describe("Azure Storage Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Storage/storageAccounts/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), progressBar: { @@ -176,7 +178,7 @@ describe("Azure Storage Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Storage/storageAccounts/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; sandbox @@ -189,7 +191,7 @@ describe("Azure Storage Deploy Driver test", () => { it("clear storage error", async () => { const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; const deploy = new AzureStorageDeployDriver(); @@ -228,7 +230,7 @@ describe("Azure Storage Deploy Driver test", () => { it("clear storage with remote server error", async () => { const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; const deploy = new AzureStorageDeployDriver(); @@ -275,7 +277,7 @@ describe("Azure Storage Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Storage/storageAccounts/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; @@ -322,7 +324,7 @@ describe("Azure Storage Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Storage/storageAccounts/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; @@ -369,7 +371,7 @@ describe("Azure Storage Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Storage/storageAccounts/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; @@ -402,7 +404,7 @@ describe("Azure Storage Deploy Driver test", () => { "/subscriptions/e24d88be-bbbb-1234-ba25-aa11aaaa1aa1/resourceGroups/hoho-rg/providers/Microsoft.Storage/storageAccounts/some-server-farm", } as DeployArgs; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; diff --git a/packages/fx-core/tests/component/driver/deploy/azure/azureStorageStaticWebsiteConfigDriver.test.ts b/packages/fx-core/tests/component/driver/deploy/azure/azureStorageStaticWebsiteConfigDriver.test.ts index a704c05026..15b24562e2 100644 --- a/packages/fx-core/tests/component/driver/deploy/azure/azureStorageStaticWebsiteConfigDriver.test.ts +++ b/packages/fx-core/tests/component/driver/deploy/azure/azureStorageStaticWebsiteConfigDriver.test.ts @@ -9,14 +9,16 @@ import * as chai from "chai"; import * as sinon from "sinon"; import * as tools from "../../../../../src/common/utils"; import { AzureStorageStaticWebsiteConfigDriver } from "../../../../../src/component/driver/deploy/azure/azureStorageStaticWebsiteConfigDriver"; -import { TestAzureAccountProvider } from "../../../util/azureAccountMock"; import { TestLogProvider } from "../../../util/logProviderMock"; import { DriverContext } from "../../../../../src/component/driver/interface/commonArgs"; import { ListAccountSasResponse, StorageManagementClient } from "@azure/arm-storage"; import { BlobServiceClient, ServiceGetPropertiesResponse } from "@azure/storage-blob"; -import { MyTokenCredential } from "../../../../plugins/solution/util"; import * as armStorage from "@azure/arm-storage"; -import { MockUserInteraction } from "../../../../core/utils"; +import { + MockedAzureAccountProvider, + MockUserInteraction, + MyTokenCredential, +} from "../../../../core/utils"; import { IProgressHandler } from "@microsoft/teamsfx-api"; describe("Azure Storage enable static website Driver test", () => { @@ -51,7 +53,7 @@ describe("Azure Storage enable static website Driver test", () => { it("Azure Storage enable static website happy path", async () => { const driver = new AzureStorageStaticWebsiteConfigDriver(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), progressBar: { @@ -107,7 +109,7 @@ describe("Azure Storage enable static website Driver test", () => { it("Azure Storage use default", async () => { const driver = new AzureStorageStaticWebsiteConfigDriver(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; @@ -146,7 +148,7 @@ describe("Azure Storage enable static website Driver test", () => { it("should skip enable static website", async () => { const driver = new AzureStorageStaticWebsiteConfigDriver(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), } as any; // fake azure credentials @@ -184,7 +186,7 @@ describe("Azure Storage enable static website Driver test", () => { it("Azure Storage set properties error", async () => { const driver = new AzureStorageStaticWebsiteConfigDriver(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; @@ -226,7 +228,7 @@ describe("Azure Storage enable static website Driver test", () => { it("Azure Storage set properties remote server error", async () => { const driver = new AzureStorageStaticWebsiteConfigDriver(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; @@ -269,7 +271,7 @@ describe("Azure Storage enable static website Driver test", () => { it("Azure Storage enable static website get properties error", async () => { const driver = new AzureStorageStaticWebsiteConfigDriver(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; @@ -304,7 +306,7 @@ describe("Azure Storage enable static website Driver test", () => { it("Azure Storage enable static website get properties remote error", async () => { const driver = new AzureStorageStaticWebsiteConfigDriver(); const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), } as any; diff --git a/packages/fx-core/tests/component/driver/deploy/spfx/deployDriver.test.ts b/packages/fx-core/tests/component/driver/deploy/spfx/deployDriver.test.ts index 0cd2dfaedf..3c878e2a94 100644 --- a/packages/fx-core/tests/component/driver/deploy/spfx/deployDriver.test.ts +++ b/packages/fx-core/tests/component/driver/deploy/spfx/deployDriver.test.ts @@ -11,11 +11,7 @@ import fs from "fs-extra"; import sinon from "sinon"; import { Constants } from "../../../../../src/component/driver/deploy/spfx/utility/constants"; -import { - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../../plugins/solution/util"; import { SPFxDeployDriver } from "../../../../../src/component/driver/deploy/spfx/deployDriver"; import { SPOClient } from "../../../../../src/component/driver/deploy/spfx/utility/spoClient"; import * as Tools from "../../../../../src/common/tools"; @@ -30,6 +26,7 @@ import { UploadAppPackageFailedError } from "../../../../../src/component/driver import { GetGraphTokenFailedError } from "../../../../../src/component/driver/deploy/spfx/error/getGraphTokenFailedError"; import { GetTenantFailedError } from "../../../../../src/component/driver/deploy/spfx/error/getTenantFailedError"; import { FileNotFoundError } from "../../../../../src/error/common"; +import { MockedM365Provider } from "../../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/driver/m365/acquire.test.ts b/packages/fx-core/tests/component/driver/m365/acquire.test.ts index 948bc0333b..111f26cd6c 100644 --- a/packages/fx-core/tests/component/driver/m365/acquire.test.ts +++ b/packages/fx-core/tests/component/driver/m365/acquire.test.ts @@ -7,16 +7,13 @@ import chai from "chai"; import fs from "fs-extra"; import { PackageService } from "../../../../src/component/m365/packageService"; import { M365TitleAcquireDriver } from "../../../../src/component/driver/m365/acquire"; -import { - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; import { FileNotFoundError, InvalidActionInputError, UnhandledError, } from "../../../../src/error/common"; +import { MockedM365Provider } from "../../../core/utils"; describe("teamsApp/extendToM365", async () => { const acquireDriver = new M365TitleAcquireDriver(); diff --git a/packages/fx-core/tests/component/driver/oauth/create.test.ts b/packages/fx-core/tests/component/driver/oauth/create.test.ts index 976b95d849..82c6895fe1 100644 --- a/packages/fx-core/tests/component/driver/oauth/create.test.ts +++ b/packages/fx-core/tests/component/driver/oauth/create.test.ts @@ -15,12 +15,8 @@ import { OauthRegistrationAppType, OauthRegistrationTargetAudience, } from "../../../../src/component/driver/teamsApp/interfaces/OauthRegistration"; -import { - MockedAzureAccountProvider, - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; +import { MockedAzureAccountProvider, MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; @@ -1028,7 +1024,7 @@ describe("CreateOauthDriver", () => { const result = await createOauthDriver.execute(args, mockedDriverContext, outputEnvVarNames); expect(result.result.isErr()).to.be.true; if (result.result.isErr()) { - expect(result.result.error.name).to.equal("OauthFailedToGetDomain"); + expect(result.result.error.name).to.equal("OauthAuthMissingInSpec"); } }); @@ -1058,6 +1054,76 @@ describe("CreateOauthDriver", () => { targetAudience: "HomeTenant", }; + const result = await createOauthDriver.execute(args, mockedDriverContext, outputEnvVarNames); + expect(result.result.isErr()).to.be.true; + if (result.result.isErr()) { + expect(result.result.error.name).to.equal("OauthAuthMissingInSpec"); + } + }); + + it("should throw error if list api contains auth but server info is null ", async () => { + sinon.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "api", + server: "", + operationId: "get", + auth: { + name: "test", + authScheme: { + type: "oauth2", + flows: { + authorizationCode: { + authorizationUrl: "mockedAuthorizationUrl", + tokenUrl: "mockedTokenUrl", + scopes: { + mockedScope: "description for mocked scope", + }, + }, + }, + }, + }, + isValid: true, + reason: [], + }, + { + api: "api", + server: "https://test", + operationId: "get2", + auth: { + name: "test2", + authScheme: { + type: "oauth2", + flows: { + authorizationCode: { + authorizationUrl: "mockedAuthorizationUrl2", + tokenUrl: "mockedTokenUrl2", + scopes: { + mockedScope2: "description for mocked scope", + }, + }, + }, + }, + }, + isValid: true, + reason: [], + }, + ], + validAPICount: 0, + allAPICount: 1, + }); + const args: any = { + name: "test", + appId: "mockedAppId", + apiSpecPath: "mockedPath", + clientId: "mockedClientId", + clientSecret: "mockedClientSecret", + flow: "authorizationCode", + refreshUrl: "mockedRefreshUrl", + applicableToApps: "SpecificApp", + targetAudience: "HomeTenant", + }; + const result = await createOauthDriver.execute(args, mockedDriverContext, outputEnvVarNames); expect(result.result.isErr()).to.be.true; if (result.result.isErr()) { diff --git a/packages/fx-core/tests/component/driver/oauth/update.test.ts b/packages/fx-core/tests/component/driver/oauth/update.test.ts index fc0ce4a086..72f51068c7 100644 --- a/packages/fx-core/tests/component/driver/oauth/update.test.ts +++ b/packages/fx-core/tests/component/driver/oauth/update.test.ts @@ -16,12 +16,8 @@ import { OauthRegistrationAppType, OauthRegistrationTargetAudience, } from "../../../../src/component/driver/teamsApp/interfaces/OauthRegistration"; -import { - MockedAzureAccountProvider, - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; +import { MockedAzureAccountProvider, MockedM365Provider } from "../../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/driver/script/dotnetBuildDriver.test.ts b/packages/fx-core/tests/component/driver/script/dotnetBuildDriver.test.ts index f9f82d8e30..19213edd2e 100644 --- a/packages/fx-core/tests/component/driver/script/dotnetBuildDriver.test.ts +++ b/packages/fx-core/tests/component/driver/script/dotnetBuildDriver.test.ts @@ -7,11 +7,10 @@ import * as sinon from "sinon"; import * as tools from "../../../../src/common/utils"; import * as utils from "../../../../src/component/driver/script/scriptDriver"; import { DotnetBuildDriver } from "../../../../src/component/driver/script/dotnetBuildDriver"; -import { TestAzureAccountProvider } from "../../util/azureAccountMock"; import { TestLogProvider } from "../../util/logProviderMock"; import { DriverContext } from "../../../../src/component/driver/interface/commonArgs"; import { assert } from "chai"; -import { MockUserInteraction } from "../../../core/utils"; +import { MockedAzureAccountProvider, MockUserInteraction } from "../../../core/utils"; import { err, IProgressHandler, ok, UserError } from "@microsoft/teamsfx-api"; describe("Dotnet Build Driver test", () => { @@ -39,7 +38,7 @@ describe("Dotnet Build Driver test", () => { execPath: "/usr/local/bin", }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), projectPath: "./", @@ -58,7 +57,7 @@ describe("Dotnet Build Driver test", () => { args: "build", }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), ui: new MockUserInteraction(), logProvider: new TestLogProvider(), projectPath: "./", @@ -76,7 +75,7 @@ describe("Dotnet Build Driver test", () => { args: "build", }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), projectPath: "./", } as any; diff --git a/packages/fx-core/tests/component/driver/script/npmBuildDriver.test.ts b/packages/fx-core/tests/component/driver/script/npmBuildDriver.test.ts index febb82d3fe..f9f69af1b9 100644 --- a/packages/fx-core/tests/component/driver/script/npmBuildDriver.test.ts +++ b/packages/fx-core/tests/component/driver/script/npmBuildDriver.test.ts @@ -9,12 +9,11 @@ import * as chai from "chai"; import * as sinon from "sinon"; import * as tools from "../../../../src/common/utils"; import * as utils from "../../../../src/component/driver/script/scriptDriver"; -import { TestAzureAccountProvider } from "../../util/azureAccountMock"; import { TestLogProvider } from "../../util/logProviderMock"; import { DriverContext } from "../../../../src/component/driver/interface/commonArgs"; import { NpmBuildDriver } from "../../../../src/component/driver/script/npmBuildDriver"; import { assert } from "chai"; -import { MockUserInteraction } from "../../../core/utils"; +import { MockedAzureAccountProvider, MockUserInteraction } from "../../../core/utils"; import { err, ok, UserError } from "@microsoft/teamsfx-api"; describe("NPM Build Driver test", () => { @@ -35,7 +34,7 @@ describe("NPM Build Driver test", () => { args: "build", }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: new MockUserInteraction(), projectPath: "./", @@ -55,7 +54,7 @@ describe("NPM Build Driver test", () => { env: { a: "HELLO" }, }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), projectPath: "./", } as any; diff --git a/packages/fx-core/tests/component/driver/script/npxBuildDriver.test.ts b/packages/fx-core/tests/component/driver/script/npxBuildDriver.test.ts index 4aed5c8aa6..550331f02e 100644 --- a/packages/fx-core/tests/component/driver/script/npxBuildDriver.test.ts +++ b/packages/fx-core/tests/component/driver/script/npxBuildDriver.test.ts @@ -12,8 +12,7 @@ import chai from "chai"; import * as tools from "../../../../src/common/utils"; import { NpxBuildDriver } from "../../../../src/component/driver/script/npxBuildDriver"; import * as utils from "../../../../src/component/driver/script/scriptDriver"; -import { MockUserInteraction } from "../../../core/utils"; -import { TestAzureAccountProvider } from "../../util/azureAccountMock"; +import { MockUserInteraction, MockedAzureAccountProvider } from "../../../core/utils"; import { TestLogProvider } from "../../util/logProviderMock"; describe("NPX Build Driver test", () => { @@ -34,7 +33,7 @@ describe("NPX Build Driver test", () => { args: "build", }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: new MockUserInteraction(), projectPath: "./", @@ -53,7 +52,7 @@ describe("NPX Build Driver test", () => { env: { a: "HELLO" }, }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), projectPath: "./", } as any; diff --git a/packages/fx-core/tests/component/driver/script/scriptDriver.test.ts b/packages/fx-core/tests/component/driver/script/scriptDriver.test.ts index ae209d617d..44b55d2a56 100644 --- a/packages/fx-core/tests/component/driver/script/scriptDriver.test.ts +++ b/packages/fx-core/tests/component/driver/script/scriptDriver.test.ts @@ -13,6 +13,7 @@ import * as tools from "../../../../src/common/utils"; import { convertScriptErrorToFxError, defaultShell, + executeCommand, getStderrHandler, parseSetOutputCommand, scriptDriver, @@ -20,8 +21,11 @@ import { import * as charsetUtils from "../../../../src/component/utils/charsetUtils"; import { DefaultEncoding, getSystemEncoding } from "../../../../src/component/utils/charsetUtils"; import { ScriptExecutionError, ScriptTimeoutError } from "../../../../src/error/script"; -import { MockLogProvider, MockUserInteraction } from "../../../core/utils"; -import { TestAzureAccountProvider } from "../../util/azureAccountMock"; +import { + MockLogProvider, + MockUserInteraction, + MockedAzureAccountProvider, +} from "../../../core/utils"; import { TestLogProvider } from "../../util/logProviderMock"; describe("Script Driver test", () => { @@ -40,7 +44,7 @@ describe("Script Driver test", () => { redirectTo: "./log", }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: new MockUserInteraction(), progressBar: { @@ -67,7 +71,7 @@ describe("Script Driver test", () => { run: "abc", }; const context = { - azureAccountProvider: new TestAzureAccountProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), logProvider: new TestLogProvider(), ui: new MockUserInteraction(), projectPath: "./", @@ -86,7 +90,19 @@ describe("Script Driver test", () => { assert.isTrue(res instanceof ScriptExecutionError); }); }); - +describe("executeCommand", () => { + const sandbox = sinon.createSandbox(); + afterEach(() => { + sandbox.restore(); + }); + it("dotnet command", async () => { + sandbox.stub(charsetUtils, "getSystemEncoding").resolves("utf-8"); + const stub = sandbox.stub(child_process, "exec").returns({} as any); + stub.yields(null); + await executeCommand("dotnet test", "./", new TestLogProvider(), new MockUserInteraction()); + assert.isTrue(stub.calledOnce); + }); +}); describe("getSystemEncoding", () => { const sandbox = sinon.createSandbox(); afterEach(() => { diff --git a/packages/fx-core/tests/component/driver/teamsApp/configure.test.ts b/packages/fx-core/tests/component/driver/teamsApp/configure.test.ts index bc6a65592e..7deee41496 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/configure.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/configure.test.ts @@ -12,13 +12,10 @@ import { teamsDevPortalClient } from "../../../../src/client/teamsDevPortalClien import { ConfigureTeamsAppDriver } from "../../../../src/component/driver/teamsApp/configure"; import { AppStudioError } from "../../../../src/component/driver/teamsApp/errors"; import { ConfigureTeamsAppArgs } from "../../../../src/component/driver/teamsApp/interfaces/ConfigureTeamsAppArgs"; -import { - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; import { Constants } from "./../../../../src/component/driver/teamsApp/constants"; import { AppDefinition } from "./../../../../src/component/driver/teamsApp/interfaces/appdefinitions/appDefinition"; +import { MockedM365Provider } from "../../../core/utils"; describe("teamsApp/update", async () => { const teamsAppDriver = new ConfigureTeamsAppDriver(); diff --git a/packages/fx-core/tests/component/driver/teamsApp/copilotGptManifest.test.ts b/packages/fx-core/tests/component/driver/teamsApp/copilotGptManifest.test.ts index 57734739b8..c7d1c97aba 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/copilotGptManifest.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/copilotGptManifest.test.ts @@ -50,10 +50,241 @@ describe("copilotGptManifestUtils", () => { }; describe("add plugin", async () => { + it("add plugin without appending conversation starters success", async () => { + sandbox.stub(fs, "pathExists").resolves(true); + sandbox.stub(fs, "readFile").resolves( + JSON.stringify({ + name: "name${{APP_NAME_SUFFIX}}", + description: "description", + conversation_starters: [ + { + text: "List all repairs", + }, + ], + }) as any + ); + sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "readJson").resolves({} as any); + + const res = await copilotGptManifestUtils.addAction("testPath", "testId", "testFile"); + + chai.assert.isTrue(res.isOk()); + if (res.isOk()) { + const updatedManifest = res.value; + chai.assert.deepEqual(updatedManifest.actions![0], { + id: "testId", + file: "testFile", + }); + + chai.assert.deepEqual(updatedManifest.conversation_starters, [ + { + text: "List all repairs", + }, + ]); + } + }); + it("add plugin success", async () => { sandbox.stub(fs, "pathExists").resolves(true); sandbox.stub(fs, "readFile").resolves(JSON.stringify(gptManifest) as any); sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "readJson").resolves({ + capabilities: { + conversation_starters: [ + { + text: "List all repairs", + }, + ], + }, + } as any); + + const res = await copilotGptManifestUtils.addAction("testPath", "testId", "testFile"); + + chai.assert.isTrue(res.isOk()); + if (res.isOk()) { + const updatedManifest = res.value; + chai.assert.deepEqual(updatedManifest.actions![0], { + id: "testId", + file: "testFile", + }); + + chai.assert.deepEqual(updatedManifest.conversation_starters, [ + { + text: "List all repairs", + }, + ]); + } + }); + + it("add plugin and append conversation starters success", async () => { + sandbox.stub(fs, "pathExists").resolves(true); + sandbox.stub(fs, "readFile").resolves( + JSON.stringify({ + name: "name${{APP_NAME_SUFFIX}}", + description: "description", + conversation_starters: [ + { + text: "List all repairs1", + }, + ], + actions: [ + { + id: "action_1", + file: "plugin1.json", + }, + ], + }) as any + ); + sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "readJson").resolves({ + capabilities: { + conversation_starters: [ + { + text: "List all repairs2", + }, + ], + }, + } as any); + + const res = await copilotGptManifestUtils.addAction("testPath", "testId", "testFile"); + + chai.assert.isTrue(res.isOk()); + if (res.isOk()) { + const updatedManifest = res.value; + chai.assert.deepEqual(updatedManifest.actions![0], { + id: "action_1", + file: "plugin1.json", + }); + chai.assert.deepEqual(updatedManifest.actions![1], { + id: "testId", + file: "testFile", + }); + + chai.assert.deepEqual(updatedManifest.conversation_starters, [ + { + text: "List all repairs1", + }, + { + text: "List all repairs2", + }, + ]); + } + }); + + it("conversation starters count should less than 6", async () => { + sandbox.stub(fs, "pathExists").resolves(true); + sandbox.stub(fs, "readFile").resolves( + JSON.stringify({ + name: "name${{APP_NAME_SUFFIX}}", + description: "description", + conversation_starters: [ + { + text: "List all repairs1", + }, + ], + actions: [ + { + id: "action_1", + file: "plugin1.json", + }, + ], + }) as any + ); + sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "readJson").resolves({ + capabilities: { + conversation_starters: [ + { + text: "List all repairs2", + }, + { + text: "List all repairs3", + }, + { + text: "List all repairs4", + }, + { + text: "List all repairs5", + }, + { + text: "List all repairs6", + }, + { + text: "List all repairs7", + }, + ], + }, + } as any); + + const res = await copilotGptManifestUtils.addAction("testPath", "testId", "testFile"); + + chai.assert.isTrue(res.isOk()); + if (res.isOk()) { + const updatedManifest = res.value; + chai.assert.deepEqual(updatedManifest.actions![0], { + id: "action_1", + file: "plugin1.json", + }); + chai.assert.deepEqual(updatedManifest.actions![1], { + id: "testId", + file: "testFile", + }); + + chai.assert.deepEqual(updatedManifest.conversation_starters, [ + { + text: "List all repairs1", + }, + { + text: "List all repairs2", + }, + { + text: "List all repairs3", + }, + { + text: "List all repairs4", + }, + { + text: "List all repairs5", + }, + { + text: "List all repairs6", + }, + ]); + } + }); + + it("conversation starters should unique", async () => { + sandbox.stub(fs, "pathExists").resolves(true); + sandbox.stub(fs, "readFile").resolves( + JSON.stringify({ + name: "name${{APP_NAME_SUFFIX}}", + description: "description", + conversation_starters: [ + { + text: "List all repairs1", + }, + ], + actions: [ + { + id: "action_1", + file: "plugin1.json", + }, + ], + }) as any + ); + sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "readJson").resolves({ + capabilities: { + conversation_starters: [ + { + text: "List all repairs1", + }, + { + text: "List all repairs2", + }, + ], + }, + } as any); const res = await copilotGptManifestUtils.addAction("testPath", "testId", "testFile"); @@ -61,9 +292,22 @@ describe("copilotGptManifestUtils", () => { if (res.isOk()) { const updatedManifest = res.value; chai.assert.deepEqual(updatedManifest.actions![0], { + id: "action_1", + file: "plugin1.json", + }); + chai.assert.deepEqual(updatedManifest.actions![1], { id: "testId", file: "testFile", }); + + chai.assert.deepEqual(updatedManifest.conversation_starters, [ + { + text: "List all repairs1", + }, + { + text: "List all repairs2", + }, + ]); } }); @@ -80,6 +324,7 @@ describe("copilotGptManifestUtils", () => { sandbox.stub(fs, "pathExists").resolves(true); sandbox.stub(fs, "readFile").resolves(JSON.stringify(gptManifest) as any); sandbox.stub(fs, "writeFile").throws("some error"); + sandbox.stub(fs, "readJson").resolves({} as any); const res = await copilotGptManifestUtils.addAction("testPath", "testId", "testFile"); chai.assert.isTrue(res.isErr()); if (res.isErr()) { @@ -530,13 +775,20 @@ describe("copilotGptManifestUtils", () => { }); it("Success on second try", async () => { - sandbox.stub(fs, "pathExists").onFirstCall().resolves(true).onSecondCall().resolves(false); + sandbox + .stub(fs, "pathExists") + .onFirstCall() + .resolves(true) + .onSecondCall() + .resolves(true) + .onThirdCall() + .resolves(false); const res = await copilotGptManifestUtils.getDefaultNextAvailablePluginManifestPath("test"); chai.assert.equal(res, path.join("test", "ai-plugin_2.json")); }); it("Success on first try", async () => { - sandbox.stub(fs, "pathExists").onFirstCall().resolves(false); + sandbox.stub(fs, "pathExists").onFirstCall().resolves(true).onSecondCall().resolves(false); const res = await copilotGptManifestUtils.getDefaultNextAvailablePluginManifestPath("test"); chai.assert.equal(res, path.join("test", "ai-plugin_1.json")); }); diff --git a/packages/fx-core/tests/component/driver/teamsApp/create.test.ts b/packages/fx-core/tests/component/driver/teamsApp/create.test.ts index ddf57073b7..914337667d 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/create.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/create.test.ts @@ -13,13 +13,10 @@ import { ExecutionResult } from "../../../../src/component/driver/interface/step import { CreateTeamsAppDriver } from "../../../../src/component/driver/teamsApp/create"; import { CreateAppPackageDriver } from "../../../../src/component/driver/teamsApp/createAppPackage"; import { CreateTeamsAppArgs } from "../../../../src/component/driver/teamsApp/interfaces/CreateTeamsAppArgs"; -import { - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; import { Constants } from "./../../../../src/component/driver/teamsApp/constants"; import { AppDefinition } from "./../../../../src/component/driver/teamsApp/interfaces/appdefinitions/appDefinition"; +import { MockedM365Provider } from "../../../core/utils"; describe("teamsApp/create", async () => { const teamsAppDriver = new CreateTeamsAppDriver(); diff --git a/packages/fx-core/tests/component/driver/teamsApp/createAppPackage.test.ts b/packages/fx-core/tests/component/driver/teamsApp/createAppPackage.test.ts index cb52f92db9..f2e4b20b51 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/createAppPackage.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/createAppPackage.test.ts @@ -9,16 +9,13 @@ import * as path from "path"; import mockedEnv, { RestoreFn } from "mocked-env"; import { CreateAppPackageDriver } from "../../../../src/component/driver/teamsApp/createAppPackage"; import { CreateAppPackageArgs } from "../../../../src/component/driver/teamsApp/interfaces/CreateAppPackageArgs"; -import { - MockedM365Provider, - MockedLogProvider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; import { FileNotFoundError, JSONSyntaxError } from "../../../../src/error/common"; import { manifestUtils } from "../../../../src/component/driver/teamsApp/utils/ManifestUtils"; import { ok, Platform, PluginManifestSchema, TeamsAppManifest } from "@microsoft/teamsfx-api"; import AdmZip from "adm-zip"; import { InvalidFileOutsideOfTheDirectotryError } from "../../../../src/error/teamsApp"; +import { MockedM365Provider } from "../../../core/utils"; describe("teamsApp/createAppPackage", async () => { const teamsAppDriver = new CreateAppPackageDriver(); diff --git a/packages/fx-core/tests/component/driver/teamsApp/manifestUtils.test.ts b/packages/fx-core/tests/component/driver/teamsApp/manifestUtils.test.ts index 9ea5ed3dfc..ca26f7feb0 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/manifestUtils.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/manifestUtils.test.ts @@ -7,6 +7,7 @@ import { ManifestUtils, } from "../../../../src/component/driver/teamsApp/utils/ManifestUtils"; import fs from "fs-extra"; +import path from "path"; import { TeamsAppManifest, InputsWithProjectPath, @@ -436,6 +437,38 @@ describe("readAppManifestSync", () => { }); }); +describe("getTeamsAppManifestPath", () => { + const sandbox = sinon.createSandbox(); + const projectPath = "projectPath"; + + afterEach(() => { + sandbox.restore(); + }); + + it("return manifest path under appManifest", () => { + sandbox.stub(fs, "existsSync").returns(true); + const res = manifestUtils.getTeamsAppManifestPath(projectPath); + assert.equal(res, path.join(projectPath, "appManifest", "manifest.json")); + }); + + it("return manifest path under root directory", () => { + sandbox.stub(fs, "existsSync").callsFake((inputPath) => { + if (inputPath === path.join(projectPath, "appManifest", "manifest.json")) { + return false; + } + return true; + }); + const res = manifestUtils.getTeamsAppManifestPath(projectPath); + assert.equal(res, path.join(projectPath, "manifest.json")); + }); + + it("return manifest path under appPackage", () => { + sandbox.stub(fs, "existsSync").returns(false); + const res = manifestUtils.getTeamsAppManifestPath(projectPath); + assert.equal(res, path.join(projectPath, "appPackage", "manifest.json")); + }); +}); + describe("trimManifestShortName", () => { const sandbox = sinon.createSandbox(); @@ -448,6 +481,7 @@ describe("trimManifestShortName", () => { teamsManifest.name.short = "shortname abcdefghijklmn123456${{APP_NAME_SUFFIX}}"; sandbox.stub(fs, "readJson").resolves(teamsManifest); sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "pathExistsSync").returns(true); const res = await manifestUtils.trimManifestShortName("projectPath"); assert.isTrue(res.isOk()); assert.equal(teamsManifest.name.short, "shortnameabcdefghijklmn12${{APP_NAME_SUFFIX}}"); @@ -457,6 +491,7 @@ describe("trimManifestShortName", () => { teamsManifest.name.short = "shortname abcdefghijklmn123456"; sandbox.stub(fs, "readJson").resolves(teamsManifest); sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "pathExistsSync").returns(true); const res = await manifestUtils.trimManifestShortName("projectPath"); assert.isTrue(res.isOk()); assert.equal(teamsManifest.name.short, "shortnameabcdefghijklmn12"); @@ -464,10 +499,24 @@ describe("trimManifestShortName", () => { it("No need to trim", async () => { const teamsManifest = new TeamsAppManifest(); teamsManifest.name.short = "shortname abcdefghijklmn${{APP_NAME_SUFFIX}}"; - sandbox.stub(fs, "readJson").resolves(teamsManifest); - sandbox.stub(fs, "writeFile").resolves(); + const readJsonStub = sandbox.stub(fs, "readJson").resolves(teamsManifest); + const writeFileStub = sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "pathExistsSync").returns(true); const res = await manifestUtils.trimManifestShortName("projectPath"); assert.isTrue(res.isOk()); + assert.isTrue(readJsonStub.calledOnce); + assert.isTrue(writeFileStub.notCalled); assert.equal(teamsManifest.name.short, "shortname abcdefghijklmn${{APP_NAME_SUFFIX}}"); }); + it("No manifest", async () => { + const teamsManifest = new TeamsAppManifest(); + teamsManifest.name.short = "shortname abcdefghijklmn${{APP_NAME_SUFFIX}}"; + const readJsonStub = sandbox.stub(fs, "readJson").resolves(teamsManifest); + const writeFileStub = sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "pathExistsSync").returns(false); + const res = await manifestUtils.trimManifestShortName("projectPath"); + assert.isTrue(res.isOk()); + assert.isTrue(readJsonStub.notCalled); + assert.isTrue(writeFileStub.notCalled); + }); }); diff --git a/packages/fx-core/tests/component/driver/teamsApp/pluginManifestUtils.test.ts b/packages/fx-core/tests/component/driver/teamsApp/pluginManifestUtils.test.ts index 1a9921a2b0..baee7ed35f 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/pluginManifestUtils.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/pluginManifestUtils.test.ts @@ -454,7 +454,14 @@ describe("pluginManifestUtils", () => { describe("getDefaultNextAvailableApiSpecPath", async () => { it("Json file: success on second try", async () => { - sandbox.stub(fs, "pathExists").onFirstCall().resolves(true).onSecondCall().resolves(false); + sandbox + .stub(fs, "pathExists") + .onFirstCall() + .resolves(true) + .onSecondCall() + .resolves(true) + .onThirdCall() + .resolves(false); const res = await pluginManifestUtils.getDefaultNextAvailableApiSpecPath( "testPath.json", @@ -465,7 +472,7 @@ describe("pluginManifestUtils", () => { }); it("Yaml file: success on first try", async () => { - sandbox.stub(fs, "pathExists").onFirstCall().resolves(false); + sandbox.stub(fs, "pathExists").onFirstCall().resolves(true).onSecondCall().resolves(false); const res = await pluginManifestUtils.getDefaultNextAvailableApiSpecPath( "testPath.yaml", @@ -484,6 +491,8 @@ describe("pluginManifestUtils", () => { .onSecondCall() .resolves(true) .onThirdCall() + .resolves(true) + .onCall(4) .resolves(false); const res = await pluginManifestUtils.getDefaultNextAvailableApiSpecPath("testPath", "test"); diff --git a/packages/fx-core/tests/component/driver/teamsApp/publishAppPackage.test.ts b/packages/fx-core/tests/component/driver/teamsApp/publishAppPackage.test.ts index b394b2b287..e237e40099 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/publishAppPackage.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/publishAppPackage.test.ts @@ -14,12 +14,9 @@ import { PublishingState } from "../../../../src/component/driver/teamsApp/inter import { PublishAppPackageArgs } from "../../../../src/component/driver/teamsApp/interfaces/PublishAppPackageArgs"; import { PublishAppPackageDriver } from "../../../../src/component/driver/teamsApp/publishAppPackage"; import { UserCancelError } from "../../../../src/error/common"; -import { - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; import { Constants } from "./../../../../src/component/driver/teamsApp/constants"; +import { MockedM365Provider } from "../../../core/utils"; describe("teamsApp/publishAppPackage", async () => { const teamsAppDriver = new PublishAppPackageDriver(); diff --git a/packages/fx-core/tests/component/driver/teamsApp/syncManifest.test.ts b/packages/fx-core/tests/component/driver/teamsApp/syncManifest.test.ts index d8f085c472..47eab994dd 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/syncManifest.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/syncManifest.test.ts @@ -5,7 +5,7 @@ import fs from "fs-extra"; import { SyncManifestDriver } from "../../../../src/component/driver/teamsApp/syncManifest"; import { AppStudioError } from "../../../../src/component/driver/teamsApp/errors"; import { SyncManifestArgs } from "../../../../src/component/driver/teamsApp/interfaces/SyncManifest"; -import { MockedLogProvider, MockedM365Provider } from "../../../plugins/solution/util"; +import { MockedLogProvider } from "../../../plugins/solution/util"; import { envUtil } from "../../../../src/component/utils/envUtil"; import { manifestUtils } from "../../../../src/component/driver/teamsApp/utils/ManifestUtils"; import { ok, err, TeamsAppManifest, Err, UserError, Result, FxError } from "@microsoft/teamsfx-api"; @@ -13,6 +13,7 @@ import * as appStudio from "../../../../src/component/driver/teamsApp/appStudio" import { DotenvOutput, getLocalizedString } from "../../../../build"; import { metadataUtil, pathUtils } from "../../../../src"; import { ILifecycle, ProjectModel } from "../../../../src/component/configManager/interface"; +import { MockedM365Provider } from "../../../core/utils"; describe("teamsApp/syncManifest", async () => { const syncManifestDriver = new SyncManifestDriver(); diff --git a/packages/fx-core/tests/component/driver/teamsApp/validate.test.ts b/packages/fx-core/tests/component/driver/teamsApp/validate.test.ts index 0bcfa6706a..01dc884bff 100644 --- a/packages/fx-core/tests/component/driver/teamsApp/validate.test.ts +++ b/packages/fx-core/tests/component/driver/teamsApp/validate.test.ts @@ -40,12 +40,8 @@ import { ValidateAppPackageDriver } from "../../../../src/component/driver/teams import { ValidateWithTestCasesDriver } from "../../../../src/component/driver/teamsApp/validateTestCases"; import { metadataUtil } from "../../../../src/component/utils/metadataUtil"; import { InvalidActionInputError, UserCancelError } from "../../../../src/error/common"; -import { MockTools } from "../../../core/utils"; -import { - MockedLogProvider, - MockedM365Provider, - MockedUserInteraction, -} from "../../../plugins/solution/util"; +import { MockedM365Provider, MockTools } from "../../../core/utils"; +import { MockedLogProvider, MockedUserInteraction } from "../../../plugins/solution/util"; describe("teamsApp/validateManifest", async () => { const teamsAppDriver = new ValidateManifestDriver(); @@ -203,6 +199,23 @@ describe("teamsApp/validateManifest", async () => { }); it("validation error - download failed", async () => { + sinon.stub(ManifestUtil, "validateManifest").resolves([]); + sinon.stub(ManifestUtil, "validateManifestAgainstSchema").throws("error"); + const args: ValidateManifestArgs = { + manifestPath: + "./tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.manifest.template.json", + }; + + process.env.CONFIG_TEAMS_APP_NAME = "fakeName"; + + const result = (await teamsAppDriver.execute(args, mockedDriverContext)).result; + chai.assert(result.isErr()); + if (result.isErr()) { + chai.assert(result.error.name, AppStudioError.ValidationFailedError.name); + } + }); + + it("validation error - localization file validation failed", async () => { sinon .stub(ManifestUtil, "validateManifest") .throws(new Error(`Failed to get manifest at url due to: unknown error`)); @@ -220,6 +233,192 @@ describe("teamsApp/validateManifest", async () => { } }); + describe("validateLocalizatoinFiles", async () => { + const teamsAppDriver = new ValidateManifestDriver(); + const mockedDriverContext: any = { + projectPath: "./", + }; + + afterEach(() => { + sinon.restore(); + }); + + it("should return ok when no additionalLanguages in manifest", async () => { + const args: ValidateManifestArgs = { manifestPath: "fakepath" }; + const manifest = { localizationInfo: { additionalLanguages: [] } } as any; + + const result = await teamsAppDriver.validateLocalizatoinFiles( + args, + mockedDriverContext, + manifest + ); + chai.assert(result.isOk()); + }); + + it("should return error when language file path is not defined", async () => { + const args: ValidateManifestArgs = { manifestPath: "fakepath" }; + const manifest = { localizationInfo: { additionalLanguages: [{ file: undefined }] } } as any; + + const result = await teamsAppDriver.validateLocalizatoinFiles( + args, + mockedDriverContext, + manifest + ); + chai.assert(result.isErr()); + if (result.isErr()) { + chai.assert.equal(result.error.name, AppStudioError.ValidationFailedError.name); + } + }); + + it("should return error when manifest file cannot be found", async () => { + const args: ValidateManifestArgs = { manifestPath: "fakepath" }; + const manifest = { localizationInfo: { additionalLanguages: [{ file: "filePath" }] } } as any; + + sinon + .stub(manifestUtils, "_readAppManifest") + .resolves(err(new SystemError("error", "error", "", ""))); + + const result = await teamsAppDriver.validateLocalizatoinFiles( + args, + mockedDriverContext, + manifest + ); + chai.assert(result.isErr()); + if (result.isErr()) { + chai.assert.equal(result.error.name, "error"); + } + }); + + it("should return error when validation fails", async () => { + const args: ValidateManifestArgs = { manifestPath: "fakepath" }; + const manifest = { localizationInfo: { additionalLanguages: [{ file: "filePath" }] } } as any; + const fakeLocalizationFile = { + $schema: + "https://developer.microsoft.com/en-us/json-schemas/teams/v1.16/MicrosoftTeams.Localization.schema.json", + }; + + sinon.stub(manifestUtils, "_readAppManifest").resolves(ok(fakeLocalizationFile as any)); + sinon.stub(ManifestUtil, "validateManifestAgainstSchema").resolves(["Validation error"]); + + const result = await teamsAppDriver.validateLocalizatoinFiles( + args, + mockedDriverContext, + manifest + ); + chai.assert(result.isOk()); + if (result.isOk()) { + chai.assert.isTrue(result.value.error[0].includes("Validation error")); + } + }); + + it("should output errors when validation fails", async () => { + const args: ValidateManifestArgs = { + manifestPath: + "./tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.localization.manifest.json", + }; + process.env.CONFIG_TEAMS_APP_NAME = "fakeName"; + + const result = (await teamsAppDriver.execute(args, mockedDriverContext)).result; + chai.assert(result.isErr()); + if (result.isErr()) { + chai.assert.isTrue(result.error.message.includes("2 failed")); + } + }); + + it("should output errors when validation fails - CLI", async () => { + const args: ValidateManifestArgs = { + manifestPath: + "./tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.localization.manifest.json", + }; + const mockedCLIDriverContext: any = { + m365TokenProvider: new MockedM365Provider(), + logProvider: new MockedLogProvider(), + ui: new MockedUserInteraction(), + projectPath: "./", + platform: Platform.CLI, + }; + process.env.CONFIG_TEAMS_APP_NAME = "fakeName"; + + const result = (await teamsAppDriver.execute(args, mockedCLIDriverContext)).result; + chai.assert(result.isErr()); + if (result.isErr()) { + chai.assert.isTrue(result.error.message.includes("2 failed")); + } + }); + + it("should output errors when default language file validation fails", async () => { + const args: ValidateManifestArgs = { + manifestPath: + "./tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.default.localization.manifest.json", + }; + process.env.CONFIG_TEAMS_APP_NAME = "fakeName"; + + const result = (await teamsAppDriver.execute(args, mockedDriverContext)).result; + chai.assert(result.isErr()); + if (result.isErr()) { + chai.assert.isTrue(result.error.message.includes("2 failed")); + } + }); + + it("should return error when validation throws exception", async () => { + const args: ValidateManifestArgs = { manifestPath: "fakepath" }; + const manifest = { localizationInfo: { additionalLanguages: [{ file: "filePath" }] } } as any; + const fakeLocalizationFile = {}; + + sinon.stub(manifestUtils, "_readAppManifest").resolves(ok(fakeLocalizationFile as any)); + sinon + .stub(ManifestUtil, "validateManifestAgainstSchema") + .throws(new Error("validation exception")); + + const result = await teamsAppDriver.validateLocalizatoinFiles( + args, + mockedDriverContext, + manifest + ); + chai.assert(result.isErr()); + if (result.isErr()) { + chai.assert.equal(result.error.name, AppStudioError.ValidationFailedError.name); + } + }); + + it("should not throw error if schema does not have patternProperties", async () => { + const args: ValidateManifestArgs = { manifestPath: "fakepath" }; + const manifest = { localizationInfo: { additionalLanguages: [{ file: "filePath" }] } } as any; + sinon.stub(ManifestUtil, "fetchSchema").resolves({} as any); + sinon.stub(manifestUtils, "_readAppManifest").resolves(ok({} as any)); + sinon.stub(ManifestUtil, "validateManifestAgainstSchema").resolves([] as any); + const result = await teamsAppDriver.validateLocalizatoinFiles( + args, + mockedDriverContext, + manifest + ); + chai.assert(result.isOk()); + }); + + it("should return ok when localization file is valid", async () => { + const args: ValidateManifestArgs = { manifestPath: "fakepath" }; + const manifest = { localizationInfo: { additionalLanguages: [{ file: "filePath" }] } } as any; + const fakeLocalizationFile = { + $schema: + "https://developer.microsoft.com/en-us/json-schemas/teams/v1.16/MicrosoftTeams.Localization.schema.json", + "name.short": "name short", + "name.full": "name full", + "description.short": "desp short", + "description.full": "desp full", + "staticTabs[0].name": "static tab name", + "activities.activityTypes[0].description": "aa", + }; + + sinon.stub(manifestUtils, "_readAppManifest").resolves(ok(fakeLocalizationFile as any)); + const result = await teamsAppDriver.validateLocalizatoinFiles( + args, + mockedDriverContext, + manifest + ); + chai.assert(result.isOk()); + }); + }); + describe("validate Copilot extensions", async () => { it("validate with errors returned", async () => { const teamsManifest: TeamsAppManifest = new TeamsAppManifest(); diff --git a/packages/fx-core/tests/component/feature/collaboration.test.ts b/packages/fx-core/tests/component/feature/collaboration.test.ts index 377af6b0c2..5b3e1a0799 100644 --- a/packages/fx-core/tests/component/feature/collaboration.test.ts +++ b/packages/fx-core/tests/component/feature/collaboration.test.ts @@ -6,15 +6,12 @@ import * as sinon from "sinon"; import * as chai from "chai"; import chaiAsPromised from "chai-as-promised"; import { AadCollaboration, TeamsCollaboration } from "../../../src/component/feature/collaboration"; -import { - MockedLogProvider, - MockedM365Provider, - MockedV2Context, -} from "../../plugins/solution/util"; +import { MockedLogProvider, MockedV2Context } from "../../plugins/solution/util"; import { AadAppClient } from "../../../src/component/driver/aad/utility/aadAppClient"; import axios from "axios"; import { AppUser } from "../../../src/component/driver/teamsApp/interfaces/appdefinitions/appUser"; import { teamsDevPortalClient } from "../../../src/client/teamsDevPortalClient"; +import { MockedM365Provider } from "../../core/utils"; chai.use(chaiAsPromised); const expect = chai.expect; diff --git a/packages/fx-core/tests/component/generator/apiSpecGenerator.test.ts b/packages/fx-core/tests/component/generator/apiSpecGenerator.test.ts index 165d88f741..f665a1ea78 100644 --- a/packages/fx-core/tests/component/generator/apiSpecGenerator.test.ts +++ b/packages/fx-core/tests/component/generator/apiSpecGenerator.test.ts @@ -6,11 +6,13 @@ */ import { + AdaptiveCardGenerator, ErrorResult, ErrorType, ProjectType, SpecParser, SpecParserError, + Utils, ValidationStatus, WarningType, } from "@microsoft/m365-spec-parser"; @@ -43,6 +45,7 @@ import { formatValidationErrors, generateScaffoldingSummary, listPluginExistingOperations, + injectAuthAction, } from "../../../src/component/generator/apiSpec/helper"; import { ApiPluginStartOptions, @@ -62,6 +65,7 @@ import { FeatureFlagName } from "../../../src/common/featureFlags"; import * as commonUtils from "../../../src/common/utils"; import * as helper from "../../../src/component/generator/apiSpec/helper"; import { fail } from "assert"; +import { ActionInjector } from "../../../src/component/configManager/actionInjector"; const teamsManifest: TeamsAppManifest = { name: { @@ -185,6 +189,31 @@ describe("generateScaffoldingSummary", async () => { assert.isTrue(res.includes("content")); }); + it("warnings about operationid contains special characters", async () => { + const res = await generateScaffoldingSummary( + [ + { + type: WarningType.OperationIdContainsSpecialCharacters, + content: + "Operation id 'user/repo' contained special characters and was renamed to 'user_repo'.", + data: { operationId: "user/repo" }, + }, + { + type: WarningType.OperationIdContainsSpecialCharacters, + content: + "Operation id 'user/issue' contained special characters and was renamed to 'user_issue'.", + data: { operationId: "user/issue" }, + }, + ], + teamsManifest, + "path", + undefined, + "" + ); + assert.isTrue(res.includes("user_repo")); + assert.isTrue(res.includes("user_issue")); + }); + it("warnings about adaptive card template in manifest", async () => { const composeExtension: IComposeExtension = { composeExtensionType: "apiBased", @@ -604,6 +633,78 @@ describe("formatValidationErrors", () => { }); }); +describe("injectAuthAction", async () => { + const sandbox = sinon.createSandbox(); + + afterEach(async () => { + sandbox.restore(); + }); + + it("api key auth", async () => { + sandbox.stub(fs, "pathExists").resolves(true); + sandbox.stub(Utils, "isBearerTokenAuth").returns(true); + const injectStub = sandbox.stub(ActionInjector, "injectCreateAPIKeyAction").resolves(undefined); + const res = await injectAuthAction( + "oauth", + "test", + { scheme: "", type: "http" }, + "test", + false + ); + + assert.isUndefined(res); + assert.isTrue(injectStub.calledTwice); + }); + + it("api key auth: no local yaml", async () => { + sandbox.stub(fs, "pathExists").resolves(false); + sandbox.stub(Utils, "isBearerTokenAuth").returns(true); + const injectStub = sandbox.stub(ActionInjector, "injectCreateAPIKeyAction").resolves(undefined); + const res = await injectAuthAction( + "oauth", + "test", + { scheme: "", type: "http" }, + "test", + false + ); + + assert.isUndefined(res); + assert.isTrue(injectStub.calledOnce); + }); + + it("oauth auth", async () => { + sandbox.stub(fs, "pathExists").resolves(true); + sandbox.stub(Utils, "isOAuthWithAuthCodeFlow").returns(true); + const injectStub = sandbox.stub(ActionInjector, "injectCreateOAuthAction").resolves(undefined); + const res = await injectAuthAction( + "oauth", + "test", + { scheme: "", type: "http" }, + "test", + false + ); + + assert.isUndefined(res); + assert.isTrue(injectStub.calledTwice); + }); + + it("oauth auth: no local yaml", async () => { + sandbox.stub(fs, "pathExists").resolves(false); + sandbox.stub(Utils, "isOAuthWithAuthCodeFlow").returns(true); + const injectStub = sandbox.stub(ActionInjector, "injectCreateOAuthAction").resolves(undefined); + const res = await injectAuthAction( + "oauth", + "test", + { scheme: "", type: "http" }, + "test", + false + ); + + assert.isUndefined(res); + assert.isTrue(injectStub.calledOnce); + }); +}); + describe("listPluginExistingOperations", () => { const teamsManifestWithPlugin: TeamsAppManifest = { ...teamsManifest, @@ -775,6 +876,133 @@ describe("updateForCustomApi", async () => { await CopilotPluginHelper.updateForCustomApi(spec, "typescript", "path", "openapi.yaml"); }); + it("happy path: should contain warning if generate adaptive card failed", async () => { + sandbox.stub(fs, "ensureDir").resolves(); + sandbox.stub(fs, "writeFile").callsFake((file, data) => { + if (file === path.join("path", "src", "prompts", "chat", "skprompt.txt")) { + expect(data).to.contains("The following is a conversation with an AI assistant."); + } else if (file === path.join("path", "src", "adaptiveCard", "hello.json")) { + assert.fail("should not generate adaptive card"); + } else if (file === path.join("path", "src", "prompts", "chat", "actions.json")) { + expect(data).to.contains("getHello"); + } else if (file === path.join("path", "src", "app", "app.ts")) { + expect(data).to.contains(`app.ai.action("getHello"`); + expect(data).not.to.contains("{{"); + expect(data).not.to.contains("// Replace with action code"); + } + }); + sandbox + .stub(fs, "readFile") + .resolves(Buffer.from("test code // Replace with action code {{OPENAPI_SPEC_PATH}}")); + sandbox + .stub(AdaptiveCardGenerator, "generateAdaptiveCard") + .throws(new Error("generate adaptive card failed")); + + const result = await CopilotPluginHelper.updateForCustomApi( + spec, + "typescript", + "path", + "openapi.yaml" + ); + + expect(result).to.be.deep.equal([ + { + type: WarningType.GenerateCardFailed, + content: + "Failed to create the adaptive card for API 'getHello': generate adaptive card failed. Mitigation: Not required but you can manually add it to the adaptiveCards folder.", + data: "getHello", + }, + { + type: WarningType.GenerateCardFailed, + content: + "Failed to create the adaptive card for API 'createPet': generate adaptive card failed. Mitigation: Not required but you can manually add it to the adaptiveCards folder.", + data: "createPet", + }, + ]); + }); + + it("happy path: js", async () => { + sandbox.stub(fs, "ensureDir").resolves(); + sandbox.stub(fs, "writeFile").callsFake((file, data) => { + if (file === path.join("path", "src", "prompts", "chat", "skprompt.txt")) { + expect(data).to.contains("The following is a conversation with an AI assistant."); + } else if (file === path.join("path", "src", "adaptiveCard", "hello.json")) { + expect(data).to.contains("getHello"); + } else if (file === path.join("path", "src", "prompts", "chat", "actions.json")) { + expect(data).to.contains("getHello"); + } else if (file === path.join("path", "src", "app", "app.ts")) { + expect(data).to.contains(`app.ai.action("getHello"`); + expect(data).not.to.contains("{{"); + expect(data).not.to.contains("// Replace with action code"); + } + }); + sandbox + .stub(fs, "readFile") + .resolves(Buffer.from("test code // Replace with action code {{OPENAPI_SPEC_PATH}}")); + await CopilotPluginHelper.updateForCustomApi(spec, "javascript", "path", "openapi.yaml"); + }); + + it("happy path: should contain warning if generate adaptive card data failed", async () => { + sandbox.stub(fs, "ensureDir").resolves(); + sandbox.stub(fs, "writeFile").callsFake((file, data) => { + if (file === path.join("path", "src", "prompts", "chat", "skprompt.txt")) { + expect(data).to.contains("The following is a conversation with an AI assistant."); + } else if (file === path.join("path", "src", "adaptiveCard", "hello.json")) { + assert.fail("should not generate adaptive card"); + } else if (file === path.join("path", "src", "prompts", "chat", "actions.json")) { + expect(data).to.contains("getHello"); + } else if (file === path.join("path", "src", "app", "app.ts")) { + expect(data).to.contains(`app.ai.action("getHello"`); + expect(data).not.to.contains("{{"); + expect(data).not.to.contains("// Replace with action code"); + } else if (file == path.join("path", "src", "adaptiveCard", "hello.data.json")) { + expect(data).to.deep.equal({}); + } + }); + sandbox + .stub(fs, "readFile") + .resolves(Buffer.from("test code // Replace with action code {{OPENAPI_SPEC_PATH}}")); + sandbox.stub(AdaptiveCardGenerator, "generateAdaptiveCard").returns([ + { + type: "AdaptiveCard", + $schema: "http://adaptivecards.io/schemas/adaptive-card.json", + version: "1.5", + body: [ + { + type: "TextBlock", + text: "name: ${if(name, name, 'N/A')}", + wrap: true, + }, + ], + }, + "$", + {}, + [{ type: WarningType.GenerateJsonDataFailed, content: "generate json data failed" }], + ]); + + const result = await CopilotPluginHelper.updateForCustomApi( + spec, + "typescript", + "path", + "openapi.yaml" + ); + + expect(result).to.be.deep.equal([ + { + type: WarningType.GenerateJsonDataFailed, + content: + "Failed to create the adaptive card mock data for API 'getHello': generate json data failed. Mitigation: Not required but you can manually add it to the adaptiveCards folder.", + data: "getHello", + }, + { + type: WarningType.GenerateJsonDataFailed, + content: + "Failed to create the adaptive card mock data for API 'createPet': generate json data failed. Mitigation: Not required but you can manually add it to the adaptiveCards folder.", + data: "createPet", + }, + ]); + }); + it("happy path: js", async () => { sandbox.stub(fs, "ensureDir").resolves(); sandbox.stub(fs, "writeFile").callsFake((file, data) => { @@ -2323,7 +2551,7 @@ describe("SpecGenerator", async () => { paths: {}, }, ]); - sandbox.stub(CopilotPluginHelper, "updateForCustomApi").resolves(); + sandbox.stub(CopilotPluginHelper, "updateForCustomApi").resolves([]); sandbox.stub(fs, "ensureDir").resolves(); sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(teamsManifest)); const generateBasedOnSpec = sandbox @@ -2375,7 +2603,7 @@ describe("SpecGenerator", async () => { paths: {}, }, ]); - sandbox.stub(CopilotPluginHelper, "updateForCustomApi").resolves(); + sandbox.stub(CopilotPluginHelper, "updateForCustomApi").resolves([]); sandbox.stub(fs, "ensureDir").resolves(); sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(teamsManifest)); const generateBasedOnSpec = sandbox @@ -2427,7 +2655,7 @@ describe("SpecGenerator", async () => { paths: {}, }, ]); - sandbox.stub(CopilotPluginHelper, "updateForCustomApi").resolves(); + sandbox.stub(CopilotPluginHelper, "updateForCustomApi").resolves([]); sandbox.stub(fs, "ensureDir").resolves(); sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(teamsManifest)); const generateBasedOnSpec = sandbox @@ -2664,7 +2892,11 @@ describe("SpecGenerator", async () => { sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(teamsManifest)); const generateBasedOnSpec = sandbox .stub(SpecParser.prototype, "generateForCopilot") - .resolves({ allSuccess: true, warnings: [] }); + .callsFake(async (manifestPath, filter, outputSpecPath, pluginFilePath) => { + assert.isTrue(outputSpecPath.includes("test.yaml")); + assert.isTrue(pluginFilePath.includes("test.json")); + return { allSuccess: true, warnings: [] }; + }); sandbox.stub(pluginGeneratorHelper, "generateScaffoldingSummary").resolves(""); const generator = new SpecGenerator(); diff --git a/packages/fx-core/tests/component/generator/generator.test.ts b/packages/fx-core/tests/component/generator/generator.test.ts index 40aba2580a..b07ad5e9f5 100644 --- a/packages/fx-core/tests/component/generator/generator.test.ts +++ b/packages/fx-core/tests/component/generator/generator.test.ts @@ -52,6 +52,7 @@ import { ActionContext } from "../../../src/component/middleware/actionExecution import { CapabilityOptions, ProgrammingLanguage, QuestionNames } from "../../../src/question"; import sampleConfigV3 from "../../common/samples-config-v3.json"; import { MockTools, randomAppName } from "../../core/utils"; +import { getLocalizedString } from "../../../src/common/localizeUtils"; const mockedSampleInfo: SampleConfig = { id: "test-id", @@ -1174,6 +1175,39 @@ describe("render template", () => { `${templateName}-${commonTemplateName}` ); }); + + it("template variables when CEA enabled", async () => { + sandbox.stub(process, "env").value({ TEAMSFX_CEA_ENABLED: "true" }); + const vars = newGeneratorFlag + ? getTemplateReplaceMap(inputs) + : Generator.getDefaultVariables("test"); + assert.equal(vars.CEAEnabled, "true"); + }); + + it("template variables when CEA disabled", async () => { + sandbox.stub(process, "env").value({ TEAMSFX_CEA_ENABLED: "false" }); + const vars = newGeneratorFlag + ? getTemplateReplaceMap(inputs) + : Generator.getDefaultVariables("test"); + assert.equal(vars.CEAEnabled, ""); + }); + + it("CEA works in M365 tag shows when CEA enabled", async () => { + sandbox.stub(process, "env").value({ TEAMSFX_CEA_ENABLED: "true" }); + const descriptionAnswer = getLocalizedString( + "core.createProjectQuestion.capability.customEngineAgent.description" + ); + assert.equal(CapabilityOptions.customCopilotBasic().description, descriptionAnswer); + assert.equal(CapabilityOptions.customCopilotRag().description, descriptionAnswer); + assert.equal(CapabilityOptions.customCopilotAssistant().description, descriptionAnswer); + }); + + it("CEA works in M365 tag doesn't show when CEA disabled", async () => { + sandbox.stub(process, "env").value({ TEAMSFX_CEA_ENABLED: "false" }); + assert.equal(CapabilityOptions.customCopilotBasic().description, undefined); + assert.equal(CapabilityOptions.customCopilotRag().description, undefined); + assert.equal(CapabilityOptions.customCopilotAssistant().description, undefined); + }); }); }); diff --git a/packages/fx-core/tests/component/generator/spfxGenerator.test.ts b/packages/fx-core/tests/component/generator/spfxGenerator.test.ts index 00c962396a..761c4e5ac4 100644 --- a/packages/fx-core/tests/component/generator/spfxGenerator.test.ts +++ b/packages/fx-core/tests/component/generator/spfxGenerator.test.ts @@ -715,7 +715,7 @@ describe("SPFxGenerator", function () { }; const result = await SPFxGenerator.generate(context, inputs, testFolder); - chai.expect(context.templateVariables!.SpfxNodeVersion).eq("16 || 18"); + chai.expect(context.templateVariables!.SpfxNodeVersion).eq("18"); chai.expect(result.isOk()).to.eq(true); }); @@ -741,7 +741,7 @@ describe("SPFxGenerator", function () { }; const result = await SPFxGenerator.generate(context, inputs, testFolder); - chai.expect(context.templateVariables!.SpfxNodeVersion).eq("16 || 18"); + chai.expect(context.templateVariables!.SpfxNodeVersion).eq("18"); chai.expect(result.isOk()).to.eq(true); }); }); diff --git a/packages/fx-core/tests/component/m365/launchHelper.test.ts b/packages/fx-core/tests/component/m365/launchHelper.test.ts index 9052cdfdb3..842592cb18 100644 --- a/packages/fx-core/tests/component/m365/launchHelper.test.ts +++ b/packages/fx-core/tests/component/m365/launchHelper.test.ts @@ -9,11 +9,11 @@ import { NotExtendedToM365Error } from "../../../src/component/m365/errors"; import { LaunchHelper } from "../../../src/component/m365/launchHelper"; import { PackageService } from "../../../src/component/m365/packageService"; import { HubTypes } from "../../../src/question"; -import { MockM365TokenProvider } from "../../core/utils"; import { outlookCopilotAppId } from "../../../src/component/m365/constants"; +import { MockedM365Provider } from "../../core/utils"; describe("LaunchHelper", () => { - const m365TokenProvider = new MockM365TokenProvider(); + const m365TokenProvider = new MockedM365Provider(); const launchHelper = new LaunchHelper(m365TokenProvider); afterEach(() => { diff --git a/packages/fx-core/tests/component/provisionUtils.test.ts b/packages/fx-core/tests/component/provisionUtils.test.ts index 122514f06b..27de023bb0 100644 --- a/packages/fx-core/tests/component/provisionUtils.test.ts +++ b/packages/fx-core/tests/component/provisionUtils.test.ts @@ -16,12 +16,13 @@ import { resourceGroupHelper } from "../../src/component/utils/ResourceGroupHelp import { setTools } from "../../src/common/globalVars"; import { ResourceGroupNotExistError } from "../../src/error/azure"; import { M365TenantIdNotFoundInTokenError, M365TokenJSONNotFoundError } from "../../src/error/m365"; -import { MockAzureAccountProvider, MockTelemetryReporter, MockTools } from "../core/utils"; import { MockedAzureAccountProvider, - MockedUserInteraction, MyTokenCredential, -} from "../plugins/solution/util"; + MockTelemetryReporter, + MockTools, +} from "../core/utils"; +import { MockedUserInteraction } from "../plugins/solution/util"; describe("provisionUtils", () => { const tools = new MockTools(); @@ -36,7 +37,7 @@ describe("provisionUtils", () => { mocker.restore(); }); it("no givenSubscriptionId - fail to select", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -45,7 +46,7 @@ describe("provisionUtils", () => { assert(res.isErr()); }); it("no givenSubscriptionId - success to select", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -58,7 +59,7 @@ describe("provisionUtils", () => { assert(res.isOk()); }); it("givenSubscriptionId - permission pass", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -73,7 +74,7 @@ describe("provisionUtils", () => { assert(res.isOk()); }); it("givenSubscriptionId - permission fail", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -95,7 +96,7 @@ describe("provisionUtils", () => { mocker.restore(); }); it("fail: azure token undefined", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker.stub(azureAccountProvider, "getIdentityCredentialAsync").resolves(undefined); const res = await provisionUtils.ensureResourceGroup( { platform: Platform.VSCode, projectPath: "" }, @@ -105,7 +106,7 @@ describe("provisionUtils", () => { assert(res.isErr()); }); it("fail: given invalid resource group 1", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -120,7 +121,7 @@ describe("provisionUtils", () => { assert(res.isErr() && res.error instanceof ResourceGroupNotExistError); }); it("fail: given invalid resource group 2", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -137,7 +138,7 @@ describe("provisionUtils", () => { assert(res.isErr()); }); it("success: given valid resource group", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -158,7 +159,7 @@ describe("provisionUtils", () => { assert(res.isOk()); }); it("failed: resource group not exist", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -176,7 +177,7 @@ describe("provisionUtils", () => { } }); it("success: ask resource group 1", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); @@ -198,7 +199,7 @@ describe("provisionUtils", () => { }); it("success: ask resource group 2", async () => { - const azureAccountProvider = new MockAzureAccountProvider(); + const azureAccountProvider = new MockedAzureAccountProvider(); mocker .stub(azureAccountProvider, "getIdentityCredentialAsync") .resolves(new MyTokenCredential()); diff --git a/packages/fx-core/tests/component/resource/appManifest/appstudio.test.ts b/packages/fx-core/tests/component/resource/appManifest/appstudio.test.ts index 4c69635b8d..29b2227fd8 100644 --- a/packages/fx-core/tests/component/resource/appManifest/appstudio.test.ts +++ b/packages/fx-core/tests/component/resource/appManifest/appstudio.test.ts @@ -35,12 +35,12 @@ import { envUtil } from "../../../../src/component/utils/envUtil"; import { QuestionNames } from "../../../../src/question"; import { MockLogProvider, - MockM365TokenProvider, + MockedM365Provider, + MockedAzureAccountProvider, MockTools, randomAppName, } from "../../../core/utils"; import { getAzureProjectRoot } from "../../../plugins/resource/appstudio/helper"; -import { MockedAzureAccountProvider, MockedM365Provider } from "../../../plugins/solution/util"; describe.skip("appStudio", () => { const tools = new MockTools(); @@ -49,7 +49,7 @@ describe.skip("appStudio", () => { describe("checkIfAppInDifferentAcountSameTenant", () => { const logger = new MockLogProvider(); const teamsAppId = "teams"; - const m365TokenProvider = new MockM365TokenProvider(); + const m365TokenProvider = new MockedM365Provider(); afterEach(() => { sandbox.restore(); @@ -122,7 +122,7 @@ describe.skip("appStudio", () => { describe("getAppPackage", () => { const logger = new MockLogProvider(); const teamsAppId = "teams"; - const m365TokenProvider = new MockM365TokenProvider(); + const m365TokenProvider = new MockedM365Provider(); afterEach(() => { sandbox.restore(); diff --git a/packages/fx-core/tests/component/resourceGroupHelper.test.ts b/packages/fx-core/tests/component/resourceGroupHelper.test.ts index bee3d17755..6ec53db28f 100644 --- a/packages/fx-core/tests/component/resourceGroupHelper.test.ts +++ b/packages/fx-core/tests/component/resourceGroupHelper.test.ts @@ -5,8 +5,7 @@ import "mocha"; import * as sinon from "sinon"; import { resourceGroupHelper } from "../../src/component/utils/ResourceGroupHelper"; import { setTools, TOOLS } from "../../src/common/globalVars"; -import { MockTools } from "../core/utils"; -import { MyTokenCredential } from "../plugins/solution/util"; +import { MockTools, MyTokenCredential } from "../core/utils"; import * as armResources from "@azure/arm-resources"; import * as armSubscriptions from "@azure/arm-subscriptions"; import { diff --git a/packages/fx-core/tests/component/util/azureAccountMock.ts b/packages/fx-core/tests/component/util/azureAccountMock.ts deleted file mode 100644 index cc3b5a4893..0000000000 --- a/packages/fx-core/tests/component/util/azureAccountMock.ts +++ /dev/null @@ -1,55 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { AzureAccountProvider, SubscriptionInfo } from "@microsoft/teamsfx-api"; -import { TokenCredential } from "@azure/core-auth"; -import { AccessToken, GetTokenOptions } from "@azure/identity"; - -class MyTokenCredential implements TokenCredential { - public async getToken( - scopes: string | string[], - options?: GetTokenOptions - ): Promise { - return { - token: "a.eyJ1c2VySWQiOiJ0ZXN0QHRlc3QuY29tIn0=.c", - expiresOnTimestamp: 1234, - }; - } -} - -export class TestAzureAccountProvider implements AzureAccountProvider { - async getIdentityCredentialAsync(): Promise { - return new MyTokenCredential(); - } - signout(): Promise { - throw new Error("Method not implemented."); - } - setStatusChangeMap( - name: string, - statusChange: ( - status: string, - token?: string, - accountInfo?: Record - ) => Promise - ): Promise { - throw new Error("Method not implemented."); - } - removeStatusChangeMap(name: string): Promise { - throw new Error("Method not implemented."); - } - getJsonObject(showDialog?: boolean): Promise> { - throw new Error("Method not implemented."); - } - listSubscriptions(): Promise { - throw new Error("Method not implemented."); - } - setSubscription(subscriptionId: string): Promise { - throw new Error("Method not implemented."); - } - getAccountInfo(): Record { - throw new Error("Method not implemented."); - } - getSelectedSubscription(): Promise { - throw new Error("Method not implemented."); - } -} diff --git a/packages/fx-core/tests/component/util/azureResourceOperation.test.ts b/packages/fx-core/tests/component/util/azureResourceOperation.test.ts index 14fcebcb35..f13982ee46 100644 --- a/packages/fx-core/tests/component/util/azureResourceOperation.test.ts +++ b/packages/fx-core/tests/component/util/azureResourceOperation.test.ts @@ -8,7 +8,8 @@ import { generateSasToken, getAzureAccountCredential, } from "../../../src/component/utils/azureResourceOperation"; -import { TestAzureAccountProvider } from "./azureAccountMock"; +import { MockedAzureAccountProvider } from "../../core/utils"; + chai.use(chaiAsPromised); describe("Azure Resource Operation test", () => { @@ -23,7 +24,7 @@ describe("Azure Resource Operation test", () => { }); it("should get Azure account credential error", async () => { - const tokenProvider = new TestAzureAccountProvider(); + const tokenProvider = new MockedAzureAccountProvider(); sandbox.stub(tokenProvider, "getIdentityCredentialAsync").resolves(undefined); await chai.expect(getAzureAccountCredential(tokenProvider)).to.be.eventually.rejectedWith(""); }); diff --git a/packages/fx-core/tests/component/util/envFunctionUtils.test.ts b/packages/fx-core/tests/component/util/envFunctionUtils.test.ts index 54667d1daf..d337527639 100644 --- a/packages/fx-core/tests/component/util/envFunctionUtils.test.ts +++ b/packages/fx-core/tests/component/util/envFunctionUtils.test.ts @@ -70,13 +70,16 @@ describe("expandVariableWithFunction", async () => { [FeatureFlagName.EnvFileFunc]: "true", }); const content = - "description:\"$[file('testfile1.txt')]\",description2:\"$[file( file( 'C://testfile2.txt' ))] $[file(${{FILE_PATH}})]\""; + "description:\"$[file('testfile1.md')]\",description2:\"$[file( file( 'C://testfile2.txt' ))] $[file(${{FILE_PATH}})]\""; sandbox.stub(fs, "pathExists").resolves(true); sandbox.stub(fs, "readFile").callsFake((file: number | fs.PathLike) => { if (file.toString().endsWith("testfile1.txt")) { return Promise.resolve("description in ${{TEST_ENV}}" as any); } else if (file.toString().endsWith("testfile2.txt")) { return Promise.resolve("test/testfile1.txt" as any); + } + if (file.toString().endsWith("testfile1.md")) { + return Promise.resolve("description in ${{TEST_ENV}}" as any); } else { throw new Error("not support " + file); } @@ -124,7 +127,7 @@ describe("expandVariableWithFunction", async () => { FILE_PATH: "testfile1.txt", [FeatureFlagName.EnvFileFunc]: "true", }); - const content = "description:\"$[ file('testfile1.md')]\"C://test"; + const content = "description:\"$[ file('testfile1.png')]\"C://test"; const res = await expandVariableWithFunction( content, context as any, diff --git a/packages/fx-core/tests/core/FxCore.test.ts b/packages/fx-core/tests/core/FxCore.test.ts index 403d2645a5..4806f74346 100644 --- a/packages/fx-core/tests/core/FxCore.test.ts +++ b/packages/fx-core/tests/core/FxCore.test.ts @@ -4,6 +4,7 @@ import { ErrorType, ListAPIResult, + ProjectType, SpecParser, SpecParserError, ValidationStatus, @@ -109,7 +110,7 @@ import { CoreHookContext } from "../../src/core/types"; import * as projectHelper from "../../src/common/projectSettingsHelper"; import * as migrationUtil from "../../src/core/middleware/utils/v3MigrationUtils"; import * as projMigrator from "../../src/core/middleware/projectMigratorV3"; -import { VersionSource, VersionState } from "../../src/common/versionMetadata"; +import { MetadataV3, VersionSource, VersionState } from "../../src/common/versionMetadata"; import * as pluginGeneratorHelper from "../../src/component/generator/apiSpec/helper"; import { SyncManifestDriver } from "../../src/component/driver/teamsApp/syncManifest"; import { ConstantString } from "../../src/common/constants"; @@ -4820,6 +4821,244 @@ describe("addPlugin", async () => { const core = new FxCore(tools); sandbox.stub(CopilotPluginHelper, "generateFromApiSpec").resolves(ok({ warnings: [] })); + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); + + const showMessageStub = sandbox + .stub(tools.ui, "showMessage") + .callsFake((level, message, modal, items) => { + if (level == "info") { + return Promise.resolve( + ok(getLocalizedString("core.addPlugin.success.viewPluginManifest")) + ); + } else if (level === "warn") { + return Promise.resolve(ok("Add")); + } else { + throw new NotImplementedError("TEST", "showMessage"); + } + }); + + const openFileStub = sandbox.stub(tools.ui, "openFile").resolves(); + + const result = await core.addPlugin(inputs); + if (result.isErr()) { + console.log(result.error); + } + assert.isTrue(result.isOk()); + assert.isTrue(showMessageStub.calledTwice); + assert.isTrue(openFileStub.calledOnce); + + if (await fs.pathExists(inputs.projectPath!)) { + await fs.remove(inputs.projectPath!); + } + }); + + it("from API spec: add action success with bearer token auth and teamsapp.local.yaml exist", async () => { + const appName = await mockV3Project(); + const inputs: Inputs = { + platform: Platform.VSCode, + [QuestionNames.Folder]: os.tmpdir(), + [QuestionNames.TeamsAppManifestFilePath]: "manifest.json", + [QuestionNames.ApiSpecLocation]: "test.yaml", + [QuestionNames.ApiOperation]: ["GET /user/{userId}"], + [QuestionNames.ApiPluginType]: ApiPluginStartOptions.apiSpec().id, + projectPath: path.join(os.tmpdir(), appName), + }; + const manifest = new TeamsAppManifest(); + manifest.copilotExtensions = { + declarativeCopilots: [ + { + file: "test1.json", + id: "action_1", + }, + ], + }; + sandbox.stub(validationUtils, "validateInputs").resolves(undefined); + sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(manifest)); + sandbox.stub(manifestUtils, "_writeAppManifest").resolves(ok(undefined)); + sandbox.stub(pluginGeneratorHelper, "generateScaffoldingSummary").resolves(""); + const writeFileStub = sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "readFile").resolves("{{test}}" as any); + sandbox.stub(fs, "pathExists").callsFake(async (path: string) => { + if (path.endsWith("openapi_1.yaml")) { + return true; + } + if (path.endsWith("ai-plugin_1.json")) { + return true; + } + if (path.endsWith("openapi_2.yaml")) { + return false; + } + if (path.endsWith("ai-plugin_2.json")) { + return false; + } + if (path.endsWith(MetadataV3.localConfigFile)) { + return true; + } + return true; + }); + sandbox + .stub(copilotGptManifestUtils, "readCopilotGptManifestFile") + .resolves(ok({} as DeclarativeCopilotManifestSchema)); + sandbox.stub(copilotGptManifestUtils, "getManifestPath").resolves(ok("dcManifest.json")); + sandbox + .stub(copilotGptManifestUtils, "addAction") + .resolves(ok({} as DeclarativeCopilotManifestSchema)); + + const core = new FxCore(tools); + sandbox.stub(CopilotPluginHelper, "generateFromApiSpec").resolves(ok({ warnings: [] })); + sandbox + .stub(CopilotPluginHelper, "injectAuthAction") + .resolves({ defaultRegistrationIdEnvName: "test", registrationIdEnvName: "test2" }); + + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + auth: { + name: "bearerAuth", + authScheme: { + type: "http", + scheme: "bearer", + }, + }, + }, + ], + allAPICount: 1, + validAPICount: 1, + }); + + const showMessageStub = sandbox + .stub(tools.ui, "showMessage") + .callsFake((level, message, modal, items) => { + if (level == "info") { + return Promise.resolve( + ok(getLocalizedString("core.addPlugin.success.viewPluginManifest")) + ); + } else if (level === "warn") { + return Promise.resolve(ok("Add")); + } else { + throw new NotImplementedError("TEST", "showMessage"); + } + }); + + const openFileStub = sandbox.stub(tools.ui, "openFile").resolves(); + + const result = await core.addPlugin(inputs); + if (result.isErr()) { + console.log(result.error); + } + assert.isTrue(result.isOk()); + assert.isTrue(showMessageStub.calledTwice); + assert.isTrue(openFileStub.calledOnce); + assert.equal(writeFileStub.args[0][1], "{{test2}}"); + + if (await fs.pathExists(inputs.projectPath!)) { + await fs.remove(inputs.projectPath!); + } + }); + + it("from API spec: add action success with oauth token auth and without teamsapp.local.yaml", async () => { + const appName = await mockV3Project(); + const inputs: Inputs = { + platform: Platform.VSCode, + [QuestionNames.Folder]: os.tmpdir(), + [QuestionNames.TeamsAppManifestFilePath]: "manifest.json", + [QuestionNames.ApiSpecLocation]: "test.yaml", + [QuestionNames.ApiOperation]: ["GET /user/{userId}"], + [QuestionNames.ApiPluginType]: ApiPluginStartOptions.apiSpec().id, + projectPath: path.join(os.tmpdir(), appName), + }; + const manifest = new TeamsAppManifest(); + manifest.copilotExtensions = { + declarativeCopilots: [ + { + file: "test1.json", + id: "action_1", + }, + ], + }; + sandbox.stub(validationUtils, "validateInputs").resolves(undefined); + sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(manifest)); + sandbox.stub(manifestUtils, "_writeAppManifest").resolves(ok(undefined)); + sandbox.stub(pluginGeneratorHelper, "generateScaffoldingSummary").resolves(""); + const writeFileStub = sandbox.stub(fs, "writeFile").resolves(); + sandbox.stub(fs, "readFile").resolves("{{test}}" as any); + sandbox.stub(fs, "pathExists").callsFake(async (path: string) => { + if (path.endsWith("openapi_1.yaml")) { + return true; + } + if (path.endsWith("ai-plugin_1.json")) { + return true; + } + if (path.endsWith("openapi_2.yaml")) { + return false; + } + if (path.endsWith("ai-plugin_2.json")) { + return false; + } + if (path.endsWith(MetadataV3.localConfigFile)) { + return false; + } + return true; + }); + sandbox + .stub(copilotGptManifestUtils, "readCopilotGptManifestFile") + .resolves(ok({} as DeclarativeCopilotManifestSchema)); + sandbox.stub(copilotGptManifestUtils, "getManifestPath").resolves(ok("dcManifest.json")); + sandbox + .stub(copilotGptManifestUtils, "addAction") + .resolves(ok({} as DeclarativeCopilotManifestSchema)); + + const core = new FxCore(tools); + sandbox.stub(CopilotPluginHelper, "generateFromApiSpec").resolves(ok({ warnings: [] })); + sandbox + .stub(CopilotPluginHelper, "injectAuthAction") + .resolves({ defaultRegistrationIdEnvName: "test", registrationIdEnvName: "test2" }); + + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + auth: { + name: "oauth2", + authScheme: { + type: "oauth2", + flows: { + authorizationCode: { + authorizationUrl: "https://example.com/auth", + tokenUrl: "https://example.com/token", + scopes: { + "user.read": "Read user profile", + }, + }, + }, + }, + }, + }, + ], + allAPICount: 1, + validAPICount: 1, + }); const showMessageStub = sandbox .stub(tools.ui, "showMessage") @@ -4844,6 +5083,7 @@ describe("addPlugin", async () => { assert.isTrue(result.isOk()); assert.isTrue(showMessageStub.calledTwice); assert.isTrue(openFileStub.calledOnce); + assert.equal(writeFileStub.args[0][1], "{{test2}}"); if (await fs.pathExists(inputs.projectPath!)) { await fs.remove(inputs.projectPath!); @@ -5033,6 +5273,19 @@ describe("addPlugin", async () => { const core = new FxCore(tools); sandbox.stub(CopilotPluginHelper, "generateFromApiSpec").resolves(ok({ warnings: [] })); + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); const showMessageStub = sandbox .stub(tools.ui, "showMessage") @@ -5109,6 +5362,19 @@ describe("addPlugin", async () => { sandbox .stub(copilotGptManifestUtils, "addAction") .resolves(ok({} as DeclarativeCopilotManifestSchema)); + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); const core = new FxCore(tools); sandbox @@ -5260,6 +5526,19 @@ describe("addPlugin", async () => { sandbox .stub(CopilotPluginHelper, "generateFromApiSpec") .resolves(err(new SystemError("", "", "", ""))); + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); const core = new FxCore(tools); const result = await core.addPlugin(inputs); assert.isTrue(result.isErr()); @@ -5285,6 +5564,19 @@ describe("addPlugin", async () => { }, ], }; + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); sandbox.stub(validationUtils, "validateInputs").resolves(undefined); sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(manifest)); sandbox.stub(manifestUtils, "_writeAppManifest").resolves(ok(undefined)); @@ -5470,6 +5762,19 @@ describe("addPlugin", async () => { }, ], }; + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); sandbox.stub(validationUtils, "validateInputs").resolves(undefined); sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(manifest)); sandbox.stub(copilotGptManifestUtils, "getManifestPath").resolves(ok("dcManifest.json")); @@ -5508,6 +5813,19 @@ describe("addPlugin", async () => { }, ], }; + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); sandbox.stub(validationUtils, "validateInputs").resolves(undefined); sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(manifest)); sandbox @@ -5528,6 +5846,160 @@ describe("addPlugin", async () => { } }); + it("call kiota: success redirect to Kiota", async () => { + const mockedEnvRestore = mockedEnv({ + [FeatureFlagName.KiotaIntegration]: "true", + }); + + const appName = await mockV3Project(); + const inputs: Inputs = { + platform: Platform.VSCode, + [QuestionNames.Folder]: os.tmpdir(), + [QuestionNames.ApiPluginType]: ApiPluginStartOptions.apiSpec().id, + [QuestionNames.TeamsAppManifestFilePath]: "manifest.json", + projectPath: path.join(os.tmpdir(), appName), + }; + + const core = new FxCore(tools); + + const result = await core.addPlugin(inputs); + assert.isTrue(result.isOk()); + if (result.isOk()) { + assert.equal(result.value.lastCommand, "addPlugin"); + assert.equal(result.value.manifestPath, "manifest.json"); + } + + mockedEnvRestore(); + }); + + it("call kiota: success create project with input", async () => { + const mockedEnvRestore = mockedEnv({ + [FeatureFlagName.KiotaIntegration]: "true", + }); + + const appName = await mockV3Project(); + const inputs: Inputs = { + platform: Platform.VSCode, + [QuestionNames.Folder]: os.tmpdir(), + [QuestionNames.ApiPluginType]: ApiPluginStartOptions.apiSpec().id, + [QuestionNames.TeamsAppManifestFilePath]: "manifest.json", + [QuestionNames.ApiPluginManifestPath]: "aiplugin-apiplugin.json", + [QuestionNames.ApiSpecLocation]: "spec-apimanifest.yaml", + [QuestionNames.ApiOperation]: "aiplugin-apiplugin.json", + projectPath: path.join(os.tmpdir(), appName), + }; + + const manifest = new TeamsAppManifest(); + manifest.copilotExtensions = { + declarativeCopilots: [ + { + file: "test1.json", + id: "action_1", + }, + ], + }; + sandbox.stub(SpecParser.prototype, "list").resolves({ + APIs: [ + { + api: "GET /user/{userId}", + server: "https://example.com", + operationId: "getExample", + isValid: true, + reason: [], + }, + ], + allAPICount: 1, + validAPICount: 1, + }); + sandbox.stub(validationUtils, "validateInputs").resolves(undefined); + sandbox.stub(manifestUtils, "_readAppManifest").resolves(ok(manifest)); + sandbox.stub(manifestUtils, "_writeAppManifest").resolves(ok(undefined)); + sandbox.stub(pluginGeneratorHelper, "generateScaffoldingSummary").resolves(""); + sandbox.stub(fs, "pathExists").callsFake(async (path: string) => { + if (path.endsWith("openapi_1.yaml")) { + return true; + } + if (path.endsWith("ai-plugin_1.json")) { + return true; + } + if (path.endsWith("openapi_2.yaml")) { + return false; + } + if (path.endsWith("ai-plugin_2.json")) { + return false; + } + if (path.endsWith("aiplugin-apiplugin.json")) { + return true; + } + if (path.endsWith("spec-apimanifest.yaml")) { + return true; + } + if (path.endsWith("aiplugin_1-apiplugin.json")) { + return false; + } + if (path.endsWith("spec_1-apimanifest.yaml")) { + return false; + } + return true; + }); + sandbox + .stub(copilotGptManifestUtils, "readCopilotGptManifestFile") + .resolves(ok({} as DeclarativeCopilotManifestSchema)); + sandbox.stub(copilotGptManifestUtils, "getManifestPath").resolves(ok("dcManifest.json")); + sandbox + .stub(copilotGptManifestUtils, "addAction") + .resolves(ok({} as DeclarativeCopilotManifestSchema)); + + const core = new FxCore(tools); + sandbox + .stub(CopilotPluginHelper, "generateFromApiSpec") + .callsFake( + async ( + specParser, + teamsManifestPath, + inputs, + context, + component, + projectType, + outputFilePath + ) => { + assert.isTrue(outputFilePath.destinationApiSpecFilePath.includes("apimanifest.yaml")); + assert.isTrue(outputFilePath.pluginManifestFilePath?.includes("apiplugin.json")); + return ok({ warnings: [] }); + } + ); + + const showMessageStub = sandbox + .stub(tools.ui, "showMessage") + .callsFake((level, message, modal, items) => { + if (level == "info") { + return Promise.resolve( + ok(getLocalizedString("core.addPlugin.success.viewPluginManifest")) + ); + } else if (level === "warn") { + return Promise.resolve(ok("Add")); + } else { + throw new NotImplementedError("TEST", "showMessage"); + } + }); + + const openFileStub = sandbox.stub(tools.ui, "openFile").resolves(); + + const result = await core.addPlugin(inputs); + if (result.isErr()) { + console.log(result.error); + } + assert.isTrue(result.isOk()); + assert.isTrue(showMessageStub.calledTwice); + assert.isTrue(openFileStub.calledOnce); + + if (await fs.pathExists(inputs.projectPath!)) { + await fs.remove(inputs.projectPath!); + } + + mockedEnvRestore(); + }); + describe("projectVersionCheck", async () => { it("invalid project", async () => { sandbox.stub(projectHelper, "isValidProjectV3").returns(false); diff --git a/packages/fx-core/tests/core/collaborator.test.ts b/packages/fx-core/tests/core/collaborator.test.ts index c3c5d4d9da..68f8a0d28f 100644 --- a/packages/fx-core/tests/core/collaborator.test.ts +++ b/packages/fx-core/tests/core/collaborator.test.ts @@ -28,12 +28,8 @@ import { listCollaborator, } from "../../src/core/collaborator"; import { QuestionNames } from "../../src/question"; -import { - MockedAzureAccountProvider, - MockedM365Provider, - MockedV2Context, -} from "../plugins/solution/util"; -import { randomAppName } from "./utils"; +import { MockedV2Context } from "../plugins/solution/util"; +import { MockedAzureAccountProvider, MockedM365Provider, randomAppName } from "./utils"; describe("Collaborator APIs for V3", () => { const sandbox = sinon.createSandbox(); diff --git a/packages/fx-core/tests/core/other.test.ts b/packages/fx-core/tests/core/other.test.ts index 5a1bbe23a8..91e14c5f9c 100644 --- a/packages/fx-core/tests/core/other.test.ts +++ b/packages/fx-core/tests/core/other.test.ts @@ -19,69 +19,8 @@ import { isValidProjectV3, } from "../../src/common/projectSettingsHelper"; import { cpUtils } from "../../src/component/utils/depsChecker/cpUtils"; -import { MyTokenCredential } from "../plugins/solution/util"; import { randomAppName } from "./utils"; -export class MockedAzureTokenProvider implements AzureAccountProvider { - getIdentityCredentialAsync(showDialog?: boolean): Promise { - return Promise.resolve(new MyTokenCredential()); - } - signout(): Promise { - throw new Error("Method not implemented."); - } - setStatusChangeCallback( - statusChange: ( - status: string, - token?: string, - accountInfo?: Record - ) => Promise - ): Promise { - throw new Error("Method not implemented."); - } - setStatusChangeMap( - name: string, - statusChange: ( - status: string, - token?: string, - accountInfo?: Record - ) => Promise, - immediateCall?: boolean - ): Promise { - throw new Error("Method not implemented."); - } - removeStatusChangeMap(name: string): Promise { - throw new Error("Method not implemented."); - } - async getJsonObject(showDialog?: boolean): Promise> { - return { - tid: "222", - }; - } - async listSubscriptions(): Promise { - return [ - { - subscriptionName: "mockedSubscriptionName", - subscriptionId: "subscriptionId", - tenantId: "mockedTenantId", - }, - ]; - } - async setSubscription(subscriptionId: string): Promise { - return; - } - getAccountInfo(): Record | undefined { - return {}; - } - getSelectedSubscription(): Promise { - const selectedSub = { - subscriptionId: "subscriptionId", - tenantId: "tenantId", - subscriptionName: "subscriptionName", - }; - return Promise.resolve(selectedSub); - } -} - describe("Other test case", () => { const sandbox = sinon.createSandbox(); diff --git a/packages/fx-core/tests/core/utils.ts b/packages/fx-core/tests/core/utils.ts index 5122adc1c1..dcd724277e 100644 --- a/packages/fx-core/tests/core/utils.ts +++ b/packages/fx-core/tests/core/utils.ts @@ -38,105 +38,93 @@ import { UserInteraction, } from "@microsoft/teamsfx-api"; import fs from "fs-extra"; -import { MyTokenCredential } from "../plugins/solution/util"; +import { AccessToken, GetTokenOptions } from "@azure/identity"; export function randomAppName() { return "mock" + new Date().getTime(); } -export class MockAzureAccountProvider implements AzureAccountProvider { - async getIdentityCredentialAsync(): Promise { - return new MyTokenCredential(); +export class MyTokenCredential implements TokenCredential { + public async getToken( + scopes: string | string[], + options?: GetTokenOptions + ): Promise { + return { + token: "a.eyJ1c2VySWQiOiJ0ZXN0QHRlc3QuY29tIn0=.c", + expiresOnTimestamp: 1234, + }; } +} - signout(): Promise { - throw new Error("Method not implemented."); +export class MockedAzureAccountProvider implements AzureAccountProvider { + async getIdentityCredentialAsync(showDialog?: boolean): Promise { + return new MyTokenCredential(); } - setStatusChangeMap( + async signout(): Promise { + return true; + } + async switchTenant(tenantId: string): Promise> { + return ok(new MyTokenCredential()); + } + async setStatusChangeMap( name: string, statusChange: ( status: string, token?: string, accountInfo?: Record - ) => Promise + ) => Promise, + immediateCall?: boolean ): Promise { - throw new Error("Method not implemented."); + return true; } - - removeStatusChangeMap(name: string): Promise { - throw new Error("Method not implemented."); + async removeStatusChangeMap(name: string): Promise { + return true; } - async getJsonObject(showDialog?: boolean): Promise> { - return { - unique_name: "test", - }; - } - - listSubscriptions(): Promise { - throw new Error("Method not implemented."); + return {}; } - - setSubscription(subscriptionId: string): Promise { - throw new Error("Method not implemented."); + async listSubscriptions(): Promise { + return []; } - + async setSubscription(subscriptionId: string): Promise {} getAccountInfo(): Record { - throw new Error("Method not implemented."); - } - - getSelectedSubscription(): Promise { - throw new Error("Method not implemented."); + return {}; } - - selectSubscription(subscriptionId?: string): Promise { - throw new Error("Method not implemented."); + async getSelectedSubscription(triggerUI?: boolean): Promise { + return { + subscriptionId: "", + subscriptionName: "", + tenantId: "", + }; } } -export class MockM365TokenProvider implements M365TokenProvider { - /** - * Get M365 access token - * @param tokenRequest permission scopes or show user interactive UX - */ - getAccessToken(tokenRequest: TokenRequest): Promise> { - throw new Error("Method not implemented."); +export class MockedM365Provider implements M365TokenProvider { + async getAccessToken(tokenRequest: TokenRequest): Promise> { + return ok("fakeToken"); } - - /** - * Get M365 token Json object - * - tid : tenantId - * - unique_name : user name - * - ... - * @param tokenRequest permission scopes or show user interactive UX - */ - getJsonObject(tokenRequest: TokenRequest): Promise, FxError>> { - throw new Error("Method not implemented."); + async getJsonObject( + tokenRequest: TokenRequest + ): Promise, FxError>> { + return ok({ + upn: "fakeUserPrincipalName@fake.com", + tid: "tenantId", + }); } - - /** - * Get user login status - * @param tokenRequest permission scopes or show user interactive UX - */ - getStatus(tokenRequest: TokenRequest): Promise> { - throw new Error("Method not implemented."); - } - /** - * m365 sign out - */ - signout(): Promise { - throw new Error("Method not implemented."); + async signout(): Promise { + return true; } - - /** - * Add update account info callback - * @param name callback name - * @param tokenRequest permission scopes - * @param statusChange callback method - * @param immediateCall whether callback when register, the default value is true - */ - setStatusChangeMap( + async switchTenant(tenantId: string): Promise> { + return ok("fakeToken"); + } + async getStatus(tokenRequest: TokenRequest): Promise> { + return ok({ + status: "SignedIn", + token: "fakeToken", + }); + } + async setStatusChangeMap( name: string, tokenRequest: TokenRequest, statusChange: ( @@ -146,15 +134,10 @@ export class MockM365TokenProvider implements M365TokenProvider { ) => Promise, immediateCall?: boolean ): Promise> { - throw new Error("Method not implemented."); + return ok(true); } - - /** - * Remove update account info callback - * @param name callback name - */ - removeStatusChangeMap(name: string): Promise> { - throw new Error("Method not implemented."); + async removeStatusChangeMap(name: string): Promise> { + return ok(true); } } @@ -274,8 +257,8 @@ export class MockUserInteraction implements UserInteraction { export class MockTools implements Tools { logProvider = new MockLogProvider(); tokenProvider: TokenProvider = { - azureAccountProvider: new MockAzureAccountProvider(), - m365TokenProvider: new MockM365TokenProvider(), + azureAccountProvider: new MockedAzureAccountProvider(), + m365TokenProvider: new MockedM365Provider(), }; telemetryReporter = new MockTelemetryReporter(); ui = new MockUserInteraction(); diff --git a/packages/fx-core/tests/plugins/resource/appstudio/helper.ts b/packages/fx-core/tests/plugins/resource/appstudio/helper.ts index 161a22cffa..56c6c577f6 100644 --- a/packages/fx-core/tests/plugins/resource/appstudio/helper.ts +++ b/packages/fx-core/tests/plugins/resource/appstudio/helper.ts @@ -122,6 +122,9 @@ export class MockedM365TokenProvider implements M365TokenProvider { removeStatusChangeMap(name: string): Promise> { throw new Error("Method not implemented."); } + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } } export class MockedM365TokenProviderFail implements M365TokenProvider { @@ -154,6 +157,9 @@ export class MockedM365TokenProviderFail implements M365TokenProvider { removeStatusChangeMap(name: string): Promise> { throw new Error("Method not implemented."); } + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } } export function getAzureProjectRoot(): string { diff --git a/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/resources/de.invalid.json b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/resources/de.invalid.json new file mode 100644 index 0000000000..88eaec1b1e --- /dev/null +++ b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/resources/de.invalid.json @@ -0,0 +1,8 @@ +{ + "$schema": "https://developer.microsoft.com/json-schemas/teams/v1.12/MicrosoftTeams.Localization.schema.json", + "name.short": "Name App", + "name.full": "Name App", + "description.short.fake": "Description Short Deutsch", + "description.full.fake": "Description Long Deutsch", + "staticTabs[0].name": "Home" +} \ No newline at end of file diff --git a/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/resources/en.invalid.json b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/resources/en.invalid.json new file mode 100644 index 0000000000..88eaec1b1e --- /dev/null +++ b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/resources/en.invalid.json @@ -0,0 +1,8 @@ +{ + "$schema": "https://developer.microsoft.com/json-schemas/teams/v1.12/MicrosoftTeams.Localization.schema.json", + "name.short": "Name App", + "name.full": "Name App", + "description.short.fake": "Description Short Deutsch", + "description.full.fake": "Description Long Deutsch", + "staticTabs[0].name": "Home" +} \ No newline at end of file diff --git a/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.default.localization.manifest.json b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.default.localization.manifest.json new file mode 100644 index 0000000000..74526e4142 --- /dev/null +++ b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.default.localization.manifest.json @@ -0,0 +1,36 @@ +{ + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + "id": "${{ TEAMS_APP_ID }}", + "developer": { + "name": "Teams App, Inc.", + "websiteUrl": "https://www.example.com", + "privacyUrl": "https://www.example.com/termofuse", + "termsOfUseUrl": "https://www.example.com/privacy" + }, + "icons": { + "color": "resources/color.png", + "outline": "resources/outline.png" + }, + "name": { + "short": "${{ CONFIG_TEAMS_APP_NAME }}", + "full": "${{ CONFIG_TEAMS_APP_NAME }}" + }, + "description": { + "short": "Short description of ${{ CONFIG_TEAMS_APP_NAME }}", + "full": "Full description of ${{ CONFIG_TEAMS_APP_NAME }}" + }, + "accentColor": "#FFFFFF", + "composeExtensions": [], + "staticTabs": [], + "permissions": [ + "identity", + "messageTeamMembers" + ], + "validDomains": [], + "localizationInfo": { + "defaultLanguageTag": "en", + "defaultLanguageFile": "resources/en.invalid.json" + } +} \ No newline at end of file diff --git a/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.localization.manifest.json b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.localization.manifest.json new file mode 100644 index 0000000000..c51ccc18f3 --- /dev/null +++ b/packages/fx-core/tests/plugins/resource/appstudio/resources-multi-env/templates/appPackage/v3.invalid.localization.manifest.json @@ -0,0 +1,42 @@ +{ + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.14/MicrosoftTeams.schema.json", + "manifestVersion": "1.14", + "version": "1.0.0", + "id": "${{ TEAMS_APP_ID }}", + "packageName": "com.microsoft.teams.extension", + "developer": { + "name": "Teams App, Inc.", + "websiteUrl": "https://www.example.com", + "privacyUrl": "https://www.example.com/termofuse", + "termsOfUseUrl": "https://www.example.com/privacy" + }, + "icons": { + "color": "resources/color.png", + "outline": "resources/outline.png" + }, + "name": { + "short": "${{ CONFIG_TEAMS_APP_NAME }}", + "full": "${{ CONFIG_TEAMS_APP_NAME }}" + }, + "description": { + "short": "Short description of ${{ CONFIG_TEAMS_APP_NAME }}", + "full": "Full description of ${{ CONFIG_TEAMS_APP_NAME }}" + }, + "accentColor": "#FFFFFF", + "composeExtensions": [], + "staticTabs": [], + "permissions": [ + "identity", + "messageTeamMembers" + ], + "validDomains": [], + "localizationInfo": { + "defaultLanguageTag": "en", + "additionalLanguages": [ + { + "languageTag": "de", + "file": "resources/de.invalid.json" + } + ] + } +} \ No newline at end of file diff --git a/packages/fx-core/tests/plugins/solution/util.ts b/packages/fx-core/tests/plugins/solution/util.ts index 0eabedd7bc..27d81231d6 100644 --- a/packages/fx-core/tests/plugins/solution/util.ts +++ b/packages/fx-core/tests/plugins/solution/util.ts @@ -1,7 +1,4 @@ -import { TokenCredential } from "@azure/core-auth"; -import { AccessToken, GetTokenOptions } from "@azure/identity"; import { - AzureAccountProvider, Colors, ConfirmConfig, ConfirmResult, @@ -14,8 +11,6 @@ import { InputTextResult, LogLevel, LogProvider, - LoginStatus, - M365TokenProvider, MultiSelectConfig, MultiSelectResult, Result, @@ -28,24 +23,11 @@ import { SingleFileOrInputConfig, SingleSelectConfig, SingleSelectResult, - SubscriptionInfo, TelemetryReporter, - TokenRequest, UserInteraction, ok, } from "@microsoft/teamsfx-api"; -export class MyTokenCredential implements TokenCredential { - public async getToken( - scopes: string | string[], - options?: GetTokenOptions - ): Promise { - return { - token: "a.eyJ1c2VySWQiOiJ0ZXN0QHRlc3QuY29tIn0=.c", - expiresOnTimestamp: 1234, - }; - } -} export class MockedLogProvider implements LogProvider { msg = ""; verbose(msg: string): void { @@ -191,82 +173,3 @@ export class MockedV2Context implements Context { this.telemetryReporter = new MockedTelemetryReporter(); } } - -export class MockedM365Provider implements M365TokenProvider { - async getAccessToken(tokenRequest: TokenRequest): Promise> { - return ok("fakeToken"); - } - async getJsonObject( - tokenRequest: TokenRequest - ): Promise, FxError>> { - return ok({ - upn: "fakeUserPrincipalName@fake.com", - tid: "tenantId", - }); - } - async signout(): Promise { - return true; - } - async getStatus(tokenRequest: TokenRequest): Promise> { - return ok({ - status: "SignedIn", - token: "fakeToken", - }); - } - async setStatusChangeMap( - name: string, - tokenRequest: TokenRequest, - statusChange: ( - status: string, - token?: string, - accountInfo?: Record - ) => Promise, - immediateCall?: boolean - ): Promise> { - return ok(true); - } - async removeStatusChangeMap(name: string): Promise> { - return ok(true); - } -} - -export class MockedAzureAccountProvider implements AzureAccountProvider { - async getIdentityCredentialAsync(showDialog?: boolean): Promise { - return new MyTokenCredential(); - } - - async signout(): Promise { - return true; - } - async setStatusChangeMap( - name: string, - statusChange: ( - status: string, - token?: string, - accountInfo?: Record - ) => Promise, - immediateCall?: boolean - ): Promise { - return true; - } - async removeStatusChangeMap(name: string): Promise { - return true; - } - async getJsonObject(showDialog?: boolean): Promise> { - return {}; - } - async listSubscriptions(): Promise { - return []; - } - async setSubscription(subscriptionId: string): Promise {} - getAccountInfo(): Record { - return {}; - } - async getSelectedSubscription(triggerUI?: boolean): Promise { - return { - subscriptionId: "", - subscriptionName: "", - tenantId: "", - }; - } -} diff --git a/packages/fx-core/tests/question/question.test.ts b/packages/fx-core/tests/question/question.test.ts index 32b815a30c..3e3352463a 100644 --- a/packages/fx-core/tests/question/question.test.ts +++ b/packages/fx-core/tests/question/question.test.ts @@ -54,9 +54,9 @@ import { selectTeamsAppManifestQuestion, } from "../../src/question/other"; import { QuestionTreeVisitor, traverse } from "../../src/ui/visitor"; -import { MockedAzureTokenProvider } from "../core/other.test"; -import { MockTools, MockUserInteraction } from "../core/utils"; +import { MockedAzureAccountProvider, MockTools, MockUserInteraction } from "../core/utils"; import { callFuncs } from "./create.test"; +import { TokenCredential } from "@azure/identity"; const ui = new MockUserInteraction(); @@ -713,9 +713,12 @@ describe("resourceGroupQuestionNode", async () => { sandbox.stub(resourceGroupHelper, "getLocations").resolves(ok(["East US", "Center US"])); const mockSubscriptionId = "mockSub"; const defaultRG = "defaultRG"; - const accountProvider = new MockedAzureTokenProvider(); + const accountProvider = new MockedAzureAccountProvider(); const mockToken = await accountProvider.getIdentityCredentialAsync(); - const mockRmClient = new ResourceManagementClient(mockToken, mockSubscriptionId); + const mockRmClient = new ResourceManagementClient( + mockToken as TokenCredential, + mockSubscriptionId + ); sandbox.stub(resourceGroupHelper, "createRmClient").resolves(mockRmClient); const node = resourceGroupQuestionNode(accountProvider, mockSubscriptionId, defaultRG); assert.isTrue(node !== undefined); @@ -763,9 +766,12 @@ describe("resourceGroupQuestionNode", async () => { ); const mockSubscriptionId = "mockSub"; const defaultRG = "defaultRG"; - const accountProvider = new MockedAzureTokenProvider(); + const accountProvider = new MockedAzureAccountProvider(); const mockToken = await accountProvider.getIdentityCredentialAsync(); - const mockRmClient = new ResourceManagementClient(mockToken, mockSubscriptionId); + const mockRmClient = new ResourceManagementClient( + mockToken as TokenCredential, + mockSubscriptionId + ); sandbox.stub(resourceGroupHelper, "createRmClient").resolves(mockRmClient); const node = resourceGroupQuestionNode(accountProvider, mockSubscriptionId, defaultRG); assert.isTrue(node !== undefined); diff --git a/packages/manifest/src/index.ts b/packages/manifest/src/index.ts index a522b4e6fa..011749c7d7 100644 --- a/packages/manifest/src/index.ts +++ b/packages/manifest/src/index.ts @@ -74,14 +74,23 @@ export class ManifestUtil { addFormats(ajv, ["uri", "email", "regex"]); validate = ajv.compile(schema); } else { - const ajv = new Ajv({ formats: { uri: true }, allErrors: true, strictTypes: false }); + const ajv = new Ajv({ + allErrors: true, + strictTypes: false, + }); + addFormats(ajv, ["uri", "email", "regex"]); validate = ajv.compile(schema); } const valid = validate(manifest); if (!valid && validate.errors) { return Promise.resolve( - validate.errors?.map((error) => `${error.instancePath} ${error.message || ""}`) + validate.errors?.map( + (error) => + `${error.instancePath} ${error.message || ""}. Details: ${ + error.params ? JSON.stringify(error.params) : "" + }` + ) ); } else { return Promise.resolve([]); diff --git a/packages/sdk/README.md b/packages/sdk/README.md index 96db8ac874..7591c765da 100644 --- a/packages/sdk/README.md +++ b/packages/sdk/README.md @@ -648,7 +648,24 @@ From `botbuilder@4.16.0`, `BotFrameworkAdapter` is deprecated, and `CloudAdapter }); ``` -4. If the project has `responseWrapper.ts`, please update the class `responseWrapper` to the class below. +4. If the project is using `express` to create a server, please add the following line after `express()`. + + ```ts + expressApp.use(express.json()); + ``` + + The complete code will be like + + ```ts + // Create HTTP server. + const expressApp = express(); + expressApp.use(express.json()); + const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); + }); + ``` + +5. If the project has `responseWrapper.ts`, please update the class `responseWrapper` to the class below. ```ts import { Response } from "botbuilder"; diff --git a/packages/sdk/src/conversationWithCloudAdapter/conversation.ts b/packages/sdk/src/conversationWithCloudAdapter/conversation.ts index c492690496..58e3e35162 100644 --- a/packages/sdk/src/conversationWithCloudAdapter/conversation.ts +++ b/packages/sdk/src/conversationWithCloudAdapter/conversation.ts @@ -185,15 +185,17 @@ export class ConversationBot { * @param logic - The additional function to handle bot context. * * @example - * For example, to use with Restify: + * For example, to use with Express: * ``` typescript * // The default/empty behavior - * server.use(restify.plugins.bodyParser()); - * server.post("api/messages", conversationBot.requestHandler); + * const expressApp = express(); + * expressApp.use(express.json()); + * expressApp.post("/api/notification", conversationBot.requestHandler); * * // Or, add your own logic - * server.use(restify.plugins.bodyParser()); - * server.post("api/messages", async (req, res) => { + * const expressApp = express(); + * expressApp.use(express.json()); + * expressApp.post("/api/notification", async (req, res) => { * await conversationBot.requestHandler(req, res, async (context) => { * // your-own-context-logic * }); diff --git a/packages/server/src/providers/token/azure.ts b/packages/server/src/providers/token/azure.ts index 9b28ffba4b..261400fafe 100644 --- a/packages/server/src/providers/token/azure.ts +++ b/packages/server/src/providers/token/azure.ts @@ -4,7 +4,13 @@ import { MessageConnection } from "vscode-jsonrpc"; import { TokenCredential } from "@azure/core-auth"; -import { AzureAccountProvider, SubscriptionInfo, TokenRequest } from "@microsoft/teamsfx-api"; +import { + AzureAccountProvider, + FxError, + Result, + SubscriptionInfo, + TokenRequest, +} from "@microsoft/teamsfx-api"; import { RequestTypes } from "../../apis"; import { getResponseWithErrorHandling } from "../../utils"; @@ -91,6 +97,10 @@ export default class ServerAzureAccountProvider implements AzureAccountProvider return JSON.parse(result.value); } + switchTenant(tenantId: string): Promise> { + throw new NotImplementedError("FxServer", `azure/switchTenant`); + } + async listSubscriptions(): Promise { const promise = this.connection.sendRequest(RequestTypes.azure.listSubscriptions); const result = await getResponseWithErrorHandling(promise); diff --git a/packages/server/src/providers/token/m365.ts b/packages/server/src/providers/token/m365.ts index 4594b0ac67..7e269f469c 100644 --- a/packages/server/src/providers/token/m365.ts +++ b/packages/server/src/providers/token/m365.ts @@ -57,6 +57,10 @@ export default class ServerM365TokenProvider implements M365TokenProvider { throw new NotImplementedError("FxServer", `m365/signout`); } + switchTenant(tenantId: string): Promise> { + throw new NotImplementedError("FxServer", `m365/switchTenant`); + } + setStatusChangeMap( name: string, tokenRequest: TokenRequest, diff --git a/packages/server/tests/providers/token/azure.test.ts b/packages/server/tests/providers/token/azure.test.ts index 1bbe2cb0fd..c80453c5c5 100644 --- a/packages/server/tests/providers/token/azure.test.ts +++ b/packages/server/tests/providers/token/azure.test.ts @@ -89,6 +89,11 @@ describe("azure", () => { chai.expect(() => azure.removeStatusChangeMap("test")).to.throw(NotImplementedError); }); + it("switchTenant", () => { + const azure = new ServerAzureAccountProvider(msgConn); + chai.expect(() => azure.switchTenant("")).to.throw(); + }); + describe("getJsonObject", () => { const azure = new ServerAzureAccountProvider(msgConn); diff --git a/packages/server/tests/providers/token/m365.test.ts b/packages/server/tests/providers/token/m365.test.ts index e3815d2b33..c396b61f51 100644 --- a/packages/server/tests/providers/token/m365.test.ts +++ b/packages/server/tests/providers/token/m365.test.ts @@ -125,5 +125,9 @@ describe("m365", () => { it("removeStatusChangeMap", async () => { chai.expect(() => appStudio.removeStatusChangeMap("test")).to.throw(NotImplementedError); }); + + it("switchTenant", async () => { + chai.expect(() => appStudio.switchTenant("")).to.throw(NotImplementedError); + }); }); }); diff --git a/packages/spec-parser/src/adaptiveCardGenerator.ts b/packages/spec-parser/src/adaptiveCardGenerator.ts index 5059fadfc4..1187b71d5b 100644 --- a/packages/spec-parser/src/adaptiveCardGenerator.ts +++ b/packages/spec-parser/src/adaptiveCardGenerator.ts @@ -10,29 +10,50 @@ import { ErrorType, ImageElement, TextBlockElement, + WarningResult, + WarningType, } from "./interfaces"; import { ConstantString } from "./constants"; import { SpecParserError } from "./specParserError"; +import { JsonDataGenerator } from "./jsonDataGenerator"; export class AdaptiveCardGenerator { static generateAdaptiveCard( operationItem: OpenAPIV3.OperationObject, - allowMultipleMediaType = false - ): [AdaptiveCard, string] { + allowMultipleMediaType = false, + maxElementCount: number = Number.MAX_SAFE_INTEGER + ): [AdaptiveCard, string, any, WarningResult[]] { try { const { json } = Utils.getResponseJson(operationItem, allowMultipleMediaType); let cardBody: Array = []; + let jsonData: any = {}; + const warnings: WarningResult[] = []; + const operationId = operationItem.operationId!; let schema = json.schema as OpenAPIV3.SchemaObject; let jsonPath = "$"; if (schema && Object.keys(schema).length > 0) { + try { + jsonData = JsonDataGenerator.generate(schema); + } catch (err) { + warnings.push({ + type: WarningType.GenerateJsonDataFailed, + content: Utils.format( + ConstantString.GenerateJsonDataFailed, + operationId, + (err as Error).toString() + ), + data: operationId, + }); + } + jsonPath = AdaptiveCardGenerator.getResponseJsonPathFromSchema(schema); if (jsonPath !== "$") { schema = schema.properties![jsonPath] as OpenAPIV3.SchemaObject; } - cardBody = AdaptiveCardGenerator.generateCardFromResponse(schema, ""); + cardBody = AdaptiveCardGenerator.generateCardFromResponse(schema, "", "", maxElementCount); } // if no schema, try to use example value @@ -64,7 +85,7 @@ export class AdaptiveCardGenerator { body: cardBody, }; - return [fullCard, jsonPath]; + return [fullCard, jsonPath, jsonData, warnings]; } catch (err) { throw new SpecParserError((err as Error).toString(), ErrorType.GenerateAdaptiveCardFailed); } @@ -73,11 +94,17 @@ export class AdaptiveCardGenerator { static generateCardFromResponse( schema: OpenAPIV3.SchemaObject, name: string, - parentArrayName = "" + parentArrayName = "", + maxElementCount = Number.MAX_SAFE_INTEGER, + counter: { count: number } = { count: 0 } ): Array { + if (counter.count >= maxElementCount) { + return []; + } if (schema.type === "array") { // schema.items can be arbitrary object: schema { type: array, items: {} } if (Object.keys(schema.items).length === 0) { + counter.count++; return [ { type: ConstantString.TextBlockType, @@ -90,8 +117,11 @@ export class AdaptiveCardGenerator { const obj = AdaptiveCardGenerator.generateCardFromResponse( schema.items as OpenAPIV3.SchemaObject, "", - name + name, + maxElementCount, + counter ); + const template = { type: ConstantString.ContainerType, $data: name ? `\${${name}}` : "${$root}", @@ -101,6 +131,7 @@ export class AdaptiveCardGenerator { template.items.push(...obj); return [template]; } + // some schema may not contain type but contain properties if (Utils.isObjectSchema(schema)) { const { properties } = schema; @@ -109,7 +140,9 @@ export class AdaptiveCardGenerator { const obj = AdaptiveCardGenerator.generateCardFromResponse( properties[property] as OpenAPIV3.SchemaObject, name ? `${name}.${property}` : property, - parentArrayName + parentArrayName, + maxElementCount, + counter ); result.push(...obj); } @@ -127,6 +160,7 @@ export class AdaptiveCardGenerator { schema.type === "boolean" || schema.type === "number" ) { + counter.count++; if (!AdaptiveCardGenerator.isImageUrlProperty(schema, name, parentArrayName)) { // string in root: "ddd" let text = "result: ${$root}"; @@ -150,23 +184,18 @@ export class AdaptiveCardGenerator { }, ]; } else { - if (name) { - return [ - { - type: "Image", - url: `\${${name}}`, - $when: `\${${name} != null && ${name} != ''}`, - }, - ]; - } else { - return [ - { - type: "Image", - url: "${$data}", - $when: "${$data != null && $data != ''}", - }, - ]; - } + const url = name ? `\${${name}}` : "${$data}"; + const condition = name + ? `\${${name} != null && ${name} != ''}` + : "${$data != null && $data != ''}"; + + return [ + { + type: "Image", + url, + $when: condition, + }, + ]; } } diff --git a/packages/spec-parser/src/constants.ts b/packages/spec-parser/src/constants.ts index 7d9ee5732a..94435299de 100644 --- a/packages/spec-parser/src/constants.ts +++ b/packages/spec-parser/src/constants.ts @@ -37,10 +37,15 @@ export class ConstantString { static readonly MultipleAuthNotSupported = "Multiple authentication methods are unsupported. Ensure all selected APIs use identical authentication."; + static readonly OperationIdContainsSpecialCharacters = + "Operation id '%s' in OpenAPI description document contained special characters and was renamed to '%s'."; + static readonly UnsupportedSchema = "Unsupported schema in %s %s: %s"; static readonly FuncDescriptionTooLong = "The description of the function '%s' is too long. The current length is %s characters, while the maximum allowed length is %s characters."; + static readonly GenerateJsonDataFailed = "Failed to generate JSON data for api: %s due to %s."; + static readonly WrappedCardVersion = "devPreview"; static readonly WrappedCardSchema = "https://developer.microsoft.com/json-schemas/teams/vDevPreview/MicrosoftTeams.ResponseRenderingTemplate.schema.json"; diff --git a/packages/spec-parser/src/interfaces.ts b/packages/spec-parser/src/interfaces.ts index cdba1ac97b..abbda16998 100644 --- a/packages/spec-parser/src/interfaces.ts +++ b/packages/spec-parser/src/interfaces.ts @@ -140,6 +140,8 @@ export enum WarningType { OperationOnlyContainsOptionalParam = "operation-only-contains-optional-param", ConvertSwaggerToOpenAPI = "convert-swagger-to-openapi", FuncDescriptionTooLong = "function-description-too-long", + OperationIdContainsSpecialCharacters = "operationid-contains-special-characters", + GenerateJsonDataFailed = "generate-json-data-failed", Unknown = "unknown", } diff --git a/packages/spec-parser/src/jsonDataGenerator.ts b/packages/spec-parser/src/jsonDataGenerator.ts new file mode 100644 index 0000000000..6fd482f814 --- /dev/null +++ b/packages/spec-parser/src/jsonDataGenerator.ts @@ -0,0 +1,123 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. +"use strict"; + +import { OpenAPIV3 } from "openapi-types"; + +export class JsonDataGenerator { + private static visitedSchemas = new Set(); + + static generate(schema: OpenAPIV3.SchemaObject): any { + return this.generateMockData(schema); + } + + static generateMockData(schema: OpenAPIV3.SchemaObject): any { + if (this.visitedSchemas.has(schema)) { + return null; // Prevent circular reference + } + this.visitedSchemas.add(schema); + + let result: any; + if (schema.anyOf) { + // Select the first schema in anyOf + const selectedSchema = schema.anyOf[0] as OpenAPIV3.SchemaObject; + result = this.generateMockData(selectedSchema); + } else if (schema.oneOf) { + // Select the first schema in oneOf + const selectedSchema = schema.oneOf[0] as OpenAPIV3.SchemaObject; + result = this.generateMockData(selectedSchema); + } else if (schema.allOf) { + // merge all schemas in allOf + result = {}; + for (const subschema of schema.allOf) { + const data = this.generateMockData(subschema as OpenAPIV3.SchemaObject); + result = { ...result, ...data }; + } + } else { + switch (schema.type) { + case "string": + if (schema.example !== undefined) { + result = schema.example; + } else if (schema.format) { + switch (schema.format) { + case "date-time": + result = "2024-11-01T05:25:43.593Z"; + break; + case "email": + result = "example@example.com"; + break; + case "uuid": + result = "123e4567-e89b-12d3-a456-426614174000"; + break; + case "ipv4": + result = "192.168.0.1"; + break; + case "ipv6": + result = "2001:0db8:85a3:0000:0000:8a2e:0370:7334"; + break; + default: + result = "example string"; + } + } else { + result = "example string"; + } + break; + case "number": + if (schema.example !== undefined) { + result = schema.example; + } else if (schema.format) { + switch (schema.format) { + case "float": + result = 3.14; + break; + case "double": + result = 3.14159; + break; + default: + result = 123; + } + } else { + result = 123; + } + break; + case "integer": + if (schema.example !== undefined) { + result = schema.example; + } else if (schema.format) { + switch (schema.format) { + case "int32": + result = 123456; + break; + case "int64": + result = 123456789; + break; + default: + result = 123; + } + } else { + result = 123; + } + break; + case "boolean": + result = schema.example !== undefined ? schema.example : true; + break; + case "array": + result = [this.generateMockData(schema.items as OpenAPIV3.SchemaObject)]; + break; + case "object": + result = {}; + if (schema.properties) { + for (const key in schema.properties) { + result[key] = this.generateMockData(schema.properties[key] as OpenAPIV3.SchemaObject); + } + } + break; + default: + result = schema.example || null; + } + } + + this.visitedSchemas.delete(schema); + return result; + } +} diff --git a/packages/spec-parser/src/manifestUpdater.ts b/packages/spec-parser/src/manifestUpdater.ts index ed7dc354da..d0605d3717 100644 --- a/packages/spec-parser/src/manifestUpdater.ts +++ b/packages/spec-parser/src/manifestUpdater.ts @@ -220,10 +220,12 @@ export class ManifestUpdater { try { const { json } = Utils.getResponseJson(operationItem); if (json.schema) { - const [card, jsonPath] = - AdaptiveCardGenerator.generateAdaptiveCard(operationItem); + const [card, jsonPath] = AdaptiveCardGenerator.generateAdaptiveCard( + operationItem, + false, + 5 + ); - card.body = Utils.limitACBodyProperties(card.body, 5); const responseSemantic = wrapResponseSemantics(card, jsonPath); funcObj.capabilities = { response_semantics: responseSemantic, diff --git a/packages/spec-parser/src/specParser.ts b/packages/spec-parser/src/specParser.ts index 365f4c242f..9cc7121ec2 100644 --- a/packages/spec-parser/src/specParser.ts +++ b/packages/spec-parser/src/specParser.ts @@ -32,7 +32,6 @@ import { AdaptiveCardGenerator } from "./adaptiveCardGenerator"; import { wrapAdaptiveCard } from "./adaptiveCardWrapper"; import { ValidatorFactory } from "./validators/validatorFactory"; import { Validator } from "./validators/validator"; -import { PluginManifestSchema } from "@microsoft/teams-manifest"; import { createHash } from "crypto"; /** @@ -311,6 +310,29 @@ export class SpecParser { const authInfo = Utils.getAuthInfo(newSpec); + const paths = newUnResolvedSpec.paths; + for (const pathUrl in paths) { + const operations = paths[pathUrl]; + for (const method in operations) { + const operationItem = (operations as any)[method] as OpenAPIV3.OperationObject; + const operationId = operationItem.operationId!; + const containsSpecialCharacters = /[^a-zA-Z0-9_]/.test(operationId); + if (!containsSpecialCharacters) { + continue; + } + operationItem.operationId = operationId.replace(/[^a-zA-Z0-9]/g, "_"); + result.warnings.push({ + type: WarningType.OperationIdContainsSpecialCharacters, + content: Utils.format( + ConstantString.OperationIdContainsSpecialCharacters, + operationId, + operationItem.operationId + ), + data: operationId, + }); + } + } + await this.saveFilterSpec(outputSpecPath, newUnResolvedSpec); if (signal?.aborted) { @@ -385,7 +407,9 @@ export class SpecParser { if (this.options.allowMethods.includes(method)) { const operation = (newSpec.paths[url] as any)[method] as OpenAPIV3.OperationObject; try { - const [card, jsonPath] = AdaptiveCardGenerator.generateAdaptiveCard(operation); + const [card, jsonPath, jsonData, warnings] = + AdaptiveCardGenerator.generateAdaptiveCard(operation); + result.warnings.push(...warnings); const safeAdaptiveCardName = operation.operationId!.replace(/[^a-zA-Z0-9]/g, "_"); const fileName = path.join(adaptiveCardFolder, `${safeAdaptiveCardName}.json`); const wrappedCard = wrapAdaptiveCard(card, jsonPath); @@ -394,7 +418,7 @@ export class SpecParser { adaptiveCardFolder, `${safeAdaptiveCardName}.data.json` ); - await fs.outputJSON(dataFileName, {}, { spaces: 2 }); + await fs.outputJSON(dataFileName, jsonData, { spaces: 2 }); } catch (err) { result.allSuccess = false; result.warnings.push({ diff --git a/packages/spec-parser/src/utils.ts b/packages/spec-parser/src/utils.ts index d49263fb9a..b0b1875590 100644 --- a/packages/spec-parser/src/utils.ts +++ b/packages/spec-parser/src/utils.ts @@ -468,35 +468,4 @@ export class Utils { return serverUrl; } - - static limitACBodyProperties(body: AdaptiveCardBody, maxCount: number): AdaptiveCardBody { - const result: AdaptiveCardBody = []; - let currentCount = 0; - - for (const element of body) { - if (element.type === ConstantString.ContainerType) { - const items = this.limitACBodyProperties( - (element as ArrayElement).items, - maxCount - currentCount - ); - - result.push({ - type: ConstantString.ContainerType, - $data: (element as ArrayElement).$data, - items: items, - }); - - currentCount += items.length; - } else { - result.push(element); - currentCount++; - } - - if (currentCount >= maxCount) { - break; - } - } - - return result; - } } diff --git a/packages/spec-parser/test/adaptiveCardGenerator.test.ts b/packages/spec-parser/test/adaptiveCardGenerator.test.ts index 223cb2abd6..ef79246e16 100644 --- a/packages/spec-parser/test/adaptiveCardGenerator.test.ts +++ b/packages/spec-parser/test/adaptiveCardGenerator.test.ts @@ -6,6 +6,7 @@ import { Utils } from "../src/utils"; import { SpecParserError } from "../src/specParserError"; import { ErrorType } from "../src/interfaces"; import { ConstantString } from "../src/constants"; +import { JsonDataGenerator } from "../src/jsonDataGenerator"; describe("adaptiveCardGenerator", () => { afterEach(() => { @@ -59,6 +60,69 @@ describe("adaptiveCardGenerator", () => { expect(jsonPath).to.equal("$"); }); + it("should return warning if generate json data throw exception", () => { + const operationItem = { + operationId: "getHello", + responses: { + "200": { + description: "OK", + content: { + "application/json": { + schema: { + type: "object", + properties: { + name: { + type: "string", + }, + age: { + type: "number", + }, + }, + }, + }, + }, + }, + }, + } as any; + const expected = { + type: "AdaptiveCard", + $schema: "http://adaptivecards.io/schemas/adaptive-card.json", + version: "1.5", + body: [ + { + type: "TextBlock", + text: "name: ${if(name, name, 'N/A')}", + wrap: true, + }, + { + type: "TextBlock", + text: "age: ${if(age, age, 'N/A')}", + wrap: true, + }, + ], + }; + + sinon.stub(JsonDataGenerator, "generate").throws(new Error("generate json data failed")); + + const [actual, jsonPath, jsonData, warnings] = + AdaptiveCardGenerator.generateAdaptiveCard(operationItem); + + expect(actual).to.deep.equal(expected); + expect(jsonPath).to.equal("$"); + expect(jsonData).to.deep.equal({}); + expect(warnings).to.deep.equal([ + { + type: "generate-json-data-failed", + content: Utils.format( + ConstantString.GenerateJsonDataFailed, + "getHello", + new Error("generate json data failed").toString() + ), + data: "getHello", + }, + ]); + }); + it("should generate a card from a schema object with image url property", () => { const operationItem = { responses: { @@ -462,11 +526,7 @@ describe("adaptiveCardGenerator", () => { }, ]; - const actual = AdaptiveCardGenerator.generateCardFromResponse( - schema as any, - name, - parentArrayName - ); + const actual = AdaptiveCardGenerator.generateCardFromResponse(schema as any, name); expect(actual).to.deep.equal(expected); }); diff --git a/packages/spec-parser/test/jsonDataGenerator.test.ts b/packages/spec-parser/test/jsonDataGenerator.test.ts new file mode 100644 index 0000000000..82a8d1a823 --- /dev/null +++ b/packages/spec-parser/test/jsonDataGenerator.test.ts @@ -0,0 +1,384 @@ +import { JsonDataGenerator } from "../src/jsonDataGenerator"; +import { OpenAPIV3 } from "openapi-types"; +import "mocha"; +import { expect } from "chai"; + +describe("JsonDataGenerator", () => { + it("should generate a string example", () => { + const schema: OpenAPIV3.SchemaObject = { type: "string", example: "test string" }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal("test string"); + }); + + it("should generate a number example", () => { + const schema: OpenAPIV3.SchemaObject = { type: "number", example: 42.5 }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(42.5); + }); + + it("should generate a boolean example", () => { + const schema: OpenAPIV3.SchemaObject = { type: "boolean", example: false }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(false); + }); + + it("should generate a boolean without example", () => { + const schema: OpenAPIV3.SchemaObject = { type: "boolean" }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(true); + }); + + it("should generate an array example", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "array", + items: { type: "integer", example: 10 }, + }; + const result = JsonDataGenerator.generate(schema); + expect(result).deep.equal([10]); + }); + + it("should generate an object example", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "object", + properties: { + name: { type: "string", example: "John Doe" }, + age: { type: "integer", example: 30 }, + }, + }; + const result = JsonDataGenerator.generate(schema); + expect(result).deep.equal({ name: "John Doe", age: 30 }); + }); + + it("should generate an object without properties", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "object", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).deep.equal({}); + }); + + it("should handle anyOf by selecting one schema", () => { + const schema: OpenAPIV3.SchemaObject = { + anyOf: [ + { type: "string", example: "Any string" }, + { type: "number", example: 100 }, + ], + }; + const result = JsonDataGenerator.generate(schema); + expect(["Any string", 100]).contain(result); + }); + + it("should handle oneOf by selecting one schema", () => { + const schema: OpenAPIV3.SchemaObject = { + oneOf: [ + { type: "boolean", example: true }, + { type: "string", example: "111" }, + ], + }; + const result = JsonDataGenerator.generate(schema); + expect([true, "111"]).contain(result); + }); + + it("should merge data correctly when data is an object and not null", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "object", + properties: { + key1: { type: "string", example: "value1" }, + key2: { type: "number", example: 123 }, + }, + }; + + const result = JsonDataGenerator.generate(schema); + expect(result).deep.equal({ + key1: "value1", + key2: 123, + }); + }); + + it("should handle allOf by merging schemas", () => { + const schema: OpenAPIV3.SchemaObject = { + allOf: [ + { + type: "object", + properties: { + firstName: { type: "string", example: "Jane" }, + }, + }, + { + type: "object", + properties: { + lastName: { type: "string", example: "Doe" }, + }, + }, + ], + }; + const result = JsonDataGenerator.generate(schema); + expect(result).deep.equal({ firstName: "Jane", lastName: "Doe" }); + }); + + it("should prevent circular references", () => { + const circularSchema: OpenAPIV3.SchemaObject = { type: "object" }; + circularSchema.properties = { + self: circularSchema, + }; + const result = JsonDataGenerator.generate(circularSchema); + expect(result).deep.equal({ self: null }); + }); + + it("should return null for invalid schema", () => { + const schema = { id: "string" }; + const result = JsonDataGenerator.generate(schema as any); + expect(result).to.be.null; + }); + + it("should handle missing example by providing default value", () => { + const schema: OpenAPIV3.SchemaObject = { type: "string" }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal("example string"); + }); + + it("should handle nested schemas", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "object", + properties: { + user: { + type: "object", + properties: { + id: { type: "integer", example: 1 }, + profile: { + type: "object", + properties: { + email: { type: "string", example: "user@example.com" }, + }, + }, + }, + }, + }, + }; + const result = JsonDataGenerator.generate(schema); + expect(result).deep.equal({ + user: { + id: 1, + profile: { email: "user@example.com" }, + }, + }); + }); + + it("should handle string format date-time", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "string", + format: "date-time", + }; + const result = JsonDataGenerator.generate(schema); + expect(new Date(result).toISOString()).to.equal(result); + }); + + it("should handle string format email", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "string", + format: "email", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal("example@example.com"); + }); + + it("should handle string format uuid", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "string", + format: "uuid", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal("123e4567-e89b-12d3-a456-426614174000"); + }); + + it("should handle string format ipv4", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "string", + format: "ipv4", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal("192.168.0.1"); + }); + + it("should handle string format ipv6", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "string", + format: "ipv6", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal("2001:0db8:85a3:0000:0000:8a2e:0370:7334"); + }); + + it("should handle string with unknown format by using default", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "string", + format: "unknown-format", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal("example string"); + }); + + it("should handle number format float", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "number", + format: "float", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(3.14); + }); + + it("should handle without format", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "number", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(123); + }); + + it("should handle number format double", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "number", + format: "double", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(3.14159); + }); + + it("should handle number with unknown format by using default", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "number", + format: "unknown-format", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(123); + }); + + it("should handle integer format int32", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "integer", + format: "int32", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(123456); + }); + + it("should handle integer without format", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "integer", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(123); + }); + + it("should handle integer format int64", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "integer", + format: "int64", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(123456789); + }); + + it("should handle integer with unknown format by using default", () => { + const schema: OpenAPIV3.SchemaObject = { + type: "integer", + format: "unknown-format", + }; + const result = JsonDataGenerator.generate(schema); + expect(result).to.equal(123); + }); + + it("should handle real case: pet store", () => { + const schema: OpenAPIV3.SchemaObject = { + required: ["name", "photoUrls"], + type: "object", + properties: { + id: { + type: "integer", + format: "int64", + example: 10, + }, + name: { + type: "string", + example: "doggie", + }, + category: { + type: "object", + properties: { + id: { + type: "integer", + format: "int64", + example: 1, + }, + name: { + type: "string", + example: "Dogs", + }, + }, + xml: { + name: "category", + }, + }, + photoUrls: { + type: "array", + xml: { + wrapped: true, + }, + items: { + type: "string", + example: "string", + xml: { + name: "photoUrl", + }, + }, + }, + tags: { + type: "array", + xml: { + wrapped: true, + }, + items: { + type: "object", + properties: { + id: { + type: "integer", + format: "int64", + example: 0, + }, + name: { + type: "string", + example: "string", + }, + }, + xml: { + name: "tag", + }, + }, + }, + status: { + type: "string", + description: "pet status in the store", + example: "available", + enum: ["available", "pending", "sold"], + }, + }, + }; + const result = JsonDataGenerator.generate(schema); + expect(result).deep.equal({ + id: 10, + name: "doggie", + category: { + id: 1, + name: "Dogs", + }, + photoUrls: ["string"], + tags: [ + { + id: 0, + name: "string", + }, + ], + status: "available", + }); + }); +}); diff --git a/packages/spec-parser/test/specParser.test.ts b/packages/spec-parser/test/specParser.test.ts index 0a7eb6095e..db4fe19048 100644 --- a/packages/spec-parser/test/specParser.test.ts +++ b/packages/spec-parser/test/specParser.test.ts @@ -21,6 +21,7 @@ import mockedEnv, { RestoreFn } from "mocked-env"; import { SMEValidator } from "../src/validators/smeValidator"; import { ValidatorFactory } from "../src/validators/validatorFactory"; import { createHash } from "crypto"; +import { JsonDataGenerator } from "../src/jsonDataGenerator"; describe("SpecParser", () => { afterEach(() => { @@ -1143,6 +1144,86 @@ describe("SpecParser", () => { expect(outputJSONStub.calledTwice).to.be.true; }); + it("should contains warning if operation id contains special characters", async () => { + const specParser = new SpecParser("path/to/spec.yaml"); + const spec = { + openapi: "3.0.0", + paths: { + "/hello": { + get: { + operationId: "get/hello", + responses: { + 200: { + content: { + "application/json": { + schema: { + type: "object", + properties: { + name: { + type: "string", + }, + }, + }, + }, + }, + }, + }, + }, + post: { + operationId: "post_hello", + responses: { + 200: { + content: { + "application/json": { + schema: { + type: "object", + properties: { + name: { + type: "string", + }, + }, + }, + }, + }, + }, + }, + }, + }, + }, + }; + const parseStub = sinon.stub(specParser.parser, "parse").resolves(spec as any); + const dereferenceStub = sinon.stub(specParser.parser, "dereference").resolves(spec as any); + const specFilterStub = sinon.stub(SpecFilter, "specFilter").returns(spec as any); + const outputFileStub = sinon.stub(fs, "outputFile").resolves(); + const outputJSONStub = sinon.stub(fs, "outputJSON").resolves(); + const JsyamlSpy = sinon.spy(jsyaml, "dump"); + + const updateManifestWithAiPluginStub = sinon + .stub(ManifestUpdater, "updateManifestWithAiPlugin") + .resolves([{}, {}, []] as any); + + const filter = ["get /hello", "post /hello"]; + + const outputSpecPath = "path/to/output.yaml"; + const pluginFilePath = "ai-plugin.json"; + const result = await specParser.generateForCopilot( + "path/to/manifest.json", + filter, + outputSpecPath, + pluginFilePath + ); + + expect(result.allSuccess).to.be.true; + expect(JsyamlSpy.calledOnce).to.be.true; + expect(specFilterStub.calledOnce).to.be.true; + expect(outputFileStub.calledOnce).to.be.true; + expect(updateManifestWithAiPluginStub.calledOnce).to.be.true; + expect(outputFileStub.firstCall.args[0]).to.equal(outputSpecPath); + expect(outputJSONStub.calledTwice).to.be.true; + expect(result.warnings.length).equals(1); + expect(result.warnings[0].content).contains("get_hello"); + }); + it("should throw a SpecParserError if outputFile throws an error", async () => { const specParser = new SpecParser("path/to/spec.yaml"); const spec = { openapi: "3.0.0", paths: {} }; @@ -1485,6 +1566,77 @@ describe("SpecParser", () => { ], }, "$", + {}, + [], + ]); + + const filter = ["get /hello"]; + + const outputSpecPath = "path/to/output.yaml"; + const result = await specParser.generate( + "path/to/manifest.json", + filter, + outputSpecPath, + "path/to/adaptiveCardFolder" + ); + + expect(result.allSuccess).to.be.true; + expect(JsyamlSpy.calledOnce).to.be.true; + expect(specFilterStub.calledOnce).to.be.true; + expect(outputFileStub.calledOnce).to.be.true; + expect(manifestUpdaterStub.calledOnce).to.be.true; + expect(outputFileStub.firstCall.args[0]).to.equal(outputSpecPath); + expect(outputJSONStub.calledThrice).to.be.true; + }); + + it("should not return warning if schema is empty and not generate json data", async () => { + const specParser = new SpecParser("path/to/spec.yaml"); + const spec = { + openapi: "3.0.0", + paths: { + "/hello": { + get: { + operationId: "helloApi", + responses: { + 200: { + content: { + "application/json": {}, + }, + }, + }, + }, + }, + }, + }; + const parseStub = sinon.stub(specParser.parser, "parse").resolves(spec as any); + const dereferenceStub = sinon.stub(specParser.parser, "dereference").resolves(spec as any); + const specFilterStub = sinon.stub(SpecFilter, "specFilter").returns({} as any); + const outputFileStub = sinon.stub(fs, "outputFile").resolves(); + const outputJSONStub = sinon.stub(fs, "outputJSON").resolves(); + const JsyamlSpy = sinon.spy(jsyaml, "dump"); + + const manifestUpdaterStub = sinon + .stub(ManifestUpdater, "updateManifest") + .resolves([{}, []] as any); + + const generateAdaptiveCardStub = sinon + .stub(AdaptiveCardGenerator, "generateAdaptiveCard") + .returns([ + { + type: "AdaptiveCard", + $schema: "http://adaptivecards.io/schemas/adaptive-card.json", + version: "1.5", + body: [ + { + type: "TextBlock", + text: "id: ${id}", + wrap: true, + }, + ], + }, + "$", + {}, + [], ]); const filter = ["get /hello"]; @@ -1498,6 +1650,7 @@ describe("SpecParser", () => { ); expect(result.allSuccess).to.be.true; + expect(result.warnings.length).equals(0); expect(JsyamlSpy.calledOnce).to.be.true; expect(specFilterStub.calledOnce).to.be.true; expect(outputFileStub.calledOnce).to.be.true; @@ -1561,6 +1714,8 @@ describe("SpecParser", () => { ], }, "$", + {}, + [], ]); const filter = ["get /hello"]; @@ -1636,6 +1791,8 @@ describe("SpecParser", () => { ], }, "$", + {}, + [], ]); const filter = ["get /hello"]; @@ -1750,6 +1907,8 @@ describe("SpecParser", () => { ], }, "$", + {}, + [], ]); const filter = ["get /hello", "post /hello"]; @@ -1861,6 +2020,8 @@ describe("SpecParser", () => { ], }, "$", + {}, + [], ]); const filter = ["get /hello", "post /hello"]; @@ -1977,6 +2138,8 @@ describe("SpecParser", () => { ], }, "$", + {}, + [], ]); const filter = ["get /hello", "post /hello"]; diff --git a/packages/tests/.vscode/launch.json b/packages/tests/.vscode/launch.json index 94d4d0806e..466859e4e3 100644 --- a/packages/tests/.vscode/launch.json +++ b/packages/tests/.vscode/launch.json @@ -14,9 +14,7 @@ "--extensions_dir", ".test-resources", "--type", - "insider", - "--code_version", - "1.90.0-insider", + "stable", "--code_settings", "./settings.json", "./out/ui-test/**/${{ YOUR TEST CASE }}.test.js" diff --git a/packages/tests/scripts/pvt.json b/packages/tests/scripts/pvt.json index 6da79d3e49..aa17102e55 100644 --- a/packages/tests/scripts/pvt.json +++ b/packages/tests/scripts/pvt.json @@ -1,18 +1,13 @@ { "windows-latest": { - "node-18": [ + "node-20": [ "localdebug-tab-nosso", "localdebug-bot", "localdebug-bot-twice", "localdebug-command-and-response", "localdebug-notification-func", - "localdebug-notification-restify", + "localdebug-notification-express", "localdebug-tab-regen-appid", - "treeview-newproject-spfx", - "treeview-collaboration-spfx", - "remotedebug-spfxreact-globalpkg", - "remotedebug-spfxnone-globalpkg-addwebpart", - "remotedebug-spfxreact-addwebpart", "treeview-newproject-outlook-add-in", "treeview-newproject-tab", "treeview-collaboration-win-only", @@ -28,8 +23,8 @@ "remotedebug-msgsa-win-only", "remotedebug-notification-func-ts-win-only", "remotedebug-notification-func-win-only", - "remotedebug-notification-restify-ts-win-only", - "remotedebug-notification-restify-win-only", + "remotedebug-notification-express-ts-win-only", + "remotedebug-notification-express-win-only", "remotedebug-tab-nosso-ts-win-only", "remotedebug-tab-nosso-win-only", "remotedebug-notification-timertrigger-ts-win-only", @@ -71,11 +66,6 @@ "localdebug-aiagent-new-openai-bot", "remotedebug-msg-newapi-apikey-ts-win-only", "remotedebug-msg-newapi-apikey-win-only", - "remotedebug-spfxreact-import-single", - "remotedebug-spfxreact-import-multiple", - "remotedebug-spfx-none", - "remotedebug-spfx-minimal", - "remotedebug-spfx-react", "remotedebug-msg-newapi-microsoftentra-ts-win-only", "remotedebug-msg-newapi-microsoftentra-win-only", "remotedebug-msg-multiple-params-win-only", @@ -98,10 +88,20 @@ "remotedebug-chatdata-customapi-ts-openai-win-only", "remotedebug-chatdata-customapi-py-azureopenai-win-only", "remotedebug-chatdata-customapi-py-openai-win-only" - - ], - "node-20": ["localdebug-obo-tab"] + "node-18": [ + "localdebug-obo-tab", + "treeview-newproject-spfx", + "treeview-collaboration-spfx", + "remotedebug-spfxreact-globalpkg", + "remotedebug-spfxnone-globalpkg-addwebpart", + "remotedebug-spfxreact-addwebpart", + "remotedebug-spfxreact-import-single", + "remotedebug-spfxreact-import-multiple", + "remotedebug-spfx-none", + "remotedebug-spfx-minimal", + "remotedebug-spfx-react" + ] }, "ubuntu-latest": { "node-18": [ @@ -109,7 +109,7 @@ "localdebug-bot", "localdebug-command-and-response", "localdebug-notification-func", - "localdebug-notification-restify", + "localdebug-notification-express", "treeview-content", "treeview-tab-manifest", "treeview-quickstart", @@ -122,7 +122,7 @@ "localdebug-msgsa-ts", "localdebug-msgsa", "localdebug-notification-func-ts", - "localdebug-notification-restify-ts", + "localdebug-notification-express-ts", "localdebug-tab-nosso-ts", "localdebug-tab-nosso", "localdebug-workflow-bot", @@ -165,7 +165,8 @@ "localdebug-chatdata-customapi-ts-azureopenai", "localdebug-chatdata-customapi-ts-openai", "localdebug-chatdata-customapi-py-azureopenai", - "localdebug-chatdata-customapi-py-openai" + "localdebug-chatdata-customapi-py-openai", + "testtooldebug-command-and-response" ], "node-20": ["localdebug-obo-tab"] }, @@ -174,7 +175,7 @@ "localdebug-bot", "localdebug-command-and-response", "localdebug-notification-func", - "localdebug-notification-restify", + "localdebug-notification-express", "treeview-collaboration-spfx" ] } diff --git a/packages/tests/scripts/randomCases.json b/packages/tests/scripts/randomCases.json index 07fdbe4d56..21dc62877e 100644 --- a/packages/tests/scripts/randomCases.json +++ b/packages/tests/scripts/randomCases.json @@ -15,12 +15,8 @@ "sample-localdebug-query-org", "sample-localdebug-stock-update", "sample-localdebug-incoming-webhook", - "basic-tab-debug-upgrade-debug", - "bot-debug-upgrade-debug", - "bot-upgrade-debug", "sample-remotedebug-todo-list-with-spfx", "sample-remotedebug-todo-list-with-m365", - "sample-localdebug-react-retail-dashboard", "sample-localdebug-spfx-productivity-dashboard", "sample-remotedebug-react-retail-dashboard", "sample-remotedebug-spfx-productivity-dashboard", @@ -75,8 +71,7 @@ "sample-localdebug-bot-sso", "sample-localdebug-dice-roller", "sample-localdebug-contact-exporter", - "sample-localdebug-hello-world-meeting", - "basic-tab-upgrade-debug" + "sample-localdebug-hello-world-meeting" ] }, { @@ -100,9 +95,7 @@ "sample-remotedebug-assistant-dashboard", "sample-remotedebug-hello-world-tab-outlook", "sample-remotedebug-bot-sso", - "sample-remotedebug-sso-tab-via-apim-proxy", - "basic-tab-upgrade-provision-debug", - "bot-upgrade-provision-debug" + "sample-remotedebug-sso-tab-via-apim-proxy" ] }, { @@ -128,10 +121,9 @@ "sample-remotedebug-bot-sso-docker", "sample-localdebug-hello-world-tab-docker", "sample-remotedebug-hello-world-tab-docker", - "basic-tab-provision-upgrade-provision-debug", - "bot-provision-upgrade-provision-debug", "sample-localdebug-todo-list-with-spfx", - "sample-localdebug-todo-list-with-m365" + "sample-localdebug-todo-list-with-m365", + "sample-localdebug-react-retail-dashboard" ] }, { diff --git a/packages/tests/src/commonlib/constants.ts b/packages/tests/src/commonlib/constants.ts index 4101a7ba96..dfb6ba56dd 100644 --- a/packages/tests/src/commonlib/constants.ts +++ b/packages/tests/src/commonlib/constants.ts @@ -45,7 +45,7 @@ export type CliCapabilities = | "BotAndMessageExtension" | "TabNonSsoAndBot"; export type CliTriggerType = - | "http-restify" + | "http-express" | "http-functions" | "http-and-timer-functions" | "timer-functions"; diff --git a/packages/tests/src/commonlib/functionValidator.ts b/packages/tests/src/commonlib/functionValidator.ts index 7aebc8f8aa..67365b4dbf 100644 --- a/packages/tests/src/commonlib/functionValidator.ts +++ b/packages/tests/src/commonlib/functionValidator.ts @@ -37,18 +37,56 @@ enum BaseConfig { API_ENDPOINT = "API_ENDPOINT", M365_APPLICATION_ID_URI = "M365_APPLICATION_ID_URI", IDENTITY_ID = "IDENTITY_ID", + WEBSITE_CONTENTSHARE = "WEBSITE_CONTENTSHARE", } +export enum ValidatorType { + API_ENDPOINT = "API_ENDPOINT", + FUNCTION_NAME = "FUNCTION_NAME", +} + +type ConfigValidator = (webappSettings: any) => Promise; + export class FunctionValidator { private ctx: any; private projectPath: string; private env: string; + private customConfigsToValidate: ValidatorType[]; private subscriptionId: string; private rg: string; private functionAppName: string; - constructor(ctx: any, projectPath: string, env: string) { + private readonly configValidatorMap: Record = + { + [ValidatorType.API_ENDPOINT]: async ( + webappSettings: any + ): Promise => { + const endpoint = + this.ctx?.[EnvConstants.FUNCTION_ENDPOINT] ?? + this.ctx?.[EnvConstants.FUNCTION_ENDPOINT_2]; + chai.assert.exists(endpoint); + chai.assert.equal(webappSettings[BaseConfig.API_ENDPOINT], endpoint); + }, + + [ValidatorType.FUNCTION_NAME]: async ( + webappSettings: any + ): Promise => { + const contentShare = webappSettings[BaseConfig.WEBSITE_CONTENTSHARE]; + if (contentShare) { + const functionNameInAzure = contentShare.split("-")[0]; + chai.assert.exists(functionNameInAzure); + chai.assert.equal(functionNameInAzure, this.functionAppName); + } + }, + }; + + constructor( + ctx: any, + projectPath: string, + env: string, + customConfigsToValidate?: ValidatorType[] + ) { console.log("Start to init validator for function."); this.ctx = ctx; @@ -67,6 +105,10 @@ export class FunctionValidator { this.functionAppName = getSiteNameFromResourceId(resourceId); chai.assert.exists(this.functionAppName); + this.customConfigsToValidate = customConfigsToValidate ?? [ + ValidatorType.API_ENDPOINT, + ]; + console.log("Successfully init validator for function."); } @@ -86,13 +128,11 @@ export class FunctionValidator { token as string ); chai.assert.exists(webappSettingsResponse); - const endpoint = - (this.ctx[EnvConstants.FUNCTION_ENDPOINT] as string) ?? - (this.ctx[EnvConstants.FUNCTION_ENDPOINT_2] as string); - chai.assert.equal( - webappSettingsResponse[BaseConfig.API_ENDPOINT], - endpoint - ); + + for (const validatorType of this.customConfigsToValidate) { + const validator = this.configValidatorMap[validatorType]; + await validator(webappSettingsResponse); + } console.log("Successfully validate Function Provision."); } diff --git a/packages/tests/src/e2e/bot/DeployToAzureStorageHappyPath.ts b/packages/tests/src/e2e/bot/DeployToAzureStorageHappyPath.ts new file mode 100644 index 0000000000..f978f9a288 --- /dev/null +++ b/packages/tests/src/e2e/bot/DeployToAzureStorageHappyPath.ts @@ -0,0 +1,160 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. +/** + * @author Siglud + */ + +import { describe } from "mocha"; +import { + cleanUp, + createResourceGroup, + execAsyncWithRetry, + getTestFolder, + getUniqueAppName, +} from "../commonUtils"; +import * as path from "path"; +import * as fs from "fs"; +import { getUuid } from "../../commonlib"; +import { expect } from "chai"; +import { environmentNameManager } from "@microsoft/teamsfx-core"; +import { Executor } from "../../utils/executor"; + +describe("Provision and deploy a Azure Storage", async function () { + // create a project with Azure Storage + const testFolder = getTestFolder(); + const appName = getUniqueAppName(); + const projectPath = path.resolve(testFolder, appName); + const projectId = getUuid(); + const envName = environmentNameManager.getDefaultEnvName(); + const rgName = appName + "-rg"; + const env = Object.assign({}, process.env); + + it("should be provision without problem", async () => { + fs.mkdirSync(projectPath, { recursive: true }); + // write teamsapp.yml + fs.writeFileSync( + path.join(projectPath, "teamsapp.yml"), + ` +# yaml-language-server: $schema=https://aka.ms/teams-toolkit/v1.7/yaml.schema.json +version: v1.7 + +environmentFolderPath: ./env + +provision: + - uses: arm/deploy + with: + subscriptionId: \${{AZURE_SUBSCRIPTION_ID}} + resourceGroupName: \${{AZURE_RESOURCE_GROUP_NAME}} + templates: + - path: ./infra/azure.bicep + parameters: ./infra/azure.parameters.json + deploymentName: Create-resources-for-tab + bicepCliVersion: v0.9.1 + - uses: azureStorage/enableStaticWebsite + with: + storageResourceId: \${{TAB_AZURE_STORAGE_RESOURCE_ID}} + indexPage: index.html + errorPage: error.html + +deploy: + - uses: azureStorage/deploy + with: + artifactFolder: build + resourceId: \${{TAB_AZURE_STORAGE_RESOURCE_ID}} +projectId: ${projectId}`, + { encoding: "utf-8", flag: "w" } + ); + // mkdir for infra + fs.mkdirSync(path.join(projectPath, "infra"), { recursive: true }); + // mkdir for env + fs.mkdirSync(path.join(projectPath, "env"), { recursive: true }); + // write azure.bicep + fs.writeFileSync( + path.join(projectPath, "infra", "azure.bicep"), + ` +param resourceBaseName string + +resource storage 'Microsoft.Storage/storageAccounts@2021-06-01' = { + kind: 'StorageV2' + location: resourceGroup().location + name: resourceBaseName + properties: { + supportsHttpsTrafficOnly: true + } + sku: { + name: 'Standard_LRS' + } +} + +output TAB_AZURE_STORAGE_RESOURCE_ID string = storage.id +output TAB_DOMAIN string = storage.properties.primaryEndpoints.web`, + { encoding: "utf-8", flag: "w" } + ); + // write azure.parameters.json + fs.writeFileSync( + path.join(projectPath, "infra", "azure.parameters.json"), + `{ + "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentParameters.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "resourceBaseName": { + "value": "hello0world\${{RESOURCE_SUFFIX}}" + } + } +}`, + { encoding: "utf-8", flag: "w" } + ); + // write .env.dev + const suffix = getUuid().split("-"); + fs.writeFileSync( + path.join(projectPath, "env", ".env.dev"), + "TEAMSFX_ENV=dev\n" + + "APP_NAME_SUFFIX=dev\n" + + `RESOURCE_SUFFIX=${suffix[suffix.length - 1]}\n` + + `AZURE_RESOURCE_GROUP_NAME=${rgName}`, + { encoding: "utf-8", flag: "w" } + ); + // write build and build/index.html + fs.mkdirSync(path.join(projectPath, "build"), { recursive: true }); + fs.writeFileSync( + path.join(projectPath, "build", "index.html"), + "

Hello World

", + { encoding: "utf-8", flag: "w" } + ); + + // run provision + const result = await createResourceGroup(rgName, "westus"); + expect(result).to.be.true; + process.env["AZURE_RESOURCE_GROUP_NAME"] = rgName; + const { success } = await Executor.provision(projectPath, envName); + expect(success).to.be.true; + console.log(`[Successfully] provision for ${projectPath}`); + + // deploy + const cmdStr = "teamsapp deploy"; + await execAsyncWithRetry(cmdStr, { + cwd: projectPath, + env: env, + timeout: 0, + }); + + console.log(`[Successfully] deploy for ${projectPath}`); + + // request to index.html to check the deployment result + const file = fs.readFileSync( + path.join(projectPath, "env", ".env.dev"), + "utf-8" + ); + const line = file.split("\n").filter((line) => { + return line.startsWith("TAB_DOMAIN"); + }); + const domain = line[0].split("=")[1]; + const response = await fetch(domain); + expect(response.status).to.equal(200); + }); + + this.afterEach(async function () { + console.log(`[Successfully] start to clean up for ${projectPath}`); + await cleanUp(appName, projectPath, false, true, false, envName, undefined); + }); +}); diff --git a/packages/tests/src/e2e/bot/NotificationBotHappyPathCommon.ts b/packages/tests/src/e2e/bot/NotificationBotHappyPathCommon.ts index 8696092d03..361f414c8b 100644 --- a/packages/tests/src/e2e/bot/NotificationBotHappyPathCommon.ts +++ b/packages/tests/src/e2e/bot/NotificationBotHappyPathCommon.ts @@ -44,7 +44,7 @@ export function happyPathTest(runtime: Runtime): void { it("Provision Resource: app service hosted notification", async function () { const cmd = runtime === Runtime.Node - ? `teamsapp new --interactive false --app-name ${appName} --capability notification --bot-host-type-trigger http-restify --programming-language typescript` + ? `teamsapp new --interactive false --app-name ${appName} --capability notification --bot-host-type-trigger http-express --programming-language typescript` : `teamsapp new --runtime dotnet --interactive false --app-name ${appName} --capability notification --bot-host-type-trigger http-webapi`; await execAsync(cmd, { cwd: testFolder, diff --git a/packages/tests/src/e2e/caseFactory.ts b/packages/tests/src/e2e/caseFactory.ts index 7b245d85ef..e34859b7a2 100644 --- a/packages/tests/src/e2e/caseFactory.ts +++ b/packages/tests/src/e2e/caseFactory.ts @@ -23,7 +23,12 @@ import { environmentNameManager, ProgrammingLanguage, } from "@microsoft/teamsfx-core"; -import { AadValidator, BotValidator, FunctionValidator } from "../commonlib"; +import { + AadValidator, + BotValidator, + FunctionValidator, + ValidatorType, +} from "../commonlib"; import m365Login from "@microsoft/teamsapp-cli/src/commonlib/m365Login"; export abstract class CaseFactory { @@ -46,6 +51,7 @@ export abstract class CaseFactory { skipDeploy?: boolean; skipValidate?: boolean; skipPackage?: boolean; + skipValidateForProvision?: boolean; }; public custimized?: Record; @@ -69,6 +75,7 @@ export abstract class CaseFactory { skipDeploy?: boolean; skipValidate?: boolean; skipPackage?: boolean; + skipValidateForProvision?: boolean; } = {}, custimized?: Record ) { @@ -128,7 +135,7 @@ export abstract class CaseFactory { onBeforeProvision, onCreate, } = this; - describe(`template Test: ${capability}`, function () { + describe(`template Test: ${capability} - ${programmingLanguage}`, function () { const testFolder = getTestFolder(); const appName = getUniqueAppName(); const projectPath = path.resolve(testFolder, appName); @@ -171,35 +178,40 @@ export abstract class CaseFactory { const { success } = await Executor.provision(projectPath); expect(success).to.be.true; - // Validate Provision - const context = await readContextMultiEnvV3(projectPath, env); - if (validate.includes("bot")) { - // Validate Bot Provision - const bot = new BotValidator(context, projectPath, env); - await bot.validateProvisionV3(false); - } - if (validate.includes("tab")) { - // Validate Tab Frontend - // const frontend = StaticSiteValidator.init(context); - // await StaticSiteValidator.validateProvision(frontend); - } - if (validate.includes("aad")) { - // Validate Aad App - const aad = AadValidator.init(context, false, m365Login); - await AadValidator.validate(aad); - } - if (validate.includes("tab & bot")) { - // Validate Tab & Bot Provision - await validateTabAndBotProjectProvision(projectPath, env); - } - if (validate.includes("function")) { - // Validate Function App - const functionValidator = new FunctionValidator( - context, - projectPath, - env - ); - await functionValidator.validateProvision(); + if (!options?.skipValidateForProvision) { + // Validate Provision + const context = await readContextMultiEnvV3(projectPath, env); + if (validate.includes("bot")) { + // Validate Bot Provision + const bot = new BotValidator(context, projectPath, env); + await bot.validateProvisionV3(false); + } + if (validate.includes("tab")) { + // Validate Tab Frontend + // const frontend = StaticSiteValidator.init(context); + // await StaticSiteValidator.validateProvision(frontend); + } + if (validate.includes("aad")) { + // Validate Aad App + const aad = AadValidator.init(context, false, m365Login); + await AadValidator.validate(aad); + } + if (validate.includes("tab & bot")) { + // Validate Tab & Bot Provision + await validateTabAndBotProjectProvision(projectPath, env); + } + if (validate.includes("function")) { + // Validate Function App + const functionValidator = new FunctionValidator( + context, + projectPath, + env, + capability === Capability.DeclarativeAgent + ? [ValidatorType.FUNCTION_NAME] + : [ValidatorType.API_ENDPOINT] + ); + await functionValidator.validateProvision(); + } } } diff --git a/packages/tests/src/e2e/copilotExtensions/DeclarativeAgentBasic.tests.ts b/packages/tests/src/e2e/copilotExtensions/DeclarativeAgentBasic.tests.ts new file mode 100644 index 0000000000..d087acfadc --- /dev/null +++ b/packages/tests/src/e2e/copilotExtensions/DeclarativeAgentBasic.tests.ts @@ -0,0 +1,29 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. + +/** + * @author Hui Miao + */ + +import { Capability } from "../../utils/constants"; +import { ProgrammingLanguage } from "@microsoft/teamsfx-core"; +import { CaseFactory } from "../caseFactory"; + +class DeclarativeAgentBasicTestCase extends CaseFactory { + public async onAfterCreate(projectPath: string): Promise { + return Promise.resolve(); + } +} + +const myRecord: Record = {}; +myRecord["with-plugin"] = "no"; + +new DeclarativeAgentBasicTestCase( + Capability.DeclarativeAgent, + 27971545, + "huimaio@microsoft.com", + ["function"], + ProgrammingLanguage.None, + { skipValidateForProvision: true, skipDeploy: true }, + myRecord +).test(); diff --git a/packages/tests/src/e2e/copilotExtensions/DeclarativeAgentWithOAuth.tests.ts b/packages/tests/src/e2e/copilotExtensions/DeclarativeAgentWithOAuth.tests.ts new file mode 100644 index 0000000000..cd9e98b3af --- /dev/null +++ b/packages/tests/src/e2e/copilotExtensions/DeclarativeAgentWithOAuth.tests.ts @@ -0,0 +1,47 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. + +/** + * @author Hui Miao + */ + +import { Capability } from "../../utils/constants"; +import { ProgrammingLanguage } from "@microsoft/teamsfx-core"; +import { CaseFactory } from "../caseFactory"; + +class DeclarativeAgentWithOAutTestCase extends CaseFactory {} + +const myRecord: Record = {}; +myRecord["with-plugin"] = "yes"; +myRecord["api-plugin-type"] = "new-api"; +myRecord["api-auth"] = "oauth"; + +new DeclarativeAgentWithOAutTestCase( + Capability.DeclarativeAgent, + 30032802, + "huimaio@microsoft.com", + ["function"], + ProgrammingLanguage.JS, + { skipValidate: true }, + myRecord +).test(); + +new DeclarativeAgentWithOAutTestCase( + Capability.DeclarativeAgent, + 30032802, + "huimaio@microsoft.com", + ["function"], + ProgrammingLanguage.TS, + { skipValidate: true }, + myRecord +).test(); + +new DeclarativeAgentWithOAutTestCase( + Capability.DeclarativeAgent, + 30032802, + "huimaio@microsoft.com", + ["function"], + ProgrammingLanguage.CSharp, + { skipValidate: true }, + myRecord +).test(); diff --git a/packages/tests/src/ui-test/localdebug/localdebug-notification-restify-ts.test.ts b/packages/tests/src/ui-test/localdebug/localdebug-notification-express-ts.test.ts similarity index 91% rename from packages/tests/src/ui-test/localdebug/localdebug-notification-restify-ts.test.ts rename to packages/tests/src/ui-test/localdebug/localdebug-notification-express-ts.test.ts index 2b9350fa91..c8c9d1f73b 100644 --- a/packages/tests/src/ui-test/localdebug/localdebug-notification-restify-ts.test.ts +++ b/packages/tests/src/ui-test/localdebug/localdebug-notification-express-ts.test.ts @@ -21,7 +21,7 @@ import { it } from "../../utils/it"; import { validateFileExist } from "../../utils/commonUtils"; // TODO: Change preview test to normal test before rc release -describe("Restify Notification Bot Local Debug Tests", function () { +describe("Express Notification Bot Local Debug Tests", function () { this.timeout(Timeout.testCase); let localDebugTestContext: LocalDebugTestContext; @@ -29,7 +29,7 @@ describe("Restify Notification Bot Local Debug Tests", function () { beforeEach(async function () { // ensure workbench is ready this.timeout(Timeout.prepareTestCase); - localDebugTestContext = new LocalDebugTestContext("restNoti", { + localDebugTestContext = new LocalDebugTestContext("expressnoti", { lang: "typescript", }); await localDebugTestContext.before(); @@ -42,7 +42,7 @@ describe("Restify Notification Bot Local Debug Tests", function () { }); it( - "[auto] [Typescript] Local debug Restify Notification Bot App", + "[auto] [Typescript] Local debug Express Notification Bot App", { testPlanCaseId: 15277322, author: "aochengwang@microsoft.com", diff --git a/packages/tests/src/ui-test/localdebug/localdebug-notification-restify.test.ts b/packages/tests/src/ui-test/localdebug/localdebug-notification-express.test.ts similarity index 91% rename from packages/tests/src/ui-test/localdebug/localdebug-notification-restify.test.ts rename to packages/tests/src/ui-test/localdebug/localdebug-notification-express.test.ts index cb0896ed9c..935b2915ab 100644 --- a/packages/tests/src/ui-test/localdebug/localdebug-notification-restify.test.ts +++ b/packages/tests/src/ui-test/localdebug/localdebug-notification-express.test.ts @@ -21,7 +21,7 @@ import { it } from "../../utils/it"; import { validateFileExist } from "../../utils/commonUtils"; // TODO: Change preview test to normal test before rc release -describe("Restify Notification Bot Local Debug Tests", function () { +describe("Express Notification Bot Local Debug Tests", function () { this.timeout(Timeout.testCase); let localDebugTestContext: LocalDebugTestContext; @@ -29,7 +29,7 @@ describe("Restify Notification Bot Local Debug Tests", function () { beforeEach(async function () { // ensure workbench is ready this.timeout(Timeout.prepareTestCase); - localDebugTestContext = new LocalDebugTestContext("restNoti"); + localDebugTestContext = new LocalDebugTestContext("expressnoti"); await localDebugTestContext.before(); }); @@ -40,7 +40,7 @@ describe("Restify Notification Bot Local Debug Tests", function () { }); it( - "[auto] Local debug Restify Notification Bot App", + "[auto] Local debug Express Notification Bot App", { testPlanCaseId: 13999815, author: "aochengwang@microsoft.com", diff --git a/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso-ts.test.ts b/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso-ts.test.ts index 2a1123254e..a039676ce6 100644 --- a/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso-ts.test.ts +++ b/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso-ts.test.ts @@ -17,6 +17,7 @@ import { LocalDebugTaskLabel, ValidationContent, DebugItemSelect, + LocalDebugTaskResult, } from "../../utils/constants"; import { Env } from "../../utils/env"; import { it } from "../../utils/it"; @@ -74,7 +75,7 @@ describe("Local Debug Tests", function () { await startDebugging(DebugItemSelect.DebugInTeamsUsingChrome); await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); const teamsAppId = await localDebugTestContext.getTeamsAppId(); diff --git a/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso.test.ts b/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso.test.ts index 248f6ecc04..5cc6f11a81 100644 --- a/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso.test.ts +++ b/packages/tests/src/ui-test/localdebug/localdebug-tab-nosso.test.ts @@ -17,6 +17,7 @@ import { LocalDebugTaskLabel, ValidationContent, DebugItemSelect, + LocalDebugTaskResult, } from "../../utils/constants"; import { Env } from "../../utils/env"; import { it } from "../../utils/it"; @@ -72,7 +73,7 @@ describe("Local Debug Tests", function () { await startDebugging(DebugItemSelect.DebugInTeamsUsingChrome); await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); const teamsAppId = await localDebugTestContext.getTeamsAppId(); diff --git a/packages/tests/src/ui-test/localdebug/localdebug-tab-regen-appid.test.ts b/packages/tests/src/ui-test/localdebug/localdebug-tab-regen-appid.test.ts index 59ebead040..34466e443f 100644 --- a/packages/tests/src/ui-test/localdebug/localdebug-tab-regen-appid.test.ts +++ b/packages/tests/src/ui-test/localdebug/localdebug-tab-regen-appid.test.ts @@ -18,6 +18,7 @@ import { LocalDebugTaskLabel, DebugItemSelect, ValidationContent, + LocalDebugTaskResult, } from "../../utils/constants"; import { Env } from "../../utils/env"; import { it } from "../../utils/it"; @@ -59,7 +60,7 @@ describe("Local Debug Tests", function () { await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); await stopDebugging(); @@ -80,13 +81,13 @@ describe("Local Debug Tests", function () { await startDebugging(DebugItemSelect.DebugInTeamsUsingChrome); await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); // check if there is error "Could not attach to main target" await driver.sleep(Timeout.startdebugging); await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); } catch { try { @@ -114,13 +115,13 @@ describe("Local Debug Tests", function () { await startDebugging(DebugItemSelect.DebugInTeamsUsingChrome); await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); // check if there is error "Debug Anyway" await driver.sleep(Timeout.startdebugging); await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); } catch { console.log(`Try to click "Debug Anyway" button for error dialog`); @@ -130,7 +131,7 @@ describe("Local Debug Tests", function () { await driver.sleep(Timeout.shortTimeLoading); await waitForTerminal( LocalDebugTaskLabel.StartApplication, - "restify listening to" + LocalDebugTaskResult.FrontendStarted ); } } diff --git a/packages/tests/src/ui-test/localdebug/localdebugContext.ts b/packages/tests/src/ui-test/localdebug/localdebugContext.ts index b87641de39..2f9625d7a8 100644 --- a/packages/tests/src/ui-test/localdebug/localdebugContext.ts +++ b/packages/tests/src/ui-test/localdebug/localdebugContext.ts @@ -19,7 +19,7 @@ export type LocalDebugTestName = | "msg" | "msgsa" | "funcNoti" // functions notification bot - | "restNoti" // restify notification bot + | "expressnoti" // express notification bot | "crbot" // command an response bot | "tabbot" | "spfx" @@ -171,10 +171,10 @@ export class LocalDebugTestContext extends TestContext { `teamsapp new --app-name ${this.appName} --interactive false --capability notification --bot-host-type-trigger http-functions --programming-language ${this.lang} --telemetry false` ); break; - case "restNoti": + case "expressnoti": await execCommand( this.testRootFolder, - `teamsapp new --app-name ${this.appName} --interactive false --capability notification --bot-host-type-trigger http-restify --programming-language ${this.lang} --telemetry false` + `teamsapp new --app-name ${this.appName} --interactive false --capability notification --bot-host-type-trigger http-express --programming-language ${this.lang} --telemetry false` ); break; case "crbot": diff --git a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-debug-upgrade-debug.test.ts deleted file mode 100644 index 2cb93e7c36..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,107 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateDeverloperInManifestFile } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.MessageExtension, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V4.0.0 message extension template migrate test - js", - { - testPlanCaseId: 17431841, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("Start Bot"); - await waitForTerminal("Start Bot", LocalDebugTaskResult.AppSuccess); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - throw new Error(error as string); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index c0a894a1c5..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,115 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.MessageExtension, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 local debugged and provisioned message extension template upgrade test", - { - testPlanCaseId: 17431841, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-upgrade-debug.test.ts deleted file mode 100644 index 9ef90c68bb..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-upgrade-debug.test.ts +++ /dev/null @@ -1,103 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateDeverloperInManifestFile } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.MessageExtension, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V4.0.0 message extension template migrate test - js", - { - testPlanCaseId: 17431840, - author: "frankqian@microsoft.com", - }, - async () => { - // option 2: create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("Start Bot"); - await waitForTerminal("Start Bot", LocalDebugTaskResult.AppSuccess); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - throw new Error(error as string); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-upgrade-provision-debug.test.ts deleted file mode 100644 index 42aeea49aa..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-msg/4.0.0-msg-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,109 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.MessageExtension, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 local debugged and provisioned message extension template upgrade test - js", - { - testPlanCaseId: 17431840, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-debug-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-debug-upgrade-debug-ts.test.ts deleted file mode 100644 index 770492a577..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-debug-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,106 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateDeverloperInManifestFile } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - ts", - { - testPlanCaseId: 17431843, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-debug-upgrade-debug.test.ts deleted file mode 100644 index 26fae6ed3b..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,106 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateDeverloperInManifestFile } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - js", - { - testPlanCaseId: 17431843, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-provision-upgrade-provision-debug-ts.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-provision-upgrade-provision-debug-ts.test.ts deleted file mode 100644 index 9f2a096576..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-provision-upgrade-provision-debug-ts.test.ts +++ /dev/null @@ -1,138 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import * as path from "path"; -import { updatePakcageJson } from "./helper"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - ts", - { - testPlanCaseId: 17431843, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - - // update package.json in bot folder - updatePakcageJson( - path.join(mirgationDebugTestContext.projectPath, "bot", "package.json") - ); - - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.testRootFolder); - // remote provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - // await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 9f0f31a07d..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,138 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import * as path from "path"; -import { updatePakcageJson } from "./helper"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - js", - { - testPlanCaseId: 17431843, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - - // update package.json in bot folder - updatePakcageJson( - path.join(mirgationDebugTestContext.projectPath, "bot", "package.json") - ); - - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.testRootFolder); - // remote provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - // await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-debug-ts.test.ts deleted file mode 100644 index dae1db2af9..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,103 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateDeverloperInManifestFile } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - ts", - { - testPlanCaseId: 17431842, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-debug.test.ts deleted file mode 100644 index ced4b19c3c..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-debug.test.ts +++ /dev/null @@ -1,103 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateDeverloperInManifestFile } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - js", - { - testPlanCaseId: 17431842, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-provision-debug-ts.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-provision-debug-ts.test.ts deleted file mode 100644 index 833b980e15..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-provision-debug-ts.test.ts +++ /dev/null @@ -1,131 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - getBotSiteEndpoint, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import { updatePakcageJson } from "./helper"; -import path from "path"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - ts", - { - testPlanCaseId: 17431842, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - - // update package.json in bot folder - updatePakcageJson( - path.join(mirgationDebugTestContext.projectPath, "bot", "package.json") - ); - - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - // await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-provision-debug.test.ts deleted file mode 100644 index 0823547dae..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/4.0.0-notification-bot-restify-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,131 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - getBotSiteEndpoint, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import { updatePakcageJson } from "./helper"; -import path from "path"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 notification bot template upgrade test - js", - { - testPlanCaseId: 17431842, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - - // update package.json in bot folder - updatePakcageJson( - path.join(mirgationDebugTestContext.projectPath, "bot", "package.json") - ); - - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/helper.ts b/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/helper.ts deleted file mode 100644 index 9eb5cba4a3..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-notification-bot-restify/helper.ts +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import * as fs from "fs"; -export function updatePakcageJson(path: string): void { - const content = fs.readFileSync(path); - const x = JSON.parse(content.toString()); - x.devDependencies["@types/restify"] = "^8.5.5"; - x.devDependencies["@types/node"] = "^18.0.0"; - x.devDependencies["ts-node"] = "^10.4.0"; - x.devDependencies["typescript"] = "^4.4.4"; - x.dependencies["@microsoft/teamsfx"] = "^2.3.1"; - x.dependencies["restify"] = "^10.0.0"; - x.dependencies["botbuilder"] = "^4.20.0"; - - fs.writeFileSync(path, JSON.stringify(x, null, 2)); -} diff --git a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-debug-upgrade-debug.test.ts deleted file mode 100644 index 6c6956a0bc..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,105 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "local"); - }); - - it( - "[auto] V4.0.0 sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17431835, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await sampledebugContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait for bot Started"); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId(); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 0f48e5ed92..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,109 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ - -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { - CLIVersionCheck, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import { updatePakcageJson } from "./helper"; -import * as path from "path"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] V4.0.0 sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17431835, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - updatePakcageJson( - path.join(sampledebugContext.projectPath, "bot", "package.json") - ); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", sampledebugContext.projectPath); - // v2 provision - await sampledebugContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile(sampledebugContext.projectPath); - - // v3 provision - await provisionProject( - sampledebugContext.appName, - sampledebugContext.projectPath - ); - await deployProject(sampledebugContext.projectPath); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-upgrade-debug.test.ts deleted file mode 100644 index 6c9e5504e6..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-upgrade-debug.test.ts +++ /dev/null @@ -1,103 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ - -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "local"); - }); - - it( - "[auto] V4.0.0 sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17431834, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait for bot Started"); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId("local"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-upgrade-provision-debug.test.ts deleted file mode 100644 index e9aa44e8e2..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/4.0.0-sample-bot-sso-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,102 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ - -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { updateDeverloperInManifestFile } from "../../../utils/commonUtils"; -import { updatePakcageJson } from "./helper"; -import * as path from "path"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] V4.0.0 sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17431834, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - updatePakcageJson( - path.join(sampledebugContext.projectPath, "bot", "package.json") - ); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile(sampledebugContext.projectPath); - - // v3 provision - await provisionProject( - sampledebugContext.appName, - sampledebugContext.projectPath - ); - await deployProject(sampledebugContext.projectPath); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/helper.ts b/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/helper.ts deleted file mode 100644 index 9eb5cba4a3..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sample-bot-sso/helper.ts +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import * as fs from "fs"; -export function updatePakcageJson(path: string): void { - const content = fs.readFileSync(path); - const x = JSON.parse(content.toString()); - x.devDependencies["@types/restify"] = "^8.5.5"; - x.devDependencies["@types/node"] = "^18.0.0"; - x.devDependencies["ts-node"] = "^10.4.0"; - x.devDependencies["typescript"] = "^4.4.4"; - x.dependencies["@microsoft/teamsfx"] = "^2.3.1"; - x.dependencies["restify"] = "^10.0.0"; - x.dependencies["botbuilder"] = "^4.20.0"; - - fs.writeFileSync(path, JSON.stringify(x, null, 2)); -} diff --git a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-debug-upgrade-debug.test.ts deleted file mode 100644 index 659e979c30..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,118 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - ResourceToDeploy, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateProactiveMessaging, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateFunctionAuthorizationPolicy } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V4.0.0 tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17431837, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.0.0", projectPath); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - - console.log("wait backend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartBackend, - LocalDebugTaskResult.BotAppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateProactiveMessaging(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 228d1a970c..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,124 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - ResourceToDeploy, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateProactiveMessaging, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - updateFunctionAuthorizationPolicy, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import * as path from "path"; -import { updatePakcageJson } from "./helper"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17431837, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - updatePakcageJson( - path.join(mirgationDebugTestContext.projectPath, "bot", "package.json") - ); - - await updateFunctionAuthorizationPolicy("4.0.0", projectPath); - - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateProactiveMessaging(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-upgrade-debug.test.ts deleted file mode 100644 index 9763ce3d4e..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-upgrade-debug.test.ts +++ /dev/null @@ -1,115 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - ResourceToDeploy, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateProactiveMessaging, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateFunctionAuthorizationPolicy } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V4.0.0 tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17431836, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.0.0", projectPath); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - - console.log("wait backend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartBackend, - LocalDebugTaskResult.BotAppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateProactiveMessaging(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-upgrade-provision-debug.test.ts deleted file mode 100644 index 46e3033036..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/4.0.0-sso-tab-bot-function-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,121 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - ResourceToDeploy, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateProactiveMessaging, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - updateFunctionAuthorizationPolicy, - updateDeverloperInManifestFile, -} from "../../../utils/commonUtils"; -import * as path from "path"; -import { updatePakcageJson } from "./helper"; -import { - deployProject, - provisionProject, -} from "../../remotedebug/remotedebugContext"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V4.0.0 tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17431836, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - updatePakcageJson( - path.join(mirgationDebugTestContext.projectPath, "bot", "package.json") - ); - - await updateFunctionAuthorizationPolicy("4.0.0", projectPath); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // enable cli v3 - CliHelper.setV3Enable(); - - await updateDeverloperInManifestFile( - mirgationDebugTestContext.projectPath - ); - - // v3 provision - await provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await deployProject(mirgationDebugTestContext.projectPath); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateProactiveMessaging(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/helper.ts b/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/helper.ts deleted file mode 100644 index 9eb5cba4a3..0000000000 --- a/packages/tests/src/ui-test/migration/4.0.0-sso-tab-bot-function/helper.ts +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import * as fs from "fs"; -export function updatePakcageJson(path: string): void { - const content = fs.readFileSync(path); - const x = JSON.parse(content.toString()); - x.devDependencies["@types/restify"] = "^8.5.5"; - x.devDependencies["@types/node"] = "^18.0.0"; - x.devDependencies["ts-node"] = "^10.4.0"; - x.devDependencies["typescript"] = "^4.4.4"; - x.dependencies["@microsoft/teamsfx"] = "^2.3.1"; - x.dependencies["restify"] = "^10.0.0"; - x.dependencies["botbuilder"] = "^4.20.0"; - - fs.writeFileSync(path, JSON.stringify(x, null, 2)); -} diff --git a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/basic-tab/basic-tab-debug-upgrade-debug.test.ts deleted file mode 100644 index 30c0ce4bcc..0000000000 --- a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,91 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateTabNoneSSO, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByCommandPalette, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.TabNonSso, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, false, "local"); - }); - - it( - "[auto] Basic Tab app with sso migrate test - js", - { - testPlanCaseId: 17184120, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - try { - await validateNotification(Notification.Upgrade); - } catch (error) { - await validateNotification(Notification.Upgrade_dicarded); - } - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByCommandPalette(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - "Compiled successfully!" - ); - } catch (error) {} - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTabNoneSSO(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/basic-tab/basic-tab-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 5ed98e03ca..0000000000 --- a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,103 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateTabNoneSSO, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - validateUpgrade, - upgradeByCommandPalette, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import * as dotenv from "dotenv"; -import { CliHelper } from "../../cliHelper"; - -dotenv.config(); - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.TabNonSso, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, false, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - false, - false - ); - }); - - it( - "[auto] Basic Tab app with sso migrate test - js", - { - testPlanCaseId: 17184120, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - try { - await validateNotification(Notification.Upgrade); - } catch (error) { - await validateNotification(Notification.Upgrade_dicarded); - } - - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByCommandPalette(); - // verify upgrade - await validateUpgrade(); - - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTabNoneSSO(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/basic-tab/basic-tab-upgrade-debug.test.ts deleted file mode 100644 index 5bf392e42d..0000000000 --- a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-upgrade-debug.test.ts +++ /dev/null @@ -1,89 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - CliVersion, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateTabNoneSSO, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByCommandPalette, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.TabNonSso, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, false, "local"); - }); - - it( - "[auto] Basic Tab app with sso migrate test - js", - { - testPlanCaseId: 17184119, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - try { - await validateNotification(Notification.Upgrade); - } catch (error) { - await validateNotification(Notification.Upgrade_dicarded); - } - - // upgrade - await upgradeByCommandPalette(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - "Compiled successfully!" - ); - } catch (error) {} - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTabNoneSSO(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/basic-tab/basic-tab-upgrade-provision-debug.test.ts deleted file mode 100644 index d8ebdf6e25..0000000000 --- a/packages/tests/src/ui-test/migration/basic-tab/basic-tab-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,100 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateTabNoneSSO, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - validateUpgrade, - upgradeByCommandPalette, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import * as dotenv from "dotenv"; -import { CliHelper } from "../../cliHelper"; - -dotenv.config(); - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.TabNonSso, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, false, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - false, - false - ); - }); - - it( - "[auto] Basic Tab app with sso migrate test - js", - { - testPlanCaseId: 17184119, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - try { - await validateNotification(Notification.Upgrade); - } catch (error) { - await validateNotification(Notification.Upgrade_dicarded); - } - - // upgrade - await upgradeByCommandPalette(); - // verify upgrade - await validateUpgrade(); - - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTabNoneSSO(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/bot/bot-debug-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/bot/bot-debug-upgrade-debug-ts.test.ts deleted file mode 100644 index 670fed09b3..0000000000 --- a/packages/tests/src/ui-test/migration/bot/bot-debug-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,97 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Helly Zhang - */ -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - startDebugging, - waitForTerminal, - validateNotification, - upgradeByTreeView, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "typescript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 bot migrate test - ts", - { - testPlanCaseId: 17184118, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal("Start Bot", "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/bot/bot-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/bot/bot-debug-upgrade-debug.test.ts deleted file mode 100644 index 94b05b5960..0000000000 --- a/packages/tests/src/ui-test/migration/bot/bot-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,98 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - startDebugging, - waitForTerminal, - validateNotification, - upgradeByTreeView, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 bot migrate test - js", - { - testPlanCaseId: 17184118, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/bot/bot-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/bot/bot-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 1b4e16faf8..0000000000 --- a/packages/tests/src/ui-test/migration/bot/bot-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,100 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; -import { CliHelper } from "../../cliHelper"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 bot migrate test - js", - { - testPlanCaseId: 17184118, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/bot/bot-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/bot/bot-upgrade-debug-ts.test.ts deleted file mode 100644 index b22c929ae9..0000000000 --- a/packages/tests/src/ui-test/migration/bot/bot-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,95 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Helly Zhang - */ -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "typescript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 bot migrate test - ts", - { - testPlanCaseId: 17184117, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal("Start Bot", "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/bot/bot-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/bot/bot-upgrade-debug.test.ts deleted file mode 100644 index 325ec6e671..0000000000 --- a/packages/tests/src/ui-test/migration/bot/bot-upgrade-debug.test.ts +++ /dev/null @@ -1,96 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 bot migrate test - js", - { - testPlanCaseId: 17184117, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/bot/bot-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/bot/bot-upgrade-provision-debug.test.ts deleted file mode 100644 index 40bf9ddbec..0000000000 --- a/packages/tests/src/ui-test/migration/bot/bot-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,95 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 bot migrate test - js", - { - testPlanCaseId: 17184117, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/command-bot/command-bot-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/command-bot/command-bot-debug-upgrade-debug.test.ts deleted file mode 100644 index 2a6d06d2e1..0000000000 --- a/packages/tests/src/ui-test/migration/command-bot/command-bot-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,101 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -/** - * @author Helly Zhang - */ -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.CommandBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 command bot migrate test - js", - { - testPlanCaseId: 17183669, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/command-bot/command-bot-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/command-bot/command-bot-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index d4bafac56f..0000000000 --- a/packages/tests/src/ui-test/migration/command-bot/command-bot-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,110 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -/** - * @author Helly Zhang - */ -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.CommandBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 command bot migrate test - js", - { - testPlanCaseId: 17183669, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/command-bot/command-bot-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/command-bot/command-bot-upgrade-debug.test.ts deleted file mode 100644 index e79b32b782..0000000000 --- a/packages/tests/src/ui-test/migration/command-bot/command-bot-upgrade-debug.test.ts +++ /dev/null @@ -1,98 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -/** - * @author Helly Zhang - */ -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.CommandBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 command bot migrate test - js", - { - testPlanCaseId: 17184125, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBotApp, - LocalDebugTaskResult.BotAppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/command-bot/command-bot-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/command-bot/command-bot-upgrade-provision-debug.test.ts deleted file mode 100644 index d48a5092d9..0000000000 --- a/packages/tests/src/ui-test/migration/command-bot/command-bot-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,106 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -/** - * @author Helly Zhang - */ -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.CommandBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 command bot migrate test - js", - { - testPlanCaseId: 17184125, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-debug-upgrade-debug.test.ts deleted file mode 100644 index a9d0a8c9e0..0000000000 --- a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,99 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBasicDashboardTab, - initPage, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.DashboardTab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 dashboard tab migrate test - js", - { - testPlanCaseId: 17184359, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - throw new Error(error as string); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBasicDashboardTab(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 5e80af4d04..0000000000 --- a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,111 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBasicDashboardTab, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.DashboardTab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 dashboard tab migrate test - js", - { - testPlanCaseId: 17184359, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBasicDashboardTab(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-upgrade-debug.test.ts deleted file mode 100644 index 6ef51e4294..0000000000 --- a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-upgrade-debug.test.ts +++ /dev/null @@ -1,97 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBasicDashboardTab, - initPage, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.DashboardTab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 dashboard tab migrate test - js", - { - testPlanCaseId: 17184358, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBasicDashboardTab(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-upgrade-provision-debug.test.ts deleted file mode 100644 index 6029499704..0000000000 --- a/packages/tests/src/ui-test/migration/dashboard-tab/dashboard-tab-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,108 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBasicDashboardTab, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.DashboardTab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 dashboard tab migrate test - js", - { - testPlanCaseId: 17184358, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBasicDashboardTab(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/migrationContext.ts b/packages/tests/src/ui-test/migration/migrationContext.ts deleted file mode 100644 index 62371d5ded..0000000000 --- a/packages/tests/src/ui-test/migration/migrationContext.ts +++ /dev/null @@ -1,323 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import path from "path"; -import * as fs from "fs-extra"; -import { openExistingProject } from "../../utils/vscodeOperation"; -import { - Capability, - Trigger, - Framework, - TestFilePath, - Timeout, -} from "../../utils/constants"; -import { TestContext } from "../testContext"; -import { CliHelper } from "../cliHelper"; -import { - cleanUpAadApp, - cleanTeamsApp, - cleanAppStudio, - cleanUpLocalProject, - cleanUpResourceGroup, - createResourceGroup, -} from "../../utils/cleanHelper"; -import { Env } from "../../utils/env"; -import { dotenvUtil } from "../../utils/envUtil"; -import { AzSqlHelper } from "../../utils/azureCliHelper"; -import { runProvision, runDeploy } from "../remotedebug/remotedebugContext"; - -export class MigrationTestContext extends TestContext { - public testName: Capability; - public lang: "javascript" | "typescript" = "javascript"; - public projectPath: string; - public trigger?: Trigger; - public framework?: Framework; - public rgName: string; - - constructor( - testName: Capability, - lang: "javascript" | "typescript" = "javascript", - trigger?: Trigger, - framework?: Framework - ) { - super(testName); - this.testName = testName; - this.lang = lang; - this.trigger = trigger; - this.framework = framework; - this.projectPath = path.resolve(this.testRootFolder, this.appName); - this.rgName = `${this.appName}-dev-rg`; - } - - public async openTemplateFolder(templateName: string): Promise { - console.log("start to open template: ", templateName); - // copy from template - const templateRootPath = path.resolve( - "src", - "ui-test", - "migration", - "templates" - ); - const templatePath = path.resolve(templateRootPath, templateName); - const projectPath = path.resolve(this.testRootFolder, this.appName); - await fs.mkdir(projectPath); - try { - await fs.copy(templatePath, projectPath); - await openExistingProject(projectPath); - console.log("create complate !!!", this.appName, " path: ", projectPath); - } catch (error) { - throw new Error(`copy template failed: ${error}`); - } - } - - public async createProjectCLI(V3: boolean): Promise { - V3 ? CliHelper.setV3Enable() : CliHelper.setV2Enable(); - if (this.trigger) { - await CliHelper.createProjectWithCapabilityMigration( - this.appName, - this.testRootFolder, - this.testName, - this.lang, - `--bot-host-type-trigger ${this.trigger}`, - process.env - ); - } else if (this.framework) { - await CliHelper.createProjectWithCapabilityMigration( - this.appName, - this.testRootFolder, - this.testName, - this.lang, - `--spfx-framework-type ${this.framework}`, - process.env - ); - } else { - await CliHelper.createProjectWithCapabilityMigration( - this.appName, - this.testRootFolder, - this.testName, - this.lang, - undefined, - process.env - ); - } - const projectPath = path.resolve(this.testRootFolder, this.appName); - await openExistingProject(projectPath); - return projectPath; - } - - public async disableDebugConsole(): Promise { - const filePath = path.resolve( - this.testRootFolder, - this.appName, - ".vscode/launch.json" - ); - const content = await fs.readJson(filePath); - const configs = content.configurations as any[]; - for (const config of configs) { - config.internalConsoleOptions = "neverOpen"; - } - await fs.writeJson(filePath, content); - } - - public async after( - hasAadPlugin = true, - hasBotPlugin = false, - envName = "dev" - ) { - await this.context!.close(); - await this.browser!.close(); - if (envName === "local") - await this.cleanResource(hasAadPlugin, hasBotPlugin); - } - - public async cleanUp( - appName: string, - projectPath: string, - hasAadPlugin = true, - hasBotPlugin = false, - hasApimPlugin = false, - envName = "dev" - ) { - const cleanUpAadAppPromise = cleanUpAadApp( - projectPath, - hasAadPlugin, - hasBotPlugin, - hasApimPlugin, - envName - ); - return Promise.all([ - // delete aad app - cleanUpAadAppPromise, - // uninstall Teams app - cleanTeamsApp(appName), - // delete Teams app in app studio - cleanAppStudio(appName), - // remove resouce group - cleanUpResourceGroup(appName, envName), - // remove project - cleanUpLocalProject(projectPath, cleanUpAadAppPromise), - ]); - } - - public async getTeamsAppId(env: "local" | "dev" = "local"): Promise { - const userDataFile = path.join( - TestFilePath.configurationFolder, - `.env.${env}` - ); - const configFilePath = path.resolve(this.projectPath, userDataFile); - const context = dotenvUtil.deserialize( - await fs.readFile(configFilePath, { encoding: "utf8" }) - ); - const result = context.obj.TEAMS_APP_ID as string; - console.log(`TEAMS APP ID: ${result}`); - return result; - } - - public async getAadObjectId(): Promise { - const userDataFile = path.join( - TestFilePath.configurationFolder, - `.env.local` - ); - const configFilePath = path.resolve( - this.testRootFolder, - this.appName, - userDataFile - ); - const context = dotenvUtil.deserialize( - await fs.readFile(configFilePath, { encoding: "utf8" }) - ); - const result = context.obj.AAD_APP_OBJECT_ID as string; - console.log(`TEAMS APP OBJECT ID: ${result}`); - return result; - } - - public async addFeatureV2(feature: string): Promise { - await CliHelper.addFeature(feature, this.projectPath); - } - - public async getBotAppId(): Promise { - const userDataFile = path.join( - TestFilePath.configurationFolder, - `.env.local` - ); - const configFilePath = path.resolve( - this.testRootFolder, - this.appName, - userDataFile - ); - const context = dotenvUtil.deserialize( - await fs.readFile(configFilePath, { encoding: "utf8" }) - ); - const result = context.obj.BOT_ID as string; - console.log(`TEAMS BOT ID: ${result}`); - return result; - } - - public async provisionWithCLI( - env: "local" | "dev", - v3: boolean, - environment: NodeJS.ProcessEnv = process.env - ): Promise { - process.env["AZURE_RESOURCE_GROUP_NAME"] = this.rgName; - await AzSqlHelper.login(); - const azhelper = new AzSqlHelper(this.rgName, []); - await azhelper.createResourceGroup(); - - await CliHelper.provisionProject(this.projectPath, env, v3, environment); - } - - public async deployWithCLI(env: "local" | "dev"): Promise { - await CliHelper.deploy(this.projectPath, env); - } - - public async publish(env: "local" | "dev"): Promise { - await CliHelper.publishProject(this.projectPath, env); - } - - public async debugWithCLI(env: "local" | "dev", v3?: boolean): Promise { - await CliHelper.debugProject(this.projectPath, env, v3); - } - - public async provisionProject( - appName: string, - projectPath = "", - createRg = true, - tool: "ttk" | "cli" = "cli", - option = "", - env: "dev" | "local" = "dev", - processEnv?: NodeJS.ProcessEnv - ) { - if (tool === "cli") { - await this.runCliProvision( - projectPath, - appName, - createRg, - option, - env, - processEnv - ); - } else { - await runProvision(appName); - } - } - - public async deployProject( - projectPath: string, - waitTime: number = Timeout.tabDeploy, - tool: "ttk" | "cli" = "cli", - option = "", - env: "dev" | "local" = "dev", - processEnv?: NodeJS.ProcessEnv, - retries?: number, - newCommand?: string - ) { - if (tool === "cli") { - await this.runCliDeploy( - projectPath, - option, - env, - processEnv, - retries, - newCommand - ); - } else { - await runDeploy(waitTime); - } - } - - public async runCliProvision( - projectPath: string, - appName: string, - createRg = true, - option = "", - env: "dev" | "local" = "dev", - processEnv?: NodeJS.ProcessEnv - ) { - if (createRg) { - await createResourceGroup(appName, env, "westus"); - } - const resourceGroupName = `${appName}-${env}-rg`; - await CliHelper.showVersion(projectPath, processEnv); - await CliHelper.provisionProject2(projectPath, option, env, { - ...process.env, - AZURE_RESOURCE_GROUP_NAME: resourceGroupName, - }); - } - - public async runCliDeploy( - projectPath: string, - option = "", - env: "dev" | "local" = "dev", - processEnv?: NodeJS.ProcessEnv, - retries?: number, - newCommand?: string - ) { - await CliHelper.deployAll( - projectPath, - option, - env, - processEnv, - retries, - newCommand - ); - } -} diff --git a/packages/tests/src/ui-test/migration/msg/msg-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/msg/msg-debug-upgrade-debug.test.ts deleted file mode 100644 index 12b49d75ae..0000000000 --- a/packages/tests/src/ui-test/migration/msg/msg-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,106 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.MessageExtension, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] message extension template migrate test - js", - { - testPlanCaseId: 17184122, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("Start Bot"); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - throw new Error(error as string); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/msg/msg-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/msg/msg-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index a8c6512705..0000000000 --- a/packages/tests/src/ui-test/migration/msg/msg-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,111 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.MessageExtension, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] local debugged and provisioned message extension template upgrade test", - { - testPlanCaseId: 17184122, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - // v2 deploy - await mirgationDebugTestContext.deployWithCLI("dev"); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/msg/msg-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/msg/msg-upgrade-debug.test.ts deleted file mode 100644 index 3d75bd54ba..0000000000 --- a/packages/tests/src/ui-test/migration/msg/msg-upgrade-debug.test.ts +++ /dev/null @@ -1,102 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.MessageExtension, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] message extension template migrate test - js", - { - testPlanCaseId: 17184121, - author: "frankqian@microsoft.com", - }, - async () => { - // option 2: create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("Start Bot"); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - throw new Error(error as string); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/msg/msg-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/msg/msg-upgrade-provision-debug.test.ts deleted file mode 100644 index a769b2d3f9..0000000000 --- a/packages/tests/src/ui-test/migration/msg/msg-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,104 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateMsg, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] local debugged and provisioned message extension template upgrade test - js", - { - testPlanCaseId: 17184121, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-debug-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-debug-upgrade-debug-ts.test.ts deleted file mode 100644 index 81432339ae..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-debug-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,104 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test - ts", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot( - page, - "http://127.0.0.1:3978/api/notification" - ); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-debug-upgrade-debug.test.ts deleted file mode 100644 index 2353ec26b7..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,104 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test - js", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot( - page, - "http://127.0.0.1:3978/api/notification" - ); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-provision-upgrade-provision-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-provision-upgrade-provision-debug-ts.test.ts deleted file mode 100644 index 9886495a0f..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-provision-upgrade-provision-debug-ts.test.ts +++ /dev/null @@ -1,120 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateNotificationBot, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test - ts", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index d7b9f4801c..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,125 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateNotificationBot, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // remote provision - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-debug-ts.test.ts deleted file mode 100644 index e3dfc08e05..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,101 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { VSBrowser } from "vscode-extension-tester"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test - ts", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot( - page, - "http://127.0.0.1:3978/api/notification" - ); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-debug.test.ts deleted file mode 100644 index e4d1be3912..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-debug.test.ts +++ /dev/null @@ -1,101 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { VSBrowser } from "vscode-extension-tester"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot( - page, - "http://127.0.0.1:3978/api/notification" - ); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-provision-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-provision-debug-ts.test.ts deleted file mode 100644 index 30ab8f85a9..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-provision-debug-ts.test.ts +++ /dev/null @@ -1,119 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateNotificationBot, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test - ts", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-provision-debug.test.ts deleted file mode 100644 index 98bd57deba..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-func-http/notification-bot-func-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,119 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateNotificationBot, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Http - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] [P0] V2 notification bot template upgrade test - js", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-debug-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-debug-upgrade-debug-ts.test.ts deleted file mode 100644 index 33bb14daf3..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-debug-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,102 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] notification bot template upgrade test - ts", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-debug-upgrade-debug.test.ts deleted file mode 100644 index 82064dd3ba..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,102 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] notification bot template upgrade test", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-provision-upgrade-provision-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-provision-upgrade-provision-debug-ts.test.ts deleted file mode 100644 index 5e4d927949..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-provision-upgrade-provision-debug-ts.test.ts +++ /dev/null @@ -1,126 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] notification bot template upgrade test - ts", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.testRootFolder); - // remote provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 96f86e2f34..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,126 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] notification bot template upgrade test - js", - { - testPlanCaseId: 17184124, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.testRootFolder); - // remote provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-debug-ts.test.ts deleted file mode 100644 index 1fa1943024..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-debug-ts.test.ts +++ /dev/null @@ -1,99 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] notification bot template upgrade test - ts", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-debug.test.ts deleted file mode 100644 index 6e3cd871e6..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-debug.test.ts +++ /dev/null @@ -1,99 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, - LocalDebugTaskLabel, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.migrationTestCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "local"); - }); - - it( - "[auto] notification bot template upgrade test - js", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - await startDebugging("Debug (Chrome)"); - await waitForTerminal(LocalDebugTaskLabel.StartLocalTunnel); - try { - await waitForTerminal( - "Start Azurite emulator", - "Azurite Blob service is successfully listening" - ); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - "Worker process started and initialized" - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateNotificationBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-provision-debug-ts.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-provision-debug-ts.test.ts deleted file mode 100644 index 4725b0a072..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-provision-debug-ts.test.ts +++ /dev/null @@ -1,120 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "typescript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] notification bot template upgrade test - ts", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-provision-debug.test.ts deleted file mode 100644 index ca734cd080..0000000000 --- a/packages/tests/src/ui-test/migration/notification-bot-restify/notification-bot-restify-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,120 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Trigger, - Notification, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateNotificationBot, - initPage, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - getBotSiteEndpoint, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV3Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Notification, - "javascript", - Trigger.Restify - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(false, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - false, - true, - false - ); - }); - - it( - "[auto] notification bot template upgrade test - js", - { - testPlanCaseId: 17184123, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.testRootFolder - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - const funcEndpoint = await getBotSiteEndpoint( - mirgationDebugTestContext.projectPath, - "dev" - ); - await validateNotificationBot(page, funcEndpoint + "/api/notification"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-debug-upgrade-debug.test.ts deleted file mode 100644 index ad5e2a57dc..0000000000 --- a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,105 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "local"); - }); - - it( - "[auto] sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17183466, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await sampledebugContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait for bot Started"); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId(); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 68ae097f0c..0000000000 --- a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,94 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ - -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17183466, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", sampledebugContext.projectPath); - // v2 provision - await sampledebugContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await sampledebugContext.provisionWithCLI("dev", true); - // v3 deploy - await CLIVersionCheck("V3", sampledebugContext.projectPath); - await sampledebugContext.deployWithCLI("dev"); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-upgrade-debug.test.ts deleted file mode 100644 index 82a0aaf038..0000000000 --- a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-upgrade-debug.test.ts +++ /dev/null @@ -1,103 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ - -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "local"); - }); - - it( - "[auto] sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17431898, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait for bot Started"); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId("local"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-upgrade-provision-debug.test.ts deleted file mode 100644 index 32a65fafda..0000000000 --- a/packages/tests/src/ui-test/migration/sample-bot-sso/sample-bot-sso-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,89 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ - -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initPage, validateBot } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.HelloWorldBotSSO, - TemplateProjectFolder.HelloWorldBotSSO - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] sample bot sso V2 to V3 upgrade test", - { - testPlanCaseId: 17431898, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - CliHelper.setV3Enable(); - - // v3 provision - await sampledebugContext.provisionWithCLI("dev", true); - await CLIVersionCheck("V3", sampledebugContext.projectPath); - // v3 deploy - await sampledebugContext.deployWithCLI("dev"); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-debug-upgrade-debug.test.ts deleted file mode 100644 index 7b084d3643..0000000000 --- a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,99 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initTeamsPage } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.MyFirstMeeting, - TemplateProjectFolder.MyFirstMeeting - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, false, "local"); - }); - - it( - "[auto] sample hello world meeting V2 to V3 upgrade test", - { - testPlanCaseId: 17184043, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - - await validateNotification(Notification.Upgrade); - - // local debug - await sampledebugContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId("local"); - console.log(teamsAppId); - const page = await initTeamsPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password, - { - teamsAppName: "Hello_World_In_Meeting_App", - type: "meeting", - } - ); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index ce9e79f261..0000000000 --- a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,92 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initTeamsPage } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.MyFirstMeeting, - TemplateProjectFolder.MyFirstMeeting - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] sample hello world meeting V2 to V3 upgrade test", - { - testPlanCaseId: 17184043, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", sampledebugContext.projectPath); - // v2 provision - await sampledebugContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await sampledebugContext.provisionWithCLI("dev", true); - // v3 deploy - await CLIVersionCheck("V3", sampledebugContext.projectPath); - await sampledebugContext.deployWithCLI("dev"); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initTeamsPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password, - { - teamsAppName: "Hello_World_In_Meeting_App", - type: "meeting", - } - ); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-upgrade-debug.test.ts deleted file mode 100644 index 5ada20f9dd..0000000000 --- a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-upgrade-debug.test.ts +++ /dev/null @@ -1,101 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initTeamsPage } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.MyFirstMeeting, - TemplateProjectFolder.MyFirstMeeting - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "local"); - }); - - it( - "[auto] sample hello world meeting V2 to V3 upgrade test", - { - testPlanCaseId: 17184042, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait for bot Started"); - await waitForTerminal( - LocalDebugTaskLabel.StartBot, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId("local"); - console.log(teamsAppId); - const page = await initTeamsPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password, - { - teamsAppName: "Hello_World_In_Meeting_App", - type: "meeting", - } - ); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-upgrade-provision-debug.test.ts deleted file mode 100644 index 7ce1a944c2..0000000000 --- a/packages/tests/src/ui-test/migration/sample-hello-world-meeting/sample-hello-world-meeting-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,87 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initTeamsPage } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.MyFirstMeeting, - TemplateProjectFolder.MyFirstMeeting - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] sample hello world meeting V2 to V3 upgrade test", - { - testPlanCaseId: 17184042, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - CliHelper.setV3Enable(); - - // v3 provision - await sampledebugContext.provisionWithCLI("dev", true); - await CLIVersionCheck("V3", sampledebugContext.projectPath); - // v3 deploy - await sampledebugContext.deployWithCLI("dev"); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initTeamsPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password, - { - teamsAppName: "Hello_World_In_Meeting_App", - type: "meeting", - } - ); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-debug-upgrade-debug.test.ts deleted file mode 100644 index 8bc832b632..0000000000 --- a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,104 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initPage, validateQueryOrg } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.QueryOrg, - TemplateProjectFolder.QueryOrg - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "local"); - }); - - it( - "[auto] [P1] V2 local debugged and provisioned org user search connector sample upgrade test", - { - testPlanCaseId: 17183861, - author: "v-annefu@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await sampledebugContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait for application Started"); - await waitForTerminal( - LocalDebugTaskLabel.StartBotApp, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId("local"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateQueryOrg(page, { - displayName: Env.displayName, - appName: sampledebugContext.appName.substring(0, 10), - }); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index d0a7c4e464..0000000000 --- a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,91 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initPage, validateQueryOrg } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.QueryOrg, - TemplateProjectFolder.QueryOrg - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] [P1] V2 local debugged and provisioned org user search connector sample upgrade test", - { - testPlanCaseId: 17183861, - author: "v-annefu@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - await CLIVersionCheck("V2", sampledebugContext.projectPath); - // v2 provision - await sampledebugContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await sampledebugContext.provisionWithCLI("dev", true); - await CLIVersionCheck("V3", sampledebugContext.projectPath); - // v3 deploy - await sampledebugContext.deployWithCLI("dev"); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateQueryOrg(page, { - displayName: Env.displayName, - appName: sampledebugContext.appName.substring(0, 10), - }); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-upgrade-debug.test.ts deleted file mode 100644 index b20ed4e3d4..0000000000 --- a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-upgrade-debug.test.ts +++ /dev/null @@ -1,101 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - startDebugging, - waitForTerminal, -} from "../../../utils/vscodeOperation"; -import { initPage, validateQueryOrg } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.QueryOrg, - TemplateProjectFolder.QueryOrg - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "local"); - }); - - it( - "[auto] [P1] V2 org user search connector sample upgrade", - { - testPlanCaseId: 17183850, - author: "v-annefu@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Debug (Chrome)"); - - console.log("Start Local Tunnel"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait for application Started"); - await waitForTerminal( - LocalDebugTaskLabel.StartBotApp, - LocalDebugTaskResult.AppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await sampledebugContext.getTeamsAppId("local"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateQueryOrg(page, { - displayName: Env.displayName, - appName: sampledebugContext.appName.substring(0, 10), - }); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-upgrade-provision-debug.test.ts deleted file mode 100644 index 78ac86eae5..0000000000 --- a/packages/tests/src/ui-test/migration/sample-org-user-search-connector/sample-org-user-search-connector-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,87 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { SampledebugContext } from "../../samples/sampledebugContext"; -import { - Timeout, - TemplateProject, - Notification, - TemplateProjectFolder, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { initPage, validateQueryOrg } from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let sampledebugContext: SampledebugContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - sampledebugContext = new SampledebugContext( - TemplateProject.QueryOrg, - TemplateProjectFolder.QueryOrg - ); - await sampledebugContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await sampledebugContext.after(true, true, "dev"); - }); - - it( - "[auto] [P1] V2 org user search connector sample upgrade", - { - testPlanCaseId: 17183850, - author: "v-annefu@microsoft.com", - }, - async () => { - // create v2 project using CLI - await sampledebugContext.openResourceFolder(); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - sampledebugContext.projectPath - ); - CliHelper.setV3Enable(); - - // v3 provision - await sampledebugContext.provisionWithCLI("dev", true); - await CLIVersionCheck("V3", sampledebugContext.projectPath); - // v3 deploy - await sampledebugContext.deployWithCLI("dev"); - - const teamsAppId = await sampledebugContext.getTeamsAppId("dev"); - console.log(teamsAppId); - const page = await initPage( - sampledebugContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateQueryOrg(page, { - displayName: Env.displayName, - appName: sampledebugContext.appName.substring(0, 10), - }); - console.log("debug finish!"); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-debug-upgrade-debug.test.ts deleted file mode 100644 index fcd9e7e31d..0000000000 --- a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,98 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateMsg } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SearchApp, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 search app tab migrate test - js", - { - testPlanCaseId: 17184363, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug in Teams (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 9b67e2c598..0000000000 --- a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,111 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateMsg } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import * as dotenv from "dotenv"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; -dotenv.config(); - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SearchApp, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 search app tab migrate test - js", - { - testPlanCaseId: 17184363, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-upgrade-debug.test.ts deleted file mode 100644 index 79f3efde59..0000000000 --- a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-upgrade-debug.test.ts +++ /dev/null @@ -1,92 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateMsg } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgrade, - waitForTerminal, - validateUpgrade, - upgradeByTreeView, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SearchApp, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 search app tab migrate test - js", - { - testPlanCaseId: 17184362, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug in Teams (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-upgrade-provision-debug.test.ts deleted file mode 100644 index 58958ddb9a..0000000000 --- a/packages/tests/src/ui-test/migration/search-based-msg/search-based-message-extension-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,107 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Frank Qian - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { initPage, validateMsg } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import * as dotenv from "dotenv"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; -dotenv.config(); - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SearchApp, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 search app migrate test - js", - { - testPlanCaseId: 17184362, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateMsg(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/spfx/spfx-react-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/spfx/spfx-react-debug-upgrade-debug.test.ts deleted file mode 100644 index b73034322c..0000000000 --- a/packages/tests/src/ui-test/migration/spfx/spfx-react-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,105 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Helly Zhang - */ - -import { expect } from "chai"; -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - Framework, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - startDebugging, - waitForTerminal, - validateNotification, - upgradeByTreeView, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { - initPage, - validateTeamsWorkbench, -} from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Spfx, - "javascript", - undefined, - Framework.React - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(); - }); - - it( - "[auto] V2 spfx react migrate test", - { - testPlanCaseId: 17184356, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Teams workbench (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.GulpServe, - LocalDebugTaskResult.GulpServeSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - console.log(teamsAppId); - expect(teamsAppId.length).to.equal(36); - - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateTeamsWorkbench(page, Env.displayName); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/spfx/spfx-react-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/spfx/spfx-react-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index c4bc06f78b..0000000000 --- a/packages/tests/src/ui-test/migration/spfx/spfx-react-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,119 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Helly Zhang - */ - -import { expect } from "chai"; -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - Framework, - CommandPaletteCommands, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateTeamsWorkbench, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - getNotification, - execCommandIfExist, - clearNotifications, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser, InputBox } from "vscode-extension-tester"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Spfx, - "javascript", - undefined, - Framework.React - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(); - }); - - it( - "[auto] V2 spfx react migrate test", - { - testPlanCaseId: 17184356, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - await CLIVersionCheck("V2", mirgationDebugTestContext.projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await clearNotifications(); - await execCommandIfExist(CommandPaletteCommands.ProvisionCommand); - const driver = VSBrowser.instance.driver; - await driver.sleep(Timeout.spfxProvision); - await getNotification( - Notification.ProvisionSucceeded, - Timeout.shortTimeWait - ); - - await clearNotifications(); - await execCommandIfExist(CommandPaletteCommands.DeployCommand); - try { - const deployConfirmInput = await InputBox.create(); - await deployConfirmInput.confirm(); - } catch (error) { - console.log("No need to confirm to deploy."); - } - await driver.sleep(Timeout.spfxDeploy); - await getNotification(Notification.DeploySucceeded, Timeout.longTimeWait); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - expect(teamsAppId.length).to.equal(36); - console.log(teamsAppId); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateTeamsWorkbench(page, Env.displayName); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/spfx/spfx-react-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/spfx/spfx-react-upgrade-debug.test.ts deleted file mode 100644 index 330538a621..0000000000 --- a/packages/tests/src/ui-test/migration/spfx/spfx-react-upgrade-debug.test.ts +++ /dev/null @@ -1,102 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Helly Zhang - */ - -import { expect } from "chai"; -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - Framework, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - startDebugging, - waitForTerminal, - validateNotification, - upgradeByTreeView, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { - initPage, - validateTeamsWorkbench, -} from "../../../utils/playwrightOperation"; -import { Env } from "../../../utils/env"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Spfx, - "javascript", - undefined, - Framework.React - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(); - }); - - it( - "[auto] V2 spfx react migrate test", - { - testPlanCaseId: 17184355, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - try { - // local debug - await startDebugging("Teams workbench (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.GulpServe, - LocalDebugTaskResult.GulpServeSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - expect(teamsAppId.length).to.equal(36); - console.log(teamsAppId); - - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateTeamsWorkbench(page, Env.displayName); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/spfx/spfx-react-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/spfx/spfx-react-upgrade-provision-debug.test.ts deleted file mode 100644 index 1a8dfcf25f..0000000000 --- a/packages/tests/src/ui-test/migration/spfx/spfx-react-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,114 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Helly Zhang - */ - -import { expect } from "chai"; -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - Framework, - CommandPaletteCommands, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - initPage, - validateTeamsWorkbench, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - validateUpgrade, - upgradeByTreeView, - getNotification, - execCommandIfExist, - clearNotifications, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser, InputBox } from "vscode-extension-tester"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Spfx, - "javascript", - undefined, - Framework.React - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(); - }); - - it( - "[auto] V2 spfx react migrate test", - { - testPlanCaseId: 17184355, - author: "v-helzha@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - await clearNotifications(); - await execCommandIfExist(CommandPaletteCommands.ProvisionCommand); - const driver = VSBrowser.instance.driver; - await driver.sleep(Timeout.spfxProvision); - await getNotification( - Notification.ProvisionSucceeded, - Timeout.shortTimeWait - ); - - await clearNotifications(); - await execCommandIfExist(CommandPaletteCommands.DeployCommand); - try { - const deployConfirmInput = await InputBox.create(); - await deployConfirmInput.confirm(); - } catch (error) { - console.log("No need to confirm to deploy."); - } - await driver.sleep(Timeout.spfxDeploy); - await getNotification(Notification.DeploySucceeded, Timeout.longTimeWait); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - expect(teamsAppId.length).to.equal(36); - console.log(teamsAppId); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - // await validateTeamsWorkbench(page, Env.displayName); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-debug-upgrade-debug.test.ts deleted file mode 100644 index b696b8da63..0000000000 --- a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,95 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SsoLaunchPage, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 sso personal tab migrate test - js", - { - testPlanCaseId: 17184361, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug in Teams (Chrome)"); - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 6683e915e8..0000000000 --- a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,104 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SsoLaunchPage, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, false, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - false, - false - ); - }); - - it( - "[auto] V2 sso personal tab migrate test - js", - { - testPlanCaseId: 17184361, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-upgrade-debug.test.ts deleted file mode 100644 index ec55e618ff..0000000000 --- a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-upgrade-debug.test.ts +++ /dev/null @@ -1,92 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SsoLaunchPage, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 sso personal tab migrate test - js", - { - testPlanCaseId: 17184360, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug in Teams (Chrome)"); - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-upgrade-provision-debug.test.ts deleted file mode 100644 index 1f7682c1b4..0000000000 --- a/packages/tests/src/ui-test/migration/sso-personal-tab/sso-personal-tab-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,102 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.M365SsoLaunchPage, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, false, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - false, - false - ); - }); - - it( - "[auto] V2 sso personal tab migrate test - js", - { - testPlanCaseId: 17184360, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - // UI verify - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-debug-upgrade-debug.test.ts deleted file mode 100644 index 4b611fd824..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,118 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - ResourceToDeploy, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateBot, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateFunctionAuthorizationPolicy } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17184049, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - - console.log("wait backend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartBackend, - LocalDebugTaskResult.BotAppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index e3b541081f..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,120 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - ResourceToDeploy, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateBot, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - updateFunctionAuthorizationPolicy, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17184049, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-upgrade-debug.test.ts deleted file mode 100644 index f189595fa7..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-upgrade-debug.test.ts +++ /dev/null @@ -1,115 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - ResourceToDeploy, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateBot, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateFunctionAuthorizationPolicy } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17184048, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - - console.log("wait backend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartBackend, - LocalDebugTaskResult.BotAppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-upgrade-provision-debug.test.ts deleted file mode 100644 index e74e7a3728..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-bot-function/sso-tab-bot-function-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,118 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - ResourceToDeploy, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateBot, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - updateFunctionAuthorizationPolicy, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] tab, bot, function app with sso migrate test - js", - { - testPlanCaseId: 17184048, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Bot); - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-debug-upgrade-debug.test.ts deleted file mode 100644 index 05118242f8..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,110 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - ResourceToDeploy, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateFunctionAuthorizationPolicy } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 tab, function app with sso migrate test - js", - { - testPlanCaseId: 17184045, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - - console.log("wait backend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartBackend, - LocalDebugTaskResult.BotAppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: true, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index c9d5e794f2..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,119 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - ResourceToDeploy, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - updateFunctionAuthorizationPolicy, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] tab, function app with sso migrate test - js", - { - testPlanCaseId: 17184045, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: true, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-upgrade-debug.test.ts deleted file mode 100644 index 33a18133e2..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-upgrade-debug.test.ts +++ /dev/null @@ -1,106 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - ResourceToDeploy, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; -import { updateFunctionAuthorizationPolicy } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] tab, function app with sso migrate test - js", - { - testPlanCaseId: 17184044, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - - console.log("wait backend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartBackend, - LocalDebugTaskResult.BotAppSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: true, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-upgrade-provision-debug.test.ts deleted file mode 100644 index 6218432adf..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab-func/sso-tab-function-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,116 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - ResourceToDeploy, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { - CLIVersionCheck, - updateFunctionAuthorizationPolicy, -} from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] tab, function app with sso migrate test - js", - { - testPlanCaseId: 17184044, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - const projectPath = await mirgationDebugTestContext.createProjectCLI( - false - ); - // verify popup - await validateNotification(Notification.Upgrade); - - // add feature - await mirgationDebugTestContext.addFeatureV2(ResourceToDeploy.Function); - - await updateFunctionAuthorizationPolicy("4.2.5", projectPath); - // upgrade - await upgradeByTreeView(); - //verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: true, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab/sso-tab-debug-upgrade-debug.test.ts deleted file mode 100644 index e48c0212f8..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,96 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, false, "local"); - }); - - it( - "[auto] Tab app with sso migrate test - js", - { - testPlanCaseId: 17184116, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab/sso-tab-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 55d61758d0..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,107 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import * as dotenv from "dotenv"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; -dotenv.config(); - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, false, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - false, - false - ); - }); - - it( - "[auto] Tab app with sso migrate test - js", - { - testPlanCaseId: 17184116, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab/sso-tab-upgrade-debug.test.ts deleted file mode 100644 index 9b20b4bad7..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-upgrade-debug.test.ts +++ /dev/null @@ -1,93 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, false, "local"); - }); - - it( - "[auto] Tab app with sso migrate test - js", - { - testPlanCaseId: 17184115, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - - console.log("wait frontend start"); - await waitForTerminal( - LocalDebugTaskLabel.StartFrontend, - LocalDebugTaskResult.FrontendSuccess - ); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("local"); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/sso-tab/sso-tab-upgrade-provision-debug.test.ts deleted file mode 100644 index c6a1eb5d52..0000000000 --- a/packages/tests/src/ui-test/migration/sso-tab/sso-tab-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,104 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { validateTab, initPage } from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import * as dotenv from "dotenv"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; -dotenv.config(); - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Tab, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, false, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - false, - false - ); - }); - - it( - "[auto] Tab app with sso migrate test - js", - { - testPlanCaseId: 17184115, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateTab(page, { - displayName: Env.displayName, - includeFunction: false, - }); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/v3migration/v2-to-v3-upgrade.test.ts b/packages/tests/src/ui-test/migration/v3migration/v2-to-v3-upgrade.test.ts deleted file mode 100644 index 3af9d17ff3..0000000000 --- a/packages/tests/src/ui-test/migration/v3migration/v2-to-v3-upgrade.test.ts +++ /dev/null @@ -1,59 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. - -/** - * @author Ivan Chen - */ - -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { - validateNotification, - startDebugging, - validateUpgrade, - upgrade, -} from "../../../utils/vscodeOperation"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "typescript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(); - }); - - it( - "[auto] V2 to V3 upgrade test", - { - testPlanCaseId: 17183430, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - - // verify popup - await validateNotification(Notification.Upgrade); - await startDebugging("Debug (Chrome)"); - - // upgrade - await upgrade(); - - //verify upgrade - await validateUpgrade(); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/v3migration/v3-to-v2-debug.test.ts b/packages/tests/src/ui-test/migration/v3migration/v3-to-v2-debug.test.ts deleted file mode 100644 index d14595b1ce..0000000000 --- a/packages/tests/src/ui-test/migration/v3migration/v3-to-v2-debug.test.ts +++ /dev/null @@ -1,53 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - startDebugging, - stopDebugging, -} from "../../../utils/vscodeOperation"; -import { VSBrowser } from "vscode-extension-tester"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testCase); - let mirgationDebugTestContext: MigrationTestContext; - CliHelper.setV2Enable(); - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.Bot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(); - }); - - it( - "[auto] V3 to V2 debug test", - { - testPlanCaseId: 17183411, - author: "v-ivanchen@microsoft.com", - }, - async () => { - // create v3 project using CLI - await mirgationDebugTestContext.createProjectCLI(true); - - // verify popup - await validateNotification(Notification.Incompatible); - await startDebugging("Debug (Chrome)"); - VSBrowser.instance.driver.sleep(Timeout.shortTimeWait); - await stopDebugging(); - await validateNotification(Notification.TaskError); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-debug-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-debug-upgrade-debug.test.ts deleted file mode 100644 index 700ffcdc06..0000000000 --- a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-debug-upgrade-debug.test.ts +++ /dev/null @@ -1,101 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBot, - initPage, - validateWorkFlowBot, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.WorkflowBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 workflow bot migrate test - js", - { - testPlanCaseId: 17184126, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // local debug - await mirgationDebugTestContext.debugWithCLI("local", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - await validateWorkFlowBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-provision-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-provision-upgrade-provision-debug.test.ts deleted file mode 100644 index 6506a5ab94..0000000000 --- a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-provision-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,110 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBot, - initPage, - validateWorkFlowBot, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.WorkflowBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 workflow bot migrate test - js", - { - testPlanCaseId: 17184126, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // v2 provision - await mirgationDebugTestContext.provisionWithCLI("dev", false); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - await validateWorkFlowBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-upgrade-debug.test.ts b/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-upgrade-debug.test.ts deleted file mode 100644 index a885b54e8d..0000000000 --- a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-upgrade-debug.test.ts +++ /dev/null @@ -1,98 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { - Timeout, - Capability, - Notification, - LocalDebugTaskLabel, - LocalDebugTaskResult, -} from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBot, - initPage, - validateWorkFlowBot, -} from "../../../utils/playwrightOperation"; -import { - validateNotification, - startDebugging, - upgradeByTreeView, - waitForTerminal, - validateUpgrade, -} from "../../../utils/vscodeOperation"; -import { CliHelper } from "../../cliHelper"; -import { VSBrowser } from "vscode-extension-tester"; -import { getScreenshotName } from "../../../utils/nameUtil"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.WorkflowBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "local"); - }); - - it( - "[auto] V2 workflow bot migrate test - js", - { - testPlanCaseId: 17184127, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - // enable cli v3 - CliHelper.setV3Enable(); - - // local debug with TTK - try { - await startDebugging("Debug (Chrome)"); - await waitForTerminal( - LocalDebugTaskLabel.StartLocalTunnel, - LocalDebugTaskResult.StartSuccess - ); - - await waitForTerminal(LocalDebugTaskLabel.StartBot, "Bot started"); - } catch (error) { - await VSBrowser.instance.takeScreenshot(getScreenshotName("debug")); - console.log("[Skip Error]: ", error); - await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); - } - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId(); - - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - await validateWorkFlowBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-upgrade-provision-debug.test.ts b/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-upgrade-provision-debug.test.ts deleted file mode 100644 index 197c8d8ce3..0000000000 --- a/packages/tests/src/ui-test/migration/workflow-bot/workflow-bot-upgrade-provision-debug.test.ts +++ /dev/null @@ -1,107 +0,0 @@ -// Copyright (c) Microsoft Corporation. -// Licensed under the MIT license. -import { MigrationTestContext } from "../migrationContext"; -import { Timeout, Capability, Notification } from "../../../utils/constants"; -import { it } from "../../../utils/it"; -import { Env } from "../../../utils/env"; -import { - validateBot, - initPage, - validateWorkFlowBot, -} from "../../../utils/playwrightOperation"; -import { CliHelper } from "../../cliHelper"; -import { - validateNotification, - upgradeByTreeView, - validateUpgrade, - execCommandIfExist, -} from "../../../utils/vscodeOperation"; -import { CLIVersionCheck } from "../../../utils/commonUtils"; - -describe("Migration Tests", function () { - this.timeout(Timeout.testAzureCase); - let mirgationDebugTestContext: MigrationTestContext; - - beforeEach(async function () { - // ensure workbench is ready - this.timeout(Timeout.prepareTestCase); - - mirgationDebugTestContext = new MigrationTestContext( - Capability.WorkflowBot, - "javascript" - ); - await mirgationDebugTestContext.before(); - }); - - afterEach(async function () { - this.timeout(Timeout.finishTestCase); - await mirgationDebugTestContext.after(true, true, "dev"); - - //Close the folder and cleanup local sample project - await execCommandIfExist("Workspaces: Close Workspace", Timeout.webView); - console.log( - `[Successfully] start to clean up for ${mirgationDebugTestContext.projectPath}` - ); - await mirgationDebugTestContext.cleanUp( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath, - true, - true, - false - ); - }); - - it( - "[auto] V2 workflow bot migrate test - js", - { - testPlanCaseId: 17184127, - author: "frankqian@microsoft.com", - }, - async () => { - // create v2 project using CLI - await mirgationDebugTestContext.createProjectCLI(false); - // verify popup - await validateNotification(Notification.Upgrade); - - // upgrade - await upgradeByTreeView(); - // verify upgrade - await validateUpgrade(); - - // install test cil in project - await CliHelper.installCLI( - Env.TARGET_CLI, - false, - mirgationDebugTestContext.projectPath - ); - // enable cli v3 - CliHelper.setV3Enable(); - - // v3 provision - await mirgationDebugTestContext.provisionProject( - mirgationDebugTestContext.appName, - mirgationDebugTestContext.projectPath - ); - // v3 deploy - await CLIVersionCheck("V3", mirgationDebugTestContext.projectPath); - await mirgationDebugTestContext.deployProject( - mirgationDebugTestContext.projectPath, - Timeout.botDeploy - ); - - const teamsAppId = await mirgationDebugTestContext.getTeamsAppId("dev"); - // UI verify - const page = await initPage( - mirgationDebugTestContext.context!, - teamsAppId, - Env.username, - Env.password - ); - await validateBot(page, { - botCommand: "helloWorld", - expected: "Your Hello World Bot is Running", - }); - await validateWorkFlowBot(page); - } - ); -}); diff --git a/packages/tests/src/ui-test/remotedebug/remotedebug-notification-restify-ts-win-only.test.ts b/packages/tests/src/ui-test/remotedebug/remotedebug-notification-express-ts-win-only.test.ts similarity index 92% rename from packages/tests/src/ui-test/remotedebug/remotedebug-notification-restify-ts-win-only.test.ts rename to packages/tests/src/ui-test/remotedebug/remotedebug-notification-express-ts-win-only.test.ts index 709541d490..d5705c336f 100644 --- a/packages/tests/src/ui-test/remotedebug/remotedebug-notification-restify-ts-win-only.test.ts +++ b/packages/tests/src/ui-test/remotedebug/remotedebug-notification-express-ts-win-only.test.ts @@ -38,7 +38,7 @@ describe("Remote debug Tests", function () { beforeEach(async function () { // ensure workbench is ready this.timeout(Timeout.prepareTestCase); - remoteDebugTestContext = new RemoteDebugTestContext("restnoti"); + remoteDebugTestContext = new RemoteDebugTestContext("expressnoti"); testRootFolder = remoteDebugTestContext.testRootFolder; appName = remoteDebugTestContext.appName; newAppFolderName = appName + appNameCopySuffix; @@ -64,14 +64,14 @@ describe("Remote debug Tests", function () { }); it( - "[auto] [Typescript] Remote debug for restify notification bot project Tests", + "[auto] [Typescript] Remote debug for express notification bot project Tests", { testPlanCaseId: 14483095, author: "v-helzha@microsoft.com", }, async function () { const driver = VSBrowser.instance.driver; - await createNewProject("restnoti", appName, { lang: "TypeScript" }); + await createNewProject("expressnoti", appName, { lang: "TypeScript" }); validateFileExist(projectPath, "src/index.ts"); await provisionProject(appName, projectPath); await deployProject(projectPath, Timeout.botDeploy); diff --git a/packages/tests/src/ui-test/remotedebug/remotedebug-notification-restify-win-only.test.ts b/packages/tests/src/ui-test/remotedebug/remotedebug-notification-express-win-only.test.ts similarity index 93% rename from packages/tests/src/ui-test/remotedebug/remotedebug-notification-restify-win-only.test.ts rename to packages/tests/src/ui-test/remotedebug/remotedebug-notification-express-win-only.test.ts index abe02f9d6f..1e7f4002d3 100644 --- a/packages/tests/src/ui-test/remotedebug/remotedebug-notification-restify-win-only.test.ts +++ b/packages/tests/src/ui-test/remotedebug/remotedebug-notification-express-win-only.test.ts @@ -38,7 +38,7 @@ describe("Remote debug Tests", function () { beforeEach(async function () { // ensure workbench is ready this.timeout(Timeout.prepareTestCase); - remoteDebugTestContext = new RemoteDebugTestContext("restnoti"); + remoteDebugTestContext = new RemoteDebugTestContext("expressnoti"); testRootFolder = remoteDebugTestContext.testRootFolder; appName = remoteDebugTestContext.appName; newAppFolderName = appName + appNameCopySuffix; @@ -64,14 +64,14 @@ describe("Remote debug Tests", function () { }); it( - "[auto] Remote debug for restify notification project Tests", + "[auto] Remote debug for express notification project Tests", { testPlanCaseId: 14112917, author: "v-helzha@microsoft.com", }, async function () { const driver = VSBrowser.instance.driver; - await createNewProject("restnoti", appName); + await createNewProject("expressnoti", appName); validateFileExist(projectPath, "src/index.js"); await provisionProject(appName, projectPath); await deployProject(projectPath, Timeout.botDeploy); diff --git a/packages/tests/src/ui-test/samples/sample-localdebug-large-scale-notification.test.ts b/packages/tests/src/ui-test/samples/sample-localdebug-large-scale-notification.test.ts index 5fb17f92ce..75049b0c4b 100644 --- a/packages/tests/src/ui-test/samples/sample-localdebug-large-scale-notification.test.ts +++ b/packages/tests/src/ui-test/samples/sample-localdebug-large-scale-notification.test.ts @@ -35,6 +35,19 @@ class LargeNotiTestCase extends CaseFactory { fs.writeFileSync(envFile, envFileString); console.log(`add endpoint ${envFileString} to .env.${env} file`); + // add storage account key + const envUserFile = path.resolve( + sampledebugContext.projectPath, + "env", + `.env.${env}.user` + ); + let envUserFileString = fs.readFileSync(envUserFile, "utf-8"); + envUserFileString += `\nSECRET_STORAGE_ACCOUNT_KEY=${process.env["STORAGE_ACCOUNT_KEY"]}`; + fs.writeFileSync(envUserFile, envUserFileString); + console.log( + `add SECRET_STORAGE_ACCOUNT_KEY ${process.env["STORAGE_ACCOUNT_KEY"]} to .env.${env}.user file` + ); + // add connect string into local.setting.json const configFilePath = path.resolve( sampledebugContext.projectPath, diff --git a/packages/tests/src/ui-test/samples/sample-localdebug-todo-list-sql.test.ts b/packages/tests/src/ui-test/samples/sample-localdebug-todo-list-sql.test.ts index b78b0e09cd..c09cecaea8 100644 --- a/packages/tests/src/ui-test/samples/sample-localdebug-todo-list-sql.test.ts +++ b/packages/tests/src/ui-test/samples/sample-localdebug-todo-list-sql.test.ts @@ -75,6 +75,7 @@ class TodoListBackendTestCase extends CaseFactory { teamsAppId: string, options?: { teamsAppName: string; + type: string; } ): Promise { return await initTeamsPage( @@ -84,6 +85,7 @@ class TodoListBackendTestCase extends CaseFactory { Env.password, { teamsAppName: options?.teamsAppName, + type: options?.type, } ); } @@ -110,6 +112,7 @@ class TodoListBackendTestCase extends CaseFactory { Env.password, { teamsAppName: options?.teamsAppName, + type: options?.type, } ); } @@ -123,7 +126,7 @@ new TodoListBackendTestCase( [LocalDebugTaskLabel.StartFrontend, LocalDebugTaskLabel.StartBackend], { teamsAppName: "toDoList-local", - skipValidation: false, testRootFolder: path.resolve(os.homedir(), "resourse"), // fix eslint error + type: "spfx", } ).test(); diff --git a/packages/tests/src/ui-test/samples/sample-remotedebug-todo-list-sql.test.ts b/packages/tests/src/ui-test/samples/sample-remotedebug-todo-list-sql.test.ts index 1203add65e..2988a91dfb 100644 --- a/packages/tests/src/ui-test/samples/sample-remotedebug-todo-list-sql.test.ts +++ b/packages/tests/src/ui-test/samples/sample-remotedebug-todo-list-sql.test.ts @@ -109,6 +109,7 @@ class TodoListBackendTestCase extends CaseFactory { teamsAppId: string, options?: { teamsAppName: string; + type: string; } ): Promise { return await initTeamsPage( @@ -118,6 +119,7 @@ class TodoListBackendTestCase extends CaseFactory { Env.password, { teamsAppName: options?.teamsAppName, + type: options?.type, } ); } @@ -134,7 +136,7 @@ new TodoListBackendTestCase( [], { teamsAppName: "toDoList-dev", - skipValidation: false, testRootFolder: path.resolve(os.homedir(), "resourse"), // fix eslint error + type: "spfx", } ).test(); diff --git a/packages/tests/src/ui-test/testtooldebug/testtooldebug-command-and-response.test.ts b/packages/tests/src/ui-test/testtooldebug/testtooldebug-command-and-response.test.ts new file mode 100644 index 0000000000..c65f3e6bce --- /dev/null +++ b/packages/tests/src/ui-test/testtooldebug/testtooldebug-command-and-response.test.ts @@ -0,0 +1,97 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. + +/** + * @author Helly Zhang + */ + +import * as path from "path"; +import os from "os"; +import { startDebugging, waitForTerminal } from "../../utils/vscodeOperation"; +import { LocalDebugTestContext } from "../localdebug/localdebugContext"; +import { + Timeout, + LocalDebugTaskLabel, + LocalDebugTaskInfo, + DebugItemSelect, + LocalDebugTaskLabel2, +} from "../../utils/constants"; +import { it } from "../../utils/it"; +import { validateFileExist } from "../../utils/commonUtils"; +import { VSBrowser } from "vscode-extension-tester"; +import { expect } from "chai"; +import { getScreenshotName } from "../../utils/nameUtil"; +import { validateWelcomeAndReplyBot } from "../../utils/testToolValidations"; + +// TODO: Change preview test to normal test before rc release +describe("Command And Response Bot Local Debug Tests", function () { + this.timeout(Timeout.testAzureCase); + let localDebugTestContext: LocalDebugTestContext; + let successFlag = true; + let errorMessage = ""; + + const oldEnv = Object.assign({}, process.env); + beforeEach(async function () { + // ensure workbench is ready + this.timeout(Timeout.prepareTestCase); + localDebugTestContext = new LocalDebugTestContext("crbot"); + await localDebugTestContext.before(); + }); + + after(async function () { + this.timeout(Timeout.finishTestCase); + await localDebugTestContext.after(false, false); + setTimeout(() => { + if (os.type() === "Windows_NT") { + if (successFlag) process.exit(0); + else process.exit(1); + } + }, 30000); + }); + + it( + "[auto] Local debug using Test Tool for Command and Response Bot App", + { + testPlanCaseId: 25666171, + author: "v-helzha@microsoft.com", + }, + async function () { + try { + const projectPath = path.resolve( + localDebugTestContext.testRootFolder, + localDebugTestContext.appName + ); + validateFileExist(projectPath, "src/index.js"); + const driver = VSBrowser.instance.driver; + + // local debug in Test Tool + await startDebugging(DebugItemSelect.DebugInTestTool); + + await waitForTerminal( + LocalDebugTaskLabel.StartBotApp, + LocalDebugTaskInfo.StartBotInfo + ); + + await waitForTerminal(LocalDebugTaskLabel2.StartTestTool); + + await driver.sleep(Timeout.startdebugging); + + await validateWelcomeAndReplyBot(localDebugTestContext.context!, { + hasWelcomeMessage: true, + hasCommandReplyValidation: true, + botCommand: "helloWorld", + expectedWelcomeMessage: "Welcome to the Command Bot!", + expectedReplyMessage: "Your Hello World App is Running", + timeout: Timeout.longTimeWait, + }); + } catch (error) { + successFlag = false; + errorMessage = "[Error]: " + error; + await VSBrowser.instance.takeScreenshot(getScreenshotName("error")); + await VSBrowser.instance.driver.sleep(Timeout.playwrightDefaultTimeout); + } + expect(successFlag, errorMessage).to.true; + console.log("debug finish!"); + } + ); +}); diff --git a/packages/tests/src/utils/constants.ts b/packages/tests/src/utils/constants.ts index a8d2f001cd..bc6d3ee1da 100644 --- a/packages/tests/src/utils/constants.ts +++ b/packages/tests/src/utils/constants.ts @@ -178,11 +178,12 @@ export enum Capability { Agent = "custom-copilot-agent", TaskPane = "taskpane", ApiPlugin = "api-plugin", + DeclarativeAgent = "declarative-agent", } export enum Trigger { Http = "http-functions", - Restify = "http-restify", + Express = "http-express", Timmer = "timer-functions", } @@ -349,7 +350,7 @@ export type AppType = | "bot" | "crbot" // command and response bot (name cannot be too long or it will exceed teams app name limit) | "funcnoti" // functions notification bot - | "restnoti" // restify notification bot + | "expressnoti" // express notification bot | "msg" | "msgsa" | "m365lp" @@ -408,6 +409,7 @@ export class LocalDebugTaskResult { static readonly FrontendSuccess = "Compiled successfully"; static readonly FrontendReady = "ready"; static readonly FrontendNoIssue = "webpack compiled"; + static readonly FrontendStarted = "Express server listening on"; static readonly StartSuccess = "started successfully"; static readonly AzuriteSuccess = "Azurite Table service is successfully"; static readonly CompiledSuccess = "Found 0 errors"; @@ -426,6 +428,7 @@ export class LocalDebugTaskResult { export enum LocalDebugTaskLabel2 { StartBot2 = "Start Bot", PythonDebugConsole = "Python Debug Console", + StartTestTool = "Start Test Tool", } export enum LocalDebugError { @@ -442,6 +445,7 @@ export class LocalDebugTaskInfo { export class DebugItemSelect { static readonly DebugInTeamsUsingChrome = "Debug in Teams (Chrome)"; + static readonly DebugInTestTool = "Debug in Test Tool"; } export class TestFilePath { diff --git a/packages/tests/src/utils/executor.ts b/packages/tests/src/utils/executor.ts index a30e49932e..0bb3a0cd9d 100644 --- a/packages/tests/src/utils/executor.ts +++ b/packages/tests/src/utils/executor.ts @@ -106,8 +106,18 @@ export class Executor { language: ProgrammingLanguage, customized: Record = {} ) { + let languageParam = ""; + if (language === ProgrammingLanguage.CSharp) { + languageParam = "--runtime dotnet"; + } else if ( + language !== ProgrammingLanguage.Common && + language !== ProgrammingLanguage.None + ) { + languageParam = `--programming-language ${language}`; + } + const command = - `teamsapp new --interactive false --app-name ${appName} --capability ${capability} --programming-language ${language} ` + + `teamsapp new --interactive false --app-name ${appName} --capability ${capability} ${languageParam} ` + Object.entries(customized) .map(([key, value]) => "--" + key + " " + value) .join(" "); diff --git a/packages/tests/src/utils/playwrightOperation.ts b/packages/tests/src/utils/playwrightOperation.ts index 0cc5f2ae57..ed791e24d5 100644 --- a/packages/tests/src/utils/playwrightOperation.ts +++ b/packages/tests/src/utils/playwrightOperation.ts @@ -198,46 +198,7 @@ export async function initPage( } } - // dashboard template will have a popup - if (options?.dashboardFlag) { - console.log("Before popup"); - const [popup] = await Promise.all([ - page - .waitForEvent("popup") - .then((popup) => - popup - .waitForEvent("close", { - timeout: Timeout.playwrightConsentPopupPage, - }) - .catch(() => popup) - ) - .catch(() => {}), - addBtn?.click(), - ]); - console.log("after popup"); - - if (popup && !popup?.isClosed()) { - // input password - console.log(`fill in password`); - await popup.fill( - "input.input[type='password'][name='passwd']", - password - ); - // sign in - await Promise.all([ - popup.click("input.button[type='submit'][value='Sign in']"), - popup.waitForNavigation(), - ]); - await popup.click("input.button[type='submit'][value='Accept']"); - try { - await popup?.close(); - } catch (error) { - console.log("popup is closed"); - } - } - } else { - await addBtn?.click(); - } + await addBtn?.click(); await page.waitForTimeout(Timeout.shortTimeLoading); // verify add page is closed try { @@ -259,7 +220,6 @@ export async function initPage( console.log("No Open App button"); } console.log("[success] app loaded"); - await page.waitForTimeout(Timeout.longTimeWait); }); return page; @@ -347,46 +307,7 @@ export async function reopenPage( } } - // dashboard template will have a popup - if (options?.dashboardFlag && password) { - console.log("Before popup"); - const [popup] = await Promise.all([ - page - .waitForEvent("popup") - .then((popup) => - popup - .waitForEvent("close", { - timeout: Timeout.playwrightConsentPopupPage, - }) - .catch(() => popup) - ) - .catch(() => {}), - addBtn?.click(), - ]); - console.log("after popup"); - - if (popup && !popup?.isClosed()) { - // input password - console.log(`fill in password`); - await popup.fill( - "input.input[type='password'][name='passwd']", - password - ); - // sign in - await Promise.all([ - popup.click("input.button[type='submit'][value='Sign in']"), - popup.waitForNavigation(), - ]); - await popup.click("input.button[type='submit'][value='Accept']"); - try { - await popup?.close(); - } catch (error) { - console.log("popup is closed"); - } - } - } else { - await addBtn?.click(); - } + await addBtn?.click(); await page.waitForTimeout(Timeout.shortTimeLoading); console.log("[success] app loaded"); // verify add page is closed @@ -498,17 +419,7 @@ export async function initTeamsPage( try { addInBtn = await page?.waitForSelector("button>span:has-text('Add')"); } catch { - try { - addInBtn = await page?.waitForSelector( - "button>span:has-text('Open')" - ); - } catch { - await page.screenshot({ - path: getPlaywrightScreenshotPath("add_page"), - fullPage: true, - }); - throw "error to add app"; - } + throw "error to add app"; } await addInBtn?.click(); if (options?.type === "meeting") { @@ -594,7 +505,6 @@ export async function initTeamsPage( console.log("No save button to click"); } } - await page.waitForTimeout(Timeout.shortTimeLoading); console.log("successful to add teams app!!!"); }); @@ -2394,8 +2304,47 @@ export async function validateBasicDashboardTab(page: Page) { export async function validateDashboardTab(page: Page) { try { + await RetryHandler.retry(async () => { + console.log("Before popup"); + const popup = await page.waitForEvent("popup"); + console.log("after popup"); + if (popup && !popup?.isClosed()) { + await popup + .click('button:has-text("Reload")', { + timeout: Timeout.playwrightConsentPageReload, + }) + .catch(() => {}); + console.log("click Accept button"); + await page.waitForTimeout(Timeout.longTimeWait); + try { + // input password + console.log(`fill in password`); + await popup.fill( + "input.input[type='password'][name='passwd']", + Env.password + ); + // sign in + await Promise.all([ + popup.click("input.button[type='submit'][value='Sign in']"), + popup.waitForNavigation(), + ]); + await popup.click("input.button[type='submit'][value='Accept']"); + try { + await popup?.close(); + } catch (error) { + console.log("popup is closed"); + } + } catch (error) { + await popup.screenshot({ + path: getPlaywrightScreenshotPath("login_error"), + fullPage: true, + }); + throw error; + } + } + }); console.log("start to verify dashboard tab"); - await page.waitForTimeout(Timeout.shortTimeLoading); + await page.waitForTimeout(Timeout.longTimeWait); const frameElementHandle = await page.waitForSelector( `iframe[name="embedded-page-container"]` ); diff --git a/packages/tests/src/utils/testToolValidations.ts b/packages/tests/src/utils/testToolValidations.ts new file mode 100644 index 0000000000..2129a021c8 --- /dev/null +++ b/packages/tests/src/utils/testToolValidations.ts @@ -0,0 +1,78 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. +import { BrowserContext } from "playwright"; +import { Timeout, ValidationContent } from "./constants"; +import { getPlaywrightScreenshotPath } from "./nameUtil"; +import { RetryHandler } from "./retryHandler"; + +export async function validateWelcomeAndReplyBot( + context: BrowserContext, + options: { + hasWelcomeMessage?: boolean; + hasCommandReplyValidation: boolean; + botCommand?: string; + expectedWelcomeMessage?: string; + expectedReplyMessage?: string; + timeout?: number; + } = { + hasWelcomeMessage: true, + hasCommandReplyValidation: true, + botCommand: "helloWorld", + expectedWelcomeMessage: ValidationContent.AiChatBotWelcomeInstruction, + expectedReplyMessage: ValidationContent.AiBotErrorMessage, + } +): Promise { + const page = await context.newPage(); + page.setDefaultTimeout(Timeout.playwrightDefaultTimeout); + const timeout = options?.timeout ? options.timeout : 30 * 60 * 1000; + try { + console.log("start to verify bot"); + await page.goto("http://localhost:56150/"); + await page.waitForTimeout(Timeout.shortTimeLoading); + + if (options.hasWelcomeMessage) { + await RetryHandler.retry(async () => { + await page?.waitForSelector( + `p:has-text("${ + options?.expectedWelcomeMessage || + ValidationContent.AiChatBotWelcomeInstruction + }")` + ); + console.log( + options?.expectedWelcomeMessage || + ValidationContent.AiChatBotWelcomeInstruction + ); + console.log("verified bot that it has sent welcome!!!"); + }, 2); + } + + if (options.hasCommandReplyValidation) { + await RetryHandler.retry(async () => { + console.log("sending message ", options?.botCommand || "helloWorld"); + const textbox = await page?.waitForSelector( + 'div[contenteditable="true"][role="textbox"]' + ); + await textbox?.fill(options?.botCommand || "helloWorld"); + const sendButton = await page?.waitForSelector( + 'button[aria-label="Send Message"]' + ); + await sendButton?.click(); + await page?.waitForSelector( + `p:has-text("${options?.expectedReplyMessage}")`, + { timeout: timeout } + ); + console.log( + `verify bot successfully with content ${options?.expectedReplyMessage}!!!` + ); + }, 2); + } + + await page.waitForTimeout(Timeout.shortTimeLoading); + } catch (error) { + await page.screenshot({ + path: getPlaywrightScreenshotPath("error"), + fullPage: true, + }); + throw error; + } +} diff --git a/packages/tests/src/utils/vscodeOperation.ts b/packages/tests/src/utils/vscodeOperation.ts index 033ab002ef..4b6a0255ec 100644 --- a/packages/tests/src/utils/vscodeOperation.ts +++ b/packages/tests/src/utils/vscodeOperation.ts @@ -624,8 +624,8 @@ export async function createNewProject( await driver.sleep(Timeout.input); // Select trigger - // Unselect restify http trigger - // await selectQuickPickWithRegex(/(HTTP Trigger.*Restify Server)|(Restify Server.*HTTP Trigger)/); + // Unselect express http trigger + // await selectQuickPickWithRegex(/(HTTP Trigger.*Express Server)|(Express Server.*HTTP Trigger)/); // Select Functions http trigger await selectQuickPickWithRegex( /(HTTP Trigger.*Azure Functions)|(Azure Functions.*HTTP Trigger)/ @@ -635,12 +635,12 @@ export async function createNewProject( await input.selectQuickPick(lang); break; } - case "restnoti": { + case "expressnoti": { await input.selectQuickPick(CreateProjectQuestion.Bot); await input.selectQuickPick("Chat Notification Message"); await driver.sleep(Timeout.input); // Select trigger - // HTTP Trigger Azure Restify, the default is Restify http trigger, no action needed. + // HTTP Trigger Azure Express, the default is Express http trigger, no action needed. await input.confirm(); // Choose programming language diff --git a/packages/vscode-extension/package.json b/packages/vscode-extension/package.json index e44ba61835..9e28a2e643 100644 --- a/packages/vscode-extension/package.json +++ b/packages/vscode-extension/package.json @@ -336,20 +336,30 @@ } ], "view/item/context": [ + { + "command": "fx-extension.m365SwitchTenant", + "when": "fx-extension.isMultiTenantEnabled && view == teamsfx-accounts && viewItem == signedinM365", + "group": "inline@1" + }, + { + "command": "fx-extension.azureSwitchTenant", + "when": "fx-extension.isMultiTenantEnabled && view == teamsfx-accounts && viewItem == signedinAzure", + "group": "inline@1" + }, { "command": "fx-extension.signOut", "when": "view == teamsfx-accounts && viewItem == signedinM365", - "group": "inline@1" + "group": "inline@2" }, { "command": "fx-extension.azureAccountSignOutHelp", "when": "view == teamsfx-accounts && viewItem == signedinAzure", - "group": "inline@1" + "group": "inline@2" }, { "command": "fx-extension.m365AccountSettings", "when": "view == teamsfx-accounts && viewItem == signedinM365", - "group": "inline@2" + "group": "inline@3" }, { "command": "fx-extension.refreshSideloading", @@ -374,7 +384,7 @@ { "command": "fx-extension.azureAccountSettings", "when": "view == teamsfx-accounts && viewItem == signedinAzure", - "group": "inline@2" + "group": "inline@3" }, { "command": "fx-extension.openDocumentLink", @@ -570,6 +580,14 @@ "command": "fx-extension.selectAndDebug", "when": "false" }, + { + "command": "fx-extension.m365SwitchTenant", + "when": "false" + }, + { + "command": "fx-extension.azureSwitchTenant", + "when": "false" + }, { "command": "fx-extension.signOut", "when": "false" @@ -891,6 +909,16 @@ "title": "%teamstoolkit.commands.checkCopilotAccess%", "icon": "$(info)" }, + { + "command": "fx-extension.m365SwitchTenant", + "title": "%teamstoolkit.commands.switchTenant.m365.title%", + "icon": "$(arrow-swap)" + }, + { + "command": "fx-extension.azureSwitchTenant", + "title": "%teamstoolkit.commands.switchTenant.azure.title%", + "icon": "$(arrow-swap)" + }, { "command": "fx-extension.signOut", "title": "%teamstoolkit.commands.signOut.title%", @@ -1693,13 +1721,15 @@ "@microsoft/tsdoc": "^0.14.2", "@microsoft/vscode-ui": "workspace:*", "@npmcli/package-json": "^1.0.1", + "@types/detect-port": "^1.3.2", "@vscode/extension-telemetry": "^0.6.2", "@vscode/webview-ui-toolkit": "^1.2.2", "async-mutex": "^0.3.1", "axios": "^1.7.5", + "detect-port": "^1.3.0", "dotenv": "^8.2.0", "dree": "^4.7.0", - "express": "^4.19.2", + "express": "^4.21.1", "fuse.js": "^6.6.2", "glob": "^10", "jscodeshift": "^0.14.0", @@ -1714,6 +1744,7 @@ "semver": "^7.5.2", "string-similarity": "^4.0.4", "tmp": "^0.2.1", + "tree-kill": "^1.2.2", "validator": "^13.7.0", "vscode-tas-client": "^0.1.75" }, diff --git a/packages/vscode-extension/package.nls.json b/packages/vscode-extension/package.nls.json index 7547e9b1fb..f7f217d21d 100644 --- a/packages/vscode-extension/package.nls.json +++ b/packages/vscode-extension/package.nls.json @@ -26,11 +26,14 @@ "teamstoolkit.azureLogin.failToFindSubscription": "We couldn't find a subscription.", "teamstoolkit.azureLogin.message": "The Teams Toolkit will use Microsoft authentication to sign in Azure account and subscription to deploy the Azure resources for your project. You won't be charged until you confirm.", "teamstoolkit.azureLogin.subscription": "subscription", - "teamstoolkit.azureLogin.selectSubscription": "Select Subscription", - "teamstoolkit.azureLogin.unknownSubscription": "We're unable to set this subscription. Select a subscription you have access to.", + "teamstoolkit.azureLogin.selectSubscription": "Select Subscription for Current Tenant ID", + "teamstoolkit.azurelogin.selectSubscription.placeholder": "To select subscription for different tenant ID, switch to that tenant ID first.", + "teamstoolkit.azureLogin.unknownSubscription": "Unable to apply this subscription. Select a subscription you've access to or try again later.", "teamstoolkit.cacheAccess.readHomeAccountIdFail": "Unable to read home account id from cache. Clear your account cache and try again.", + "teamstoolkit.cacheAccess.readTenantIdFail": "Unable to read tenant id from cache. Clear your account cache and try again.", "teamstoolkit.cacheAccess.readTokenFail": "Unable to read token from cache. Clear your account cache and try again.", "teamstoolkit.cacheAccess.saveHomeAccountIdFail": "Unable to save home account id to cache. Clear your account cache and try again.", + "teamstoolkit.cacheAccess.saveTenantIdFail": "Unable to save tenant id to cache. Clear your account cache and try again.", "teamstoolkit.cacheAccess.saveTokenFail": "Unable to save token to cache. Clear your account cache and try again.", "teamstoolkit.cacheAccess.writeTokenFail": "Unable to save token to cache. Clear your account cache and try again.", "teamstoolkit.capabilities.untrustedWorkspaces.description": "The Teams Toolkit extension supports limited features in untrusted workspaces.", @@ -96,6 +99,8 @@ "teamstoolkit.commands.refresh.title": "Refresh", "teamstoolkit.commands.reportIssue.title": "Report Issues on GitHub", "teamstoolkit.commands.selectTutorials.title": "View How-to Guides", + "teamstoolkit.commands.switchTenant.m365.title": "Switch between your available tenants for Microsoft 365 account", + "teamstoolkit.commands.switchTenant.azure.title": "Switch between your available tenants for Azure account", "teamstoolkit.commands.signOut.title": "Sign Out", "teamstoolkit.commands.checkCopilotAccess.title": "Check Copilot Access", "teamstoolkit.commands.updateManifest.title": "Update Teams App", @@ -213,6 +218,8 @@ "teamstoolkit.envTree.subscriptionTooltipWithoutName": "'%s' environment is provisioned in Azure subscription '%s'", "teamstoolkit.handlers.azureSignIn": "Successfully signed in to Azure account.", "teamstoolkit.handlers.azureSignOut": "Successfully signed out of Azure account.", + "teamstoolkit.handlers.switchtenant.quickpick.title": "Switch Tenant", + "teamstoolkit.handlers.switchtenant.error": "Unable to obtain your Azure credentials. Make sure your Azure account is properly authenticated and try again", "teamstoolkit.handlers.coreNotReady": "Core module is loading", "teamstoolkit.handlers.createProjectNotification": "Create a new app or open an existing one to open the README file.", "teamstoolkit.handlers.createProjectTitle": "Create New App", @@ -274,12 +281,14 @@ "teamstoolkit.handlers.installOfficeAddinDependencyCancelled": "Dependency installation is canceled, but you can install dependencies manually by clicking the 'Development - Check and Install Dependencies' button on the left side.", "teamstoolkit.localDebug.learnMore": "Get More Info", "teamstoolkit.localDebug.m365TenantHintMessage": "After enrolling your developer tenant in Office 365 Target Release, enrollment may come into effect in couple of days. Click 'Get More Info' button for details on setting up dev environment to extend Teams apps across Microsoft 365.", - "teamstoolkit.handlers.askInstallCopilot": "To use GitHub Copilot Extension for Teams Toolkit when developing Teams apps, you need to install both GitHub Copilot and GitHub Copilot Extension for Teams Toolkit (@teamsapp).", - "_teamstoolkit.handlers.askInstallCopilot.comment": "@teamsapp is used to call Teams agent in Github Copilot Chat and should not be translated.", + "teamstoolkit.handlers.askInstallCopilot": "To use GitHub Copilot Extension for Teams Toolkit when developing Teams apps or customizing Microsoft 365 Copilot, you need to install GitHub Copilot first.", "teamstoolkit.handlers.askInstallCopilot.install": "Install GitHub Copilot", - "teamstoolkit.handlers.askInstallCopilot.installTeamsApp": "Install @teamsapp", - "_teamstoolkit.handlers.askInstallCopilot.installTeamsApp.comment": "@teamsapp is used to call Teams agent in Github Copilot Chat and should not be translated.", - "teamstoolkit.handlers.installExtension.output": "To use GitHub Copilot Extension for Teams Toolkit when developing Teams apps, you need to install both GitHub Copilot Chat following \"%s\" and GitHub Copilot Extension for Teams Toolkit (@teamsapp) following \"%s\".", + "teamstoolkit.handlers.askInstallTeamsAgent": "To use GitHub Copilot Extension for Teams Toolkit when developing Teams apps or customizing Microsoft 365 Copilot, please install it first. If you've already installed it, confirm below.", + "teamstoolkit.handlers.askInstallTeamsAgent.install": "Install from GitHub.com", + "_teamstoolkit.handlers.askInstallTeamsAgent.install.comment": "GitHub.com is the website address and should not be translated.", + "teamstoolkit.handlers.askInstallTeamsAgent.confirmInstall": "Confirm Installation", + "teamstoolkit.handlers.installCopilotAndAgent.output": "To use the GitHub Copilot Extension for Teams Toolkit when developing Teams apps or customizing Microsoft 365 Copilot, install GitHub Copilot from \"%s\" and Github Copilot Extension for Teams Toolkit from \"%s\".", + "teamstoolkit.handlers.installAgent.output": "To use GitHub Copilot Extension for Teams Toolkit when developing Teams apps or customizing Microsoft 365 Copilot, install GitHub Copilot Extension for Teams Toolkit from \"%s\".", "teamstoolkit.handlers.installCopilotError": "Unable to install GitHub Copilot Chat. Install it following %s and try again.", "teamstoolkit.handlers.chatTeamsAgentError": "Unable to automatically focus GitHub Copilot Chat. Open GitHub Copilot Chat and start with \"%s\"", "teamstoolkit.handlers.verifyCopilotExtensionError": "Unable to verify GitHub Copilot Chat. Install it manually following %s and try again.", @@ -342,6 +351,8 @@ "teamstoolkit.localDebug.startDeletingNotificationLocalStoreFile": "Start updating notification local store file.", "teamstoolkit.localDebug.successDeleteNotificationLocalStoreFile": "Successfully updated notification local store file.", "teamstoolkit.localDebug.launchTeamsDesktopClientMessage": "Before proceeding, make sure your Teams desktop login matches your current Microsoft 365 account%s used in Teams Toolkit.", + "teamstoolkit.localDebug.terminateProcess.notification": "Port %s is occupied. Terminate the corresponding process(es) to continue local debug.", + "teamstoolkit.localDebug.terminateProcess.notification.plural": "Ports %s are occupied. Terminate the corresponding process(es) to continue local debug.", "teamstoolkit.migrateTeamsManifest.progressTitle": "Upgrade Teams Manifest to extend in Outlook and the Microsoft 365 app", "teamstoolkit.migrateTeamsManifest.selectFileConfig.name": "Select Teams Manifest to Upgrade", "teamstoolkit.migrateTeamsManifest.selectFileConfig.title": "Select Teams Manifest to Upgrade", diff --git a/packages/vscode-extension/pnpm-lock.yaml b/packages/vscode-extension/pnpm-lock.yaml index cc92eeb090..98501c29a1 100644 --- a/packages/vscode-extension/pnpm-lock.yaml +++ b/packages/vscode-extension/pnpm-lock.yaml @@ -47,9 +47,12 @@ dependencies: '@npmcli/package-json': specifier: ^1.0.1 version: 1.0.1 + '@types/detect-port': + specifier: ^1.3.2 + version: 1.3.2 '@vscode/extension-telemetry': specifier: ^0.6.2 - version: 0.6.2(tslib@2.6.2) + version: 0.6.2(tslib@2.8.1) '@vscode/webview-ui-toolkit': specifier: ^1.2.2 version: 1.2.2(react@17.0.2) @@ -58,7 +61,10 @@ dependencies: version: 0.3.1 axios: specifier: ^1.7.5 - version: 1.7.5(debug@4.3.4) + version: 1.7.5(debug@4.3.7) + detect-port: + specifier: ^1.3.0 + version: 1.3.0 dotenv: specifier: ^8.2.0 version: 8.2.0 @@ -66,8 +72,8 @@ dependencies: specifier: ^4.7.0 version: 4.7.0 express: - specifier: ^4.19.2 - version: 4.19.2 + specifier: ^4.21.1 + version: 4.21.1 fuse.js: specifier: ^6.6.2 version: 6.6.2 @@ -76,7 +82,7 @@ dependencies: version: 10.0.0 jscodeshift: specifier: ^0.14.0 - version: 0.14.0(@babel/preset-env@7.23.8) + version: 0.14.0(@babel/preset-env@7.26.0) jsonc-parser: specifier: ^3.0.0 version: 3.0.0 @@ -88,7 +94,7 @@ dependencies: version: 1.1.1 office-addin-manifest: specifier: ^1.13.1 - version: 1.13.2 + version: 1.13.1 query-string: specifier: 6.14.1 version: 6.14.1 @@ -103,13 +109,16 @@ dependencies: version: 15.5.0(react@17.0.2) semver: specifier: ^7.5.2 - version: 7.5.4 + version: 7.5.2 string-similarity: specifier: ^4.0.4 version: 4.0.4 tmp: specifier: ^0.2.1 - version: 0.2.3 + version: 0.2.1 + tree-kill: + specifier: ^1.2.2 + version: 1.2.2 validator: specifier: ^13.7.0 version: 13.7.0 @@ -177,7 +186,7 @@ devDependencies: version: 15.5.5 '@types/semver': specifier: ^7.3.4 - version: 7.5.8 + version: 7.3.4 '@types/sinon': specifier: ^9.0.9 version: 9.0.9 @@ -186,7 +195,7 @@ devDependencies: version: 4.0.2 '@types/tmp': specifier: ^0.2.0 - version: 0.2.6 + version: 0.2.0 '@types/uuid': specifier: ^8.3.0 version: 8.3.0 @@ -204,7 +213,7 @@ devDependencies: version: 5.0.0(eslint@8.1.0)(typescript@4.7.4) '@vitejs/plugin-react': specifier: ^4.3.1 - version: 4.3.1(vite@5.3.6) + version: 4.3.1(vite@5.4.0) '@vscode/codicons': specifier: 0.0.33 version: 0.0.33 @@ -321,47 +330,41 @@ devDependencies: version: 8.3.2 vite: specifier: ^5.3.6 - version: 5.3.6(@types/node@14.14.21)(sass@1.77.6) + version: 5.4.0(@types/node@14.14.21)(sass@1.77.6) vite-plugin-svgr: specifier: ^4.2.0 - version: 4.2.0(typescript@4.7.4)(vite@5.3.6) + version: 4.2.0(typescript@4.7.4)(vite@5.4.0) packages: - /@aashutoshrathi/word-wrap@1.2.6: - resolution: {integrity: sha512-1Yjs2SvM8TflER/OD3cOjhWWOZb58A2t7wpE2S9XfBYTiIl+XFhQG2bjy4Pu1I+EAlCNUzRDYDdFwFYUKvXcIA==} - engines: {node: '>=0.10.0'} - dev: true - - /@ampproject/remapping@2.2.1: - resolution: {integrity: sha512-lFMjJTrFL3j7L9yBxwYfCq2k6qqwHyzuUl/XBnif78PWTJYyL/dfowQHWE3sp6U6ZzqWiiIZnpTMO96zhkjwtg==} + /@ampproject/remapping@2.3.0: + resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==} engines: {node: '>=6.0.0'} dependencies: - '@jridgewell/gen-mapping': 0.3.3 + '@jridgewell/gen-mapping': 0.3.5 '@jridgewell/trace-mapping': 0.3.25 /@azure/abort-controller@1.1.0: resolution: {integrity: sha512-TrRLIoSQVzfAJX9H1JeFjzAoDGcoK1IYX1UImfceTZpsyYfWr09Ss1aHW1y5TrrR3iq6RZLBwJ3E24uwPhwahw==} engines: {node: '>=12.0.0'} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 /@azure/abort-controller@2.1.2: resolution: {integrity: sha512-nBrLsEWm4J2u5LpAPjxADTlq3trDgVZZXHNKabeXZtpq3d3AbN/KGO82R87rdDz5/lYB024rtEf10/q0urNgsA==} engines: {node: '>=18.0.0'} dependencies: - tslib: 2.6.2 - dev: false + tslib: 2.8.1 /@azure/arm-resources-subscriptions@2.1.0: resolution: {integrity: sha512-vKiu/3Yh84IV3IuJJ+0Fgs/ZQpvuGzoZ3dAoBksIV++Uu/Qz9RcQVz7pj+APWYIuODuR9I0eGKswZvzynzekug==} engines: {node: '>=14.0.0'} dependencies: '@azure/core-auth': 1.4.0 - '@azure/core-client': 1.7.3 - '@azure/core-paging': 1.5.0 - '@azure/core-rest-pipeline': 1.13.0 - tslib: 2.6.2 + '@azure/core-client': 1.9.2 + '@azure/core-paging': 1.6.2 + '@azure/core-rest-pipeline': 1.17.0 + tslib: 2.8.1 transitivePeerDependencies: - supports-color dev: false @@ -372,11 +375,11 @@ packages: dependencies: '@azure/abort-controller': 1.1.0 '@azure/core-auth': 1.4.0 - '@azure/core-client': 1.7.3 - '@azure/core-lro': 2.5.4 - '@azure/core-paging': 1.5.0 - '@azure/core-rest-pipeline': 1.13.0 - tslib: 2.6.2 + '@azure/core-client': 1.9.2 + '@azure/core-lro': 2.7.2 + '@azure/core-paging': 1.6.2 + '@azure/core-rest-pipeline': 1.17.0 + tslib: 2.8.1 transitivePeerDependencies: - supports-color dev: true @@ -386,121 +389,120 @@ packages: engines: {node: '>=12.0.0'} dependencies: '@azure/abort-controller': 1.1.0 - tslib: 2.6.2 + tslib: 2.8.1 - /@azure/core-auth@1.7.2: - resolution: {integrity: sha512-Igm/S3fDYmnMq1uKS38Ae1/m37B3zigdlZw+kocwEhh5GjyKjPrXKO2J6rzpC1wAxrNil/jX9BJRqBshyjnF3g==} + /@azure/core-auth@1.9.0: + resolution: {integrity: sha512-FPwHpZywuyasDSLMqJ6fhbOK3TqUdviZNF8OqRGA4W5Ewib2lEEZ+pBsYcBa88B2NGO/SEnYPGhyBqNlE8ilSw==} engines: {node: '>=18.0.0'} dependencies: '@azure/abort-controller': 2.1.2 - '@azure/core-util': 1.6.1 - tslib: 2.6.2 - dev: false + '@azure/core-util': 1.11.0 + tslib: 2.8.1 - /@azure/core-client@1.7.3: - resolution: {integrity: sha512-kleJ1iUTxcO32Y06dH9Pfi9K4U+Tlb111WXEnbt7R/ne+NLRwppZiTGJuTD5VVoxTMK5NTbEtm5t2vcdNCFe2g==} - engines: {node: '>=14.0.0'} + /@azure/core-client@1.9.2: + resolution: {integrity: sha512-kRdry/rav3fUKHl/aDLd/pDLcB+4pOFwPPTVEExuMyaI5r+JBbMWqRbCY1pn5BniDaU3lRxO9eaQ1AmSMehl/w==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 + '@azure/abort-controller': 2.1.2 '@azure/core-auth': 1.4.0 - '@azure/core-rest-pipeline': 1.13.0 - '@azure/core-tracing': 1.0.1 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - tslib: 2.6.2 + '@azure/core-rest-pipeline': 1.17.0 + '@azure/core-tracing': 1.2.0 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + tslib: 2.8.1 transitivePeerDependencies: - supports-color - /@azure/core-lro@2.5.4: - resolution: {integrity: sha512-3GJiMVH7/10bulzOKGrrLeG/uCBH/9VtxqaMcB9lIqAeamI/xYQSHJL/KcsLDuH+yTjYpro/u6D/MuRe4dN70Q==} - engines: {node: '>=14.0.0'} + /@azure/core-lro@2.7.2: + resolution: {integrity: sha512-0YIpccoX8m/k00O7mDDMdJpbr6mf1yWo2dfmxt5A8XVZVVMz2SSKaEbMCeJRvgQ0IaSlqhjT47p4hVIRRy90xw==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - tslib: 2.6.2 + '@azure/abort-controller': 2.1.2 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + tslib: 2.8.1 dev: true - /@azure/core-paging@1.5.0: - resolution: {integrity: sha512-zqWdVIt+2Z+3wqxEOGzR5hXFZ8MGKK52x4vFLw8n58pR6ZfKRx3EXYTxTaYxYHc/PexPUTyimcTWFJbji9Z6Iw==} - engines: {node: '>=14.0.0'} + /@azure/core-paging@1.6.2: + resolution: {integrity: sha512-YKWi9YuCU04B55h25cnOYZHxXYtEvQEbKST5vqRga7hWY9ydd3FZHdeQF8pyh+acWZvppw13M/LMGx0LABUVMA==} + engines: {node: '>=18.0.0'} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 - /@azure/core-rest-pipeline@1.13.0: - resolution: {integrity: sha512-a62aP/wppgmnfIkJLfcB4ssPBcH94WzrzPVJ3tlJt050zX4lfmtnvy95D3igDo3f31StO+9BgPrzvkj4aOxnoA==} + /@azure/core-rest-pipeline@1.17.0: + resolution: {integrity: sha512-62Vv8nC+uPId3j86XJ0WI+sBf0jlqTqPUFCBNrGtlaUeQUIXWV/D8GE5A1d+Qx8H7OQojn2WguC8kChD6v0shA==} engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - '@azure/core-auth': 1.4.0 - '@azure/core-tracing': 1.0.1 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - http-proxy-agent: 5.0.0 - https-proxy-agent: 5.0.1 - tslib: 2.6.2 + '@azure/abort-controller': 2.1.2 + '@azure/core-auth': 1.9.0 + '@azure/core-tracing': 1.2.0 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + http-proxy-agent: 7.0.2 + https-proxy-agent: 7.0.5 + tslib: 2.8.1 transitivePeerDependencies: - supports-color - /@azure/core-tracing@1.0.1: - resolution: {integrity: sha512-I5CGMoLtX+pI17ZdiFJZgxMJApsK6jjfm85hpgp3oazCdq5Wxgh4wMr7ge/TTWW1B5WBuvIOI1fMU/FrOAMKrw==} - engines: {node: '>=12.0.0'} + /@azure/core-tracing@1.2.0: + resolution: {integrity: sha512-UKTiEJPkWcESPYJz3X5uKRYyOcJD+4nYph+KpfdPRnQJVrZfk0KJgdnaAWKfhsBBtAf/D58Az4AvCJEmWgIBAg==} + engines: {node: '>=18.0.0'} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 - /@azure/core-util@1.6.1: - resolution: {integrity: sha512-h5taHeySlsV9qxuK64KZxy4iln1BtMYlNt5jbuEFN3UFSAd1EwKg/Gjl5a6tZ/W8t6li3xPnutOx7zbDyXnPmQ==} - engines: {node: '>=16.0.0'} + /@azure/core-util@1.11.0: + resolution: {integrity: sha512-DxOSLua+NdpWoSqULhjDyAZTXFdP/LKkqtYuxxz1SCN289zk3OG8UOpnCQAz/tygyACBtWp/BoO72ptK7msY8g==} + engines: {node: '>=18.0.0'} dependencies: - '@azure/abort-controller': 1.1.0 - tslib: 2.6.2 + '@azure/abort-controller': 2.1.2 + tslib: 2.8.1 /@azure/identity@4.1.0: resolution: {integrity: sha512-BhYkF8Xr2gXjyDxocm0pc9RI5J5a1jw8iW0dw6Bx95OGdYbuMyFZrrwNw4eYSqQ2BB6FZOqpJP3vjsAqRcvDhw==} engines: {node: '>=18.0.0'} dependencies: '@azure/abort-controller': 1.1.0 - '@azure/core-auth': 1.7.2 - '@azure/core-client': 1.7.3 - '@azure/core-rest-pipeline': 1.13.0 - '@azure/core-tracing': 1.0.1 - '@azure/core-util': 1.6.1 - '@azure/logger': 1.0.4 - '@azure/msal-browser': 3.13.0 + '@azure/core-auth': 1.9.0 + '@azure/core-client': 1.9.2 + '@azure/core-rest-pipeline': 1.17.0 + '@azure/core-tracing': 1.2.0 + '@azure/core-util': 1.11.0 + '@azure/logger': 1.1.4 + '@azure/msal-browser': 3.26.1 '@azure/msal-node': 2.6.6 events: 3.3.0 jws: 4.0.0 open: 8.4.2 stoppable: 1.1.0 - tslib: 2.6.2 + tslib: 2.8.1 transitivePeerDependencies: - supports-color dev: false - /@azure/logger@1.0.4: - resolution: {integrity: sha512-ustrPY8MryhloQj7OWGe+HrYx+aoiOxzbXTtgblbV3xwCqpzUK36phH3XNHQKj3EPonyFUuDTfR3qFhTEAuZEg==} - engines: {node: '>=14.0.0'} + /@azure/logger@1.1.4: + resolution: {integrity: sha512-4IXXzcCdLdlXuCG+8UKEwLA1T1NHqUfanhXYHiQTn+6sfWCZXduqbtXDGceg3Ce5QxTGo7EqmbV6Bi+aqKuClQ==} + engines: {node: '>=18.0.0'} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 /@azure/ms-rest-azure-env@2.0.0: resolution: {integrity: sha512-dG76W7ElfLi+fbTjnZVGj+M9e0BIEJmRxU6fHaUQ12bZBe8EJKYb2GV50YWNaP2uJiVQ5+7nXEVj1VN1UQtaEw==} dev: false - /@azure/msal-browser@3.13.0: - resolution: {integrity: sha512-fD906nmJei3yE7la6DZTdUtXKvpwzJURkfsiz9747Icv4pit77cegSm6prJTKLQ1fw4iiZzrrWwxnhMLrTf5gQ==} + /@azure/msal-browser@3.26.1: + resolution: {integrity: sha512-y78sr9g61aCAH9fcLO1um+oHFXc1/5Ap88RIsUSuzkm0BHzFnN+PXGaQeuM1h5Qf5dTnWNOd6JqkskkMPAhh7Q==} engines: {node: '>=0.8.0'} dependencies: - '@azure/msal-common': 14.9.0 + '@azure/msal-common': 14.15.0 dev: false - /@azure/msal-common@14.8.1: - resolution: {integrity: sha512-9HfBMDTIgtFFkils+o6gO/aGEoLLuc4z+QLLfhy/T1bTNPiVsX/9CjaBPMZGnMltN/IlMkU5SGGNggGh55p5xA==} + /@azure/msal-common@14.15.0: + resolution: {integrity: sha512-ImAQHxmpMneJ/4S8BRFhjt1MZ3bppmpRPYYNyzeQPeFN288YKbb8TmmISQEbtfkQ1BPASvYZU5doIZOPBAqENQ==} engines: {node: '>=0.8.0'} dev: false - /@azure/msal-common@14.9.0: - resolution: {integrity: sha512-yzBPRlWPnTBeixxLNI3BBIgF5/bHpbhoRVuuDBnYjCyWRavaPUsKAHUDYLqpGkBLDciA6TCc6GOxN4/S3WiSxg==} + /@azure/msal-common@14.8.1: + resolution: {integrity: sha512-9HfBMDTIgtFFkils+o6gO/aGEoLLuc4z+QLLfhy/T1bTNPiVsX/9CjaBPMZGnMltN/IlMkU5SGGNggGh55p5xA==} engines: {node: '>=0.8.0'} dev: false @@ -513,1496 +515,1185 @@ packages: uuid: 8.3.2 dev: false - /@babel/code-frame@7.23.5: - resolution: {integrity: sha512-CgH3s1a96LipHCmSUmYFPwY7MNx8C3avkq7i4Wl3cfa662ldtUe4VM1TPXX70pfmrlWTb6jLqTYrZyT2ZTJBgA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/highlight': 7.23.4 - chalk: 2.4.2 - - /@babel/code-frame@7.24.7: - resolution: {integrity: sha512-BcYH1CVJBO9tvyIZ2jVeXgSIMvGZ2FDRvDdOIVQyuklNKSsx+eppDEBq/g47Ayw+RqNFE+URvOShmf+f/qwAlA==} + /@babel/code-frame@7.26.2: + resolution: {integrity: sha512-RJlIHRueQgwWitWgF8OdFYGZX328Ax5BCemNGlqHfplnRT9ESi8JkFlvaVYbS+UubVY6dpv87Fs2u5M29iNFVQ==} engines: {node: '>=6.9.0'} dependencies: - '@babel/highlight': 7.24.7 - picocolors: 1.0.1 - - /@babel/compat-data@7.23.5: - resolution: {integrity: sha512-uU27kfDRlhfKl+w1U6vp16IuvSLtjAxdArVXPa9BvLkrr7CYIsxH5adpHObeAGY/41+syctUWOZ140a2Rvkgjw==} - engines: {node: '>=6.9.0'} - - /@babel/compat-data@7.24.7: - resolution: {integrity: sha512-qJzAIcv03PyaWqxRgO4mSU3lihncDT296vnyuE2O8uA4w3UHWI4S3hgeZd1L8W1Bft40w9JxJ2b412iDUFFRhw==} - engines: {node: '>=6.9.0'} + '@babel/helper-validator-identifier': 7.25.9 + js-tokens: 4.0.0 + picocolors: 1.1.1 - /@babel/core@7.23.7: - resolution: {integrity: sha512-+UpDgowcmqe36d4NwqvKsyPMlOLNGMsfMmQ5WGCu+siCe3t3dfe9njrzGfdN4qq+bcNUt0+Vw6haRxBOycs4dw==} + /@babel/compat-data@7.26.2: + resolution: {integrity: sha512-Z0WgzSEa+aUcdiJuCIqgujCshpMWgUpgOxXotrYPSA53hA3qopNaqcJpyr0hVb1FeWdnqFA35/fUtXgBK8srQg==} engines: {node: '>=6.9.0'} - dependencies: - '@ampproject/remapping': 2.2.1 - '@babel/code-frame': 7.23.5 - '@babel/generator': 7.23.6 - '@babel/helper-compilation-targets': 7.23.6 - '@babel/helper-module-transforms': 7.23.3(@babel/core@7.23.7) - '@babel/helpers': 7.23.8 - '@babel/parser': 7.23.6 - '@babel/template': 7.22.15 - '@babel/traverse': 7.23.7 - '@babel/types': 7.23.6 - convert-source-map: 2.0.0 - debug: 4.3.4(supports-color@8.1.1) - gensync: 1.0.0-beta.2 - json5: 2.2.3 - semver: 6.3.1 - transitivePeerDependencies: - - supports-color - /@babel/core@7.24.7: - resolution: {integrity: sha512-nykK+LEK86ahTkX/3TgauT0ikKoNCfKHEaZYTUVupJdTLzGNvrblu4u6fa7DhZONAltdf8e662t/abY8idrd/g==} + /@babel/core@7.26.0: + resolution: {integrity: sha512-i1SLeK+DzNnQ3LL/CswPCa/E5u4lh1k6IAEphON8F+cXt0t9euTshDru0q7/IqMa1PMPz5RnHuHscF8/ZJsStg==} engines: {node: '>=6.9.0'} dependencies: - '@ampproject/remapping': 2.2.1 - '@babel/code-frame': 7.24.7 - '@babel/generator': 7.24.7 - '@babel/helper-compilation-targets': 7.24.7 - '@babel/helper-module-transforms': 7.24.7(@babel/core@7.24.7) - '@babel/helpers': 7.24.7 - '@babel/parser': 7.24.7 - '@babel/template': 7.24.7 - '@babel/traverse': 7.24.7 - '@babel/types': 7.24.7 + '@ampproject/remapping': 2.3.0 + '@babel/code-frame': 7.26.2 + '@babel/generator': 7.26.2 + '@babel/helper-compilation-targets': 7.25.9 + '@babel/helper-module-transforms': 7.26.0(@babel/core@7.26.0) + '@babel/helpers': 7.26.0 + '@babel/parser': 7.26.2 + '@babel/template': 7.25.9 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 convert-source-map: 2.0.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) gensync: 1.0.0-beta.2 json5: 2.2.3 semver: 6.3.1 transitivePeerDependencies: - supports-color - /@babel/generator@7.23.6: - resolution: {integrity: sha512-qrSfCYxYQB5owCmGLbl8XRpX1ytXlpueOb0N0UmQwA073KZxejgQTzAmJezxvpwQD9uGtK2shHdi55QT+MbjIw==} + /@babel/generator@7.26.2: + resolution: {integrity: sha512-zevQbhbau95nkoxSq3f/DC/SC+EEOUZd3DYqfSkMhY2/wfSeaHV1Ew4vk8e+x8lja31IbyuUa2uQ3JONqKbysw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/types': 7.23.6 - '@jridgewell/gen-mapping': 0.3.3 - '@jridgewell/trace-mapping': 0.3.25 - jsesc: 2.5.2 - - /@babel/generator@7.24.7: - resolution: {integrity: sha512-oipXieGC3i45Y1A41t4tAqpnEZWgB/lC6Ehh6+rOviR5XWpTtMmLN+fGjz9vOiNRt0p6RtO6DtD0pdU3vpqdSA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.24.7 + '@babel/parser': 7.26.2 + '@babel/types': 7.26.0 '@jridgewell/gen-mapping': 0.3.5 '@jridgewell/trace-mapping': 0.3.25 - jsesc: 2.5.2 + jsesc: 3.0.2 - /@babel/helper-annotate-as-pure@7.22.5: - resolution: {integrity: sha512-LvBTxu8bQSQkcyKOU+a1btnNFQ1dMAd0R6PyW3arXes06F6QLWLIrd681bxRPIXlrMGR3XYnW9JyML7dP3qgxg==} + /@babel/helper-annotate-as-pure@7.25.9: + resolution: {integrity: sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==} engines: {node: '>=6.9.0'} dependencies: - '@babel/types': 7.23.6 + '@babel/types': 7.26.0 dev: false - /@babel/helper-builder-binary-assignment-operator-visitor@7.22.15: - resolution: {integrity: sha512-QkBXwGgaoC2GtGZRoma6kv7Szfv06khvhFav67ZExau2RaXzy8MpHSMO2PNoP2XtmQphJQRHFfg77Bq731Yizw==} + /@babel/helper-builder-binary-assignment-operator-visitor@7.25.9: + resolution: {integrity: sha512-C47lC7LIDCnz0h4vai/tpNOI95tCd5ZT3iBt/DBH5lXKHZsyNQv18yf1wIIg2ntiQNgmAvA+DgZ82iW8Qdym8g==} engines: {node: '>=6.9.0'} dependencies: - '@babel/types': 7.24.7 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 + transitivePeerDependencies: + - supports-color dev: false - /@babel/helper-compilation-targets@7.23.6: - resolution: {integrity: sha512-9JB548GZoQVmzrFgp8o7KxdgkTGm6xs9DW0o/Pim72UDjzr5ObUQ6ZzYPqA+g9OTS2bBQoctLJrky0RDCAWRgQ==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/compat-data': 7.23.5 - '@babel/helper-validator-option': 7.23.5 - browserslist: 4.22.2 - lru-cache: 5.1.1 - semver: 6.3.1 - - /@babel/helper-compilation-targets@7.24.7: - resolution: {integrity: sha512-ctSdRHBi20qWOfy27RUb4Fhp07KSJ3sXcuSvTrXrc4aG8NSYDo1ici3Vhg9bg69y5bj0Mr1lh0aeEgTvc12rMg==} + /@babel/helper-compilation-targets@7.25.9: + resolution: {integrity: sha512-j9Db8Suy6yV/VHa4qzrj9yZfZxhLWQdVnRlXxmKLYlhWUVB1sB2G5sxuWYXk/whHD9iW76PmNzxZ4UCnTQTVEQ==} engines: {node: '>=6.9.0'} dependencies: - '@babel/compat-data': 7.24.7 - '@babel/helper-validator-option': 7.24.7 - browserslist: 4.22.2 + '@babel/compat-data': 7.26.2 + '@babel/helper-validator-option': 7.25.9 + browserslist: 4.24.2 lru-cache: 5.1.1 semver: 6.3.1 - /@babel/helper-create-class-features-plugin@7.23.7(@babel/core@7.23.7): - resolution: {integrity: sha512-xCoqR/8+BoNnXOY7RVSgv6X+o7pmT5q1d+gGcRlXYkI+9B31glE4jeejhKVpA04O1AtzOt7OSQ6VYKP5FcRl9g==} + /@babel/helper-create-class-features-plugin@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-UTZQMvt0d/rSz6KI+qdu7GQze5TIajwTS++GUozlw8VBJDEOAqSXwm1WvmYEZwqdqSGQshRocPDqrt4HBZB3fQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-function-name': 7.23.0 - '@babel/helper-member-expression-to-functions': 7.23.0 - '@babel/helper-optimise-call-expression': 7.22.5 - '@babel/helper-replace-supers': 7.22.20(@babel/core@7.23.7) - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - semver: 6.3.1 - dev: false - - /@babel/helper-create-class-features-plugin@7.23.7(@babel/core@7.24.7): - resolution: {integrity: sha512-xCoqR/8+BoNnXOY7RVSgv6X+o7pmT5q1d+gGcRlXYkI+9B31glE4jeejhKVpA04O1AtzOt7OSQ6VYKP5FcRl9g==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-function-name': 7.23.0 - '@babel/helper-member-expression-to-functions': 7.23.0 - '@babel/helper-optimise-call-expression': 7.22.5 - '@babel/helper-replace-supers': 7.22.20(@babel/core@7.24.7) - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 + '@babel/core': 7.26.0 + '@babel/helper-annotate-as-pure': 7.25.9 + '@babel/helper-member-expression-to-functions': 7.25.9 + '@babel/helper-optimise-call-expression': 7.25.9 + '@babel/helper-replace-supers': 7.25.9(@babel/core@7.26.0) + '@babel/helper-skip-transparent-expression-wrappers': 7.25.9 + '@babel/traverse': 7.25.9 semver: 6.3.1 + transitivePeerDependencies: + - supports-color dev: false - /@babel/helper-create-regexp-features-plugin@7.22.15(@babel/core@7.24.7): - resolution: {integrity: sha512-29FkPLFjn4TPEa3RE7GpW+qbE8tlsu3jntNYNfcGsc49LphF1PQIiD+vMZ1z1xVOKt+93khA9tc2JBs3kBjA7w==} + /@babel/helper-create-regexp-features-plugin@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-ORPNZ3h6ZRkOyAa/SaHU+XsLZr0UQzRwuDQ0cczIA17nAzZ+85G5cVkOJIj7QavLZGSe8QXUmNFxSZzjcZF9bw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-annotate-as-pure': 7.22.5 - regexpu-core: 5.3.2 + '@babel/core': 7.26.0 + '@babel/helper-annotate-as-pure': 7.25.9 + regexpu-core: 6.1.1 semver: 6.3.1 dev: false - /@babel/helper-define-polyfill-provider@0.4.4(@babel/core@7.24.7): - resolution: {integrity: sha512-QcJMILQCu2jm5TFPGA3lCpJJTeEP+mqeXooG/NZbg/h5FTFi6V0+99ahlRsW8/kRLyb24LZVCCiclDedhLKcBA==} + /@babel/helper-define-polyfill-provider@0.6.2(@babel/core@7.26.0): + resolution: {integrity: sha512-LV76g+C502biUK6AyZ3LK10vDpDyCzZnhZFXkH1L75zHPj68+qc8Zfpx2th+gzwA2MzyK+1g/3EPl62yFnVttQ==} peerDependencies: '@babel/core': ^7.4.0 || ^8.0.0-0 <8.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-compilation-targets': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - debug: 4.3.4(supports-color@8.1.1) + '@babel/core': 7.26.0 + '@babel/helper-compilation-targets': 7.25.9 + '@babel/helper-plugin-utils': 7.25.9 + debug: 4.3.7(supports-color@8.1.1) lodash.debounce: 4.0.8 resolve: 1.22.8 transitivePeerDependencies: - supports-color dev: false - /@babel/helper-define-polyfill-provider@0.5.0(@babel/core@7.24.7): - resolution: {integrity: sha512-NovQquuQLAQ5HuyjCz7WQP9MjRj7dx++yspwiyUiGl9ZyadHRSql1HZh5ogRd8W8w6YM6EQ/NTB8rgjLt5W65Q==} - peerDependencies: - '@babel/core': ^7.4.0 || ^8.0.0-0 <8.0.0 + /@babel/helper-member-expression-to-functions@7.25.9: + resolution: {integrity: sha512-wbfdZ9w5vk0C0oyHqAJbc62+vet5prjj01jjJ8sKn3j9h3MQQlflEdXYvuqRWjHnM12coDEqiC1IRCi0U/EKwQ==} + engines: {node: '>=6.9.0'} dependencies: - '@babel/core': 7.24.7 - '@babel/helper-compilation-targets': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - debug: 4.3.4(supports-color@8.1.1) - lodash.debounce: 4.0.8 - resolve: 1.22.8 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 transitivePeerDependencies: - supports-color dev: false - /@babel/helper-environment-visitor@7.22.20: - resolution: {integrity: sha512-zfedSIzFhat/gFhWfHtgWvlec0nqB9YEIVrpuwjruLlXfUSnA8cJB0miHKwqDnQ7d32aKo2xt88/xZptwxbfhA==} - engines: {node: '>=6.9.0'} - - /@babel/helper-environment-visitor@7.24.7: - resolution: {integrity: sha512-DoiN84+4Gnd0ncbBOM9AZENV4a5ZiL39HYMyZJGZ/AZEykHYdJw0wW3kdcsh9/Kn+BRXHLkkklZ51ecPKmI1CQ==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.24.7 - - /@babel/helper-function-name@7.23.0: - resolution: {integrity: sha512-OErEqsrxjZTJciZ4Oo+eoZqeW9UIiOcuYKRJA4ZAgV9myA+pOXhhmpfNCKjEH/auVfEYVFJ6y1Tc4r0eIApqiw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/template': 7.22.15 - '@babel/types': 7.23.6 - - /@babel/helper-function-name@7.24.7: - resolution: {integrity: sha512-FyoJTsj/PEUWu1/TYRiXTIHc8lbw+TDYkZuoE43opPS5TrI7MyONBE1oNvfguEXAD9yhQRrVBnXdXzSLQl9XnA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/template': 7.24.7 - '@babel/types': 7.24.7 - - /@babel/helper-hoist-variables@7.22.5: - resolution: {integrity: sha512-wGjk9QZVzvknA6yKIUURb8zY3grXCcOZt+/7Wcy8O2uctxhplmUPkOdlgoNhmdVee2c92JXbf1xpMtVNbfoxRw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 - - /@babel/helper-hoist-variables@7.24.7: - resolution: {integrity: sha512-MJJwhkoGy5c4ehfoRyrJ/owKeMl19U54h27YYftT0o2teQ3FJ3nQUf/I3LlJsX4l3qlw7WRXUmiyajvHXoTubQ==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.24.7 - - /@babel/helper-member-expression-to-functions@7.23.0: - resolution: {integrity: sha512-6gfrPwh7OuT6gZyJZvd6WbTfrqAo7vm4xCzAXOusKqq/vWdKXphTpj5klHKNmRUU6/QRGlBsyU9mAIPaWHlqJA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 - dev: false - - /@babel/helper-module-imports@7.22.15: - resolution: {integrity: sha512-0pYVBnDKZO2fnSPCrgM/6WMc7eS20Fbok+0r88fp+YtWVLZrp4CkafFGIp+W0VKw4a22sgebPT99y+FDNMdP4w==} + /@babel/helper-module-imports@7.25.9: + resolution: {integrity: sha512-tnUA4RsrmflIM6W6RFTLFSXITtl0wKjgpnLgXyowocVPrbYrLUXSBXDgTs8BlbmIzIdlBySRQjINYs2BAkiLtw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/types': 7.23.6 - - /@babel/helper-module-imports@7.24.7: - resolution: {integrity: sha512-8AyH3C+74cgCVVXow/myrynrAGv+nTVg5vKu2nZph9x7RcRwzmh0VFallJuFTZ9mx6u4eSdXZfcOzSqTUm0HCA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/traverse': 7.24.7 - '@babel/types': 7.24.7 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 transitivePeerDependencies: - supports-color - /@babel/helper-module-transforms@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-7bBs4ED9OmswdfDzpz4MpWgSrV7FXlc3zIagvLFjS5H+Mk7Snr21vQ6QwrsoCGMfNC4e4LQPdoULEt4ykz0SRQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.23.7 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-module-imports': 7.22.15 - '@babel/helper-simple-access': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/helper-validator-identifier': 7.22.20 - - /@babel/helper-module-transforms@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-7bBs4ED9OmswdfDzpz4MpWgSrV7FXlc3zIagvLFjS5H+Mk7Snr21vQ6QwrsoCGMfNC4e4LQPdoULEt4ykz0SRQ==} + /@babel/helper-module-transforms@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-xO+xu6B5K2czEnQye6BHA7DolFFmS3LB7stHZFaOLb1pAwO1HWLS8fXA+eh0A2yIvltPVmx3eNNDBJA2SLHXFw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-module-imports': 7.22.15 - '@babel/helper-simple-access': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/helper-validator-identifier': 7.22.20 - dev: false - - /@babel/helper-module-transforms@7.24.7(@babel/core@7.24.7): - resolution: {integrity: sha512-1fuJEwIrp+97rM4RWdO+qrRsZlAeL1lQJoPqtCYWv0NL115XM93hIH4CSRln2w52SqvmY5hqdtauB6QFCDiZNQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-environment-visitor': 7.24.7 - '@babel/helper-module-imports': 7.24.7 - '@babel/helper-simple-access': 7.24.7 - '@babel/helper-split-export-declaration': 7.24.7 - '@babel/helper-validator-identifier': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-module-imports': 7.25.9 + '@babel/helper-validator-identifier': 7.25.9 + '@babel/traverse': 7.25.9 transitivePeerDependencies: - supports-color - /@babel/helper-optimise-call-expression@7.22.5: - resolution: {integrity: sha512-HBwaojN0xFRx4yIvpwGqxiV2tUfl7401jlok564NgB9EHS1y6QT17FmKWm4ztqjeVdXLuC4fSvHc5ePpQjoTbw==} + /@babel/helper-optimise-call-expression@7.25.9: + resolution: {integrity: sha512-FIpuNaz5ow8VyrYcnXQTDRGvV6tTjkNtCK/RYNDXGSLlUD6cBuQTSw43CShGxjvfBTfcUA/r6UhUCbtYqkhcuQ==} engines: {node: '>=6.9.0'} dependencies: - '@babel/types': 7.23.6 + '@babel/types': 7.26.0 dev: false - /@babel/helper-plugin-utils@7.22.5: - resolution: {integrity: sha512-uLls06UVKgFG9QD4OeFYLEGteMIAa5kpTPcFL28yuCIIzsf6ZyKZMllKVOCZFhiZ5ptnwX4mtKdWCBE/uT4amg==} + /@babel/helper-plugin-utils@7.25.9: + resolution: {integrity: sha512-kSMlyUVdWe25rEsRGviIgOWnoT/nfABVWlqt9N19/dIPWViAOW2s9wznP5tURbs/IDuNk4gPy3YdYRgH3uxhBw==} engines: {node: '>=6.9.0'} - dev: false - /@babel/helper-plugin-utils@7.24.7: - resolution: {integrity: sha512-Rq76wjt7yz9AAc1KnlRKNAi/dMSVWgDRx43FHoJEbcYU6xOWaE2dVPwcdTukJrjxS65GITyfbvEYHvkirZ6uEg==} - engines: {node: '>=6.9.0'} - - /@babel/helper-remap-async-to-generator@7.22.20(@babel/core@7.24.7): - resolution: {integrity: sha512-pBGyV4uBqOns+0UvhsTO8qgl8hO89PmiDYv+/COyp1aeMcmfrfruz+/nCMFiYyFF/Knn0yfrC85ZzNFjembFTw==} + /@babel/helper-remap-async-to-generator@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-IZtukuUeBbhgOcaW2s06OXTzVNJR0ybm4W5xC1opWFFJMZbwRj5LCk+ByYH7WdZPZTt8KnFwA8pvjN2yqcPlgw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-environment-visitor': 7.24.7 - '@babel/helper-wrap-function': 7.22.20 + '@babel/core': 7.26.0 + '@babel/helper-annotate-as-pure': 7.25.9 + '@babel/helper-wrap-function': 7.25.9 + '@babel/traverse': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/helper-replace-supers@7.22.20(@babel/core@7.23.7): - resolution: {integrity: sha512-qsW0In3dbwQUbK8kejJ4R7IHVGwHJlV6lpG6UA7a9hSa2YEiAib+N1T2kr6PEeUT+Fl7najmSOS6SmAwCHK6Tw==} + /@babel/helper-replace-supers@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-IiDqTOTBQy0sWyeXyGSC5TBJpGFXBkRynjBeXsvbhQFKj2viwJC76Epz35YLU1fpe/Am6Vppb7W7zM4fPQzLsQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-member-expression-to-functions': 7.23.0 - '@babel/helper-optimise-call-expression': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-member-expression-to-functions': 7.25.9 + '@babel/helper-optimise-call-expression': 7.25.9 + '@babel/traverse': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/helper-replace-supers@7.22.20(@babel/core@7.24.7): - resolution: {integrity: sha512-qsW0In3dbwQUbK8kejJ4R7IHVGwHJlV6lpG6UA7a9hSa2YEiAib+N1T2kr6PEeUT+Fl7najmSOS6SmAwCHK6Tw==} + /@babel/helper-simple-access@7.25.9: + resolution: {integrity: sha512-c6WHXuiaRsJTyHYLJV75t9IqsmTbItYfdj99PnzYGQZkYKvan5/2jKJ7gu31J3/BJ/A18grImSPModuyG/Eo0Q==} engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-member-expression-to-functions': 7.23.0 - '@babel/helper-optimise-call-expression': 7.22.5 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 + transitivePeerDependencies: + - supports-color dev: false - /@babel/helper-simple-access@7.22.5: - resolution: {integrity: sha512-n0H99E/K+Bika3++WNL17POvo4rKWZ7lZEp1Q+fStVbUi8nxPQEBOlTmCOxW/0JsS56SKKQ+ojAe2pHKJHN35w==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 - - /@babel/helper-simple-access@7.24.7: - resolution: {integrity: sha512-zBAIvbCMh5Ts+b86r/CjU+4XGYIs+R1j951gxI3KmmxBMhCg4oQMsv6ZXQ64XOm/cvzfU1FmoCyt6+owc5QMYg==} + /@babel/helper-skip-transparent-expression-wrappers@7.25.9: + resolution: {integrity: sha512-K4Du3BFa3gvyhzgPcntrkDgZzQaq6uozzcpGbOO1OEJaI+EJdqWIMTLgFgQf6lrfiDFo5FU+BxKepI9RmZqahA==} engines: {node: '>=6.9.0'} dependencies: - '@babel/traverse': 7.24.7 - '@babel/types': 7.24.7 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 transitivePeerDependencies: - supports-color - - /@babel/helper-skip-transparent-expression-wrappers@7.22.5: - resolution: {integrity: sha512-tK14r66JZKiC43p8Ki33yLBVJKlQDFoA8GYN67lWCDCqoL6EMMSuM9b+Iff2jHaM/RRFYl7K+iiru7hbRqNx8Q==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 dev: false - /@babel/helper-split-export-declaration@7.22.6: - resolution: {integrity: sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.23.6 - - /@babel/helper-split-export-declaration@7.24.7: - resolution: {integrity: sha512-oy5V7pD+UvfkEATUKvIjvIAH/xCzfsFVw7ygW2SI6NClZzquT+mwdTfgfdbUiceh6iQO0CHtCPsyze/MZ2YbAA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/types': 7.24.7 - - /@babel/helper-string-parser@7.23.4: - resolution: {integrity: sha512-803gmbQdqwdf4olxrX4AJyFBV/RTr3rSmOj0rKwesmzlfhYNDEs+/iOcznzpNWlJlIlTJC2QfPFcHB6DlzdVLQ==} + /@babel/helper-string-parser@7.25.9: + resolution: {integrity: sha512-4A/SCr/2KLd5jrtOMFzaKjVtAei3+2r/NChoBNoZ3EyP/+GlhoaEGoWOZUmFmoITP7zOJyHIMm+DYRd8o3PvHA==} engines: {node: '>=6.9.0'} - /@babel/helper-string-parser@7.24.7: - resolution: {integrity: sha512-7MbVt6xrwFQbunH2DNQsAP5sTGxfqQtErvBIvIMi6EQnbgUOuVYanvREcmFrOPhoXBrTtjhhP+lW+o5UfK+tDg==} + /@babel/helper-validator-identifier@7.25.9: + resolution: {integrity: sha512-Ed61U6XJc3CVRfkERJWDz4dJwKe7iLmmJsbOGu9wSloNSFttHV0I8g6UAgb7qnK5ly5bGLPd4oXZlxCdANBOWQ==} engines: {node: '>=6.9.0'} - /@babel/helper-validator-identifier@7.22.20: - resolution: {integrity: sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A==} + /@babel/helper-validator-option@7.25.9: + resolution: {integrity: sha512-e/zv1co8pp55dNdEcCynfj9X7nyUKUXoUEwfXqaZt0omVOmDe9oOTdKStH4GmAw6zxMFs50ZayuMfHDKlO7Tfw==} engines: {node: '>=6.9.0'} - /@babel/helper-validator-identifier@7.24.7: - resolution: {integrity: sha512-rR+PBcQ1SMQDDyF6X0wxtG8QyLCgUB0eRAGguqRLfkCA87l7yAP7ehq8SNj96OOGTO8OBV70KhuFYcIkHXOg0w==} - engines: {node: '>=6.9.0'} - - /@babel/helper-validator-option@7.23.5: - resolution: {integrity: sha512-85ttAOMLsr53VgXkTbkx8oA6YTfT4q7/HzXSLEYmjcSTJPMPQtvq1BD79Byep5xMUYbGRzEpDsjUf3dyp54IKw==} - engines: {node: '>=6.9.0'} - - /@babel/helper-validator-option@7.24.7: - resolution: {integrity: sha512-yy1/KvjhV/ZCL+SM7hBrvnZJ3ZuT9OuZgIJAGpPEToANvc3iM6iDvBnRjtElWibHU6n8/LPR/EjX9EtIEYO3pw==} - engines: {node: '>=6.9.0'} - - /@babel/helper-wrap-function@7.22.20: - resolution: {integrity: sha512-pms/UwkOpnQe/PDAEdV/d7dVCoBbB+R4FvYoHGZz+4VPcg7RtYy2KP7S2lbuWM6FCSgob5wshfGESbC/hzNXZw==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/helper-function-name': 7.24.7 - '@babel/template': 7.24.7 - '@babel/types': 7.24.7 - dev: false - - /@babel/helpers@7.23.8: - resolution: {integrity: sha512-KDqYz4PiOWvDFrdHLPhKtCThtIcKVy6avWD2oG4GEvyQ+XDZwHD4YQd+H2vNMnq2rkdxsDkU82T+Vk8U/WXHRQ==} + /@babel/helper-wrap-function@7.25.9: + resolution: {integrity: sha512-ETzz9UTjQSTmw39GboatdymDq4XIQbR8ySgVrylRhPOFpsd+JrKHIuF0de7GCWmem+T4uC5z7EZguod7Wj4A4g==} engines: {node: '>=6.9.0'} dependencies: - '@babel/template': 7.22.15 - '@babel/traverse': 7.23.7 - '@babel/types': 7.23.6 + '@babel/template': 7.25.9 + '@babel/traverse': 7.25.9 + '@babel/types': 7.26.0 transitivePeerDependencies: - supports-color + dev: false - /@babel/helpers@7.24.7: - resolution: {integrity: sha512-NlmJJtvcw72yRJRcnCmGvSi+3jDEg8qFu3z0AFoymmzLx5ERVWyzd9kVXr7Th9/8yIJi2Zc6av4Tqz3wFs8QWg==} + /@babel/helpers@7.26.0: + resolution: {integrity: sha512-tbhNuIxNcVb21pInl3ZSjksLCvgdZy9KwJ8brv993QtIVKJBBkYXz4q4ZbAv31GdnC+R90np23L5FbEBlthAEw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/template': 7.24.7 - '@babel/types': 7.24.7 + '@babel/template': 7.25.9 + '@babel/types': 7.26.0 - /@babel/highlight@7.23.4: - resolution: {integrity: sha512-acGdbYSfp2WheJoJm/EBBBLh/ID8KDc64ISZ9DYtBmC8/Q204PZJLHyzeB5qMzJ5trcOkybd78M4x2KWsUq++A==} - engines: {node: '>=6.9.0'} + /@babel/parser@7.26.2: + resolution: {integrity: sha512-DWMCZH9WA4Maitz2q21SRKHo9QXZxkDsbNZoVD62gusNtNBBqDg9i7uOhASfTfIGNzW+O+r7+jAlM8dwphcJKQ==} + engines: {node: '>=6.0.0'} + hasBin: true dependencies: - '@babel/helper-validator-identifier': 7.22.20 - chalk: 2.4.2 - js-tokens: 4.0.0 + '@babel/types': 7.26.0 - /@babel/highlight@7.24.7: - resolution: {integrity: sha512-EStJpq4OuY8xYfhGVXngigBJRWxftKX9ksiGDnmlY3o7B/V7KIAc9X4oiK87uPJSc/vs5L869bem5fhZa8caZw==} + /@babel/plugin-bugfix-firefox-class-in-computed-class-key@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-ZkRyVkThtxQ/J6nv3JFYv1RYY+JT5BvU0y3k5bWrmuG4woXypRa4PXmm9RhOwodRkYFWqC0C0cqcJ4OqR7kW+g==} engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0 dependencies: - '@babel/helper-validator-identifier': 7.24.7 - chalk: 2.4.2 - js-tokens: 4.0.0 - picocolors: 1.0.1 - - /@babel/parser@7.23.6: - resolution: {integrity: sha512-Z2uID7YJ7oNvAI20O9X0bblw7Qqs8Q2hFy0R9tAfnfLkp5MW0UH9eUvnDSnFwKZ0AvgS1ucqR4KzvVHgnke1VQ==} - engines: {node: '>=6.0.0'} - hasBin: true - dependencies: - '@babel/types': 7.23.6 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/traverse': 7.25.9 + transitivePeerDependencies: + - supports-color + dev: false - /@babel/parser@7.24.7: - resolution: {integrity: sha512-9uUYRm6OqQrCqQdG1iCBwBPZgN8ciDBro2nIOFaiRz1/BCxaI7CNvQbDHvsArAC7Tw9Hda/B3U+6ui9u4HWXPw==} - engines: {node: '>=6.0.0'} - hasBin: true + /@babel/plugin-bugfix-safari-class-field-initializer-scope@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-MrGRLZxLD/Zjj0gdU15dfs+HH/OXvnw/U4jJD8vpcP2CJQapPEv1IWwjc/qMg7ItBlPwSv1hRBbb7LeuANdcnw==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0 dependencies: - '@babel/types': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + dev: false - /@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-iRkKcCqb7iGnq9+3G6rZ+Ciz5VywC4XNRHe57lKM+jOeYAoR0lVqdeeDRfh0tQcTfw/+vBhHn926FmQhLtlFLQ==} + /@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-2qUwwfAFpJLZqxd02YW9btUCZHl+RFvdDkNfZwaIJrvB8Tesjsk8pEQkTvGwZXLqXUx/2oyY3ySRhm6HOXuCug==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-WwlxbfMNdVEpQjZmK5mhm7oSwD3dS6eU+Iwsi4Knl9wAletWem7kaRsGOG+8UEbRyqxY4SS5zvtfXwX+jMxUwQ==} + /@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-6xWgLZTJXwilVjlnV7ospI3xi+sl8lN8rXXbBD6vYn3UYDlGsag8wrZkKcSI8G6KgqKP7vNFaDgeDnfAABq61g==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.13.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/plugin-transform-optional-chaining': 7.23.4(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-skip-transparent-expression-wrappers': 7.25.9 + '@babel/plugin-transform-optional-chaining': 7.25.9(@babel/core@7.26.0) + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly@7.23.7(@babel/core@7.24.7): - resolution: {integrity: sha512-LlRT7HgaifEpQA1ZgLVOIJZZFVPWN5iReq/7/JixwBtwcoeVGDBD53ZV28rrsLYOZs1Y/EHhA8N/Z6aazHR8cw==} + /@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-aLnMXYPnzwwqhYSCyXfKkIkYgJ8zv9RK+roo9DkTXz38ynIhd9XCbN08s3MGvqL2MYGVUGdRQLL/JqBIeJhJBg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-environment-visitor': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/traverse': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-proposal-class-properties@7.18.6(@babel/core@7.23.7): + /@babel/plugin-proposal-class-properties@7.18.6(@babel/core@7.26.0): resolution: {integrity: sha512-cumfXOF0+nzZrrN8Rf0t7M+tF6sZc7vhQwYQck9q1/5w2OExlD+b4v4RpMJFaV1Z7WcDRgO6FqvxqxGlwo+RHQ==} engines: {node: '>=6.9.0'} deprecated: This proposal has been merged to the ECMAScript standard and thus this plugin is no longer maintained. Please use @babel/plugin-transform-class-properties instead. peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-create-class-features-plugin': 7.23.7(@babel/core@7.23.7) - '@babel/helper-plugin-utils': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-create-class-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-proposal-nullish-coalescing-operator@7.18.6(@babel/core@7.23.7): + /@babel/plugin-proposal-nullish-coalescing-operator@7.18.6(@babel/core@7.26.0): resolution: {integrity: sha512-wQxQzxYeJqHcfppzBDnm1yAY0jSRkUXR2z8RePZYrKwMKgMlE8+Z6LUno+bd6LvbGh8Gltvy74+9pIYkr+XkKA==} engines: {node: '>=6.9.0'} deprecated: This proposal has been merged to the ECMAScript standard and thus this plugin is no longer maintained. Please use @babel/plugin-transform-nullish-coalescing-operator instead. peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.26.0) dev: false - /@babel/plugin-proposal-optional-chaining@7.21.0(@babel/core@7.23.7): + /@babel/plugin-proposal-optional-chaining@7.21.0(@babel/core@7.26.0): resolution: {integrity: sha512-p4zeefM72gpmEe2fkUr/OnOXpWEf8nAgk7ZYVqqfFiyIG7oFfVZcCrU64hWn5xp4tQ9LkV4bTIa5rD0KANpKNA==} engines: {node: '>=6.9.0'} deprecated: This proposal has been merged to the ECMAScript standard and thus this plugin is no longer maintained. Please use @babel/plugin-transform-optional-chaining instead. peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-skip-transparent-expression-wrappers': 7.25.9 + '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.26.0) + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-proposal-private-property-in-object@7.21.0-placeholder-for-preset-env.2(@babel/core@7.24.7): + /@babel/plugin-proposal-private-property-in-object@7.21.0-placeholder-for-preset-env.2(@babel/core@7.26.0): resolution: {integrity: sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - dev: false - - /@babel/plugin-syntax-async-generators@7.8.4(@babel/core@7.24.7): - resolution: {integrity: sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-class-properties@7.12.13(@babel/core@7.24.7): - resolution: {integrity: sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-class-static-block@7.14.5(@babel/core@7.24.7): - resolution: {integrity: sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 dev: false - /@babel/plugin-syntax-dynamic-import@7.8.3(@babel/core@7.24.7): - resolution: {integrity: sha512-5gdGbFon+PszYzqs83S3E5mpi7/y/8M9eC90MRTZfduQOYW76ig6SOSPNe41IG5LoP3FGBn2N0RjVDSQiS94kQ==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-export-namespace-from@7.8.3(@babel/core@7.24.7): - resolution: {integrity: sha512-MXf5laXo6c1IbEbegDmzGPwGNTsHZmEy6QGznu5Sh2UCWvueywb2ee+CCE4zQiZstxU9BMoQO9i6zUFSY0Kj0Q==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-flow@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-YZiAIpkJAwQXBJLIQbRFayR5c+gJ35Vcz3bg954k7cd73zqjvhacJuL9RbrzPz8qPmZdgqP6EUKwy0PCNhaaPA==} + /@babel/plugin-syntax-flow@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-B+O2DnPc0iG+YXFqOxv2WNuNU97ToWjOomUQ78DouOENWUaM5sVrmet9mcomUGQFwpJd//gvUagXBSdzO1fRKg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-syntax-import-assertions@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-lPgDSU+SJLK3xmFDTV2ZRQAiM7UuUjGidwBywFavObCiZc1BeAAcMtHJKUya92hPHO+at63JJPLygilZard8jw==} + /@babel/plugin-syntax-import-assertions@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-QCWT5Hh830hK5EQa7XzuqIkQU9tT/whqbDz7kuaZMHFl1inRRg7JnuAEOQ0Ur0QUl0NufCk1msK2BeY79Aj/eg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-syntax-import-attributes@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-pawnE0P9g10xgoP7yKr6CK63K2FMsTE+FZidZO/1PwRdzmAPVs+HS1mAURUsgaoxammTJvULUdIkEK0gOcU2tA==} + /@babel/plugin-syntax-import-attributes@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-e2dttdsJ1ZTpi3B9UYGLw41hifAubg19AtCu/2I/F1QNVclOBr1dYpTdmdyZ84Xiz43BS/tCUkMAZNLv12Pi+A==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-import-meta@7.10.4(@babel/core@7.24.7): - resolution: {integrity: sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-json-strings@7.8.3(@babel/core@7.24.7): - resolution: {integrity: sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-syntax-jsx@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-EB2MELswq55OHUoRZLGg/zC7QWUKfNLpE57m/S2yr1uEneIgsTgrSzXP3NXEsMkVn76OlaVVnzN+ugObuYGwhg==} + /@babel/plugin-syntax-jsx@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-ld6oezHQMZsZfp6pWtbjaNDF2tiiCYYDqQszHt5VV437lewP9aSi2Of99CK0D0XB21k7FLgnLcmQKyKzynfeAA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-syntax-logical-assignment-operators@7.10.4(@babel/core@7.24.7): - resolution: {integrity: sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-nullish-coalescing-operator@7.8.3(@babel/core@7.23.7): + /@babel/plugin-syntax-nullish-coalescing-operator@7.8.3(@babel/core@7.26.0): resolution: {integrity: sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-nullish-coalescing-operator@7.8.3(@babel/core@7.24.7): - resolution: {integrity: sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-numeric-separator@7.10.4(@babel/core@7.24.7): - resolution: {integrity: sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-object-rest-spread@7.8.3(@babel/core@7.24.7): - resolution: {integrity: sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-syntax-optional-catch-binding@7.8.3(@babel/core@7.24.7): - resolution: {integrity: sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - dev: false - - /@babel/plugin-syntax-optional-chaining@7.8.3(@babel/core@7.23.7): + /@babel/plugin-syntax-optional-chaining@7.8.3(@babel/core@7.26.0): resolution: {integrity: sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-optional-chaining@7.8.3(@babel/core@7.24.7): - resolution: {integrity: sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-private-property-in-object@7.14.5(@babel/core@7.24.7): - resolution: {integrity: sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-syntax-top-level-await@7.14.5(@babel/core@7.24.7): - resolution: {integrity: sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw==} + /@babel/plugin-syntax-typescript@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-hjMgRy5hb8uJJjUcdWunWVcoi9bGpJp8p5Ol1229PoN6aytsLwNMgmdftO23wnCLMfVmTwZDWMPNq/D1SY60JQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-syntax-typescript@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-9EiNjVJOMwCO+43TqoTrgQ8jMwcAd0sWyXi9RPfIsLTj4R2MADDDQXELhffaUx/uJv2AYcxBgPwH6j4TIA4ytQ==} - engines: {node: '>=6.9.0'} - peerDependencies: - '@babel/core': ^7.0.0-0 - dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - dev: false - - /@babel/plugin-syntax-unicode-sets-regex@7.18.6(@babel/core@7.24.7): + /@babel/plugin-syntax-unicode-sets-regex@7.18.6(@babel/core@7.26.0): resolution: {integrity: sha512-727YkEAPwSIQTv5im8QHz3upqp92JTWhidIC81Tdx4VJYIte/VndKf1qKrfnnhPLiPghStWfvC/iFaMCQu7Nqg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-regexp-features-plugin': 7.22.15(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-arrow-functions@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-NzQcQrzaQPkaEwoTm4Mhyl8jI1huEL/WWIEvudjTCMJ9aBZNpsJbMASx7EQECtQQPS/DcnFpo0FIh3LvEO9cxQ==} + /@babel/plugin-transform-arrow-functions@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-6jmooXYIwn9ca5/RylZADJ+EnSxVUS5sjeJ9UPk6RWRzXCmOJCy6dqItPJFpw2cuCangPK4OYr5uhGKcmrm5Qg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-async-generator-functions@7.23.7(@babel/core@7.24.7): - resolution: {integrity: sha512-PdxEpL71bJp1byMG0va5gwQcXHxuEYC/BgI/e88mGTtohbZN28O5Yit0Plkkm/dBzCF/BxmbNcses1RH1T+urA==} + /@babel/plugin-transform-async-generator-functions@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-RXV6QAzTBbhDMO9fWwOmwwTuYaiPbggWQ9INdZqAYeSHyG7FzQ+nOZaUUjNwKv9pV3aE4WFqFm1Hnbci5tBCAw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-environment-visitor': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-remap-async-to-generator': 7.22.20(@babel/core@7.24.7) - '@babel/plugin-syntax-async-generators': 7.8.4(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-remap-async-to-generator': 7.25.9(@babel/core@7.26.0) + '@babel/traverse': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-async-to-generator@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-A7LFsKi4U4fomjqXJlZg/u0ft/n8/7n7lpffUP/ZULx/DtV9SGlNKZolHH6PE8Xl1ngCc0M11OaeZptXVkfKSw==} + /@babel/plugin-transform-async-to-generator@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-NT7Ejn7Z/LjUH0Gv5KsBCxh7BH3fbLTV0ptHvpeMvrt3cPThHfJfst9Wrb7S8EvJ7vRTFI7z+VAvFVEQn/m5zQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-module-imports': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-remap-async-to-generator': 7.22.20(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-module-imports': 7.25.9 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-remap-async-to-generator': 7.25.9(@babel/core@7.26.0) transitivePeerDependencies: - supports-color dev: false - /@babel/plugin-transform-block-scoped-functions@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-vI+0sIaPIO6CNuM9Kk5VmXcMVRiOpDh7w2zZt9GXzmE/9KD70CUEVhvPR/etAeNK/FAEkhxQtXOzVF3EuRL41A==} + /@babel/plugin-transform-block-scoped-functions@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-toHc9fzab0ZfenFpsyYinOX0J/5dgJVA2fm64xPewu7CoYHWEivIWKxkK2rMi4r3yQqLnVmheMXRdG+k239CgA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-block-scoping@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-0QqbP6B6HOh7/8iNR4CQU2Th/bbRtBp4KS9vcaZd1fZ0wSh5Fyssg0UCIHwxh+ka+pNDREbVLQnHCMHKZfPwfw==} + /@babel/plugin-transform-block-scoping@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-1F05O7AYjymAtqbsFETboN1NvBdcnzMerO+zlMyJBEz6WkMdejvGWw9p05iTSjC85RLlBseHHQpYaM4gzJkBGg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-class-properties@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-uM+AN8yCIjDPccsKGlw271xjJtGii+xQIF/uMPS8H15L12jZTsLfF4o5vNO7d/oUguOyfdikHGc/yi9ge4SGIg==} + /@babel/plugin-transform-class-properties@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-bbMAII8GRSkcd0h0b4X+36GksxuheLFjP65ul9w6C3KgAamI3JqErNgSrosX6ZPj+Mpim5VvEbawXxJCyEUV3Q==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-class-features-plugin': 7.23.7(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-class-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-class-static-block@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-nsWu/1M+ggti1SOALj3hfx5FXzAY06fwPJsUZD4/A5e1bWi46VUIWtD+kOX6/IdhXGsXBWllLFDSnqSCdUNydQ==} + /@babel/plugin-transform-class-static-block@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-6J2APTs7BDDm+UMqP1useWqhcRAXo0WIoVj26N7kPFB6S73Lgvyka4KTZYIxtgYXiN5HTyRObA72N2iu628iTQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.12.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-class-features-plugin': 7.23.7(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-class-static-block': 7.14.5(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-create-class-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-classes@7.23.8(@babel/core@7.24.7): - resolution: {integrity: sha512-yAYslGsY1bX6Knmg46RjiCiNSwJKv2IUC8qOdYKqMMr0491SXFhcHqOdRDeCRohOOIzwN/90C6mQ9qAKgrP7dg==} + /@babel/plugin-transform-classes@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-mD8APIXmseE7oZvZgGABDyM34GUmK45Um2TXiBUt7PnuAxrgoSVf123qUzPxEr/+/BHrRn5NMZCdE2m/1F8DGg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-compilation-targets': 7.24.7 - '@babel/helper-environment-visitor': 7.24.7 - '@babel/helper-function-name': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-replace-supers': 7.22.20(@babel/core@7.24.7) - '@babel/helper-split-export-declaration': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-annotate-as-pure': 7.25.9 + '@babel/helper-compilation-targets': 7.25.9 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-replace-supers': 7.25.9(@babel/core@7.26.0) + '@babel/traverse': 7.25.9 globals: 11.12.0 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-computed-properties@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-dTj83UVTLw/+nbiHqQSFdwO9CbTtwq1DsDqm3CUEtDrZNET5rT5E6bIdTlOftDTDLMYxvxHNEYO4B9SLl8SLZw==} + /@babel/plugin-transform-computed-properties@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-HnBegGqXZR12xbcTHlJ9HGxw1OniltT26J5YpfruGqtUHlz/xKf/G2ak9e+t0rVqrjXa9WOhvYPz1ERfMj23AA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/template': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/template': 7.25.9 dev: false - /@babel/plugin-transform-destructuring@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-n225npDqjDIr967cMScVKHXJs7rout1q+tt50inyBCPkyZ8KxeI6d+GIbSBTT/w/9WdlWDOej3V9HE5Lgk57gw==} + /@babel/plugin-transform-destructuring@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-WkCGb/3ZxXepmMiX101nnGiU+1CAdut8oHyEOHxkKuS1qKpU2SMXE2uSvfz8PBuLd49V6LEsbtyPhWC7fnkgvQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-dotall-regex@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-vgnFYDHAKzFaTVp+mneDsIEbnJ2Np/9ng9iviHw3P/KVcgONxpNULEW/51Z/BaFojG2GI2GwwXck5uV1+1NOYQ==} + /@babel/plugin-transform-dotall-regex@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-t7ZQ7g5trIgSRYhI9pIJtRl64KHotutUJsh4Eze5l7olJv+mRSg4/MmbZ0tv1eeqRbdvo/+trvJD/Oc5DmW2cA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-regexp-features-plugin': 7.22.15(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-duplicate-keys@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-RrqQ+BQmU3Oyav3J+7/myfvRCq7Tbz+kKLLshUmMwNlDHExbGL7ARhajvoBJEvc+fCguPPu887N+3RRXBVKZUA==} + /@babel/plugin-transform-duplicate-keys@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-LZxhJ6dvBb/f3x8xwWIuyiAHy56nrRG3PeYTpBkkzkYRRQ6tJLu68lEF5VIqMUZiAV7a8+Tb78nEoMCMcqjXBw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-dynamic-import@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-V6jIbLhdJK86MaLh4Jpghi8ho5fGzt3imHOBu/x0jlBaPYqDoWz4RDXjmMOfnh+JWNaQleEAByZLV0QzBT4YQQ==} + /@babel/plugin-transform-duplicate-named-capturing-groups-regex@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-0UfuJS0EsXbRvKnwcLjFtJy/Sxc5J5jhLHnFhy7u4zih97Hz6tJkLU+O+FMMrNZrosUPxDi6sYxJ/EA8jDiAog==} engines: {node: '>=6.9.0'} peerDependencies: - '@babel/core': ^7.0.0-0 + '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-dynamic-import': 7.8.3(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-exponentiation-operator@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-5fhCsl1odX96u7ILKHBj4/Y8vipoqwsJMh4csSA8qFfxrZDEA4Ssku2DyNvMJSmZNOEBT750LfFPbtrnTP90BQ==} + /@babel/plugin-transform-dynamic-import@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-GCggjexbmSLaFhqsojeugBpeaRIgWNTcgKVq/0qIteFEqY2A+b9QidYadrWlnbWQUrW5fn+mCvf3tr7OeBFTyg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-builder-binary-assignment-operator-visitor': 7.22.15 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-export-namespace-from@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-GzuSBcKkx62dGzZI1WVgTWvkkz84FZO5TC5T8dl/Tht/rAla6Dg/Mz9Yhypg+ezVACf/rgDuQt3kbWEv7LdUDQ==} + /@babel/plugin-transform-exponentiation-operator@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-KRhdhlVk2nObA5AYa7QMgTMTVJdfHprfpAk4DjZVtllqRg9qarilstTKEhpVjyt+Npi8ThRyiV8176Am3CodPA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-export-namespace-from': 7.8.3(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-builder-binary-assignment-operator-visitor': 7.25.9 + '@babel/helper-plugin-utils': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-flow-strip-types@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-26/pQTf9nQSNVJCrLB1IkHUKyPxR+lMrH2QDPG89+Znu9rAMbtrybdbWeE9bb7gzjmE5iXHEY+e0HUwM6Co93Q==} + /@babel/plugin-transform-export-namespace-from@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-2NsEz+CxzJIVOPx2o9UsW1rXLqtChtLoVnwYHHiB04wS5sgn7mrV45fWMBX0Kk+ub9uXytVYfNP2HjbVbCB3Ww==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-flow': 7.23.3(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-for-of@7.23.6(@babel/core@7.24.7): - resolution: {integrity: sha512-aYH4ytZ0qSuBbpfhuofbg/e96oQ7U2w1Aw/UQmKT+1l39uEhUPoFS3fHevDc1G0OvewyDudfMKY1OulczHzWIw==} + /@babel/plugin-transform-flow-strip-types@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-/VVukELzPDdci7UUsWQaSkhgnjIWXnIyRpM02ldxaVoFK96c41So8JcKT3m0gYjyv7j5FNPGS5vfELrWalkbDA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/plugin-syntax-flow': 7.26.0(@babel/core@7.26.0) dev: false - /@babel/plugin-transform-function-name@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-I1QXp1LxIvt8yLaib49dRW5Okt7Q4oaxao6tFVKS/anCdEOMtYwWVKoiOA1p34GOWIZjUK0E+zCp7+l1pfQyiw==} + /@babel/plugin-transform-for-of@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-LqHxduHoaGELJl2uhImHwRQudhCM50pT46rIBNvtT/Oql3nqiS3wOwP+5ten7NpYSXrrVLgtZU3DZmPtWZo16A==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-compilation-targets': 7.24.7 - '@babel/helper-function-name': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-skip-transparent-expression-wrappers': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-json-strings@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-81nTOqM1dMwZ/aRXQ59zVubN9wHGqk6UtqRK+/q+ciXmRy8fSolhGVvG09HHRGo4l6fr/c4ZhXUQH0uFW7PZbg==} + /@babel/plugin-transform-function-name@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-8lP+Yxjv14Vc5MuWBpJsoUCd3hD6V9DgBon2FVYL4jJgbnVQ9fTgYmonchzZJOVNgzEgbxp4OwAf6xz6M/14XA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-json-strings': 7.8.3(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-compilation-targets': 7.25.9 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/traverse': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-literals@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-wZ0PIXRxnwZvl9AYpqNUxpZ5BiTGrYt7kueGQ+N5FiQ7RCOD4cm8iShd6S6ggfVIWaJf2EMk8eRzAh52RfP4rQ==} + /@babel/plugin-transform-json-strings@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-xoTMk0WXceiiIvsaquQQUaLLXSW1KJ159KP87VilruQm0LNNGxWzahxSS6T6i4Zg3ezp4vA4zuwiNUR53qmQAw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-logical-assignment-operators@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-Mc/ALf1rmZTP4JKKEhUwiORU+vcfarFVLfcFiolKUo6sewoxSEgl36ak5t+4WamRsNr6nzjZXQjM35WsU+9vbg==} + /@babel/plugin-transform-literals@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-9N7+2lFziW8W9pBl2TzaNht3+pgMIRP74zizeCSrtnSKVdUl8mAjjOP2OOVQAfZ881P2cNjDj1uAMEdeD50nuQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-logical-assignment-operators': 7.10.4(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-member-expression-literals@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-sC3LdDBDi5x96LA+Ytekz2ZPk8i/Ck+DEuDbRAll5rknJ5XRTSaPKEYwomLcs1AA8wg9b3KjIQRsnApj+q51Ag==} + /@babel/plugin-transform-logical-assignment-operators@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-wI4wRAzGko551Y8eVf6iOY9EouIDTtPb0ByZx+ktDGHwv6bHFimrgJM/2T021txPZ2s4c7bqvHbd+vXG6K948Q==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-modules-amd@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-vJYQGxeKM4t8hYCKVBlZX/gtIY2I7mRGFNcm85sgXGMTBcoV3QdVtdpbcWEbzbfUIUZKwvgFT82mRvaQIebZzw==} + /@babel/plugin-transform-member-expression-literals@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-PYazBVfofCQkkMzh2P6IdIUaCEWni3iYEerAsRWuVd8+jlM1S9S9cz1dF9hIzyoZ8IA3+OwVYIp9v9e+GbgZhA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-module-transforms': 7.24.7(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 - transitivePeerDependencies: - - supports-color + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-modules-commonjs@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-aVS0F65LKsdNOtcz6FRCpE4OgsP2OFnW46qNxNIX9h3wuzaNcSQsJysuMwqSibC98HPrf2vCgtxKNwS0DAlgcA==} + /@babel/plugin-transform-modules-amd@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-g5T11tnI36jVClQlMlt4qKDLlWnG5pP9CSM4GhdRciTNMRgkfpo5cR6b4rGIOYPgRRuFAvwjPQ/Yk+ql4dyhbw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-module-transforms': 7.23.3(@babel/core@7.23.7) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-simple-access': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-module-transforms': 7.26.0(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-modules-commonjs@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-aVS0F65LKsdNOtcz6FRCpE4OgsP2OFnW46qNxNIX9h3wuzaNcSQsJysuMwqSibC98HPrf2vCgtxKNwS0DAlgcA==} + /@babel/plugin-transform-modules-commonjs@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-dwh2Ol1jWwL2MgkCzUSOvfmKElqQcuswAZypBSUsScMXvgdT8Ekq5YA6TtqpTVWH+4903NmboMuH1o9i8Rxlyg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-module-transforms': 7.23.3(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-simple-access': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-module-transforms': 7.26.0(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-simple-access': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-modules-systemjs@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-ZxyKGTkF9xT9YJuKQRo19ewf3pXpopuYQd8cDXqNzc3mUNbOME0RKMoZxviQk74hwzfQsEe66dE92MaZbdHKNQ==} + /@babel/plugin-transform-modules-systemjs@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-hyss7iIlH/zLHaehT+xwiymtPOpsiwIIRlCAOwBB04ta5Tt+lNItADdlXw3jAWZ96VJ2jlhl/c+PNIQPKNfvcA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-hoist-variables': 7.24.7 - '@babel/helper-module-transforms': 7.24.7(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-validator-identifier': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-module-transforms': 7.26.0(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-validator-identifier': 7.25.9 + '@babel/traverse': 7.25.9 transitivePeerDependencies: - supports-color dev: false - /@babel/plugin-transform-modules-umd@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-zHsy9iXX2nIsCBFPud3jKn1IRPWg3Ing1qOZgeKV39m1ZgIdpJqvlWVeiHBZC6ITRG0MfskhYe9cLgntfSFPIg==} + /@babel/plugin-transform-modules-umd@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-bS9MVObUgE7ww36HEfwe6g9WakQ0KF07mQF74uuXdkoziUPfKyu/nIm663kz//e5O1nPInPFx36z7WJmJ4yNEw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-module-transforms': 7.24.7(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-module-transforms': 7.26.0(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 transitivePeerDependencies: - supports-color dev: false - /@babel/plugin-transform-named-capturing-groups-regex@7.22.5(@babel/core@7.24.7): - resolution: {integrity: sha512-YgLLKmS3aUBhHaxp5hi1WJTgOUb/NCuDHzGT9z9WTt3YG+CPRhJs6nprbStx6DnWM4dh6gt7SU3sZodbZ08adQ==} + /@babel/plugin-transform-named-capturing-groups-regex@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-oqB6WHdKTGl3q/ItQhpLSnWWOpjUJLsOCLVyeFgeTktkBSCiurvPOsyt93gibI9CmuKvTUEtWmG5VhZD+5T/KA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-regexp-features-plugin': 7.22.15(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-new-target@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-YJ3xKqtJMAT5/TIZnpAR3I+K+WaDowYbN3xyxI8zxx/Gsypwf9B9h0VB+1Nh6ACAAPRS5NSRje0uVv5i79HYGQ==} + /@babel/plugin-transform-new-target@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-U/3p8X1yCSoKyUj2eOBIx3FOn6pElFOKvAAGf8HTtItuPyB+ZeOqfn+mvTtg9ZlOAjsPdK3ayQEjqHjU/yLeVQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-nullish-coalescing-operator@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-jHE9EVVqHKAQx+VePv5LLGHjmHSJR76vawFPTdlxR/LVJPfOEGxREQwQfjuZEOPTwG92X3LINSh3M40Rv4zpVA==} + /@babel/plugin-transform-nullish-coalescing-operator@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-ENfftpLZw5EItALAD4WsY/KUWvhUlZndm5GC7G3evUsVeSJB6p0pBeLQUnRnBCBx7zV0RKQjR9kCuwrsIrjWog==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-numeric-separator@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-mps6auzgwjRrwKEZA05cOwuDc9FAzoyFS4ZsG/8F43bTLf/TgkJg7QXOrPO1JO599iA3qgK9MXdMGOEC8O1h6Q==} + /@babel/plugin-transform-numeric-separator@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-TlprrJ1GBZ3r6s96Yq8gEQv82s8/5HnCVHtEJScUj90thHQbwe+E5MLhi2bbNHBEJuzrvltXSru+BUxHDoog7Q==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-numeric-separator': 7.10.4(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-object-rest-spread@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-9x9K1YyeQVw0iOXJlIzwm8ltobIIv7j2iLyP2jIhEbqPRQ7ScNgwQufU2I0Gq11VjyG4gI4yMXt2VFags+1N3g==} + /@babel/plugin-transform-object-rest-spread@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-fSaXafEE9CVHPweLYw4J0emp1t8zYTXyzN3UuG+lylqkvYd7RMrsOQ8TYx5RF231be0vqtFC6jnx3UmpJmKBYg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/compat-data': 7.24.7 - '@babel/core': 7.24.7 - '@babel/helper-compilation-targets': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-object-rest-spread': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-transform-parameters': 7.23.3(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-compilation-targets': 7.25.9 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/plugin-transform-parameters': 7.25.9(@babel/core@7.26.0) dev: false - /@babel/plugin-transform-object-super@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-BwQ8q0x2JG+3lxCVFohg+KbQM7plfpBwThdW9A6TMtWwLsbDA01Ek2Zb/AgDN39BiZsExm4qrXxjk+P1/fzGrA==} + /@babel/plugin-transform-object-super@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-Kj/Gh+Rw2RNLbCK1VAWj2U48yxxqL2x0k10nPtSdRa0O2xnHXalD0s+o1A6a0W43gJ00ANo38jxkQreckOzv5A==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-replace-supers': 7.22.20(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-replace-supers': 7.25.9(@babel/core@7.26.0) + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-optional-catch-binding@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-XIq8t0rJPHf6Wvmbn9nFxU6ao4c7WhghTR5WyV8SrJfUFzyxhCm4nhC+iAp3HFhbAKLfYpgzhJ6t4XCtVwqO5A==} + /@babel/plugin-transform-optional-catch-binding@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-qM/6m6hQZzDcZF3onzIhZeDHDO43bkNNlOX0i8n3lR6zLbu0GN2d8qfM/IERJZYauhAHSLHy39NF0Ctdvcid7g==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-optional-catch-binding': 7.8.3(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-optional-chaining@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-ZU8y5zWOfjM5vZ+asjgAPwDaBjJzgufjES89Rs4Lpq63O300R/kOz30WCLo6BxxX6QVEilwSlpClnG5cZaikTA==} + /@babel/plugin-transform-optional-chaining@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-6AvV0FsLULbpnXeBjrY4dmWF8F7gf8QnvTEoO/wX/5xm/xE1Xo8oPuD3MPS+KS9f9XBEAWN7X1aWr4z9HdOr7A==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 - '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-skip-transparent-expression-wrappers': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-parameters@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-09lMt6UsUb3/34BbECKVbVwrT9bO6lILWln237z7sLaWnMsTi7Yc9fhX5DLpkJzAGfaReXI22wP41SZmnAA3Vw==} + /@babel/plugin-transform-parameters@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-wzz6MKwpnshBAiRmn4jR8LYz/g8Ksg0o80XmwZDlordjwEk9SxBzTWC7F5ef1jhbrbOW2DJ5J6ayRukrJmnr0g==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-private-methods@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-UzqRcRtWsDMTLrRWFvUBDwmw06tCQH9Rl1uAjfh6ijMSmGYQ+fpdB+cnqRC8EMh5tuuxSv0/TejGL+7vyj+50g==} + /@babel/plugin-transform-private-methods@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-D/JUozNpQLAPUVusvqMxyvjzllRaF8/nSrP1s2YGQT/W4LHK4xxsMcHjhOGTS01mp9Hda8nswb+FblLdJornQw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-class-features-plugin': 7.23.7(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-class-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-private-property-in-object@7.23.4(@babel/core@7.24.7): - resolution: {integrity: sha512-9G3K1YqTq3F4Vt88Djx1UZ79PDyj+yKRnUy7cZGSMe+a7jkwD259uKKuUzQlPkGam7R+8RJwh5z4xO27fA1o2A==} + /@babel/plugin-transform-private-property-in-object@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-Evf3kcMqzXA3xfYJmZ9Pg1OvKdtqsDMSWBDzZOPLvHiTt36E75jLDQo5w1gtRU95Q4E5PDttrTf25Fw8d/uWLw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-create-class-features-plugin': 7.23.7(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 - '@babel/plugin-syntax-private-property-in-object': 7.14.5(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-annotate-as-pure': 7.25.9 + '@babel/helper-create-class-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-property-literals@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-jR3Jn3y7cZp4oEWPFAlRsSWjxKe4PZILGBSd4nis1TsC5qeSpb+nrtihJuDhNI7QHiVbUaiXa0X2RZY3/TI6Nw==} + /@babel/plugin-transform-property-literals@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-IvIUeV5KrS/VPavfSM/Iu+RE6llrHrYIKY1yfCzyO/lMXHQ+p7uGhonmGVisv6tSBSVgWzMBohTcvkC9vQcQFA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-react-jsx-self@7.24.7(@babel/core@7.24.7): - resolution: {integrity: sha512-fOPQYbGSgH0HUp4UJO4sMBFjY6DuWq+2i8rixyUMb3CdGixs/gccURvYOAhajBdKDoGajFr3mUq5rH3phtkGzw==} + /@babel/plugin-transform-react-jsx-self@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-y8quW6p0WHkEhmErnfe58r7x0A70uKphQm8Sp8cV7tjNQwK56sNVK0M73LK3WuYmsuyrftut4xAkjjgU0twaMg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: true - /@babel/plugin-transform-react-jsx-source@7.24.7(@babel/core@7.24.7): - resolution: {integrity: sha512-J2z+MWzZHVOemyLweMqngXrgGC42jQ//R0KdxqkIz/OrbVIIlhFI3WigZ5fO+nwFvBlncr4MGapd8vTyc7RPNQ==} + /@babel/plugin-transform-react-jsx-source@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-+iqjT8xmXhhYv4/uiYd8FNQsraMFZIfxVSqxxVSZP0WbbSAWvBXAul0m/zu+7Vv4O/3WtApy9pmaTMiumEZgfg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: true - /@babel/plugin-transform-regenerator@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-KP+75h0KghBMcVpuKisx3XTu9Ncut8Q8TuvGO4IhY+9D5DFEckQefOuIsB/gQ2tG71lCke4NMrtIPS8pOj18BQ==} + /@babel/plugin-transform-regenerator@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-vwDcDNsgMPDGP0nMqzahDWE5/MLcX8sv96+wfX7as7LoF/kr97Bo/7fI00lXY4wUXYfVmwIIyG80fGZ1uvt2qg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 regenerator-transform: 0.15.2 dev: false - /@babel/plugin-transform-reserved-words@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-QnNTazY54YqgGxwIexMZva9gqbPa15t/x9VS+0fsEFWplwVpXYZivtgl43Z1vMpc1bdPP2PP8siFeVcnFvA3Cg==} + /@babel/plugin-transform-regexp-modifiers@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-vN6saax7lrA2yA/Pak3sCxuD6F5InBjn9IcrIKQPjpsLvuHYLVroTxjdlVRHjjBWxKOqIwpTXDkOssYT4BFdRw==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0 + dependencies: + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + dev: false + + /@babel/plugin-transform-reserved-words@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-7DL7DKYjn5Su++4RXu8puKZm2XBPHyjWLUidaPEkCUBbE7IPcsrkRHggAOOKydH1dASWdcUBxrkOGNxUv5P3Jg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-shorthand-properties@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-ED2fgqZLmexWiN+YNFX26fx4gh5qHDhn1O2gvEhreLW2iI63Sqm4llRLCXALKrCnbN4Jy0VcMQZl/SAzqug/jg==} + /@babel/plugin-transform-shorthand-properties@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-MUv6t0FhO5qHnS/W8XCbHmiRWOphNufpE1IVxhK5kuN3Td9FT1x4rx4K42s3RYdMXCXpfWkGSbCSd0Z64xA7Ng==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-spread@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-VvfVYlrlBVu+77xVTOAoxQ6mZbnIq5FM0aGBSFEcIh03qHf+zNqA4DC/3XMUozTg7bZV3e3mZQ0i13VB6v5yUg==} + /@babel/plugin-transform-spread@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-oNknIB0TbURU5pqJFVbOOFspVlrpVwo2H1+HUIsVDvp5VauGGDP1ZEvO8Nn5xyMEs3dakajOxlmkNW7kNgSm6A==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-skip-transparent-expression-wrappers': 7.22.5 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-skip-transparent-expression-wrappers': 7.25.9 + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-sticky-regex@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-HZOyN9g+rtvnOU3Yh7kSxXrKbzgrm5X4GncPY1QOquu7epga5MxKHVpYu2hvQnry/H+JjckSYRb93iNfsioAGg==} + /@babel/plugin-transform-sticky-regex@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-WqBUSgeVwucYDP9U/xNRQam7xV8W5Zf+6Eo7T2SRVUFlhRiMNFdFz58u0KZmCVVqs2i7SHgpRnAhzRNmKfi2uA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-template-literals@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-Flok06AYNp7GV2oJPZZcP9vZdszev6vPBkHLwxwSpaIqx75wn6mUd3UFWsSsA0l8nXAKkyCmL/sR02m8RYGeHg==} + /@babel/plugin-transform-template-literals@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-o97AE4syN71M/lxrCtQByzphAdlYluKPDBzDVzMmfCobUjjhAryZV0AIpRPrxN0eAkxXO6ZLEScmt+PNhj2OTw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-typeof-symbol@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-4t15ViVnaFdrPC74be1gXBSMzXk3B4Us9lP7uLRQHTFpV5Dvt33pn+2MyyNxmN3VTTm3oTrZVMUmuw3oBnQ2oQ==} + /@babel/plugin-transform-typeof-symbol@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-v61XqUMiueJROUv66BVIOi0Fv/CUuZuZMl5NkRoCVxLAnMexZ0A3kMe7vvZ0nulxMuMp0Mk6S5hNh48yki08ZA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-typescript@7.23.6(@babel/core@7.23.7): - resolution: {integrity: sha512-6cBG5mBvUu4VUD04OHKnYzbuHNP8huDsD3EDqqpIpsswTDoqHCjLoHb6+QgsV1WsT2nipRqCPgxD3LXnEO7XfA==} + /@babel/plugin-transform-typescript@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-7PbZQZP50tzv2KGGnhh82GSyMB01yKY9scIjf1a+GfZCtInOWqUH5+1EBU4t9fyR5Oykkkc9vFTs4OHrhHXljQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-annotate-as-pure': 7.22.5 - '@babel/helper-create-class-features-plugin': 7.23.7(@babel/core@7.23.7) - '@babel/helper-plugin-utils': 7.22.5 - '@babel/plugin-syntax-typescript': 7.23.3(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@babel/helper-annotate-as-pure': 7.25.9 + '@babel/helper-create-class-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-skip-transparent-expression-wrappers': 7.25.9 + '@babel/plugin-syntax-typescript': 7.25.9(@babel/core@7.26.0) + transitivePeerDependencies: + - supports-color dev: false - /@babel/plugin-transform-unicode-escapes@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-OMCUx/bU6ChE3r4+ZdylEqAjaQgHAgipgW8nsCfu5pGqDcFytVd91AwRvUJSBZDz0exPGgnjoqhgRYLRjFZc9Q==} + /@babel/plugin-transform-unicode-escapes@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-s5EDrE6bW97LtxOcGj1Khcx5AaXwiMmi4toFWRDP9/y0Woo6pXC+iyPu/KuhKtfSrNFd7jJB+/fkOtZy6aIC6Q==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-unicode-property-regex@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-KcLIm+pDZkWZQAFJ9pdfmh89EwVfmNovFBcXko8szpBeF8z68kWIPeKlmSOkT9BXJxs2C0uk+5LxoxIv62MROA==} + /@babel/plugin-transform-unicode-property-regex@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-Jt2d8Ga+QwRluxRQ307Vlxa6dMrYEMZCgGxoPR8V52rxPyldHu3hdlHspxaqYmE7oID5+kB+UKUB/eWS+DkkWg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-regexp-features-plugin': 7.22.15(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-unicode-regex@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-wMHpNA4x2cIA32b/ci3AfwNgheiva2W0WUKWTK7vBHBhDKfPsc5cFGNWm69WBqpwd86u1qwZ9PWevKqm1A3yAw==} + /@babel/plugin-transform-unicode-regex@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-yoxstj7Rg9dlNn9UQxzk4fcNivwv4nUYz7fYXBaKxvw/lnmPuOm/ikoELygbYq68Bls3D/D+NBPHiLwZdZZ4HA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-regexp-features-plugin': 7.22.15(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/plugin-transform-unicode-sets-regex@7.23.3(@babel/core@7.24.7): - resolution: {integrity: sha512-W7lliA/v9bNR83Qc3q1ip9CQMZ09CcHDbHfbLRDNuAhn1Mvkr1ZNF7hPmztMQvtTGVLJ9m8IZqWsTkXOml8dbw==} + /@babel/plugin-transform-unicode-sets-regex@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-8BYqO3GeVNHtx69fdPshN3fnzUNLrWdHhk/icSwigksJGczKSizZ+Z6SBCxTs723Fr5VSNorTIK7a+R2tISvwQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-create-regexp-features-plugin': 7.22.15(@babel/core@7.24.7) - '@babel/helper-plugin-utils': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-create-regexp-features-plugin': 7.25.9(@babel/core@7.26.0) + '@babel/helper-plugin-utils': 7.25.9 dev: false - /@babel/preset-env@7.23.8(@babel/core@7.24.7): - resolution: {integrity: sha512-lFlpmkApLkEP6woIKprO6DO60RImpatTQKtz4sUcDjVcK8M8mQ4sZsuxaTMNOZf0sqAq/ReYW1ZBHnOQwKpLWA==} + /@babel/preset-env@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-H84Fxq0CQJNdPFT2DrfnylZ3cf5K43rGfWK4LJGPpjKHiZlk0/RzwEus3PDDZZg+/Er7lCA03MVacueUuXdzfw==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/compat-data': 7.24.7 - '@babel/core': 7.24.7 - '@babel/helper-compilation-targets': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/helper-validator-option': 7.24.7 - '@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly': 7.23.7(@babel/core@7.24.7) - '@babel/plugin-proposal-private-property-in-object': 7.21.0-placeholder-for-preset-env.2(@babel/core@7.24.7) - '@babel/plugin-syntax-async-generators': 7.8.4(@babel/core@7.24.7) - '@babel/plugin-syntax-class-properties': 7.12.13(@babel/core@7.24.7) - '@babel/plugin-syntax-class-static-block': 7.14.5(@babel/core@7.24.7) - '@babel/plugin-syntax-dynamic-import': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-syntax-export-namespace-from': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-syntax-import-assertions': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-syntax-import-attributes': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-syntax-import-meta': 7.10.4(@babel/core@7.24.7) - '@babel/plugin-syntax-json-strings': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-syntax-logical-assignment-operators': 7.10.4(@babel/core@7.24.7) - '@babel/plugin-syntax-nullish-coalescing-operator': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-syntax-numeric-separator': 7.10.4(@babel/core@7.24.7) - '@babel/plugin-syntax-object-rest-spread': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-syntax-optional-catch-binding': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-syntax-optional-chaining': 7.8.3(@babel/core@7.24.7) - '@babel/plugin-syntax-private-property-in-object': 7.14.5(@babel/core@7.24.7) - '@babel/plugin-syntax-top-level-await': 7.14.5(@babel/core@7.24.7) - '@babel/plugin-syntax-unicode-sets-regex': 7.18.6(@babel/core@7.24.7) - '@babel/plugin-transform-arrow-functions': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-async-generator-functions': 7.23.7(@babel/core@7.24.7) - '@babel/plugin-transform-async-to-generator': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-block-scoped-functions': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-block-scoping': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-class-properties': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-class-static-block': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-classes': 7.23.8(@babel/core@7.24.7) - '@babel/plugin-transform-computed-properties': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-destructuring': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-dotall-regex': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-duplicate-keys': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-dynamic-import': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-exponentiation-operator': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-export-namespace-from': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-for-of': 7.23.6(@babel/core@7.24.7) - '@babel/plugin-transform-function-name': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-json-strings': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-literals': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-logical-assignment-operators': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-member-expression-literals': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-modules-amd': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-modules-commonjs': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-modules-systemjs': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-modules-umd': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-named-capturing-groups-regex': 7.22.5(@babel/core@7.24.7) - '@babel/plugin-transform-new-target': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-nullish-coalescing-operator': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-numeric-separator': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-object-rest-spread': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-object-super': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-optional-catch-binding': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-optional-chaining': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-parameters': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-private-methods': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-private-property-in-object': 7.23.4(@babel/core@7.24.7) - '@babel/plugin-transform-property-literals': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-regenerator': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-reserved-words': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-shorthand-properties': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-spread': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-sticky-regex': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-template-literals': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-typeof-symbol': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-unicode-escapes': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-unicode-property-regex': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-unicode-regex': 7.23.3(@babel/core@7.24.7) - '@babel/plugin-transform-unicode-sets-regex': 7.23.3(@babel/core@7.24.7) - '@babel/preset-modules': 0.1.6-no-external-plugins(@babel/core@7.24.7) - babel-plugin-polyfill-corejs2: 0.4.8(@babel/core@7.24.7) - babel-plugin-polyfill-corejs3: 0.8.7(@babel/core@7.24.7) - babel-plugin-polyfill-regenerator: 0.5.5(@babel/core@7.24.7) - core-js-compat: 3.35.1 + '@babel/compat-data': 7.26.2 + '@babel/core': 7.26.0 + '@babel/helper-compilation-targets': 7.25.9 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-validator-option': 7.25.9 + '@babel/plugin-bugfix-firefox-class-in-computed-class-key': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-bugfix-safari-class-field-initializer-scope': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-proposal-private-property-in-object': 7.21.0-placeholder-for-preset-env.2(@babel/core@7.26.0) + '@babel/plugin-syntax-import-assertions': 7.26.0(@babel/core@7.26.0) + '@babel/plugin-syntax-import-attributes': 7.26.0(@babel/core@7.26.0) + '@babel/plugin-syntax-unicode-sets-regex': 7.18.6(@babel/core@7.26.0) + '@babel/plugin-transform-arrow-functions': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-async-generator-functions': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-async-to-generator': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-block-scoped-functions': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-block-scoping': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-class-properties': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-class-static-block': 7.26.0(@babel/core@7.26.0) + '@babel/plugin-transform-classes': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-computed-properties': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-destructuring': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-dotall-regex': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-duplicate-keys': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-duplicate-named-capturing-groups-regex': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-dynamic-import': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-exponentiation-operator': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-export-namespace-from': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-for-of': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-function-name': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-json-strings': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-literals': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-logical-assignment-operators': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-member-expression-literals': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-modules-amd': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-modules-commonjs': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-modules-systemjs': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-modules-umd': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-named-capturing-groups-regex': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-new-target': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-nullish-coalescing-operator': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-numeric-separator': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-object-rest-spread': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-object-super': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-optional-catch-binding': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-optional-chaining': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-parameters': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-private-methods': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-private-property-in-object': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-property-literals': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-regenerator': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-regexp-modifiers': 7.26.0(@babel/core@7.26.0) + '@babel/plugin-transform-reserved-words': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-shorthand-properties': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-spread': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-sticky-regex': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-template-literals': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-typeof-symbol': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-unicode-escapes': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-unicode-property-regex': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-unicode-regex': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-unicode-sets-regex': 7.25.9(@babel/core@7.26.0) + '@babel/preset-modules': 0.1.6-no-external-plugins(@babel/core@7.26.0) + babel-plugin-polyfill-corejs2: 0.4.11(@babel/core@7.26.0) + babel-plugin-polyfill-corejs3: 0.10.6(@babel/core@7.26.0) + babel-plugin-polyfill-regenerator: 0.6.2(@babel/core@7.26.0) + core-js-compat: 3.39.0 semver: 6.3.1 transitivePeerDependencies: - supports-color dev: false - /@babel/preset-flow@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-7yn6hl8RIv+KNk6iIrGZ+D06VhVY35wLVf23Cz/mMu1zOr7u4MMP4j0nZ9tLf8+4ZFpnib8cFYgB/oYg9hfswA==} + /@babel/preset-flow@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-EASHsAhE+SSlEzJ4bzfusnXSHiU+JfAYzj+jbw2vgQKgq5HrUr8qs+vgtiEL5dOH6sEweI+PNt2D7AqrDSHyqQ==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-validator-option': 7.23.5 - '@babel/plugin-transform-flow-strip-types': 7.23.3(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-validator-option': 7.25.9 + '@babel/plugin-transform-flow-strip-types': 7.25.9(@babel/core@7.26.0) dev: false - /@babel/preset-modules@0.1.6-no-external-plugins(@babel/core@7.24.7): + /@babel/preset-modules@0.1.6-no-external-plugins(@babel/core@7.26.0): resolution: {integrity: sha512-HrcgcIESLm9aIR842yhJ5RWan/gebQUJ6E/E5+rf0y9o6oj7w0Br+sWuL6kEQ/o/AdfvR1Je9jG18/gnpwjEyA==} peerDependencies: '@babel/core': ^7.0.0-0 || ^8.0.0-0 <8.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-plugin-utils': 7.24.7 - '@babel/types': 7.24.7 + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/types': 7.26.0 esutils: 2.0.3 dev: false - /@babel/preset-typescript@7.23.3(@babel/core@7.23.7): - resolution: {integrity: sha512-17oIGVlqz6CchO9RFYn5U6ZpWRZIngayYCtrPRSgANSwC2V1Jb+iP74nVxzzXJte8b8BYxrL1yY96xfhTBrNNQ==} + /@babel/preset-typescript@7.26.0(@babel/core@7.26.0): + resolution: {integrity: sha512-NMk1IGZ5I/oHhoXEElcm+xUnL/szL6xflkFZmoEU9xj1qSJXpiS7rsspYo92B4DRCDvZn2erT5LdsCeXAKNCkg==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@babel/helper-plugin-utils': 7.22.5 - '@babel/helper-validator-option': 7.23.5 - '@babel/plugin-syntax-jsx': 7.23.3(@babel/core@7.23.7) - '@babel/plugin-transform-modules-commonjs': 7.23.3(@babel/core@7.23.7) - '@babel/plugin-transform-typescript': 7.23.6(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@babel/helper-plugin-utils': 7.25.9 + '@babel/helper-validator-option': 7.25.9 + '@babel/plugin-syntax-jsx': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-modules-commonjs': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-typescript': 7.25.9(@babel/core@7.26.0) + transitivePeerDependencies: + - supports-color dev: false - /@babel/register@7.23.7(@babel/core@7.23.7): - resolution: {integrity: sha512-EjJeB6+kvpk+Y5DAkEAmbOBEFkh9OASx0huoEkqYTFxAZHzOAX2Oh5uwAUuL2rUddqfM0SA+KPXV2TbzoZ2kvQ==} + /@babel/register@7.25.9(@babel/core@7.26.0): + resolution: {integrity: sha512-8D43jXtGsYmEeDvm4MWHYUpWf8iiXgWYx3fW7E7Wb7Oe6FWqJPl5K6TuFW0dOwNZzEE5rjlaSJYH9JjrUKJszA==} engines: {node: '>=6.9.0'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 clone-deep: 4.0.1 find-cache-dir: 2.1.0 make-dir: 2.1.0 @@ -2010,81 +1701,40 @@ packages: source-map-support: 0.5.21 dev: false - /@babel/regjsgen@0.8.0: - resolution: {integrity: sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA==} - dev: false - - /@babel/runtime@7.23.8: - resolution: {integrity: sha512-Y7KbAP984rn1VGMbGqKmBLio9V7y5Je9GvU4rQPCPinCyNfUcToxIXl06d59URp/F3LwinvODxab5N/G6qggkw==} + /@babel/runtime@7.26.0: + resolution: {integrity: sha512-FDSOghenHTiToteC/QRlv2q3DhPZ/oOXTBoirfWNx1Cx3TMVcGWQtMMmQcSvb/JjpNeGzx8Pq/b4fKEJuWm1sw==} engines: {node: '>=6.9.0'} dependencies: regenerator-runtime: 0.14.1 - /@babel/template@7.22.15: - resolution: {integrity: sha512-QPErUVm4uyJa60rkI73qneDacvdvzxshT3kksGqlGWYdOTIUOwJ7RDUL8sGqslY1uXWSL6xMFKEXDS3ox2uF0w==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/code-frame': 7.23.5 - '@babel/parser': 7.23.6 - '@babel/types': 7.23.6 - - /@babel/template@7.24.7: - resolution: {integrity: sha512-jYqfPrU9JTF0PmPy1tLYHW4Mp4KlgxJD9l2nP9fD6yT/ICi554DmrWBAEYpIelzjHf1msDP3PxJIRt/nFNfBig==} + /@babel/template@7.25.9: + resolution: {integrity: sha512-9DGttpmPvIxBb/2uwpVo3dqJ+O6RooAFOS+lB+xDqoE2PVCE8nfoHMdZLpfCQRLwvohzXISPZcgxt80xLfsuwg==} engines: {node: '>=6.9.0'} dependencies: - '@babel/code-frame': 7.24.7 - '@babel/parser': 7.24.7 - '@babel/types': 7.24.7 + '@babel/code-frame': 7.26.2 + '@babel/parser': 7.26.2 + '@babel/types': 7.26.0 - /@babel/traverse@7.23.7: - resolution: {integrity: sha512-tY3mM8rH9jM0YHFGyfC0/xf+SB5eKUu7HPj7/k3fpi9dAlsMc5YbQvDi0Sh2QTPXqMhyaAtzAr807TIyfQrmyg==} + /@babel/traverse@7.25.9: + resolution: {integrity: sha512-ZCuvfwOwlz/bawvAuvcj8rrithP2/N55Tzz342AkTvq4qaWbGfmCk/tKhNaV2cthijKrPAA8SRJV5WWe7IBMJw==} engines: {node: '>=6.9.0'} dependencies: - '@babel/code-frame': 7.23.5 - '@babel/generator': 7.23.6 - '@babel/helper-environment-visitor': 7.22.20 - '@babel/helper-function-name': 7.23.0 - '@babel/helper-hoist-variables': 7.22.5 - '@babel/helper-split-export-declaration': 7.22.6 - '@babel/parser': 7.23.6 - '@babel/types': 7.23.6 - debug: 4.3.4(supports-color@8.1.1) - globals: 11.12.0 - transitivePeerDependencies: - - supports-color - - /@babel/traverse@7.24.7: - resolution: {integrity: sha512-yb65Ed5S/QAcewNPh0nZczy9JdYXkkAbIsEo+P7BE7yO3txAY30Y/oPa3QkQ5It3xVG2kpKMg9MsdxZaO31uKA==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/code-frame': 7.24.7 - '@babel/generator': 7.24.7 - '@babel/helper-environment-visitor': 7.24.7 - '@babel/helper-function-name': 7.24.7 - '@babel/helper-hoist-variables': 7.24.7 - '@babel/helper-split-export-declaration': 7.24.7 - '@babel/parser': 7.24.7 - '@babel/types': 7.24.7 - debug: 4.3.4(supports-color@8.1.1) + '@babel/code-frame': 7.26.2 + '@babel/generator': 7.26.2 + '@babel/parser': 7.26.2 + '@babel/template': 7.25.9 + '@babel/types': 7.26.0 + debug: 4.3.7(supports-color@8.1.1) globals: 11.12.0 transitivePeerDependencies: - supports-color - /@babel/types@7.23.6: - resolution: {integrity: sha512-+uarb83brBzPKN38NX1MkB6vb6+mwvR6amUulqAE7ccQw1pEl+bCia9TbdG1lsnFP7lZySvUn37CHyXQdfTwzg==} - engines: {node: '>=6.9.0'} - dependencies: - '@babel/helper-string-parser': 7.23.4 - '@babel/helper-validator-identifier': 7.22.20 - to-fast-properties: 2.0.0 - - /@babel/types@7.24.7: - resolution: {integrity: sha512-XEFXSlxiG5td2EJRe8vOmRbaXVgfcBlszKujvVmWIK/UpywWljQCfzAv3RQCGujWQ1RD4YYWEAqDXfuJiy8f5Q==} + /@babel/types@7.26.0: + resolution: {integrity: sha512-Z/yiTPj+lDVnF7lWeKCIJzaIkI0vYO87dMpZ4bg4TDrFe4XXLFWL1TbXU27gBP3QccxV9mZICCrnjnYlJjXHOA==} engines: {node: '>=6.9.0'} dependencies: - '@babel/helper-string-parser': 7.24.7 - '@babel/helper-validator-identifier': 7.24.7 - to-fast-properties: 2.0.0 + '@babel/helper-string-parser': 7.25.9 + '@babel/helper-validator-identifier': 7.25.9 /@braintree/sanitize-url@6.0.4: resolution: {integrity: sha512-s3jaWicZd0pkP0jf5ysyHUI/RE7MHos6qlToFcGWXVp+ykHOy77OUMrfbgJ9it2C5bow7OIQwYYaHjk9XlBQ2A==} @@ -2525,10 +2175,10 @@ packages: engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} dependencies: ajv: 6.12.6 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) espree: 9.6.1 globals: 13.24.0 - ignore: 5.3.0 + ignore: 5.3.2 import-fresh: 3.3.0 js-yaml: 4.1.0 minimatch: 3.1.2 @@ -2537,111 +2187,111 @@ packages: - supports-color dev: true - /@fluentui/date-time-utilities@8.5.16: - resolution: {integrity: sha512-l+mLfJ2VhdHjBpELLLPDaWgT7GMLynm2aqR7SttbEb6Jh7hc/7ck1MWm93RTb3gYVHYai8SENqimNcvIxHt/zg==} + /@fluentui/date-time-utilities@8.6.9: + resolution: {integrity: sha512-dgOlVm4nXBWDLqijmvn4iAtyv1hVpQZjN6p0So74BW+7ASUTkQGe3lf8PHV/OjBiXfZa4qwONvmTQBGCheNU0w==} dependencies: - '@fluentui/set-version': 8.2.14 - tslib: 2.6.2 + '@fluentui/set-version': 8.2.23 + tslib: 2.8.1 dev: true - /@fluentui/dom-utilities@2.2.14: - resolution: {integrity: sha512-+4DVm5sNfJh+l8fM+7ylpOkGNZkNr4X1z1uKQPzRJ1PRhlnvc6vLpWNNicGwpjTbgufSrVtGKXwP5sf++r81lg==} + /@fluentui/dom-utilities@2.3.9: + resolution: {integrity: sha512-8PPzv31VXnyMvZrzK7iSGPRx8piJjas0xV+qaNQ1tzAXHuTaLXPeADJK/gEDH1XA/e9Vaakb3lPUpRVa8tal+w==} dependencies: - '@fluentui/set-version': 8.2.14 - tslib: 2.6.2 + '@fluentui/set-version': 8.2.23 + tslib: 2.8.1 dev: true - /@fluentui/font-icons-mdl2@8.5.31(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-jioHZ9XUfR9vUT5XnxdCrJ+hoC9TpYim+4YdtlUE/euI8kdW1tDZ5zqlSNk1GLDR34n03R09yWj5gVDCcMJbyQ==} + /@fluentui/font-icons-mdl2@8.5.55(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-nboUBzP8q05C2NstMgEBSGBVHlgjwIjtttX7RQzsmXRr6C5w/DstImp7Gg/L1GnJUNXhy0pcGuV4V+kyR+f8xA==} dependencies: - '@fluentui/set-version': 8.2.14 - '@fluentui/style-utilities': 8.10.2(@types/react@17.0.3)(react@17.0.2) - '@fluentui/utilities': 8.13.24(@types/react@17.0.3)(react@17.0.2) - tslib: 2.6.2 + '@fluentui/set-version': 8.2.23 + '@fluentui/style-utilities': 8.11.4(@types/react@17.0.3)(react@17.0.2) + '@fluentui/utilities': 8.15.19(@types/react@17.0.3)(react@17.0.2) + tslib: 2.8.1 transitivePeerDependencies: - '@types/react' - react dev: true - /@fluentui/foundation-legacy@8.2.51(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-z/jrp1imV66/D2MGpN/55LGk/Istymk5tN+XUFHDENDi+9zyb2MgSxFshp774DJIrg3vVlyuS8oo+dBuTM3UbQ==} + /@fluentui/foundation-legacy@8.4.21(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-8lqf61wGi7EHtH3o/UaFSsFO7CnhIz316TMoGtLgBwkmLXzKAC+vS+jCf6+nU+bHKF7/d1Z+B54ZE/dH0Rtsrw==} peerDependencies: '@types/react': '>=16.8.0 <19.0.0' react: '>=16.8.0 <19.0.0' dependencies: - '@fluentui/merge-styles': 8.5.15 - '@fluentui/set-version': 8.2.14 - '@fluentui/style-utilities': 8.10.2(@types/react@17.0.3)(react@17.0.2) - '@fluentui/utilities': 8.13.24(@types/react@17.0.3)(react@17.0.2) + '@fluentui/merge-styles': 8.6.13 + '@fluentui/set-version': 8.2.23 + '@fluentui/style-utilities': 8.11.4(@types/react@17.0.3)(react@17.0.2) + '@fluentui/utilities': 8.15.19(@types/react@17.0.3)(react@17.0.2) '@types/react': 17.0.3 react: 17.0.2 - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /@fluentui/keyboard-key@0.4.14: - resolution: {integrity: sha512-XzZHcyFEM20H23h3i15UpkHi2AhRBriXPGAHq0Jm98TKFppXehedjjEFuUsh+CyU5JKBhDalWp8TAQ1ArpNzow==} + /@fluentui/keyboard-key@0.4.23: + resolution: {integrity: sha512-9GXeyUqNJUdg5JiQUZeGPiKnRzMRi9YEUn1l9zq6X/imYdMhxHrxpVZS12129cBfgvPyxt9ceJpywSfmLWqlKA==} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /@fluentui/merge-styles@8.5.15: - resolution: {integrity: sha512-4CdKwo4k1Un2QLulpSVIz/KMgLNBMgin4NPyapmKDMVuO1OOxJUqfocubRGNO5x9mKgAMMYwBKGO9i0uxMMpJw==} + /@fluentui/merge-styles@8.6.13: + resolution: {integrity: sha512-IWgvi2CC+mcQ7/YlCvRjsmHL2+PUz7q+Pa2Rqk3a+QHN0V1uBvgIbKk5y/Y/awwDXy1yJHiqMCcDHjBNmS1d4A==} dependencies: - '@fluentui/set-version': 8.2.14 - tslib: 2.6.2 + '@fluentui/set-version': 8.2.23 + tslib: 2.8.1 dev: true - /@fluentui/react-focus@8.8.39(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-7PnI+3e37jxt0PlWykNfbCbPdnKroJY+olOxZDHkXfI/ANr8lm4YuyLAYNAtyapfnkf+FBoO6vxU51P8hNk7tQ==} + /@fluentui/react-focus@8.9.18(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-IuRE7XmbLkdPvJH5O9kKy2vzdNb8MRLzwkJpPhDCtDWFJSeZmGaCb8IDhaEmiK1dGFkser6AxWttKL/Qt14CxA==} peerDependencies: '@types/react': '>=16.8.0 <19.0.0' react: '>=16.8.0 <19.0.0' dependencies: - '@fluentui/keyboard-key': 0.4.14 - '@fluentui/merge-styles': 8.5.15 - '@fluentui/set-version': 8.2.14 - '@fluentui/style-utilities': 8.10.2(@types/react@17.0.3)(react@17.0.2) - '@fluentui/utilities': 8.13.24(@types/react@17.0.3)(react@17.0.2) + '@fluentui/keyboard-key': 0.4.23 + '@fluentui/merge-styles': 8.6.13 + '@fluentui/set-version': 8.2.23 + '@fluentui/style-utilities': 8.11.4(@types/react@17.0.3)(react@17.0.2) + '@fluentui/utilities': 8.15.19(@types/react@17.0.3)(react@17.0.2) '@types/react': 17.0.3 react: 17.0.2 - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /@fluentui/react-hooks@8.6.36(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-kI0Z4Q4xHUs4SOmmI5n5OH5fPckqMSCovTRpiuxzCO2TNzLmfC861+nqf4Ygw/ChqNm2gWNZZfUADfnNAEsq+Q==} + /@fluentui/react-hooks@8.8.16(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-PQ1BeOp+99mdO0g7j6QLtChfXG1LxXeHG0q5CtUeD1OUGR+vUDK84h60sw7e7qU9sSmvPmHO7jn69Lg3CS+DXw==} peerDependencies: '@types/react': '>=16.8.0 <19.0.0' react: '>=16.8.0 <19.0.0' dependencies: - '@fluentui/react-window-provider': 2.2.18(@types/react@17.0.3)(react@17.0.2) - '@fluentui/set-version': 8.2.14 - '@fluentui/utilities': 8.13.24(@types/react@17.0.3)(react@17.0.2) + '@fluentui/react-window-provider': 2.2.28(@types/react@17.0.3)(react@17.0.2) + '@fluentui/set-version': 8.2.23 + '@fluentui/utilities': 8.15.19(@types/react@17.0.3)(react@17.0.2) '@types/react': 17.0.3 react: 17.0.2 - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /@fluentui/react-portal-compat-context@9.0.11(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-ubvW/ej0O+Pago9GH3mPaxzUgsNnBoqvghNamWjyKvZIViyaXUG6+sgcAl721R+qGAFac+A20akI5qDJz/xtdg==} + /@fluentui/react-portal-compat-context@9.0.12(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-5AVXWX9GnbvwnJZYUb4LSIF7BsI/N8oTI6+7Yn0w6B3yaWykA8Menlz757X5tgVBjouEj4Eom+AoVvA7u8gPDA==} peerDependencies: '@types/react': '>=16.14.0 <19.0.0' react: '>=16.14.0 <19.0.0' dependencies: - '@swc/helpers': 0.5.3 + '@swc/helpers': 0.5.13 '@types/react': 17.0.3 react: 17.0.2 dev: true - /@fluentui/react-window-provider@2.2.18(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-nBKqxd0P8NmIR0qzFvka1urE2LVbUm6cse1I1T7TcOVNYa5jDf5BrO06+JRZfwbn00IJqOnIVoP0qONqceypWQ==} + /@fluentui/react-window-provider@2.2.28(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-YdZ74HTaoDwlvLDzoBST80/17ExIl93tLJpTxnqK5jlJOAUVQ+mxLPF2HQEJq+SZr5IMXHsQ56w/KaZVRn72YA==} peerDependencies: '@types/react': '>=16.8.0 <19.0.0' react: '>=16.8.0 <19.0.0' dependencies: - '@fluentui/set-version': 8.2.14 + '@fluentui/set-version': 8.2.23 '@types/react': 17.0.3 react: 17.0.2 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /@fluentui/react@8.106.1(@types/react-dom@17.0.2)(@types/react@17.0.3)(react-dom@17.0.2)(react@17.0.2): @@ -2652,92 +2302,93 @@ packages: react: '>=16.8.0 <19.0.0' react-dom: '>=16.8.0 <19.0.0' dependencies: - '@fluentui/date-time-utilities': 8.5.16 - '@fluentui/font-icons-mdl2': 8.5.31(@types/react@17.0.3)(react@17.0.2) - '@fluentui/foundation-legacy': 8.2.51(@types/react@17.0.3)(react@17.0.2) - '@fluentui/merge-styles': 8.5.15 - '@fluentui/react-focus': 8.8.39(@types/react@17.0.3)(react@17.0.2) - '@fluentui/react-hooks': 8.6.36(@types/react@17.0.3)(react@17.0.2) - '@fluentui/react-portal-compat-context': 9.0.11(@types/react@17.0.3)(react@17.0.2) - '@fluentui/react-window-provider': 2.2.18(@types/react@17.0.3)(react@17.0.2) - '@fluentui/set-version': 8.2.14 - '@fluentui/style-utilities': 8.10.2(@types/react@17.0.3)(react@17.0.2) - '@fluentui/theme': 2.6.41(@types/react@17.0.3)(react@17.0.2) - '@fluentui/utilities': 8.13.24(@types/react@17.0.3)(react@17.0.2) + '@fluentui/date-time-utilities': 8.6.9 + '@fluentui/font-icons-mdl2': 8.5.55(@types/react@17.0.3)(react@17.0.2) + '@fluentui/foundation-legacy': 8.4.21(@types/react@17.0.3)(react@17.0.2) + '@fluentui/merge-styles': 8.6.13 + '@fluentui/react-focus': 8.9.18(@types/react@17.0.3)(react@17.0.2) + '@fluentui/react-hooks': 8.8.16(@types/react@17.0.3)(react@17.0.2) + '@fluentui/react-portal-compat-context': 9.0.12(@types/react@17.0.3)(react@17.0.2) + '@fluentui/react-window-provider': 2.2.28(@types/react@17.0.3)(react@17.0.2) + '@fluentui/set-version': 8.2.23 + '@fluentui/style-utilities': 8.11.4(@types/react@17.0.3)(react@17.0.2) + '@fluentui/theme': 2.6.63(@types/react@17.0.3)(react@17.0.2) + '@fluentui/utilities': 8.15.19(@types/react@17.0.3)(react@17.0.2) '@microsoft/load-themed-styles': 1.10.295 '@types/react': 17.0.3 '@types/react-dom': 17.0.2 react: 17.0.2 react-dom: 17.0.2(react@17.0.2) - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /@fluentui/set-version@8.2.14: - resolution: {integrity: sha512-f/QWJnSeyfAjGAqq57yjMb6a5ejPlwfzdExPmzFBuEOuupi8hHbV8Yno12XJcTW4I0KXEQGw+PUaM1aOf/j7jw==} + /@fluentui/set-version@8.2.23: + resolution: {integrity: sha512-VPXaBsiaa3Xn/AY40nLU9bvDQ62lpMVnFzFTlQ8CbpdwrjxNlRxDUY5vRToNzp1+Zu5gD/+CgsXqIZGcry5L5w==} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /@fluentui/style-utilities@8.10.2(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-ocELtMb/85nBa3rSfiAIwYx6TydN+3rQqv1P0H/L7etYNNtxOfS86JSWfn8zAsHMejbwUKJ1ZsIKs47c598XGQ==} + /@fluentui/style-utilities@8.11.4(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-qJGlwX1FiDemPwCuzqYkmjfDNi0JQMum47FNB5dEtGz65/C2MSqLsZChcSpYwQEGCgY+L0qI1EwgbquTFxJqSw==} dependencies: - '@fluentui/merge-styles': 8.5.15 - '@fluentui/set-version': 8.2.14 - '@fluentui/theme': 2.6.41(@types/react@17.0.3)(react@17.0.2) - '@fluentui/utilities': 8.13.24(@types/react@17.0.3)(react@17.0.2) + '@fluentui/merge-styles': 8.6.13 + '@fluentui/set-version': 8.2.23 + '@fluentui/theme': 2.6.63(@types/react@17.0.3)(react@17.0.2) + '@fluentui/utilities': 8.15.19(@types/react@17.0.3)(react@17.0.2) '@microsoft/load-themed-styles': 1.10.295 - tslib: 2.6.2 + tslib: 2.8.1 transitivePeerDependencies: - '@types/react' - react dev: true - /@fluentui/theme@2.6.41(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-h9RguEzqzJ0+59ys5Kkp7JtsjhDUxBLmQunu5rpHp5Mp788OtEjI/n1a9FIcOAL/priPSQwXN7RbuDpeP7+aSw==} + /@fluentui/theme@2.6.63(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-BZ+YG4Vqb+ulhmZzDv8yZFuYo2kHp1m2cttBZLkc+61FnrwCaDBmJxwg65gXoF7wwXKh2qJIcJueSLMmvVyAOQ==} peerDependencies: '@types/react': '>=16.8.0 <19.0.0' react: '>=16.8.0 <19.0.0' dependencies: - '@fluentui/merge-styles': 8.5.15 - '@fluentui/set-version': 8.2.14 - '@fluentui/utilities': 8.13.24(@types/react@17.0.3)(react@17.0.2) + '@fluentui/merge-styles': 8.6.13 + '@fluentui/set-version': 8.2.23 + '@fluentui/utilities': 8.15.19(@types/react@17.0.3)(react@17.0.2) '@types/react': 17.0.3 react: 17.0.2 - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /@fluentui/utilities@8.13.24(@types/react@17.0.3)(react@17.0.2): - resolution: {integrity: sha512-/jo6hWCzTGCx06l2baAMwsjjBZ/dyMouls53uNaQLUGUUhUwXh/DcDDXMqLRJB3MaH9zvgfvRw61iKmm2s9fIA==} + /@fluentui/utilities@8.15.19(@types/react@17.0.3)(react@17.0.2): + resolution: {integrity: sha512-20WoYz0wW7pkmur+7qxTwRfvkdAnHfylLdCYSm91WLupb0cwQ1wWZWIuyo+e0cjcvem1T9TC1+NjWs0kavTWBg==} peerDependencies: '@types/react': '>=16.8.0 <19.0.0' react: '>=16.8.0 <19.0.0' dependencies: - '@fluentui/dom-utilities': 2.2.14 - '@fluentui/merge-styles': 8.5.15 - '@fluentui/set-version': 8.2.14 + '@fluentui/dom-utilities': 2.3.9 + '@fluentui/merge-styles': 8.6.13 + '@fluentui/react-window-provider': 2.2.28(@types/react@17.0.3)(react@17.0.2) + '@fluentui/set-version': 8.2.23 '@types/react': 17.0.3 react: 17.0.2 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /@formatjs/ecma402-abstract@1.6.3: resolution: {integrity: sha512-7ijswObmYXabVy5GvcpKG29jbyJ9rGtFdRBdmdQvoDmMo0PwlOl/L08GtrjA4YWLAZ0j2owb2YrRLGNAvLBk+Q==} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: true /@formatjs/intl-displaynames@4.0.11: resolution: {integrity: sha512-e3917+HmXStxb2fNP3sOr3R1DMALdWrUteBb3nerA2AKa12mXwmL0lDavrdltwZWqF7/Egh8fF/esB0Z/fqOgQ==} dependencies: '@formatjs/ecma402-abstract': 1.6.3 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /@formatjs/intl-listformat@5.0.12: resolution: {integrity: sha512-xWAndG73lqJ1+ar6SljCpM9nUsi2YoZfKi45F2YZRSxtUx4JbWYkhpbroOwxjCQ8ppZFoPc2mlLZjhPZiTyG7g==} dependencies: '@formatjs/ecma402-abstract': 1.6.3 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /@formatjs/intl@1.8.4(typescript@4.7.4): @@ -2754,7 +2405,7 @@ packages: fast-memoize: 2.5.2 intl-messageformat: 9.5.3 intl-messageformat-parser: 6.4.3 - tslib: 2.6.2 + tslib: 2.8.1 typescript: 4.7.4 dev: true @@ -2765,9 +2416,10 @@ packages: /@humanwhocodes/config-array@0.6.0: resolution: {integrity: sha512-JQlEKbcgEUjBFhLIF4iqM7u/9lwgHRBcpHrmUNCALK0Q3amXN6lxdoXLnF0sm11E9VqTmBALR87IlUg1bZ8A9A==} engines: {node: '>=10.10.0'} + deprecated: Use @eslint/config-array instead dependencies: '@humanwhocodes/object-schema': 1.2.1 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) minimatch: 3.1.2 transitivePeerDependencies: - supports-color @@ -2775,6 +2427,7 @@ packages: /@humanwhocodes/object-schema@1.2.1: resolution: {integrity: sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA==} + deprecated: Use @eslint/object-schema instead dev: true /@istanbuljs/load-nyc-config@1.1.0: @@ -2803,78 +2456,66 @@ packages: engines: {node: '>=8'} dev: true - /@jridgewell/gen-mapping@0.3.3: - resolution: {integrity: sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==} - engines: {node: '>=6.0.0'} - dependencies: - '@jridgewell/set-array': 1.1.2 - '@jridgewell/sourcemap-codec': 1.4.15 - '@jridgewell/trace-mapping': 0.3.25 - /@jridgewell/gen-mapping@0.3.5: resolution: {integrity: sha512-IzL8ZoEDIBRWEzlCcRhOaCupYyN5gdIK+Q6fbFdPDg6HqX6jpkItn7DFIpW9LQzXG6Df9sA7+OKnq0qlz/GaQg==} engines: {node: '>=6.0.0'} dependencies: '@jridgewell/set-array': 1.2.1 - '@jridgewell/sourcemap-codec': 1.4.15 + '@jridgewell/sourcemap-codec': 1.5.0 '@jridgewell/trace-mapping': 0.3.25 - /@jridgewell/resolve-uri@3.1.1: - resolution: {integrity: sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA==} - engines: {node: '>=6.0.0'} - - /@jridgewell/set-array@1.1.2: - resolution: {integrity: sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==} + /@jridgewell/resolve-uri@3.1.2: + resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} engines: {node: '>=6.0.0'} /@jridgewell/set-array@1.2.1: resolution: {integrity: sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==} engines: {node: '>=6.0.0'} - /@jridgewell/sourcemap-codec@1.4.15: - resolution: {integrity: sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==} + /@jridgewell/sourcemap-codec@1.5.0: + resolution: {integrity: sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==} /@jridgewell/trace-mapping@0.3.25: resolution: {integrity: sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==} dependencies: - '@jridgewell/resolve-uri': 3.1.1 - '@jridgewell/sourcemap-codec': 1.4.15 + '@jridgewell/resolve-uri': 3.1.2 + '@jridgewell/sourcemap-codec': 1.5.0 /@jridgewell/trace-mapping@0.3.9: resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==} dependencies: - '@jridgewell/resolve-uri': 3.1.1 - '@jridgewell/sourcemap-codec': 1.4.15 + '@jridgewell/resolve-uri': 3.1.2 + '@jridgewell/sourcemap-codec': 1.5.0 dev: true - /@microsoft/1ds-core-js@3.2.15(tslib@2.6.2): - resolution: {integrity: sha512-w/35jS80jVl+YBbL69BHg6iTHuIkmmnwSuy8LhfBHm8QDTQny2C73GdwUN8c00BqSClM1ldl2w2bQWW1aMJLTg==} + /@microsoft/1ds-core-js@3.2.18(tslib@2.8.1): + resolution: {integrity: sha512-ytlFv3dfb8OGqvbZP8tSIlNvn3QNYxdsF0k6ikRMWSr6CmBxBi1sliaxc2Q5KuYOuaeWkd8WRm25Rx/UtHcyMg==} dependencies: - '@microsoft/applicationinsights-core-js': 2.8.16(tslib@2.6.2) + '@microsoft/applicationinsights-core-js': 2.8.18(tslib@2.8.1) '@microsoft/applicationinsights-shims': 2.0.2 '@microsoft/dynamicproto-js': 1.1.11 transitivePeerDependencies: - tslib dev: false - /@microsoft/1ds-post-js@3.2.15(tslib@2.6.2): - resolution: {integrity: sha512-SZQdaiLpoPelTFC0G1EVZXnuQxzqPdY3F6tcBHfnmQv+h8aJR3HAIiy65xI+p7u9m9LdV+8Mx5buE0s6NfXnQA==} + /@microsoft/1ds-post-js@3.2.18(tslib@2.8.1): + resolution: {integrity: sha512-Tzjcja4SMyws3UP58kD2edFPNb7BJtx5uCgwf/PWXwDyfbUY1/crsTQdEyR98wy/vorvLDZdQlcL++VMChfYnQ==} dependencies: - '@microsoft/1ds-core-js': 3.2.15(tslib@2.6.2) + '@microsoft/1ds-core-js': 3.2.18(tslib@2.8.1) '@microsoft/applicationinsights-shims': 2.0.2 '@microsoft/dynamicproto-js': 1.1.11 transitivePeerDependencies: - tslib dev: false - /@microsoft/applicationinsights-core-js@2.8.16(tslib@2.6.2): - resolution: {integrity: sha512-pO5rR6UuiPymiHFj8XxNXhQgBSTvyHWygf+gdEVDh0xpUXYFO99bZe0Ux0D0HqYqVkJrRfXzL1Ocru6+S0x53Q==} + /@microsoft/applicationinsights-core-js@2.8.18(tslib@2.8.1): + resolution: {integrity: sha512-yPHRZFLpnEO0uSgFPM1BLMRRwjoten9YBbn4pJRbCT4PigLnj748knmWsMwXIdcehtkRTYz78kPYa/LWP7nvmA==} peerDependencies: tslib: '*' dependencies: '@microsoft/applicationinsights-shims': 2.0.2 '@microsoft/dynamicproto-js': 1.1.11 - tslib: 2.6.2 + tslib: 2.8.1 dev: false /@microsoft/applicationinsights-shims@2.0.2: @@ -2887,14 +2528,14 @@ packages: '@microsoft/dev-tunnels-contracts': 1.1.9 '@microsoft/dev-tunnels-management': 1.1.9 '@microsoft/dev-tunnels-ssh': 3.11.36 - '@microsoft/dev-tunnels-ssh-tcp': 3.11.36 + '@microsoft/dev-tunnels-ssh-tcp': 3.12.5 await-semaphore: 0.1.3 buffer: 5.7.1 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) es5-ext: 0.10.53 uuid: 3.4.0 vscode-jsonrpc: 4.0.0 - websocket: 1.0.34 + websocket: 1.0.35 transitivePeerDependencies: - supports-color dev: false @@ -2903,7 +2544,7 @@ packages: resolution: {integrity: sha512-OayhehwI+CnO0Wr53e29ZJZWGsNA5yVG7r54qmZSLc5HxA5Cozk4hP7EbYDCXkxh4NbQoT1dhTzC8bkRo+wWXw==} dependencies: buffer: 5.7.1 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) vscode-jsonrpc: 4.0.0 transitivePeerDependencies: - supports-color @@ -2913,27 +2554,38 @@ packages: resolution: {integrity: sha512-wGuFEzvRiWZmDxQMGKEjOKhEIVnLiG6vRUuM9Hwqxpe/kbiyA2WiUyEVpniNPaaw8gDHTf9zJHnPNNj0JiL5mA==} dependencies: '@microsoft/dev-tunnels-contracts': 1.1.9 - axios: 1.7.5(debug@4.3.4) + axios: 1.7.5(debug@4.3.7) buffer: 5.7.1 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) vscode-jsonrpc: 4.0.0 transitivePeerDependencies: - supports-color dev: false - /@microsoft/dev-tunnels-ssh-tcp@3.11.36: - resolution: {integrity: sha512-TAxraYXguA0y3M3MueeLma/dyoyvelyITSHVbHUrnOkgbYobs45LyQHuOzD42F57iJuP9DzpjC45RG+mKW3a/g==} + /@microsoft/dev-tunnels-ssh-tcp@3.12.5: + resolution: {integrity: sha512-/3kaDJpWPq+bRJJqiI3cqJsLfk8yddJ0+d3KmjIlcwF9wQewGp+rgTTdv29gl9dTm/cAhJh655Qh+vBHfrquZw==} dependencies: - '@microsoft/dev-tunnels-ssh': 3.11.36 + '@microsoft/dev-tunnels-ssh': 3.12.5 + transitivePeerDependencies: + - supports-color + dev: false + + /@microsoft/dev-tunnels-ssh@3.11.36: + resolution: {integrity: sha512-j7SlGaavPRs1Aho9a0JFRjL9N1V6UFo1Q2BUq6cpu+CnlWexmjvZmjeZyNQqwnnnEEAAGc5Vkz74cIQ8JHpvSA==} + dependencies: + buffer: 5.7.1 + debug: 4.3.7(supports-color@8.1.1) + diffie-hellman: 5.0.3 + vscode-jsonrpc: 4.0.0 transitivePeerDependencies: - supports-color dev: false - /@microsoft/dev-tunnels-ssh@3.11.36: - resolution: {integrity: sha512-j7SlGaavPRs1Aho9a0JFRjL9N1V6UFo1Q2BUq6cpu+CnlWexmjvZmjeZyNQqwnnnEEAAGc5Vkz74cIQ8JHpvSA==} + /@microsoft/dev-tunnels-ssh@3.12.5: + resolution: {integrity: sha512-elDcBd4yBOfjCmmISv0cC/SeTmuF4Pj1Y5+aBVXuvg2xdfl/sF7gIPgYbiFpPxU8P6zyN+JlxWbwZkRABjlxaA==} dependencies: buffer: 5.7.1 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) diffie-hellman: 5.0.3 vscode-jsonrpc: 4.0.0 transitivePeerDependencies: @@ -2944,14 +2596,14 @@ packages: resolution: {integrity: sha512-gNw9z9LbqLV+WadZ6/MMrWwO3e0LuoUH1wve/1iPsBNbgqeVCiB0EZFNNj2lysxS2gkqoF9hmyVaG3MoM1BkxA==} dev: false - /@microsoft/fast-element@1.12.0: - resolution: {integrity: sha512-gQutuDHPKNxUEcQ4pypZT4Wmrbapus+P9s3bR/SEOLsMbNqNoXigGImITygI5zhb+aA5rzflM6O8YWkmRbGkPA==} + /@microsoft/fast-element@1.14.0: + resolution: {integrity: sha512-zXvuSOzvsu8zDTy9eby8ix8VqLop2rwKRgp++ZN2kTCsoB3+QJVoaGD2T/Cyso2ViZQFXNpiNCVKfnmxBvmWkQ==} dev: false - /@microsoft/fast-foundation@2.49.5: - resolution: {integrity: sha512-3PpG1BNmZ5kUM1goYU3SsxjsM2H7Rk0ZmpDJ7mnRhWDgKiM5SzJ02KvALRUqDrJQoeDnkW0Q2Q+r9SkEd68Gpg==} + /@microsoft/fast-foundation@2.50.0: + resolution: {integrity: sha512-8mFYG88Xea1jZf2TI9Lm/jzZ6RWR8x29r24mGuLojNYqIR2Bl8+hnswoV6laApKdCbGMPKnsAL/O68Q0sRxeVg==} dependencies: - '@microsoft/fast-element': 1.12.0 + '@microsoft/fast-element': 1.14.0 '@microsoft/fast-web-utilities': 5.4.1 tabbable: 5.3.3 tslib: 1.14.1 @@ -2962,8 +2614,8 @@ packages: peerDependencies: react: '>=16.9.0' dependencies: - '@microsoft/fast-element': 1.12.0 - '@microsoft/fast-foundation': 2.49.5 + '@microsoft/fast-element': 1.14.0 + '@microsoft/fast-foundation': 2.50.0 react: 17.0.2 dev: false @@ -2977,14 +2629,14 @@ packages: resolution: {integrity: sha512-W+IzEBw8a6LOOfRJM02dTT7BDZijxm+Z7lhtOAz1+y9vQm1Kdz9jlAO+qCEKsfxtUOmKilW8DIRqFw2aUgKeGg==} dev: true - /@microsoft/teams-manifest@0.1.4: - resolution: {integrity: sha512-VVFnItrOi2MS7seQC/EkFGyqJNkR2jRASTeSaUhyJ+pdnrUszYPRqyOwBzFw4HmXBmlnOD1WTfRgwdeav/KpgA==} + /@microsoft/teams-manifest@0.1.6: + resolution: {integrity: sha512-5/M0WvhU14tefAYJQwo5Edx/jqJBou11u+8SOE1CkaJTpxSQPdq/PI3Ea4mWQj+0Ab3/MGbcgjmriPKuzTb0KQ==} dependencies: '@types/fs-extra': 11.0.4 '@types/node-fetch': 2.6.11 - ajv: 8.12.0 - ajv-draft-04: 1.0.0(ajv@8.12.0) - ajv-formats: 3.0.1(ajv@8.12.0) + ajv: 8.17.1 + ajv-draft-04: 1.0.0(ajv@8.17.1) + ajv-formats: 3.0.1(ajv@8.17.1) fs-extra: 9.1.0 node-fetch: 2.7.0 transitivePeerDependencies: @@ -3020,7 +2672,7 @@ packages: engines: {node: '>= 8'} dependencies: '@nodelib/fs.scandir': 2.1.5 - fastq: 1.16.0 + fastq: 1.17.1 dev: true /@npmcli/fs@2.1.2: @@ -3028,7 +2680,7 @@ packages: engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} dependencies: '@gar/promisify': 1.1.3 - semver: 7.5.4 + semver: 7.5.2 dev: true /@npmcli/move-file@2.0.1: @@ -3046,8 +2698,8 @@ packages: json-parse-even-better-errors: 2.3.1 dev: false - /@rollup/pluginutils@5.1.0: - resolution: {integrity: sha512-XTIWOPPcpvyKI6L1NHo0lFlCyznUEyPmPY1mc3KpPVDYulHSTvyeLNVW00QTLIAFNhR3kYnJTQHeGqU4M3n09g==} + /@rollup/pluginutils@5.1.3: + resolution: {integrity: sha512-Pnsb6f32CD2W3uCaLZIzDmeFyQ2b8UWMFI7xtwUezpcGBDVDW6y9XgAWIlARiGAo6eNF5FK5aQTr0LFyNyqq5A==} engines: {node: '>=14.0.0'} peerDependencies: rollup: ^1.20.0||^2.0.0||^3.0.0||^4.0.0 @@ -3055,133 +2707,149 @@ packages: rollup: optional: true dependencies: - '@types/estree': 1.0.5 + '@types/estree': 1.0.6 estree-walker: 2.0.2 - picomatch: 2.3.1 + picomatch: 4.0.2 dev: true - /@rollup/rollup-android-arm-eabi@4.18.0: - resolution: {integrity: sha512-Tya6xypR10giZV1XzxmH5wr25VcZSncG0pZIjfePT0OVBvqNEurzValetGNarVrGiq66EBVAFn15iYX4w6FKgQ==} + /@rollup/rollup-android-arm-eabi@4.24.4: + resolution: {integrity: sha512-jfUJrFct/hTA0XDM5p/htWKoNNTbDLY0KRwEt6pyOA6k2fmk0WVwl65PdUdJZgzGEHWx+49LilkcSaumQRyNQw==} cpu: [arm] os: [android] requiresBuild: true dev: true optional: true - /@rollup/rollup-android-arm64@4.18.0: - resolution: {integrity: sha512-avCea0RAP03lTsDhEyfy+hpfr85KfyTctMADqHVhLAF3MlIkq83CP8UfAHUssgXTYd+6er6PaAhx/QGv4L1EiA==} + /@rollup/rollup-android-arm64@4.24.4: + resolution: {integrity: sha512-j4nrEO6nHU1nZUuCfRKoCcvh7PIywQPUCBa2UsootTHvTHIoIu2BzueInGJhhvQO/2FTRdNYpf63xsgEqH9IhA==} cpu: [arm64] os: [android] requiresBuild: true dev: true optional: true - /@rollup/rollup-darwin-arm64@4.18.0: - resolution: {integrity: sha512-IWfdwU7KDSm07Ty0PuA/W2JYoZ4iTj3TUQjkVsO/6U+4I1jN5lcR71ZEvRh52sDOERdnNhhHU57UITXz5jC1/w==} + /@rollup/rollup-darwin-arm64@4.24.4: + resolution: {integrity: sha512-GmU/QgGtBTeraKyldC7cDVVvAJEOr3dFLKneez/n7BvX57UdhOqDsVwzU7UOnYA7AAOt+Xb26lk79PldDHgMIQ==} cpu: [arm64] os: [darwin] requiresBuild: true dev: true optional: true - /@rollup/rollup-darwin-x64@4.18.0: - resolution: {integrity: sha512-n2LMsUz7Ynu7DoQrSQkBf8iNrjOGyPLrdSg802vk6XT3FtsgX6JbE8IHRvposskFm9SNxzkLYGSq9QdpLYpRNA==} + /@rollup/rollup-darwin-x64@4.24.4: + resolution: {integrity: sha512-N6oDBiZCBKlwYcsEPXGDE4g9RoxZLK6vT98M8111cW7VsVJFpNEqvJeIPfsCzbf0XEakPslh72X0gnlMi4Ddgg==} cpu: [x64] os: [darwin] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-arm-gnueabihf@4.18.0: - resolution: {integrity: sha512-C/zbRYRXFjWvz9Z4haRxcTdnkPt1BtCkz+7RtBSuNmKzMzp3ZxdM28Mpccn6pt28/UWUCTXa+b0Mx1k3g6NOMA==} + /@rollup/rollup-freebsd-arm64@4.24.4: + resolution: {integrity: sha512-py5oNShCCjCyjWXCZNrRGRpjWsF0ic8f4ieBNra5buQz0O/U6mMXCpC1LvrHuhJsNPgRt36tSYMidGzZiJF6mw==} + cpu: [arm64] + os: [freebsd] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-freebsd-x64@4.24.4: + resolution: {integrity: sha512-L7VVVW9FCnTTp4i7KrmHeDsDvjB4++KOBENYtNYAiYl96jeBThFfhP6HVxL74v4SiZEVDH/1ILscR5U9S4ms4g==} + cpu: [x64] + os: [freebsd] + requiresBuild: true + dev: true + optional: true + + /@rollup/rollup-linux-arm-gnueabihf@4.24.4: + resolution: {integrity: sha512-10ICosOwYChROdQoQo589N5idQIisxjaFE/PAnX2i0Zr84mY0k9zul1ArH0rnJ/fpgiqfu13TFZR5A5YJLOYZA==} cpu: [arm] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-arm-musleabihf@4.18.0: - resolution: {integrity: sha512-l3m9ewPgjQSXrUMHg93vt0hYCGnrMOcUpTz6FLtbwljo2HluS4zTXFy2571YQbisTnfTKPZ01u/ukJdQTLGh9A==} + /@rollup/rollup-linux-arm-musleabihf@4.24.4: + resolution: {integrity: sha512-ySAfWs69LYC7QhRDZNKqNhz2UKN8LDfbKSMAEtoEI0jitwfAG2iZwVqGACJT+kfYvvz3/JgsLlcBP+WWoKCLcw==} cpu: [arm] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-arm64-gnu@4.18.0: - resolution: {integrity: sha512-rJ5D47d8WD7J+7STKdCUAgmQk49xuFrRi9pZkWoRD1UeSMakbcepWXPF8ycChBoAqs1pb2wzvbY6Q33WmN2ftw==} + /@rollup/rollup-linux-arm64-gnu@4.24.4: + resolution: {integrity: sha512-uHYJ0HNOI6pGEeZ/5mgm5arNVTI0nLlmrbdph+pGXpC9tFHFDQmDMOEqkmUObRfosJqpU8RliYoGz06qSdtcjg==} cpu: [arm64] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-arm64-musl@4.18.0: - resolution: {integrity: sha512-be6Yx37b24ZwxQ+wOQXXLZqpq4jTckJhtGlWGZs68TgdKXJgw54lUUoFYrg6Zs/kjzAQwEwYbp8JxZVzZLRepQ==} + /@rollup/rollup-linux-arm64-musl@4.24.4: + resolution: {integrity: sha512-38yiWLemQf7aLHDgTg85fh3hW9stJ0Muk7+s6tIkSUOMmi4Xbv5pH/5Bofnsb6spIwD5FJiR+jg71f0CH5OzoA==} cpu: [arm64] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-powerpc64le-gnu@4.18.0: - resolution: {integrity: sha512-hNVMQK+qrA9Todu9+wqrXOHxFiD5YmdEi3paj6vP02Kx1hjd2LLYR2eaN7DsEshg09+9uzWi2W18MJDlG0cxJA==} + /@rollup/rollup-linux-powerpc64le-gnu@4.24.4: + resolution: {integrity: sha512-q73XUPnkwt9ZNF2xRS4fvneSuaHw2BXuV5rI4cw0fWYVIWIBeDZX7c7FWhFQPNTnE24172K30I+dViWRVD9TwA==} cpu: [ppc64] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-riscv64-gnu@4.18.0: - resolution: {integrity: sha512-ROCM7i+m1NfdrsmvwSzoxp9HFtmKGHEqu5NNDiZWQtXLA8S5HBCkVvKAxJ8U+CVctHwV2Gb5VUaK7UAkzhDjlg==} + /@rollup/rollup-linux-riscv64-gnu@4.24.4: + resolution: {integrity: sha512-Aie/TbmQi6UXokJqDZdmTJuZBCU3QBDA8oTKRGtd4ABi/nHgXICulfg1KI6n9/koDsiDbvHAiQO3YAUNa/7BCw==} cpu: [riscv64] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-s390x-gnu@4.18.0: - resolution: {integrity: sha512-0UyyRHyDN42QL+NbqevXIIUnKA47A+45WyasO+y2bGJ1mhQrfrtXUpTxCOrfxCR4esV3/RLYyucGVPiUsO8xjg==} + /@rollup/rollup-linux-s390x-gnu@4.24.4: + resolution: {integrity: sha512-P8MPErVO/y8ohWSP9JY7lLQ8+YMHfTI4bAdtCi3pC2hTeqFJco2jYspzOzTUB8hwUWIIu1xwOrJE11nP+0JFAQ==} cpu: [s390x] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-x64-gnu@4.18.0: - resolution: {integrity: sha512-xuglR2rBVHA5UsI8h8UbX4VJ470PtGCf5Vpswh7p2ukaqBGFTnsfzxUBetoWBWymHMxbIG0Cmx7Y9qDZzr648w==} + /@rollup/rollup-linux-x64-gnu@4.24.4: + resolution: {integrity: sha512-K03TljaaoPK5FOyNMZAAEmhlyO49LaE4qCsr0lYHUKyb6QacTNF9pnfPpXnFlFD3TXuFbFbz7tJ51FujUXkXYA==} cpu: [x64] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-linux-x64-musl@4.18.0: - resolution: {integrity: sha512-LKaqQL9osY/ir2geuLVvRRs+utWUNilzdE90TpyoX0eNqPzWjRm14oMEE+YLve4k/NAqCdPkGYDaDF5Sw+xBfg==} + /@rollup/rollup-linux-x64-musl@4.24.4: + resolution: {integrity: sha512-VJYl4xSl/wqG2D5xTYncVWW+26ICV4wubwN9Gs5NrqhJtayikwCXzPL8GDsLnaLU3WwhQ8W02IinYSFJfyo34Q==} cpu: [x64] os: [linux] requiresBuild: true dev: true optional: true - /@rollup/rollup-win32-arm64-msvc@4.18.0: - resolution: {integrity: sha512-7J6TkZQFGo9qBKH0pk2cEVSRhJbL6MtfWxth7Y5YmZs57Pi+4x6c2dStAUvaQkHQLnEQv1jzBUW43GvZW8OFqA==} + /@rollup/rollup-win32-arm64-msvc@4.24.4: + resolution: {integrity: sha512-ku2GvtPwQfCqoPFIJCqZ8o7bJcj+Y54cZSr43hHca6jLwAiCbZdBUOrqE6y29QFajNAzzpIOwsckaTFmN6/8TA==} cpu: [arm64] os: [win32] requiresBuild: true dev: true optional: true - /@rollup/rollup-win32-ia32-msvc@4.18.0: - resolution: {integrity: sha512-Txjh+IxBPbkUB9+SXZMpv+b/vnTEtFyfWZgJ6iyCmt2tdx0OF5WhFowLmnh8ENGNpfUlUZkdI//4IEmhwPieNg==} + /@rollup/rollup-win32-ia32-msvc@4.24.4: + resolution: {integrity: sha512-V3nCe+eTt/W6UYNr/wGvO1fLpHUrnlirlypZfKCT1fG6hWfqhPgQV/K/mRBXBpxc0eKLIF18pIOFVPh0mqHjlg==} cpu: [ia32] os: [win32] requiresBuild: true dev: true optional: true - /@rollup/rollup-win32-x64-msvc@4.18.0: - resolution: {integrity: sha512-UOo5FdvOL0+eIVTgS4tIdbW+TtnBLWg1YBCcU2KWM7nuNwRz9bksDX1bekJJCpu25N1DVWaCwnT39dVQxzqS8g==} + /@rollup/rollup-win32-x64-msvc@4.24.4: + resolution: {integrity: sha512-LTw1Dfd0mBIEqUVCxbvTE/LLo+9ZxVC9k99v1v4ahg9Aak6FpqOfNu5kRkeTAn0wphoC4JU7No1/rL+bBCEwhg==} cpu: [x64] os: [win32] requiresBuild: true @@ -3212,108 +2880,108 @@ packages: dependencies: '@sinonjs/commons': 1.8.6 lodash.get: 4.4.2 - type-detect: 4.0.8 + type-detect: 4.1.0 dev: true - /@sinonjs/text-encoding@0.7.2: - resolution: {integrity: sha512-sXXKG+uL9IrKqViTtao2Ws6dy0znu9sOaP1di/jKGW1M6VssO8vlpXCQcpZ+jisQ1tTFAC5Jo/EOzFbggBagFQ==} + /@sinonjs/text-encoding@0.7.3: + resolution: {integrity: sha512-DE427ROAphMQzU4ENbliGYrBSYPXF+TtLg9S8vzeA+OF4ZKzoDdzfL8sxuMUGS/lgRhM6j1URSk9ghf7Xo1tyA==} dev: true - /@svgr/babel-plugin-add-jsx-attribute@8.0.0(@babel/core@7.23.7): + /@svgr/babel-plugin-add-jsx-attribute@8.0.0(@babel/core@7.26.0): resolution: {integrity: sha512-b9MIk7yhdS1pMCZM8VeNfUlSKVRhsHZNMl5O9SfaX0l0t5wjdgu4IDzGB8bpnGBBOjGST3rRFVsaaEtI4W6f7g==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-plugin-remove-jsx-attribute@8.0.0(@babel/core@7.23.7): + /@svgr/babel-plugin-remove-jsx-attribute@8.0.0(@babel/core@7.26.0): resolution: {integrity: sha512-BcCkm/STipKvbCl6b7QFrMh/vx00vIP63k2eM66MfHJzPr6O2U0jYEViXkHJWqXqQYjdeA9cuCl5KWmlwjDvbA==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-plugin-remove-jsx-empty-expression@8.0.0(@babel/core@7.23.7): + /@svgr/babel-plugin-remove-jsx-empty-expression@8.0.0(@babel/core@7.26.0): resolution: {integrity: sha512-5BcGCBfBxB5+XSDSWnhTThfI9jcO5f0Ai2V24gZpG+wXF14BzwxxdDb4g6trdOux0rhibGs385BeFMSmxtS3uA==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-plugin-replace-jsx-attribute-value@8.0.0(@babel/core@7.23.7): + /@svgr/babel-plugin-replace-jsx-attribute-value@8.0.0(@babel/core@7.26.0): resolution: {integrity: sha512-KVQ+PtIjb1BuYT3ht8M5KbzWBhdAjjUPdlMtpuw/VjT8coTrItWX6Qafl9+ji831JaJcu6PJNKCV0bp01lBNzQ==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-plugin-svg-dynamic-title@8.0.0(@babel/core@7.23.7): + /@svgr/babel-plugin-svg-dynamic-title@8.0.0(@babel/core@7.26.0): resolution: {integrity: sha512-omNiKqwjNmOQJ2v6ge4SErBbkooV2aAWwaPFs2vUY7p7GhVkzRkJ00kILXQvRhA6miHnNpXv7MRnnSjdRjK8og==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-plugin-svg-em-dimensions@8.0.0(@babel/core@7.23.7): + /@svgr/babel-plugin-svg-em-dimensions@8.0.0(@babel/core@7.26.0): resolution: {integrity: sha512-mURHYnu6Iw3UBTbhGwE/vsngtCIbHE43xCRK7kCw4t01xyGqb2Pd+WXekRRoFOBIY29ZoOhUCTEweDMdrjfi9g==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-plugin-transform-react-native-svg@8.1.0(@babel/core@7.23.7): + /@svgr/babel-plugin-transform-react-native-svg@8.1.0(@babel/core@7.26.0): resolution: {integrity: sha512-Tx8T58CHo+7nwJ+EhUwx3LfdNSG9R2OKfaIXXs5soiy5HtgoAEkDay9LIimLOcG8dJQH1wPZp/cnAv6S9CrR1Q==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-plugin-transform-svg-component@8.0.0(@babel/core@7.23.7): + /@svgr/babel-plugin-transform-svg-component@8.0.0(@babel/core@7.26.0): resolution: {integrity: sha512-DFx8xa3cZXTdb/k3kfPeaixecQLgKh5NVBMwD0AQxOzcZawK4oo1Jh9LbrcACUivsCA7TLG8eeWgrDXjTMhRmw==} engines: {node: '>=12'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: true - /@svgr/babel-preset@8.1.0(@babel/core@7.23.7): + /@svgr/babel-preset@8.1.0(@babel/core@7.26.0): resolution: {integrity: sha512-7EYDbHE7MxHpv4sxvnVPngw5fuR6pw79SkcrILHJ/iMpuKySNCl5W1qcwPEpU+LgyRXOaAFgH0KhwD18wwg6ug==} engines: {node: '>=14'} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 - '@svgr/babel-plugin-add-jsx-attribute': 8.0.0(@babel/core@7.23.7) - '@svgr/babel-plugin-remove-jsx-attribute': 8.0.0(@babel/core@7.23.7) - '@svgr/babel-plugin-remove-jsx-empty-expression': 8.0.0(@babel/core@7.23.7) - '@svgr/babel-plugin-replace-jsx-attribute-value': 8.0.0(@babel/core@7.23.7) - '@svgr/babel-plugin-svg-dynamic-title': 8.0.0(@babel/core@7.23.7) - '@svgr/babel-plugin-svg-em-dimensions': 8.0.0(@babel/core@7.23.7) - '@svgr/babel-plugin-transform-react-native-svg': 8.1.0(@babel/core@7.23.7) - '@svgr/babel-plugin-transform-svg-component': 8.0.0(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@svgr/babel-plugin-add-jsx-attribute': 8.0.0(@babel/core@7.26.0) + '@svgr/babel-plugin-remove-jsx-attribute': 8.0.0(@babel/core@7.26.0) + '@svgr/babel-plugin-remove-jsx-empty-expression': 8.0.0(@babel/core@7.26.0) + '@svgr/babel-plugin-replace-jsx-attribute-value': 8.0.0(@babel/core@7.26.0) + '@svgr/babel-plugin-svg-dynamic-title': 8.0.0(@babel/core@7.26.0) + '@svgr/babel-plugin-svg-em-dimensions': 8.0.0(@babel/core@7.26.0) + '@svgr/babel-plugin-transform-react-native-svg': 8.1.0(@babel/core@7.26.0) + '@svgr/babel-plugin-transform-svg-component': 8.0.0(@babel/core@7.26.0) dev: true /@svgr/core@8.1.0(typescript@4.7.4): resolution: {integrity: sha512-8QqtOQT5ACVlmsvKOJNEaWmRPmcojMOzCz4Hs2BGG/toAp/K38LcsMRyLp349glq5AzJbCEeimEoxaX6v/fLrA==} engines: {node: '>=14'} dependencies: - '@babel/core': 7.23.7 - '@svgr/babel-preset': 8.1.0(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@svgr/babel-preset': 8.1.0(@babel/core@7.26.0) camelcase: 6.3.0 cosmiconfig: 8.3.6(typescript@4.7.4) snake-case: 3.0.4 @@ -3326,7 +2994,7 @@ packages: resolution: {integrity: sha512-EbDKwO9GpfWP4jN9sGdYwPBU0kdomaPIL2Eu4YwmgP+sJeXT+L7bMwJUBnhzfH8Q2qMBqZ4fJwpCyYsAN3mt2Q==} engines: {node: '>=14'} dependencies: - '@babel/types': 7.23.6 + '@babel/types': 7.26.0 entities: 4.5.0 dev: true @@ -3336,8 +3004,8 @@ packages: peerDependencies: '@svgr/core': '*' dependencies: - '@babel/core': 7.23.7 - '@svgr/babel-preset': 8.1.0(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@svgr/babel-preset': 8.1.0(@babel/core@7.26.0) '@svgr/core': 8.1.0(typescript@4.7.4) '@svgr/hast-util-to-babel-ast': 8.0.0 svg-parser: 2.0.4 @@ -3345,15 +3013,16 @@ packages: - supports-color dev: true - /@swc/helpers@0.5.3: - resolution: {integrity: sha512-FaruWX6KdudYloq1AHD/4nU+UsMTdNE8CKyrseXWEcgjDAbvkwJg2QGPAnfIJLIWsjZOSPLOAykK6fuYp4vp4A==} + /@swc/helpers@0.5.13: + resolution: {integrity: sha512-UoKGxQ3r5kYI9dALKJapMmuK+1zWM/H17Z1+iwnNmzcJRnfFuevZs375TA5rW31pu4BS4NoSy1fRsexDXfWn5w==} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: true /@tootallnate/once@2.0.0: resolution: {integrity: sha512-XCuKFP5PS55gnMVu3dty8KPatLqUoy/ZYzDzAGCQ8JNFCkLXzmI7vNHCR+XpbZaMWQK/vQubr7PkYq8g470J/A==} engines: {node: '>= 10'} + dev: true /@trysound/sax@0.2.0: resolution: {integrity: sha512-L7z9BgrNEcYyUYtF+HaEfiS5ebkh9jXqbszz7pC0hRBPaatV0XjSD3+eHrpqFemQfgwiFF0QPIarnIihIDn7OA==} @@ -3379,8 +3048,8 @@ packages: /@types/babel__core@7.20.5: resolution: {integrity: sha512-qoQprZvz5wQFJwMDqeseRXWv3rqMvhgpbXFfVyWhbx9X47POIA6i/+dXefEmZKoAgOaTdaIgNSMqMIU61yRyzA==} dependencies: - '@babel/parser': 7.23.6 - '@babel/types': 7.23.6 + '@babel/parser': 7.26.2 + '@babel/types': 7.26.0 '@types/babel__generator': 7.6.8 '@types/babel__template': 7.4.4 '@types/babel__traverse': 7.20.6 @@ -3389,20 +3058,20 @@ packages: /@types/babel__generator@7.6.8: resolution: {integrity: sha512-ASsj+tpEDsEiFr1arWrlN6V3mdfjRMZt6LtK/Vp/kreFLnr5QH5+DhvD5nINYZXzwJvXeGq+05iUXcAzVrqWtw==} dependencies: - '@babel/types': 7.23.6 + '@babel/types': 7.26.0 dev: true /@types/babel__template@7.4.4: resolution: {integrity: sha512-h/NUaSyG5EyxBIp8YRxo4RMe2/qQgvyowRwVMzhYhBCONbW8PUsg4lkFMrhgZhUe5z3L3MiLDuvyJ/CaPa2A8A==} dependencies: - '@babel/parser': 7.23.6 - '@babel/types': 7.23.6 + '@babel/parser': 7.26.2 + '@babel/types': 7.26.0 dev: true /@types/babel__traverse@7.20.6: resolution: {integrity: sha512-r1bzfrm0tomOI8g1SzvCaQHo6Lcv6zu0EA+W2kHrt8dyrHQxGzBBL4kdkzIS+jBMV+EYcMAEAqXqYaLJq5rOZg==} dependencies: - '@babel/types': 7.23.6 + '@babel/types': 7.26.0 dev: true /@types/body-parser@1.19.5: @@ -3460,19 +3129,23 @@ packages: '@types/ms': 0.7.34 dev: true + /@types/detect-port@1.3.2: + resolution: {integrity: sha512-xxgAGA2SAU4111QefXPSp5eGbDm/hW6zhvYl9IeEPZEry9F4d66QAHm5qpUXjb6IsevZV/7emAEx5MhP6O192g==} + dev: false + /@types/ejs@3.1.5: resolution: {integrity: sha512-nv+GSx77ZtXiJzwKdsASqi+YQ5Z7vwHsTP0JY2SiQgjGckkBRKZnk8nIM+7oUZ1VCtuTz0+By4qVR7fqzp/Dfg==} dev: true - /@types/estree@1.0.5: - resolution: {integrity: sha512-/kYRxGDLWzHOB7q+wtSUQlFrtcdUccpfy+X+9iMBpHK8QLLhx2wIPYuS5DYtR9Wa/YlZAbIovy7qVdB1Aq6Lyw==} + /@types/estree@1.0.6: + resolution: {integrity: sha512-AYnb1nQyY49te+VRAVgmzfcgjYS91mY5P0TKUDCLEM+gNnA+3T6rWITXRLYCpahpqSQbN5cE+gHpnPyXjHWxcw==} dev: true - /@types/express-serve-static-core@4.17.41: - resolution: {integrity: sha512-OaJ7XLaelTgrvlZD8/aa0vvvxZdUmlCn6MtWeB7TkiKW70BQLc9XEPpDLPdbo52ZhXUCrznlWdCHWxJWtdyajA==} + /@types/express-serve-static-core@4.19.6: + resolution: {integrity: sha512-N4LZ2xG7DatVqhCZzOGb1Yi5lMbXSZcmdLDe9EzSndPV2HpWYWzRbaerl2n27irrm94EPpprqa8KpskPT085+A==} dependencies: '@types/node': 14.14.21 - '@types/qs': 6.9.11 + '@types/qs': 6.9.16 '@types/range-parser': 1.2.7 '@types/send': 0.17.4 dev: true @@ -3481,9 +3154,9 @@ packages: resolution: {integrity: sha512-TEbt+vaPFQ+xpxFLFssxUDXj5cWCxZJjIcB7Yg0k0GMHGtgtQgpvx/MUQUeAkNbA9AAGrwkAsoeItdTgS7FMyg==} dependencies: '@types/body-parser': 1.19.5 - '@types/express-serve-static-core': 4.17.41 - '@types/qs': 6.9.11 - '@types/serve-static': 1.15.5 + '@types/express-serve-static-core': 4.19.6 + '@types/qs': 6.9.16 + '@types/serve-static': 1.15.7 dev: true /@types/fs-extra@11.0.4: @@ -3498,10 +3171,10 @@ packages: '@types/node': 14.14.21 dev: true - /@types/hast@2.3.9: - resolution: {integrity: sha512-pTHyNlaMD/oKJmS+ZZUyFUcsZeBZpC0lmGquw98CqRVNgAdJZJeD7GoeLiT6Xbx5rU9VCjSt0RwEvDgzh4obFw==} + /@types/hast@2.3.10: + resolution: {integrity: sha512-McWspRw8xx8J9HurkVBfYj0xKoE25tOFlHGdx4MJ5xORQrMGZNqJhVQWaIbm6Oyla5kYOXtDiopzKRJzEOkwJw==} dependencies: - '@types/unist': 2.0.10 + '@types/unist': 2.0.11 dev: false /@types/history@4.7.11: @@ -3553,17 +3226,13 @@ packages: /@types/mdast@3.0.15: resolution: {integrity: sha512-LnwD+mUEfxWMa1QpDraczIn6k0Ee3SMicuYSSzS6ZYl2gKS09EClnJYGd8Du6rfc5r/GZEk5o1mRb8TaTj03sQ==} dependencies: - '@types/unist': 2.0.10 + '@types/unist': 2.0.11 dev: true /@types/mime@1.3.5: resolution: {integrity: sha512-/pyBZWSLD2n0dcHE3hq8s8ZvcETHtEuF+3E7XVt0Ig2nvsVQXdghHVcEkIWjy9A0wKfTn97a/PSDYohKIlnP/w==} dev: true - /@types/mime@3.0.4: - resolution: {integrity: sha512-iJt33IQnVRkqeqC7PzBHPTC6fDlRNRW8vjrgqtScAhrmMwe8c4Eo7+fUGTa+XdWrpEgpyKWMYmi2dIwMAYRzPw==} - dev: true - /@types/mocha@8.0.4: resolution: {integrity: sha512-M4BwiTJjHmLq6kjON7ZoI2JMlBvpY3BYSdiP6s/qCT3jb1s9/DeJF0JELpAxiVSIxXDzfNKe+r7yedMIoLbknQ==} dev: true @@ -3582,7 +3251,7 @@ packages: resolution: {integrity: sha512-24xFj9R5+rfQJLRyM56qh+wnVSYhyXC2tkoBndtY0U+vubqNsYXGjufB2nn8Q6gt0LrARwL6UBtMCSVCwl4B1g==} dependencies: '@types/node': 14.14.21 - form-data: 4.0.0 + form-data: 4.0.1 dev: false /@types/node@14.14.21: @@ -3592,12 +3261,12 @@ packages: resolution: {integrity: sha512-dISoDXWWQwUquiKsyZ4Ng+HX2KsPL7LyHKHQwgGFEA3IaKac4Obd+h2a/a6waisAoepJlBcx9paWqjA8/HVjCw==} dev: true - /@types/prop-types@15.7.11: - resolution: {integrity: sha512-ga8y9v9uyeiLdpKddhxYQkxNDrfvuPrlFb0N1qnZZByvcElJaXthF1UhvCh9TLWJBEHeNtdnbysW7Y6Uq8CVng==} + /@types/prop-types@15.7.13: + resolution: {integrity: sha512-hCZTSvwbzWGvhqxp/RqVqwU999pBf2vp7hzIjiYOsl8wqOmUxkQ6ddw1cV3l8811+kdUFus/q4d1Y3E3SyEifA==} dev: true - /@types/qs@6.9.11: - resolution: {integrity: sha512-oGk0gmhnEJK4Yyk+oI7EfXsLayXatCWPHary1MtcmbAifkobT9cM9yutG/hZKIseOU0MqbIwQ/u2nn/Gb+ltuQ==} + /@types/qs@6.9.16: + resolution: {integrity: sha512-7i+zxXdPD0T4cKDuxCUXJ4wHcsJLwENa6Z3dCu8cfCK743OGy5Nu1RmAGqDPsoTDINVEcdXKRvR/zre+P2Ku1A==} dev: true /@types/range-parser@1.2.7: @@ -3640,17 +3309,17 @@ packages: /@types/react@17.0.3: resolution: {integrity: sha512-wYOUxIgs2HZZ0ACNiIayItyluADNbONl7kt8lkLjVK8IitMH5QMyAh75Fwhmo37r1m7L2JaFj03sIfxBVDvRAg==} dependencies: - '@types/prop-types': 15.7.11 - '@types/scheduler': 0.16.8 + '@types/prop-types': 15.7.13 + '@types/scheduler': 0.23.0 csstype: 3.1.3 dev: true - /@types/scheduler@0.16.8: - resolution: {integrity: sha512-WZLiwShhwLRmeV6zH+GkbOFT6Z6VklCItrDioxUnv+u4Ll+8vKeFySoFyK/0ctcRpOmwAicELfmys1sDc/Rw+A==} + /@types/scheduler@0.23.0: + resolution: {integrity: sha512-YIoDCTH3Af6XM5VuwGG/QL/CJqga1Zm3NkU3HZ4ZHK2fRMPYP1VczsTUqtsf43PH/iJNVlPHAo2oWX7BSdB2Hw==} dev: true - /@types/semver@7.5.8: - resolution: {integrity: sha512-I8EUhyrgfLrcTkzV3TSsGyl1tSuPrEDzr0yd5m90UgNxQkyDXULk3b6MlQqTCpZpNtWe1K0hzclnZkTcLBe2UQ==} + /@types/semver@7.3.4: + resolution: {integrity: sha512-+nVsLKlcUCeMzD2ufHEYuJ9a2ovstb6Dp52A5VsoKxDXgvE051XgHI/33I1EymwkRGQkwnA0LkhnUzituGs4EQ==} dev: true /@types/send@0.17.4: @@ -3660,12 +3329,12 @@ packages: '@types/node': 14.14.21 dev: true - /@types/serve-static@1.15.5: - resolution: {integrity: sha512-PDRk21MnK70hja/YF8AHfC7yIsiQHn1rcXx7ijCFBX/k+XQJhQT/gw3xekXKJvx+5SXaMMS8oqQy09Mzvz2TuQ==} + /@types/serve-static@1.15.7: + resolution: {integrity: sha512-W8Ym+h8nhuRwaKPaDw34QUkwsGi6Rc4yYqvKFo5rm2FUEhCFbzVWrxXUxuKK8TASjWsysJY0nsmNCGhCOIsrOw==} dependencies: '@types/http-errors': 2.0.4 - '@types/mime': 3.0.4 '@types/node': 14.14.21 + '@types/send': 0.17.4 dev: true /@types/sinon-chai@3.2.12: @@ -3699,8 +3368,8 @@ packages: '@types/node': 14.14.21 dev: true - /@types/tmp@0.2.6: - resolution: {integrity: sha512-chhaNf2oKHlRkDGt+tiKE2Z5aJ6qalm7Z9rlLdBwmOiAAf09YQvvoLXjWK4HWPF1xU/fqvMgfNfpVoBscA/tKA==} + /@types/tmp@0.2.0: + resolution: {integrity: sha512-flgpHJjntpBAdJD43ShRosQvNC0ME97DCfGvZEDlAThQmnerRXrLbX6YgzRBQCZTthET9eAWFAMaYP0m0Y4HzQ==} dev: true /@types/ttf2eot@2.0.2: @@ -3721,8 +3390,8 @@ packages: '@types/node': 14.14.21 dev: true - /@types/unist@2.0.10: - resolution: {integrity: sha512-IfYcSBWE3hLpBg8+X2SEa8LVkJdJEkT2Ese2aaLs3ptGdVtABxndrMaxuFlQ1qdFf9Q5rDvDpxI3WwgvKFAsQA==} + /@types/unist@2.0.11: + resolution: {integrity: sha512-CmBKiL6NNo/OqgmMn95Fk9Whlp2mtvIv+KNpQKN2F4SjvrEesubTRWGYSg+BnWZOnlCaSTU1sMpsBOzgbYhnsA==} /@types/uuid@8.3.0: resolution: {integrity: sha512-eQ9qFW/fhfGJF8WKHGEHZEyVWfZxrT+6CLIJGBcZPfxUh/+BnEj+UCGYMlr9qZuX/2AltsvwrGqp0LhEW8D0zQ==} @@ -3750,12 +3419,12 @@ packages: '@typescript-eslint/experimental-utils': 5.0.0(eslint@8.1.0)(typescript@4.7.4) '@typescript-eslint/parser': 5.0.0(eslint@8.1.0)(typescript@4.7.4) '@typescript-eslint/scope-manager': 5.0.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) eslint: 8.1.0 functional-red-black-tree: 1.0.1 - ignore: 5.3.0 + ignore: 5.3.2 regexpp: 3.2.0 - semver: 7.5.4 + semver: 7.5.2 tsutils: 3.21.0(typescript@4.7.4) typescript: 4.7.4 transitivePeerDependencies: @@ -3793,7 +3462,7 @@ packages: '@typescript-eslint/scope-manager': 5.0.0 '@typescript-eslint/types': 5.0.0 '@typescript-eslint/typescript-estree': 5.0.0(typescript@4.7.4) - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) eslint: 8.1.0 typescript: 4.7.4 transitivePeerDependencies: @@ -3824,10 +3493,10 @@ packages: dependencies: '@typescript-eslint/types': 5.0.0 '@typescript-eslint/visitor-keys': 5.0.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) globby: 11.1.0 is-glob: 4.0.3 - semver: 7.5.4 + semver: 7.5.2 tsutils: 3.21.0(typescript@4.7.4) typescript: 4.7.4 transitivePeerDependencies: @@ -3846,18 +3515,18 @@ packages: resolution: {integrity: sha512-sL/cEvJWAnClXw0wHk85/2L0G6Sj8UB0Ctc1TEMbKSsmpRosqhwj9gWgFRZSrBr2f9tiXISwNhCPmlfqUqyb9Q==} dev: true - /@vitejs/plugin-react@4.3.1(vite@5.3.6): + /@vitejs/plugin-react@4.3.1(vite@5.4.0): resolution: {integrity: sha512-m/V2syj5CuVnaxcUJOQRel/Wr31FFXRFlnOoq1TVtkCxsY5veGMTEmpWHndrhB2U8ScHtCQB1e+4hWYExQc6Lg==} engines: {node: ^14.18.0 || >=16.0.0} peerDependencies: vite: ^4.2.0 || ^5.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/plugin-transform-react-jsx-self': 7.24.7(@babel/core@7.24.7) - '@babel/plugin-transform-react-jsx-source': 7.24.7(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/plugin-transform-react-jsx-self': 7.25.9(@babel/core@7.26.0) + '@babel/plugin-transform-react-jsx-source': 7.25.9(@babel/core@7.26.0) '@types/babel__core': 7.20.5 react-refresh: 0.14.2 - vite: 5.3.6(@types/node@14.14.21)(sass@1.77.6) + vite: 5.4.0(@types/node@14.14.21)(sass@1.77.6) transitivePeerDependencies: - supports-color dev: true @@ -3866,12 +3535,12 @@ packages: resolution: {integrity: sha512-VdgpnD75swH9hpXjd34VBgQ2w2quK63WljodlUcOoJDPKiV+rPjHrcUc2sjLCNKxhl6oKqmsZgwOWcDAY2GKKQ==} dev: true - /@vscode/extension-telemetry@0.6.2(tslib@2.6.2): + /@vscode/extension-telemetry@0.6.2(tslib@2.8.1): resolution: {integrity: sha512-yb/wxLuaaCRcBAZtDCjNYSisAXz3FWsSqAha5nhHcYxx2ZPdQdWuZqVXGKq0ZpHVndBWWtK6XqtpCN2/HB4S1w==} engines: {vscode: ^1.60.0} dependencies: - '@microsoft/1ds-core-js': 3.2.15(tslib@2.6.2) - '@microsoft/1ds-post-js': 3.2.15(tslib@2.6.2) + '@microsoft/1ds-core-js': 3.2.18(tslib@2.8.1) + '@microsoft/1ds-post-js': 3.2.18(tslib@2.8.1) transitivePeerDependencies: - tslib dev: false @@ -3881,8 +3550,8 @@ packages: peerDependencies: react: '>=16.9.0' dependencies: - '@microsoft/fast-element': 1.12.0 - '@microsoft/fast-foundation': 2.49.5 + '@microsoft/fast-element': 1.14.0 + '@microsoft/fast-foundation': 2.50.0 '@microsoft/fast-react-wrapper': 0.1.48(react@17.0.2) react: 17.0.2 dev: false @@ -3890,6 +3559,7 @@ packages: /@xmldom/xmldom@0.7.13: resolution: {integrity: sha512-lm2GW5PkosIzccsaZIz7tp8cPADSIlIHWDFTR1N0SzfinhhYgeIQjFMz4rYzanCScr3DqQLeomUDArp6MWKm+g==} engines: {node: '>=10.0.0'} + deprecated: this version is no longer supported, please update to at least 0.8.* dev: true /abbrev@1.1.1: @@ -3904,37 +3574,51 @@ packages: negotiator: 0.6.3 dev: false - /acorn-jsx@5.3.2(acorn@8.11.3): + /acorn-jsx@5.3.2(acorn@8.14.0): resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 dependencies: - acorn: 8.11.3 + acorn: 8.14.0 dev: true - /acorn-walk@8.3.3: - resolution: {integrity: sha512-MxXdReSRhGO7VlFe1bRG/oI7/mdLV9B9JJT0N8vZOhF7gFRR5l3M8W9G8JxmKV+JC5mGqJ0QvqfSOLsCPa4nUw==} + /acorn-walk@8.3.4: + resolution: {integrity: sha512-ueEepnujpqee2o5aIYnvHU6C0A42MNdsIDeqy5BydrkuC5R1ZuUFnm27EeFJGoEHJQgn3uleRvmTXaJgfXbt4g==} engines: {node: '>=0.4.0'} dependencies: - acorn: 8.11.3 + acorn: 8.14.0 dev: true - /acorn@8.11.3: - resolution: {integrity: sha512-Y9rRfJG5jcKOE0CLisYbojUjIrIEE7AGMzA/Sm4BslANhbS+cDMpgBdcPT91oJ7OuJ9hYJBx59RjbhxVnrF8Xg==} + /acorn@8.14.0: + resolution: {integrity: sha512-cl669nCJTZBsL97OF4kUQm5g5hC2uihk0NxY3WENAC0TYdILVkAyHymAntgxGkl7K+t0cXIrH5siy5S4XkFycA==} engines: {node: '>=0.4.0'} hasBin: true dev: true - /adm-zip@0.5.12: - resolution: {integrity: sha512-6TVU49mK6KZb4qG6xWaaM4C7sA/sgUMLy/JYMOzkcp3BvVLpW0fXDFQiIzAuxFCt/2+xD7fNIiPFAoLZPhVNLQ==} - engines: {node: '>=6.0'} + /address@1.2.2: + resolution: {integrity: sha512-4B/qKCfeE/ODUaAUpSwfzazo5x29WD4r3vXiWsB7I2mSDAihwEqKO+g8GELZUQSSAo5e1XTYh3ZVfLyxBc12nA==} + engines: {node: '>= 10.0.0'} + dev: false + + /adm-zip@0.5.16: + resolution: {integrity: sha512-TGw5yVi4saajsSEgz25grObGHEUaDrniwvA2qwSC060KfqGPdglhvPMA2lPIoxs3PQIItj2iag35fONcQqgUaQ==} + engines: {node: '>=12.0'} dev: false /agent-base@6.0.2: resolution: {integrity: sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==} engines: {node: '>= 6.0.0'} dependencies: - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) + transitivePeerDependencies: + - supports-color + dev: true + + /agent-base@7.1.1: + resolution: {integrity: sha512-H0TSyFNDMomMNJQBn8wFV5YC/2eJ+VXECwOadZJT554xP6cODZHPX3H9QMQECxvrgiSOP1pHjy1sMWQVYJOUOA==} + engines: {node: '>= 14'} + dependencies: + debug: 4.3.7(supports-color@8.1.1) transitivePeerDependencies: - supports-color @@ -3953,7 +3637,7 @@ packages: indent-string: 4.0.0 dev: true - /ajv-draft-04@1.0.0(ajv@8.12.0): + /ajv-draft-04@1.0.0(ajv@8.17.1): resolution: {integrity: sha512-mv00Te6nmYbRp5DCwclxtt7yV/joXJPGS7nM+97GdxvuttCOfgI3K4U25zboyeX0O+myI8ERluxQe5wljMmVIw==} peerDependencies: ajv: ^8.5.0 @@ -3961,10 +3645,10 @@ packages: ajv: optional: true dependencies: - ajv: 8.12.0 + ajv: 8.17.1 dev: false - /ajv-formats@3.0.1(ajv@8.12.0): + /ajv-formats@3.0.1(ajv@8.17.1): resolution: {integrity: sha512-8iUql50EUR+uUcdRQ3HDqa6EVyo3docL8g5WJ3FNcWmu62IbkGUue/pEyLBW8VGKKucTPgqeks4fIU1DA4yowQ==} peerDependencies: ajv: ^8.0.0 @@ -3972,7 +3656,7 @@ packages: ajv: optional: true dependencies: - ajv: 8.12.0 + ajv: 8.17.1 dev: false /ajv@6.12.6: @@ -3984,13 +3668,13 @@ packages: uri-js: 4.4.1 dev: true - /ajv@8.12.0: - resolution: {integrity: sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==} + /ajv@8.17.1: + resolution: {integrity: sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==} dependencies: fast-deep-equal: 3.1.3 + fast-uri: 3.0.3 json-schema-traverse: 1.0.0 require-from-string: 2.0.2 - uri-js: 4.4.1 dev: false /ansi-colors@4.1.1: @@ -4061,6 +3745,7 @@ packages: /are-we-there-yet@3.0.1: resolution: {integrity: sha512-QZW4EDmGwlYur0Yyf/b2uGucHQMa8aFUP7eu9ddR73vvhFyt4V0Vl3QHPcTNJ8l6qYOBdxgXdnBXQrHilfRQBg==} engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + deprecated: This package is no longer supported. dependencies: delegates: 1.0.0 readable-stream: 3.6.2 @@ -4095,25 +3780,27 @@ packages: engines: {node: '>=0.10.0'} dev: true - /array-buffer-byte-length@1.0.0: - resolution: {integrity: sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A==} + /array-buffer-byte-length@1.0.1: + resolution: {integrity: sha512-ahC5W1xgou+KTXix4sAO8Ki12Q+jf4i0+tmk3sC+zgcynshkHxzpXdImBehiUYKKKDwvfFiJl1tZt6ewscS1Mg==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - is-array-buffer: 3.0.2 + call-bind: 1.0.7 + is-array-buffer: 3.0.4 dev: true /array-flatten@1.1.1: resolution: {integrity: sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==} dev: false - /array-includes@3.1.7: - resolution: {integrity: sha512-dlcsNBIiWhPkHdOEEKnehA+RNUWDc4UqFtnIXU4uuYDPtA4LDkr7qip2p0VvFAEXNDr0yWZ9PJyIRiGjRLQzwQ==} + /array-includes@3.1.8: + resolution: {integrity: sha512-itaWrbYbqpGXkGhZPGUulwnhVf5Hpy1xiCFsGqyIGglbBxmG5vSjxQen3/WGOjPpNEv1RtBLKxbmVXm8HpJStQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 - get-intrinsic: 1.2.2 + es-abstract: 1.23.3 + es-object-atoms: 1.0.0 + get-intrinsic: 1.2.4 is-string: 1.0.7 dev: true @@ -4131,23 +3818,24 @@ packages: resolution: {integrity: sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-abstract: 1.23.3 es-shim-unscopables: 1.0.2 dev: true - /arraybuffer.prototype.slice@1.0.2: - resolution: {integrity: sha512-yMBKppFur/fbHu9/6USUe03bZ4knMYiwFBcyiaXB8Go0qNehwX6inYPzK9U0NeQvGxKthcmHcaR8P5MStSRBAw==} + /arraybuffer.prototype.slice@1.0.3: + resolution: {integrity: sha512-bMxMKAjg13EBSVscxTaYA4mRc5t1UAXa2kXiGTNfZ079HIWXEkKmkgFrh/nJqamaLSrXO5H4WFFkPEaLJWbs3A==} engines: {node: '>= 0.4'} dependencies: - array-buffer-byte-length: 1.0.0 - call-bind: 1.0.5 + array-buffer-byte-length: 1.0.1 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 - get-intrinsic: 1.2.2 - is-array-buffer: 3.0.2 - is-shared-array-buffer: 1.0.2 + es-abstract: 1.23.3 + es-errors: 1.3.0 + get-intrinsic: 1.2.4 + is-array-buffer: 3.0.4 + is-shared-array-buffer: 1.0.3 dev: true /asn1@0.2.6: @@ -4169,14 +3857,14 @@ packages: resolution: {integrity: sha512-O0yuUDnZeQDL+ncNGlJ78BiO4jnYI3bvMsD5prT0/nsgijG/LpNBIr63gTjVTNsiGkgQhiyCShTgxt8oXOrklA==} engines: {node: '>=4'} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: true /ast-types@0.15.2: resolution: {integrity: sha512-c27loCv9QkZinsa5ProX751khO9DJl/AcB5c2KNtA6NRvHKS0PgLfcftz72KVq504vB0Gku5s2kUZzDBvQWvHg==} engines: {node: '>=4'} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: false /astral-regex@2.0.0: @@ -4202,11 +3890,11 @@ packages: /async-mutex@0.3.1: resolution: {integrity: sha512-vRfQwcqBnJTLzVQo72Sf7KIUbcSUP5hNchx6udI1U6LuPQpfePgdjJzlCe76yFZ8pxlLjn9lwcl/Ya0TSOv0Tw==} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: false - /async@3.2.5: - resolution: {integrity: sha512-baNZyqaaLhyLVKm/DlvdW051MSgO6b8eVfIezl9E5PqWxFgzLm/wQntEW4zOytVburDEr0JlALEpdOFwvErLsg==} + /async@3.2.6: + resolution: {integrity: sha512-htCUDlxyyCLMgaM3xXg0C0LW2xqfuQ6p05pCEIsXuyQ+a1koYKTuBMzRNwmybfLgvJDMd0r1LTn4+E0Ti6C2AA==} dev: true /asynckit@0.4.0: @@ -4223,65 +3911,67 @@ packages: hasBin: true dev: true - /available-typed-arrays@1.0.5: - resolution: {integrity: sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==} + /available-typed-arrays@1.0.7: + resolution: {integrity: sha512-wvUjBtSGN7+7SjNpq/9M2Tg350UZD3q62IFZLbRAR1bSMlCo1ZaeW+BJ+D090e4hIIZLBcTDWe4Mh4jvUDajzQ==} engines: {node: '>= 0.4'} + dependencies: + possible-typed-array-names: 1.0.0 dev: true /await-semaphore@0.1.3: resolution: {integrity: sha512-d1W2aNSYcz/sxYO4pMGX9vq65qOTu0P800epMud+6cYYX0QcT7zyqcxec3VWzpgvdXo57UWmVbZpLMjX2m1I7Q==} dev: false - /axios@1.7.5(debug@4.3.4): + /axios@1.7.5(debug@4.3.7): resolution: {integrity: sha512-fZu86yCo+svH3uqJ/yTdQ0QHpQu5oL+/QE+QPSv6BZSkDAoky9vytxp7u5qk83OJFS3kEBcesWni9WTZAv3tSw==} dependencies: - follow-redirects: 1.15.6(debug@4.3.4) - form-data: 4.0.0 + follow-redirects: 1.15.9(debug@4.3.7) + form-data: 4.0.1 proxy-from-env: 1.1.0 transitivePeerDependencies: - debug dev: false - /babel-core@7.0.0-bridge.0(@babel/core@7.23.7): + /babel-core@7.0.0-bridge.0(@babel/core@7.26.0): resolution: {integrity: sha512-poPX9mZH/5CSanm50Q+1toVci6pv5KSRv/5TWCwtzQS5XEwn40BcCrgIeMFWP9CKKIniKXNxoIOnOq4VVlGXhg==} peerDependencies: '@babel/core': ^7.0.0-0 dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 dev: false - /babel-plugin-polyfill-corejs2@0.4.8(@babel/core@7.24.7): - resolution: {integrity: sha512-OtIuQfafSzpo/LhnJaykc0R/MMnuLSSVjVYy9mHArIZ9qTCSZ6TpWCuEKZYVoN//t8HqBNScHrOtCrIK5IaGLg==} + /babel-plugin-polyfill-corejs2@0.4.11(@babel/core@7.26.0): + resolution: {integrity: sha512-sMEJ27L0gRHShOh5G54uAAPaiCOygY/5ratXuiyb2G46FmlSpc9eFCzYVyDiPxfNbwzA7mYahmjQc5q+CZQ09Q==} peerDependencies: '@babel/core': ^7.4.0 || ^8.0.0-0 <8.0.0 dependencies: - '@babel/compat-data': 7.24.7 - '@babel/core': 7.24.7 - '@babel/helper-define-polyfill-provider': 0.5.0(@babel/core@7.24.7) + '@babel/compat-data': 7.26.2 + '@babel/core': 7.26.0 + '@babel/helper-define-polyfill-provider': 0.6.2(@babel/core@7.26.0) semver: 6.3.1 transitivePeerDependencies: - supports-color dev: false - /babel-plugin-polyfill-corejs3@0.8.7(@babel/core@7.24.7): - resolution: {integrity: sha512-KyDvZYxAzkC0Aj2dAPyDzi2Ym15e5JKZSK+maI7NAwSqofvuFglbSsxE7wUOvTg9oFVnHMzVzBKcqEb4PJgtOA==} + /babel-plugin-polyfill-corejs3@0.10.6(@babel/core@7.26.0): + resolution: {integrity: sha512-b37+KR2i/khY5sKmWNVQAnitvquQbNdWy6lJdsr0kmquCKEEUgMKK4SboVM3HtfnZilfjr4MMQ7vY58FVWDtIA==} peerDependencies: '@babel/core': ^7.4.0 || ^8.0.0-0 <8.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-define-polyfill-provider': 0.4.4(@babel/core@7.24.7) - core-js-compat: 3.35.1 + '@babel/core': 7.26.0 + '@babel/helper-define-polyfill-provider': 0.6.2(@babel/core@7.26.0) + core-js-compat: 3.39.0 transitivePeerDependencies: - supports-color dev: false - /babel-plugin-polyfill-regenerator@0.5.5(@babel/core@7.24.7): - resolution: {integrity: sha512-OJGYZlhLqBh2DDHeqAxWB1XIvr49CxiJ2gIt61/PU55CQK4Z58OzMqjDe1zwQdQk+rBYsRc+1rJmdajM3gimHg==} + /babel-plugin-polyfill-regenerator@0.6.2(@babel/core@7.26.0): + resolution: {integrity: sha512-2R25rQZWP63nGwaAswvDazbPXfrM3HwVoBXK6HcqeKrSrL/JqcC/rDcf95l4r7LXLyxDXc8uQDa064GubtCABg==} peerDependencies: '@babel/core': ^7.4.0 || ^8.0.0-0 <8.0.0 dependencies: - '@babel/core': 7.24.7 - '@babel/helper-define-polyfill-provider': 0.5.0(@babel/core@7.24.7) + '@babel/core': 7.26.0 + '@babel/helper-define-polyfill-provider': 0.6.2(@babel/core@7.26.0) transitivePeerDependencies: - supports-color dev: false @@ -4310,8 +4000,8 @@ packages: resolution: {integrity: sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==} dev: true - /binary-extensions@2.2.0: - resolution: {integrity: sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==} + /binary-extensions@2.3.0: + resolution: {integrity: sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==} engines: {node: '>=8'} dev: true @@ -4325,8 +4015,8 @@ packages: resolution: {integrity: sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA==} dev: false - /body-parser@1.20.2: - resolution: {integrity: sha512-ml9pReCu3M61kGlqoTm2umSXTlRTuGTx0bfYj+uIUKKYycG5NtSbeetV3faSU6R7ajOPw0g/J1PvK4qNy7s5bA==} + /body-parser@1.20.3: + resolution: {integrity: sha512-7rAxByjUMqQ3/bHJy7D6OGXvx/MMc4IqBn/X0fcM1QUcAItpZrBEYhWGem+tzXH90c+G01ypMcYJBO9Y30203g==} engines: {node: '>= 0.8', npm: 1.2.8000 || >= 1.4.16} dependencies: bytes: 3.1.2 @@ -4337,7 +4027,7 @@ packages: http-errors: 2.0.0 iconv-lite: 0.4.24 on-finished: 2.4.1 - qs: 6.11.0 + qs: 6.13.0 raw-body: 2.5.2 type-is: 1.6.18 unpipe: 1.0.0 @@ -4378,11 +4068,11 @@ packages: - supports-color dev: true - /braces@3.0.2: - resolution: {integrity: sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==} + /braces@3.0.3: + resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} engines: {node: '>=8'} dependencies: - fill-range: 7.0.1 + fill-range: 7.1.1 /brorand@1.1.0: resolution: {integrity: sha512-cKV8tMCEpQs4hK/ik71d6LrPOnpkpGBR0wzxqr68g2m/LB2GxVYQroAjMJZRVM1Y4BCjCKc3vAamxSzOY2RP+w==} @@ -4392,15 +4082,15 @@ packages: resolution: {integrity: sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw==} dev: true - /browserslist@4.22.2: - resolution: {integrity: sha512-0UgcrvQmBDvZHFGdYUehrCNIazki7/lUP3kkoi/r3YB2amZbFM9J43ZRkJTXBUZK4gmx56+Sqk9+Vs9mwZx9+A==} + /browserslist@4.24.2: + resolution: {integrity: sha512-ZIc+Q62revdMcqC6aChtW4jz3My3klmCO1fEmINZY/8J3EpBg5/A/D0AKmBveUh6pgoeycoMkVMko84tuYS+Gg==} engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} hasBin: true dependencies: - caniuse-lite: 1.0.30001579 - electron-to-chromium: 1.4.645 - node-releases: 2.0.14 - update-browserslist-db: 1.0.13(browserslist@4.22.2) + caniuse-lite: 1.0.30001677 + electron-to-chromium: 1.5.51 + node-releases: 2.0.18 + update-browserslist-db: 1.1.1(browserslist@4.24.2) /buffer-equal-constant-time@1.0.1: resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==} @@ -4429,7 +4119,7 @@ packages: engines: {node: '>=6.14.2'} requiresBuild: true dependencies: - node-gyp-build: 4.8.0 + node-gyp-build: 4.8.2 dev: false /bytes@3.1.2: @@ -4457,7 +4147,7 @@ packages: promise-inflight: 1.0.1 rimraf: 3.0.2 ssri: 9.0.1 - tar: 6.2.0 + tar: 6.2.1 unique-filename: 2.0.1 transitivePeerDependencies: - bluebird @@ -4488,12 +4178,15 @@ packages: write-file-atomic: 3.0.3 dev: true - /call-bind@1.0.5: - resolution: {integrity: sha512-C3nQxfFZxFRVoJoGKKI8y3MOEo129NQ+FgQ08iye+Mk4zNZZGdjfs06bVTr+DBSlA66Q2VEcMki/cUCP4SercQ==} + /call-bind@1.0.7: + resolution: {integrity: sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==} + engines: {node: '>= 0.4'} dependencies: + es-define-property: 1.0.0 + es-errors: 1.3.0 function-bind: 1.1.2 - get-intrinsic: 1.2.2 - set-function-length: 1.2.0 + get-intrinsic: 1.2.4 + set-function-length: 1.2.2 /callsites@3.1.0: resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} @@ -4510,8 +4203,8 @@ packages: engines: {node: '>=10'} dev: true - /caniuse-lite@1.0.30001579: - resolution: {integrity: sha512-u5AUVkixruKHJjw/pj9wISlcMpgFWzSrczLZbrqBSxukQixmg0SJ5sZTpvaFvxU0HoQKd4yoyAogyrAz9pzJnA==} + /caniuse-lite@1.0.30001677: + resolution: {integrity: sha512-fmfjsOlJUpMWu+mAAtZZZHz7UEwsUxIIvu1TJfO1HqFQvB/B+ii0xr9B5HpbZY/mC4XZ8SvjHJqtAY6pDPQEog==} /chai-as-promised@7.1.1(chai@4.2.0): resolution: {integrity: sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA==} @@ -4540,7 +4233,7 @@ packages: deep-eql: 3.0.1 get-func-name: 2.0.2 pathval: 1.1.1 - type-detect: 4.0.8 + type-detect: 4.1.0 dev: true /chalk@2.4.2: @@ -4596,17 +4289,21 @@ packages: domutils: 3.1.0 dev: true - /cheerio@1.0.0-rc.12: - resolution: {integrity: sha512-VqR8m68vM46BNnuZ5NtnGBKIE/DfN0cRIzg9n40EIq9NOv90ayxLBXA8fXC5gquFRGJSTRqBq25Jt2ECLR431Q==} - engines: {node: '>= 6'} + /cheerio@1.0.0: + resolution: {integrity: sha512-quS9HgjQpdaXOvsZz82Oz7uxtXiy6UIsIQcpBj7HRw2M63Skasm9qlDocAM7jNuaxdhpPU7c4kJN+gA5MCu4ww==} + engines: {node: '>=18.17'} dependencies: cheerio-select: 2.1.0 dom-serializer: 2.0.0 domhandler: 5.0.3 domutils: 3.1.0 - htmlparser2: 8.0.2 - parse5: 7.1.2 - parse5-htmlparser2-tree-adapter: 7.0.0 + encoding-sniffer: 0.2.0 + htmlparser2: 9.1.0 + parse5: 7.2.1 + parse5-htmlparser2-tree-adapter: 7.1.0 + parse5-parser-stream: 7.1.2 + undici: 6.20.1 + whatwg-mimetype: 4.0.0 dev: true /chokidar@3.5.3: @@ -4614,7 +4311,22 @@ packages: engines: {node: '>= 8.10.0'} dependencies: anymatch: 3.1.3 - braces: 3.0.2 + braces: 3.0.3 + glob-parent: 5.1.2 + is-binary-path: 2.1.0 + is-glob: 4.0.3 + normalize-path: 3.0.0 + readdirp: 3.6.0 + optionalDependencies: + fsevents: 2.3.3 + dev: true + + /chokidar@3.6.0: + resolution: {integrity: sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==} + engines: {node: '>= 8.10.0'} + dependencies: + anymatch: 3.1.3 + braces: 3.0.3 glob-parent: 5.1.2 is-binary-path: 2.1.0 is-glob: 4.0.3 @@ -4819,8 +4531,8 @@ packages: resolution: {integrity: sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==} dev: false - /cookie@0.6.0: - resolution: {integrity: sha512-U71cyTamuh1CRNCfpGY6to28lxvNwPG4Guz/EVjgf3Jmzv0vlDp1atT9eS5dDjMYHucpHbWns6Lwf3BKz6svdw==} + /cookie@0.7.1: + resolution: {integrity: sha512-6DnInpx7SJ2AK3+CTUE/ZM0vWTUboZCegxhC2xiIydHR9jNuTAASBrfEpHhiGOZw/nX51bHt6YQl8jsGo4y/0w==} engines: {node: '>= 0.6'} dev: false @@ -4851,10 +4563,10 @@ packages: toggle-selection: 1.0.6 dev: false - /core-js-compat@3.35.1: - resolution: {integrity: sha512-sftHa5qUJY3rs9Zht1WEnmkvXputCyDBczPnr7QDgL8n3qrF3CMXY4VPSYtOLLiOUJcah2WNXREd48iOl6mQIw==} + /core-js-compat@3.39.0: + resolution: {integrity: sha512-VgEUx3VwlExr5no0tXlBt+silBvhTryPwCXRI2Id1PN8WTKu7MreethvddqOubrYxkFdv/RnYrqlv1sFNAUelw==} dependencies: - browserslist: 4.22.2 + browserslist: 4.24.2 dev: false /core-util-is@1.0.3: @@ -4922,7 +4634,7 @@ packages: engines: {node: ^10 || ^12.20.0 || ^14.13.0 || >=15.0.0, npm: '>=7.0.0'} dependencies: mdn-data: 2.0.28 - source-map-js: 1.2.0 + source-map-js: 1.2.1 dev: true /css-tree@2.3.1: @@ -4930,7 +4642,7 @@ packages: engines: {node: ^10 || ^12.20.0 || ^14.13.0 || >=15.0.0} dependencies: mdn-data: 2.0.30 - source-map-js: 1.2.0 + source-map-js: 1.2.1 dev: true /css-what@6.1.0: @@ -4953,21 +4665,18 @@ packages: resolution: {integrity: sha512-wT5Y7mO8abrV16gnssKdmIhIbA9wSkeMzhh27jAguKrV82i24wER0vL5TGhUJ9dbJNDcigoRZ0IAHFEEEI4THQ==} dev: true - /cytoscape-cose-bilkent@4.1.0(cytoscape@3.28.1): + /cytoscape-cose-bilkent@4.1.0(cytoscape@3.30.3): resolution: {integrity: sha512-wgQlVIUJF13Quxiv5e1gstZ08rnZj2XaLHGoFMYXz7SkNfCDOOteKBE6SYRfA9WxxI/iBc3ajfDoc6hb/MRAHQ==} peerDependencies: cytoscape: ^3.2.0 dependencies: cose-base: 1.0.3 - cytoscape: 3.28.1 + cytoscape: 3.30.3 dev: true - /cytoscape@3.28.1: - resolution: {integrity: sha512-xyItz4O/4zp9/239wCcH8ZcFuuZooEeF8KHRmzjDfGdXsj3OG9MFSMA0pJE0uX3uCN/ygof6hHf4L7lst+JaDg==} + /cytoscape@3.30.3: + resolution: {integrity: sha512-HncJ9gGJbVtw7YXtIs3+6YAFSSiKsom0amWc33Z7QbylbY2JGMrA0yz4EwrdTScZxnwclXeEZHzO5pxoy0ZE4g==} engines: {node: '>=0.10'} - dependencies: - heap: 0.2.7 - lodash: 4.17.21 dev: true /d3-array@2.12.1: @@ -5241,11 +4950,12 @@ packages: d3-zoom: 3.0.0 dev: true - /d@1.0.1: - resolution: {integrity: sha512-m62ShEObQ39CfralilEQRjH6oAMtNCV1xJyEx5LpRYUVN+EviphDgUc/F3hnYbADmkiNs67Y+3ylmlG7Lnu+FA==} + /d@1.0.2: + resolution: {integrity: sha512-MOqHvMWF9/9MX6nza0KgvFH4HpMU0EF5uUDXqX/BtxtU8NfB0QzRtJ8Oe/6SuS4kbhyzVJwjd97EA4PKrzJ8bw==} + engines: {node: '>=0.12'} dependencies: - es5-ext: 0.10.53 - type: 1.2.0 + es5-ext: 0.10.64 + type: 2.7.3 dev: false /dagre-d3-es@7.0.10: @@ -5255,13 +4965,40 @@ packages: lodash-es: 4.17.21 dev: true + /data-view-buffer@1.0.1: + resolution: {integrity: sha512-0lht7OugA5x3iJLOWFhWK/5ehONdprk0ISXqVFn/NFrDu+cuc8iADFrGQz5BnRK7LLU3JmkbXSxaqX+/mXYtUA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.7 + es-errors: 1.3.0 + is-data-view: 1.0.1 + dev: true + + /data-view-byte-length@1.0.1: + resolution: {integrity: sha512-4J7wRJD3ABAzr8wP+OcIcqq2dlUKp4DVflx++hs5h5ZKydWMI6/D/fAot+yh6g2tHh8fLFTvNOaVN357NvSrOQ==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.7 + es-errors: 1.3.0 + is-data-view: 1.0.1 + dev: true + + /data-view-byte-offset@1.0.0: + resolution: {integrity: sha512-t/Ygsytq+R995EJ5PZlD4Cu56sWa8InXySaViRzw9apusqsOO2bQP+SbYzAhR0pFKoB+43lYy8rWban9JSuXnA==} + engines: {node: '>= 0.4'} + dependencies: + call-bind: 1.0.7 + es-errors: 1.3.0 + is-data-view: 1.0.1 + dev: true + /date-format@4.0.14: resolution: {integrity: sha512-39BOQLs9ZjKh0/patS9nrT8wc3ioX3/eA/zgbKNopnF2wCqJEoxywwwElATYvRsXdnOxA/OQeQoFZ3rFjVajhg==} engines: {node: '>=4.0'} dev: false - /dayjs@1.11.7: - resolution: {integrity: sha512-+Yw9U6YO5TQohxLcIkrXBeY73WP3ejHWVvx8XCk3gxvQDCTEmS48ZrSZCKciI7Bhl/uCMyxYtE9UqRILmFphkQ==} + /dayjs@1.11.13: + resolution: {integrity: sha512-oaMBel6gjolK862uaPQOVTA7q3TZhuSvuMQAAglQDOWYO9A91IrAOUJEyKVlqJlHE0vq5p5UXxzdPfMH/x6xNg==} dev: true /debug@2.6.9: @@ -5308,6 +5045,19 @@ packages: dependencies: ms: 2.1.2 supports-color: 8.1.1 + dev: true + + /debug@4.3.7(supports-color@8.1.1): + resolution: {integrity: sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ==} + engines: {node: '>=6.0'} + peerDependencies: + supports-color: '*' + peerDependenciesMeta: + supports-color: + optional: true + dependencies: + ms: 2.1.3 + supports-color: 8.1.1 /decamelize@1.2.0: resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==} @@ -5333,7 +5083,7 @@ packages: resolution: {integrity: sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==} engines: {node: '>=0.12'} dependencies: - type-detect: 4.0.8 + type-detect: 4.1.0 dev: true /deep-is@0.1.4: @@ -5347,13 +5097,13 @@ packages: strip-bom: 4.0.0 dev: true - /define-data-property@1.1.1: - resolution: {integrity: sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ==} + /define-data-property@1.1.4: + resolution: {integrity: sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==} engines: {node: '>= 0.4'} dependencies: - get-intrinsic: 1.2.2 + es-define-property: 1.0.0 + es-errors: 1.3.0 gopd: 1.0.1 - has-property-descriptors: 1.0.1 /define-lazy-prop@2.0.0: resolution: {integrity: sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==} @@ -5364,8 +5114,8 @@ packages: resolution: {integrity: sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==} engines: {node: '>= 0.4'} dependencies: - define-data-property: 1.1.1 - has-property-descriptors: 1.0.1 + define-data-property: 1.1.4 + has-property-descriptors: 1.0.2 object-keys: 1.1.1 dev: true @@ -5435,6 +5185,17 @@ packages: engines: {node: '>= 0.8', npm: 1.2.8000 || >= 1.4.16} dev: false + /detect-port@1.3.0: + resolution: {integrity: sha512-E+B1gzkl2gqxt1IhUzwjrxBKRqx1UzC3WLONHinn8S3T6lwV/agVCyitiFOsGJ/eYuEUBvD71MZHy3Pv1G9doQ==} + engines: {node: '>= 4.2.1'} + hasBin: true + dependencies: + address: 1.2.2 + debug: 2.6.9 + transitivePeerDependencies: + - supports-color + dev: false + /diagnostic-channel-publishers@0.4.4(diagnostic-channel@0.3.1): resolution: {integrity: sha512-l126t01d2ZS9EreskvEtZPrcgstuvH3rbKy82oUhUrVmBaGx4hO9wECdl3cvZbKDYjMF3QJDB5z5dL9yWAjvZQ==} peerDependencies: @@ -5459,6 +5220,11 @@ packages: engines: {node: '>=0.3.1'} dev: true + /diff@5.2.0: + resolution: {integrity: sha512-uIFDxqpRZGZ6ThOk84hEfqWoHx2devRFvpTZcTHur85vImfaxUbTW9Ryh4CpCuDnToOP1CEtXKIgytHBPVff5A==} + engines: {node: '>=0.3.1'} + dev: true + /diffie-hellman@5.0.3: resolution: {integrity: sha512-kqag/Nl+f3GwyK25fhUMYj81BUOrZ9IuJsjIcDE5icNM9FJHAVm3VcUDxdLPoQtTuUylWm6ZIknYJwwaPxsUzg==} dependencies: @@ -5523,7 +5289,7 @@ packages: resolution: {integrity: sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==} dependencies: no-case: 3.0.4 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /dotenv@8.2.0: @@ -5535,7 +5301,7 @@ packages: resolution: {integrity: sha512-YDBmkNhQ6pvUY6gDpwmWe+A6Id819eR3RPAVZIhaZfCL1C+F7/0uzXPSjE2DprKruc3kuVhOCMJl2Z/6whLUzQ==} hasBin: true dependencies: - minimatch: 9.0.3 + minimatch: 9.0.5 yargs: 17.7.2 dev: false @@ -5549,19 +5315,19 @@ packages: resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} dev: false - /ejs@3.1.9: - resolution: {integrity: sha512-rC+QVNMJWv+MtPgkt0y+0rVEIdbtxVADApW9JXrUVlzHetgcyczP/E7DJmWJ4fJCZF2cPcBk0laWO9ZHMG3DmQ==} + /ejs@3.1.10: + resolution: {integrity: sha512-UeJmFfOrAQS8OJWPZ4qtgHyWExa088/MtK5UEyoJGFH67cDEXkZSviOiKRCZ4Xij0zxI3JECgYs3oKx+AizQBA==} engines: {node: '>=0.10.0'} hasBin: true dependencies: - jake: 10.8.7 + jake: 10.9.2 dev: true - /electron-to-chromium@1.4.645: - resolution: {integrity: sha512-EeS1oQDCmnYsRDRy2zTeC336a/4LZ6WKqvSaM1jLocEk5ZuyszkQtCpsqvuvaIXGOUjwtvF6LTcS8WueibXvSw==} + /electron-to-chromium@1.5.51: + resolution: {integrity: sha512-kKeWV57KSS8jH4alKt/jKnvHPmJgBxXzGUSbMd4eQF+iOsVPl7bz2KUmu6eo80eMP8wVioTfTyTzdMgM15WXNg==} - /elkjs@0.9.2: - resolution: {integrity: sha512-2Y/RaA1pdgSHpY0YG4TYuYCD2wh97CRvu22eLG3Kz0pgQ/6KbIFTxsTnDc4MH/6hFlg2L/9qXrDMG0nMjP63iw==} + /elkjs@0.9.3: + resolution: {integrity: sha512-f/ZeWvW/BCXbhGEf1Ujp29EASo/lk1FDnETgNKwJrsVvGZhUWCZyg3xLJjAsxfOmt8KjswHmI5EwCQcPMpOYhQ==} dev: true /emitter-listener@1.1.2: @@ -5583,6 +5349,18 @@ packages: engines: {node: '>= 0.8'} dev: false + /encodeurl@2.0.0: + resolution: {integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==} + engines: {node: '>= 0.8'} + dev: false + + /encoding-sniffer@0.2.0: + resolution: {integrity: sha512-ju7Wq1kg04I3HtiYIOrUrdfdDvkyO9s5XM8QAj/bN61Yo/Vb4vgJxy5vi4Yxk01gWHbrofpPtpxM8bKger9jhg==} + dependencies: + iconv-lite: 0.6.3 + whatwg-encoding: 3.1.1 + dev: true + /encoding@0.1.13: resolution: {integrity: sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==} requiresBuild: true @@ -5641,64 +5419,88 @@ packages: is-arrayish: 0.2.1 dev: true - /es-abstract@1.22.3: - resolution: {integrity: sha512-eiiY8HQeYfYH2Con2berK+To6GrK2RxbPawDkGq4UiCQQfZHb6wX9qQqkbpPqaxQFcl8d9QzZqo0tGE0VcrdwA==} + /es-abstract@1.23.3: + resolution: {integrity: sha512-e+HfNH61Bj1X9/jLc5v1owaLYuHdeHHSQlkhCBiTK8rBvKaULl/beGMxwrMXjpYrv4pz22BlY570vVePA2ho4A==} engines: {node: '>= 0.4'} dependencies: - array-buffer-byte-length: 1.0.0 - arraybuffer.prototype.slice: 1.0.2 - available-typed-arrays: 1.0.5 - call-bind: 1.0.5 - es-set-tostringtag: 2.0.2 + array-buffer-byte-length: 1.0.1 + arraybuffer.prototype.slice: 1.0.3 + available-typed-arrays: 1.0.7 + call-bind: 1.0.7 + data-view-buffer: 1.0.1 + data-view-byte-length: 1.0.1 + data-view-byte-offset: 1.0.0 + es-define-property: 1.0.0 + es-errors: 1.3.0 + es-object-atoms: 1.0.0 + es-set-tostringtag: 2.0.3 es-to-primitive: 1.2.1 function.prototype.name: 1.1.6 - get-intrinsic: 1.2.2 - get-symbol-description: 1.0.0 - globalthis: 1.0.3 + get-intrinsic: 1.2.4 + get-symbol-description: 1.0.2 + globalthis: 1.0.4 gopd: 1.0.1 - has-property-descriptors: 1.0.1 - has-proto: 1.0.1 + has-property-descriptors: 1.0.2 + has-proto: 1.0.3 has-symbols: 1.0.3 - hasown: 2.0.0 - internal-slot: 1.0.6 - is-array-buffer: 3.0.2 + hasown: 2.0.2 + internal-slot: 1.0.7 + is-array-buffer: 3.0.4 is-callable: 1.2.7 - is-negative-zero: 2.0.2 + is-data-view: 1.0.1 + is-negative-zero: 2.0.3 is-regex: 1.1.4 - is-shared-array-buffer: 1.0.2 + is-shared-array-buffer: 1.0.3 is-string: 1.0.7 - is-typed-array: 1.1.12 + is-typed-array: 1.1.13 is-weakref: 1.0.2 - object-inspect: 1.13.1 + object-inspect: 1.13.2 object-keys: 1.1.1 object.assign: 4.1.5 - regexp.prototype.flags: 1.5.1 - safe-array-concat: 1.1.0 - safe-regex-test: 1.0.2 - string.prototype.trim: 1.2.8 - string.prototype.trimend: 1.0.7 - string.prototype.trimstart: 1.0.7 - typed-array-buffer: 1.0.0 - typed-array-byte-length: 1.0.0 - typed-array-byte-offset: 1.0.0 - typed-array-length: 1.0.4 + regexp.prototype.flags: 1.5.3 + safe-array-concat: 1.1.2 + safe-regex-test: 1.0.3 + string.prototype.trim: 1.2.9 + string.prototype.trimend: 1.0.8 + string.prototype.trimstart: 1.0.8 + typed-array-buffer: 1.0.2 + typed-array-byte-length: 1.0.1 + typed-array-byte-offset: 1.0.2 + typed-array-length: 1.0.6 unbox-primitive: 1.0.2 - which-typed-array: 1.1.13 + which-typed-array: 1.1.15 + dev: true + + /es-define-property@1.0.0: + resolution: {integrity: sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==} + engines: {node: '>= 0.4'} + dependencies: + get-intrinsic: 1.2.4 + + /es-errors@1.3.0: + resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} + engines: {node: '>= 0.4'} + + /es-object-atoms@1.0.0: + resolution: {integrity: sha512-MZ4iQ6JwHOBQjahnjwaC1ZtIBH+2ohjamzAO3oaHcXYup7qxjF2fixyH+Q71voWHeOkI2q/TnJao/KfXYIZWbw==} + engines: {node: '>= 0.4'} + dependencies: + es-errors: 1.3.0 dev: true - /es-set-tostringtag@2.0.2: - resolution: {integrity: sha512-BuDyupZt65P9D2D2vA/zqcI3G5xRsklm5N3xCwuiy+/vKy8i0ifdsQP1sLgO4tZDSCaQUSnmC48khknGMV3D2Q==} + /es-set-tostringtag@2.0.3: + resolution: {integrity: sha512-3T8uNMC3OQTHkFUsFq8r/BwAXLHvU/9O9mE0fBc/MY5iq/8H7ncvO947LmYA6ldWw9Uh8Yhf25zu6n7nML5QWQ==} engines: {node: '>= 0.4'} dependencies: - get-intrinsic: 1.2.2 - has-tostringtag: 1.0.0 - hasown: 2.0.0 + get-intrinsic: 1.2.4 + has-tostringtag: 1.0.2 + hasown: 2.0.2 dev: true /es-shim-unscopables@1.0.2: resolution: {integrity: sha512-J3yBRXCzDu4ULnQwxyToo/OjdMx6akgVC7K6few0a7F/0wLtmKKN7I73AH5T2836UuXRqN7Qg+IIUw/+YJksRw==} dependencies: - hasown: 2.0.0 + hasown: 2.0.2 dev: true /es-to-primitive@1.2.1: @@ -5714,10 +5516,21 @@ packages: resolution: {integrity: sha512-Xs2Stw6NiNHWypzRTY1MtaG/uJlwCk8kH81920ma8mvN8Xq1gsfhZvpkImLQArw8AHnv8MT2I45J3c0R8slE+Q==} dependencies: es6-iterator: 2.0.3 - es6-symbol: 3.1.3 + es6-symbol: 3.1.4 next-tick: 1.0.0 dev: false + /es5-ext@0.10.64: + resolution: {integrity: sha512-p2snDhiLaXe6dahss1LddxqEm+SkuDvV8dnIQG0MWjyHpcMNfXKPE+/Cc0y+PhxJX3A4xGNeFCj5oc0BUh6deg==} + engines: {node: '>=0.10'} + requiresBuild: true + dependencies: + es6-iterator: 2.0.3 + es6-symbol: 3.1.4 + esniff: 2.0.1 + next-tick: 1.1.0 + dev: false + /es6-error@4.1.1: resolution: {integrity: sha512-Um/+FxMr9CISWh0bi5Zv0iOD+4cFh5qLeks1qhAopKVAJw3drgKbKySikp7wGhDL0HPeaja0P5ULZrxLkniUVg==} dev: true @@ -5725,15 +5538,16 @@ packages: /es6-iterator@2.0.3: resolution: {integrity: sha512-zw4SRzoUkd+cl+ZoE15A9o1oQd920Bb0iOJMQkQhl3jNc03YqVjAhG7scf9C5KWRU/R13Orf588uCC6525o02g==} dependencies: - d: 1.0.1 + d: 1.0.2 es5-ext: 0.10.53 - es6-symbol: 3.1.3 + es6-symbol: 3.1.4 dev: false - /es6-symbol@3.1.3: - resolution: {integrity: sha512-NJ6Yn3FuDinBaBRWl/q5X/s4koRHBrgKAu+yGI6JCBeiu3qrcbJhwT2GeR/EXVfylRk8dpQVJoLEFhK+Mu31NA==} + /es6-symbol@3.1.4: + resolution: {integrity: sha512-U9bFFjX8tFiATgtkJ1zg25+KviIXpgRvRHS8sau3GfhVzThRQrOeksPeT0BWW2MNZs1OEWJ1DPXOQMn0KKRkvg==} + engines: {node: '>=0.12'} dependencies: - d: 1.0.1 + d: 1.0.2 ext: 1.7.0 dev: false @@ -5804,8 +5618,8 @@ packages: '@esbuild/win32-x64': 0.23.0 dev: true - /escalade@3.1.1: - resolution: {integrity: sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==} + /escalade@3.2.0: + resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} engines: {node: '>=6'} /escape-html@1.0.3: @@ -5825,14 +5639,14 @@ packages: resolution: {integrity: sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g==} dependencies: debug: 3.2.7 - is-core-module: 2.13.1 + is-core-module: 2.15.1 resolve: 1.22.8 transitivePeerDependencies: - supports-color dev: true - /eslint-module-utils@2.8.0(@typescript-eslint/parser@5.0.0)(eslint-import-resolver-node@0.3.9)(eslint@8.1.0): - resolution: {integrity: sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw==} + /eslint-module-utils@2.12.0(@typescript-eslint/parser@5.0.0)(eslint-import-resolver-node@0.3.9)(eslint@8.1.0): + resolution: {integrity: sha512-wALZ0HFoytlyh/1+4wuZ9FJCD/leWHQzzrxJ8+rebyReSLk7LApMyd3WJaLVoN+D5+WIdJyDK1c6JnE65V4Zyg==} engines: {node: '>=4'} peerDependencies: '@typescript-eslint/parser': '*' @@ -5879,18 +5693,18 @@ packages: optional: true dependencies: '@typescript-eslint/parser': 5.0.0(eslint@8.1.0)(typescript@4.7.4) - array-includes: 3.1.7 + array-includes: 3.1.8 array.prototype.flat: 1.3.2 debug: 2.6.9 doctrine: 2.1.0 eslint: 8.1.0 eslint-import-resolver-node: 0.3.9 - eslint-module-utils: 2.8.0(@typescript-eslint/parser@5.0.0)(eslint-import-resolver-node@0.3.9)(eslint@8.1.0) + eslint-module-utils: 2.12.0(@typescript-eslint/parser@5.0.0)(eslint-import-resolver-node@0.3.9)(eslint@8.1.0) has: 1.0.4 - is-core-module: 2.13.1 + is-core-module: 2.15.1 is-glob: 4.0.3 minimatch: 3.1.2 - object.values: 1.1.7 + object.values: 1.2.0 resolve: 1.22.8 tsconfig-paths: 3.15.0 transitivePeerDependencies: @@ -5970,7 +5784,7 @@ packages: ajv: 6.12.6 chalk: 4.1.2 cross-spawn: 7.0.3 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) doctrine: 3.0.0 enquirer: 2.4.1 escape-string-regexp: 4.0.0 @@ -5978,7 +5792,7 @@ packages: eslint-utils: 3.0.0(eslint@8.1.0) eslint-visitor-keys: 3.4.3 espree: 9.6.1 - esquery: 1.5.0 + esquery: 1.6.0 esutils: 2.0.3 fast-deep-equal: 3.1.3 file-entry-cache: 6.0.1 @@ -5995,10 +5809,10 @@ packages: lodash.merge: 4.6.2 minimatch: 3.1.2 natural-compare: 1.4.0 - optionator: 0.9.3 + optionator: 0.9.4 progress: 2.0.3 regexpp: 3.2.0 - semver: 7.5.4 + semver: 7.5.2 strip-ansi: 6.0.1 strip-json-comments: 3.1.1 text-table: 0.2.0 @@ -6007,12 +5821,22 @@ packages: - supports-color dev: true + /esniff@2.0.1: + resolution: {integrity: sha512-kTUIGKQ/mDPFoJ0oVfcmyJn4iBDRptjNVIzwIFR7tqWXdVI9xfA2RMwY/gbSpJG3lkdWNEjLap/NqVHZiJsdfg==} + engines: {node: '>=0.10'} + dependencies: + d: 1.0.2 + es5-ext: 0.10.64 + event-emitter: 0.3.5 + type: 2.7.3 + dev: false + /espree@9.6.1: resolution: {integrity: sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} dependencies: - acorn: 8.11.3 - acorn-jsx: 5.3.2(acorn@8.11.3) + acorn: 8.14.0 + acorn-jsx: 5.3.2(acorn@8.14.0) eslint-visitor-keys: 3.4.3 dev: true @@ -6021,8 +5845,8 @@ packages: engines: {node: '>=4'} hasBin: true - /esquery@1.5.0: - resolution: {integrity: sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg==} + /esquery@1.6.0: + resolution: {integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==} engines: {node: '>=0.10'} dependencies: estraverse: 5.3.0 @@ -6058,6 +5882,13 @@ packages: engines: {node: '>= 0.6'} dev: false + /event-emitter@0.3.5: + resolution: {integrity: sha512-D9rRn9y7kLPnJ+hMq7S/nhvoKwwvVJahBi2BPmx3bvbsEdK3W9ii8cBSGjP+72/LnM4n6fo3+dkCX5FeTQruXA==} + dependencies: + d: 1.0.2 + es5-ext: 0.10.64 + dev: false + /events@3.3.0: resolution: {integrity: sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==} engines: {node: '>=0.8.x'} @@ -6101,36 +5932,36 @@ packages: resolution: {integrity: sha512-dX7e/LHVJ6W3DE1MHWi9S1EYzDESENfLrYohG2G++ovZrYOkm4Knwa0mc1cn84xJOR4KEU0WSchhLbd0UklbHw==} dev: true - /express@4.19.2: - resolution: {integrity: sha512-5T6nhjsT+EOMzuck8JjBHARTHfMht0POzlA60WV2pMD3gyXw2LZnZ+ueGdNxG+0calOJcWKbpFcuzLZ91YWq9Q==} + /express@4.21.1: + resolution: {integrity: sha512-YSFlK1Ee0/GC8QaO91tHcDxJiE/X4FbpAyQWkxAvG6AXCuR65YzK8ua6D9hvi/TzUfZMpc+BwuM1IPw8fmQBiQ==} engines: {node: '>= 0.10.0'} dependencies: accepts: 1.3.8 array-flatten: 1.1.1 - body-parser: 1.20.2 + body-parser: 1.20.3 content-disposition: 0.5.4 content-type: 1.0.5 - cookie: 0.6.0 + cookie: 0.7.1 cookie-signature: 1.0.6 debug: 2.6.9 depd: 2.0.0 - encodeurl: 1.0.2 + encodeurl: 2.0.0 escape-html: 1.0.3 etag: 1.8.1 - finalhandler: 1.2.0 + finalhandler: 1.3.1 fresh: 0.5.2 http-errors: 2.0.0 - merge-descriptors: 1.0.1 + merge-descriptors: 1.0.3 methods: 1.1.2 on-finished: 2.4.1 parseurl: 1.3.3 - path-to-regexp: 0.1.7 + path-to-regexp: 0.1.10 proxy-addr: 2.0.7 - qs: 6.11.0 + qs: 6.13.0 range-parser: 1.2.1 safe-buffer: 5.2.1 - send: 0.18.0 - serve-static: 1.15.0 + send: 0.19.0 + serve-static: 1.16.2 setprototypeof: 1.2.0 statuses: 2.0.1 type-is: 1.6.18 @@ -6143,7 +5974,7 @@ packages: /ext@1.7.0: resolution: {integrity: sha512-6hxeJYaL110a9b5TEJSj0gojyHQAmA2ch5Os+ySCiA1QGdS697XWY1pzsrSjqA9LDEEgdB/KypIlR59RcLuHYw==} dependencies: - type: 2.7.2 + type: 2.7.3 dev: false /extend-shallow@2.0.1: @@ -6192,7 +6023,7 @@ packages: '@nodelib/fs.walk': 1.2.8 glob-parent: 5.1.2 merge2: 1.4.1 - micromatch: 4.0.5 + micromatch: 4.0.8 dev: true /fast-json-stable-stringify@2.1.0: @@ -6207,8 +6038,12 @@ packages: resolution: {integrity: sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==} dev: true - /fastq@1.16.0: - resolution: {integrity: sha512-ifCoaXsDrsdkWTtiNJX5uzHDsrck5TzfKKDcuFFTIrrc/BS076qgEIfoIy1VeZqViznfKiysPYTh/QeHtnIsYA==} + /fast-uri@3.0.3: + resolution: {integrity: sha512-aLrHthzCjH5He4Z2H9YZ+v6Ujb9ocRuW6ZzkJQOrTxleEijANq4v1TsaPaVG1PZcuurEzrLcWRyYBYXD5cEiaw==} + dev: false + + /fastq@1.17.1: + resolution: {integrity: sha512-sRVD3lWVIXWg6By68ZN7vho9a1pQcN/WBFaAAsDDFzlJjvoGx0P8z7V1t72grFJfJhu3YPZBuu25f7Kaw2jN1w==} dependencies: reusify: 1.0.4 dev: true @@ -6246,8 +6081,8 @@ packages: to-regex-range: 2.1.1 dev: true - /fill-range@7.0.1: - resolution: {integrity: sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==} + /fill-range@7.1.1: + resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} engines: {node: '>=8'} dependencies: to-regex-range: 5.0.1 @@ -6257,12 +6092,12 @@ packages: engines: {node: '>=0.10.0'} dev: false - /finalhandler@1.2.0: - resolution: {integrity: sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==} + /finalhandler@1.3.1: + resolution: {integrity: sha512-6BN9trH7bp3qvnrRyzsBz+g3lZxTNZTbVO2EV1CS0WIcDbawYVdYvGflME/9QP0h0pYlCDBCTjYa9nZzMDpyxQ==} engines: {node: '>= 0.8'} dependencies: debug: 2.6.9 - encodeurl: 1.0.2 + encodeurl: 2.0.0 escape-html: 1.0.3 on-finished: 2.4.1 parseurl: 1.3.3 @@ -6317,7 +6152,7 @@ packages: resolution: {integrity: sha512-CYcENa+FtcUKLmhhqyctpclsq7QF38pKjZHsGNiSQF5r4FtoKDWabFDl3hzaEQMvT1LHEysw5twgLvpYYb4vbw==} engines: {node: ^10.12.0 || >=12.0.0} dependencies: - flatted: 3.2.9 + flatted: 3.3.1 keyv: 4.5.4 rimraf: 3.0.2 dev: true @@ -6327,16 +6162,16 @@ packages: hasBin: true dev: true - /flatted@3.2.9: - resolution: {integrity: sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ==} + /flatted@3.3.1: + resolution: {integrity: sha512-X8cqMLLie7KsNUDSdzeN8FYK9rEt4Dt67OsG/DNGnYTSDBG4uFAJFBnUeiV+zCVAvwFy56IjM9sH51jVaEhNxw==} - /flow-parser@0.227.0: - resolution: {integrity: sha512-nOygtGKcX/siZK/lFzpfdHEfOkfGcTW7rNroR1Zsz6T/JxSahPALXVt5qVHq/fgvMJuv096BTKbgxN3PzVBaDA==} + /flow-parser@0.251.1: + resolution: {integrity: sha512-8ZuLqJPlL/T9K3zFdr1m88Lx8JOoJluTTdyvN4uH5NT9zoIIFqbCDoXVhkHh022k2lhuAyFF27cu0BYKh5SmDA==} engines: {node: '>=0.4.0'} dev: false - /follow-redirects@1.15.6(debug@4.3.4): - resolution: {integrity: sha512-wWN62YITEaOpSK584EZXJafH1AGpO8RVgElfkuXbTOrPX4fIfOyEpW/CsiNd8JdYrAoOvafRTOEnvsO++qCqFA==} + /follow-redirects@1.15.9(debug@4.3.7): + resolution: {integrity: sha512-gew4GsXizNgdoRyqmyfMHyAmXsZDk6mHkSxZFCzW9gwlbtOW44CDtYavM+y+72qD/Vq2l550kMF52DT8fOLJqQ==} engines: {node: '>=4.0'} peerDependencies: debug: '*' @@ -6344,7 +6179,7 @@ packages: debug: optional: true dependencies: - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) dev: false /for-each@0.3.3: @@ -6366,8 +6201,8 @@ packages: signal-exit: 3.0.7 dev: true - /form-data@4.0.0: - resolution: {integrity: sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==} + /form-data@4.0.1: + resolution: {integrity: sha512-tzN8e4TX8+kkxGPK8D5u0FNmjPUjw3lwC9lSLxxoB/+GtsJG91CO8bSWy73APlgAZzZbXEYZJuxjkHH2w+Ezhw==} engines: {node: '>= 6'} dependencies: asynckit: 0.4.0 @@ -6473,9 +6308,9 @@ packages: resolution: {integrity: sha512-Z5kx79swU5P27WEayXM1tBi5Ze/lbIyiNgU3qyXUOf9b2rgXYyF9Dy9Cx+IQv/Lc8WCG6L82zwUPpSS9hGehIg==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-abstract: 1.23.3 functions-have-names: 1.2.3 dev: true @@ -6495,6 +6330,7 @@ packages: /gauge@4.0.4: resolution: {integrity: sha512-f9m+BEN5jkg6a0fZjleidjN51VE1X+mPFQ2DJ0uv1V39oCLCbsGe6yjbBnp7eK7z/+GAon99a3nHuqbuuthyPg==} engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + deprecated: This package is no longer supported. dependencies: aproba: 2.0.0 color-support: 1.1.3 @@ -6518,13 +6354,15 @@ packages: resolution: {integrity: sha512-8vXOvuE167CtIc3OyItco7N/dpRtBbYOsPsXCz7X/PMnlGjYjSGuZJgM1Y7mmew7BKf9BqvLX2tnOVy1BBUsxQ==} dev: true - /get-intrinsic@1.2.2: - resolution: {integrity: sha512-0gSo4ml/0j98Y3lngkFEot/zhiCeWsbYIlZ+uZOVgzLyLaUw7wxUL+nCTP0XJvJg1AXulJRI3UJi8GsbDuxdGA==} + /get-intrinsic@1.2.4: + resolution: {integrity: sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==} + engines: {node: '>= 0.4'} dependencies: + es-errors: 1.3.0 function-bind: 1.1.2 - has-proto: 1.0.1 + has-proto: 1.0.3 has-symbols: 1.0.3 - hasown: 2.0.0 + hasown: 2.0.2 /get-own-enumerable-property-symbols@3.0.2: resolution: {integrity: sha512-I0UBV/XOz1XkIJHEUDMZAbzCThU/H8DxmSfmdGcKPnVhu2VfFqr34jr9777IyaTYvxjedWhqVIilEDsCdP5G6g==} @@ -6540,12 +6378,13 @@ packages: engines: {node: '>=10'} dev: true - /get-symbol-description@1.0.0: - resolution: {integrity: sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==} + /get-symbol-description@1.0.2: + resolution: {integrity: sha512-g0QYk1dZBxGwk+Ngc+ltRH2IBp2f7zBkBMBJZCDerh6EhlhSR6+9irMCuT/09zD6qkarHUSn529sK/yL4S27mg==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 + call-bind: 1.0.7 + es-errors: 1.3.0 + get-intrinsic: 1.2.4 dev: true /get-value@2.0.6: @@ -6572,13 +6411,14 @@ packages: engines: {node: '>=16 || 14 >=14.17'} dependencies: fs.realpath: 1.0.0 - minimatch: 9.0.3 + minimatch: 9.0.5 minipass: 5.0.0 - path-scurry: 1.10.1 + path-scurry: 1.11.1 dev: false /glob@7.2.0: resolution: {integrity: sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q==} + deprecated: Glob versions prior to v9 are no longer supported dependencies: fs.realpath: 1.0.0 inflight: 1.0.6 @@ -6590,6 +6430,7 @@ packages: /glob@7.2.3: resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} + deprecated: Glob versions prior to v9 are no longer supported dependencies: fs.realpath: 1.0.0 inflight: 1.0.6 @@ -6601,6 +6442,7 @@ packages: /glob@8.1.0: resolution: {integrity: sha512-r8hpEjiQEYlF2QU0df3dS+nxxSIreXQS1qRhMJM0Q5NDdR386C7jb7Hwwod8Fgiuex+k0GFjgft18yvxm5XoCQ==} engines: {node: '>=12'} + deprecated: Glob versions prior to v9 are no longer supported dependencies: fs.realpath: 1.0.0 inflight: 1.0.6 @@ -6620,11 +6462,12 @@ packages: type-fest: 0.20.2 dev: true - /globalthis@1.0.3: - resolution: {integrity: sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA==} + /globalthis@1.0.4: + resolution: {integrity: sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ==} engines: {node: '>= 0.4'} dependencies: define-properties: 1.2.1 + gopd: 1.0.1 dev: true /globby@11.1.0: @@ -6634,7 +6477,7 @@ packages: array-union: 2.1.0 dir-glob: 3.0.1 fast-glob: 3.3.2 - ignore: 5.3.0 + ignore: 5.3.2 merge2: 1.4.1 slash: 3.0.0 dev: true @@ -6642,7 +6485,7 @@ packages: /gopd@1.0.1: resolution: {integrity: sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==} dependencies: - get-intrinsic: 1.2.2 + get-intrinsic: 1.2.4 /graceful-fs@4.2.11: resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==} @@ -6659,21 +6502,21 @@ packages: resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} engines: {node: '>=8'} - /has-property-descriptors@1.0.1: - resolution: {integrity: sha512-VsX8eaIewvas0xnvinAe9bw4WfIeODpGYikiWYLH+dma0Jw6KHYqWiWfhQlgOVK8D6PvjubK5Uc4P0iIhIcNVg==} + /has-property-descriptors@1.0.2: + resolution: {integrity: sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==} dependencies: - get-intrinsic: 1.2.2 + es-define-property: 1.0.0 - /has-proto@1.0.1: - resolution: {integrity: sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==} + /has-proto@1.0.3: + resolution: {integrity: sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==} engines: {node: '>= 0.4'} /has-symbols@1.0.3: resolution: {integrity: sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==} engines: {node: '>= 0.4'} - /has-tostringtag@1.0.0: - resolution: {integrity: sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==} + /has-tostringtag@1.0.2: + resolution: {integrity: sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==} engines: {node: '>= 0.4'} dependencies: has-symbols: 1.0.3 @@ -6727,8 +6570,8 @@ packages: type-fest: 0.8.1 dev: true - /hasown@2.0.0: - resolution: {integrity: sha512-vUptKVTpIJhcczKBbgnS+RtcuYMB8+oNzPK2/Hp3hanz8JmpATdmmgLgSaadVREkDm+e2giHwY3ZRkyjSIDDFA==} + /hasown@2.0.2: + resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} engines: {node: '>= 0.4'} dependencies: function-bind: 1.1.2 @@ -6740,7 +6583,7 @@ packages: /hastscript@6.0.0: resolution: {integrity: sha512-nDM6bvd7lIqDUiYEiu5Sl/+6ReP0BMk/2f4U/Rooccxkj0P5nm+acM5PrGJ/t5I8qPGiqZSE6hVAwZEdZIvP4w==} dependencies: - '@types/hast': 2.3.9 + '@types/hast': 2.3.10 comma-separated-tokens: 1.0.8 hast-util-parse-selector: 2.2.5 property-information: 5.6.0 @@ -6752,10 +6595,6 @@ packages: hasBin: true dev: true - /heap@0.2.7: - resolution: {integrity: sha512-2bsegYkkHO+h/9MGbn6KWcE45cHZgPANo5LXF7EvWdT0yT2EguSVO1nDgU5c8+ZOPwp2vMNa7YFsJhVcDR9Sdg==} - dev: true - /highlight.js@10.7.3: resolution: {integrity: sha512-tzcUFauisWKNHaRkN4Wjl/ZA07gENAjFl3J/c480dprkGTg5EQstgaNFqBfUqCq54kZRIEcreTsAgF/m2quD7A==} dev: false @@ -6763,10 +6602,10 @@ packages: /history@4.10.1: resolution: {integrity: sha512-36nwAD620w12kuzPAsyINPWJqlNbij+hpK1k9XRloDtym8mxzGYl2c17LnV6IAGB2Dmg4tEa7G7DlawS0+qjew==} dependencies: - '@babel/runtime': 7.23.8 + '@babel/runtime': 7.26.0 loose-envify: 1.4.0 resolve-pathname: 3.0.0 - tiny-invariant: 1.3.1 + tiny-invariant: 1.3.3 tiny-warning: 1.0.3 value-equal: 1.0.1 dev: true @@ -6774,7 +6613,7 @@ packages: /history@5.3.0: resolution: {integrity: sha512-ZqaKwjjrAYUYfLG+htGaIIZ4nioX2L70ZUMIFysS3xvBsSG4x/n1V6TXV3N8ZYNuFGlDirFg32T7B6WOUPDYcQ==} dependencies: - '@babel/runtime': 7.23.8 + '@babel/runtime': 7.26.0 dev: true /hoist-non-react-statics@3.3.2: @@ -6787,8 +6626,8 @@ packages: resolution: {integrity: sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==} dev: true - /htmlparser2@8.0.2: - resolution: {integrity: sha512-GYdjWKDkbRLkZ5geuHs5NY1puJ+PXwP7+fHPRz06Eirsb9ugf6d8kkXav6ADhcODhFFPMIXyxkxSuMf3D6NCFA==} + /htmlparser2@9.1.0: + resolution: {integrity: sha512-5zfg6mHUoaer/97TxnGpxmbR7zJtPwIYFMZ/H5ucTlPZhKvtum05yiPK3Mgai3a0DyVxv7qYqoweaEd2nrYQzQ==} dependencies: domelementtype: 2.3.0 domhandler: 5.0.3 @@ -6817,7 +6656,17 @@ packages: dependencies: '@tootallnate/once': 2.0.0 agent-base: 6.0.2 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) + transitivePeerDependencies: + - supports-color + dev: true + + /http-proxy-agent@7.0.2: + resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==} + engines: {node: '>= 14'} + dependencies: + agent-base: 7.1.1 + debug: 4.3.7(supports-color@8.1.1) transitivePeerDependencies: - supports-color @@ -6826,7 +6675,17 @@ packages: engines: {node: '>= 6'} dependencies: agent-base: 6.0.2 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) + transitivePeerDependencies: + - supports-color + dev: true + + /https-proxy-agent@7.0.5: + resolution: {integrity: sha512-1e4Wqeblerz+tMKPIq2EMGiiWW1dIjZOksyHWSUm1rmuvw/how9hBHZ38lAGj5ID4Ik6EdkOw7NmWPy6LAwalw==} + engines: {node: '>= 14'} + dependencies: + agent-base: 7.1.1 + debug: 4.3.7(supports-color@8.1.1) transitivePeerDependencies: - supports-color @@ -6851,7 +6710,6 @@ packages: /iconv-lite@0.6.3: resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} engines: {node: '>=0.10.0'} - requiresBuild: true dependencies: safer-buffer: 2.1.2 dev: true @@ -6865,8 +6723,8 @@ packages: engines: {node: '>= 4'} dev: true - /ignore@5.3.0: - resolution: {integrity: sha512-g7dmpshy+gD7mh88OC9NwSGTKoc3kyLAZQRU1mt53Aw/vnvfXnbC+F/7F7QoYVKbV+KNvJx8wArewKy1vXMtlg==} + /ignore@5.3.2: + resolution: {integrity: sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==} engines: {node: '>= 4'} dev: true @@ -6874,8 +6732,8 @@ packages: resolution: {integrity: sha512-y0BKZgnoDLRIF2J0Pg/Wa6uhY5i6SqR7Wfagghf0UHRpnWJ5jm1IS0bZjAV5ADOxHAM2zdzYWmw8EbQgEUlvmw==} dev: true - /immutable@4.3.6: - resolution: {integrity: sha512-Ju0+lEMyzMVZarkTn/gqRpdqd5dOPaz1mCZ0SH3JV6iFw81PldE/PEB1hWVEA288HPt4WXW8O7AWxB10M+03QQ==} + /immutable@4.3.7: + resolution: {integrity: sha512-1hqclzwYwjRDFLjcFxOM5AYkkG0rpFPpr1RLPMEuGczoS7YA8gLhy8SWXYRAA/XwfEHpfo3cw5JGioS32fnMRw==} dev: true /import-fresh@3.3.0: @@ -6901,6 +6759,7 @@ packages: /inflight@1.0.6: resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==} + deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful. dependencies: once: 1.4.0 wrappy: 1.0.2 @@ -6912,13 +6771,13 @@ packages: /inherits@2.0.4: resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==} - /internal-slot@1.0.6: - resolution: {integrity: sha512-Xj6dv+PsbtwyPpEflsejS+oIZxmMlV44zAhG479uYu89MsjcYOhCFnNyKrkJrihbsiasQyY0afoCl/9BLR65bg==} + /internal-slot@1.0.7: + resolution: {integrity: sha512-NGnrKwXzSms2qUUih/ILZ5JBqNTSa1+ZmP6flaIp6KmSElgE9qdndzS3cqjrDovwFdmwsGsLdeFgB6suw+1e9g==} engines: {node: '>= 0.4'} dependencies: - get-intrinsic: 1.2.2 - hasown: 2.0.0 - side-channel: 1.0.4 + es-errors: 1.3.0 + hasown: 2.0.2 + side-channel: 1.0.6 dev: true /internmap@1.0.1: @@ -6935,7 +6794,7 @@ packages: deprecated: We've written a new parser that's 6x faster and is backwards compatible. Please use @formatjs/icu-messageformat-parser dependencies: '@formatjs/ecma402-abstract': 1.6.3 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /intl-messageformat@9.5.3: @@ -6943,11 +6802,15 @@ packages: dependencies: fast-memoize: 2.5.2 intl-messageformat-parser: 6.4.3 - tslib: 2.6.2 + tslib: 2.8.1 dev: true - /ip@2.0.0: - resolution: {integrity: sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ==} + /ip-address@9.0.5: + resolution: {integrity: sha512-zHtQzGojZXTwZTHQqra+ETKd4Sn3vgi7uBmlPoXVWZqYvuKmtI0l/VZTjqGmJY9x88GGOaZ9+G9ES8hC4T4X8g==} + engines: {node: '>= 12'} + dependencies: + jsbn: 1.1.0 + sprintf-js: 1.1.3 dev: true /ipaddr.js@1.9.1: @@ -6959,7 +6822,7 @@ packages: resolution: {integrity: sha512-YBUanLI8Yoihw923YeFUS5fs0fF2f5TSFTNiYAAzhhDscDa3lEqYuz1pDOEP5KvX94I9ey3vsqjJcLVFVU+3QA==} engines: {node: '>= 0.10'} dependencies: - hasown: 2.0.0 + hasown: 2.0.2 dev: true /is-alphabetical@1.0.4: @@ -6973,12 +6836,12 @@ packages: is-decimal: 1.0.4 dev: false - /is-array-buffer@3.0.2: - resolution: {integrity: sha512-y+FyyR/w8vfIRq4eQcM1EYgSTnmHXPqaF+IgzgraytCFq5Xh8lllDVmAZolPJiZttZLeFSINPYMaEJ7/vWUa1w==} + /is-array-buffer@3.0.4: + resolution: {integrity: sha512-wcjaerHw0ydZwfhiKbXJWLDY8A7yV7KhjQOpb83hGgGfId/aQa4TOvwyzn2PuswW2gPCYEL/nEAiSVpdOj1lXw==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 - is-typed-array: 1.1.12 + call-bind: 1.0.7 + get-intrinsic: 1.2.4 dev: true /is-arrayish@0.2.1: @@ -6995,15 +6858,15 @@ packages: resolution: {integrity: sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==} engines: {node: '>=8'} dependencies: - binary-extensions: 2.2.0 + binary-extensions: 2.3.0 dev: true /is-boolean-object@1.1.2: resolution: {integrity: sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - has-tostringtag: 1.0.0 + call-bind: 1.0.7 + has-tostringtag: 1.0.2 dev: true /is-buffer@1.1.6: @@ -7015,23 +6878,31 @@ packages: engines: {node: '>= 0.4'} dev: true - /is-core-module@2.13.1: - resolution: {integrity: sha512-hHrIjvZsftOsvKSn2TRYl63zvxsgE0K+0mYMoH6gD4omR5IWB2KynivBQczo3+wF1cCkjzvptnI9Q0sPU66ilw==} + /is-core-module@2.15.1: + resolution: {integrity: sha512-z0vtXSwucUJtANQWldhbtbt7BnL0vxiFjIdDLAatwhDYty2bad6s+rijD6Ri4YuYJubLzIJLUidCh09e1djEVQ==} + engines: {node: '>= 0.4'} dependencies: - hasown: 2.0.0 + hasown: 2.0.2 /is-data-descriptor@1.0.1: resolution: {integrity: sha512-bc4NlCDiCr28U4aEsQ3Qs2491gVq4V8G7MQyws968ImqjKuYtTJXrl7Vq7jsN7Ly/C3xj5KWFrY7sHNeDkAzXw==} engines: {node: '>= 0.4'} dependencies: - hasown: 2.0.0 + hasown: 2.0.2 + dev: true + + /is-data-view@1.0.1: + resolution: {integrity: sha512-AHkaJrsUVW6wq6JS8y3JnM/GJF/9cf+k20+iDzlSaJrinEo5+7vRiteOSwBhHRiAyQATN1AmY4hwzxJKPmYf+w==} + engines: {node: '>= 0.4'} + dependencies: + is-typed-array: 1.1.13 dev: true /is-date-object@1.0.5: resolution: {integrity: sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==} engines: {node: '>= 0.4'} dependencies: - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /is-decimal@1.0.4: @@ -7096,8 +6967,8 @@ packages: resolution: {integrity: sha512-z7CMFGNrENq5iFB9Bqo64Xk6Y9sg+epq1myIcdHaGnbMTYOxvzsEtdYqQUylB7LxfkvgrrjP32T6Ywciio9UIQ==} dev: true - /is-negative-zero@2.0.2: - resolution: {integrity: sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==} + /is-negative-zero@2.0.3: + resolution: {integrity: sha512-5KoIu2Ngpyek75jXodFvnafB6DJgr3u8uuK0LEZJjrU19DrMD3EVERaR8sjz8CCGgpZvxPl9SuE1GMVPFHx1mw==} engines: {node: '>= 0.4'} dev: true @@ -7105,7 +6976,7 @@ packages: resolution: {integrity: sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==} engines: {node: '>= 0.4'} dependencies: - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /is-number@3.0.0: @@ -7149,8 +7020,8 @@ packages: resolution: {integrity: sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - has-tostringtag: 1.0.0 + call-bind: 1.0.7 + has-tostringtag: 1.0.2 dev: true /is-regexp@1.0.0: @@ -7158,10 +7029,11 @@ packages: engines: {node: '>=0.10.0'} dev: true - /is-shared-array-buffer@1.0.2: - resolution: {integrity: sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==} + /is-shared-array-buffer@1.0.3: + resolution: {integrity: sha512-nA2hv5XIhLR3uVzDDfCIknerhx8XUKnstuOERPNNIinXG7v9u+ohXF67vxm4TPTEPU6lm61ZkwP3c9PCB97rhg==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 dev: true /is-stream@2.0.1: @@ -7173,7 +7045,7 @@ packages: resolution: {integrity: sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==} engines: {node: '>= 0.4'} dependencies: - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /is-symbol@1.0.4: @@ -7183,11 +7055,11 @@ packages: has-symbols: 1.0.3 dev: true - /is-typed-array@1.1.12: - resolution: {integrity: sha512-Z14TF2JNG8Lss5/HMqt0//T9JeHXttXy5pH/DBU4vi98ozO2btxzq9MwYDZYnKwU8nRsz/+GVFVRDq3DkVuSPg==} + /is-typed-array@1.1.13: + resolution: {integrity: sha512-uZ25/bUAlUY5fR4OKT4rZQEBrzQWYV9ZJYGGsUmEJ6thodVJ1HX64ePQ6Z0qPWP+m+Uq6e9UugrE38jeYsDSMw==} engines: {node: '>= 0.4'} dependencies: - which-typed-array: 1.1.13 + which-typed-array: 1.1.15 dev: true /is-typedarray@1.0.0: @@ -7201,7 +7073,7 @@ packages: /is-weakref@1.0.2: resolution: {integrity: sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 dev: true /is-windows@1.0.2: @@ -7259,7 +7131,7 @@ packages: resolution: {integrity: sha512-BXgQl9kf4WTCPCCpmFGoJkz/+uhvm7h7PFKUYxh7qarQd3ER33vHG//qaE8eN25l07YqZPpHXU9I09l/RD5aGQ==} engines: {node: '>=8'} dependencies: - '@babel/core': 7.23.7 + '@babel/core': 7.26.0 '@istanbuljs/schema': 0.1.3 istanbul-lib-coverage: 3.2.2 semver: 6.3.1 @@ -7292,27 +7164,27 @@ packages: resolution: {integrity: sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==} engines: {node: '>=10'} dependencies: - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) istanbul-lib-coverage: 3.2.2 source-map: 0.6.1 transitivePeerDependencies: - supports-color dev: true - /istanbul-reports@3.1.6: - resolution: {integrity: sha512-TLgnMkKg3iTDsQ9PbPTdpfAK2DzjF9mqUG7RMgcQl8oFjad8ob4laGxv5XV5U9MAfx8D6tSJiUyuAwzLicaxlg==} + /istanbul-reports@3.1.7: + resolution: {integrity: sha512-BewmUXImeuRk2YY0PVbxgKAysvhRPUQE0h5QRM++nVWyubKGV0l8qQ5op8+B2DOmwSe63Jivj0BjkPQVf8fP5g==} engines: {node: '>=8'} dependencies: html-escaper: 2.0.2 istanbul-lib-report: 3.0.1 dev: true - /jake@10.8.7: - resolution: {integrity: sha512-ZDi3aP+fG/LchyBzUM804VjddnwfSfsdeYkwt8NcbKRvo4rFkjhs456iLFn3k2ZUWvNe4i48WACDbza8fhq2+w==} + /jake@10.9.2: + resolution: {integrity: sha512-2P4SQ0HrLQ+fw6llpLnOaGAvN2Zu6778SJMrCUwns4fOoG9ayrTiZk3VV8sCPkVZF8ab0zksVpS8FDY5pRCNBA==} engines: {node: '>=10'} hasBin: true dependencies: - async: 3.2.5 + async: 3.2.6 chalk: 4.1.2 filelist: 1.0.4 minimatch: 3.1.2 @@ -7336,27 +7208,31 @@ packages: argparse: 2.0.1 dev: true - /jscodeshift@0.14.0(@babel/preset-env@7.23.8): + /jsbn@1.1.0: + resolution: {integrity: sha512-4bYVV3aAMtDTTu4+xsDYa6sy9GyJ69/amsu9sYF2zqjiEoZA5xJi3BrfX3uY+/IekIu7MwdObdbDWpoZdBv3/A==} + dev: true + + /jscodeshift@0.14.0(@babel/preset-env@7.26.0): resolution: {integrity: sha512-7eCC1knD7bLUPuSCwXsMZUH51O8jIcoVyKtI6P0XM0IVzlGjckPy3FIwQlorzbN0Sg79oK+RlohN32Mqf/lrYA==} hasBin: true peerDependencies: '@babel/preset-env': ^7.1.6 dependencies: - '@babel/core': 7.23.7 - '@babel/parser': 7.23.6 - '@babel/plugin-proposal-class-properties': 7.18.6(@babel/core@7.23.7) - '@babel/plugin-proposal-nullish-coalescing-operator': 7.18.6(@babel/core@7.23.7) - '@babel/plugin-proposal-optional-chaining': 7.21.0(@babel/core@7.23.7) - '@babel/plugin-transform-modules-commonjs': 7.23.3(@babel/core@7.23.7) - '@babel/preset-env': 7.23.8(@babel/core@7.24.7) - '@babel/preset-flow': 7.23.3(@babel/core@7.23.7) - '@babel/preset-typescript': 7.23.3(@babel/core@7.23.7) - '@babel/register': 7.23.7(@babel/core@7.23.7) - babel-core: 7.0.0-bridge.0(@babel/core@7.23.7) + '@babel/core': 7.26.0 + '@babel/parser': 7.26.2 + '@babel/plugin-proposal-class-properties': 7.18.6(@babel/core@7.26.0) + '@babel/plugin-proposal-nullish-coalescing-operator': 7.18.6(@babel/core@7.26.0) + '@babel/plugin-proposal-optional-chaining': 7.21.0(@babel/core@7.26.0) + '@babel/plugin-transform-modules-commonjs': 7.25.9(@babel/core@7.26.0) + '@babel/preset-env': 7.26.0(@babel/core@7.26.0) + '@babel/preset-flow': 7.25.9(@babel/core@7.26.0) + '@babel/preset-typescript': 7.26.0(@babel/core@7.26.0) + '@babel/register': 7.25.9(@babel/core@7.26.0) + babel-core: 7.0.0-bridge.0(@babel/core@7.26.0) chalk: 4.1.2 - flow-parser: 0.227.0 + flow-parser: 0.251.1 graceful-fs: 4.2.11 - micromatch: 4.0.5 + micromatch: 4.0.8 neo-async: 2.6.2 node-dir: 0.1.17 recast: 0.21.5 @@ -7366,14 +7242,9 @@ packages: - supports-color dev: false - /jsesc@0.5.0: - resolution: {integrity: sha512-uZz5UnB7u4T9LvwmFqXii7pZSouaRPorGs5who1Ip7VO0wxanFvBL7GkM6dTHlgX+jhBApRetaWpnDabOeTcnA==} - hasBin: true - dev: false - - /jsesc@2.5.2: - resolution: {integrity: sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==} - engines: {node: '>=4'} + /jsesc@3.0.2: + resolution: {integrity: sha512-xKqzzWXDttJuOcawBt4KnKHHIf5oQ/Cxax+0PWFG+DFDgHNAdi+TXECADI+RYiFUMmx8792xsMbbgXj4CwnP4g==} + engines: {node: '>=6'} hasBin: true /json-buffer@3.0.1: @@ -7437,7 +7308,7 @@ packages: lodash.isstring: 4.0.1 lodash.once: 4.1.1 ms: 2.1.3 - semver: 7.5.4 + semver: 7.6.3 dev: false /just-extend@4.2.1: @@ -7474,8 +7345,8 @@ packages: safe-buffer: 5.2.1 dev: false - /katex@0.16.10: - resolution: {integrity: sha512-ZiqaC04tp2O5utMsl2TEZTXxa6WSC4yo0fv5ML++D3QZv/vx2Mct0mTlRx3O+uUkjfuAgOkzsCmq5MiUEsDDdA==} + /katex@0.16.11: + resolution: {integrity: sha512-RQrI8rlHY92OLf3rho/Ts8i/XvjgguEjOkO1BEXcU3N8BqPpSzBNwV/G0Ukr+P/l3ivvJUE/Fa/CwbS6HesGNQ==} hasBin: true dependencies: commander: 8.3.0 @@ -7543,11 +7414,11 @@ packages: colorette: 1.4.0 commander: 8.3.0 cosmiconfig: 7.1.0 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) enquirer: 2.4.1 execa: 5.1.1 listr2: 3.14.0(enquirer@2.4.1) - micromatch: 4.0.5 + micromatch: 4.0.8 normalize-path: 3.0.0 please-upgrade-node: 3.2.0 string-argv: 0.3.1 @@ -7569,7 +7440,7 @@ packages: enquirer: 2.4.1 log-update: 4.0.0 p-map: 4.0.0 - rfdc: 1.3.1 + rfdc: 1.4.1 rxjs: 7.8.1 through: 2.3.8 wrap-ansi: 7.0.0 @@ -7681,9 +7552,9 @@ packages: engines: {node: '>=8.0'} dependencies: date-format: 4.0.14 - debug: 4.3.4(supports-color@8.1.1) - flatted: 3.2.9 - rfdc: 1.3.1 + debug: 4.3.7(supports-color@8.1.1) + flatted: 3.3.1 + rfdc: 1.4.1 streamroller: 3.1.5 transitivePeerDependencies: - supports-color @@ -7698,7 +7569,7 @@ packages: /lower-case@2.0.2: resolution: {integrity: sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: true /lowlight@1.20.0: @@ -7708,9 +7579,8 @@ packages: highlight.js: 10.7.3 dev: false - /lru-cache@10.1.0: - resolution: {integrity: sha512-/1clY/ui8CzjKFyjdvwPWJUYKiFVXG2I2cY0ssG7h4+hwk+XOIX7ZSG9Q7TW8TW3Kp3BUSqgFWBLgL4PJ+Blag==} - engines: {node: 14 || >=16.14} + /lru-cache@10.4.3: + resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==} dev: false /lru-cache@5.1.1: @@ -7753,7 +7623,7 @@ packages: resolution: {integrity: sha512-hXdUTZYIVOt1Ex//jAQi+wTZZpUpwBj/0QsOzqegb3rGMMeJiSEu5xLHnYfBrRV4RH2+OCSOO95Is/7x1WJ4bw==} engines: {node: '>=10'} dependencies: - semver: 7.5.4 + semver: 7.6.3 dev: true /make-error@1.3.6: @@ -7776,7 +7646,7 @@ packages: minipass-fetch: 2.1.2 minipass-flush: 1.0.5 minipass-pipeline: 1.2.4 - negotiator: 0.6.3 + negotiator: 0.6.4 promise-retry: 2.0.1 socks-proxy-agent: 7.0.0 ssri: 9.0.1 @@ -7814,7 +7684,7 @@ packages: resolution: {integrity: sha512-4xTO/M8c82qBcnQc1tgpNtubGUW/Y1tBQ1B0i5CtSoelOLKFYlElIr3bvgREYYO5iRqbMY1YuqZng0GVOI8Qww==} dependencies: '@types/mdast': 3.0.15 - '@types/unist': 2.0.10 + '@types/unist': 2.0.11 decode-named-character-reference: 1.0.2 mdast-util-to-string: 3.2.0 micromark: 3.2.0 @@ -7856,8 +7726,8 @@ packages: readable-stream: 2.3.8 dev: true - /merge-descriptors@1.0.1: - resolution: {integrity: sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==} + /merge-descriptors@1.0.3: + resolution: {integrity: sha512-gaNvAS7TZ897/rVaZ0nMtAyxNyi/pdbjbAwUpFQpN70GqnVfOiXpeUUMKRBmzXaSQ8DdTX4/0ms62r2K+hE6mQ==} dev: false /merge-stream@2.0.0: @@ -7875,20 +7745,20 @@ packages: '@braintree/sanitize-url': 6.0.4 '@types/d3-scale': 4.0.8 '@types/d3-scale-chromatic': 3.0.3 - cytoscape: 3.28.1 - cytoscape-cose-bilkent: 4.1.0(cytoscape@3.28.1) + cytoscape: 3.30.3 + cytoscape-cose-bilkent: 4.1.0(cytoscape@3.30.3) d3: 7.9.0 d3-sankey: 0.12.3 dagre-d3-es: 7.0.10 - dayjs: 1.11.7 + dayjs: 1.11.13 dompurify: 3.0.6 - elkjs: 0.9.2 - katex: 0.16.10 + elkjs: 0.9.3 + katex: 0.16.11 khroma: 2.1.0 lodash-es: 4.17.21 mdast-util-from-markdown: 1.3.1 non-layered-tidy-tree-layout: 2.0.2 - stylis: 4.3.1 + stylis: 4.3.4 ts-dedent: 2.2.0 uuid: 9.0.1 web-worker: 1.3.0 @@ -8060,7 +7930,7 @@ packages: resolution: {integrity: sha512-uD66tJj54JLYq0De10AhWycZWGQNUvDI55xPgk2sQM5kn1JYlhbCMTtEeT27+vAhW2FBQxLlOmS3pmA7/2z4aA==} dependencies: '@types/debug': 4.1.12 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) decode-named-character-reference: 1.0.2 micromark-core-commonmark: 1.1.0 micromark-factory-space: 1.1.0 @@ -8101,11 +7971,11 @@ packages: - supports-color dev: true - /micromatch@4.0.5: - resolution: {integrity: sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==} + /micromatch@4.0.8: + resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} engines: {node: '>=8.6'} dependencies: - braces: 3.0.2 + braces: 3.0.3 picomatch: 2.3.1 /miller-rabin@4.0.1: @@ -8146,7 +8016,7 @@ packages: prop-types: ^15.0.0 react: ^0.14.0 || ^15.0.0 || ^16.0.0 || ^17.0.0 dependencies: - '@babel/runtime': 7.23.8 + '@babel/runtime': 7.26.0 prop-types: 15.8.1 react: 17.0.2 tiny-warning: 1.0.3 @@ -8171,8 +8041,8 @@ packages: brace-expansion: 2.0.1 dev: true - /minimatch@9.0.3: - resolution: {integrity: sha512-RHiac9mvaRw0x3AYRgDC1CxAP7HTcNrrECeA8YYJeWnpo+2Q5CegtZjaotWTWxDG3UeGA1coE05iH1mPjT/2mg==} + /minimatch@9.0.5: + resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} engines: {node: '>=16 || 14 >=14.17'} dependencies: brace-expansion: 2.0.1 @@ -8267,7 +8137,7 @@ packages: peerDependencies: mocha: '>=3.1.2' dependencies: - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) lodash: 4.17.21 mocha: 10.0.0 transitivePeerDependencies: @@ -8337,12 +8207,13 @@ packages: /ms@2.1.2: resolution: {integrity: sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==} + dev: true /ms@2.1.3: resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} - /nan@2.18.0: - resolution: {integrity: sha512-W7tfG7vMOGtD30sHoZSSc/JVYiyDPEyQVso/Zz+/uQd0B0L46gtC+pHha5FFMRpil6fm/AoEcRWyOVi4+E/f8w==} + /nan@2.22.0: + resolution: {integrity: sha512-nbajikzWTMwsW+eSsNm3QwlOs7het9gGJU5dDZzRTQGk03vyBOauxgI4VakDzE0PtsGTmXPsXTbbjVhRwR5mpw==} dev: true /nanoid@3.3.3: @@ -8383,6 +8254,12 @@ packages: /negotiator@0.6.3: resolution: {integrity: sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==} engines: {node: '>= 0.6'} + dev: false + + /negotiator@0.6.4: + resolution: {integrity: sha512-myRT3DiWPHqho5PrJaIRyaMv2kgYf0mUVgBNOYMuCH5Ki1yEiQaf/ZJuQ62nvpc44wL5WDbTX7yGJi1Neevw8w==} + engines: {node: '>= 0.6'} + dev: true /neo-async@2.6.2: resolution: {integrity: sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==} @@ -8392,21 +8269,25 @@ packages: resolution: {integrity: sha512-mc/caHeUcdjnC/boPWJefDr4KUIWQNv+tlnFnJd38QMou86QtxQzBJfxgGRzvx8jazYRqrVlaHarfO72uNxPOg==} dev: false + /next-tick@1.1.0: + resolution: {integrity: sha512-CXdUiJembsNjuToQvxayPZF9Vqht7hewsvy2sOWafLvi2awflj9mOC6bHIg50orX8IJvWKY9wYQ/zB2kogPslQ==} + dev: false + /nise@4.1.0: resolution: {integrity: sha512-eQMEmGN/8arp0xsvGoQ+B1qvSkR73B1nWSCh7nOt5neMCtwcQVYQGdzQMhcNscktTsWB54xnlSQFzOAPJD8nXA==} dependencies: '@sinonjs/commons': 1.8.6 '@sinonjs/fake-timers': 6.0.1 - '@sinonjs/text-encoding': 0.7.2 + '@sinonjs/text-encoding': 0.7.3 just-extend: 4.2.1 - path-to-regexp: 1.8.0 + path-to-regexp: 1.9.0 dev: true /no-case@3.0.4: resolution: {integrity: sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg==} dependencies: lower-case: 2.0.2 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /node-dir@0.1.17: @@ -8416,18 +8297,6 @@ packages: minimatch: 3.1.2 dev: false - /node-fetch@2.6.7: - resolution: {integrity: sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==} - engines: {node: 4.x || >=6.0.0} - peerDependencies: - encoding: ^0.1.0 - peerDependenciesMeta: - encoding: - optional: true - dependencies: - whatwg-url: 5.0.0 - dev: false - /node-fetch@2.7.0: resolution: {integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==} engines: {node: 4.x || >=6.0.0} @@ -8440,8 +8309,8 @@ packages: whatwg-url: 5.0.0 dev: false - /node-gyp-build@4.8.0: - resolution: {integrity: sha512-u6fs2AEUljNho3EYTJNBfImO5QTo/J/1Etd+NVdCj7qWKUSN/bSLkZwhDv7I+w/MSC6qJ4cknepkAYykDdK8og==} + /node-gyp-build@4.8.2: + resolution: {integrity: sha512-IRUxE4BVsHWXkV/SFOut4qTlagw2aM8T5/vnTsmrHJvVoKueJHRc/JaFND7QDDc61kLYUJ6qlZM3sqTSyx2dTw==} hasBin: true dev: false @@ -8458,8 +8327,8 @@ packages: nopt: 6.0.0 npmlog: 6.0.2 rimraf: 3.0.2 - semver: 7.5.4 - tar: 6.2.0 + semver: 7.5.2 + tar: 6.2.1 which: 2.0.2 transitivePeerDependencies: - bluebird @@ -8473,8 +8342,8 @@ packages: process-on-spawn: 1.0.0 dev: true - /node-releases@2.0.14: - resolution: {integrity: sha512-y10wOWt8yZpqXmOgRo77WaHEmhYQYGNA6y421PKsKYWEK8aW+cqAphborZDhqfyKrbZEN92CN1X2KbafY2s7Yw==} + /node-releases@2.0.18: + resolution: {integrity: sha512-d9VeXT4SJ7ZeOqGX6R5EM022wpL+eWPooLI+5UpWn2jCT1aosUQEhQP214x33Wkwx3JQMvIm+tIoVOdodFS40g==} /node-rsa@1.1.1: resolution: {integrity: sha512-Jd4cvbJMryN21r5HgxQOpMEqv+ooke/korixNNK3mGqfGJmy0M77WDDzo/05969+OkMy3XW1UuZsSmW9KQm7Fw==} @@ -8513,6 +8382,7 @@ packages: /npmlog@6.0.2: resolution: {integrity: sha512-/vBvz5Jfr9dT/aFWd0FIRf+T/Q2WBsLENygUaFUqstqsycmZAP/t5BvFJTK0viFmSUxiUKTUplWy5vt+rvKIxg==} engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} + deprecated: This package is no longer supported. dependencies: are-we-there-yet: 3.0.1 console-control-strings: 1.1.0 @@ -8547,7 +8417,7 @@ packages: istanbul-lib-processinfo: 2.0.3 istanbul-lib-report: 3.0.1 istanbul-lib-source-maps: 4.0.1 - istanbul-reports: 3.1.6 + istanbul-reports: 3.1.7 make-dir: 3.1.0 node-preload: 0.2.1 p-map: 3.0.0 @@ -8575,8 +8445,9 @@ packages: kind-of: 3.2.2 dev: true - /object-inspect@1.13.1: - resolution: {integrity: sha512-5qoj1RUiKOMsCCNLV1CBiPYE10sziTsnmNxkAI/rZhiD63CF7IqdFGC/XzjWjpSgLf0LxXX3bDFIh0E18f6UhQ==} + /object-inspect@1.13.2: + resolution: {integrity: sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==} + engines: {node: '>= 0.4'} /object-keys@1.1.1: resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==} @@ -8594,7 +8465,7 @@ packages: resolution: {integrity: sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 has-symbols: 1.0.3 object-keys: 1.1.1 @@ -8607,26 +8478,26 @@ packages: isobject: 3.0.1 dev: true - /object.values@1.1.7: - resolution: {integrity: sha512-aU6xnDFYT3x17e/f0IiiwlGPTy2jzMySGfUB4fq6z7CV8l85CWHDk5ErhyhpfDHhrOMwGFhSQkhMGHaIotA6Ng==} + /object.values@1.2.0: + resolution: {integrity: sha512-yBYjY9QX2hnRmZHAjG/f13MzmBzxzYgQhFrke06TTyKY5zSTEqkOeukBzIdVA3j3ulu8Qa3MbVFShV7T2RmGtQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-object-atoms: 1.0.0 dev: true - /office-addin-manifest@1.13.2: - resolution: {integrity: sha512-+IBmcMbgoAsjE7FOO15HeVQD91GbWd3mcdmq43xulFaI5uC5bYhw70TI7XEUUYRrPU1iLFGbdYNHvsjFfNdqzQ==} + /office-addin-manifest@1.13.1: + resolution: {integrity: sha512-uIYpEE3tLr3grchqx9GOIHl3P+/4EqQ/Mrx4u5y7EsFzB5YqSIjwsvw6/x6OLrEhD5+0qtEh4fcAJVtfMPSpmw==} hasBin: true dependencies: - '@microsoft/teams-manifest': 0.1.4 - adm-zip: 0.5.12 + '@microsoft/teams-manifest': 0.1.6 + adm-zip: 0.5.16 chalk: 2.4.2 commander: 6.2.1 fs-extra: 7.0.1 - node-fetch: 2.6.7 - office-addin-usage-data: 1.6.11 + node-fetch: 2.7.0 + office-addin-usage-data: 1.6.14 path: 0.12.7 uuid: 8.3.2 xml2js: 0.5.0 @@ -8634,8 +8505,8 @@ packages: - encoding dev: false - /office-addin-usage-data@1.6.11: - resolution: {integrity: sha512-8n86S1PkAktGFtrM2kYVX8zbgo/i8VyH6RzO3ApX6GeFOeTWJPtYVWmGs7WklkoTlZGTwDjfiR+noB0vWA9Vpg==} + /office-addin-usage-data@1.6.14: + resolution: {integrity: sha512-V3TQoMR7McjJ62TWQeRnZqVp1mpjk1bbazvea/pqCJod5zggjlgDspjL5NJzTZc4+MwwJPR8k5Yr5Me+OcRLQw==} hasBin: true dependencies: applicationinsights: 1.8.10 @@ -8672,16 +8543,16 @@ packages: is-wsl: 2.2.0 dev: false - /optionator@0.9.3: - resolution: {integrity: sha512-JjCoypp+jKn1ttEFExxhetCKeJt9zhAgAve5FXHixTvFDW/5aEktX9bufBKLRRMdU7bNtpLfcGu94B3cdEJgjg==} + /optionator@0.9.4: + resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} engines: {node: '>= 0.8.0'} dependencies: - '@aashutoshrathi/word-wrap': 1.2.6 deep-is: 0.1.4 fast-levenshtein: 2.0.6 levn: 0.4.1 prelude-ls: 1.2.1 type-check: 0.4.0 + word-wrap: 1.2.5 dev: true /p-limit@2.3.0: @@ -8772,21 +8643,27 @@ packages: resolution: {integrity: sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==} engines: {node: '>=8'} dependencies: - '@babel/code-frame': 7.23.5 + '@babel/code-frame': 7.26.2 error-ex: 1.3.2 json-parse-even-better-errors: 2.3.1 lines-and-columns: 1.2.4 dev: true - /parse5-htmlparser2-tree-adapter@7.0.0: - resolution: {integrity: sha512-B77tOZrqqfUfnVcOrUvfdLbz4pu4RopLD/4vmu3HUPswwTA8OH0EMW9BlWR2B0RCoiZRAHEUu7IxeP1Pd1UU+g==} + /parse5-htmlparser2-tree-adapter@7.1.0: + resolution: {integrity: sha512-ruw5xyKs6lrpo9x9rCZqZZnIUntICjQAd0Wsmp396Ul9lN/h+ifgVV1x1gZHi8euej6wTfpqX8j+BFQxF0NS/g==} dependencies: domhandler: 5.0.3 - parse5: 7.1.2 + parse5: 7.2.1 dev: true - /parse5@7.1.2: - resolution: {integrity: sha512-Czj1WaSVpaoj0wbhMzLmWD69anp2WH7FXMB9n1Sy8/ZFF9jolSQVMu1Ij5WIyGmcBmhk7EOndpO4mIpihVqAXw==} + /parse5-parser-stream@7.1.2: + resolution: {integrity: sha512-JyeQc9iwFLn5TbvvqACIF/VXG6abODeB3Fwmv/TGdLk2LfbWkaySGY72at4+Ty7EkPZj854u4CrICqNk2qIbow==} + dependencies: + parse5: 7.2.1 + dev: true + + /parse5@7.2.1: + resolution: {integrity: sha512-BuBYQYlv1ckiPdQi/ohiivi9Sagc9JG+Ozs0r7b/0iK3sKmrb0b9FdWdBbOdx6hBCM/F9Ir82ofnBhtZOjCRPQ==} dependencies: entities: 4.5.0 dev: true @@ -8823,20 +8700,20 @@ packages: /path-parse@1.0.7: resolution: {integrity: sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==} - /path-scurry@1.10.1: - resolution: {integrity: sha512-MkhCqzzBEpPvxxQ71Md0b1Kk51W01lrYvlMzSUaIzNsODdd7mqhiimSZlr+VegAz5Z6Vzt9Xg2ttE//XBhH3EQ==} - engines: {node: '>=16 || 14 >=14.17'} + /path-scurry@1.11.1: + resolution: {integrity: sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA==} + engines: {node: '>=16 || 14 >=14.18'} dependencies: - lru-cache: 10.1.0 + lru-cache: 10.4.3 minipass: 5.0.0 dev: false - /path-to-regexp@0.1.7: - resolution: {integrity: sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==} + /path-to-regexp@0.1.10: + resolution: {integrity: sha512-7lf7qcQidTku0Gu3YDPc8DJ1q7OOucfa/BSsIwjuh56VU7katFvuM8hULfkwB3Fns/rsVF7PwPKVw1sl5KQS9w==} dev: false - /path-to-regexp@1.8.0: - resolution: {integrity: sha512-n43JRhlUKUAlibEJhPeir1ncUID16QnEjNpwzNdO3Lm4ywrBpBZ5oLD0I6br9evr1Y9JTqwRtAh7JLoOzAQdVA==} + /path-to-regexp@1.9.0: + resolution: {integrity: sha512-xIp7/apCFJuUHdDLWe8O1HIkb0kQrOMb/0u6FXQjemHn/ii5LrIzU6bdECnsiTF/GjZkMEKg1xdiZwNqDYlZ6g==} dependencies: isarray: 0.0.1 dev: true @@ -8857,13 +8734,18 @@ packages: resolution: {integrity: sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ==} dev: true - /picocolors@1.0.1: - resolution: {integrity: sha512-anP1Z8qwhkbmu7MFP5iTt+wQKXgwzf7zTyGlcdzabySa9vd0Xt392U0rVmz9poOaBj0uHJKyyo9/upk0HrEQew==} + /picocolors@1.1.1: + resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} /picomatch@2.3.1: resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} engines: {node: '>=8.6'} + /picomatch@4.0.2: + resolution: {integrity: sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==} + engines: {node: '>=12'} + dev: true + /pify@4.0.1: resolution: {integrity: sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==} engines: {node: '>=6'} @@ -8899,13 +8781,18 @@ packages: engines: {node: '>=0.10.0'} dev: true - /postcss@8.4.39: - resolution: {integrity: sha512-0vzE+lAiG7hZl1/9I8yzKLx3aR9Xbof3fBHKunvMfOCYAtMhrsnccJY2iTURb9EZd5+pLuiNV9/c/GZJOHsgIw==} + /possible-typed-array-names@1.0.0: + resolution: {integrity: sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==} + engines: {node: '>= 0.4'} + dev: true + + /postcss@8.4.47: + resolution: {integrity: sha512-56rxCq7G/XfB4EkXq9Egn5GCqugWvDFjafDOThIdMBsI15iqPqR5r15TfSr1YPYeEI19YeaXMCbY6u88Y76GLQ==} engines: {node: ^10 || ^12 || >=14} dependencies: nanoid: 3.3.7 - picocolors: 1.0.1 - source-map-js: 1.2.0 + picocolors: 1.1.1 + source-map-js: 1.2.1 dev: true /postinstall-build@2.1.3: @@ -9019,12 +8906,13 @@ packages: /punycode@2.3.1: resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} engines: {node: '>=6'} + dev: true - /qs@6.11.0: - resolution: {integrity: sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==} + /qs@6.13.0: + resolution: {integrity: sha512-+38qI9SOr8tfZ4QmJNplMUxqjbe7LKvvZgWdExBOmd+egZTtjLB67Gu0HRX3u/XOq7UU2Nx6nsjvS16Z9uwfpg==} engines: {node: '>=0.6'} dependencies: - side-channel: 1.0.4 + side-channel: 1.0.6 dev: false /query-string@6.14.1: @@ -9113,7 +9001,7 @@ packages: intl-messageformat: 9.5.3 intl-messageformat-parser: 6.4.3 react: 17.0.2 - tslib: 2.6.2 + tslib: 2.8.1 typescript: 4.7.4 dev: true @@ -9130,13 +9018,13 @@ packages: peerDependencies: react: '>=15' dependencies: - '@babel/runtime': 7.23.8 + '@babel/runtime': 7.26.0 history: 4.10.1 loose-envify: 1.4.0 prop-types: 15.8.1 react: 17.0.2 react-router: 5.2.0(react@17.0.2) - tiny-invariant: 1.3.1 + tiny-invariant: 1.3.3 tiny-warning: 1.0.3 dev: true @@ -9145,16 +9033,16 @@ packages: peerDependencies: react: '>=15' dependencies: - '@babel/runtime': 7.23.8 + '@babel/runtime': 7.26.0 history: 4.10.1 hoist-non-react-statics: 3.3.2 loose-envify: 1.4.0 mini-create-react-context: 0.4.1(prop-types@15.8.1)(react@17.0.2) - path-to-regexp: 1.8.0 + path-to-regexp: 1.9.0 prop-types: 15.8.1 react: 17.0.2 react-is: 16.13.1 - tiny-invariant: 1.3.1 + tiny-invariant: 1.3.3 tiny-warning: 1.0.3 dev: true @@ -9163,7 +9051,7 @@ packages: peerDependencies: react: '>= 0.14.0' dependencies: - '@babel/runtime': 7.23.8 + '@babel/runtime': 7.26.0 highlight.js: 10.7.3 lowlight: 1.20.0 prismjs: 1.29.0 @@ -9229,7 +9117,7 @@ packages: ast-types: 0.14.2 esprima: 4.0.1 source-map: 0.6.1 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /recast@0.21.5: @@ -9239,7 +9127,7 @@ packages: ast-types: 0.15.2 esprima: 4.0.1 source-map: 0.6.1 - tslib: 2.6.2 + tslib: 2.8.1 dev: false /reflect-metadata@0.1.13: @@ -9254,8 +9142,8 @@ packages: prismjs: 1.27.0 dev: false - /regenerate-unicode-properties@10.1.1: - resolution: {integrity: sha512-X007RyZLsCJVVrjgEFVpLUTZwyOZk3oiL75ZcuYjlIWd6rNJtOjkBwQc5AsRrpbKVkxN6sklw/k/9m2jJYOf8Q==} + /regenerate-unicode-properties@10.2.0: + resolution: {integrity: sha512-DqHn3DwbmmPVzeKj9woBadqmXxLvQoQIwu7nopMc72ztvxVmVk2SBhSnx67zuye5TP+lJsb/TBQsjLKhnDf3MA==} engines: {node: '>=4'} dependencies: regenerate: 1.4.2 @@ -9271,7 +9159,7 @@ packages: /regenerator-transform@0.15.2: resolution: {integrity: sha512-hfMp2BoF0qOk3uc5V20ALGDS2ddjQaLrdl7xrGXvAIow7qeWRM2VA2HuCHkUKk9slq3VwEwLNK3DFBqDfPGYtg==} dependencies: - '@babel/runtime': 7.23.8 + '@babel/runtime': 7.26.0 dev: false /regex-not@1.0.2: @@ -9282,13 +9170,14 @@ packages: safe-regex: 1.1.0 dev: true - /regexp.prototype.flags@1.5.1: - resolution: {integrity: sha512-sy6TXMN+hnP/wMy+ISxg3krXx7BAtWVO4UouuCN/ziM9UEne0euamVNafDfvC83bRNr95y0V5iijeDQFUNpvrg==} + /regexp.prototype.flags@1.5.3: + resolution: {integrity: sha512-vqlC04+RQoFalODCbCumG2xIOvapzVMHwsyIGM/SIE8fRhFFsXeH8/QQ+s0T0kDAhKc4k30s73/0ydkHQz6HlQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - set-function-name: 2.0.1 + es-errors: 1.3.0 + set-function-name: 2.0.2 dev: true /regexpp@3.2.0: @@ -9296,23 +9185,27 @@ packages: engines: {node: '>=8'} dev: true - /regexpu-core@5.3.2: - resolution: {integrity: sha512-RAM5FlZz+Lhmo7db9L298p2vHP5ZywrVXmVXpmAD9GuL5MPH6t9ROw1iA/wfHkQ76Qe7AaPF0nGuim96/IrQMQ==} + /regexpu-core@6.1.1: + resolution: {integrity: sha512-k67Nb9jvwJcJmVpw0jPttR1/zVfnKf8Km0IPatrU/zJ5XeG3+Slx0xLXs9HByJSzXzrlz5EDvN6yLNMDc2qdnw==} engines: {node: '>=4'} dependencies: - '@babel/regjsgen': 0.8.0 regenerate: 1.4.2 - regenerate-unicode-properties: 10.1.1 - regjsparser: 0.9.1 + regenerate-unicode-properties: 10.2.0 + regjsgen: 0.8.0 + regjsparser: 0.11.2 unicode-match-property-ecmascript: 2.0.0 - unicode-match-property-value-ecmascript: 2.1.0 + unicode-match-property-value-ecmascript: 2.2.0 + dev: false + + /regjsgen@0.8.0: + resolution: {integrity: sha512-RvwtGe3d7LvWiDQXeQw8p5asZUmfU1G/l6WbUXeHta7Y2PEIvBTwH6E2EfmYUK8pxcxEdEmaomqyp0vZZ7C+3Q==} dev: false - /regjsparser@0.9.1: - resolution: {integrity: sha512-dQUtn90WanSNl+7mQKcXAgZxvUe7Z0SqXlgzv0za4LwiUhyzBC58yQO3liFoUgu8GiJVInAhJjkj1N0EtQ5nkQ==} + /regjsparser@0.11.2: + resolution: {integrity: sha512-3OGZZ4HoLJkkAZx/48mTXJNlmqTGOzc0o9OWQPuWpkOlXXPbyN6OafCcoXUnBqE2D3f/T5L+pWc1kdEmnfnRsA==} hasBin: true dependencies: - jsesc: 0.5.0 + jsesc: 3.0.2 dev: false /release-zalgo@1.0.0: @@ -9368,7 +9261,7 @@ packages: resolution: {integrity: sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw==} hasBin: true dependencies: - is-core-module: 2.13.1 + is-core-module: 2.15.1 path-parse: 1.0.7 supports-preserve-symlinks-flag: 1.0.0 @@ -9395,11 +9288,12 @@ packages: engines: {iojs: '>=1.0.0', node: '>=0.10.0'} dev: true - /rfdc@1.3.1: - resolution: {integrity: sha512-r5a3l5HzYlIC68TpmYKlxWjmOP6wiPJ1vWv2HeLhNsRZMrCkxeqxiHlQ21oXmQ4F3SiryXBHhAD7JZqvOJjFmg==} + /rfdc@1.4.1: + resolution: {integrity: sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==} /rimraf@2.6.3: resolution: {integrity: sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==} + deprecated: Rimraf versions prior to v4 are no longer supported hasBin: true dependencies: glob: 7.2.3 @@ -9407,38 +9301,40 @@ packages: /rimraf@3.0.2: resolution: {integrity: sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==} + deprecated: Rimraf versions prior to v4 are no longer supported hasBin: true dependencies: glob: 7.2.3 - dev: true /robust-predicates@3.0.2: resolution: {integrity: sha512-IXgzBWvWQwE6PrDI05OvmXUIruQTcoMDzRsOd5CDvHCVLcLHMTSYvOK5Cm46kWqlV3yAbuSpBZdJ5oP5OUoStg==} dev: true - /rollup@4.18.0: - resolution: {integrity: sha512-QmJz14PX3rzbJCN1SG4Xe/bAAX2a6NpCP8ab2vfu2GiUr8AQcr2nCV/oEO3yneFarB67zk8ShlIyWb2LGTb3Sg==} + /rollup@4.24.4: + resolution: {integrity: sha512-vGorVWIsWfX3xbcyAS+I047kFKapHYivmkaT63Smj77XwvLSJos6M1xGqZnBPFQFBRZDOcG1QnYEIxAvTr/HjA==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true dependencies: - '@types/estree': 1.0.5 + '@types/estree': 1.0.6 optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.18.0 - '@rollup/rollup-android-arm64': 4.18.0 - '@rollup/rollup-darwin-arm64': 4.18.0 - '@rollup/rollup-darwin-x64': 4.18.0 - '@rollup/rollup-linux-arm-gnueabihf': 4.18.0 - '@rollup/rollup-linux-arm-musleabihf': 4.18.0 - '@rollup/rollup-linux-arm64-gnu': 4.18.0 - '@rollup/rollup-linux-arm64-musl': 4.18.0 - '@rollup/rollup-linux-powerpc64le-gnu': 4.18.0 - '@rollup/rollup-linux-riscv64-gnu': 4.18.0 - '@rollup/rollup-linux-s390x-gnu': 4.18.0 - '@rollup/rollup-linux-x64-gnu': 4.18.0 - '@rollup/rollup-linux-x64-musl': 4.18.0 - '@rollup/rollup-win32-arm64-msvc': 4.18.0 - '@rollup/rollup-win32-ia32-msvc': 4.18.0 - '@rollup/rollup-win32-x64-msvc': 4.18.0 + '@rollup/rollup-android-arm-eabi': 4.24.4 + '@rollup/rollup-android-arm64': 4.24.4 + '@rollup/rollup-darwin-arm64': 4.24.4 + '@rollup/rollup-darwin-x64': 4.24.4 + '@rollup/rollup-freebsd-arm64': 4.24.4 + '@rollup/rollup-freebsd-x64': 4.24.4 + '@rollup/rollup-linux-arm-gnueabihf': 4.24.4 + '@rollup/rollup-linux-arm-musleabihf': 4.24.4 + '@rollup/rollup-linux-arm64-gnu': 4.24.4 + '@rollup/rollup-linux-arm64-musl': 4.24.4 + '@rollup/rollup-linux-powerpc64le-gnu': 4.24.4 + '@rollup/rollup-linux-riscv64-gnu': 4.24.4 + '@rollup/rollup-linux-s390x-gnu': 4.24.4 + '@rollup/rollup-linux-x64-gnu': 4.24.4 + '@rollup/rollup-linux-x64-musl': 4.24.4 + '@rollup/rollup-win32-arm64-msvc': 4.24.4 + '@rollup/rollup-win32-ia32-msvc': 4.24.4 + '@rollup/rollup-win32-x64-msvc': 4.24.4 fsevents: 2.3.3 dev: true @@ -9455,7 +9351,7 @@ packages: /rxjs@7.8.1: resolution: {integrity: sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==} dependencies: - tslib: 2.6.2 + tslib: 2.8.1 dev: true /sade@1.8.1: @@ -9465,12 +9361,12 @@ packages: mri: 1.2.0 dev: true - /safe-array-concat@1.1.0: - resolution: {integrity: sha512-ZdQ0Jeb9Ofti4hbt5lX3T2JcAamT9hfzYU1MNB+z/jaEbB6wfFfPIR/zEORmZqobkCCJhSjodobH6WHNmJ97dg==} + /safe-array-concat@1.1.2: + resolution: {integrity: sha512-vj6RsCsWBCf19jIeHEfkRMw8DPiBb+DMXklQ/1SGDHOMlHdPUkZXFQ2YdplS23zESTijAcurb1aSgJA3AgMu1Q==} engines: {node: '>=0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 + call-bind: 1.0.7 + get-intrinsic: 1.2.4 has-symbols: 1.0.3 isarray: 2.0.5 dev: true @@ -9482,12 +9378,12 @@ packages: /safe-buffer@5.2.1: resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} - /safe-regex-test@1.0.2: - resolution: {integrity: sha512-83S9w6eFq12BBIJYvjMux6/dkirb8+4zJRA9cxNBVb7Wq5fJBW+Xze48WqR8pxua7bDuAaaAxtVVd4Idjp1dBQ==} + /safe-regex-test@1.0.3: + resolution: {integrity: sha512-CdASjNJPvRa7roO6Ra/gLYBTzYzzPyyBXxIMdGW3USQLyjWEls2RgW5UBTXaQVp+OrpeCK3bLem8smtmheoRuw==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 + call-bind: 1.0.7 + es-errors: 1.3.0 is-regex: 1.1.4 dev: true @@ -9505,13 +9401,13 @@ packages: engines: {node: '>=14.0.0'} hasBin: true dependencies: - chokidar: 3.5.3 - immutable: 4.3.6 - source-map-js: 1.2.0 + chokidar: 3.6.0 + immutable: 4.3.7 + source-map-js: 1.2.1 dev: true - /sax@1.3.0: - resolution: {integrity: sha512-0s+oAmw9zLl1V1cS9BtZN7JAd0cW5e0QH4W3LWEK6a4LaLEA2OTpGYWDY+6XasBLtz6wkm3u1xRw95mRuJ59WA==} + /sax@1.4.1: + resolution: {integrity: sha512-+aWOz7yVScEGoKNd4PA10LZ8sk0A/z5+nXQG5giUO5rprX9jgYsTdov9qCchZiPIZezbZH+jRut8nPodFAX4Jg==} /scheduler@0.20.2: resolution: {integrity: sha512-2eWfGgAqqWFGqtdMmcL5zCMK1U8KlXv8SQFGglL3CEtd0aDVDWgeF/YoCmvln55m5zSk3J/20hTaSBeSObsQDQ==} @@ -9532,15 +9428,20 @@ packages: resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} hasBin: true - /semver@7.5.4: - resolution: {integrity: sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==} + /semver@7.5.2: + resolution: {integrity: sha512-SoftuTROv/cRjCze/scjGyiDtcUyxw1rgYQSZY7XTmtR5hX+dm76iDbTH8TkLPHCQmlbQVSSbNZCPM2hb0knnQ==} engines: {node: '>=10'} hasBin: true dependencies: lru-cache: 6.0.0 - /send@0.18.0: - resolution: {integrity: sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==} + /semver@7.6.3: + resolution: {integrity: sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==} + engines: {node: '>=10'} + hasBin: true + + /send@0.19.0: + resolution: {integrity: sha512-dW41u5VfLXu8SJh5bwRmyYUbAoSB3c9uQh6L8h/KtsFREPWpbX1lrljJo186Jc4nmci/sGUZ9a0a0J2zgfq2hw==} engines: {node: '>= 0.8.0'} dependencies: debug: 2.6.9 @@ -9566,14 +9467,14 @@ packages: randombytes: 2.1.0 dev: true - /serve-static@1.15.0: - resolution: {integrity: sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==} + /serve-static@1.16.2: + resolution: {integrity: sha512-VqpjJZKadQB/PEbEwvFdO43Ax5dFBZ2UECszz8bQ7pi7wt//PWe1P6MN7eCnjsatYtBT6EuiClbjSWP2WrIoTw==} engines: {node: '>= 0.8.0'} dependencies: - encodeurl: 1.0.2 + encodeurl: 2.0.0 escape-html: 1.0.3 parseurl: 1.3.3 - send: 0.18.0 + send: 0.19.0 transitivePeerDependencies: - supports-color dev: false @@ -9582,23 +9483,25 @@ packages: resolution: {integrity: sha512-KiKBS8AnWGEyLzofFfmvKwpdPzqiy16LvQfK3yv/fVH7Bj13/wl3JSR1J+rfgRE9q7xUJK4qvgS8raSOeLUehw==} dev: true - /set-function-length@1.2.0: - resolution: {integrity: sha512-4DBHDoyHlM1IRPGYcoxexgh67y4ueR53FKV1yyxwFMY7aCqcN/38M1+SwZ/qJQ8iLv7+ck385ot4CcisOAPT9w==} + /set-function-length@1.2.2: + resolution: {integrity: sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==} engines: {node: '>= 0.4'} dependencies: - define-data-property: 1.1.1 + define-data-property: 1.1.4 + es-errors: 1.3.0 function-bind: 1.1.2 - get-intrinsic: 1.2.2 + get-intrinsic: 1.2.4 gopd: 1.0.1 - has-property-descriptors: 1.0.1 + has-property-descriptors: 1.0.2 - /set-function-name@2.0.1: - resolution: {integrity: sha512-tMNCiqYVkXIZgc2Hnoy2IvC/f8ezc5koaRFkCjrpWzGpCd3qbZXPzVy9MAZzK1ch/X0jvSkojys3oqJN0qCmdA==} + /set-function-name@2.0.2: + resolution: {integrity: sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ==} engines: {node: '>= 0.4'} dependencies: - define-data-property: 1.1.1 + define-data-property: 1.1.4 + es-errors: 1.3.0 functions-have-names: 1.2.3 - has-property-descriptors: 1.0.1 + has-property-descriptors: 1.0.2 dev: true /set-value@2.0.1: @@ -9638,12 +9541,14 @@ packages: resolution: {integrity: sha512-sQTKC1Re/rM6XyFM6fIAGHRPVGvyXfgzIDvzoq608vM+jeyVD0Tu1E6Np0Kc2zAIFWIj963V2800iF/9LPieQw==} dev: false - /side-channel@1.0.4: - resolution: {integrity: sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==} + /side-channel@1.0.6: + resolution: {integrity: sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 - object-inspect: 1.13.1 + call-bind: 1.0.7 + es-errors: 1.3.0 + get-intrinsic: 1.2.4 + object-inspect: 1.13.2 /signal-exit@3.0.7: resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==} @@ -9693,7 +9598,7 @@ packages: resolution: {integrity: sha512-LAOh4z89bGQvl9pFfNF8V146i7o7/CqFPbqzYgP+yYzDIDeS9HaNFtXABamRW+AQzEVODcvE79ljJ+8a9YSdMg==} dependencies: dot-case: 3.0.4 - tslib: 2.6.2 + tslib: 2.8.1 dev: true /snapdragon-node@2.1.1: @@ -9733,22 +9638,22 @@ packages: engines: {node: '>= 10'} dependencies: agent-base: 6.0.2 - debug: 4.3.4(supports-color@8.1.1) - socks: 2.7.1 + debug: 4.3.7(supports-color@8.1.1) + socks: 2.8.3 transitivePeerDependencies: - supports-color dev: true - /socks@2.7.1: - resolution: {integrity: sha512-7maUZy1N7uo6+WVEX6psASxtNlKaNVMlGQKkG/63nEDdLOWNbiUMoLK7X4uYoLhQstau72mLgfEWcXcwsaHbYQ==} - engines: {node: '>= 10.13.0', npm: '>= 3.0.0'} + /socks@2.8.3: + resolution: {integrity: sha512-l5x7VUUWbjVFbafGLxPWkYsHIhEvmF85tbIeFZWc8ZPtoMyybuEhL7Jye/ooC4/d48FgOjSJXgsF/AJPYCW8Zw==} + engines: {node: '>= 10.0.0', npm: '>= 3.0.0'} dependencies: - ip: 2.0.0 + ip-address: 9.0.5 smart-buffer: 4.2.0 dev: true - /source-map-js@1.2.0: - resolution: {integrity: sha512-itJW8lvSA0TXEphiRoawsCksnlf8SyvmFzIhltqAHluXd88pkCd+cXJVHTDwdCr0IzwptSm035IHQktUu1QUMg==} + /source-map-js@1.2.1: + resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} engines: {node: '>=0.10.0'} dev: true @@ -9822,6 +9727,10 @@ packages: resolution: {integrity: sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==} dev: true + /sprintf-js@1.1.3: + resolution: {integrity: sha512-Oo+0REFV59/rz3gfJNKQiBlwfHaSESl1pcGyABQsnnIfWOFt6JNj5gCog2U6MLZ//IGYD+nA8nI+mTShREReaA==} + dev: true + /ssri@9.0.1: resolution: {integrity: sha512-o57Wcn66jMQvfHG1FlYbWeZWW/dHZhJXjpIcTfXldXEk5nz5lStPo3mK0OJQfGR3RbZUlbISexbljkJzuEj/8Q==} engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0} @@ -9856,7 +9765,7 @@ packages: engines: {node: '>=8.0'} dependencies: date-format: 4.0.14 - debug: 4.3.4(supports-color@8.1.1) + debug: 4.3.7(supports-color@8.1.1) fs-extra: 8.1.0 transitivePeerDependencies: - supports-color @@ -9885,29 +9794,31 @@ packages: is-fullwidth-code-point: 3.0.0 strip-ansi: 6.0.1 - /string.prototype.trim@1.2.8: - resolution: {integrity: sha512-lfjY4HcixfQXOfaqCvcBuOIapyaroTXhbkfJN3gcB1OtyupngWK4sEET9Knd0cXd28kTUqu/kHoV4HKSJdnjiQ==} + /string.prototype.trim@1.2.9: + resolution: {integrity: sha512-klHuCNxiMZ8MlsOihJhJEBJAiMVqU3Z2nEXWfWnIqjN0gEFS9J9+IxKozWWtQGcgoa1WUZzLjKPTr4ZHNFTFxw==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-abstract: 1.23.3 + es-object-atoms: 1.0.0 dev: true - /string.prototype.trimend@1.0.7: - resolution: {integrity: sha512-Ni79DqeB72ZFq1uH/L6zJ+DKZTkOtPIHovb3YZHQViE+HDouuU4mBrLOLDn5Dde3RF8qw5qVETEjhu9locMLvA==} + /string.prototype.trimend@1.0.8: + resolution: {integrity: sha512-p73uL5VCHCO2BZZ6krwwQE3kCzM7NKmis8S//xEC6fQonchbum4eP6kR4DLEjQFO3Wnj3Fuo8NM0kOSjVdHjZQ==} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-object-atoms: 1.0.0 dev: true - /string.prototype.trimstart@1.0.7: - resolution: {integrity: sha512-NGhtDFu3jCEm7B4Fy0DpLewdJQOZcQ0rGbwQ/+stjnrp2i+rlKeCvos9hOIeCmqwratM47OBxY7uFZzjxHXmrg==} + /string.prototype.trimstart@1.0.8: + resolution: {integrity: sha512-UXSH262CSZY1tfu3G3Secr6uGLCFVPMhIqHjlgCUtCCcgihYc/xKs9djMTMUOb2j1mVSeU8EU6NWc/iQKU6Gfg==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 define-properties: 1.2.1 - es-abstract: 1.22.3 + es-object-atoms: 1.0.0 dev: true /string_decoder@1.1.1: @@ -9957,8 +9868,8 @@ packages: engines: {node: '>=8'} dev: true - /stylis@4.3.1: - resolution: {integrity: sha512-EQepAV+wMsIaGVGX1RECzgrcqRRU/0sYOHkeLsZ3fzHaHXZy4DaOOX0vOlGQdlsjkh3mFHAIlVimpwAs4dslyQ==} + /stylis@4.3.4: + resolution: {integrity: sha512-osIBl6BGUmSfDkyH2mB7EFvCJntXDrLhKjHTRj/rK6xLH0yuPrHULDRQzKokSOD4VoorhtKpfcfW1GAntu8now==} dev: true /supports-color@5.5.0: @@ -10011,7 +9922,7 @@ packages: dependencies: commander: 9.5.0 glob: 8.1.0 - sax: 1.3.0 + sax: 1.4.1 svg-pathdata: 6.0.3 dev: true @@ -10026,7 +9937,7 @@ packages: css-tree: 2.3.1 css-what: 6.1.0 csso: 5.0.5 - picocolors: 1.0.1 + picocolors: 1.1.1 dev: true /svgpath@2.6.0: @@ -10046,11 +9957,11 @@ packages: '@types/ttf2eot': 2.0.2 '@types/ttf2woff': 2.0.4 '@types/ttf2woff2': 2.0.2 - cheerio: 1.0.0-rc.12 + cheerio: 1.0.0 colors-cli: 1.0.33 copy-template-dir: 1.4.0 del: 6.1.1 - ejs: 3.1.9 + ejs: 3.1.10 fs-extra: 11.1.1 image2uri: 1.0.5 move-file: 2.1.0 @@ -10060,7 +9971,7 @@ packages: ttf2eot: 3.1.0 ttf2woff: 3.0.0 ttf2woff2: 5.0.0 - yaml: 2.3.4 + yaml: 2.6.0 yargs: 17.7.2 transitivePeerDependencies: - bluebird @@ -10076,8 +9987,8 @@ packages: engines: {node: '>=6'} dev: true - /tar@6.2.0: - resolution: {integrity: sha512-/Wo7DcT0u5HUV486xg675HtjNd3BXZ6xDbzsCUZPt5iw8bTQ63bP0Raut3mvro9u+CUyq7YQd8Cx55fsZXxqLQ==} + /tar@6.2.1: + resolution: {integrity: sha512-DZ4yORTwrbTj/7MZYq2w+/ZFdI6OZ/f9SFHR+71gIVUZhOQPHzVCLpvRnPgyaMpfWxxk/4ONva3GQSyNIKRv6A==} engines: {node: '>=10'} dependencies: chownr: 2.0.0 @@ -10091,7 +10002,7 @@ packages: /tas-client@0.1.73: resolution: {integrity: sha512-UDdUF9kV2hYdlv+7AgqP2kXarVSUhjK7tg1BUflIRGEgND0/QoNpN64rcEuhEcM8AIbW65yrCopJWqRhLZ3m8w==} dependencies: - axios: 1.7.5(debug@4.3.4) + axios: 1.7.5(debug@4.3.7) transitivePeerDependencies: - debug dev: false @@ -10127,23 +10038,21 @@ packages: resolution: {integrity: sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg==} dev: true - /tiny-invariant@1.3.1: - resolution: {integrity: sha512-AD5ih2NlSssTCwsMznbvwMZpJ1cbhkGd2uueNxzv2jDlEeZdU04JQfRnggJQ8DrcVBGjAsCKwFBbDlVNtEMlzw==} + /tiny-invariant@1.3.3: + resolution: {integrity: sha512-+FbBPE1o9QAYvviau/qC5SE3caw21q3xkvWKBtja5vgqOWIHHJ3ioaq1VPfn/Szqctz2bU/oYeKd9/z5BL+PVg==} dev: true /tiny-warning@1.0.3: resolution: {integrity: sha512-lBN9zLN/oAf68o3zNXYrdCt1kP8WsiGW8Oo2ka41b2IM5JL/S1CTyX1rW0mb/zSuJun0ZUrDxx4sqvYS2FWzPA==} dev: true - /tmp@0.2.3: - resolution: {integrity: sha512-nZD7m9iCPC5g0pYmcaxogYKggSfLsdxl8of3Q/oIbqCqLLIO9IAF0GWjX1z9NZRHPiXv8Wex4yDCaZsgEw0Y8w==} - engines: {node: '>=14.14'} + /tmp@0.2.1: + resolution: {integrity: sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==} + engines: {node: '>=8.17.0'} + dependencies: + rimraf: 3.0.2 dev: false - /to-fast-properties@2.0.0: - resolution: {integrity: sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==} - engines: {node: '>=4'} - /to-object-path@0.3.0: resolution: {integrity: sha512-9mWHdnGRuh3onocaHzukyvCZhzvr6tiflAy/JRFXcJX0TjgfWA9pk9t8CMbzmBE4Jfw58pXbkngtBtqYxzNEyg==} engines: {node: '>=0.10.0'} @@ -10188,6 +10097,11 @@ packages: resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} dev: false + /tree-kill@1.2.2: + resolution: {integrity: sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==} + hasBin: true + dev: false + /ts-dedent@2.2.0: resolution: {integrity: sha512-q5W7tVM71e2xjHZTlgfTDoPF/SmqKG5hddq9SzR49CH2hayqRKJtQ4mtRlSxKaJlR/+9rEM+mnBHf7I2/BQcpQ==} engines: {node: '>=6.10'} @@ -10202,7 +10116,7 @@ packages: chalk: 2.4.2 enhanced-resolve: 4.5.0 loader-utils: 1.4.2 - micromatch: 4.0.5 + micromatch: 4.0.8 semver: 6.3.1 typescript: 4.7.4 dev: true @@ -10227,8 +10141,8 @@ packages: '@tsconfig/node14': 1.0.3 '@tsconfig/node16': 1.0.4 '@types/node': 14.14.21 - acorn: 8.11.3 - acorn-walk: 8.3.3 + acorn: 8.14.0 + acorn-walk: 8.3.4 arg: 4.1.3 create-require: 1.1.1 diff: 4.0.2 @@ -10259,8 +10173,8 @@ packages: /tslib@1.14.1: resolution: {integrity: sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==} - /tslib@2.6.2: - resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==} + /tslib@2.8.1: + resolution: {integrity: sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==} /tsutils@3.21.0(typescript@4.7.4): resolution: {integrity: sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==} @@ -10287,7 +10201,7 @@ packages: dependencies: bindings: 1.5.0 bufferstreams: 3.0.0 - nan: 2.18.0 + nan: 2.22.0 node-gyp: 9.4.1 transitivePeerDependencies: - bluebird @@ -10314,6 +10228,11 @@ packages: engines: {node: '>=4'} dev: true + /type-detect@4.1.0: + resolution: {integrity: sha512-Acylog8/luQ8L7il+geoSxhEkazvkslg7PSNKOX59mbB9cOveP5aq9h74Y7YU8yDpJwetzQQrfIwtf4Wp4LKcw==} + engines: {node: '>=4'} + dev: true + /type-fest@0.20.2: resolution: {integrity: sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==} engines: {node: '>=10'} @@ -10337,50 +10256,52 @@ packages: mime-types: 2.1.35 dev: false - /type@1.2.0: - resolution: {integrity: sha512-+5nt5AAniqsCnu2cEQQdpzCAh33kVx8n0VoFidKpB1dVVLAN/F+bgVOqOJqOnEnrhp222clB5p3vUlD+1QAnfg==} + /type@2.7.3: + resolution: {integrity: sha512-8j+1QmAbPvLZow5Qpi6NCaN8FB60p/6x8/vfNqOk/hC+HuvFZhL4+WfekuhQLiqFZXOgQdrs3B+XxEmCc6b3FQ==} dev: false - /type@2.7.2: - resolution: {integrity: sha512-dzlvlNlt6AXU7EBSfpAscydQ7gXB+pPGsPnfJnZpiNJBDj7IaJzQlBZYGdEi4R9HmPdBv2XmWJ6YUtoTa7lmCw==} - dev: false - - /typed-array-buffer@1.0.0: - resolution: {integrity: sha512-Y8KTSIglk9OZEr8zywiIHG/kmQ7KWyjseXs1CbSo8vC42w7hg2HgYTxSWwP0+is7bWDc1H+Fo026CpHFwm8tkw==} + /typed-array-buffer@1.0.2: + resolution: {integrity: sha512-gEymJYKZtKXzzBzM4jqa9w6Q1Jjm7x2d+sh19AdsD4wqnMPDYyvwpsIc2Q/835kHuo3BEQ7CjelGhfTsoBb2MQ==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 - get-intrinsic: 1.2.2 - is-typed-array: 1.1.12 + call-bind: 1.0.7 + es-errors: 1.3.0 + is-typed-array: 1.1.13 dev: true - /typed-array-byte-length@1.0.0: - resolution: {integrity: sha512-Or/+kvLxNpeQ9DtSydonMxCx+9ZXOswtwJn17SNLvhptaXYDJvkFFP5zbfU/uLmvnBJlI4yrnXRxpdWH/M5tNA==} + /typed-array-byte-length@1.0.1: + resolution: {integrity: sha512-3iMJ9q0ao7WE9tWcaYKIptkNBuOIcZCCT0d4MRvuuH88fEoEH62IuQe0OtraD3ebQEoTRk8XCBoknUNc1Y67pw==} engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 for-each: 0.3.3 - has-proto: 1.0.1 - is-typed-array: 1.1.12 + gopd: 1.0.1 + has-proto: 1.0.3 + is-typed-array: 1.1.13 dev: true - /typed-array-byte-offset@1.0.0: - resolution: {integrity: sha512-RD97prjEt9EL8YgAgpOkf3O4IF9lhJFr9g0htQkm0rchFp/Vx7LW5Q8fSXXub7BXAODyUQohRMyOc3faCPd0hg==} + /typed-array-byte-offset@1.0.2: + resolution: {integrity: sha512-Ous0vodHa56FviZucS2E63zkgtgrACj7omjwd/8lTEMEPFFyjfixMZ1ZXenpgCFBBt4EC1J2XsyVS2gkG0eTFA==} engines: {node: '>= 0.4'} dependencies: - available-typed-arrays: 1.0.5 - call-bind: 1.0.5 + available-typed-arrays: 1.0.7 + call-bind: 1.0.7 for-each: 0.3.3 - has-proto: 1.0.1 - is-typed-array: 1.1.12 + gopd: 1.0.1 + has-proto: 1.0.3 + is-typed-array: 1.1.13 dev: true - /typed-array-length@1.0.4: - resolution: {integrity: sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng==} + /typed-array-length@1.0.6: + resolution: {integrity: sha512-/OxDN6OtAk5KBpGb28T+HZc2M+ADtvRxXrKKbUwtsLgdoxgX13hyy7ek6bFRl5+aBs2yZzB0c4CnQfAtVypW/g==} + engines: {node: '>= 0.4'} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 for-each: 0.3.3 - is-typed-array: 1.1.12 + gopd: 1.0.1 + has-proto: 1.0.3 + is-typed-array: 1.1.13 + possible-typed-array-names: 1.0.0 dev: true /typedarray-to-buffer@3.1.5: @@ -10406,14 +10327,19 @@ packages: /unbox-primitive@1.0.2: resolution: {integrity: sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==} dependencies: - call-bind: 1.0.5 + call-bind: 1.0.7 has-bigints: 1.0.2 has-symbols: 1.0.3 which-boxed-primitive: 1.0.2 dev: true - /unicode-canonical-property-names-ecmascript@2.0.0: - resolution: {integrity: sha512-yY5PpDlfVIU5+y/BSCxAJRBIS1Zc2dDG3Ujq+sR0U+JjUevW2JhocOF+soROYDSaAezOzOKuyyixhD6mBknSmQ==} + /undici@6.20.1: + resolution: {integrity: sha512-AjQF1QsmqfJys+LXfGTNum+qw4S88CojRInG/6t31W/1fk6G59s92bnAvGz5Cmur+kQv2SURXEvvudLmbrE8QA==} + engines: {node: '>=18.17'} + dev: true + + /unicode-canonical-property-names-ecmascript@2.0.1: + resolution: {integrity: sha512-dA8WbNeb2a6oQzAQ55YlT5vQAWGV9WXOsi3SskE3bcCdM0P4SDd+24zS/OCacdRq5BkdsRj9q3Pg6YyQoxIGqg==} engines: {node: '>=4'} dev: false @@ -10421,12 +10347,12 @@ packages: resolution: {integrity: sha512-5kaZCrbp5mmbz5ulBkDkbY0SsPOjKqVS35VpL9ulMPfSl0J0Xsm+9Evphv9CoIZFwre7aJoa94AY6seMKGVN5Q==} engines: {node: '>=4'} dependencies: - unicode-canonical-property-names-ecmascript: 2.0.0 + unicode-canonical-property-names-ecmascript: 2.0.1 unicode-property-aliases-ecmascript: 2.1.0 dev: false - /unicode-match-property-value-ecmascript@2.1.0: - resolution: {integrity: sha512-qxkjQt6qjg/mYscYMC0XKRn3Rh0wFPlfxB0xkt9CfyTvpX1Ra0+rAmdX2QyAobptSEvuy4RtpPRui6XkV+8wjA==} + /unicode-match-property-value-ecmascript@2.2.0: + resolution: {integrity: sha512-4IehN3V/+kkr5YeSSDDQG8QLqO26XpL2XP3GQtqwlT/QYSECAwFztxVHjlbh0+gjJ3XmNLS0zDsbgs9jWKExLg==} engines: {node: '>=4'} dev: false @@ -10462,7 +10388,7 @@ packages: /unist-util-stringify-position@3.0.3: resolution: {integrity: sha512-k5GzIBZ/QatR8N5X2y+drfpWG8IDBzdnVj6OInRNWm1oXrzydiaAT2OQiA8DPRRZyAKb9b6I2a6PxYklZD0gKg==} dependencies: - '@types/unist': 2.0.10 + '@types/unist': 2.0.11 dev: true /universalify@0.1.2: @@ -10492,20 +10418,21 @@ packages: isobject: 3.0.1 dev: true - /update-browserslist-db@1.0.13(browserslist@4.22.2): - resolution: {integrity: sha512-xebP81SNcPuNpPP3uzeW1NYXxI3rxyJzF3pD6sH4jE7o/IX+WtSpwnVU+qIsDPyk0d3hmFQ7mjqc6AtV604hbg==} + /update-browserslist-db@1.1.1(browserslist@4.24.2): + resolution: {integrity: sha512-R8UzCaa9Az+38REPiJ1tXlImTJXlVfgHZsglwBD/k6nj76ctsH1E3q4doGrukiLQd3sGQYu56r5+lo5r94l29A==} hasBin: true peerDependencies: browserslist: '>= 4.21.0' dependencies: - browserslist: 4.22.2 - escalade: 3.1.1 - picocolors: 1.0.1 + browserslist: 4.24.2 + escalade: 3.2.0 + picocolors: 1.1.1 /uri-js@4.4.1: resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} dependencies: punycode: 2.3.1 + dev: true /urix@0.1.0: resolution: {integrity: sha512-Am1ousAhSLBeB9cG/7k7r2R0zj50uDRlZHPGbazid5s9rlF1F/QKYObEKSIunSjIOkJZqwRRLpvewjEkM7pSqg==} @@ -10522,7 +10449,7 @@ packages: engines: {node: '>=6.14.2'} requiresBuild: true dependencies: - node-gyp-build: 4.8.0 + node-gyp-build: 4.8.2 dev: false /util-deprecate@1.0.2: @@ -10561,7 +10488,7 @@ packages: hasBin: true dependencies: dequal: 2.0.3 - diff: 5.0.0 + diff: 5.2.0 kleur: 4.1.5 sade: 1.8.1 dev: true @@ -10588,23 +10515,23 @@ packages: engines: {node: '>= 0.8'} dev: false - /vite-plugin-svgr@4.2.0(typescript@4.7.4)(vite@5.3.6): + /vite-plugin-svgr@4.2.0(typescript@4.7.4)(vite@5.4.0): resolution: {integrity: sha512-SC7+FfVtNQk7So0XMjrrtLAbEC8qjFPifyD7+fs/E6aaNdVde6umlVVh0QuwDLdOMu7vp5RiGFsB70nj5yo0XA==} peerDependencies: vite: ^2.6.0 || 3 || 4 || 5 dependencies: - '@rollup/pluginutils': 5.1.0 + '@rollup/pluginutils': 5.1.3 '@svgr/core': 8.1.0(typescript@4.7.4) '@svgr/plugin-jsx': 8.1.0(@svgr/core@8.1.0) - vite: 5.3.6(@types/node@14.14.21)(sass@1.77.6) + vite: 5.4.0(@types/node@14.14.21)(sass@1.77.6) transitivePeerDependencies: - rollup - supports-color - typescript dev: true - /vite@5.3.6(@types/node@14.14.21)(sass@1.77.6): - resolution: {integrity: sha512-es78AlrylO8mTVBygC0gTC0FENv0C6T496vvd33ydbjF/mIi9q3XQ9A3NWo5qLGFKywvz10J26813OkLvcQleA==} + /vite@5.4.0(@types/node@14.14.21)(sass@1.77.6): + resolution: {integrity: sha512-5xokfMX0PIiwCMCMb9ZJcMyh5wbBun0zUzKib+L65vAZ8GY9ePZMXxFrHbr/Kyll2+LSCY7xtERPpxkBDKngwg==} engines: {node: ^18.0.0 || >=20.0.0} hasBin: true peerDependencies: @@ -10612,6 +10539,7 @@ packages: less: '*' lightningcss: ^1.21.0 sass: '*' + sass-embedded: '*' stylus: '*' sugarss: '*' terser: ^5.4.0 @@ -10624,6 +10552,8 @@ packages: optional: true sass: optional: true + sass-embedded: + optional: true stylus: optional: true sugarss: @@ -10633,8 +10563,8 @@ packages: dependencies: '@types/node': 14.14.21 esbuild: 0.21.5 - postcss: 8.4.39 - rollup: 4.18.0 + postcss: 8.4.47 + rollup: 4.24.4 sass: 1.77.6 optionalDependencies: fsevents: 2.3.3 @@ -10662,13 +10592,13 @@ packages: resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==} dev: false - /websocket@1.0.34: - resolution: {integrity: sha512-PRDso2sGwF6kM75QykIesBijKSVceR6jL2G8NGYyq2XrItNC2P5/qL5XeR056GhA+Ly7JMFvJb9I312mJfmqnQ==} + /websocket@1.0.35: + resolution: {integrity: sha512-/REy6amwPZl44DDzvRCkaI1q1bIiQB0mEFQLUrhz3z2EK91cp3n72rAjUlrTP0zV22HJIUOVHQGPxhFRjxjt+Q==} engines: {node: '>=4.0.0'} dependencies: bufferutil: 4.0.8 debug: 2.6.9 - es5-ext: 0.10.53 + es5-ext: 0.10.64 typedarray-to-buffer: 3.1.5 utf-8-validate: 5.0.10 yaeti: 0.0.6 @@ -10676,6 +10606,18 @@ packages: - supports-color dev: false + /whatwg-encoding@3.1.1: + resolution: {integrity: sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==} + engines: {node: '>=18'} + dependencies: + iconv-lite: 0.6.3 + dev: true + + /whatwg-mimetype@4.0.0: + resolution: {integrity: sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==} + engines: {node: '>=18'} + dev: true + /whatwg-url@5.0.0: resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==} dependencies: @@ -10697,15 +10639,15 @@ packages: resolution: {integrity: sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==} dev: true - /which-typed-array@1.1.13: - resolution: {integrity: sha512-P5Nra0qjSncduVPEAr7xhoF5guty49ArDTwzJ/yNuPIbZppyRxFQsRCWrocxIY+CnMVG+qfbU2FmDKyvSGClow==} + /which-typed-array@1.1.15: + resolution: {integrity: sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA==} engines: {node: '>= 0.4'} dependencies: - available-typed-arrays: 1.0.5 - call-bind: 1.0.5 + available-typed-arrays: 1.0.7 + call-bind: 1.0.7 for-each: 0.3.3 gopd: 1.0.1 - has-tostringtag: 1.0.0 + has-tostringtag: 1.0.2 dev: true /which@2.0.2: @@ -10722,6 +10664,11 @@ packages: string-width: 4.2.3 dev: true + /word-wrap@1.2.5: + resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} + engines: {node: '>=0.10.0'} + dev: true + /workerpool@6.2.1: resolution: {integrity: sha512-ILEIE97kDZvF9Wb9f6h5aXK4swSlKGUcOEGiIYb2OOu/IrDU9iwj0fD//SsA6E5ibwJxpEvhullJY4Sl4GcpAw==} dev: true @@ -10767,7 +10714,7 @@ packages: resolution: {integrity: sha512-drPFnkQJik/O+uPKpqSgr22mpuFHqKdbS835iAQrUC73L2F5WkboIRd63ai/2Yg6I1jzifPFKH2NTK+cfglkIA==} engines: {node: '>=4.0.0'} dependencies: - sax: 1.3.0 + sax: 1.4.1 xmlbuilder: 11.0.1 dev: false @@ -10804,9 +10751,10 @@ packages: engines: {node: '>= 6'} dev: true - /yaml@2.3.4: - resolution: {integrity: sha512-8aAvwVUSHpfEqTQ4w/KMlf3HcRdt50E5ODIQJBw1fQ5RL34xabzxtUlzTXVqc4rkZsPbvrXKWnABCD7kWSmocA==} + /yaml@2.6.0: + resolution: {integrity: sha512-a6ae//JvKDEra2kdi1qzCyrJW/WZCgFi8ydDV+eXExl95t+5R+ijnqHJbz9tmMh8FUjx3iv2fCQ4dclAQlO2UQ==} engines: {node: '>= 14'} + hasBin: true dev: true /yargs-parser@18.1.3: @@ -10822,11 +10770,6 @@ packages: engines: {node: '>=10'} dev: true - /yargs-parser@20.2.9: - resolution: {integrity: sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==} - engines: {node: '>=10'} - dev: true - /yargs-parser@21.1.1: resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==} engines: {node: '>=12'} @@ -10863,12 +10806,12 @@ packages: engines: {node: '>=10'} dependencies: cliui: 7.0.4 - escalade: 3.1.1 + escalade: 3.2.0 get-caller-file: 2.0.5 require-directory: 2.1.1 string-width: 4.2.3 y18n: 5.0.8 - yargs-parser: 20.2.9 + yargs-parser: 20.2.4 dev: true /yargs@17.7.2: @@ -10876,7 +10819,7 @@ packages: engines: {node: '>=12'} dependencies: cliui: 8.0.1 - escalade: 3.1.1 + escalade: 3.2.0 get-caller-file: 2.0.5 require-directory: 2.1.1 string-width: 4.2.3 diff --git a/packages/vscode-extension/src/commonlib/azureLogin.ts b/packages/vscode-extension/src/commonlib/azureLogin.ts index 54130f6e80..e94935eb77 100644 --- a/packages/vscode-extension/src/commonlib/azureLogin.ts +++ b/packages/vscode-extension/src/commonlib/azureLogin.ts @@ -13,11 +13,23 @@ import { SubscriptionInfo, SingleSelectConfig, OptionItem, + FxError, + Result, + ok, + err, } from "@microsoft/teamsfx-api"; import { ExtensionErrors } from "../error/error"; import { LoginFailureError } from "./codeFlowLogin"; import * as vscode from "vscode"; -import { loggedIn, loggedOut, loggingIn, signedIn, signedOut, signingIn } from "./common/constant"; +import { + azureCacheName, + loggedIn, + loggedOut, + loggingIn, + signedIn, + signedOut, + signingIn, +} from "./common/constant"; import { login, LoginStatus } from "./common/login"; import * as util from "util"; import { ExtTelemetry } from "../telemetry/extTelemetry"; @@ -30,13 +42,20 @@ import { TelemetryErrorType, } from "../telemetry/extTelemetryEvents"; import { VS_CODE_UI } from "../qm/vsc_ui"; -import { AzureScopes, globalStateGet, globalStateUpdate } from "@microsoft/teamsfx-core"; +import { + AzureScopes, + featureFlagManager, + FeatureFlags, + globalStateGet, + globalStateUpdate, +} from "@microsoft/teamsfx-core"; import { getDefaultString, localize } from "../utils/localizeUtils"; import { Microsoft, VSCodeAzureSubscriptionProvider, getSessionFromVSCode, } from "./vscodeAzureSubscriptionProvider"; +import { loadTenantId, saveTenantId } from "./cacheAccess"; const showAzureSignOutHelp = "ShowAzureSignOutHelp"; @@ -70,22 +89,36 @@ export class AzureAccountManager extends login implements AzureAccountProvider { * Async get identity [crendential](https://github.com/Azure/azure-sdk-for-js/blob/master/sdk/core/core-auth/src/tokenCredential.ts) */ async getIdentityCredentialAsync(showDialog = true): Promise { - if (await this.isUserLogin()) { + if (featureFlagManager.getBooleanValue(FeatureFlags.MultiTenant)) { + const tenantId = await loadTenantId(azureCacheName); + if (await this.isUserLogin(tenantId)) { + const res = await this.getIdentityCredentialSilently(tenantId); + if (res.isOk()) { + return res.value; + } else { + return undefined; + } + } else { + return await this.login(showDialog, tenantId); + } + } else { + if (await this.isUserLogin()) { + return this.doGetIdentityCredentialAsync(); + } + await this.login(showDialog); return this.doGetIdentityCredentialAsync(); } - await this.login(showDialog); - return this.doGetIdentityCredentialAsync(); } - private async isUserLogin(): Promise { - const session = await getSessionFromVSCode(AzureScopes, undefined, { + private async isUserLogin(tenantId?: string): Promise { + const session = await getSessionFromVSCode(AzureScopes, tenantId, { createIfNone: false, silent: true, }); return session !== undefined; } - private async login(showDialog: boolean): Promise { + private async login(showDialog: boolean, tenantId?: string): Promise { if (showDialog) { const userConfirmation: boolean = await this.doesUserConfirmLogin(); if (!userConfirmation) { @@ -105,7 +138,7 @@ export class AzureAccountManager extends login implements AzureAccountProvider { try { AzureAccountManager.currentStatus = loggingIn; void this.notifyStatus(); - const session = await getSessionFromVSCode(AzureScopes, undefined, { createIfNone: true }); + const session = await getSessionFromVSCode(AzureScopes, tenantId, { createIfNone: true }); if (session === undefined) { throw new UserError( getDefaultString("teamstoolkit.codeFlowLogin.loginComponent"), @@ -126,6 +159,19 @@ export class AzureAccountManager extends login implements AzureAccountProvider { } }); } + if (featureFlagManager.getBooleanValue(FeatureFlags.MultiTenant)) { + await saveTenantId(azureCacheName, session.id.split("/")[0]); + } + const credential: TokenCredential = { + // eslint-disable-next-line @typescript-eslint/require-await + getToken: async () => { + return { + token: session.accessToken, + expiresOnTimestamp: 0, + }; + }, + }; + return credential; } catch (e) { AzureAccountManager.currentStatus = loggedOut; void this.notifyStatus(); @@ -185,6 +231,29 @@ export class AzureAccountManager extends login implements AzureAccountProvider { return Promise.reject(LoginFailureError()); } + private async getIdentityCredentialSilently( + tenantId?: string + ): Promise> { + const session = await getSessionFromVSCode(AzureScopes, tenantId, { + createIfNone: false, + silent: true, + }); + if (!session) { + return err(LoginFailureError()); + } + + const credential: TokenCredential = { + // eslint-disable-next-line @typescript-eslint/require-await + getToken: async () => { + return { + token: session.accessToken, + expiresOnTimestamp: 0, + }; + }, + }; + return ok(credential); + } + private async doesUserConfirmLogin(): Promise { const message = localize("teamstoolkit.azureLogin.message"); const signin = localize("teamstoolkit.common.signin"); @@ -277,10 +346,28 @@ export class AzureAccountManager extends login implements AzureAccountProvider { } } + async switchTenant(tenantId: string): Promise> { + let result: TokenCredential; + + const res = await this.getIdentityCredentialSilently(tenantId); + if (res.isErr()) { + try { + result = await this.login(false, tenantId); + } catch (e) { + return err(LoginFailureError(e)); + } + } else { + result = res.value; + } + + await saveTenantId(azureCacheName, tenantId); + await this.notifyStatus(); + return ok(result); + } /** * list all subscriptions */ - async listSubscriptions(): Promise { + async listAllSubscriptions(): Promise { const arr: SubscriptionInfo[] = []; if (await this.isUserLogin()) { const subs = await this.vscodeAzureSubscriptionProvider.getSubscriptions(); @@ -297,6 +384,27 @@ export class AzureAccountManager extends login implements AzureAccountProvider { return arr; } + /** + * List subscriptions under current tenant + */ + async listSubscriptions(): Promise { + const arr: SubscriptionInfo[] = []; + if (await this.isUserLogin()) { + const tenantId = await loadTenantId(azureCacheName); + const subs = await this.vscodeAzureSubscriptionProvider.getSubscriptions(tenantId); + for (let i = 0; i < subs.length; ++i) { + const item = subs[i]; + arr.push({ + subscriptionId: item.subscriptionId, + tenantId: item.tenantId, + subscriptionName: item.name, + }); + } + } + + return arr; + } + /** * set tenantId and subscriptionId */ @@ -366,6 +474,7 @@ export class AzureAccountManager extends login implements AzureAccountProvider { await this.notifyStatus(); } else { AzureAccountManager.currentStatus = loggedOut; + await saveTenantId(azureCacheName, ""); await this.notifyStatus(); } }); @@ -434,6 +543,7 @@ export class AzureAccountManager extends login implements AzureAccountProvider { const config: SingleSelectConfig = { name: localize("teamstoolkit.azureLogin.subscription"), title: localize("teamstoolkit.azureLogin.selectSubscription"), + placeholder: localize("teamstoolkit.azurelogin.selectSubscription.placeholder"), options: options, }; const result = await VS_CODE_UI.selectOption(config); diff --git a/packages/vscode-extension/src/commonlib/cacheAccess.ts b/packages/vscode-extension/src/commonlib/cacheAccess.ts index 4749e1f796..5f3037966f 100644 --- a/packages/vscode-extension/src/commonlib/cacheAccess.ts +++ b/packages/vscode-extension/src/commonlib/cacheAccess.ts @@ -19,6 +19,7 @@ import { SecretStorage } from "vscode"; const cacheDir = os.homedir() + `/.${ConfigFolderName}/account`; const cachePath = os.homedir() + `/.${ConfigFolderName}/account/token.cache.`; const accountPath = os.homedir() + `/.${ConfigFolderName}/account/homeId.cache.`; +const tenantPath = os.homedir() + `/.${ConfigFolderName}/account/tenantId.cache.`; const cachePathEnd = ".json"; // the friendly service name to store secret in keytar @@ -227,3 +228,32 @@ export async function loadAccountId(accountName: string) { return undefined; } + +export async function loadTenantId(accountName: string) { + if (await fs.pathExists(tenantPath + accountName)) { + try { + return await fs.readFile(tenantPath + accountName, UTF8); + } catch (err) { + VsCodeLogInstance.warning( + localize("teamstoolkit.cacheAccess.readTenantIdFail") + (err.message as string) + ); + } + } + + return undefined; +} + +export async function saveTenantId(accountName: string, tenantId?: string) { + await fs.ensureDir(cacheDir); + try { + if (tenantId) { + await fs.writeFile(tenantPath + accountName, tenantId, UTF8); + } else { + await fs.writeFile(tenantPath + accountName, "", UTF8); + } + } catch (err) { + VsCodeLogInstance.warning( + localize("teamstoolkit.cacheAccess.saveTenantIdFail") + (err.message as string) + ); + } +} diff --git a/packages/vscode-extension/src/commonlib/codeFlowLogin.ts b/packages/vscode-extension/src/commonlib/codeFlowLogin.ts index 820aa4ea39..3084e6976d 100644 --- a/packages/vscode-extension/src/commonlib/codeFlowLogin.ts +++ b/packages/vscode-extension/src/commonlib/codeFlowLogin.ts @@ -21,7 +21,14 @@ import { FxError, ok, Result, UserError, err } from "@microsoft/teamsfx-api"; import VsCodeLogInstance from "./log"; import * as crypto from "crypto"; import { AddressInfo } from "net"; -import { clearCache, loadAccountId, saveAccountId, UTF8 } from "./cacheAccess"; +import { + clearCache, + loadAccountId, + loadTenantId, + saveAccountId, + saveTenantId, + UTF8, +} from "./cacheAccess"; import * as stringUtil from "util"; import { codeSpacesAuthComplete, @@ -44,7 +51,9 @@ import { env, Uri } from "vscode"; import { randomBytes } from "crypto"; import { getExchangeCode } from "./exchangeCode"; import * as os from "os"; -import { ErrorCategory } from "@microsoft/teamsfx-core"; +import { ErrorCategory, featureFlagManager, FeatureFlags } from "@microsoft/teamsfx-core"; + +const BASE_AUTHORITY = "https://login.microsoftonline.com/"; interface Deferred { resolve: (result: T | Promise) => void; reject: (reason: any) => void; @@ -89,7 +98,7 @@ export class CodeFlowLogin { } } - async login(scopes: Array, loginHint?: string): Promise { + async login(scopes: Array, loginHint?: string, tenantId?: string): Promise { if (process.env.CODESPACES == "true") { return await this.loginInCodeSpace(scopes); } @@ -108,6 +117,10 @@ export class CodeFlowLogin { const app = express(); const server = app.listen(serverPort); serverPort = (server.address() as AddressInfo).port; + const authority = + featureFlagManager.getBooleanValue(FeatureFlags.MultiTenant) && tenantId + ? BASE_AUTHORITY + tenantId + : undefined; const authCodeUrlParameters: AuthorizationUrlRequest = { scopes: scopes, @@ -116,6 +129,7 @@ export class CodeFlowLogin { redirectUri: `http://localhost:${serverPort}`, prompt: !loginHint ? "select_account" : "login", loginHint, + authority: authority, }; let deferredRedirect: Deferred; @@ -220,7 +234,9 @@ export class CodeFlowLogin { [TelemetryProperty.AccountType]: this.accountName, [TelemetryProperty.Success]: TelemetrySuccess.Yes, [TelemetryProperty.UserId]: (tokenJson as any).oid ? (tokenJson as any).oid : "", - [TelemetryProperty.Internal]: (tokenJson as any).upn?.endsWith("@microsoft.com") + [TelemetryProperty.Internal]: ( + (tokenJson as any).upn ?? (tokenJson as any).unique_name + ).endsWith("@microsoft.com") ? "true" : "false", }); @@ -287,6 +303,7 @@ export class CodeFlowLogin { async logout(): Promise { try { await saveAccountId(this.accountName, undefined); + await saveTenantId(this.accountName, undefined); (this.msalTokenCache as any).storage.setCache({}); await clearCache(this.accountName); this.account = undefined; @@ -310,75 +327,79 @@ export class CodeFlowLogin { } } - /** - * @deprecated will be removed after unify m365 login - */ - async getToken(refresh = true): Promise { - try { - if (!this.account) { - const accessToken = await this.login(this.scopes); - return accessToken; - } else { - return this.pca - .acquireTokenSilent({ - account: this.account, - scopes: this.scopes, - forceRefresh: false, - }) - .then((response) => { - if (response) { - return response.accessToken; - } else { - return undefined; - } - }) - .catch(async (error) => { - VsCodeLogInstance.debug( - "[Login] " + - stringUtil.format( - localize("teamstoolkit.codeFlowLogin.silentAcquireToken"), - path.join(os.homedir(), ".fx", "account"), - error.message - ) - ); - if (!(await checkIsOnline())) { - return undefined; - } - await this.logout(); - if (refresh) { - const accessToken = await this.login(this.scopes); - return accessToken; - } - return undefined; - }); + async getTokenByScopes( + scopes: Array, + refresh = true, + loginHint?: string, + tenantId?: string + ): Promise> { + if (featureFlagManager.getBooleanValue(FeatureFlags.MultiTenant)) { + if (!tenantId) { + tenantId = await loadTenantId(this.accountName); } - } catch (error) { - VsCodeLogInstance.error("[Login] " + (error.message as string)); - if ( - error.name !== getDefaultString("teamstoolkit.codeFlowLogin.loginTimeoutTitle") && - error.name !== getDefaultString("teamstoolkit.codeFlowLogin.loginPortConflictTitle") - ) { - throw LoginCodeFlowError(error); - } else { - throw error; + return await this.getToken(scopes, refresh, tenantId, loginHint); + } + + if (!this.account) { + const accessToken = await this.login(scopes, loginHint); + return ok(accessToken); + } else { + try { + const res = await this.pca.acquireTokenSilent({ + account: this.account, + scopes: scopes, + forceRefresh: false, + }); + if (res) { + return ok(res.accessToken); + } else { + return err(LoginCodeFlowError(new Error("No token response."))); + } + } catch (error) { + VsCodeLogInstance.debug( + "[Login] " + + stringUtil.format( + localize("teamstoolkit.codeFlowLogin.silentAcquireToken"), + path.join(os.homedir(), ".fx", "account"), + error.message + ) + ); + if (!(await checkIsOnline())) { + return err(CheckOnlineError()); + } + await this.logout(); + if (refresh) { + const accessToken = await this.login(scopes, loginHint); + return ok(accessToken); + } + return err(LoginCodeFlowError(error)); } } } - async getTokenByScopes( + // For multi-tenant support, the legacy function wil be removed later + async getToken( scopes: Array, refresh = true, + tenantId?: string, loginHint?: string ): Promise> { if (!this.account) { - const accessToken = await this.login(scopes, loginHint); + const accessToken = await this.login(scopes, loginHint, tenantId); return ok(accessToken); } else { + let tenantedAccount: AccountInfo | undefined = undefined; + if (tenantId) { + const allAccounts = await this.msalTokenCache.getAllAccounts(); + tenantedAccount = allAccounts.find((account) => account.tenantId == tenantId); + } + try { const res = await this.pca.acquireTokenSilent({ - account: this.account, + account: tenantedAccount ? tenantedAccount : this.account, scopes: scopes, - forceRefresh: false, + forceRefresh: tenantedAccount ? false : true, + authority: tenantId ? BASE_AUTHORITY + tenantId : this.config.auth.authority, }); if (res) { return ok(res.accessToken); @@ -399,7 +420,7 @@ export class CodeFlowLogin { } await this.logout(); if (refresh) { - const accessToken = await this.login(scopes, loginHint); + const accessToken = await this.login(scopes, loginHint, tenantId); return ok(accessToken); } return err(LoginCodeFlowError(error)); @@ -432,6 +453,10 @@ export class CodeFlowLogin { } } + async switchTenant(tenantId: string): Promise { + return await saveTenantId(this.accountName, tenantId); + } + async startServer(server: http.Server, port: number): Promise { // handle port timeout let defferedPort: Deferred; diff --git a/packages/vscode-extension/src/commonlib/common/constant.ts b/packages/vscode-extension/src/commonlib/common/constant.ts index 684f12bee8..17e3c07b30 100644 --- a/packages/vscode-extension/src/commonlib/common/constant.ts +++ b/packages/vscode-extension/src/commonlib/common/constant.ts @@ -13,6 +13,7 @@ export const switching = "Switching"; export const initializing = "Initializing"; export const m365CacheName = "m365"; +export const azureCacheName = "azure"; export const extensionID = "TeamsDevApp.ms-teams-vscode-extension"; export const codeSpacesAuthComplete = "auth-complete"; diff --git a/packages/vscode-extension/src/commonlib/m365Login.ts b/packages/vscode-extension/src/commonlib/m365Login.ts index b90d7f9f3f..b0c00aa8e9 100644 --- a/packages/vscode-extension/src/commonlib/m365Login.ts +++ b/packages/vscode-extension/src/commonlib/m365Login.ts @@ -15,9 +15,10 @@ import { LoginStatus, BasicLogin, UserError, + SystemError, } from "@microsoft/teamsfx-api"; import { AccountInfo, LogLevel } from "@azure/msal-node"; -import { ExtensionErrors } from "../error/error"; +import { ExtensionErrors, ExtensionSource } from "../error/error"; import { CodeFlowLogin, ConvertTokenToJson, UserCancelError } from "./codeFlowLogin"; import VsCodeLogInstance from "./log"; import * as vscode from "vscode"; @@ -212,6 +213,30 @@ export class M365Login extends BasicLogin implements M365TokenProvider { return true; } + async switchTenant(tenantId: string): Promise> { + try { + const res = await M365Login.codeFlowInstance.getTokenByScopes( + AppStudioScopes, + true, + undefined, + tenantId + ); + if (res.isOk()) { + await M365Login.codeFlowInstance.switchTenant(tenantId); + await this.notifyStatus({ scopes: AppStudioScopes }); + } + return res; + } catch (e) { + return err( + new SystemError({ + error: e, + source: ExtensionSource, + name: ExtensionErrors.LoginCacheError, + }) + ); + } + } + private async doesUserConfirmLogin(): Promise { const message = localize("teamstoolkit.appStudioLogin.message"); const signin = localize("teamstoolkit.common.signin"); diff --git a/packages/vscode-extension/src/commonlib/vscodeAzureSubscriptionProvider.ts b/packages/vscode-extension/src/commonlib/vscodeAzureSubscriptionProvider.ts index b374100cc2..45605ced16 100644 --- a/packages/vscode-extension/src/commonlib/vscodeAzureSubscriptionProvider.ts +++ b/packages/vscode-extension/src/commonlib/vscodeAzureSubscriptionProvider.ts @@ -5,7 +5,7 @@ import { SubscriptionClient, TenantIdDescription } from "@azure/arm-resources-su import { TokenCredential } from "@azure/core-auth"; import * as vscode from "vscode"; import * as azureEnv from "@azure/ms-rest-azure-env"; -import { AzureScopes } from "@microsoft/teamsfx-core"; +import { AzureScopes, featureFlagManager, FeatureFlags } from "@microsoft/teamsfx-core"; import { LoginFailureError } from "./codeFlowLogin"; import { Environment } from "@azure/ms-rest-azure-env"; @@ -72,19 +72,24 @@ export class VSCodeAzureSubscriptionProvider { /** * Gets a list of Azure subscriptions available to the user. */ - public async getSubscriptions(): Promise { + public async getSubscriptions(tenantId?: string): Promise { const results: AzureSubscription[] = []; - for (const tenant of await this.getTenants()) { - try { - // Get the list of tenants - // eslint-disable-next-line @typescript-eslint/no-non-null-assertion - const tenantId = tenant.tenantId!; - - // For each tenant, get the list of subscriptions - results.push(...(await this.getSubscriptionsForTenant(tenantId))); - } catch (e) {} + if (featureFlagManager.getBooleanValue(FeatureFlags.MultiTenant) && tenantId) { + results.push(...(await this.getSubscriptionsForTenant(tenantId))); + } else { + for (const tenant of await this.getTenants()) { + try { + // Get the list of tenants + // eslint-disable-next-line @typescript-eslint/no-non-null-assertion + const tenantId = tenant.tenantId!; + + // For each tenant, get the list of subscriptions + results.push(...(await this.getSubscriptionsForTenant(tenantId))); + } catch (e) {} + } } + const sortSubscriptions = (subscriptions: AzureSubscription[]): AzureSubscription[] => subscriptions.sort((a, b) => a.name.localeCompare(b.name)); return sortSubscriptions(results); diff --git a/packages/vscode-extension/src/constants.ts b/packages/vscode-extension/src/constants.ts index f7076ee5f0..9c0b723643 100644 --- a/packages/vscode-extension/src/constants.ts +++ b/packages/vscode-extension/src/constants.ts @@ -36,6 +36,7 @@ export enum GlobalKey { SampleGalleryLayout = "teamsToolkit:sampleGallery:layout", SampleGalleryInitialSample = "teamsToolkit:sampleGallery:initialSample", AutoInstallDependency = "teamsToolkit:autoInstallDependency", + DoNotRemindInstallTeamsAgent = "teamsToolkit:doNotRemindInstallTeamsAgent", } export enum CommandKey { diff --git a/packages/vscode-extension/src/controls/PanelType.ts b/packages/vscode-extension/src/controls/PanelType.ts index b222973222..a06a5ebfc6 100644 --- a/packages/vscode-extension/src/controls/PanelType.ts +++ b/packages/vscode-extension/src/controls/PanelType.ts @@ -6,5 +6,5 @@ export enum PanelType { RespondToCardActions = "respond-to-card-actions", AccountHelp = "account-help", FunctionBasedNotificationBotReadme = "function-based-notification-bot-readme", - RestifyServerNotificationBotReadme = "restify-server-notification-bot-readme", + ExpressServerNotificationBotReadme = "express-server-notification-bot-readme", } diff --git a/packages/vscode-extension/src/controls/index.tsx b/packages/vscode-extension/src/controls/index.tsx index b7fed20779..7c736f705c 100644 --- a/packages/vscode-extension/src/controls/index.tsx +++ b/packages/vscode-extension/src/controls/index.tsx @@ -9,7 +9,7 @@ import { PanelType } from "./PanelType"; import SampleGallery from "./sampleGallery/SampleGallery"; import AccountHelp from "./webviewDocs/accountHelp"; import FunctionBasedNotificationBot from "./webviewDocs/functionBasedNotificationBot"; -import RestifyServerNotificationBot from "./webviewDocs/restifyServerNotificationBot"; +import ExpressServerNotificationBot from "./webviewDocs/expressServerNotificationBot"; import WorkflowBot from "./webviewDocs/workflowBot"; const language = "en"; @@ -32,7 +32,7 @@ function App(props: any) { initialIndex = 2; } else if (panelType === PanelType.FunctionBasedNotificationBotReadme) { initialIndex = 3; - } else if (panelType === PanelType.RestifyServerNotificationBotReadme) { + } else if (panelType === PanelType.ExpressServerNotificationBotReadme) { initialIndex = 4; } @@ -43,7 +43,7 @@ function App(props: any) { "/respond-to-card-actions", "/account-help", "/function-based-notification-bot", - "/restify-server-notification-bot", + "/express-server-notification-bot", ]} initialIndex={initialIndex} > @@ -54,7 +54,7 @@ function App(props: any) { - + ); } diff --git a/packages/vscode-extension/src/controls/webviewDocs/restifyServerNotificationBot.tsx b/packages/vscode-extension/src/controls/webviewDocs/expressServerNotificationBot.tsx similarity index 97% rename from packages/vscode-extension/src/controls/webviewDocs/restifyServerNotificationBot.tsx rename to packages/vscode-extension/src/controls/webviewDocs/expressServerNotificationBot.tsx index da3d7579a4..2c9a4f9bd5 100644 --- a/packages/vscode-extension/src/controls/webviewDocs/restifyServerNotificationBot.tsx +++ b/packages/vscode-extension/src/controls/webviewDocs/expressServerNotificationBot.tsx @@ -16,11 +16,11 @@ import ExternalLink from "./components/externalLink"; import { useEffect } from "react"; import NotificationAdaptiveCard from "../../../img/webview/guide/notification-sends-adaptive-card.png"; -export default function RestifyServerNotificationBot() { +export default function ExpressServerNotificationBot() { let scrollToBottom = false; const [theme, setTheme] = React.useState("light"); - const name = "restify-server-notification-bot"; + const name = "express-server-notification-bot"; useEffect(() => { let currentTheme = document.body.className; @@ -163,7 +163,7 @@ export default function RestifyServerNotificationBot() { @@ -218,7 +218,7 @@ export default function RestifyServerNotificationBot() { src/index.js @@ -247,10 +247,10 @@ export default function RestifyServerNotificationBot() { step={1} title="Customize the trigger point from event source" triggerFrom={TelemetryTriggerFrom.InProductDoc} - identifier="restify-server-notification-bot-step1" + identifier="express-server-notification-bot-step1" >

- By default Teams Toolkit scaffolds a single restify entry + By default Teams Toolkit scaffolds a single express entry point in src/index.js. When a HTTP request is sent to this entry point, the default implementation sends a hard-coded Adaptive Card to Teams. You can customize this behavior by customizing src/index.js. A @@ -288,7 +288,7 @@ export default function RestifyServerNotificationBot() { step={2} title="Customize the notification content" triggerFrom={TelemetryTriggerFrom.InProductDoc} - identifier="restify-server-notification-bot-step2" + identifier="express-server-notification-bot-step2" >

src/adaptiveCards/notification-default.json defines the @@ -328,7 +328,7 @@ export default function RestifyServerNotificationBot() { step={3} title="Customize where notifications are sent" triggerFrom={TelemetryTriggerFrom.InProductDoc} - identifier="restify-server-notification-bot-step3" + identifier="express-server-notification-bot-step3" >

Notifications can be sent to where the bot is installed:

    diff --git a/packages/vscode-extension/src/controls/webviewDocs/workflowBot.tsx b/packages/vscode-extension/src/controls/webviewDocs/workflowBot.tsx index d7743a80d3..941e4009a0 100644 --- a/packages/vscode-extension/src/controls/webviewDocs/workflowBot.tsx +++ b/packages/vscode-extension/src/controls/webviewDocs/workflowBot.tsx @@ -298,7 +298,7 @@ module.exports = { src/index.js
diff --git a/packages/vscode-extension/src/controls/webviewPanel.ts b/packages/vscode-extension/src/controls/webviewPanel.ts index 1cf53d5d87..7cbb03ba4d 100644 --- a/packages/vscode-extension/src/controls/webviewPanel.ts +++ b/packages/vscode-extension/src/controls/webviewPanel.ts @@ -110,7 +110,7 @@ export class WebviewPanel { TreatmentVariableValue.inProductDoc && (panelType === PanelType.RespondToCardActions || panelType === PanelType.FunctionBasedNotificationBotReadme || - panelType === PanelType.RestifyServerNotificationBotReadme) + panelType === PanelType.ExpressServerNotificationBotReadme) ) { ExtTelemetry.sendTelemetryEvent(TelemetryEvent.InteractWithInProductDoc, { [TelemetryProperty.TriggerFrom]: TelemetryTriggerFrom.InProductDoc, @@ -309,7 +309,7 @@ export class WebviewPanel { return localize("teamstoolkit.guides.cardActionResponse.label"); case PanelType.AccountHelp: return localize("teamstoolkit.webview.accountHelp"); - case PanelType.RestifyServerNotificationBotReadme: + case PanelType.ExpressServerNotificationBotReadme: return localize("teamstoolkit.guides.notificationBot.label"); case PanelType.FunctionBasedNotificationBotReadme: return localize("teamstoolkit.guides.notificationBot.label"); diff --git a/packages/vscode-extension/src/debug/depsChecker/common.ts b/packages/vscode-extension/src/debug/depsChecker/common.ts index 2afce39af6..a163680950 100644 --- a/packages/vscode-extension/src/debug/depsChecker/common.ts +++ b/packages/vscode-extension/src/debug/depsChecker/common.ts @@ -7,6 +7,7 @@ import { FxError, M365TokenProvider, + OptionItem, Result, SystemError, UserError, @@ -27,6 +28,7 @@ import { PortsConflictError, SideloadingDisabledError, TelemetryContext, + UserCancelError, assembleError, getSideloadingStatus, } from "@microsoft/teamsfx-core"; @@ -39,7 +41,7 @@ import M365TokenInstance from "../../commonlib/m365Login"; import { PanelType } from "../../controls/PanelType"; import { WebviewPanel } from "../../controls/webviewPanel"; import { ExtensionErrors, ExtensionSource } from "../../error/error"; -import { tools, workspaceUri } from "../../globalVariables"; +import { LocalDebugPorts, resetLocalDebugPorts, tools, workspaceUri } from "../../globalVariables"; import { checkCopilotCallback } from "../../handlers/accounts/checkAccessCallback"; import { VS_CODE_UI } from "../../qm/vsc_ui"; import { ExtTelemetry } from "../../telemetry/extTelemetry"; @@ -66,6 +68,7 @@ import { } from "./prerequisitesCheckerConstants"; import { vscodeLogger } from "./vscodeLogger"; import { vscodeTelemetry } from "./vscodeTelemetry"; +import { processUtil } from "../../utils/processUtil"; export async function _checkAndInstall( displayMessages: DisplayMessages, @@ -146,18 +149,117 @@ async function runWithCheckResultTelemetryProperties( ); } +async function selectPortsToKill( + portsInUse: number[] +): Promise> { + const killRes = await VS_CODE_UI.showMessage( + "info", + portsInUse.length === 1 + ? util.format( + localize("teamstoolkit.localDebug.terminateProcess.notification"), + portsInUse[0] + ) + : util.format( + localize("teamstoolkit.localDebug.terminateProcess.notification.plural"), + portsInUse.join(",") + ), + true, + "Terminate Process", + "Learn More" + ); + + if (killRes.isErr()) { + LocalDebugPorts.terminateButton = "Cancel"; + return err(new UserCancelError(ExtensionSource)); + } + + const selectButton = killRes.value; + LocalDebugPorts.terminateButton = selectButton!; + + if (selectButton === "Terminate Process") { + const process2ports = new Map(); + for (const port of portsInUse) { + const processId = await processUtil.getProcessId(port); + if (processId) { + const ports = process2ports.get(processId); + if (ports) { + ports.push(port); + } else { + process2ports.set(processId, [port]); + } + } + } + if (process2ports.size > 0) { + const options: OptionItem[] = []; + for (const processId of process2ports.keys()) { + const ports = process2ports.get(processId); + LocalDebugPorts.process2conflictPorts[processId] = ports!; + const processInfo = await processUtil.getProcessInfo(parseInt(processId)); + options.push({ + id: processId, + label: `'${processInfo}' (${processId}) occupies port(s): ${ports!.join(",")}`, + data: processInfo, + }); + } + const res = await VS_CODE_UI.selectOptions({ + title: "Select process(es) to terminate", + name: "select_processes", + options, + default: options.map((o) => o.id), + }); + if (res.isOk() && res.value.type === "success") { + const processIds = res.value.result as string[]; + LocalDebugPorts.terminateProcesses = processIds; + for (const processId of processIds) { + await processUtil.killProcess(processId); + } + if (processIds.length > 0) { + const processInfo = options + .filter((o) => processIds.includes(o.id)) + .map((o) => `'${o.data as string}' (${o.id})`) + .join(", "); + void VS_CODE_UI.showMessage( + "info", + `Process(es) ${processInfo} have been killed.`, + false + ); + } + } else { + LocalDebugPorts.terminateProcesses = []; + return err(new UserCancelError(ExtensionSource)); + } + } + return ok(undefined); + } else if (selectButton === "Learn More") { + void VS_CODE_UI.openUrl( + "https://github.com/OfficeDev/teams-toolkit/wiki/%7BDebug%7D-FAQ#what-to-do-if-some-port-is-already-in-use" + ); + } + return err(new UserCancelError(ExtensionSource)); +} + async function checkPort( localEnvManager: LocalEnvManager, ports: number[], displayMessage: string, additionalTelemetryProperties: { [key: string]: string } ): Promise { + resetLocalDebugPorts(); + LocalDebugPorts.checkPorts = ports; return await runWithCheckResultTelemetryProperties( TelemetryEvent.DebugPrereqsCheckPorts, additionalTelemetryProperties, async (ctx: TelemetryContext) => { VsCodeLogInstance.outputChannel.appendLine(displayMessage); - const portsInUse = await localEnvManager.getPortsInUse(ports); + let portsInUse = await localEnvManager.getPortsInUse(ports); + LocalDebugPorts.conflictPorts = portsInUse; + if (portsInUse.length > 0) { + const killRes = await selectPortsToKill(portsInUse); + if (killRes.isOk()) { + // recheck + portsInUse = await localEnvManager.getPortsInUse(ports); + } + } const formatPortStr = (ports: number[]) => ports.length > 1 ? ports.join(", ") : `${ports[0]}`; if (portsInUse.length > 0) { diff --git a/packages/vscode-extension/src/debug/localTelemetryReporter.ts b/packages/vscode-extension/src/debug/localTelemetryReporter.ts index 49c52d9c44..c6b0e5cd62 100644 --- a/packages/vscode-extension/src/debug/localTelemetryReporter.ts +++ b/packages/vscode-extension/src/debug/localTelemetryReporter.ts @@ -25,6 +25,7 @@ import { getLocalDebugSession } from "./common/localDebugSession"; import { updateProjectStatus } from "../utils/projectStatusUtils"; import { CommandKey } from "../constants"; import { TeamsFxTaskType } from "./common/debugConstants"; +import detectPort from "detect-port"; function saveEventTime(eventName: string, time: number) { const session = getLocalDebugSession(); @@ -154,6 +155,23 @@ export async function sendDebugAllEvent( [TelemetryMeasurements.DebugServicesGapDuration]: servicesGap, }; + const closedPorts: number[] = []; + for (const port of globalVariables.LocalDebugPorts.checkPorts) { + const port2 = await detectPort(port); + if (port2 === port) { + closedPorts.push(port); + } + } + properties["debug-checked-ports"] = globalVariables.LocalDebugPorts.checkPorts.join(","); + properties["debug-closed-ports"] = closedPorts.join(","); + properties["debug-conflict-ports"] = globalVariables.LocalDebugPorts.conflictPorts.join(","); + properties["debug-terminate-button"] = globalVariables.LocalDebugPorts.terminateButton; + properties["debug-process2conflict-ports"] = JSON.stringify( + globalVariables.LocalDebugPorts.process2conflictPorts + ); + properties["debug-terminate-processes"] = + globalVariables.LocalDebugPorts.terminateProcesses.join(","); + if (error === undefined) { localTelemetryReporter.sendTelemetryEvent(TelemetryEvent.DebugAll, properties, measurements); } else { diff --git a/packages/vscode-extension/src/debug/teamsfxDebugProvider.ts b/packages/vscode-extension/src/debug/teamsfxDebugProvider.ts index 878a3851cc..7417ab0124 100644 --- a/packages/vscode-extension/src/debug/teamsfxDebugProvider.ts +++ b/packages/vscode-extension/src/debug/teamsfxDebugProvider.ts @@ -213,7 +213,7 @@ async function generateAccountHint(includeTenantId = true): Promise { if (tokenObject) { // user signed in tenantId = tokenObject.tid as string; - loginHint = tokenObject.upn as string; + loginHint = (tokenObject.upn as string) ?? (tokenObject.unique_name as string); } else { // no signed user loginHint = "login_your_m365_account"; // a workaround that user has the chance to login diff --git a/packages/vscode-extension/src/debug/teamsfxTaskHandler.ts b/packages/vscode-extension/src/debug/teamsfxTaskHandler.ts index e135979ecf..4d5bc0fbe9 100644 --- a/packages/vscode-extension/src/debug/teamsfxTaskHandler.ts +++ b/packages/vscode-extension/src/debug/teamsfxTaskHandler.ts @@ -46,6 +46,7 @@ import { } from "./common/localDebugSession"; import { allRunningDebugSessions } from "./officeTaskHandler"; import { deleteAad } from "./deleteAadHelper"; +import kill from "tree-kill"; class NpmInstallTaskInfo { private startTime: number; @@ -248,6 +249,9 @@ async function onDidStartTaskProcessHandler(event: vscode.TaskProcessStartEvent) return; } await sendDebugAllEvent(undefined, { [TelemetryProperty.DebugTestTool]: "true" }); + // Need to endLocalDebugSession() here. + // Otherwise, when user stops debugging, or task exits, it will incorrectly send an incorrect debug-all event with success=no + endLocalDebugSession(); } } } @@ -529,7 +533,7 @@ export function terminateAllRunningTeamsfxTasks(): void { for (const task of allRunningTeamsfxTasks) { try { if (task[1] > 0) { - process.kill(task[1], "SIGTERM"); + kill(task[1], "SIGTERM"); } } catch (e) { // ignore and keep killing others diff --git a/packages/vscode-extension/src/extension.ts b/packages/vscode-extension/src/extension.ts index 9817b69b53..196deb727b 100644 --- a/packages/vscode-extension/src/extension.ts +++ b/packages/vscode-extension/src/extension.ts @@ -200,6 +200,7 @@ import { ExtensionSurvey } from "./utils/survey"; import { getSettingsVersion, projectVersionCheck } from "./utils/telemetryUtils"; import { createPluginWithManifest } from "./handlers/createPluginWithManifestHandler"; import { manifestListener } from "./manifestListener"; +import { onSwitchAzureTenant, onSwitchM365Tenant } from "./handlers/accounts/switchTenantHandler"; export async function activate(context: vscode.ExtensionContext) { const value = IsChatParticipantEnabled && semver.gte(vscode.version, "1.90.0"); @@ -534,7 +535,7 @@ function registerInternalCommands(context: vscode.ExtensionContext) { if (featureFlagManager.getBooleanValue(FeatureFlags.KiotaIntegration)) { const createPluginWithManifestCommand = vscode.commands.registerCommand( "fx-extension.createprojectfromkiota", - () => Correlator.run(createPluginWithManifest) + (args) => Correlator.run(createPluginWithManifest, args) ); context.subscriptions.push(createPluginWithManifestCommand); } @@ -974,9 +975,27 @@ function registerAccountMenuCommands(context: vscode.ExtensionContext) { } }) ); + + const m365SwitchTenant = vscode.commands.registerCommand( + "fx-extension.m365SwitchTenant", + (...args) => Correlator.run(onSwitchM365Tenant, [TelemetryTriggerFrom.SideBar]) + ); + context.subscriptions.push(m365SwitchTenant); + + const azureSwitchTenant = vscode.commands.registerCommand( + "fx-extension.azureSwitchTenant", + (...args) => Correlator.run(onSwitchAzureTenant, [TelemetryTriggerFrom.SideBar]) + ); + context.subscriptions.push(azureSwitchTenant); } async function initializeContextKey(context: vscode.ExtensionContext, isTeamsFxProject: boolean) { + await vscode.commands.executeCommand( + "setContext", + "fx-extension.isMultiTenantEnabled", + featureFlagManager.getBooleanValue(CoreFeatureFlags.MultiTenant) + ); + await vscode.commands.executeCommand("setContext", "fx-extension.isSPFx", isSPFxProject); await vscode.commands.executeCommand( diff --git a/packages/vscode-extension/src/globalVariables.ts b/packages/vscode-extension/src/globalVariables.ts index c80c4dc0e5..160c8c2718 100644 --- a/packages/vscode-extension/src/globalVariables.ts +++ b/packages/vscode-extension/src/globalVariables.ts @@ -33,6 +33,30 @@ export let tools: Tools; export let diagnosticCollection: vscode.DiagnosticCollection; // Collection of diagnositcs after running app validation. export let deleteAadInProgress = false; +export interface ILocalDebugPorts { + checkPorts: number[]; + conflictPorts: number[]; + terminateButton: string; + process2conflictPorts: Record; + terminateProcesses: string[]; +} + +export const LocalDebugPorts: ILocalDebugPorts = { + checkPorts: [], + conflictPorts: [], + terminateButton: "", + process2conflictPorts: {}, + terminateProcesses: [], +}; + +export function resetLocalDebugPorts() { + LocalDebugPorts.checkPorts = []; + LocalDebugPorts.conflictPorts = []; + LocalDebugPorts.terminateButton = ""; + LocalDebugPorts.process2conflictPorts = {}; + LocalDebugPorts.terminateProcesses = []; +} + if (vscode.workspace && vscode.workspace.workspaceFolders) { if (vscode.workspace.workspaceFolders.length > 0) { workspaceUri = vscode.workspace.workspaceFolders[0].uri; diff --git a/packages/vscode-extension/src/handlers/accounts/accountHandlers.ts b/packages/vscode-extension/src/handlers/accounts/accountHandlers.ts index e482ecebaf..22b3fe1807 100644 --- a/packages/vscode-extension/src/handlers/accounts/accountHandlers.ts +++ b/packages/vscode-extension/src/handlers/accounts/accountHandlers.ts @@ -108,7 +108,7 @@ export async function cmpAccountsHandler(args: any[]) { const m365Account = m365AccountRes.isOk() ? m365AccountRes.value : undefined; if (m365Account && m365Account.status === "SignedIn") { const accountInfo = m365Account.accountInfo; - const email = (accountInfo as any).upn ? (accountInfo as any).upn : undefined; + const email = (accountInfo as any).upn ?? (accountInfo as any).unique_name ?? undefined; if (email !== undefined) { signOutM365Option.label = signOutM365Option.label.concat(email); } diff --git a/packages/vscode-extension/src/handlers/accounts/signinAccountHandlers.ts b/packages/vscode-extension/src/handlers/accounts/signinAccountHandlers.ts index c28add735d..4989a23dcd 100644 --- a/packages/vscode-extension/src/handlers/accounts/signinAccountHandlers.ts +++ b/packages/vscode-extension/src/handlers/accounts/signinAccountHandlers.ts @@ -34,7 +34,10 @@ export async function signinM365Callback(...args: unknown[]): Promise { + ExtTelemetry.sendTelemetryEvent(TelemetryEvent.SwitchTenantStart, { + [TelemetryProperty.AccountType]: AccountType.M365, + ...getTriggerFromProperty(args), + }); + + let error: FxError | undefined = undefined; + const tokenRes = await M365TokenInstance.getAccessToken({ + scopes: AzureScopes, + }); + if (tokenRes.isOk()) { + const config: SingleSelectConfig = { + name: "SwitchTenant", + title: localize("teamstoolkit.handlers.switchtenant.quickpick.title"), + options: async () => { + const tenants = await listAllTenants(tokenRes.value); + return tenants.map((tenant: any) => { + return { + id: tenant.tenantId, + label: tenant.displayName, + description: tenant.defaultDomain, + }; + }); + }, + }; + const result = await VS_CODE_UI.selectOption(config); + if (result.isOk()) { + const switchRes = await M365TokenInstance.switchTenant(result.value.result as string); + if (switchRes.isOk()) { + ExtTelemetry.sendTelemetryEvent(TelemetryEvent.SwitchTenant, { + [TelemetryProperty.AccountType]: AccountType.M365, + ...getTriggerFromProperty(args), + }); + return; + } else { + error = switchRes.error; + } + } else { + error = result.error; + } + } else { + error = tokenRes.error; + } + + if (!isUserCancelError(error)) { + void showError(error); + } + ExtTelemetry.sendTelemetryErrorEvent(TelemetryEvent.SwitchTenant, error, { + [TelemetryProperty.AccountType]: AccountType.M365, + ...getTriggerFromProperty(args), + }); +} + +export async function onSwitchAzureTenant(...args: unknown[]): Promise { + ExtTelemetry.sendTelemetryEvent(TelemetryEvent.SwitchTenantStart, { + [TelemetryProperty.AccountType]: AccountType.Azure, + ...getTriggerFromProperty(args), + }); + + const config: SingleSelectConfig = { + name: "SwitchTenant", + title: localize("teamstoolkit.handlers.switchtenant.quickpick.title"), + options: async () => { + const tokenCredential = await azureAccountManager.getIdentityCredentialAsync(false); + const token = tokenCredential ? await tokenCredential.getToken(AzureScopes) : undefined; + if (token && token.token) { + const tenants = await listAllTenants(token.token); + return tenants.map((tenant: any) => { + return { + id: tenant.tenantId, + label: tenant.displayName, + description: tenant.defaultDomain, + }; + }); + } else { + throw new SystemError( + ExtensionSource, + "SwitchTenantFailed", + localize("teamstoolkit.handlers.switchtenant.error") + ); + } + }, + }; + const result = await VS_CODE_UI.selectOption(config); + let error: any; + if (result.isOk()) { + const switchRes = await azureAccountManager.switchTenant(result.value.result as string); + if (switchRes.isOk()) { + ExtTelemetry.sendTelemetryEvent(TelemetryEvent.SwitchTenant, { + [TelemetryProperty.AccountType]: AccountType.Azure, + ...getTriggerFromProperty(args), + }); + return; + } else { + error = switchRes.error; + } + } else { + error = result.error; + } + + if (!isUserCancelError(error)) { + void showError(error); + } + ExtTelemetry.sendTelemetryErrorEvent(TelemetryEvent.SwitchTenant, error, { + [TelemetryProperty.AccountType]: AccountType.Azure, + ...getTriggerFromProperty(args), + }); +} diff --git a/packages/vscode-extension/src/handlers/copilotChatHandlers.ts b/packages/vscode-extension/src/handlers/copilotChatHandlers.ts index 0c48e906e3..3b809d6dc3 100644 --- a/packages/vscode-extension/src/handlers/copilotChatHandlers.ts +++ b/packages/vscode-extension/src/handlers/copilotChatHandlers.ts @@ -4,7 +4,7 @@ import * as util from "util"; import * as vscode from "vscode"; import { FxError, Result, SystemError, err, ok } from "@microsoft/teamsfx-api"; -import { assembleError } from "@microsoft/teamsfx-core"; +import { assembleError, globalStateGet, globalStateUpdate } from "@microsoft/teamsfx-core"; import { UserCancelError, sleep } from "@microsoft/vscode-ui"; import VsCodeLogInstance from "../commonlib/log"; import { ExtTelemetry } from "../telemetry/extTelemetry"; @@ -17,16 +17,12 @@ import { import { getTriggerFromProperty } from "../utils/telemetryUtils"; import { localize } from "../utils/localizeUtils"; import { showOutputChannelHandler } from "./showOutputChannel"; -import { InstallCopilotChatLink } from "../constants"; +import { GlobalKey, InstallCopilotChatLink } from "../constants"; import { isVSCodeInsiderVersion } from "../utils/versionUtil"; import { VS_CODE_UI } from "../qm/vsc_ui"; const githubCopilotChatExtensionId = "github.copilot-chat"; const teamsAgentLink = "https://aka.ms/install-teamsapp"; -enum installationTarget { - copilotChat = "copilot-chat", - teamsAgent = "teams-agent", -} function githubCopilotInstalled(): boolean { const extension = vscode.extensions.getExtension(githubCopilotChatExtensionId); @@ -64,20 +60,24 @@ async function openGithubCopilotChat(query: string): Promise> { - const eventName = "installCopilotChat"; +): Promise> { + const startEventName = "install-copilot-chat-start"; + const eventName = "install-copilot-chat"; const telemetryProperties = { [TelemetryProperty.TriggerFrom]: triggerFrom, }; - ExtTelemetry.sendTelemetryEvent(eventName, telemetryProperties); + ExtTelemetry.sendTelemetryEvent(startEventName, telemetryProperties); try { const confirmRes = await vscode.window.showInformationMessage( localize("teamstoolkit.handlers.askInstallCopilot"), - localize("teamstoolkit.handlers.askInstallCopilot.install"), - localize("teamstoolkit.handlers.askInstallCopilot.installTeamsApp") + localize("teamstoolkit.handlers.askInstallCopilot.install") ); - if (confirmRes === localize("teamstoolkit.handlers.askInstallCopilot.install")) { + if (confirmRes !== localize("teamstoolkit.handlers.askInstallCopilot.install")) { + const error = new UserCancelError(eventName, "cancel"); + ExtTelemetry.sendTelemetryErrorEvent(eventName, error, telemetryProperties); + return err(error); + } else { await vscode.commands.executeCommand( "workbench.extensions.installExtension", githubCopilotChatExtensionId, @@ -90,27 +90,9 @@ export async function installGithubCopilotChatExtension( ExtTelemetry.sendTelemetryEvent(eventName, { ...telemetryProperties, [TelemetryProperty.Success]: TelemetrySuccess.Yes, - [TelemetryProperty.InstallTarget]: installationTarget.copilotChat, }); - return ok({ installCopilot: true }); - } else if (confirmRes === localize("teamstoolkit.handlers.askInstallCopilot.installTeamsApp")) { - const openUrlRes = await VS_CODE_UI.openUrl(teamsAgentLink); - if (openUrlRes.isOk()) { - ExtTelemetry.sendTelemetryEvent(eventName, { - ...telemetryProperties, - [TelemetryProperty.Success]: TelemetrySuccess.Yes, - [TelemetryProperty.InstallTarget]: installationTarget.teamsAgent, - }); - return ok({ installCopilot: false }); - } else { - ExtTelemetry.sendTelemetryErrorEvent(eventName, openUrlRes.error, telemetryProperties); - return err(openUrlRes.error); - } - } else { - const error = new UserCancelError(eventName, "cancel"); - ExtTelemetry.sendTelemetryErrorEvent(eventName, error, telemetryProperties); - return err(error); + return ok(null); } } catch (e) { const error = new SystemError( @@ -131,10 +113,44 @@ export async function installGithubCopilotChatExtension( } } +export async function handleInstallTeamsAgentSelection( + selection: string | undefined, + telemetryProperties: { + [key: string]: string; + } +) { + const eventName = "install-teams-agent-notification"; + const selectionTelemetryPropertyName = "selection"; + if (selection === localize("teamstoolkit.handlers.askInstallTeamsAgent.install")) { + const installTelemetryProperties = { + ...telemetryProperties, + [selectionTelemetryPropertyName]: "install", + }; + const openUrlRes = await VS_CODE_UI.openUrl(teamsAgentLink); + if (openUrlRes.isOk()) { + ExtTelemetry.sendTelemetryEvent(eventName, { + ...installTelemetryProperties, + }); + } else { + ExtTelemetry.sendTelemetryErrorEvent(eventName, openUrlRes.error, installTelemetryProperties); + VsCodeLogInstance.error(openUrlRes.error.message); + } + } else if (selection === localize("teamstoolkit.handlers.askInstallTeamsAgent.confirmInstall")) { + ExtTelemetry.sendTelemetryEvent(eventName, { + ...telemetryProperties, + [selectionTelemetryPropertyName]: "confirmed", + }); + await globalStateUpdate(GlobalKey.DoNotRemindInstallTeamsAgent, true); + } else { + const error = new UserCancelError(eventName, "cancel"); + ExtTelemetry.sendTelemetryErrorEvent(eventName, error, telemetryProperties); + } +} + export async function invokeTeamsAgent(args?: any[]): Promise> { const eventName = TelemetryEvent.InvokeTeamsAgent; const triggerFromProperty = getTriggerFromProperty(args); - ExtTelemetry.sendTelemetryEvent(eventName, triggerFromProperty); + ExtTelemetry.sendTelemetryEvent(TelemetryEvent.InvokeTeamsAgentStart, triggerFromProperty); const query = triggerFromProperty["trigger-from"] === TelemetryTriggerFrom.TreeView || @@ -143,13 +159,33 @@ export async function invokeTeamsAgent(args?: any[]): Promise; + const skipRemindInstallTeamsAgent = await globalStateGet( + GlobalKey.DoNotRemindInstallTeamsAgent, + false + ); + if (!skipRemindInstallTeamsAgent) { + void vscode.window + .showInformationMessage( + localize("teamstoolkit.handlers.askInstallTeamsAgent"), + localize("teamstoolkit.handlers.askInstallTeamsAgent.install"), + localize("teamstoolkit.handlers.askInstallTeamsAgent.confirmInstall") + ) + .then(async (selection) => { + await handleInstallTeamsAgentSelection(selection, triggerFromProperty); + }); + } + const isExtensionInstalled = githubCopilotInstalled(); if (isExtensionInstalled) { + VsCodeLogInstance.info( + util.format(localize("teamstoolkit.handlers.installAgent.output"), teamsAgentLink) + ); + showOutputChannelHandler(); res = await openGithubCopilotChat(query); } else { VsCodeLogInstance.info( util.format( - localize("teamstoolkit.handlers.installExtension.output"), + localize("teamstoolkit.handlers.installCopilotAndAgent.output"), InstallCopilotChatLink, teamsAgentLink ) @@ -160,7 +196,7 @@ export async function invokeTeamsAgent(args?: any[]): Promise { +function handleTriggerKiotaCommand(args: any[], result: any, event: string): Result { if (!validateKiotaInstallation()) { void vscode.window .showInformationMessage( @@ -271,7 +278,7 @@ function handleTriggerKiotaCommand( } }); - ExtTelemetry.sendTelemetryEvent(TelemetryEvent.CreateProject, { + ExtTelemetry.sendTelemetryEvent(event, { [TelemetryProperty.KiotaInstalled]: "No", ...getTriggerFromProperty(args), }); @@ -286,9 +293,10 @@ function handleTriggerKiotaCommand( source: "ttk", ttkContext: { lastCommand: result.lastCommand, + manifestPath: result.manifestPath, }, }); - ExtTelemetry.sendTelemetryEvent(TelemetryEvent.CreateProject, { + ExtTelemetry.sendTelemetryEvent(event, { [TelemetryProperty.KiotaInstalled]: "Yes", ...getTriggerFromProperty(args), }); diff --git a/packages/vscode-extension/src/handlers/readmeHandlers.ts b/packages/vscode-extension/src/handlers/readmeHandlers.ts index ba6a5d448d..6916c9d4d6 100644 --- a/packages/vscode-extension/src/handlers/readmeHandlers.ts +++ b/packages/vscode-extension/src/handlers/readmeHandlers.ts @@ -61,14 +61,14 @@ export async function openReadMeHandler(...args: unknown[]) { const content = await fs.readFile(uri.fsPath, "utf8"); if (content.includes("## Get Started with the Notification bot")) { // A notification bot project. - if (content.includes("restify")) { - // Restify server notification bot. + if (content.includes("express")) { + // Express server notification bot. ExtTelemetry.sendTelemetryEvent(TelemetryEvent.InteractWithInProductDoc, { [TelemetryProperty.TriggerFrom]: TelemetryTriggerFrom.Auto, [TelemetryProperty.Interaction]: InProductGuideInteraction.Open, - [TelemetryProperty.Identifier]: PanelType.RestifyServerNotificationBotReadme, + [TelemetryProperty.Identifier]: PanelType.ExpressServerNotificationBotReadme, }); - WebviewPanel.createOrShow(PanelType.RestifyServerNotificationBotReadme); + WebviewPanel.createOrShow(PanelType.ExpressServerNotificationBotReadme); } else { ExtTelemetry.sendTelemetryEvent(TelemetryEvent.InteractWithInProductDoc, { [TelemetryProperty.TriggerFrom]: TelemetryTriggerFrom.Auto, diff --git a/packages/vscode-extension/src/migration/constants.ts b/packages/vscode-extension/src/migration/constants.ts index c37a6f16eb..716652315e 100644 --- a/packages/vscode-extension/src/migration/constants.ts +++ b/packages/vscode-extension/src/migration/constants.ts @@ -15,8 +15,8 @@ export class CommentMessages { export const teamsClientSDKName = "@microsoft/teams-js"; export const teamsClientSDKVersion = "^2.0.0"; export const teamsManifestSchema = - "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json"; -export const teamsManifestVersion = "1.17"; + "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json"; +export const teamsManifestVersion = "1.19"; export const teamsClientSDKDefaultNamespace = "microsoftTeams"; diff --git a/packages/vscode-extension/src/telemetry/extTelemetryEvents.ts b/packages/vscode-extension/src/telemetry/extTelemetryEvents.ts index 4967b0753e..231baa953a 100644 --- a/packages/vscode-extension/src/telemetry/extTelemetryEvents.ts +++ b/packages/vscode-extension/src/telemetry/extTelemetryEvents.ts @@ -20,6 +20,9 @@ export enum TelemetryEvent { SignOutStart = "sign-out-start", SignOut = "sign-out", + SwitchTenantStart = "switch-tenant-start", + SwitchTenant = "switch-tenant", + SelectSubscription = "select-subscription", CreateProjectStart = "create-project-start", @@ -274,6 +277,7 @@ export enum TelemetryEvent { FindSimilarIssues = "find-similar-issues", + InvokeTeamsAgentStart = "invoke-teams-agent-start", InvokeTeamsAgent = "invoke-teams-agent", // Copilot Chat @@ -297,6 +301,8 @@ export enum TelemetryEvent { Configuration = "vsc-configuration", UpdateAddPluginTreeview = "update-add-plugin-tree-view", + + AddPluginWithManifest = "add-plugin-with-manifest", } export enum TelemetryProperty { @@ -418,7 +424,6 @@ export enum TelemetryProperty { CopilotChatResponseToken = "copilot-chat-response-token", KiotaInstalled = "kiota-installed", ShowAddPluginTreeView = "show-add-plugin-tree-view", - InstallTarget = "install-target", } export enum TelemetryMeasurements { diff --git a/packages/vscode-extension/src/treeview/account/accountTreeViewProvider.ts b/packages/vscode-extension/src/treeview/account/accountTreeViewProvider.ts index e84aa08ce4..8b388414c2 100644 --- a/packages/vscode-extension/src/treeview/account/accountTreeViewProvider.ts +++ b/packages/vscode-extension/src/treeview/account/accountTreeViewProvider.ts @@ -72,8 +72,9 @@ async function m365AccountStatusChangeHandler( const instance = AccountTreeViewProvider.getInstance(); if (status === "SignedIn") { if (accountInfo) { - instance.m365AccountNode.setSignedIn( - (accountInfo.upn as string) ? (accountInfo.upn as string) : "" + await instance.m365AccountNode.setSignedIn( + (accountInfo.upn as string) ?? (accountInfo.unique_name as string) ?? "", + (accountInfo.tid as string) ?? "" ); if (token && source === "appStudio") { instance.m365AccountNode.updateChecks(token, true, true); @@ -99,7 +100,11 @@ async function azureAccountStatusChangeHandler( if (status === "SignedIn") { const username = (accountInfo?.email as string) || (accountInfo?.upn as string); if (username) { - instance.azureAccountNode.setSignedIn(username); + await instance.azureAccountNode.setSignedIn( + token as string, + accountInfo?.tid as string, + username + ); await envTreeProviderInstance.reloadEnvironments(); } } else if (status === "SigningIn") { diff --git a/packages/vscode-extension/src/treeview/account/azureNode.ts b/packages/vscode-extension/src/treeview/account/azureNode.ts index 69056f4716..eadd3665de 100644 --- a/packages/vscode-extension/src/treeview/account/azureNode.ts +++ b/packages/vscode-extension/src/treeview/account/azureNode.ts @@ -7,6 +7,8 @@ import { TelemetryTriggerFrom } from "../../telemetry/extTelemetryEvents"; import { localize } from "../../utils/localizeUtils"; import { DynamicNode } from "../dynamicNode"; import { AccountItemStatus, azureIcon, loadingIcon } from "./common"; +import { featureFlagManager, FeatureFlags } from "@microsoft/teamsfx-core"; +import { listAllTenants } from "@microsoft/teamsfx-core/build/common/tools"; export class AzureAccountNode extends DynamicNode { public status: AccountItemStatus; @@ -17,14 +19,22 @@ export class AzureAccountNode extends DynamicNode { this.contextValue = "signinAzure"; } - public setSignedIn(upn: string) { + public async setSignedIn(token: string, tid: string, upn: string) { if (this.status === AccountItemStatus.SignedIn && this.label === upn) { return false; } this.status = AccountItemStatus.SignedIn; this.label = upn; + if (featureFlagManager.getBooleanValue(FeatureFlags.MultiTenant)) { + const tenants = await listAllTenants(token); + for (const tenant of tenants) { + if (tenant.tenantId === tid && tenant.displayName) { + this.label = `${upn} (${tenant.displayName as string})`; + } + } + } this.contextValue = "signedinAzure"; - this.eventEmitter.fire(undefined); + this.eventEmitter.fire(this); return false; } diff --git a/packages/vscode-extension/src/treeview/account/m365Node.ts b/packages/vscode-extension/src/treeview/account/m365Node.ts index 86129fbddd..dec00bdcbc 100644 --- a/packages/vscode-extension/src/treeview/account/m365Node.ts +++ b/packages/vscode-extension/src/treeview/account/m365Node.ts @@ -1,7 +1,7 @@ // Copyright (c) Microsoft Corporation. // Licensed under the MIT license. -import { featureFlagManager, FeatureFlags as FxCoreFeatureFlags } from "@microsoft/teamsfx-core"; +import { AzureScopes, featureFlagManager, FeatureFlags } from "@microsoft/teamsfx-core"; import * as vscode from "vscode"; import { TelemetryTriggerFrom } from "../../telemetry/extTelemetryEvents"; import { localize } from "../../utils/localizeUtils"; @@ -9,11 +9,14 @@ import { DynamicNode } from "../dynamicNode"; import { AccountItemStatus, loadingIcon, m365Icon } from "./common"; import { CopilotNode } from "./copilotNode"; import { SideloadingNode } from "./sideloadingNode"; +import { tools } from "../../globalVariables"; +import { listAllTenants } from "@microsoft/teamsfx-core/build/common/tools"; export class M365AccountNode extends DynamicNode { public status: AccountItemStatus; private sideloadingNode: SideloadingNode; private copilotNode: CopilotNode | undefined; + private tid: string | undefined; constructor(private eventEmitter: vscode.EventEmitter) { super("", vscode.TreeItemCollapsibleState.None); @@ -23,12 +26,27 @@ export class M365AccountNode extends DynamicNode { this.copilotNode = new CopilotNode(this.eventEmitter, ""); } - public setSignedIn(upn: string) { - if (this.status === AccountItemStatus.SignedIn) { + public async setSignedIn(displayName: string, tid: string) { + if (this.status === AccountItemStatus.SignedIn && this.tid && this.tid === tid) { return; } this.status = AccountItemStatus.SignedIn; - this.label = upn; + + this.label = displayName; + if (featureFlagManager.getBooleanValue(FeatureFlags.MultiTenant)) { + const tokenRes = await tools.tokenProvider.m365TokenProvider.getAccessToken({ + scopes: AzureScopes, + }); + if (tokenRes.isOk() && tokenRes.value) { + const tenants = await listAllTenants(tokenRes.value); + for (const tenant of tenants) { + if (tenant.tenantId === tid && tenant.displayName) { + this.label = `${displayName} (${tenant.displayName as string})`; + this.tid = tid; + } + } + } + } this.contextValue = "signedinM365"; // refresh this.eventEmitter.fire(undefined); diff --git a/packages/vscode-extension/src/treeview/environmentTreeItem.ts b/packages/vscode-extension/src/treeview/environmentTreeItem.ts index 8c19f8a303..e16c506634 100644 --- a/packages/vscode-extension/src/treeview/environmentTreeItem.ts +++ b/packages/vscode-extension/src/treeview/environmentTreeItem.ts @@ -122,7 +122,7 @@ export class EnvironmentNode extends DynamicNode { const provisionedSubId = subscriptionInfo?.subscriptionId; if (provisionedSubId) { - const subscriptions: SubscriptionInfo[] = await azureAccountManager.listSubscriptions(); + const subscriptions: SubscriptionInfo[] = await azureAccountManager.listAllSubscriptions(); const targetSub = subscriptions.find( (sub) => sub.subscriptionId === subscriptionInfo?.subscriptionId ); diff --git a/packages/vscode-extension/src/utils/processUtil.ts b/packages/vscode-extension/src/utils/processUtil.ts new file mode 100644 index 0000000000..ded005968e --- /dev/null +++ b/packages/vscode-extension/src/utils/processUtil.ts @@ -0,0 +1,81 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT license. +import { exec } from "child_process"; + +class ProcessUtil { + async getProcessId(port: number): Promise { + return new Promise((resolve, reject) => { + const command = + process.platform === "win32" ? `netstat -ano | findstr :${port}` : `lsof -i :${port}`; + exec(command, (error, stdout) => { + if (error) { + return reject(error); + } + if (stdout) { + if (process.platform === "win32") { + const lines = stdout.split("\n"); + const pidLine = lines.find((line) => line.includes(`:${port}`)); + if (pidLine) { + const pid = pidLine.trim().split(/\s+/).pop(); + resolve(pid || ""); + } else { + resolve(""); + } + } else { + const pid = stdout.split("\n")[1]?.split(/\s+/)[1]; + resolve(pid || ""); + } + } else { + resolve(""); + } + }); + }); + } + + async killProcess(pid: string): Promise { + return new Promise((resolve, reject) => { + const command = process.platform === "win32" ? `taskkill /PID ${pid} /F` : `kill -9 ${pid}`; + exec(command, (error) => { + if (error) { + return reject(error); + } + resolve(); + }); + }); + } + + async getProcessInfo(pid: number): Promise { + if (process.platform === "win32") return await this.getProcessInfoWindows(pid); + else return await this.getProcessCommandLineMac(pid); + } + + async getProcessInfoWindows(pid: number): Promise { + return new Promise((resolve, reject) => { + exec( + `wmic process where ProcessId=${pid} get CommandLine /value`, + (error, stdout, stderr) => { + if (error) { + reject(error); + } else { + const commandLine = stdout.split("=")[1]?.trim(); + resolve(commandLine || "No CommandLine found"); + } + } + ); + }); + } + + async getProcessCommandLineMac(pid: number): Promise { + return new Promise((resolve, reject) => { + exec(`ps -p ${pid} -o command=`, (error, stdout, stderr) => { + if (error) { + reject(error); + } else { + resolve(stdout.trim()); + } + }); + }); + } +} + +export const processUtil = new ProcessUtil(); diff --git a/packages/vscode-extension/test/handlers/accounts/accountHandlers.test.ts b/packages/vscode-extension/test/handlers/accounts/accountHandlers.test.ts index 728736047a..b3ddd4008a 100644 --- a/packages/vscode-extension/test/handlers/accounts/accountHandlers.test.ts +++ b/packages/vscode-extension/test/handlers/accounts/accountHandlers.test.ts @@ -165,6 +165,41 @@ describe("AccountHandlers", () => { chai.expect(executeCommandStub.args[2][0]).to.be.equal("fx-extension.signinAzure"); chai.assert.isTrue(hideStub.calledOnce); }); + + it("Sign out happy path - unique_name", async () => { + sandbox.stub(vscode.window, "showInformationMessage").resolves(undefined); + sandbox.stub(M365TokenInstance, "signout"); + sandbox + .stub(M365TokenInstance, "getStatus") + .resolves(ok({ status: "SignedIn", accountInfo: { unique_name: "test.email.com" } })); + sandbox + .stub(AzureAccountManager.prototype, "getStatus") + .resolves({ status: "SignedIn", accountInfo: { upn: "test.email.com" } }); + sandbox.stub(stubQuickPick, "hide"); + + await cmpAccountsHandler([]); + + chai.assert.isTrue((stubQuickPick.items[0].label as string).includes("test.email.com")); + }); + + it("Sign out happy path - undefined", async () => { + sandbox.stub(vscode.window, "showInformationMessage").resolves(undefined); + sandbox.stub(M365TokenInstance, "signout"); + sandbox + .stub(M365TokenInstance, "getStatus") + .resolves(ok({ status: "SignedIn", accountInfo: {} })); + sandbox + .stub(AzureAccountManager.prototype, "getStatus") + .resolves({ status: "SignedIn", accountInfo: { upn: "test.email.com" } }); + sandbox.stub(stubQuickPick, "hide"); + + await cmpAccountsHandler([]); + + chai.assert.equal( + stubQuickPick.items[0].label as string, + localizeUtils.localize("teamstoolkit.handlers.signOutOfM365") + ); + }); }); describe("azureAccountSignOutHelpHandler", () => { diff --git a/packages/vscode-extension/test/handlers/accounts/signinAccountHandlers.test.ts b/packages/vscode-extension/test/handlers/accounts/signinAccountHandlers.test.ts index 02772f9f43..9f9db611ec 100644 --- a/packages/vscode-extension/test/handlers/accounts/signinAccountHandlers.test.ts +++ b/packages/vscode-extension/test/handlers/accounts/signinAccountHandlers.test.ts @@ -1,7 +1,7 @@ import * as sinon from "sinon"; import * as chai from "chai"; import * as vscode from "vscode"; -import { UserCancelError } from "@microsoft/teamsfx-core"; +import { NetworkError, UserCancelError } from "@microsoft/teamsfx-core"; import { AzureAccountManager } from "../../../src/commonlib/azureLogin"; import { signinAzureCallback, @@ -9,11 +9,7 @@ import { } from "../../../src/handlers/accounts/signinAccountHandlers"; import { ExtTelemetry } from "../../../src/telemetry/extTelemetry"; import { setTools, tools } from "../../../src/globalVariables"; -import { ok } from "@microsoft/teamsfx-api"; -import VsCodeLogInstance from "../../../src/commonlib/log"; -import { VsCodeUI } from "../../../src/qm/vsc_ui"; -import { getExpService } from "../../../src/exp"; -import M365TokenInstance from "../../../src/commonlib/m365Login"; +import { err, ok } from "@microsoft/teamsfx-api"; import { MockTools } from "../../mocks/mockTools"; describe("SigninAccountHandlers", () => { @@ -85,12 +81,72 @@ describe("SigninAccountHandlers", () => { sandbox.stub(ExtTelemetry, "sendTelemetryEvent"); }); - it("Happy path", async () => { + it("Happy path - valid upn", async () => { const setSignedInStub = sandbox.stub(); const getJsonObjectStub = sandbox .stub(tools.tokenProvider.m365TokenProvider, "getJsonObject") .returns(Promise.resolve(ok({ upn: "test" }))); + await signinM365Callback( + {}, + { + status: 0, + setSignedIn: (...args: any[]) => { + setSignedInStub(args); + }, + } + ); + + chai.assert.isTrue(getJsonObjectStub.calledOnce); + chai.assert.isTrue(setSignedInStub.calledOnceWith(["test", ""])); + }); + + it("Happy path - valid tid", async () => { + const setSignedInStub = sandbox.stub(); + const getJsonObjectStub = sandbox + .stub(tools.tokenProvider.m365TokenProvider, "getJsonObject") + .returns(Promise.resolve(ok({ tid: "test" }))); + + await signinM365Callback( + {}, + { + status: 0, + setSignedIn: (...args: any[]) => { + setSignedInStub(args); + }, + } + ); + + chai.assert.isTrue(getJsonObjectStub.calledOnce); + chai.assert.isTrue(setSignedInStub.calledOnceWith(["", "test"])); + }); + + it("Happy path - valid upn & tid", async () => { + const setSignedInStub = sandbox.stub(); + const getJsonObjectStub = sandbox + .stub(tools.tokenProvider.m365TokenProvider, "getJsonObject") + .returns(Promise.resolve(ok({ upn: "test upn", tid: "test tid" }))); + + await signinM365Callback( + {}, + { + status: 0, + setSignedIn: (...args: any[]) => { + setSignedInStub(args); + }, + } + ); + + chai.assert.isTrue(getJsonObjectStub.calledOnce); + chai.assert.isTrue(setSignedInStub.calledOnceWith(["test upn", "test tid"])); + }); + + it("invalid token result", async () => { + const setSignedInStub = sandbox.stub(); + const getJsonObjectStub = sandbox + .stub(tools.tokenProvider.m365TokenProvider, "getJsonObject") + .returns(Promise.resolve(err(new NetworkError("source", "Failed to retrieve token")))); + await signinM365Callback( {}, { @@ -102,7 +158,7 @@ describe("SigninAccountHandlers", () => { ); chai.assert.isTrue(getJsonObjectStub.calledOnce); - chai.assert.isTrue(setSignedInStub.calledOnceWith("test")); + chai.assert.isTrue(setSignedInStub.notCalled); }); it("Signed in", async () => { diff --git a/packages/vscode-extension/test/handlers/accounts/switchTenantHandler.test.ts b/packages/vscode-extension/test/handlers/accounts/switchTenantHandler.test.ts new file mode 100644 index 0000000000..d82addb740 --- /dev/null +++ b/packages/vscode-extension/test/handlers/accounts/switchTenantHandler.test.ts @@ -0,0 +1,280 @@ +import * as sinon from "sinon"; +import * as chai from "chai"; +import * as vscode from "vscode"; + +import { ExtTelemetry } from "../../../src/telemetry/extTelemetry"; +import M365TokenInstance from "../../../src/commonlib/m365Login"; +import azureAccountManager from "../../../src/commonlib/azureLogin"; +import { err, ok, SystemError } from "@microsoft/teamsfx-api"; +import { NetworkError, UserCancelError } from "@microsoft/teamsfx-core"; +import { + onSwitchM365Tenant, + onSwitchAzureTenant, +} from "../../../src/handlers/accounts/switchTenantHandler"; +import { TelemetryTriggerFrom } from "../../../src/telemetry/extTelemetryEvents"; +import * as tool from "@microsoft/teamsfx-core/build/common/tools"; +import * as vsc_ui from "../../../src/qm/vsc_ui"; +import { LoginFailureError } from "../../../src/commonlib/codeFlowLogin"; + +describe("onSwitchM365Tenant", () => { + const sandbox = sinon.createSandbox(); + let sendTelemetryEventStub: sinon.SinonStub; + let sendTelemetryErrorEventStub: sinon.SinonStub; + let selectOptionStub: sinon.SinonStub; + + beforeEach(() => { + sendTelemetryEventStub = sandbox.stub(ExtTelemetry, "sendTelemetryEvent"); + sendTelemetryErrorEventStub = sandbox.stub(ExtTelemetry, "sendTelemetryErrorEvent"); + sandbox.stub(vsc_ui, "VS_CODE_UI").value(new vsc_ui.VsCodeUI({})); + }); + + afterEach(() => { + sandbox.restore(); + }); + + it("Failed to retrieve access token", async () => { + sandbox + .stub(M365TokenInstance, "getAccessToken") + .resolves(err(new NetworkError("extension", ""))); + + await onSwitchM365Tenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.args[0][1] instanceof NetworkError); + }); + + it("Failed to select tenant in UI", async () => { + sandbox.stub(M365TokenInstance, "getAccessToken").resolves(ok("faked token")); + sandbox.stub(M365TokenInstance, "switchTenant").resolves(ok("faked token")); + sandbox.stub(tool, "listAllTenants").resolves([ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + displayName: "MSFT", + defaultDomain: "t815h.onmicrosoft.com", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + displayName: "Cisco", + defaultDomain: "Cisco561.onmicrosoft.com", + }, + ]); + selectOptionStub = sandbox + .stub(vsc_ui.VS_CODE_UI, "selectOption") + .resolves(err(new UserCancelError())); + + await onSwitchM365Tenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.args[0][1] instanceof UserCancelError); + }); + + it("Failed to switch tenant", async () => { + sandbox.stub(M365TokenInstance, "getAccessToken").resolves(ok("faked token")); + sandbox + .stub(M365TokenInstance, "switchTenant") + .resolves(err(new NetworkError("extension", ""))); + sandbox.stub(tool, "listAllTenants").resolves([ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + displayName: "MSFT", + defaultDomain: "t815h.onmicrosoft.com", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + displayName: "Cisco", + defaultDomain: "Cisco561.onmicrosoft.com", + }, + ]); + selectOptionStub = sandbox + .stub(vsc_ui.VS_CODE_UI, "selectOption") + .resolves(ok({ type: "success" })); + + await onSwitchM365Tenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.args[0][1] instanceof NetworkError); + }); + + it("Succeed to switch tenant", async () => { + sandbox.stub(M365TokenInstance, "getAccessToken").resolves(ok("faked token")); + sandbox.stub(M365TokenInstance, "switchTenant").resolves(ok("faked token")); + sandbox.stub(tool, "listAllTenants").resolves([ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + displayName: "MSFT", + defaultDomain: "t815h.onmicrosoft.com", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + displayName: "Cisco", + defaultDomain: "Cisco561.onmicrosoft.com", + }, + ]); + selectOptionStub = sandbox + .stub(vsc_ui.VS_CODE_UI, "selectOption") + .resolves(ok({ type: "success" })); + + await onSwitchM365Tenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledTwice); + chai.assert.isTrue(sendTelemetryErrorEventStub.notCalled); + const items = await selectOptionStub.args[0][0].options(); + chai.assert.deepEqual(items, [ + { + id: "0022fd51-06f5-4557-8a34-69be98de6e20", + label: "MSFT", + description: "t815h.onmicrosoft.com", + }, + { + id: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + label: "Cisco", + description: "Cisco561.onmicrosoft.com", + }, + ]); + }); +}); + +describe("onSwitchAzureTenant", () => { + const sandbox = sinon.createSandbox(); + let sendTelemetryEventStub: sinon.SinonStub; + let sendTelemetryErrorEventStub: sinon.SinonStub; + let selectOptionStub: sinon.SinonStub; + + beforeEach(() => { + sendTelemetryEventStub = sandbox.stub(ExtTelemetry, "sendTelemetryEvent"); + sendTelemetryErrorEventStub = sandbox.stub(ExtTelemetry, "sendTelemetryErrorEvent"); + sandbox.stub(vsc_ui, "VS_CODE_UI").value(new vsc_ui.VsCodeUI({})); + }); + + afterEach(() => { + sandbox.restore(); + }); + + it("Failed to retrieve access token", async () => { + sandbox.stub(azureAccountManager, "getIdentityCredentialAsync").resolves({ + getToken: () => { + return Promise.resolve(null); + }, + }); + selectOptionStub = sandbox.stub(vsc_ui.VS_CODE_UI, "selectOption").resolves( + err({ + name: "switchTenantFailed", + source: "extension", + timestamp: new Date(), + message: "failed", + }) + ); + + await onSwitchAzureTenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.calledOnce); + try { + await selectOptionStub.args[0][0].options(); + } catch (e) { + chai.assert.isTrue(e instanceof SystemError); + } + }); + + it("User cancelled", async () => { + sandbox.stub(azureAccountManager, "getIdentityCredentialAsync").resolves({ + getToken: () => { + return Promise.resolve(null); + }, + }); + selectOptionStub = sandbox + .stub(vsc_ui.VS_CODE_UI, "selectOption") + .resolves(err(new UserCancelError())); + + await onSwitchAzureTenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.calledOnce); + }); + + it("Failed to switch tenant", async () => { + sandbox.stub(azureAccountManager, "getIdentityCredentialAsync").resolves({ + getToken: () => { + return Promise.resolve({ token: "faked token", expiresOnTimestamp: 0 }); + }, + }); + sandbox.stub(tool, "listAllTenants").resolves([ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + displayName: "MSFT", + defaultDomain: "t815h.onmicrosoft.com", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + displayName: "Cisco", + defaultDomain: "Cisco561.onmicrosoft.com", + }, + ]); + selectOptionStub = sandbox + .stub(vsc_ui.VS_CODE_UI, "selectOption") + .resolves(ok({ type: "success" })); + const switchTenantStub = sandbox + .stub(azureAccountManager, "switchTenant") + .resolves(err(LoginFailureError())); + + await onSwitchAzureTenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledOnce); + chai.assert.isTrue(sendTelemetryErrorEventStub.calledOnce); + chai.assert.isTrue(selectOptionStub.calledOnce); + chai.assert.isTrue(switchTenantStub.calledOnce); + }); + + it("Succeed to switch tenant", async () => { + sandbox.stub(azureAccountManager, "getIdentityCredentialAsync").resolves({ + getToken: () => { + return Promise.resolve({ token: "faked token", expiresOnTimestamp: 0 }); + }, + }); + sandbox.stub(tool, "listAllTenants").resolves([ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + displayName: "MSFT", + defaultDomain: "t815h.onmicrosoft.com", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + displayName: "Cisco", + defaultDomain: "Cisco561.onmicrosoft.com", + }, + ]); + selectOptionStub = sandbox + .stub(vsc_ui.VS_CODE_UI, "selectOption") + .resolves(ok({ type: "success" })); + const switchTenantStub = sandbox.stub(azureAccountManager, "switchTenant").resolves( + ok({ + getToken: () => { + return Promise.resolve(null); + }, + }) + ); + + await onSwitchAzureTenant(TelemetryTriggerFrom.SideBar); + + chai.assert.isTrue(sendTelemetryEventStub.calledTwice); + chai.assert.isTrue(sendTelemetryErrorEventStub.notCalled); + chai.assert.isTrue(selectOptionStub.calledOnce); + chai.assert.isTrue(switchTenantStub.calledOnce); + const items = await selectOptionStub.args[0][0].options(); + chai.assert.deepEqual(items, [ + { + id: "0022fd51-06f5-4557-8a34-69be98de6e20", + label: "MSFT", + description: "t815h.onmicrosoft.com", + }, + { + id: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + label: "Cisco", + description: "Cisco561.onmicrosoft.com", + }, + ]); + }); +}); diff --git a/packages/vscode-extension/test/handlers/copilotChatHandlers.test.ts b/packages/vscode-extension/test/handlers/copilotChatHandlers.test.ts index ca5f8bf30c..44bf9c2697 100644 --- a/packages/vscode-extension/test/handlers/copilotChatHandlers.test.ts +++ b/packages/vscode-extension/test/handlers/copilotChatHandlers.test.ts @@ -7,8 +7,10 @@ import * as handlers from "../../src/handlers/copilotChatHandlers"; import { ExtTelemetry } from "../../src/telemetry/extTelemetry"; import * as extTelemetryEvents from "../../src/telemetry/extTelemetryEvents"; import * as versionUtils from "../../src/utils/versionUtil"; -import { err, ok, SystemError } from "@microsoft/teamsfx-api"; +import * as globalState from "@microsoft/teamsfx-core/build/common/globalState"; +import { localize } from "../../src/utils/localizeUtils"; import * as vsc_ui from "../../src/qm/vsc_ui"; +import { err, ok, SystemError } from "@microsoft/teamsfx-api"; after(() => { sinon.restore(); @@ -43,6 +45,7 @@ describe("invokeTeamsAgent", async () => { }); it("no need to install Github Copilot", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(true); sandbox.stub(vscode.extensions, "getExtension").returns({ name: "github.copilot" } as any); sandbox.stub(vscode.commands, "executeCommand").resolves(); @@ -54,6 +57,7 @@ describe("invokeTeamsAgent", async () => { }); it("install Github Copilot and invoke Teams Agent", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(true); clock = sandbox.useFakeTimers(); sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); sandbox @@ -65,7 +69,9 @@ describe("invokeTeamsAgent", async () => { const commandStub = sandbox.stub(vscode.commands, "executeCommand").resolves(); sandbox .stub(vscode.window, "showInformationMessage") - .resolves("Install GitHub Copilot" as unknown as vscode.MessageItem); + .resolves( + localize("teamstoolkit.handlers.askInstallCopilot.install") as unknown as vscode.MessageItem + ); const job = handlers.invokeTeamsAgent([extTelemetryEvents.TelemetryTriggerFrom.TreeView]); await clock.tickAsync(6000); @@ -82,53 +88,8 @@ describe("invokeTeamsAgent", async () => { ); }); - it("View Teams Agent link successfully", async () => { - clock = sandbox.useFakeTimers(); - sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); - sandbox - .stub(vscode.extensions, "getExtension") - .onFirstCall() - .returns(undefined) - .onSecondCall() - .returns({ name: "github.copilot" } as any); - sandbox.stub(vscode.commands, "executeCommand").resolves(); - sandbox - .stub(vscode.window, "showInformationMessage") - .resolves("Install @teamsapp" as unknown as vscode.MessageItem); - const openUrlStub = sandbox.stub(vsc_ui.VS_CODE_UI, "openUrl").resolves(ok(true)); - - const res = await handlers.invokeTeamsAgent([extTelemetryEvents.TelemetryTriggerFrom.TreeView]); - - if (res.isErr()) { - console.log(res.error); - } - - chai.assert.isTrue(res.isOk()); - chai.assert.isTrue(openUrlStub.called); - }); - - it("Failed to view Teams Agent link", async () => { - clock = sandbox.useFakeTimers(); - sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); - sandbox - .stub(vscode.extensions, "getExtension") - .onFirstCall() - .returns(undefined) - .onSecondCall() - .returns({ name: "github.copilot" } as any); - sandbox.stub(vscode.commands, "executeCommand").resolves(); - sandbox - .stub(vscode.window, "showInformationMessage") - .resolves("Install @teamsapp" as unknown as vscode.MessageItem); - sandbox - .stub(vsc_ui.VS_CODE_UI, "openUrl") - .resolves(err(new SystemError("source", "name", "", ""))); - const res = await handlers.invokeTeamsAgent([extTelemetryEvents.TelemetryTriggerFrom.TreeView]); - - chai.assert.isTrue(res.isErr() && res.error.source === "source"); - }); - it("install Github Copilot, wait and invoke Teams Agent", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(true); clock = sandbox.useFakeTimers(); sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); sandbox @@ -142,7 +103,9 @@ describe("invokeTeamsAgent", async () => { const commandStub = sandbox.stub(vscode.commands, "executeCommand").resolves(); sandbox .stub(vscode.window, "showInformationMessage") - .resolves("Install GitHub Copilot" as unknown as vscode.MessageItem); + .resolves( + localize("teamstoolkit.handlers.askInstallCopilot.install") as unknown as vscode.MessageItem + ); const job = handlers.invokeTeamsAgent(); await clock.tickAsync(6000); @@ -153,6 +116,7 @@ describe("invokeTeamsAgent", async () => { }); it("Install github copilot extension error", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(true); sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); sandbox.stub(vscode.extensions, "getExtension").onFirstCall().returns(undefined); const commandStub = sandbox @@ -166,19 +130,22 @@ describe("invokeTeamsAgent", async () => { }); sandbox .stub(vscode.window, "showInformationMessage") - .resolves("Install GitHub Copilot" as unknown as vscode.MessageItem); + .resolves( + localize("teamstoolkit.handlers.askInstallCopilot.install") as unknown as vscode.MessageItem + ); sandbox.stub(VsCodeLogInstance, "error").resolves(); const res = await handlers.invokeTeamsAgent(); chai.assert.isTrue(res.isErr()); if (res.isErr()) { - chai.assert.equal(res.error.source, "installCopilotChat"); + chai.assert.equal(res.error.source, "install-copilot-chat"); } chai.assert.equal(commandStub.callCount, 1); }); it("Install github copilot extension cancel", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(true); sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); const loggerStub = sandbox.stub(VsCodeLogInstance, "error").resolves(); sandbox @@ -206,13 +173,16 @@ describe("invokeTeamsAgent", async () => { }); it("Verify installation error", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(true); clock = sandbox.useFakeTimers(); sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); sandbox.stub(vscode.extensions, "getExtension").returns(undefined); const commandStub = sandbox.stub(vscode.commands, "executeCommand").resolves(); sandbox .stub(vscode.window, "showInformationMessage") - .resolves("Install GitHub Copilot" as unknown as vscode.MessageItem); + .resolves( + localize("teamstoolkit.handlers.askInstallCopilot.install") as unknown as vscode.MessageItem + ); const job = handlers.invokeTeamsAgent(); await clock.tickAsync(30000); @@ -226,6 +196,7 @@ describe("invokeTeamsAgent", async () => { }); it("invoke Copilot chat error", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(true); sandbox.stub(versionUtils, "isVSCodeInsiderVersion").returns(true); sandbox.stub(vscode.extensions, "getExtension").returns({ name: "github.copilot" } as any); const commandStub = sandbox @@ -239,7 +210,9 @@ describe("invokeTeamsAgent", async () => { }); sandbox .stub(vscode.window, "showInformationMessage") - .resolves("Install GitHub Copilot" as unknown as vscode.MessageItem); + .resolves( + localize("teamstoolkit.handlers.askInstallCopilot.install") as unknown as vscode.MessageItem + ); const loggerError = sandbox.stub(VsCodeLogInstance, "error").resolves(); const res = await handlers.invokeTeamsAgent(); @@ -251,4 +224,68 @@ describe("invokeTeamsAgent", async () => { chai.assert.equal(commandStub.callCount, 1); chai.assert.equal(loggerError.callCount, 2); }); + + it("need to show notification of installing @teamsapp", async () => { + sandbox.stub(globalState, "globalStateGet").resolves(false); + sandbox.stub(vscode.extensions, "getExtension").returns({ name: "github.copilot" } as any); + sandbox.stub(vscode.commands, "executeCommand").resolves(); + + sandbox + .stub(vscode.window, "showInformationMessage") + .returns( + Promise.resolve( + localize( + "teamstoolkit.handlers.askInstallTeamsAgent.install" + ) as unknown as vscode.MessageItem + ) + ); + sandbox.stub(vsc_ui.VS_CODE_UI, "openUrl").resolves(ok(true)); + const res = await handlers.invokeTeamsAgent([ + extTelemetryEvents.TelemetryTriggerFrom.CreateAppQuestionFlow, + ]); + chai.assert.isTrue(res.isOk()); + }); + + describe("handleInstallTeamsAgentSelection", async () => { + it("open url", async () => { + const openUrlStub = sandbox.stub(vsc_ui.VS_CODE_UI, "openUrl").resolves(ok(true)); + await handlers.handleInstallTeamsAgentSelection( + localize("teamstoolkit.handlers.askInstallTeamsAgent.install"), + { key: "value" } + ); + + chai.assert.isTrue(openUrlStub.called); + }); + + it("confirm install", async () => { + const stub = sandbox.stub(globalState, "globalStateUpdate").resolves(undefined); + await handlers.handleInstallTeamsAgentSelection( + localize("teamstoolkit.handlers.askInstallTeamsAgent.confirmInstall"), + { key: "value" } + ); + + chai.assert.isTrue(stub.called); + }); + + it("open url error", async () => { + const openUrlStub = sandbox + .stub(vsc_ui.VS_CODE_UI, "openUrl") + .resolves(err(new SystemError("openUrl", "openUrlError", "", ""))); + const logError = sandbox.stub(VsCodeLogInstance, "error").resolves(); + await handlers.handleInstallTeamsAgentSelection( + localize("teamstoolkit.handlers.askInstallTeamsAgent.install"), + { key: "value" } + ); + + chai.assert.isTrue(openUrlStub.called); + chai.assert.isTrue(logError.called); + }); + + it("cancel", async () => { + const openUrlStub = sandbox.stub(vsc_ui.VS_CODE_UI, "openUrl").resolves(ok(true)); + await handlers.handleInstallTeamsAgentSelection(undefined, { key: "value" }); + + chai.assert.isTrue(openUrlStub.notCalled); + }); + }); }); diff --git a/packages/vscode-extension/test/handlers/createPluginWithManifestHandler.test.ts b/packages/vscode-extension/test/handlers/createPluginWithManifestHandler.test.ts index a6d29c2aee..9f5512c6a2 100644 --- a/packages/vscode-extension/test/handlers/createPluginWithManifestHandler.test.ts +++ b/packages/vscode-extension/test/handlers/createPluginWithManifestHandler.test.ts @@ -170,4 +170,38 @@ describe("createPluginWithManifestHandler", () => { chai.assert.equal(res.error.name, "fakeError"); } }); + + it("happy path: add plugin", async () => { + const core = new MockCore(); + sandbox.stub(globalVariables, "core").value(core); + const res = await createPluginWithManifest([ + "specPath", + "pluginManifestPath", + { + lastCommand: "addPlugin", + manifestPath: "manifestPath", + }, + ]); + chai.assert.isTrue(res.isOk()); + }); + + it("should throw error if add plugin core return error", async () => { + const core = new MockCore(); + sandbox.stub(globalVariables, "core").value(core); + sandbox + .stub(globalVariables.core, "addPlugin") + .resolves(err(new UserError("core", "fakeError", "fakeErrorMessage"))); + const res = await createPluginWithManifest([ + "specPath", + "pluginManifestPath", + { + lastCommand: "addPlugin", + manifestPath: "manifestPath", + }, + ]); + chai.assert.isTrue(res.isErr()); + if (res.isErr()) { + chai.assert.equal(res.error.name, "fakeError"); + } + }); }); diff --git a/packages/vscode-extension/test/handlers/lifecycleHandlers.test.ts b/packages/vscode-extension/test/handlers/lifecycleHandlers.test.ts index 68551672f1..100c683100 100644 --- a/packages/vscode-extension/test/handlers/lifecycleHandlers.test.ts +++ b/packages/vscode-extension/test/handlers/lifecycleHandlers.test.ts @@ -550,5 +550,42 @@ describe("Lifecycle handlers", () => { sinon.assert.calledOnce(addPluginHanlder); }); + + it("success: success call kiota", async () => { + const mockedEnvRestore = mockedEnv({ + [FeatureFlagName.KiotaIntegration]: "true", + }); + sandbox.stub(globalVariables, "core").value(new MockCore()); + sandbox + .stub(globalVariables.core, "addPlugin") + .resolves(ok({ lastCommand: "addPlugin", manifestPath: "manifest.json" })); + sandbox.stub(shared, "runCommand").resolves( + ok({ + projectPath: "", + lastCommand: "command", + }) + ); + sandbox.stub(vscode.extensions, "getExtension").returns({ + id: "mockedId", + extensionUri: vscode.Uri.parse("file://mockedUri"), + isActive: true, + extensionPath: "mockedPath", + extensionKind: vscode.ExtensionKind.UI, + exports: {}, + packageJSON: { + version: "1.18.100000002", + }, + activate: () => Promise.resolve(), + }); + const executeCommand = sandbox.stub(vscode.commands, "executeCommand").resolves(); + const logError = sandbox.stub(VsCodeLogInstance, "error").resolves(); + + const result = await addPluginHandler(); + + assert.isTrue(result.isOk()); + assert.isTrue(executeCommand.calledOnce); + assert.isTrue(logError.notCalled); + mockedEnvRestore(); + }); }); }); diff --git a/packages/vscode-extension/test/handlers/readmeHandlers.test.ts b/packages/vscode-extension/test/handlers/readmeHandlers.test.ts index 2251d8e07a..8f05860b20 100644 --- a/packages/vscode-extension/test/handlers/readmeHandlers.test.ts +++ b/packages/vscode-extension/test/handlers/readmeHandlers.test.ts @@ -96,7 +96,7 @@ describe("readmeHandlers", () => { ); }); - it("Restify Notification Bot Template", async () => { + it("Express Notification Bot Template", async () => { sandbox.stub(ExtTelemetry, "sendTelemetryEvent"); sandbox.stub(globalVariables, "isTeamsFxProject").value(true); sandbox @@ -106,14 +106,14 @@ describe("readmeHandlers", () => { sandbox.stub(fs, "pathExists").resolves(true); sandbox .stub(fs, "readFile") - .resolves(Buffer.from("## Get Started with the Notification bot restify")); + .resolves(Buffer.from("## Get Started with the Notification bot express")); const createOrShow = sandbox.stub(WebviewPanel, "createOrShow"); await openReadMeHandler([extTelemetryEvents.TelemetryTriggerFrom.Auto]); sandbox.assert.calledOnceWithExactly( createOrShow, - PanelType.RestifyServerNotificationBotReadme + PanelType.ExpressServerNotificationBotReadme ); }); }); diff --git a/packages/vscode-extension/test/mocks/mockTools.ts b/packages/vscode-extension/test/mocks/mockTools.ts index c16ff8acc3..21f9b61570 100644 --- a/packages/vscode-extension/test/mocks/mockTools.ts +++ b/packages/vscode-extension/test/mocks/mockTools.ts @@ -99,6 +99,10 @@ export class MockAzureAccountProvider implements AzureAccountProvider { }; } + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } + listSubscriptions(): Promise { throw new Error("Method not implemented."); } @@ -154,6 +158,10 @@ export class MockM365TokenProvider implements M365TokenProvider { throw new Error("Method not implemented."); } + switchTenant(tenantId: string): Promise> { + throw new Error("Method not implemented."); + } + /** * Add update account info callback * @param name callback name diff --git a/packages/vscode-extension/test/treeview/account/accountsTreeViewProvider.test.ts b/packages/vscode-extension/test/treeview/account/accountsTreeViewProvider.test.ts index b0a34a42d3..bd5b7d3ff4 100644 --- a/packages/vscode-extension/test/treeview/account/accountsTreeViewProvider.test.ts +++ b/packages/vscode-extension/test/treeview/account/accountsTreeViewProvider.test.ts @@ -80,7 +80,19 @@ describe("AccountTreeViewProvider", () => { const m365SignedInStub = sandbox.stub(AccountTreeViewProvider.m365AccountNode, "setSignedIn"); const updateChecksStub = sandbox.stub(AccountTreeViewProvider.m365AccountNode, "updateChecks"); await m365StatusChange("SignedIn", "token", { upn: "upn" }); - chai.assert.isTrue(m365SignedInStub.calledOnce); + chai.assert.isTrue(m365SignedInStub.calledOnceWithExactly("upn", "")); + chai.assert.isTrue(updateChecksStub.calledOnce); + + m365SignedInStub.reset(); + updateChecksStub.reset(); + await m365StatusChange("SignedIn", "token", { tid: "tid" }); + chai.assert.isTrue(m365SignedInStub.calledOnceWithExactly("", "tid")); + chai.assert.isTrue(updateChecksStub.calledOnce); + + m365SignedInStub.reset(); + updateChecksStub.reset(); + await m365StatusChange("SignedIn", "token", { upn: "upn", tid: "tid" }); + chai.assert.isTrue(m365SignedInStub.calledOnceWithExactly("upn", "tid")); chai.assert.isTrue(updateChecksStub.calledOnce); const m365SwitchingStub = sandbox.stub(AccountTreeViewProvider.m365AccountNode, "setSwitching"); @@ -98,6 +110,10 @@ describe("AccountTreeViewProvider", () => { await azureStatusChange("SignedIn", "token", { upn: "upn" }); chai.assert.isTrue(azureSignedInStub.calledOnce); + azureSignedInStub.reset(); + await azureStatusChange("SignedIn", "token", { upn: "upn", tid: "tid" }); + chai.assert.isTrue(azureSignedInStub.calledOnceWithExactly("token", "tid", "upn")); + const azureSigningInStub = sandbox.stub( AccountTreeViewProvider.azureAccountNode, "setSigningIn" diff --git a/packages/vscode-extension/test/treeview/account/azureNode.test.ts b/packages/vscode-extension/test/treeview/account/azureNode.test.ts index f56238c247..b2317a2817 100644 --- a/packages/vscode-extension/test/treeview/account/azureNode.test.ts +++ b/packages/vscode-extension/test/treeview/account/azureNode.test.ts @@ -6,6 +6,8 @@ import { AzureAccountManager } from "../../../src/commonlib/azureLogin"; import { AzureAccountNode } from "../../../src/treeview/account/azureNode"; import { AccountItemStatus, azureIcon, loadingIcon } from "../../../src/treeview/account/common"; import { DynamicNode } from "../../../src/treeview/dynamicNode"; +import { featureFlagManager } from "@microsoft/teamsfx-core"; +import * as tools from "@microsoft/teamsfx-core/build/common/tools"; describe("AzureNode", () => { const sandbox = sinon.createSandbox(); @@ -21,7 +23,7 @@ describe("AzureNode", () => { it("setSignedIn", async () => { const azureNode = new AzureAccountNode(eventEmitter); - await azureNode.setSignedIn("test upn"); + await azureNode.setSignedIn("", "", "test upn"); const treeItem = await azureNode.getTreeItem(); chai.assert.equal(treeItem.iconPath, azureIcon); @@ -33,8 +35,8 @@ describe("AzureNode", () => { it("setSignedIn with same account", async () => { const azureNode = new AzureAccountNode(eventEmitter); - await azureNode.setSignedIn("test upn"); - await azureNode.setSignedIn("test upn"); + await azureNode.setSignedIn("", "", "test upn"); + await azureNode.setSignedIn("", "", "test upn"); const treeItem = await azureNode.getTreeItem(); chai.assert.equal(treeItem.iconPath, azureIcon); @@ -46,8 +48,8 @@ describe("AzureNode", () => { it("setSignedIn with different account", async () => { const azureNode = new AzureAccountNode(eventEmitter); - await azureNode.setSignedIn("test upn"); - await azureNode.setSignedIn("test upn2"); + await azureNode.setSignedIn("", "", "test upn"); + await azureNode.setSignedIn("", "", "test upn2"); const treeItem = await azureNode.getTreeItem(); chai.assert.equal(treeItem.iconPath, azureIcon); @@ -57,6 +59,29 @@ describe("AzureNode", () => { chai.assert.equal(treeItem.command, undefined); }); + it("setSignedIn with multi-tenant", async () => { + sandbox.stub(featureFlagManager, "getBooleanValue").returns(true); + sandbox.stub(tools, "listAllTenants").resolves([ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + displayName: "MSFT", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + displayName: "Cisco", + }, + ]); + const azureNode = new AzureAccountNode(eventEmitter); + await azureNode.setSignedIn("token", "0022fd51-06f5-4557-8a34-69be98de6e20", "test upn"); + const treeItem = await azureNode.getTreeItem(); + + chai.assert.equal(treeItem.iconPath, azureIcon); + chai.assert.equal(treeItem.collapsibleState, vscode.TreeItemCollapsibleState.None); + chai.assert.equal(treeItem.label, "test upn (MSFT)"); + chai.assert.equal(treeItem.contextValue, "signedinAzure"); + chai.assert.equal(treeItem.command, undefined); + }); + it("setSigningIn", async () => { const azureNode = new AzureAccountNode(eventEmitter); azureNode.setSigningIn(); diff --git a/packages/vscode-extension/test/treeview/account/m365Node.test.ts b/packages/vscode-extension/test/treeview/account/m365Node.test.ts index 175b00a011..5d49c639e7 100644 --- a/packages/vscode-extension/test/treeview/account/m365Node.test.ts +++ b/packages/vscode-extension/test/treeview/account/m365Node.test.ts @@ -5,6 +5,10 @@ import * as vscode from "vscode"; import { AccountItemStatus, loadingIcon, m365Icon } from "../../../src/treeview/account/common"; import { M365AccountNode } from "../../../src/treeview/account/m365Node"; import { DynamicNode } from "../../../src/treeview/dynamicNode"; +import * as tool from "@microsoft/teamsfx-core/build/common/tools"; +import * as globalVariables from "../../../src/globalVariables"; +import { MockTools } from "../../mocks/mockTools"; +import { ok } from "@microsoft/teamsfx-api"; describe("m365Node", () => { const sandbox = sinon.createSandbox(); @@ -15,8 +19,9 @@ describe("m365Node", () => { }); it("setSignedIn", async () => { + sandbox.stub(featureFlagManager, "getBooleanValue").returns(false); const m365Node = new M365AccountNode(eventEmitter); - await m365Node.setSignedIn("test upn"); + await m365Node.setSignedIn("test upn", ""); const treeItem = await m365Node.getTreeItem(); chai.assert.equal(treeItem.iconPath, m365Icon); @@ -26,6 +31,34 @@ describe("m365Node", () => { chai.assert.equal(treeItem.command, undefined); }); + it("setSignedIn - multitenant", async () => { + sandbox.stub(featureFlagManager, "getBooleanValue").returns(true); + sandbox.stub(globalVariables, "tools").value(new MockTools()); + sandbox + .stub(globalVariables.tools.tokenProvider.m365TokenProvider, "getAccessToken") + .resolves(ok("test-token")); + sandbox.stub(tool, "listAllTenants").resolves([ + { + tenantId: "0022fd51-06f5-4557-8a34-69be98de6e20", + displayName: "MSFT", + }, + { + tenantId: "313ef12c-d7cb-4f01-af90-1b113db5aa9a", + displayName: "Cisco", + }, + ]); + + const m365Node = new M365AccountNode(eventEmitter); + await m365Node.setSignedIn("test upn", "0022fd51-06f5-4557-8a34-69be98de6e20"); + const treeItem = await m365Node.getTreeItem(); + + chai.assert.equal(treeItem.iconPath, m365Icon); + chai.assert.equal(treeItem.collapsibleState, vscode.TreeItemCollapsibleState.None); + chai.assert.equal(treeItem.label, "test upn (MSFT)"); + chai.assert.equal(treeItem.contextValue, "signedinM365"); + chai.assert.equal(treeItem.command, undefined); + }); + it("setSigningIn", async () => { const m365Node = new M365AccountNode(eventEmitter); m365Node.setSigningIn(); diff --git a/packages/vscode-extension/test/utils/globalVars.test.ts b/packages/vscode-extension/test/utils/globalVars.test.ts new file mode 100644 index 0000000000..1a52fb839a --- /dev/null +++ b/packages/vscode-extension/test/utils/globalVars.test.ts @@ -0,0 +1,22 @@ +import * as chai from "chai"; +import * as sinon from "sinon"; +import { LocalDebugPorts, resetLocalDebugPorts } from "../../src/globalVariables"; + +describe("GlobalVariables", () => { + const sandbox = sinon.createSandbox(); + + afterEach(() => { + sandbox.restore(); + }); + + it("resetLocalDebugPorts", async () => { + resetLocalDebugPorts(); + chai.assert.deepEqual(LocalDebugPorts, { + checkPorts: [], + conflictPorts: [], + terminateButton: "", + process2conflictPorts: {}, + terminateProcesses: [], + }); + }); +}); diff --git a/packages/vscode-extension/test/utils/processUtil.test.ts b/packages/vscode-extension/test/utils/processUtil.test.ts new file mode 100644 index 0000000000..7814f2981e --- /dev/null +++ b/packages/vscode-extension/test/utils/processUtil.test.ts @@ -0,0 +1,170 @@ +import { expect } from "chai"; +import sinon from "sinon"; +import child_process from "child_process"; +import { processUtil } from "../../src/utils/processUtil"; // Adjust the import path as necessary + +describe("ProcessUtil", () => { + let execStub: any; + const sandbox = sinon.createSandbox(); + beforeEach(() => { + execStub = sandbox.stub(child_process, "exec"); + }); + + afterEach(() => { + sandbox.restore(); + }); + + describe("getProcessId", () => { + it("should return the process ID on Windows", async () => { + const port = 8080; + const stdout = `TCP 0.0.0.0:${port} 0.0.0.0:0 LISTENING 1234`; + execStub.yields(null, stdout); + sandbox.stub(process, "platform").value("win32"); + const pid = await processUtil.getProcessId(port); + expect(pid).to.equal("1234"); + }); + + it("should return the process ID on Unix-based systems", async () => { + const port = 8080; + const stdout = `COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME\nnode 5678 user 22u IPv4 0t0 TCP *:${port} (LISTEN)`; + sandbox.stub(process, "platform").value("linux"); + execStub.yields(null, stdout); + const pid = await processUtil.getProcessId(port); + expect(pid).to.equal("5678"); + }); + + it("should return an empty string if no process is found on Windows", async () => { + const port = 8080; + execStub.yields(null, ""); + sandbox.stub(process, "platform").value("win32"); + const pid = await processUtil.getProcessId(port); + expect(pid).to.equal(""); + }); + it("should return an empty string if no process is found on Windows", async () => { + const port = 8080; + execStub.yields(null, "abc"); + sandbox.stub(process, "platform").value("win32"); + const pid = await processUtil.getProcessId(port); + expect(pid).to.equal(""); + }); + it("should return an empty string if no process is found on Unix-based systems", async () => { + const port = 8080; + execStub.yields(null, "COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME\n"); + sandbox.stub(process, "platform").value("linux"); + const pid = await processUtil.getProcessId(port); + expect(pid).to.equal(""); + }); + + it("should reject with an error if exec fails", async () => { + const port = 8080; + const error = new Error("exec error"); + execStub.yields(error, ""); + try { + await processUtil.getProcessId(port); + throw new Error("Expected method to reject."); + } catch (err) { + expect(err).to.equal(error); + } + }); + }); + + describe("killProcess", () => { + it("should kill the process on Windows", async () => { + sandbox.stub(process, "platform").value("win32"); + const pid = "1234"; + execStub.yields(null); + + await processUtil.killProcess(pid); + expect(execStub.calledWith(`taskkill /PID ${pid} /F`)).to.be.true; + }); + + it("should kill the process on Unix-based systems", async () => { + sandbox.stub(process, "platform").value("linux"); + const pid = "5678"; + execStub.yields(null); + + await processUtil.killProcess(pid); + expect(execStub.calledWith(`kill -9 ${pid}`)).to.be.true; + }); + + it("should reject with an error if exec fails on Windows", async () => { + sandbox.stub(process, "platform").value("win32"); + const pid = "1234"; + const error = new Error("exec error"); + execStub.yields(error); + + try { + await processUtil.killProcess(pid); + throw new Error("Expected method to reject."); + } catch (err) { + expect(err).to.equal(error); + } + }); + + it("should reject with an error if exec fails on Unix-based systems", async () => { + sandbox.stub(process, "platform").value("linux"); + const pid = "5678"; + const error = new Error("exec error"); + execStub.yields(error); + + try { + await processUtil.killProcess(pid); + throw new Error("Expected method to reject."); + } catch (err) { + expect(err).to.equal(error); + } + }); + }); + + describe("getProcessInfo", () => { + it("should return process info on Unix-based systems", async () => { + sandbox.stub(process, "platform").value("linux"); + const pid = 5678; + const stdout = `5678 /usr/bin/node`; + execStub.yields(null, stdout); + + const processInfo = await processUtil.getProcessInfo(pid); + expect(processInfo).to.equal(stdout); + expect(execStub.calledWith(`ps -p ${pid} -o command=`)).to.be.true; + }); + + it("should return process info on Windows", async () => { + sandbox.stub(process, "platform").value("win32"); + const pid = 1234; + const stdout = `CommandLine="node.exe"`; + execStub.yields(null, stdout); + + const processInfo = await processUtil.getProcessInfo(pid); + expect(processInfo).to.equal('"node.exe"'); + expect(execStub.calledWith(`wmic process where ProcessId=${pid} get CommandLine /value`)).to + .be.true; + }); + + it("should reject with an error if exec fails linux", async () => { + sandbox.stub(process, "platform").value("linux"); + const pid = 5678; + const error = new Error("exec error"); + execStub.yields(error); + + try { + await processUtil.getProcessInfo(pid); + throw new Error("Expected method to reject."); + } catch (err) { + expect(err).to.equal(error); + } + }); + it("should reject with an error if exec fails win32", async () => { + sandbox.stub(process, "platform").value("win32"); + const pid = 5678; + const error = new Error("exec error"); + execStub.yields(error); + + try { + await processUtil.getProcessInfo(pid); + throw new Error("Expected method to reject."); + } catch (err) { + expect(err).to.equal(error); + } + }); + }); +}); diff --git a/templates/CONTRIBUTING.md b/templates/CONTRIBUTING.md deleted file mode 100644 index a3422b89c7..0000000000 --- a/templates/CONTRIBUTING.md +++ /dev/null @@ -1,157 +0,0 @@ -## How to scaffold from pre-release templates? - -Teams Toolkit downloads latest stable templates by default from [GitHub releases](https://github.com/OfficeDev/TeamsFx/releases) for scaffolding. - -To scaffold your project from rc templates, set the environment varaible `TEAMSFX_TEMPLATE_PRERELEASE=rc`. Then Teams Toolkit download templates from [rc release](https://github.com/OfficeDev/TeamsFx/releases/tag/templates%400.0.0-rc) - -We do not release alpha template since alpha fx-core use local template to avoid incompatibility. `TEAMSFX_TEMPLATE_PRERELEASE=alpha`does nothing. -To test latest template in dev branch, please refer to [How to debug templates](#how-to-debug-templates). - -## How to release a new template? - -1. If your template relies on @microsoft/teamsfx, @microsoft/teamsfx-react or @microsoft/adaptivecards-tools, please include the relative path to your new template in the [package.json](https://github.com/OfficeDev/TeamsFx/blob/dev/templates/package.json) file. Here is an example of how to add the path: - ``` - "templates": [ - "js/command-and-response", - "ts/command-and-response", - "language/your-new-template" - ] - ``` -1. The CD pipeline will automatically update the dependencies in the package.json or package.json.tpl file when a new version of @microsoft/teamsfx, @microsoft/teamsfx-react or @microsoft/adaptivecards-tools is released. You can access the script used for this process [here](https://github.com/OfficeDev/TeamsFx/blob/dev/.github/scripts/sync-version.js). -1. TeamsFx no longer uses Lerna for template versioning. Adding a `BREAKING CHANGE` footer will no longer have any effect. The release manager must manually bump up the major version of the template when a breaking change occurs. - -Some breaking change cases: - -* Involve new placeholder in templates. -* Upgrade template's dependencies which deprecates support to lower version NodeJs. Latest Teams Toolkit notices users to upgrade their environment but older version Teams Toolkit does not. -* Remove or rename templates. - -Cases that are not breaking changes: - -* Add new templates that old Teams Toolkit does not have entry to get and scaffold them. -* Add new features to templates that does not require any change in Teams Toolkit. -* Totally rewrite a template but old Teams Toolkit can still work with it. - -## How to develop templates? - -Developing templates is similiar to other packages. Follow the steps below to get started: - -1. Run `npm run setup` in the root folder to setup the whole project. -1. Make changes to the templates. -1. Run `npm run build` in the templates folder to apply your changes. -1. Start the vscode-extension, cli or vs server and create a project that uses your updated template to preview the changes. - -By default, fx-core uses local template packages for scaffolding. -If you prefer to use the latest stable template packages from GitHub Releases, you can go to [templates-config.json](../packages/fx-core/src/common/templates-config.json), set `useLocalTemplate` to false and build the fx-core to apply the changes. - -## How to upgrade teamsapp.yml schema version for all templates? - -For example, upgrading teamsapp.yml schema version for all templates to v1.5, you can run following command: - -> `npm run upgrade-schema v1.5` - -This command finds all teamsapp yaml file, matches the following header and replaces the version in the file. - -``` -# yaml-language-server: $schema=https://aka.ms/teams-toolkit/${version}/yaml.schema.json -# Visit https://aka.ms/teamsfx-v5.0-guide for details on this file -# Visit https://aka.ms/teamsfx-actions for details on actions -version: ${version} -``` - -## What is template constraints? - -In order to streamline the maintenance process and reduce the risk of errors, it is necessary to address the issue of duplicate content in our templates. -To address this issue, we are implementing a system of constraints that will standardize the way templates are updated and protect them from unexpected changes. - -Currently, these constraints have been applied to the following files within the template: - - * teamsapp.yml (teamsapp.yml.tpl) - * teamsapp.local.yml (teamsapp.local.yml.tpl) - -The [constraints for yml](https://github.com/OfficeDev/TeamsFx/tree/dev/templates/constraints/yml/templates) are in [mustache](https://mustache.github.io/mustache.5.html) format and follow a folder naming convention where one mustache file corresponds to a yml file. - -For example, `js/dashboard-tab/teamsapp.yml.tpl` corresponds to `js/dashboard-tab/teamsapp.yml.tpl.mustache`. - -Each teamsapp.yml file consists of a header and several actions. To simplify the process, we have abstracted each action into a partial mustache template that can be invoked by the yml constraints. - -### How to work with constraints? - -The constraint engine provides four distinct commands: - -``` -> npm run verify -``` - -The verify command verifies whether the constraint is satisfied. -When no constraint path is provided, this command will scan through all constraint files and verify that each one is being satisfied. - -``` -> npm run apply -``` - -The apply command applies the constraint to corresponding template. -When no constraint path is provided, this command will scan through all constraint files and apply them to the templates. -This command will overwrite the template file, so ensure that there are no untracked changes in target templates before running this command. - -``` -> npm run init -``` - -The init command scans the template folder and identifies all supported files to initialize constraints for them. -Usually, you will need to review the generated constraints and make any necessary adjustments to ensure their correctness. - -``` -> npm run watch -``` - -The watch command watches all mustache template in the [constraints/yml/actions](./constraints/yml/actions). Whenever a file change event occurs, it generates a preview of the mustache template in the same folder, which is particularly useful when writing a mustache template. -![preview mustache demo](https://user-images.githubusercontent.com/26134943/255495650-a5bcd0f9-5342-4901-a53b-a41dda5f32ef.gif) - -### How to update templates with constraints? - -Let us take Teams App project file (teamsapp.yml) as an example. - -To update the Teams App project file for a specific template as a template owner, follow these steps: - -1. Locate the corresponding YAML constraints for your template at [constraints/yml/templates](./constraints/yml/templates). -1. Make the necessary changes in the constraint, such as adding or updating an action, metadata, or upgrading the schema version. -1. Apply the constraint changes to your template by running `apply` command: - ``` - > npm run apply - ``` -1. Commit both the constraint and Teams App project file, and create a pull request to submit the changes. The CI action will ensure that all template constraints are satisfied. - -To update all Teams App project files that reference your action as an action owner, follow these steps: - -1. Find your action snippets at [constraints/yml/actions](./constraints/yml/actions/) -1. Make the necessary changes in the action snippet, such as adding new parameters, updating comments, creating a placeholder, or adding a new built-in action. -1. (Optional) Preview the action snippets by running the `watch` command: - ``` - > npm run watch - ``` -1. (Optional) If you are updating the interface of the action snippet, update existing YAML constraints to avoid breaking them. -1. Apply the action snippet changes to all templates by running the `apply` command: - ``` - > npm run apply - ``` -1. Commit both the action snippet and Teams App project files, and create a pull request to submit the changes. Ask for template owners review since you are updating the Teams App project file for their templates. - -### How to create constraints for a new template? - -It is recommended to apply constraints to all templates to ensure consistency, minimize errors and optimize maintenance. - -As a template owner, you can draft the template constraints first and use the `apply` command to generate the corresponding solution when adding a new template. -Alternatively, you can prepare the template to ensure that it works from end to end and follow the steps to create constraints: - -1. Use the `init` command to initialize the corresponding constraints based on the solution: - - ``` - > npm run init - ``` - -1. Adjust the generated constraints to ensure their correctness and verify the constraints are satisfied by running the `verify` command: - - ``` - > npm run verify - ``` diff --git a/templates/common/api-plugin-existing-api/README.md.tpl b/templates/common/api-plugin-existing-api/README.md.tpl index 685da7654e..370f969c0f 100644 --- a/templates/common/api-plugin-existing-api/README.md.tpl +++ b/templates/common/api-plugin-existing-api/README.md.tpl @@ -35,7 +35,7 @@ You can extend declarative agents using plugins to retrieve data and execute tas > > To run this app template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts). > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) > - [Microsoft 365 Copilot license](https://learn.microsoft.com/microsoft-365-copilot/extensibility/prerequisites#prerequisites) diff --git a/templates/common/copilot-gpt-basic/README.md b/templates/common/copilot-gpt-basic/README.md index 3dc3fe41c2..b99d19e97c 100644 --- a/templates/common/copilot-gpt-basic/README.md +++ b/templates/common/copilot-gpt-basic/README.md @@ -10,7 +10,7 @@ With the declarative agent, you can build a custom version of Copilot that can b > > To run this app template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts). > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) > - [Microsoft 365 Copilot license](https://learn.microsoft.com/microsoft-365-copilot/extensibility/prerequisites#prerequisites) @@ -34,10 +34,10 @@ With the declarative agent, you can build a custom version of Copilot that can b The following files can be customized and demonstrate an example implementation to get you started. -| File | Contents | -| ------------------------------------ | ------------------------------------------------------------------------------ | +| File | Contents | +| ---------------------------------- | ---------------------------------------------------------------------------- | | `appPackage/declarativeAgent.json` | Define the behaviour and configurations of the declarative agent. | -| `appPackage/manifest.json` | Teams application manifest that defines metadata for your declarative agent. | +| `appPackage/manifest.json` | Teams application manifest that defines metadata for your declarative agent. | The following are Teams Toolkit specific project files. You can [visit a complete guide on Github](https://github.com/OfficeDev/TeamsFx/wiki/Teams-Toolkit-Visual-Studio-Code-v5-Guide#overview) to understand how Teams Toolkit works. diff --git a/templates/common/copilot-plugin-existing-api/README.md.tpl b/templates/common/copilot-plugin-existing-api/README.md.tpl index 82f0a43316..373f62291f 100644 --- a/templates/common/copilot-plugin-existing-api/README.md.tpl +++ b/templates/common/copilot-plugin-existing-api/README.md.tpl @@ -13,7 +13,7 @@ This app template allows Teams to interact directly with third-party data, apps, > > To run this app template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts). > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) diff --git a/templates/constraints/yml/actions/aadAppCreate.mustache b/templates/constraints/yml/actions/aadAppCreate.mustache deleted file mode 100644 index 2840f3bb99..0000000000 --- a/templates/constraints/yml/actions/aadAppCreate.mustache +++ /dev/null @@ -1,32 +0,0 @@ - # Creates a new Microsoft Entra app to authenticate users if - # the environment variable that stores clientId is empty - - uses: aadApp/create - with: - # Note: when you run aadApp/update, the Microsoft Entra app name will be updated - # based on the definition in manifest. If you don't want to change the - # name, make sure the name in Microsoft Entra manifest is the same with the name - # defined here. - name: {{appName}} - # If the value is false, the action will not generate client secret for you - {{#skipClientSecret}} - generateClientSecret: false - {{/skipClientSecret}} - {{^skipClientSecret}} - generateClientSecret: true - {{/skipClientSecret}} - # Authenticate users with a Microsoft work or school account in your - # organization's Microsoft Entra tenant (for example, single tenant). - signInAudience: AzureADMyOrg - # Write the information of created resources into environment file for the - # specified environment variable(s). - writeToEnvironmentFile: - clientId: AAD_APP_CLIENT_ID - {{^skipClientSecret}} - # Environment variable that starts with `SECRET_` will be stored to the - # .env.{envName}.user environment file - clientSecret: SECRET_AAD_APP_CLIENT_SECRET - {{/skipClientSecret}} - objectId: AAD_APP_OBJECT_ID - tenantId: AAD_APP_TENANT_ID - authority: AAD_APP_OAUTH_AUTHORITY - authorityHost: AAD_APP_OAUTH_AUTHORITY_HOST \ No newline at end of file diff --git a/templates/constraints/yml/actions/aadAppUpdate.mustache b/templates/constraints/yml/actions/aadAppUpdate.mustache deleted file mode 100644 index 405af63915..0000000000 --- a/templates/constraints/yml/actions/aadAppUpdate.mustache +++ /dev/null @@ -1,8 +0,0 @@ - # Apply the Microsoft Entra manifest to an existing Microsoft Entra app. Will use the object id in - # manifest file to determine which Microsoft Entra app to update. - - uses: aadApp/update - with: - # Relative path to this file. Environment variables in manifest will - # be replaced before apply to Microsoft Entra app - manifestPath: ./aad.manifest.json - outputFilePath: ./build/aad.manifest.${{TEAMSFX_ENV}}.json \ No newline at end of file diff --git a/templates/constraints/yml/actions/apiKeyRegister.mustache b/templates/constraints/yml/actions/apiKeyRegister.mustache deleted file mode 100644 index f28b57fe89..0000000000 --- a/templates/constraints/yml/actions/apiKeyRegister.mustache +++ /dev/null @@ -1,19 +0,0 @@ - # Register API KEY - - uses: apiKey/register - with: - # Name of the API Key - name: {{ApiSpecAuthName}} - {{#primaryClientSecret}} - # Value of the API Key - primaryClientSecret: {{{primaryClientSecret}}} - {{/primaryClientSecret}} - # Teams app ID - appId: ${{TEAMS_APP_ID}} - {{#apiSpecPath}} - # Path to OpenAPI description document - apiSpecPath: {{{apiSpecPath}}} - {{/apiSpecPath}} - # Write the registration information of API Key into environment file for - # the specified environment variable(s). - writeToEnvironmentFile: - registrationId: {{ApiSpecAuthRegistrationIdEnvName}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/apiKeyUpdate.mustache b/templates/constraints/yml/actions/apiKeyUpdate.mustache deleted file mode 100644 index 5bd878e1d5..0000000000 --- a/templates/constraints/yml/actions/apiKeyUpdate.mustache +++ /dev/null @@ -1,14 +0,0 @@ - # Update API KEY - - uses: apiKey/update - with: - # Name of the API Key - name: {{ApiSpecAuthName}} - # Teams app ID - appId: ${{TEAMS_APP_ID}} - {{#apiSpecPath}} - # Path to OpenAPI description document - apiSpecPath: {{{apiSpecPath}}} - {{/apiSpecPath}} - {{#registrationId}} - registrationId: {{{registrationId}}} - {{/registrationId}} diff --git a/templates/constraints/yml/actions/armDeploy.mustache b/templates/constraints/yml/actions/armDeploy.mustache deleted file mode 100644 index 3669470feb..0000000000 --- a/templates/constraints/yml/actions/armDeploy.mustache +++ /dev/null @@ -1,24 +0,0 @@ - - uses: arm/deploy # Deploy given ARM templates parallelly. - with: - # AZURE_SUBSCRIPTION_ID is a built-in environment variable, - # if its value is empty, TeamsFx will prompt you to select a subscription. - # Referencing other environment variables with empty values - # will skip the subscription selection prompt. - subscriptionId: ${{AZURE_SUBSCRIPTION_ID}} - # AZURE_RESOURCE_GROUP_NAME is a built-in environment variable, - # if its value is empty, TeamsFx will prompt you to select or create one - # resource group. - # Referencing other environment variables with empty values - # will skip the resource group selection prompt. - resourceGroupName: ${{AZURE_RESOURCE_GROUP_NAME}} - templates: - - path: ./infra/azure.bicep # Relative path to this file - # Relative path to this yaml file. - # Placeholders will be replaced with corresponding environment - # variable before ARM deployment. - parameters: ./infra/azure.parameters.json - # Required when deploying ARM template - deploymentName: {{{deploymentName}}} - # Teams Toolkit will download this bicep CLI version from github for you, - # will use bicep CLI in PATH if you remove this config. - bicepCliVersion: v0.9.1 \ No newline at end of file diff --git a/templates/constraints/yml/actions/azureAppServiceZipDeploy.mustache b/templates/constraints/yml/actions/azureAppServiceZipDeploy.mustache deleted file mode 100644 index 502e63295a..0000000000 --- a/templates/constraints/yml/actions/azureAppServiceZipDeploy.mustache +++ /dev/null @@ -1,23 +0,0 @@ - # Deploy your application to Azure App Service using the zip deploy feature. - # For additional details, refer to https://aka.ms/zip-deploy-to-app-services. - - uses: azureAppService/zipDeploy - with: - {{#workingDirectory}} - workingDirectory: {{{workingDirectory}}} - {{/workingDirectory}} - # Deploy base folder - {{#artifactFolder}} - artifactFolder: {{{artifactFolder}}} - {{/artifactFolder}} - {{^artifactFolder}} - artifactFolder: . - {{/artifactFolder}} - {{#ignoreFile}} - # Ignore file location, leave blank will ignore nothing - ignoreFile: {{{ignoreFile}}} - {{/ignoreFile}} - # The resource id of the cloud resource to be deployed to. - # This key will be generated by arm/deploy action automatically. - # You can replace it with your existing Azure Resource id - # or add it to your environment variable file. - resourceId: {{{resourceId}}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/azureFunctionsZipDeploy.mustache b/templates/constraints/yml/actions/azureFunctionsZipDeploy.mustache deleted file mode 100644 index fccd6c056e..0000000000 --- a/templates/constraints/yml/actions/azureFunctionsZipDeploy.mustache +++ /dev/null @@ -1,23 +0,0 @@ - # Deploy your application to Azure Functions using the zip deploy feature. - # For additional details, see at https://aka.ms/zip-deploy-to-azure-functions - - uses: azureFunctions/zipDeploy - with: - {{#workingDirectory}} - workingDirectory: {{{workingDirectory}}} - {{/workingDirectory}} - # deploy base folder - {{#artifactFolder}} - artifactFolder: {{{artifactFolder}}} - {{/artifactFolder}} - {{^artifactFolder}} - artifactFolder: . - {{/artifactFolder}} - {{#ignoreFile}} - # Ignore file location, leave blank will ignore nothing - ignoreFile: {{{ignoreFile}}} - {{/ignoreFile}} - # The resource id of the cloud resource to be deployed to. - # This key will be generated by arm/deploy action automatically. - # You can replace it with your existing Azure Resource id - # or add it to your environment variable file. - resourceId: {{resourceId}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/azureStaticWebAppDeploy.mustache b/templates/constraints/yml/actions/azureStaticWebAppDeploy.mustache deleted file mode 100644 index 36b3207eed..0000000000 --- a/templates/constraints/yml/actions/azureStaticWebAppDeploy.mustache +++ /dev/null @@ -1,5 +0,0 @@ - # Deploy bits to Azure Static Web Apps - - uses: cli/runNpxCommand - name: deploy to Azure Static Web Apps - with: - args: '@azure/static-web-apps-cli deploy {{{artifactFolder}}} -d ${{SECRET_TAB_SWA_DEPLOYMENT_TOKEN}} --env production' \ No newline at end of file diff --git a/templates/constraints/yml/actions/azureStaticWebAppGetDeploymentToken.mustache b/templates/constraints/yml/actions/azureStaticWebAppGetDeploymentToken.mustache deleted file mode 100644 index b82b2bb93a..0000000000 --- a/templates/constraints/yml/actions/azureStaticWebAppGetDeploymentToken.mustache +++ /dev/null @@ -1,7 +0,0 @@ - # Get the deployment token from Azure Static Web Apps - - uses: azureStaticWebApps/getDeploymentToken - with: - resourceId: ${{AZURE_STATIC_WEB_APPS_RESOURCE_ID}} - # Save deployment token to the environment file for the deployment action - writeToEnvironmentFile: - deploymentToken: SECRET_TAB_SWA_DEPLOYMENT_TOKEN \ No newline at end of file diff --git a/templates/constraints/yml/actions/azureStorageDeploy.mustache b/templates/constraints/yml/actions/azureStorageDeploy.mustache deleted file mode 100644 index 6affb91703..0000000000 --- a/templates/constraints/yml/actions/azureStorageDeploy.mustache +++ /dev/null @@ -1,31 +0,0 @@ - # Deploy bits to Azure Storage Static Website - - uses: azureStorage/deploy - with: - {{#workingDirectory}} - workingDirectory: {{{workingDirectory}}} - {{/workingDirectory}} - {{#ignoreFile}} - # Deploy base folder. This folder includes manifest files for Microsoft Entra app and Teams app that should be ignored using the ignoreFile. - {{/ignoreFile}} - {{^ignoreFile}} - # Deploy base folder - {{/ignoreFile}} - {{#artifactFolder}} - artifactFolder: {{{artifactFolder}}} - {{/artifactFolder}} - {{^artifactFolder}} - artifactFolder: build - {{/artifactFolder}} - {{#ignoreFile}} - ignoreFile: .storageignore - {{/ignoreFile}} - # The resource id of the cloud resource to be deployed to. - # This key will be generated by arm/deploy action automatically. - # You can replace it with your existing Azure Resource id - # or add it to your environment variable file. - {{#resourceId}} - resourceId: {{resourceId}} - {{/resourceId}} - {{^resourceId}} - resourceId: ${{TAB_AZURE_STORAGE_RESOURCE_ID}} - {{/resourceId}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/azureStorageEnableStaticWebsite.mustache b/templates/constraints/yml/actions/azureStorageEnableStaticWebsite.mustache deleted file mode 100644 index a59d822670..0000000000 --- a/templates/constraints/yml/actions/azureStorageEnableStaticWebsite.mustache +++ /dev/null @@ -1,10 +0,0 @@ - - uses: azureStorage/enableStaticWebsite - with: - {{#storageResourceId}} - storageResourceId: {{storageResourceId}} - {{/storageResourceId}} - {{^storageResourceId}} - storageResourceId: ${{TAB_AZURE_STORAGE_RESOURCE_ID}} - {{/storageResourceId}} - indexPage: index.html - errorPage: error.html \ No newline at end of file diff --git a/templates/constraints/yml/actions/botAadAppCreate.mustache b/templates/constraints/yml/actions/botAadAppCreate.mustache deleted file mode 100644 index 8dbb487177..0000000000 --- a/templates/constraints/yml/actions/botAadAppCreate.mustache +++ /dev/null @@ -1,14 +0,0 @@ - # Create or reuse an existing Microsoft Entra application for bot. - - uses: aadApp/create - with: - # The Microsoft Entra application's display name - name: {{appName}}${{APP_NAME_SUFFIX}} - generateClientSecret: true - signInAudience: AzureADMultipleOrgs - writeToEnvironmentFile: - # The Microsoft Entra application's client id created for bot. - clientId: BOT_ID - # The Microsoft Entra application's client secret created for bot. - clientSecret: SECRET_BOT_PASSWORD - # The Microsoft Entra application's object id created for bot. - objectId: BOT_OBJECT_ID \ No newline at end of file diff --git a/templates/constraints/yml/actions/botFrameworkCreate.mustache b/templates/constraints/yml/actions/botFrameworkCreate.mustache deleted file mode 100644 index 59123b8fcd..0000000000 --- a/templates/constraints/yml/actions/botFrameworkCreate.mustache +++ /dev/null @@ -1,12 +0,0 @@ - # Create or update the bot registration on dev.botframework.com - - uses: botFramework/create - with: - botId: ${{BOT_ID}} - name: {{appName}} - messagingEndpoint: ${{BOT_ENDPOINT}}/api/messages - description: "" - channels: - - name: msteams - {{#m365extensions}} - - name: m365extensions - {{/m365extensions}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/cliRunDotnetCommand.mustache b/templates/constraints/yml/actions/cliRunDotnetCommand.mustache deleted file mode 100644 index ceb1a5be19..0000000000 --- a/templates/constraints/yml/actions/cliRunDotnetCommand.mustache +++ /dev/null @@ -1,15 +0,0 @@ -{{#extensions}} - # TeamsFx Azure Functions project depends on extra Azure Functions binding extensions for HTTP trigger authorization. -{{/extensions}} - - uses: cli/runDotnetCommand - with: - {{#workingDirectory}} - workingDirectory: {{{workingDirectory}}} - {{/workingDirectory}} - {{#publish}} - args: publish --configuration Release - {{/publish}} - {{#extensions}} - args: build extensions.csproj -o bin --ignore-failed-sources - execPath: ${{DOTNET_PATH}} - {{/extensions}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/cliRunNpmCommand.mustache b/templates/constraints/yml/actions/cliRunNpmCommand.mustache deleted file mode 100644 index efdd2d2fc1..0000000000 --- a/templates/constraints/yml/actions/cliRunNpmCommand.mustache +++ /dev/null @@ -1,29 +0,0 @@ - {{#install}} - # Run npm command - - uses: cli/runNpmCommand - name: install dependencies - with: - {{#workingDirectory}} - workingDirectory: {{{workingDirectory}}} - {{/workingDirectory}} - {{#args}} - args: {{{args}}} - {{/args}} - {{^args}} - args: install - {{/args}} - {{/install}} - {{#build}} - - uses: cli/runNpmCommand - name: build app - with: - {{#workingDirectory}} - workingDirectory: {{{workingDirectory}}} - {{/workingDirectory}} - {{#args}} - args: {{{args}}} - {{/args}} - {{^args}} - args: run build --if-present - {{/args}} - {{/build}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/cliRunNpxCommand.mustache b/templates/constraints/yml/actions/cliRunNpxCommand.mustache deleted file mode 100644 index 862acdce89..0000000000 --- a/templates/constraints/yml/actions/cliRunNpxCommand.mustache +++ /dev/null @@ -1,11 +0,0 @@ - - uses: cli/runNpxCommand - with: - {{#workingDirectory}} - workingDirectory: {{{workingDirectory}}} - {{/workingDirectory}} - {{#bundle}} - args: gulp bundle --ship --no-color - {{/bundle}} - {{#package}} - args: gulp package-solution --ship --no-color - {{/package}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/devToolInstall.mustache b/templates/constraints/yml/actions/devToolInstall.mustache deleted file mode 100644 index 7a111ecc65..0000000000 --- a/templates/constraints/yml/actions/devToolInstall.mustache +++ /dev/null @@ -1,33 +0,0 @@ - # Install development tool(s) - - uses: devTool/install - with: -{{#devCert}} - devCert: - trust: true -{{/devCert}} -{{#func}} - func: - {{#funcToolsVersion}} - version: {{{funcToolsVersion}}} - {{/funcToolsVersion}} - {{^funcToolsVersion}} - version: ~4.0.5174 - {{/funcToolsVersion}} - symlinkDir: ./devTools/func -{{/func}} -{{#dotnet}} - dotnet: true -{{/dotnet}} - # Write the information of installed development tool(s) into environment - # file for the specified environment variable(s). - writeToEnvironmentFile: -{{#devCert}} - sslCertFile: SSL_CRT_FILE - sslKeyFile: SSL_KEY_FILE -{{/devCert}} -{{#func}} - funcPath: FUNC_PATH -{{/func}} -{{#dotnet}} - dotnetPath: DOTNET_PATH -{{/dotnet}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/fileCreateOrUpdateEnvironmentFile.mustache b/templates/constraints/yml/actions/fileCreateOrUpdateEnvironmentFile.mustache deleted file mode 100644 index 8adef8b942..0000000000 --- a/templates/constraints/yml/actions/fileCreateOrUpdateEnvironmentFile.mustache +++ /dev/null @@ -1,26 +0,0 @@ - {{^noComment}} - # Generate runtime environment variables - {{/noComment}} - - uses: file/createOrUpdateEnvironmentFile - with: - {{#target}} - target: {{{target}}} - {{/target}} - {{^target}} - target: ./.localConfigs - {{/target}} - envs: - {{#BOT}} - BOT_ID: ${{BOT_ID}} - BOT_PASSWORD: ${{SECRET_BOT_PASSWORD}} - {{/BOT}} - {{#TAB}} - BROWSER: none - HTTPS: true - PORT: 53000 - SSL_CRT_FILE: ${{SSL_CRT_FILE}} - SSL_KEY_FILE: ${{SSL_KEY_FILE}} - {{/TAB}} - {{#COPILOT}} - OPENAPI_SERVER_URL: https://${{DEV_TUNNEL_URL}} - {{/COPILOT}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/fileCreateOrUpdateJsonFile.mustache b/templates/constraints/yml/actions/fileCreateOrUpdateJsonFile.mustache deleted file mode 100644 index be73973773..0000000000 --- a/templates/constraints/yml/actions/fileCreateOrUpdateJsonFile.mustache +++ /dev/null @@ -1,81 +0,0 @@ -{{#launchSettings}} - # Create or update debug profile in lauchsettings file - - uses: file/createOrUpdateJsonFile - with: - target: ./Properties/launchSettings.json - content: - profiles: - {{#profiles}} - {{{profileName}}} - commandName: "Project" - {{#commandLineArgs}} - commandLineArgs: {{{commandLineArgs}}} - {{/commandLineArgs}} - dotnetRunMessages: true - launchBrowser: true - {{#launchUrl}} - launchUrl: {{{launchUrl}}} - {{/launchUrl}} - {{#applicationUrl}} - applicationUrl: {{{applicationUrl}}} - {{/applicationUrl}} - environmentVariables: - ASPNETCORE_ENVIRONMENT: "Development" - {{#localstore}} - TEAMSFX_NOTIFICATION_LOCALSTORE_DIR: "../../.." - {{/localstore}} - {{#hotReload}} - hotReloadProfile: "aspnetcore" - {{/hotReload}} - {{/profiles}} - {{^profiles}} - {{#profileName}} - {{{profileName}}} - {{/profileName}} - {{^profileName}} - Microsoft Teams (browser): - {{/profileName}} - commandName: "Project" - {{#commandLineArgs}} - commandLineArgs: {{{commandLineArgs}}} - {{/commandLineArgs}} - dotnetRunMessages: true - launchBrowser: true - {{#launchUrl}} - launchUrl: {{{launchUrl}}} - {{/launchUrl}} - {{^launchUrl}} - launchUrl: "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}" - {{/launchUrl}} - {{#applicationUrl}} - applicationUrl: {{{applicationUrl}}} - {{/applicationUrl}} - environmentVariables: - ASPNETCORE_ENVIRONMENT: "Development" - {{#localstore}} - TEAMSFX_NOTIFICATION_LOCALSTORE_DIR: "../../.." - {{/localstore}} - {{#hotReload}} - hotReloadProfile: "aspnetcore" - {{/hotReload}} - {{/profiles}} -{{/launchSettings}} -{{#appsettings}} - # Generate runtime appsettings to JSON file - - uses: file/createOrUpdateJsonFile - with: - target: ./appsettings.Development.json - content: - {{#BOT}} - BOT_ID: ${{BOT_ID}} - BOT_PASSWORD: ${{SECRET_BOT_PASSWORD}} - {{/BOT}} - {{#Authentication}} - TeamsFx: - Authentication: - ClientId: ${{AAD_APP_CLIENT_ID}} - ClientSecret: ${{SECRET_AAD_APP_CLIENT_SECRET}} - InitiateLoginEndpoint: ${{TAB_ENDPOINT}}/auth-start.html - OAuthAuthority: ${{AAD_APP_OAUTH_AUTHORITY}} - {{/Authentication}} -{{/appsettings}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/header.mustache b/templates/constraints/yml/actions/header.mustache deleted file mode 100644 index b8946c322f..0000000000 --- a/templates/constraints/yml/actions/header.mustache +++ /dev/null @@ -1,4 +0,0 @@ -# yaml-language-server: $schema=https://aka.ms/teams-toolkit/{{{version}}}/yaml.schema.json -# Visit https://aka.ms/teamsfx-v5.0-guide for details on this file -# Visit https://aka.ms/teamsfx-actions for details on actions -version: {{{version}}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/script.mustache b/templates/constraints/yml/actions/script.mustache deleted file mode 100644 index 48211bcc8b..0000000000 --- a/templates/constraints/yml/actions/script.mustache +++ /dev/null @@ -1,36 +0,0 @@ -{{#FUNC}} - # Set required variables for local launch -{{/FUNC}} -{{^FUNC}} - {{#COPILOT}} - # Set OPENAPI_SERVER_URL for local launch - {{/COPILOT}} - {{^COPILOT}} - # Set TAB_DOMAIN and TAB_ENDPOINT for local launch - {{/COPILOT}} -{{/FUNC}} - - uses: script - with: - run: -{{#TAB}} - {{#DOTNET}} - echo "::set-teamsfx-env TAB_DOMAIN=localhost"; - echo "::set-teamsfx-env TAB_ENDPOINT=https://localhost:44302"; - {{/DOTNET}} - {{^DOTNET}} - echo "::set-teamsfx-env TAB_DOMAIN=localhost"; - echo "::set-teamsfx-env TAB_ENDPOINT=https://localhost:53000"; - {{/DOTNET}} -{{/TAB}} -{{#FUNC}} - {{#FUNC_NAME}} - echo "::set-teamsfx-env FUNC_NAME={{{FUNC_NAME}}}"; - {{/FUNC_NAME}} - {{^FUNC_NAME}} - echo "::set-teamsfx-env FUNC_NAME=getUserProfile"; - {{/FUNC_NAME}} - echo "::set-teamsfx-env FUNC_ENDPOINT=http://localhost:7071"; -{{/FUNC}} -{{#COPILOT}} - echo "::set-teamsfx-env OPENAPI_SERVER_URL=https://${{DEV_TUNNEL_URL}}"; -{{/COPILOT}} diff --git a/templates/constraints/yml/actions/spfxDeploy.mustache b/templates/constraints/yml/actions/spfxDeploy.mustache deleted file mode 100644 index f3831258f2..0000000000 --- a/templates/constraints/yml/actions/spfxDeploy.mustache +++ /dev/null @@ -1,4 +0,0 @@ - - uses: spfx/deploy - with: - createAppCatalogIfNotExist: false - packageSolutionPath: ./src/config/package-solution.json \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppCopyAppPackageToSPFx.mustache b/templates/constraints/yml/actions/teamsAppCopyAppPackageToSPFx.mustache deleted file mode 100644 index 38e1957357..0000000000 --- a/templates/constraints/yml/actions/teamsAppCopyAppPackageToSPFx.mustache +++ /dev/null @@ -1,4 +0,0 @@ - - uses: teamsApp/copyAppPackageToSPFx - with: - appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip - spfxFolder: ./src \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppCreate.mustache b/templates/constraints/yml/actions/teamsAppCreate.mustache deleted file mode 100644 index c53195e6b6..0000000000 --- a/templates/constraints/yml/actions/teamsAppCreate.mustache +++ /dev/null @@ -1,9 +0,0 @@ - # Creates a Teams app - - uses: teamsApp/create - with: - # Teams app name - name: {{appName}}${{APP_NAME_SUFFIX}} - # Write the information of created resources into environment file for - # the specified environment variable(s). - writeToEnvironmentFile: - teamsAppId: TEAMS_APP_ID \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppExtendToM365.mustache b/templates/constraints/yml/actions/teamsAppExtendToM365.mustache deleted file mode 100644 index b72418eab6..0000000000 --- a/templates/constraints/yml/actions/teamsAppExtendToM365.mustache +++ /dev/null @@ -1,10 +0,0 @@ - # Extend your Teams app to Outlook and the Microsoft 365 app - - uses: teamsApp/extendToM365 - with: - # Relative path to the build app package. - appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip - # Write the information of created resources into environment file for - # the specified environment variable(s). - writeToEnvironmentFile: - titleId: M365_TITLE_ID - appId: M365_APP_ID \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppPublishAppPackage.mustache b/templates/constraints/yml/actions/teamsAppPublishAppPackage.mustache deleted file mode 100644 index f762949774..0000000000 --- a/templates/constraints/yml/actions/teamsAppPublishAppPackage.mustache +++ /dev/null @@ -1,10 +0,0 @@ - # Publish the app to - # Teams Admin Center (https://admin.teams.microsoft.com/policies/manage-apps) - # for review and approval - - uses: teamsApp/publishAppPackage - with: - appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip - # Write the information of created resources into environment file for - # the specified environment variable(s). - writeToEnvironmentFile: - publishedAppId: TEAMS_APP_PUBLISHED_APP_ID \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppUpdate.mustache b/templates/constraints/yml/actions/teamsAppUpdate.mustache deleted file mode 100644 index 23aef1c476..0000000000 --- a/templates/constraints/yml/actions/teamsAppUpdate.mustache +++ /dev/null @@ -1,7 +0,0 @@ - # Apply the Teams app manifest to an existing Teams app in - # Teams Developer Portal. - # Will use the app id in manifest file to determine which Teams app to update. - - uses: teamsApp/update - with: - # Relative path to this file. This is the path for built zip file. - appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppValidateAppPackage.mustache b/templates/constraints/yml/actions/teamsAppValidateAppPackage.mustache deleted file mode 100644 index 9b6625ec08..0000000000 --- a/templates/constraints/yml/actions/teamsAppValidateAppPackage.mustache +++ /dev/null @@ -1,5 +0,0 @@ - # Validate app package using validation rules - - uses: teamsApp/validateAppPackage - with: - # Relative path to this file. This is the path for built zip file. - appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppValidateManifest.mustache b/templates/constraints/yml/actions/teamsAppValidateManifest.mustache deleted file mode 100644 index 4667ebef29..0000000000 --- a/templates/constraints/yml/actions/teamsAppValidateManifest.mustache +++ /dev/null @@ -1,10 +0,0 @@ - # Validate using manifest schema - - uses: teamsApp/validateManifest - with: - # Path to manifest template - {{#localManifest}} - manifestPath: ./appPackage/manifest.local.json - {{/localManifest}} - {{^localManifest}} - manifestPath: ./appPackage/manifest.json - {{/localManifest}} \ No newline at end of file diff --git a/templates/constraints/yml/actions/teamsAppZipAppPackage.mustache b/templates/constraints/yml/actions/teamsAppZipAppPackage.mustache deleted file mode 100644 index f331fa12da..0000000000 --- a/templates/constraints/yml/actions/teamsAppZipAppPackage.mustache +++ /dev/null @@ -1,12 +0,0 @@ - # Build Teams app package with latest env value - - uses: teamsApp/zipAppPackage - with: - # Path to manifest template - {{#localManifest}} - manifestPath: ./appPackage/manifest.local.json - {{/localManifest}} - {{^localManifest}} - manifestPath: ./appPackage/manifest.json - {{/localManifest}} - outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip - outputFolder: ./appPackage/build \ No newline at end of file diff --git a/templates/constraints/yml/templates/common/api-plugin-existing-api/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/common/api-plugin-existing-api/teamsapp.yml.tpl.mustache deleted file mode 100644 index 0cea5ce306..0000000000 --- a/templates/constraints/yml/templates/common/api-plugin-existing-api/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,17 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/common/copilot-plugin-existing-api/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/common/copilot-plugin-existing-api/teamsapp.yml.tpl.mustache deleted file mode 100644 index 8b6ead81b5..0000000000 --- a/templates/constraints/yml/templates/common/copilot-plugin-existing-api/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/common/office-addin/teamsapp.yml.mustache b/templates/constraints/yml/templates/common/office-addin/teamsapp.yml.mustache deleted file mode 100644 index 1ed7af2c94..0000000000 --- a/templates/constraints/yml/templates/common/office-addin/teamsapp.yml.mustache +++ /dev/null @@ -1,19 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStorageEnableStaticWebsite}} storageResourceId: ${{ADDIN_AZURE_STORAGE_RESOURCE_ID}} {{/azureStorageEnableStaticWebsite}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureStorageDeploy}} - workingDirectory: ., - artifactFolder: dist, - resourceId: ${{ADDIN_AZURE_STORAGE_RESOURCE_ID}} -{{/azureStorageDeploy}} diff --git a/templates/constraints/yml/templates/csharp/api-message-extension-sso/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/api-message-extension-sso/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index e43cadcb62..0000000000 --- a/templates/constraints/yml/templates/csharp/api-message-extension-sso/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#aadAppCreate}} skipClientSecret {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} COPILOT {{/script}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "profileName": "Microsoft Teams (browser):", - "commandLineArgs": "\"host start --port 5130 --pause-on-error\"", - "launchUrl": "\"https://teams.microsoft.com?appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "launchSettings": true, - "hotReload": true -} -{{/fileCreateOrUpdateJsonFile}} - diff --git a/templates/constraints/yml/templates/csharp/api-message-extension-sso/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/api-message-extension-sso/teamsapp.yml.tpl.mustache deleted file mode 100644 index b5a7eac101..0000000000 --- a/templates/constraints/yml/templates/csharp/api-message-extension-sso/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#aadAppCreate}} skipClientSecret {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureFunctionsZipDeploy}} - artifactFolder: bin/Release/{{TargetFramework}}/publish, - resourceId: ${{API_FUNCTION_RESOURCE_ID}} -{{/azureFunctionsZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/api-plugin-existing-api/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/api-plugin-existing-api/teamsapp.yml.tpl.mustache deleted file mode 100644 index 21acc838c5..0000000000 --- a/templates/constraints/yml/templates/csharp/api-plugin-existing-api/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,13 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} diff --git a/templates/constraints/yml/templates/csharp/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 70b79fcd49..0000000000 --- a/templates/constraints/yml/templates/csharp/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} COPILOT {{/script}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "profileName": "Microsoft Teams (browser):", - "commandLineArgs": "\"host start --port 5130 --pause-on-error\"", - "launchUrl": "\"https://teams.microsoft.com?appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "launchSettings": true, - "hotReload": true -} -{{/fileCreateOrUpdateJsonFile}} - diff --git a/templates/constraints/yml/templates/csharp/api-plugin-from-scratch/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/api-plugin-from-scratch/teamsapp.yml.tpl.mustache deleted file mode 100644 index cddf3e2744..0000000000 --- a/templates/constraints/yml/templates/csharp/api-plugin-from-scratch/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,23 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureFunctionsZipDeploy}} - artifactFolder: bin/Release/{{TargetFramework}}/publish, - resourceId: ${{API_FUNCTION_RESOURCE_ID}} -{{/azureFunctionsZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/command-and-response/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/command-and-response/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 9052e3342c..0000000000 --- a/templates/constraints/yml/templates/csharp/command-and-response/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,18 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#fileCreateOrUpdateJsonFile}} {"launchSettings": true, "applicationUrl": "\"http://localhost:5130\"", "hotReload": true} {{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/command-and-response/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/command-and-response/teamsapp.yml.tpl.mustache deleted file mode 100644 index 855b8805f2..0000000000 --- a/templates/constraints/yml/templates/csharp/command-and-response/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/copilot-plugin-existing-api/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/copilot-plugin-existing-api/teamsapp.yml.tpl.mustache deleted file mode 100644 index f9b09389a0..0000000000 --- a/templates/constraints/yml/templates/csharp/copilot-plugin-existing-api/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,17 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} diff --git a/templates/constraints/yml/templates/csharp/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index c2ea875d5b..0000000000 --- a/templates/constraints/yml/templates/csharp/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,27 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} COPILOT {{/script}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "profileName": "Microsoft Teams (browser):", - "commandLineArgs": "\"host start --port 5130 --pause-on-error\"", - "launchUrl": "\"https://teams.microsoft.com?appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "launchSettings": true, - "hotReload": true -} -{{/fileCreateOrUpdateJsonFile}} - diff --git a/templates/constraints/yml/templates/csharp/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache deleted file mode 100644 index 8ad65c9e77..0000000000 --- a/templates/constraints/yml/templates/csharp/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,27 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureFunctionsZipDeploy}} - artifactFolder: bin/Release/{{TargetFramework}}/publish, - resourceId: ${{API_FUNCTION_RESOURCE_ID}} -{{/azureFunctionsZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/link-unfurling/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/link-unfurling/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 96e41c8a1c..0000000000 --- a/templates/constraints/yml/templates/csharp/link-unfurling/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,40 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"http://localhost:5130\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"http://localhost:5130\"", - "launchUrl": "\"https://outlook.office.com/mail?login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/link-unfurling/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/link-unfurling/teamsapp.yml.tpl.mustache deleted file mode 100644 index b3c8e85850..0000000000 --- a/templates/constraints/yml/templates/csharp/link-unfurling/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,26 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/message-extension-copilot/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/message-extension-copilot/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 0006989160..0000000000 --- a/templates/constraints/yml/templates/csharp/message-extension-copilot/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,46 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"https://localhost:7130;http://localhost:5130\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Copilot (browser):", - "applicationUrl": "\"https://localhost:7130;http://localhost:5130\"", - "launchUrl": "\"https://teams.microsoft.com?appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"https://localhost:7130;http://localhost:5130\"", - "launchUrl": "\"https://outlook.office.com/mail?appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} \ No newline at end of file diff --git a/templates/constraints/yml/templates/csharp/message-extension-copilot/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/message-extension-copilot/teamsapp.yml.tpl.mustache deleted file mode 100644 index 84dabf4b18..0000000000 --- a/templates/constraints/yml/templates/csharp/message-extension-copilot/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,27 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-mxt {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} - -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/message-extension-search/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/message-extension-search/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 96e41c8a1c..0000000000 --- a/templates/constraints/yml/templates/csharp/message-extension-search/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,40 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"http://localhost:5130\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"http://localhost:5130\"", - "launchUrl": "\"https://outlook.office.com/mail?login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/message-extension-search/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/message-extension-search/teamsapp.yml.tpl.mustache deleted file mode 100644 index 69ac7eada2..0000000000 --- a/templates/constraints/yml/templates/csharp/message-extension-search/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,25 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/message-extension/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/message-extension/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 96e41c8a1c..0000000000 --- a/templates/constraints/yml/templates/csharp/message-extension/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,40 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"http://localhost:5130\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"http://localhost:5130\"", - "launchUrl": "\"https://outlook.office.com/mail?login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/message-extension/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/message-extension/teamsapp.yml.tpl.mustache deleted file mode 100644 index b3c8e85850..0000000000 --- a/templates/constraints/yml/templates/csharp/message-extension/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,26 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/non-sso-tab-ssr/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/non-sso-tab-ssr/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3c8c5d0801..0000000000 --- a/templates/constraints/yml/templates/csharp/non-sso-tab-ssr/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,42 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#script}} TAB, DOTNET {{/script}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Microsoft 365 app (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://www.office.com/m365apps/${{M365_APP_ID}}?auth=2&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://outlook.office.com/host/${{M365_APP_ID}}?login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} \ No newline at end of file diff --git a/templates/constraints/yml/templates/csharp/non-sso-tab-ssr/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/non-sso-tab-ssr/teamsapp.yml.tpl.mustache deleted file mode 100644 index dac18a1587..0000000000 --- a/templates/constraints/yml/templates/csharp/non-sso-tab-ssr/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{TAB_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/non-sso-tab/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/non-sso-tab/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3c8c5d0801..0000000000 --- a/templates/constraints/yml/templates/csharp/non-sso-tab/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,42 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#script}} TAB, DOTNET {{/script}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Microsoft 365 app (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://www.office.com/m365apps/${{M365_APP_ID}}?auth=2&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://outlook.office.com/host/${{M365_APP_ID}}?login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} \ No newline at end of file diff --git a/templates/constraints/yml/templates/csharp/non-sso-tab/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/non-sso-tab/teamsapp.yml.tpl.mustache deleted file mode 100644 index dac18a1587..0000000000 --- a/templates/constraints/yml/templates/csharp/non-sso-tab/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{TAB_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index bf1eb43c93..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "localstore": true, - "commandLineArgs": "\"host start --port 5130 --pause-on-error\"" - } -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/notification-http-timer-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-http-timer-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 16ade2e65a..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-http-timer-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureFunctionsZipDeploy}} - artifactFolder: bin/Release/{{TargetFramework}}/publish, - resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}} -{{/azureFunctionsZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/notification-http-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-http-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index bf1eb43c93..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-http-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "localstore": true, - "commandLineArgs": "\"host start --port 5130 --pause-on-error\"" - } -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/notification-http-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-http-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 16ade2e65a..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-http-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureFunctionsZipDeploy}} - artifactFolder: bin/Release/{{TargetFramework}}/publish, - resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}} -{{/azureFunctionsZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/notification-timer-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-timer-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index bf1eb43c93..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-timer-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "localstore": true, - "commandLineArgs": "\"host start --port 5130 --pause-on-error\"" - } -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/notification-timer-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-timer-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 16ade2e65a..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-timer-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureFunctionsZipDeploy}} - artifactFolder: bin/Release/{{TargetFramework}}/publish, - resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}} -{{/azureFunctionsZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/notification-webapi/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-webapi/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 9052e3342c..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-webapi/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,18 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#fileCreateOrUpdateJsonFile}} {"launchSettings": true, "applicationUrl": "\"http://localhost:5130\"", "hotReload": true} {{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/notification-webapi/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/notification-webapi/teamsapp.yml.tpl.mustache deleted file mode 100644 index 855b8805f2..0000000000 --- a/templates/constraints/yml/templates/csharp/notification-webapi/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/sso-tab-ssr/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/sso-tab-ssr/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 557cbdbc5e..0000000000 --- a/templates/constraints/yml/templates/csharp/sso-tab-ssr/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,48 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} TAB, DOTNET {{/script}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, Authentication {{/fileCreateOrUpdateJsonFile}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Microsoft 365 app (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://www.office.com/m365apps/${{M365_APP_ID}}?auth=2&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://outlook.office.com/host/${{M365_APP_ID}}?login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/sso-tab-ssr/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/sso-tab-ssr/teamsapp.yml.tpl.mustache deleted file mode 100644 index 131f22c519..0000000000 --- a/templates/constraints/yml/templates/csharp/sso-tab-ssr/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{TAB_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/sso-tab/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/sso-tab/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 557cbdbc5e..0000000000 --- a/templates/constraints/yml/templates/csharp/sso-tab/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,48 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} TAB, DOTNET {{/script}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, Authentication {{/fileCreateOrUpdateJsonFile}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -{{#fileCreateOrUpdateJsonFile}} -{ - "launchSettings": true, - "profiles": [ - { - "profileName": "Microsoft Teams (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Microsoft 365 app (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://www.office.com/m365apps/${{M365_APP_ID}}?auth=2&login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - }, - { - "profileName": "Outlook (browser):", - "applicationUrl": "\"https://localhost:44302;http://localhost:2544\"", - "launchUrl": "\"https://outlook.office.com/host/${{M365_APP_ID}}?login_hint=${{TEAMSFX_M365_USER_NAME}}\"", - "hotReload": true - } - ] -} -{{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/sso-tab/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/sso-tab/teamsapp.yml.tpl.mustache deleted file mode 100644 index 131f22c519..0000000000 --- a/templates/constraints/yml/templates/csharp/sso-tab/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{TAB_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/csharp/workflow/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/workflow/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 9052e3342c..0000000000 --- a/templates/constraints/yml/templates/csharp/workflow/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,18 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#fileCreateOrUpdateJsonFile}} appsettings, BOT {{/fileCreateOrUpdateJsonFile}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#fileCreateOrUpdateJsonFile}} {"launchSettings": true, "applicationUrl": "\"http://localhost:5130\"", "hotReload": true} {{/fileCreateOrUpdateJsonFile}} diff --git a/templates/constraints/yml/templates/csharp/workflow/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/csharp/workflow/teamsapp.yml.tpl.mustache deleted file mode 100644 index 855b8805f2..0000000000 --- a/templates/constraints/yml/templates/csharp/workflow/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.1.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunDotnetCommand}} publish {{/cliRunDotnetCommand}} -{{#azureAppServiceZipDeploy}} artifactFolder: bin/Release/{{TargetFramework}}/publish, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}} {{/azureAppServiceZipDeploy}} diff --git a/templates/constraints/yml/templates/js/api-message-extension-sso/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/api-message-extension-sso/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 60067aa177..0000000000 --- a/templates/constraints/yml/templates/js/api-message-extension-sso/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,25 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#aadAppCreate}} skipClientSecret {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} diff --git a/templates/constraints/yml/templates/js/api-message-extension-sso/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/api-message-extension-sso/teamsapp.yml.tpl.mustache deleted file mode 100644 index f08ea877a9..0000000000 --- a/templates/constraints/yml/templates/js/api-message-extension-sso/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,37 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#aadAppCreate}} skipClientSecret {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index de4f973142..0000000000 --- a/templates/constraints/yml/templates/js/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,17 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5530 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} diff --git a/templates/constraints/yml/templates/js/api-plugin-from-scratch/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/api-plugin-from-scratch/teamsapp.yml.tpl.mustache deleted file mode 100644 index 8c1cb587b5..0000000000 --- a/templates/constraints/yml/templates/js/api-plugin-from-scratch/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,27 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/command-and-response/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/command-and-response/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 5c1cf40800..0000000000 --- a/templates/constraints/yml/templates/js/command-and-response/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,20 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/command-and-response/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/command-and-response/teamsapp.yml.tpl.mustache deleted file mode 100644 index d6f3e52be3..0000000000 --- a/templates/constraints/yml/templates/js/command-and-response/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .appserviceIgnore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch-api-key/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/copilot-plugin-from-scratch-api-key/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 7e62e83aae..0000000000 --- a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch-api-key/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: v1.7 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#apiKeyRegister}}ApiSpecAuthName: apiKey, primaryClientSecret: ${{SECRET_API_KEY}}, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, ApiSpecAuthRegistrationIdEnvName: APIKEY_REGISTRATION_ID{{/apiKeyRegister}} - -{{#apiKeyUpdate}}ApiSpecAuthName: apiKey, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, registrationId: ${{APIKEY_REGISTRATION_ID}}{{/apiKeyUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs {{/fileCreateOrUpdateEnvironmentFile}} - API_KEY: ${{SECRET_API_KEY}} \ No newline at end of file diff --git a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch-api-key/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/copilot-plugin-from-scratch-api-key/teamsapp.yml.tpl.mustache deleted file mode 100644 index 633b56743f..0000000000 --- a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch-api-key/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,37 +0,0 @@ -{{#header}} version: v1.7 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#apiKeyRegister}}ApiSpecAuthName: apiKey, primaryClientSecret: ${{SECRET_API_KEY}}, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, ApiSpecAuthRegistrationIdEnvName: APIKEY_REGISTRATION_ID{{/apiKeyRegister}} - -{{#apiKeyUpdate}}ApiSpecAuthName: apiKey, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, registrationId: ${{APIKEY_REGISTRATION_ID}}{{/apiKeyUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index d07d243f2c..0000000000 --- a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} diff --git a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache deleted file mode 100644 index 9fcbacb22a..0000000000 --- a/templates/constraints/yml/templates/js/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,33 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/dashboard-tab/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/dashboard-tab/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index fa9595223e..0000000000 --- a/templates/constraints/yml/templates/js/dashboard-tab/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,16 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} TAB {{/script}} -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} devCert {{/devToolInstall}} -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, TAB {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/dashboard-tab/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/dashboard-tab/teamsapp.yml.tpl.mustache deleted file mode 100644 index 0fb7f4d554..0000000000 --- a/templates/constraints/yml/templates/js/dashboard-tab/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: v1.4 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStaticWebAppGetDeploymentToken}} {{/azureStaticWebAppGetDeploymentToken}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureStaticWebAppDeploy}} artifactFolder: ./build {{/azureStaticWebAppDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/default-bot-message-extension/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/default-bot-message-extension/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 0a864c21dc..0000000000 --- a/templates/constraints/yml/templates/js/default-bot-message-extension/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,17 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/default-bot-message-extension/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/default-bot-message-extension/teamsapp.yml.tpl.mustache deleted file mode 100644 index 62e1307243..0000000000 --- a/templates/constraints/yml/templates/js/default-bot-message-extension/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore{{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/default-bot/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/default-bot/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 0a864c21dc..0000000000 --- a/templates/constraints/yml/templates/js/default-bot/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,17 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/default-bot/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/default-bot/teamsapp.yml.tpl.mustache deleted file mode 100644 index 62e1307243..0000000000 --- a/templates/constraints/yml/templates/js/default-bot/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore{{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/link-unfurling/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/link-unfurling/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index adf933e129..0000000000 --- a/templates/constraints/yml/templates/js/link-unfurling/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,18 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/link-unfurling/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/link-unfurling/teamsapp.yml.tpl.mustache deleted file mode 100644 index 1175a7b75d..0000000000 --- a/templates/constraints/yml/templates/js/link-unfurling/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/m365-message-extension/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/m365-message-extension/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 23579533b1..0000000000 --- a/templates/constraints/yml/templates/js/m365-message-extension/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/m365-message-extension/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/m365-message-extension/teamsapp.yml.tpl.mustache deleted file mode 100644 index 042fd4632c..0000000000 --- a/templates/constraints/yml/templates/js/m365-message-extension/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/message-extension-copilot/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/message-extension-copilot/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 23579533b1..0000000000 --- a/templates/constraints/yml/templates/js/message-extension-copilot/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/message-extension-copilot/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/message-extension-copilot/teamsapp.yml.tpl.mustache deleted file mode 100644 index 042fd4632c..0000000000 --- a/templates/constraints/yml/templates/js/message-extension-copilot/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/message-extension/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/message-extension/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index adf933e129..0000000000 --- a/templates/constraints/yml/templates/js/message-extension/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,18 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/message-extension/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/message-extension/teamsapp.yml.tpl.mustache deleted file mode 100644 index 042fd4632c..0000000000 --- a/templates/constraints/yml/templates/js/message-extension/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/non-sso-tab-default-bot/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/non-sso-tab-default-bot/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index d0e5b2ba5c..0000000000 --- a/templates/constraints/yml/templates/js/non-sso-tab-default-bot/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,25 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#script}} TAB {{/script}} -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} devCert {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - - # Generate runtime environment variables for tab -{{#fileCreateOrUpdateEnvironmentFile}} target: ./tab/.localConfigs, TAB, noComment {{/fileCreateOrUpdateEnvironmentFile}} - - # Generate runtime environment variables for bot -{{#fileCreateOrUpdateEnvironmentFile}} target: ./bot/.localConfigs, BOT, noComment {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/non-sso-tab-default-bot/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/non-sso-tab-default-bot/teamsapp.yml.tpl.mustache deleted file mode 100644 index d9e389db78..0000000000 --- a/templates/constraints/yml/templates/js/non-sso-tab-default-bot/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,33 +0,0 @@ -{{#header}} version: v1.4 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStaticWebAppGetDeploymentToken}} {{/azureStaticWebAppGetDeploymentToken}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} workingDirectory: tab, args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureStaticWebAppDeploy}} artifactFolder: ./build {{/azureStaticWebAppDeploy}} -{{#azureAppServiceZipDeploy}} workingDirectory: bot, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/non-sso-tab/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/non-sso-tab/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index dc09af8f6f..0000000000 --- a/templates/constraints/yml/templates/js/non-sso-tab/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,19 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} TAB {{/script}} -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} devCert {{/devToolInstall}} -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs {{/fileCreateOrUpdateEnvironmentFile}} - PORT: 53000 - SSL_CRT_FILE: ${{SSL_CRT_FILE}} - SSL_KEY_FILE: ${{SSL_KEY_FILE}} diff --git a/templates/constraints/yml/templates/js/non-sso-tab/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/non-sso-tab/teamsapp.yml.tpl.mustache deleted file mode 100644 index 1071c83009..0000000000 --- a/templates/constraints/yml/templates/js/non-sso-tab/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{TAB_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3ad44bd136..0000000000 --- a/templates/constraints/yml/templates/js/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} func {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/notification-http-timer-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-http-timer-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 7bdbe7038f..0000000000 --- a/templates/constraints/yml/templates/js/notification-http-timer-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/notification-http-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-http-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3ad44bd136..0000000000 --- a/templates/constraints/yml/templates/js/notification-http-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} func {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/notification-http-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-http-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 7bdbe7038f..0000000000 --- a/templates/constraints/yml/templates/js/notification-http-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/notification-restify/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-restify/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 39e50433ba..0000000000 --- a/templates/constraints/yml/templates/js/notification-restify/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,19 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/notification-restify/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-restify/teamsapp.yml.tpl.mustache deleted file mode 100644 index a70accea44..0000000000 --- a/templates/constraints/yml/templates/js/notification-restify/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .appserviceignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/notification-timer-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-timer-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3ad44bd136..0000000000 --- a/templates/constraints/yml/templates/js/notification-timer-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} func {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/notification-timer-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/notification-timer-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 7bdbe7038f..0000000000 --- a/templates/constraints/yml/templates/js/notification-timer-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/sso-tab-with-obo-flow/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/sso-tab-with-obo-flow/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index b92831d96c..0000000000 --- a/templates/constraints/yml/templates/js/sso-tab-with-obo-flow/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,42 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} TAB, FUNC {{/script}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} devCert, func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#cliRunNpmCommand}} install, workingDirectory: api, args: install --no-audit {{/cliRunNpmCommand}} - - # Generate runtime environment variables for tab -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, TAB, noComment {{/fileCreateOrUpdateEnvironmentFile}} - REACT_APP_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - REACT_APP_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html - REACT_APP_FUNC_NAME: ${{FUNC_NAME}} - REACT_APP_FUNC_ENDPOINT: ${{FUNC_ENDPOINT}} - - # Generate runtime environment variables for backend -{{#fileCreateOrUpdateEnvironmentFile}} target: ./api/.localConfigs, noComment {{/fileCreateOrUpdateEnvironmentFile}} - M365_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - M365_CLIENT_SECRET: ${{SECRET_AAD_APP_CLIENT_SECRET}} - M365_TENANT_ID: ${{AAD_APP_TENANT_ID}} - M365_AUTHORITY_HOST: ${{AAD_APP_OAUTH_AUTHORITY_HOST}} - ALLOWED_APP_IDS: 1fec8e78-bce4-4aaf-ab1b-5451cc387264;5e3ce6c0-2b1f-4285-8d4b-75ee78787346;0ec893e0-5785-4de6-99da-4ed124e5296c;4345a7b9-9a63-4910-a426-35363201d503;4765445b-32c6-49b0-83e6-1d93765276ca;d3590ed6-52b3-4102-aeff-aad2292ab01c;00000002-0000-0ff1-ce00-000000000000;bc59ab01-8403-45c6-8796-ac3ef710b3e3;27922004-5251-4030-b22d-91ecd9a37ea4 diff --git a/templates/constraints/yml/templates/js/sso-tab-with-obo-flow/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/sso-tab-with-obo-flow/teamsapp.yml.tpl.mustache deleted file mode 100644 index 48c5a3dbbd..0000000000 --- a/templates/constraints/yml/templates/js/sso-tab-with-obo-flow/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,42 +0,0 @@ -{{#header}} version: v1.4 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStaticWebAppGetDeploymentToken}} {{/azureStaticWebAppGetDeploymentToken}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} - env: - REACT_APP_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - REACT_APP_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html - REACT_APP_FUNC_NAME: getUserProfile - REACT_APP_FUNC_ENDPOINT: ${{API_FUNCTION_ENDPOINT}} -{{#azureStaticWebAppDeploy}} artifactFolder: ./build {{/azureStaticWebAppDeploy}} -{{#cliRunNpmCommand}} install, workingDirectory: api, args: install {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} workingDirectory: api, resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/js/workflow/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/js/workflow/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 5c1cf40800..0000000000 --- a/templates/constraints/yml/templates/js/workflow/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,20 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/js/workflow/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/js/workflow/teamsapp.yml.tpl.mustache deleted file mode 100644 index a70accea44..0000000000 --- a/templates/constraints/yml/templates/js/workflow/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .appserviceignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/api-message-extension-sso/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/api-message-extension-sso/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 60067aa177..0000000000 --- a/templates/constraints/yml/templates/ts/api-message-extension-sso/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,25 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#aadAppCreate}} skipClientSecret {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} diff --git a/templates/constraints/yml/templates/ts/api-message-extension-sso/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/api-message-extension-sso/teamsapp.yml.tpl.mustache deleted file mode 100644 index d0b79fb865..0000000000 --- a/templates/constraints/yml/templates/ts/api-message-extension-sso/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,39 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#aadAppCreate}} skipClientSecret {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} - -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index de4f973142..0000000000 --- a/templates/constraints/yml/templates/ts/api-plugin-from-scratch/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,17 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5530 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} diff --git a/templates/constraints/yml/templates/ts/api-plugin-from-scratch/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/api-plugin-from-scratch/teamsapp.yml.tpl.mustache deleted file mode 100644 index 5bcb32e105..0000000000 --- a/templates/constraints/yml/templates/ts/api-plugin-from-scratch/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} - -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/command-and-response/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/command-and-response/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index dd3d5e40a4..0000000000 --- a/templates/constraints/yml/templates/ts/command-and-response/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,20 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}}{{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}}{{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/command-and-response/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/command-and-response/teamsapp.yml.tpl.mustache deleted file mode 100644 index 36e963a8d2..0000000000 --- a/templates/constraints/yml/templates/ts/command-and-response/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .appserviceignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch-api-key/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch-api-key/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 7e62e83aae..0000000000 --- a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch-api-key/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,28 +0,0 @@ -{{#header}} version: v1.7 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#apiKeyRegister}}ApiSpecAuthName: apiKey, primaryClientSecret: ${{SECRET_API_KEY}}, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, ApiSpecAuthRegistrationIdEnvName: APIKEY_REGISTRATION_ID{{/apiKeyRegister}} - -{{#apiKeyUpdate}}ApiSpecAuthName: apiKey, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, registrationId: ${{APIKEY_REGISTRATION_ID}}{{/apiKeyUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs {{/fileCreateOrUpdateEnvironmentFile}} - API_KEY: ${{SECRET_API_KEY}} \ No newline at end of file diff --git a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch-api-key/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch-api-key/teamsapp.yml.tpl.mustache deleted file mode 100644 index 90b531700b..0000000000 --- a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch-api-key/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,39 +0,0 @@ -{{#header}} version: v1.7 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#apiKeyRegister}}ApiSpecAuthName: apiKey, primaryClientSecret: ${{SECRET_API_KEY}}, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, ApiSpecAuthRegistrationIdEnvName: APIKEY_REGISTRATION_ID{{/apiKeyRegister}} - -{{#apiKeyUpdate}}ApiSpecAuthName: apiKey, apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml, registrationId: ${{APIKEY_REGISTRATION_ID}}{{/apiKeyUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} - -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index d07d243f2c..0000000000 --- a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} FUNC, FUNC_NAME: repair {{/script}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} diff --git a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache deleted file mode 100644 index ca2cd4680c..0000000000 --- a/templates/constraints/yml/templates/ts/copilot-plugin-from-scratch/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,35 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-sme {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} - -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} - -{{#azureFunctionsZipDeploy}} resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/dashboard-tab/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/dashboard-tab/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index b1f113340d..0000000000 --- a/templates/constraints/yml/templates/ts/dashboard-tab/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,18 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} TAB {{/script}} -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} devCert {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, TAB {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/dashboard-tab/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/dashboard-tab/teamsapp.yml.tpl.mustache deleted file mode 100644 index 41957c316d..0000000000 --- a/templates/constraints/yml/templates/ts/dashboard-tab/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: v1.4 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStaticWebAppGetDeploymentToken}} {{/azureStaticWebAppGetDeploymentToken}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install --production {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureStaticWebAppDeploy}} artifactFolder: build {{/azureStaticWebAppDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/default-bot-message-extension/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/default-bot-message-extension/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 5c1cf40800..0000000000 --- a/templates/constraints/yml/templates/ts/default-bot-message-extension/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,20 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/default-bot-message-extension/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/default-bot-message-extension/teamsapp.yml.tpl.mustache deleted file mode 100644 index 0d9d74daf2..0000000000 --- a/templates/constraints/yml/templates/ts/default-bot-message-extension/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore{{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/default-bot/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/default-bot/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 5c1cf40800..0000000000 --- a/templates/constraints/yml/templates/ts/default-bot/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,20 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/default-bot/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/default-bot/teamsapp.yml.tpl.mustache deleted file mode 100644 index 2e8c3c895c..0000000000 --- a/templates/constraints/yml/templates/ts/default-bot/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/link-unfurling/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/link-unfurling/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 8be44c6960..0000000000 --- a/templates/constraints/yml/templates/ts/link-unfurling/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/link-unfurling/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/link-unfurling/teamsapp.yml.tpl.mustache deleted file mode 100644 index 6c469929da..0000000000 --- a/templates/constraints/yml/templates/ts/link-unfurling/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore{{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/m365-message-extension/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/m365-message-extension/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 8be44c6960..0000000000 --- a/templates/constraints/yml/templates/ts/m365-message-extension/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/m365-message-extension/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/m365-message-extension/teamsapp.yml.tpl.mustache deleted file mode 100644 index d601f34979..0000000000 --- a/templates/constraints/yml/templates/ts/m365-message-extension/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/message-extension-copilot/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/message-extension-copilot/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 8be44c6960..0000000000 --- a/templates/constraints/yml/templates/ts/message-extension-copilot/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/message-extension-copilot/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/message-extension-copilot/teamsapp.yml.tpl.mustache deleted file mode 100644 index d601f34979..0000000000 --- a/templates/constraints/yml/templates/ts/message-extension-copilot/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/message-extension/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/message-extension/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 91014f29a3..0000000000 --- a/templates/constraints/yml/templates/ts/message-extension/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,21 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} m365extensions {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/message-extension/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/message-extension/teamsapp.yml.tpl.mustache deleted file mode 100644 index 6c469929da..0000000000 --- a/templates/constraints/yml/templates/ts/message-extension/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,31 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-me {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore{{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/non-sso-tab-default-bot/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/non-sso-tab-default-bot/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index c15325242d..0000000000 --- a/templates/constraints/yml/templates/ts/non-sso-tab-default-bot/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,24 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} -{{#script}} TAB {{/script}} -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} devCert {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - - # Generate runtime environment variables for tab -{{#fileCreateOrUpdateEnvironmentFile}} target: ./tab/.localConfigs, TAB, noComment {{/fileCreateOrUpdateEnvironmentFile}} - - # Generate runtime environment variables for bot -{{#fileCreateOrUpdateEnvironmentFile}} target: ./bot/.localConfigs, BOT, noComment {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/non-sso-tab-default-bot/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/non-sso-tab-default-bot/teamsapp.yml.tpl.mustache deleted file mode 100644 index 973441dd4e..0000000000 --- a/templates/constraints/yml/templates/ts/non-sso-tab-default-bot/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,33 +0,0 @@ -{{#header}} version: v1.4 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStaticWebAppGetDeploymentToken}} {{/azureStaticWebAppGetDeploymentToken}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} workingDirectory: ., args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureStaticWebAppDeploy}} artifactFolder: tab/build {{/azureStaticWebAppDeploy}} -{{#azureAppServiceZipDeploy}} workingDirectory: bot, resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/non-sso-tab/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/non-sso-tab/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 2a2d657dcf..0000000000 --- a/templates/constraints/yml/templates/ts/non-sso-tab/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - - # Set TAB_DOMAIN and TAB_ENDPOINT for local launch - - uses: script - with: - run: - echo "::set-teamsfx-env TAB_DOMAIN=localhost:53000"; - echo "::set-teamsfx-env TAB_ENDPOINT=https://localhost:53000"; - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} devCert {{/devToolInstall}} - - # Run npm command - - uses: cli/runNpmCommand - with: - args: install --no-audit - -{{#fileCreateOrUpdateEnvironmentFile}} {{/fileCreateOrUpdateEnvironmentFile}} - PORT: 53000 - SSL_CRT_FILE: ${{SSL_CRT_FILE}} - SSL_KEY_FILE: ${{SSL_KEY_FILE}} diff --git a/templates/constraints/yml/templates/ts/non-sso-tab/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/non-sso-tab/teamsapp.yml.tpl.mustache deleted file mode 100644 index 36bf303f5d..0000000000 --- a/templates/constraints/yml/templates/ts/non-sso-tab/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{TAB_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .webappignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3ad44bd136..0000000000 --- a/templates/constraints/yml/templates/ts/notification-http-timer-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} func {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/notification-http-timer-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-http-timer-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 774172e109..0000000000 --- a/templates/constraints/yml/templates/ts/notification-http-timer-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/notification-http-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-http-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3ad44bd136..0000000000 --- a/templates/constraints/yml/templates/ts/notification-http-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} func {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/notification-http-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-http-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 774172e109..0000000000 --- a/templates/constraints/yml/templates/ts/notification-http-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/notification-restify/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-restify/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 5c1cf40800..0000000000 --- a/templates/constraints/yml/templates/ts/notification-restify/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,20 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/notification-restify/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-restify/teamsapp.yml.tpl.mustache deleted file mode 100644 index 36e963a8d2..0000000000 --- a/templates/constraints/yml/templates/ts/notification-restify/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .appserviceignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/notification-timer-trigger/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-timer-trigger/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 3ad44bd136..0000000000 --- a/templates/constraints/yml/templates/ts/notification-timer-trigger/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,22 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#devToolInstall}} func {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/notification-timer-trigger/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/notification-timer-trigger/teamsapp.yml.tpl.mustache deleted file mode 100644 index 774172e109..0000000000 --- a/templates/constraints/yml/templates/ts/notification-timer-trigger/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} resourceId: ${{BOT_AZURE_FUNCTION_APP_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/office-addin/teamsapp.yml.mustache b/templates/constraints/yml/templates/ts/office-addin/teamsapp.yml.mustache deleted file mode 100644 index 1828e06293..0000000000 --- a/templates/constraints/yml/templates/ts/office-addin/teamsapp.yml.mustache +++ /dev/null @@ -1,15 +0,0 @@ -{{#header}} version: v1.4 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStaticWebAppGetDeploymentToken}} {{/azureStaticWebAppGetDeploymentToken}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureStaticWebAppDeploy}} artifactFolder: dist {{/azureStaticWebAppDeploy}} diff --git a/templates/constraints/yml/templates/ts/spfx-tab/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/spfx-tab/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index f154503c92..0000000000 --- a/templates/constraints/yml/templates/ts/spfx-tab/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,15 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppValidateManifest}} localManifest {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} localManifest {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#cliRunNpmCommand}} install, workingDirectory: src, args: install --no-audit {{/cliRunNpmCommand}} diff --git a/templates/constraints/yml/templates/ts/spfx-tab/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/spfx-tab/teamsapp.yml.tpl.mustache deleted file mode 100644 index 7dea04ecc8..0000000000 --- a/templates/constraints/yml/templates/ts/spfx-tab/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,29 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, workingDirectory: src, args: install {{/cliRunNpmCommand}} -{{#cliRunNpxCommand}} workingDirectory: src, bundle {{/cliRunNpxCommand}} -{{#cliRunNpxCommand}} workingDirectory: src, package {{/cliRunNpxCommand}} -{{#spfxDeploy}} {{/spfxDeploy}} - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppCopyAppPackageToSPFx}} {{/teamsAppCopyAppPackageToSPFx}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/sso-tab-with-obo-flow/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/sso-tab-with-obo-flow/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index b92831d96c..0000000000 --- a/templates/constraints/yml/templates/ts/sso-tab-with-obo-flow/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,42 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#script}} TAB, FUNC {{/script}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} - -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -deploy: -{{#devToolInstall}} devCert, func, funcToolsVersion: ~4.0.5455 {{/devToolInstall}} - -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#cliRunNpmCommand}} install, workingDirectory: api, args: install --no-audit {{/cliRunNpmCommand}} - - # Generate runtime environment variables for tab -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, TAB, noComment {{/fileCreateOrUpdateEnvironmentFile}} - REACT_APP_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - REACT_APP_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html - REACT_APP_FUNC_NAME: ${{FUNC_NAME}} - REACT_APP_FUNC_ENDPOINT: ${{FUNC_ENDPOINT}} - - # Generate runtime environment variables for backend -{{#fileCreateOrUpdateEnvironmentFile}} target: ./api/.localConfigs, noComment {{/fileCreateOrUpdateEnvironmentFile}} - M365_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - M365_CLIENT_SECRET: ${{SECRET_AAD_APP_CLIENT_SECRET}} - M365_TENANT_ID: ${{AAD_APP_TENANT_ID}} - M365_AUTHORITY_HOST: ${{AAD_APP_OAUTH_AUTHORITY_HOST}} - ALLOWED_APP_IDS: 1fec8e78-bce4-4aaf-ab1b-5451cc387264;5e3ce6c0-2b1f-4285-8d4b-75ee78787346;0ec893e0-5785-4de6-99da-4ed124e5296c;4345a7b9-9a63-4910-a426-35363201d503;4765445b-32c6-49b0-83e6-1d93765276ca;d3590ed6-52b3-4102-aeff-aad2292ab01c;00000002-0000-0ff1-ce00-000000000000;bc59ab01-8403-45c6-8796-ac3ef710b3e3;27922004-5251-4030-b22d-91ecd9a37ea4 diff --git a/templates/constraints/yml/templates/ts/sso-tab-with-obo-flow/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/sso-tab-with-obo-flow/teamsapp.yml.tpl.mustache deleted file mode 100644 index 5b91a8d061..0000000000 --- a/templates/constraints/yml/templates/ts/sso-tab-with-obo-flow/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,43 +0,0 @@ -{{#header}} version: v1.4 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#aadAppCreate}} {{/aadAppCreate}} - -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-tab {{/armDeploy}} - -{{#azureStaticWebAppGetDeploymentToken}} {{/azureStaticWebAppGetDeploymentToken}} - -{{#aadAppUpdate}} {{/aadAppUpdate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppExtendToM365}} {{/teamsAppExtendToM365}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} - env: - REACT_APP_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - REACT_APP_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html - REACT_APP_FUNC_NAME: getUserProfile - REACT_APP_FUNC_ENDPOINT: ${{API_FUNCTION_ENDPOINT}} -{{#azureStaticWebAppDeploy}} artifactFolder: ./build {{/azureStaticWebAppDeploy}} -{{#cliRunNpmCommand}} install, workingDirectory: api, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} workingDirectory: api, args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureFunctionsZipDeploy}} workingDirectory: api, resourceId: ${{API_FUNCTION_RESOURCE_ID}}, ignoreFile: .funcignore {{/azureFunctionsZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/constraints/yml/templates/ts/workflow/teamsapp.local.yml.tpl.mustache b/templates/constraints/yml/templates/ts/workflow/teamsapp.local.yml.tpl.mustache deleted file mode 100644 index 5c1cf40800..0000000000 --- a/templates/constraints/yml/templates/ts/workflow/teamsapp.local.yml.tpl.mustache +++ /dev/null @@ -1,20 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#botFrameworkCreate}} {{/botFrameworkCreate}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} - -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} - -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -deploy: -{{#cliRunNpmCommand}} install, args: install --no-audit {{/cliRunNpmCommand}} - -{{#fileCreateOrUpdateEnvironmentFile}} target: ./.localConfigs, BOT {{/fileCreateOrUpdateEnvironmentFile}} diff --git a/templates/constraints/yml/templates/ts/workflow/teamsapp.yml.tpl.mustache b/templates/constraints/yml/templates/ts/workflow/teamsapp.yml.tpl.mustache deleted file mode 100644 index 36e963a8d2..0000000000 --- a/templates/constraints/yml/templates/ts/workflow/teamsapp.yml.tpl.mustache +++ /dev/null @@ -1,30 +0,0 @@ -{{#header}} version: 1.0.0 {{/header}} - -environmentFolderPath: ./env - -# Triggered when 'teamsapp provision' is executed -provision: -{{#teamsAppCreate}} {{/teamsAppCreate}} - -{{#botAadAppCreate}} {{/botAadAppCreate}} - -{{#armDeploy}} deploymentName: Create-resources-for-bot {{/armDeploy}} - -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} - -# Triggered when 'teamsapp deploy' is executed -deploy: -{{#cliRunNpmCommand}} install, args: install {{/cliRunNpmCommand}} -{{#cliRunNpmCommand}} args: run build --if-present, build {{/cliRunNpmCommand}} -{{#azureAppServiceZipDeploy}} resourceId: ${{BOT_AZURE_APP_SERVICE_RESOURCE_ID}}, ignoreFile: .appserviceignore {{/azureAppServiceZipDeploy}} - -# Triggered when 'teamsapp publish' is executed -publish: -{{#teamsAppValidateManifest}} {{/teamsAppValidateManifest}} -{{#teamsAppZipAppPackage}} {{/teamsAppZipAppPackage}} -{{#teamsAppValidateAppPackage}} {{/teamsAppValidateAppPackage}} -{{#teamsAppUpdate}} {{/teamsAppUpdate}} -{{#teamsAppPublishAppPackage}} {{/teamsAppPublishAppPackage}} diff --git a/templates/csharp/ai-assistant-bot/appPackage/manifest.json.tpl b/templates/csharp/ai-assistant-bot/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/ai-assistant-bot/appPackage/manifest.json.tpl +++ b/templates/csharp/ai-assistant-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/ai-bot/appPackage/manifest.json.tpl b/templates/csharp/ai-bot/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/ai-bot/appPackage/manifest.json.tpl +++ b/templates/csharp/ai-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl b/templates/csharp/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl index e00d86c5f7..750906601c 100644 --- a/templates/csharp/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl +++ b/templates/csharp/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl b/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl index 1e73ae0853..dc38518bb1 100644 --- a/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl +++ b/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl b/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl index ae9474d675..e542e9efb4 100644 --- a/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl +++ b/templates/csharp/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/csharp/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl b/templates/csharp/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl index 68c0e9d958..f21d2fc7f5 100644 --- a/templates/csharp/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl +++ b/templates/csharp/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/csharp/command-and-response/appPackage/manifest.json.tpl b/templates/csharp/command-and-response/appPackage/manifest.json.tpl index cf2bbc13dc..84ea23d920 100644 --- a/templates/csharp/command-and-response/appPackage/manifest.json.tpl +++ b/templates/csharp/command-and-response/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/copilot-gpt-from-scratch-plugin/appPackage/ai-plugin.json.tpl b/templates/csharp/copilot-gpt-from-scratch-plugin/appPackage/ai-plugin.json.tpl index 84c5aa2141..4bdad51d83 100644 --- a/templates/csharp/copilot-gpt-from-scratch-plugin/appPackage/ai-plugin.json.tpl +++ b/templates/csharp/copilot-gpt-from-scratch-plugin/appPackage/ai-plugin.json.tpl @@ -14,8 +14,7 @@ "data_path": "$", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/csharp/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl b/templates/csharp/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl +++ b/templates/csharp/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/custom-copilot-assistant-new/appPackage/manifest.json.tpl b/templates/csharp/custom-copilot-assistant-new/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/custom-copilot-assistant-new/appPackage/manifest.json.tpl +++ b/templates/csharp/custom-copilot-assistant-new/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/custom-copilot-basic/appPackage/manifest.json.tpl b/templates/csharp/custom-copilot-basic/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/custom-copilot-basic/appPackage/manifest.json.tpl +++ b/templates/csharp/custom-copilot-basic/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl b/templates/csharp/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl +++ b/templates/csharp/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl b/templates/csharp/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl +++ b/templates/csharp/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/custom-copilot-rag-customize/appPackage/manifest.json.tpl b/templates/csharp/custom-copilot-rag-customize/appPackage/manifest.json.tpl index 7d6a5403f9..0341b046e6 100644 --- a/templates/csharp/custom-copilot-rag-customize/appPackage/manifest.json.tpl +++ b/templates/csharp/custom-copilot-rag-customize/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl b/templates/csharp/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl index 4035db1526..b76346494d 100644 --- a/templates/csharp/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl +++ b/templates/csharp/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/default-bot/appPackage/manifest.json.tpl b/templates/csharp/default-bot/appPackage/manifest.json.tpl index 38c4bed7c0..d81265f547 100644 --- a/templates/csharp/default-bot/appPackage/manifest.json.tpl +++ b/templates/csharp/default-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/link-unfurling/.gitignore b/templates/csharp/link-unfurling/.gitignore index 90f87c2f9c..7ca8560fdb 100644 --- a/templates/csharp/link-unfurling/.gitignore +++ b/templates/csharp/link-unfurling/.gitignore @@ -24,3 +24,7 @@ bld/ # Notification local store .notification.localstore.json + +# Test Tool +.notification.testtoolstore.json +devTools diff --git a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/.gitignore b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/.gitignore index c5cae9258c..76e707553c 100644 --- a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/.gitignore +++ b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/.gitignore @@ -5,6 +5,10 @@ env/.env.*.user env/.env.local appsettings.Development.json .deployment +appsettings.TestTool.json # User-specific files *.user + +# Notification local store +.notification.localstore \ No newline at end of file diff --git a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/README.md.tpl b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/README.md.tpl index 4e419534be..57849ac8b9 100644 --- a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/README.md.tpl +++ b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/create-devtunnel-button.png) 2. Right-click the '{{NewProjectTypeName}}' project in Solution Explorer and select Teams Toolkit > Prepare Teams App Dependencies @@ -10,6 +15,12 @@
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/debug-button.png) 5. In the opened web browser, select Add button to test the app in Teams 6. You can unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} + +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} ## Run the app on other platforms diff --git a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/launchSettings.json.tpl b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/launchSettings.json.tpl index 56adc22e94..070cd51932 100644 --- a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/launchSettings.json.tpl +++ b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/launchSettings.json.tpl @@ -1,5 +1,13 @@ { "profiles": { +{{#enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -8,6 +16,14 @@ "Outlook (browser)": { "commandName": "Project", "launchUrl": "https://outlook.office.com/mail?login_hint=${{TEAMSFX_M365_USER_NAME}}", - } + }, +{{^enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} } } \ No newline at end of file diff --git a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl index bddd3ac21e..51bf89be2a 100644 --- a/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl +++ b/templates/csharp/link-unfurling/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl @@ -1,4 +1,29 @@ [ +{{#enableTestToolByDefault}} + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] + }, +{{/enableTestToolByDefault}} { "Name": "Microsoft Teams (browser)", "Projects": [ @@ -44,5 +69,33 @@ "DebugTarget": "Start Project" } ] +{{#enableTestToolByDefault}} + } +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + }, + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] } +{{/enableTestToolByDefault}} ] \ No newline at end of file diff --git a/templates/csharp/link-unfurling/Properties/launchSettings.json.tpl b/templates/csharp/link-unfurling/Properties/launchSettings.json.tpl index e954ad3c6f..e22891341f 100644 --- a/templates/csharp/link-unfurling/Properties/launchSettings.json.tpl +++ b/templates/csharp/link-unfurling/Properties/launchSettings.json.tpl @@ -1,6 +1,22 @@ { "profiles": { {{^isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -23,7 +39,23 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} //// Uncomment following profile to debug project only (without launching Teams) //, //"Start Project (not in Teams)": { @@ -38,6 +70,18 @@ //} {{/isNewProjectTypeEnabled}} {{#isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} "Start Project": { "commandName": "Project", "dotnetRunMessages": true, @@ -46,7 +90,19 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} {{/isNewProjectTypeEnabled}} } } \ No newline at end of file diff --git a/templates/csharp/link-unfurling/README.md b/templates/csharp/link-unfurling/README.md.tpl similarity index 69% rename from templates/csharp/link-unfurling/README.md rename to templates/csharp/link-unfurling/README.md.tpl index fcf754e406..2515638273 100644 --- a/templates/csharp/link-unfurling/README.md +++ b/templates/csharp/link-unfurling/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel 2. Right-click your project and select Teams Toolkit > Prepare Teams App Dependencies 3. If prompted, sign in with a Microsoft 365 account for the Teams organization you want @@ -9,9 +14,15 @@ to install the app to 4. Press F5, or select the Debug > Start Debugging menu in Visual Studio 5. In the launched browser, select the Add button to load the app in Teams 6. You can unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} > For local debugging using Teams Toolkit CLI, you need to do some extra steps described in [Set up your Teams Toolkit CLI for local debugging](https://aka.ms/teamsfx-cli-debugging). +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} + ## Learn more New to Teams app development or Teams Toolkit? Learn more about diff --git a/templates/csharp/link-unfurling/appPackage/manifest.json.tpl b/templates/csharp/link-unfurling/appPackage/manifest.json.tpl index 8dc3179f18..36e217f4d2 100644 --- a/templates/csharp/link-unfurling/appPackage/manifest.json.tpl +++ b/templates/csharp/link-unfurling/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/link-unfurling/appsettings.TestTool.json b/templates/csharp/link-unfurling/appsettings.TestTool.json new file mode 100644 index 0000000000..80c82ca282 --- /dev/null +++ b/templates/csharp/link-unfurling/appsettings.TestTool.json @@ -0,0 +1,13 @@ +{ + "Logging": { + "LogLevel": { + "Default": "Information", + "Microsoft": "Warning", + "Microsoft.Hosting.Lifetime": "Information" + } + }, + "AllowedHosts": "*", + "BOT_ID": "", + "BOT_PASSWORD": "", + "BOT_TYPE": "" +} \ No newline at end of file diff --git a/templates/csharp/message-extension-action/.gitignore b/templates/csharp/message-extension-action/.gitignore index 9ecb6a5c1b..8ca0037bab 100644 --- a/templates/csharp/message-extension-action/.gitignore +++ b/templates/csharp/message-extension-action/.gitignore @@ -24,3 +24,7 @@ bld/ # Notification local store .notification.localstore.json + +# Test Tool +.notification.testtoolstore.json +devTools diff --git a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/.gitignore b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/.gitignore index c5cae9258c..cfc9328179 100644 --- a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/.gitignore +++ b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/.gitignore @@ -8,3 +8,6 @@ appsettings.Development.json # User-specific files *.user + +# Notification local store +.notification.localstore diff --git a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/README.md.tpl b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/README.md.tpl index 966729d824..8689db4c11 100644 --- a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/README.md.tpl +++ b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can trigger "create card" command from compose message area, the command box, or directly from a message. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/create-devtunnel-button.png) 2. Right-click the '{{NewProjectTypeName}}' project in Solution Explorer and select Teams Toolkit > Prepare Teams App Dependencies @@ -10,6 +15,12 @@
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/debug-button.png) 5. In the opened web browser, select Add button to test the app in Teams 6. You can trigger "create card" command from compose message area, the command box, or directly from a message. +{{/enableTestToolByDefault}} + +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} ## Get more info diff --git a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/launchSettings.json.tpl b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/launchSettings.json.tpl index 5f945db2d1..389b761a75 100644 --- a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/launchSettings.json.tpl +++ b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/launchSettings.json.tpl @@ -1,9 +1,25 @@ { "profiles": { +{{#enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", "launchUrl": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}", - } + }, +{{^enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} } } \ No newline at end of file diff --git a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl index 12c3f14c3f..3eb661cd35 100644 --- a/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl +++ b/templates/csharp/message-extension-action/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl @@ -1,4 +1,29 @@ [ + {{#enableTestToolByDefault}} + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] + }, +{{/enableTestToolByDefault}} { "Name": "Microsoft Teams (browser)", "Projects": [ @@ -21,5 +46,33 @@ "DebugTarget": "Start Project" } ] +{{#enableTestToolByDefault}} + } +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + }, + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] } +{{/enableTestToolByDefault}} ] \ No newline at end of file diff --git a/templates/csharp/message-extension-action/Properties/launchSettings.json.tpl b/templates/csharp/message-extension-action/Properties/launchSettings.json.tpl index c2d5650e2b..f4fd01061c 100644 --- a/templates/csharp/message-extension-action/Properties/launchSettings.json.tpl +++ b/templates/csharp/message-extension-action/Properties/launchSettings.json.tpl @@ -1,6 +1,22 @@ { "profiles": { {{^isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -12,7 +28,23 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} //// Uncomment following profile to debug project only (without launching Teams) //, //"Start Project (not in Teams)": { @@ -27,6 +59,18 @@ //} {{/isNewProjectTypeEnabled}} {{#isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} "Start Project": { "commandName": "Project", "dotnetRunMessages": true, @@ -35,7 +79,19 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} {{/isNewProjectTypeEnabled}} } } \ No newline at end of file diff --git a/templates/csharp/message-extension-action/README.md b/templates/csharp/message-extension-action/README.md.tpl similarity index 65% rename from templates/csharp/message-extension-action/README.md rename to templates/csharp/message-extension-action/README.md.tpl index b7ae6ea531..254f0114bf 100644 --- a/templates/csharp/message-extension-action/README.md +++ b/templates/csharp/message-extension-action/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can trigger "create card" command from compose message area, the command box, or directly from a message. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel 2. Right-click your project and select Teams Toolkit > Prepare Teams App Dependencies 3. If prompted, sign in with a Microsoft 365 account for the Teams organization you want @@ -9,9 +14,15 @@ to install the app to 4. Press F5, or select the Debug > Start Debugging menu in Visual Studio 5. In the launched browser, select the Add button to load the app in Teams 6. You can trigger "create card" command from compose message area, the command box, or directly from a message. +{{/enableTestToolByDefault}} > For local debugging using Teams Toolkit CLI, you need to do some extra steps described in [Set up your Teams Toolkit CLI for local debugging](https://aka.ms/teamsfx-cli-debugging). +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} + ## Learn more New to Teams app development or Teams Toolkit? Learn more about diff --git a/templates/csharp/message-extension-action/appPackage/manifest.json.tpl b/templates/csharp/message-extension-action/appPackage/manifest.json.tpl index f10cec7aeb..06004b7e45 100644 --- a/templates/csharp/message-extension-action/appPackage/manifest.json.tpl +++ b/templates/csharp/message-extension-action/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/message-extension-action/appsettings.TestTool.json b/templates/csharp/message-extension-action/appsettings.TestTool.json new file mode 100644 index 0000000000..9578f3c646 --- /dev/null +++ b/templates/csharp/message-extension-action/appsettings.TestTool.json @@ -0,0 +1,14 @@ +{ + "Logging": { + "LogLevel": { + "Default": "Information", + "Microsoft": "Warning", + "Microsoft.Hosting.Lifetime": "Information" + } + }, + "AllowedHosts": "*", + "BOT_ID": "", + "BOT_PASSWORD": "", + "BOT_TYPE": "", + "BOT_TENANT_ID": "" +} diff --git a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/.gitignore b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/.gitignore index c5cae9258c..3de544e49c 100644 --- a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/.gitignore +++ b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/.gitignore @@ -5,6 +5,10 @@ env/.env.*.user env/.env.local appsettings.Development.json .deployment +appsettings.Development.json # User-specific files *.user + +# Notification local store +.notification.localstore \ No newline at end of file diff --git a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/README.md.tpl b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/README.md.tpl index ab0b6759ed..2ef14d449d 100644 --- a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/README.md.tpl +++ b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/README.md.tpl @@ -7,9 +7,16 @@ > To run the app template in your local dev machine, you will need: > > - [Visual Studio 2022](https://aka.ms/vs) 17.8 or higher and [install Teams Toolkit](https://aka.ms/install-teams-toolkit-vs). +{{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) +{{/enableTestToolByDefault}} > - [Microsoft 365 Copilot license](https://learn.microsoft.com/microsoft-365-copilot/extensibility/prerequisites#prerequisites) +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can search NuGet package from compose message area, or from the command box. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create a Tunnel (set authentication type to Public) or select an existing public dev tunnel
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/create-devtunnel-button.png). 2. Right-click the '{{NewProjectTypeName}}' project and select Teams Toolkit > Prepare Teams App Dependencies @@ -19,6 +26,14 @@
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/debug-button.png) 5. In the launched browser, select the Add button to load the app in Teams. 6. You can search for NuGet package from the message input field or the command box. +{{/enableTestToolByDefault}} + +> For local debugging using Teams Toolkit CLI, you need to do some extra steps described in [Set up your Teams Toolkit CLI for local debugging](https://aka.ms/teamsfx-cli-debugging). + +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} ## Run the app on other platforms diff --git a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/launchSettings.json.tpl b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/launchSettings.json.tpl index 33a3da8878..4c57989778 100644 --- a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/launchSettings.json.tpl +++ b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/launchSettings.json.tpl @@ -1,5 +1,13 @@ { "profiles": { +{{#enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -14,6 +22,14 @@ "Outlook (browser)": { "commandName": "Project", "launchUrl": "https://outlook.office.com/mail?appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}", - } + }, +{{^enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} } } \ No newline at end of file diff --git a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl index 0ffba5707d..950205a451 100644 --- a/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl +++ b/templates/csharp/message-extension-copilot/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl @@ -1,4 +1,29 @@ [ +{{#enableTestToolByDefault}} + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] + }, +{{/enableTestToolByDefault}} { "Name": "Microsoft Teams (browser)", "Projects": [ @@ -67,5 +92,33 @@ "DebugTarget": "Start Project" } ] +{{#enableTestToolByDefault}} + } +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + }, + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] } +{{/enableTestToolByDefault}} ] \ No newline at end of file diff --git a/templates/csharp/message-extension-copilot/Properties/launchSettings.json.tpl b/templates/csharp/message-extension-copilot/Properties/launchSettings.json.tpl index 23dc213183..c6335ce577 100644 --- a/templates/csharp/message-extension-copilot/Properties/launchSettings.json.tpl +++ b/templates/csharp/message-extension-copilot/Properties/launchSettings.json.tpl @@ -1,6 +1,22 @@ { "profiles": { {{^isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -36,7 +52,23 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} //// Uncomment following profile to debug project only (without launching Teams) //, //"Start Project (not in Teams)": { @@ -51,6 +83,18 @@ //} {{/isNewProjectTypeEnabled}} {{#isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} "Start Project": { "commandName": "Project", "dotnetRunMessages": true, @@ -59,7 +103,19 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} {{/isNewProjectTypeEnabled}} } } diff --git a/templates/csharp/message-extension-copilot/README.md b/templates/csharp/message-extension-copilot/README.md.tpl similarity index 78% rename from templates/csharp/message-extension-copilot/README.md rename to templates/csharp/message-extension-copilot/README.md.tpl index d0510f18db..1a8748fa9d 100644 --- a/templates/csharp/message-extension-copilot/README.md +++ b/templates/csharp/message-extension-copilot/README.md.tpl @@ -7,9 +7,16 @@ > To run the app template in your local dev machine, you will need: > > - [Visual Studio 2022](https://aka.ms/vs) 17.8 or higher and [install Teams Toolkit](https://aka.ms/install-teams-toolkit-vs). +{{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts). +{{/enableTestToolByDefault}} > - [Microsoft 365 Copilot license](https://learn.microsoft.com/microsoft-365-copilot/extensibility/prerequisites#prerequisites) +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can search NuGet package from compose message area, or from the command box. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select `Dev Tunnels > Create a Tunnel` (set authentication type to Public) or select an existing public dev tunnel. 2. Right-click your project and select `Teams Toolkit > Prepare Teams App Dependencies`. 3. If prompted, sign in with a Microsoft 365 account for the Teams organization you want @@ -24,9 +31,15 @@ 3. Open the `Copilot` app, select `Plugins`, and from the list of plugins, turn on the toggle for your message extension. Now, you can send a prompt to trigger your plugin. 4. Send a message to Copilot to find an NuGet package information. For example: Find the NuGet package info on Microsoft.CSharp. > Note: This prompt may not always make Copilot include a response from your message extension. If it happens, try some other prompts or leave a feedback to us by thumbing down the Copilot response and leave a message tagged with [MessageExtension]. +{{/enableTestToolByDefault}} > For local debugging using Teams Toolkit CLI, you need to do some extra steps described in [Set up your Teams Toolkit CLI for local debugging](https://aka.ms/teamsfx-cli-debugging). +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} + ## Learn more - [Extend Microsoft 365 Copilot](https://aka.ms/teamsfx-copilot-plugin) diff --git a/templates/csharp/message-extension-search/.gitignore b/templates/csharp/message-extension-search/.gitignore index 9ecb6a5c1b..8ca0037bab 100644 --- a/templates/csharp/message-extension-search/.gitignore +++ b/templates/csharp/message-extension-search/.gitignore @@ -24,3 +24,7 @@ bld/ # Notification local store .notification.localstore.json + +# Test Tool +.notification.testtoolstore.json +devTools diff --git a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/.gitignore b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/.gitignore index c5cae9258c..3de544e49c 100644 --- a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/.gitignore +++ b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/.gitignore @@ -5,6 +5,10 @@ env/.env.*.user env/.env.local appsettings.Development.json .deployment +appsettings.Development.json # User-specific files *.user + +# Notification local store +.notification.localstore \ No newline at end of file diff --git a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/README.md.tpl b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/README.md.tpl index 8aa846a89f..3a9480be36 100644 --- a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/README.md.tpl +++ b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can search nuget package from compose message area, or from the command box. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/create-devtunnel-button.png) 2. Right-click the '{{NewProjectTypeName}}' project in Solution Explorer and select Teams Toolkit > Prepare Teams App Dependencies @@ -10,6 +15,12 @@
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/debug-button.png) 5. In the opened web browser, select Add button to test the app in Teams 6. You can search for NuGet package from the message input field or the command box. +{{/enableTestToolByDefault}} + +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} ## Run the app on other platforms diff --git a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/launchSettings.json.tpl b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/launchSettings.json.tpl index dd29a8f995..3f660a8034 100644 --- a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/launchSettings.json.tpl +++ b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/launchSettings.json.tpl @@ -1,5 +1,13 @@ { "profiles": { +{{#enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -10,5 +18,13 @@ "commandName": "Project", "launchUrl": "https://outlook.office.com/mail?appTenantId=${{TEAMS_APP_TENANT_ID}}&login_hint=${{TEAMSFX_M365_USER_NAME}}", } - } + }, +{{^enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} } \ No newline at end of file diff --git a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl index bddd3ac21e..0f49223a86 100644 --- a/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl +++ b/templates/csharp/message-extension-search/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl @@ -1,4 +1,29 @@ [ + {{#enableTestToolByDefault}} + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] + }, +{{/enableTestToolByDefault}} { "Name": "Microsoft Teams (browser)", "Projects": [ @@ -44,5 +69,33 @@ "DebugTarget": "Start Project" } ] +{{#enableTestToolByDefault}} + } +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + }, + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] } +{{/enableTestToolByDefault}} ] \ No newline at end of file diff --git a/templates/csharp/message-extension-search/Properties/launchSettings.json.tpl b/templates/csharp/message-extension-search/Properties/launchSettings.json.tpl index e954ad3c6f..e22891341f 100644 --- a/templates/csharp/message-extension-search/Properties/launchSettings.json.tpl +++ b/templates/csharp/message-extension-search/Properties/launchSettings.json.tpl @@ -1,6 +1,22 @@ { "profiles": { {{^isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -23,7 +39,23 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} //// Uncomment following profile to debug project only (without launching Teams) //, //"Start Project (not in Teams)": { @@ -38,6 +70,18 @@ //} {{/isNewProjectTypeEnabled}} {{#isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} "Start Project": { "commandName": "Project", "dotnetRunMessages": true, @@ -46,7 +90,19 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} {{/isNewProjectTypeEnabled}} } } \ No newline at end of file diff --git a/templates/csharp/message-extension-search/README.md b/templates/csharp/message-extension-search/README.md.tpl similarity index 66% rename from templates/csharp/message-extension-search/README.md rename to templates/csharp/message-extension-search/README.md.tpl index 0821d5f467..6fd647b104 100644 --- a/templates/csharp/message-extension-search/README.md +++ b/templates/csharp/message-extension-search/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can search nuget package from compose message area, or from the command box. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel 2. Right-click your project and select Teams Toolkit > Prepare Teams App Dependencies 3. If prompted, sign in with a Microsoft 365 account for the Teams organization you want @@ -9,9 +14,15 @@ to install the app to 4. Press F5, or select the Debug > Start Debugging menu in Visual Studio 5. In the launched browser, select the Add button to load the app in Teams 6. You can search nuget package from compose message area, or from the command box. +{{/enableTestToolByDefault}} > For local debugging using Teams Toolkit CLI, you need to do some extra steps described in [Set up your Teams Toolkit CLI for local debugging](https://aka.ms/teamsfx-cli-debugging). +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} + ## Learn more New to Teams app development or Teams Toolkit? Learn more about diff --git a/templates/csharp/message-extension-search/appPackage/manifest.json.tpl b/templates/csharp/message-extension-search/appPackage/manifest.json.tpl index 2e0be68cd6..90176e22b6 100644 --- a/templates/csharp/message-extension-search/appPackage/manifest.json.tpl +++ b/templates/csharp/message-extension-search/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/message-extension/.{{NewProjectTypeName}}/.gitignore b/templates/csharp/message-extension/.{{NewProjectTypeName}}/.gitignore index c5cae9258c..76e707553c 100644 --- a/templates/csharp/message-extension/.{{NewProjectTypeName}}/.gitignore +++ b/templates/csharp/message-extension/.{{NewProjectTypeName}}/.gitignore @@ -5,6 +5,10 @@ env/.env.*.user env/.env.local appsettings.Development.json .deployment +appsettings.TestTool.json # User-specific files *.user + +# Notification local store +.notification.localstore \ No newline at end of file diff --git a/templates/csharp/message-extension/.{{NewProjectTypeName}}/README.md.tpl b/templates/csharp/message-extension/.{{NewProjectTypeName}}/README.md.tpl index 1621aafb21..2680524024 100644 --- a/templates/csharp/message-extension/.{{NewProjectTypeName}}/README.md.tpl +++ b/templates/csharp/message-extension/.{{NewProjectTypeName}}/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can play with this app to create an adaptive card, search for an NuGet package or unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/create-devtunnel-button.png) 2. Right-click the '{{NewProjectTypeName}}' project in Solution Explorer and select Teams Toolkit > Prepare Teams App Dependencies @@ -10,6 +15,12 @@
![image](https://raw.githubusercontent.com/OfficeDev/TeamsFx/dev/docs/images/visualstudio/debug/debug-button.png) 5. In the opened web browser, select Add button to test the app in Teams 6. You can play with this app to create an adaptive card, search for an NuGet package or unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} + +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} ## Run the app on other platforms diff --git a/templates/csharp/message-extension/.{{NewProjectTypeName}}/launchSettings.json.tpl b/templates/csharp/message-extension/.{{NewProjectTypeName}}/launchSettings.json.tpl index 56adc22e94..070cd51932 100644 --- a/templates/csharp/message-extension/.{{NewProjectTypeName}}/launchSettings.json.tpl +++ b/templates/csharp/message-extension/.{{NewProjectTypeName}}/launchSettings.json.tpl @@ -1,5 +1,13 @@ { "profiles": { +{{#enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -8,6 +16,14 @@ "Outlook (browser)": { "commandName": "Project", "launchUrl": "https://outlook.office.com/mail?login_hint=${{TEAMSFX_M365_USER_NAME}}", - } + }, +{{^enableTestToolByDefault}} + // Launch project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + }, +{{/enableTestToolByDefault}} } } \ No newline at end of file diff --git a/templates/csharp/message-extension/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl b/templates/csharp/message-extension/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl index bddd3ac21e..0f49223a86 100644 --- a/templates/csharp/message-extension/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl +++ b/templates/csharp/message-extension/.{{NewProjectTypeName}}/{{ProjectName}}.slnLaunch.user.tpl @@ -1,4 +1,29 @@ [ + {{#enableTestToolByDefault}} + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] + }, +{{/enableTestToolByDefault}} { "Name": "Microsoft Teams (browser)", "Projects": [ @@ -44,5 +69,33 @@ "DebugTarget": "Start Project" } ] +{{#enableTestToolByDefault}} + } +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + }, + { + "Name": "Teams App Test Tool (browser)", + "Projects": [ + { + "Path": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Name": "{{NewProjectTypeName}}\\{{NewProjectTypeName}}.{{NewProjectTypeExt}}", + "Action": "StartWithoutDebugging", + "DebugTarget": "Teams App Test Tool (browser)" + }, + { +{{#PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}.csproj", + "Name": "{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} +{{^PlaceProjectFileInSolutionDir}} + "Path": "{{ProjectName}}\\{{ProjectName}}.csproj", + "Name": "{{ProjectName}}\\{{ProjectName}}.csproj", +{{/PlaceProjectFileInSolutionDir}} + "Action": "Start", + "DebugTarget": "Teams App Test Tool" + } + ] } +{{/enableTestToolByDefault}} ] \ No newline at end of file diff --git a/templates/csharp/message-extension/Properties/launchSettings.json.tpl b/templates/csharp/message-extension/Properties/launchSettings.json.tpl index e954ad3c6f..e22891341f 100644 --- a/templates/csharp/message-extension/Properties/launchSettings.json.tpl +++ b/templates/csharp/message-extension/Properties/launchSettings.json.tpl @@ -1,6 +1,22 @@ { "profiles": { {{^isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} // Debug project within Teams "Microsoft Teams (browser)": { "commandName": "Project", @@ -23,7 +39,23 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + // Debug project within Teams App Test Tool + "Teams App Test Tool (browser)": { + "commandName": "Project", + "dotnetRunMessages": true, + "launchBrowser": true, + "launchTestTool": true, + "launchUrl": "http://localhost:56150", + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} //// Uncomment following profile to debug project only (without launching Teams) //, //"Start Project (not in Teams)": { @@ -38,6 +70,18 @@ //} {{/isNewProjectTypeEnabled}} {{#isNewProjectTypeEnabled}} +{{#enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} "Start Project": { "commandName": "Project", "dotnetRunMessages": true, @@ -46,7 +90,19 @@ "ASPNETCORE_ENVIRONMENT": "Development" }, "hotReloadProfile": "aspnetcore" - } + }, +{{^enableTestToolByDefault}} + "Teams App Test Tool": { + "commandName": "Project", + "dotnetRunMessages": true, + "applicationUrl": "http://localhost:5130", + "environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "TestTool", + "TEAMSFX_NOTIFICATION_STORE_FILENAME": ".notification.testtoolstore.json" + }, + "hotReloadProfile": "aspnetcore" + }, +{{/enableTestToolByDefault}} {{/isNewProjectTypeEnabled}} } } \ No newline at end of file diff --git a/templates/csharp/message-extension/README.md b/templates/csharp/message-extension/README.md.tpl similarity index 65% rename from templates/csharp/message-extension/README.md rename to templates/csharp/message-extension/README.md.tpl index 486a7c6044..07d22d50ea 100644 --- a/templates/csharp/message-extension/README.md +++ b/templates/csharp/message-extension/README.md.tpl @@ -2,6 +2,11 @@ ## Quick Start +{{#enableTestToolByDefault}} +1. Press F5 to start debugging which launches your app in Teams App Test Tool using a web browser. +2. You can play with this app to create an adaptive card, search for an NuGet package or unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} 1. In the debug dropdown menu, select Dev Tunnels > Create A Tunnel (set authentication type to Public) or select an existing public dev tunnel 2. Right-click your project and select Teams Toolkit > Prepare Teams App Dependencies 3. If prompted, sign in with a Microsoft 365 account for the Teams organization you want @@ -9,9 +14,15 @@ to install the app to 4. Press F5, or select the Debug > Start Debugging menu in Visual Studio 5. In the launched browser, select the Add button to load the app in Teams 6. You can play with this app to create an adaptive card, search for an NuGet package or unfurl links from ".botframework.com" domain. +{{/enableTestToolByDefault}} > For local debugging using Teams Toolkit CLI, you need to do some extra steps described in [Set up your Teams Toolkit CLI for local debugging](https://aka.ms/teamsfx-cli-debugging). +{{^enableTestToolByDefault}} +## Debug in Test Tool +Teams App Test Tool allows developers test and debug bots locally without needing Microsoft 365 accounts, development tunnels, or Teams app and bot registration. See https://aka.ms/teams-toolkit-vs-test-tool for more details. +{{/enableTestToolByDefault}} + ## Learn more New to Teams app development or Teams Toolkit? Learn more about diff --git a/templates/csharp/message-extension/appPackage/manifest.json.tpl b/templates/csharp/message-extension/appPackage/manifest.json.tpl index f14ff9c6d1..3926bb7377 100644 --- a/templates/csharp/message-extension/appPackage/manifest.json.tpl +++ b/templates/csharp/message-extension/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/message-extension/appsettings.TestTool.json b/templates/csharp/message-extension/appsettings.TestTool.json new file mode 100644 index 0000000000..ddb2577519 --- /dev/null +++ b/templates/csharp/message-extension/appsettings.TestTool.json @@ -0,0 +1,14 @@ +{ + "Logging": { + "LogLevel": { + "Default": "Information", + "Microsoft": "Warning", + "Microsoft.Hosting.Lifetime": "Information" + } + }, + "AllowedHosts": "*", + "BOT_ID": "", + "BOT_PASSWORD": "", + "BOT_TYPE": "", + "BOT_TENANT_ID": "" +} \ No newline at end of file diff --git a/templates/csharp/non-sso-tab-ssr/appPackage/manifest.json.tpl b/templates/csharp/non-sso-tab-ssr/appPackage/manifest.json.tpl index 55678cd172..863caff4dd 100644 --- a/templates/csharp/non-sso-tab-ssr/appPackage/manifest.json.tpl +++ b/templates/csharp/non-sso-tab-ssr/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/non-sso-tab/appPackage/manifest.json.tpl b/templates/csharp/non-sso-tab/appPackage/manifest.json.tpl index e6d4641137..3a1f9d8fed 100644 --- a/templates/csharp/non-sso-tab/appPackage/manifest.json.tpl +++ b/templates/csharp/non-sso-tab/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/notification-http-timer-trigger-isolated/appPackage/manifest.json.tpl b/templates/csharp/notification-http-timer-trigger-isolated/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/csharp/notification-http-timer-trigger-isolated/appPackage/manifest.json.tpl +++ b/templates/csharp/notification-http-timer-trigger-isolated/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/notification-http-timer-trigger/appPackage/manifest.json.tpl b/templates/csharp/notification-http-timer-trigger/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/csharp/notification-http-timer-trigger/appPackage/manifest.json.tpl +++ b/templates/csharp/notification-http-timer-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/notification-http-trigger-isolated/appPackage/manifest.json.tpl b/templates/csharp/notification-http-trigger-isolated/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/csharp/notification-http-trigger-isolated/appPackage/manifest.json.tpl +++ b/templates/csharp/notification-http-trigger-isolated/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/notification-http-trigger/appPackage/manifest.json.tpl b/templates/csharp/notification-http-trigger/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/csharp/notification-http-trigger/appPackage/manifest.json.tpl +++ b/templates/csharp/notification-http-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/notification-timer-trigger-isolated/appPackage/manifest.json.tpl b/templates/csharp/notification-timer-trigger-isolated/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/csharp/notification-timer-trigger-isolated/appPackage/manifest.json.tpl +++ b/templates/csharp/notification-timer-trigger-isolated/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/notification-timer-trigger/appPackage/manifest.json.tpl b/templates/csharp/notification-timer-trigger/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/csharp/notification-timer-trigger/appPackage/manifest.json.tpl +++ b/templates/csharp/notification-timer-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/notification-webapi/appPackage/manifest.json.tpl b/templates/csharp/notification-webapi/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/csharp/notification-webapi/appPackage/manifest.json.tpl +++ b/templates/csharp/notification-webapi/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/sso-tab-ssr/appPackage/manifest.json.tpl b/templates/csharp/sso-tab-ssr/appPackage/manifest.json.tpl index 930bb37940..ab01aa477e 100644 --- a/templates/csharp/sso-tab-ssr/appPackage/manifest.json.tpl +++ b/templates/csharp/sso-tab-ssr/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/sso-tab/appPackage/manifest.json.tpl b/templates/csharp/sso-tab/appPackage/manifest.json.tpl index 930bb37940..ab01aa477e 100644 --- a/templates/csharp/sso-tab/appPackage/manifest.json.tpl +++ b/templates/csharp/sso-tab/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/csharp/workflow/appPackage/manifest.json.tpl b/templates/csharp/workflow/appPackage/manifest.json.tpl index cf2bbc13dc..84ea23d920 100644 --- a/templates/csharp/workflow/appPackage/manifest.json.tpl +++ b/templates/csharp/workflow/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/ai-assistant-bot/.vscode/tasks.json b/templates/js/ai-assistant-bot/.vscode/tasks.json index 1c3e241f27..ee29945797 100644 --- a/templates/js/ai-assistant-bot/.vscode/tasks.json +++ b/templates/js/ai-assistant-bot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/js/ai-assistant-bot/README.md.tpl b/templates/js/ai-assistant-bot/README.md.tpl index 93875180d7..4f3e0b08e1 100644 --- a/templates/js/ai-assistant-bot/README.md.tpl +++ b/templates/js/ai-assistant-bot/README.md.tpl @@ -15,7 +15,7 @@ It showcases how to build an intelligent chat bot in Teams capable of helping us > > To run the AI Assistant Bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/ai-assistant-bot/appPackage/manifest.json.tpl b/templates/js/ai-assistant-bot/appPackage/manifest.json.tpl index ea7aad4540..b8fb3bed95 100644 --- a/templates/js/ai-assistant-bot/appPackage/manifest.json.tpl +++ b/templates/js/ai-assistant-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/ai-assistant-bot/package.json.tpl b/templates/js/ai-assistant-bot/package.json.tpl index 6737aa2c62..0a727dfb48 100644 --- a/templates/js/ai-assistant-bot/package.json.tpl +++ b/templates/js/ai-assistant-bot/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Assistant Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -27,11 +27,11 @@ }, "dependencies": { "@microsoft/teams-ai": "^1.0.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/ai-assistant-bot/src/index.js b/templates/js/ai-assistant-bot/src/index.js index 07d7da5315..5896808d5c 100644 --- a/templates/js/ai-assistant-bot/src/index.js +++ b/templates/js/ai-assistant-bot/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -48,16 +48,16 @@ const onTurnErrorHandler = async (context, error) => { // Set the onTurnError for the singleton CloudAdapter. adapter.onTurnError = onTurnErrorHandler; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/ai-bot/.vscode/tasks.json b/templates/js/ai-bot/.vscode/tasks.json index 1c3e241f27..ee29945797 100644 --- a/templates/js/ai-bot/.vscode/tasks.json +++ b/templates/js/ai-bot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/js/ai-bot/README.md.tpl b/templates/js/ai-bot/README.md.tpl index 12a8158b56..9f63dc2863 100644 --- a/templates/js/ai-bot/README.md.tpl +++ b/templates/js/ai-bot/README.md.tpl @@ -17,7 +17,7 @@ The app template is built using the Teams AI library, which provides the capabil > > To run the AI Chat Bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/ai-bot/appPackage/manifest.json.tpl b/templates/js/ai-bot/appPackage/manifest.json.tpl index 5f4b526f64..3501e3282c 100644 --- a/templates/js/ai-bot/appPackage/manifest.json.tpl +++ b/templates/js/ai-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/ai-bot/package.json.tpl b/templates/js/ai-bot/package.json.tpl index 2145df80cb..47a5ecf0f9 100644 --- a/templates/js/ai-bot/package.json.tpl +++ b/templates/js/ai-bot/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Chat Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,11 +26,11 @@ }, "dependencies": { "@microsoft/teams-ai": "^1.0.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/ai-bot/src/index.js b/templates/js/ai-bot/src/index.js index 07d7da5315..5896808d5c 100644 --- a/templates/js/ai-bot/src/index.js +++ b/templates/js/ai-bot/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -48,16 +48,16 @@ const onTurnErrorHandler = async (context, error) => { // Set the onTurnError for the singleton CloudAdapter. adapter.onTurnError = onTurnErrorHandler; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/api-message-extension-sso/.tours/custom-token-validation-without-using-Easy-Auth.tour b/templates/js/api-message-extension-sso/.tours/custom-token-validation-without-using-Easy-Auth.tour new file mode 100644 index 0000000000..43f13e1f89 --- /dev/null +++ b/templates/js/api-message-extension-sso/.tours/custom-token-validation-without-using-Easy-Auth.tour @@ -0,0 +1,81 @@ +{ + "$schema": "https://aka.ms/codetour-schema", + "title": "custom-token-validation-without-using-Easy-Auth", + "steps": [ + { + "file": "src/functions/repair.js", + "selection": { + "start": { + "line": 51, + "character": 3 + }, + "end": { + "line": 51, + "character": 25 + } + }, + "description": "The reason for custom token validation is that Azure Function Core Tools do not support authentication when running locally. This template is designed to demonstrate local debugging of authentication functionalities in the API Message Extension. Therefore, this approach was taken. In production, you should leverage the authentication capabilities of Azure Functions as they are more secure and reliable.", + "title": "Introduction" + }, + { + "file": "package.json", + "selection": { + "start": { + "line": 12, + "character": 1 + }, + "end": { + "line": 14, + "character": 33 + } + }, + "description": "Added dependencies for token validation.\r\n", + "title": "Add dependencies" + }, + { + "file": "teamsapp.local.yml", + "selection": { + "start": { + "line": 9, + "character": 1 + }, + "end": { + "line": 28, + "character": 50 + } + }, + "description": "Added new action for creating a Microsoft Entra app.", + "title": "Config yaml actions" + }, + { + "file": "src/functions/repair.js", + "selection": { + "start": { + "line": 54, + "character": 1 + }, + "end": { + "line": 60, + "character": 6 + } + }, + "description": "Check if the request is authenticated. You can remove those code when deploying the project remotely because it already uses Azure's built-in authentication in production.", + "title": "Check request" + }, + { + "file": "src/functions/middleware/authMiddleware.js", + "selection": { + "start": { + "line": 27, + "character": 5 + }, + "end": { + "line": 34, + "character": 51 + } + }, + "description": "Validating tokens against specified options, including issuer, audience, scopes, roles, and allowed tenants, using a JWKS client for key retrieval and caching.", + "title": "Validate token" + } + ] +} \ No newline at end of file diff --git a/templates/js/api-message-extension-sso/.vscode/extensions.json b/templates/js/api-message-extension-sso/.vscode/extensions.json index 92a389add7..f4f7f2388a 100644 --- a/templates/js/api-message-extension-sso/.vscode/extensions.json +++ b/templates/js/api-message-extension-sso/.vscode/extensions.json @@ -1,5 +1,6 @@ { "recommendations": [ - "teamsdevapp.ms-teams-vscode-extension" + "teamsdevapp.ms-teams-vscode-extension", + "vsls-contrib.codetour" ] } \ No newline at end of file diff --git a/templates/js/api-message-extension-sso/README.md b/templates/js/api-message-extension-sso/README.md index 4c3599df70..aedefee3e4 100644 --- a/templates/js/api-message-extension-sso/README.md +++ b/templates/js/api-message-extension-sso/README.md @@ -13,7 +13,7 @@ This app template allows Teams to interact directly with third-party data, apps, > > To run this app template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -35,12 +35,17 @@ This app template allows Teams to interact directly with third-party data, apps, The following files can be customized and demonstrate an example implementation to get you started. -| File | Contents | -| -------------------------------------------- | ------------------------------------------------------------------- | -| `src/functions/repair.js` | The main file of a function in Azure Functions. | -| `src/repairsData.json` | The data source for the repair API. | -| `appPackage/apiSpecificationFile/repair.yml` | A file that describes the structure and behavior of the repair API. | -| `appPackage/responseTemplates/repair.json` | A generated Adaptive Card that used to render API response. | +| File | Contents | +| ----------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------- | +| `src/functions/repair.js` | The main file of a function in Azure Functions. | +| `src/functions/middleware/tokenCacheWrapper.js` | A wrapper class that handles caching of JWT signing keys to improve performance of token validation. | +| `src/functions/middleware/tokenValidator.js` | Core class for validating JWT tokens from Microsoft Entra, including checks for claims, scopes, roles, and tenant validation. | +| `src/functions/middleware/authMiddleware.js` | Middleware function that handles authorization using JWT tokens, integrating with the token validator. | +| `src/functions/middleware/utils.js` | Utility functions for authentication, including retrieving JWKS URIs for different cloud environments. | +| `src/functions/middleware/config.js` | Configuration file that exports Microsoft Entra app settings from environment variables. | +| `src/repairsData.json` | The data source for the repair API. | +| `appPackage/apiSpecificationFile/repair.yml` | A file that describes the structure and behavior of the repair API. | +| `appPackage/responseTemplates/repair.json` | A generated Adaptive Card that used to render API response. | The following are Teams Toolkit specific project files. You can [visit a complete guide on Github](https://github.com/OfficeDev/TeamsFx/wiki/Teams-Toolkit-Visual-Studio-Code-v5-Guide#overview) to understand how Teams Toolkit works. @@ -54,8 +59,6 @@ The following are Teams Toolkit specific project files. You can [visit a complet ![microsoft-entra-flow](https://github.com/OfficeDev/TeamsFx/assets/107838226/846e7a60-8cc1-4d8b-852e-2aec93b61fe9) -> **Note**: The Azure Active Directory (AAD) flow is only functional in remote environments. It cannot be tested in a local environment due to the lack of authentication support in Azure Function core tools. - ## Addition information and references - [Extend Teams platform with APIs](https://aka.ms/teamsfx-api-plugin) diff --git a/templates/js/api-message-extension-sso/aad.manifest.json.tpl b/templates/js/api-message-extension-sso/aad.manifest.json.tpl index ae843abc3b..b9a0822ad9 100644 --- a/templates/js/api-message-extension-sso/aad.manifest.json.tpl +++ b/templates/js/api-message-extension-sso/aad.manifest.json.tpl @@ -16,27 +16,16 @@ ], "saml2Token": [] }, - "requiredResourceAccess": [ - { - "resourceAppId": "Microsoft Graph", - "resourceAccess": [ - { - "id": "User.Read", - "type": "Scope" - } - ] - } - ], "oauth2Permissions": [ { - "adminConsentDescription": "Allows Teams to call the app's web APIs as the current user.", - "adminConsentDisplayName": "Teams can access app's web APIs", + "adminConsentDescription": "Allows Copilot to read repair records on your behalf.", + "adminConsentDisplayName": "Read repairs", "id": "${{AAD_APP_ACCESS_AS_USER_PERMISSION_ID}}", "isEnabled": true, "type": "User", - "userConsentDescription": "Enable Teams to call this app's web APIs with the same rights that you have", - "userConsentDisplayName": "Teams can access app's web APIs and make requests on your behalf", - "value": "access_as_user" + "userConsentDescription": "Allows Copilot to read repair records.", + "userConsentDisplayName": "Read repairs", + "value": "repairs_read" } ], "preAuthorizedApplications": [ diff --git a/templates/js/api-message-extension-sso/infra/azure.bicep b/templates/js/api-message-extension-sso/infra/azure.bicep index 2a07dc9a9f..981e6d4cb6 100644 --- a/templates/js/api-message-extension-sso/infra/azure.bicep +++ b/templates/js/api-message-extension-sso/infra/azure.bicep @@ -57,11 +57,11 @@ resource functionApp 'Microsoft.Web/sites@2021-02-01' = { value: '~18' // Set NodeJS version to 18.x } { - name: 'M365_CLIENT_ID' + name: 'aadAppClientId' value: aadAppClientId } { - name: 'M365_TENANT_ID' + name: 'aadAppTenantId' value: aadAppTenantId } { diff --git a/templates/js/api-message-extension-sso/package.json.tpl b/templates/js/api-message-extension-sso/package.json.tpl index b16d0c06a8..bbf779ff8f 100644 --- a/templates/js/api-message-extension-sso/package.json.tpl +++ b/templates/js/api-message-extension-sso/package.json.tpl @@ -8,7 +8,10 @@ "test": "echo \"Error: no test specified\" && exit 1" }, "dependencies": { - "@azure/functions": "^4.3.0" + "@azure/functions": "^4.3.0", + "jsonwebtoken": "^9.0.2", + "jwks-rsa": "^3.1.0", + "lru-memoizer": "^2.3.0" }, "devDependencies": { "env-cmd": "^10.1.0" diff --git a/templates/js/api-message-extension-sso/src/functions/middleware/authMiddleware.js b/templates/js/api-message-extension-sso/src/functions/middleware/authMiddleware.js new file mode 100644 index 0000000000..0a18d5fcb7 --- /dev/null +++ b/templates/js/api-message-extension-sso/src/functions/middleware/authMiddleware.js @@ -0,0 +1,44 @@ +const config = require("./config"); +const { TokenValidator } = require("./tokenValidator"); +const { getEntraJwksUri } = require("./utils"); + +/** + * Middleware function to handle authorization using JWT. + * + * @param req - The HTTP request. + * @returns A promise that resolves to a boolean value. + */ +async function authMiddleware(req) { + // Get the token from the request headers + const token = req.headers.get("authorization")?.split(" ")[1]; + if (!token) { + return false; + } + + try { + // Get the JWKS URL for the Microsoft Entra common tenant + const entraJwksUri = await getEntraJwksUri(); + + // Create a new token validator with the JWKS URL + const validator = new TokenValidator({ + jwksUri: entraJwksUri, + }); + + const options = { + allowedTenants: [config.aadAppTenantId], + audience: config.aadAppClientId, + issuer: `https://login.microsoftonline.com/${config.aadAppTenantId}/v2.0`, + scp: ["repairs_read"], + }; + // Validate the token + await validator.validateToken(token, options); + + return true; + } catch (err) { + // Handle JWT verification errors + console.error("Token is invalid:", err); + return false; + } +} + +module.exports = { authMiddleware }; diff --git a/templates/js/api-message-extension-sso/src/functions/middleware/config.js b/templates/js/api-message-extension-sso/src/functions/middleware/config.js new file mode 100644 index 0000000000..13d27183ca --- /dev/null +++ b/templates/js/api-message-extension-sso/src/functions/middleware/config.js @@ -0,0 +1,6 @@ +const config = { + aadAppClientId: process.env.aadAppClientId, + aadAppTenantId: process.env.aadAppTenantId, +}; + +module.exports = config; diff --git a/templates/js/api-message-extension-sso/src/functions/middleware/tokenCacheWrapper.js b/templates/js/api-message-extension-sso/src/functions/middleware/tokenCacheWrapper.js new file mode 100644 index 0000000000..f8f99cad4b --- /dev/null +++ b/templates/js/api-message-extension-sso/src/functions/middleware/tokenCacheWrapper.js @@ -0,0 +1,25 @@ +const createDebug = require("debug"); +const memoizer = require("lru-memoizer"); +const { callbackify, promisify } = require("util"); + +const logger = createDebug("jwt-validate"); + +// Based on https://github.com/auth0/node-jwks-rsa/blob/4fe372be935c2aa0882e0f1e58d33eead4be966d/src/wrappers/cache.js +// exposes cache to make it possible to clear cache and keys +class TokenCacheWrapper { + constructor(client, { cacheMaxEntries = 5, cacheMaxAge = 600000 } = {}) { + logger(`Configured caching of signing keys. Max: ${cacheMaxEntries} / Age: ${cacheMaxAge}`); + this.cache = memoizer({ + hash: (kid) => kid, + load: callbackify(client.getSigningKey.bind(client)), + maxAge: cacheMaxAge, + max: cacheMaxEntries, + }); + } + + getCacheWrapper() { + return promisify(this.cache); + } +} + +module.exports = { TokenCacheWrapper }; diff --git a/templates/js/api-message-extension-sso/src/functions/middleware/tokenValidator.js b/templates/js/api-message-extension-sso/src/functions/middleware/tokenValidator.js new file mode 100644 index 0000000000..1504be9fed --- /dev/null +++ b/templates/js/api-message-extension-sso/src/functions/middleware/tokenValidator.js @@ -0,0 +1,141 @@ +const jwt = require("jsonwebtoken"); +const jwksClient = require("jwks-rsa"); + +const { TokenCacheWrapper } = require("./tokenCacheWrapper.js"); + +const claimsType = Object.freeze({ + scopes: "scopes", + roles: "roles", +}); + +class TokenValidator { + constructor(options) { + if (!options) { + throw new Error("options is required"); + } + + const cache = options.cache ?? true; + + this.client = jwksClient({ + cache, + cacheMaxAge: options.cacheMaxAge ?? 24 * 60 * 60 * 1000, // 24 hours in milliseconds + jwksUri: options.jwksUri, + }); + if (cache) { + this.cacheWrapper = new TokenCacheWrapper(this.client, options); + this.client.getSigningKey = this.cacheWrapper.getCacheWrapper(); + } + } + + async validateToken(token, options) { + const decoded = jwt.decode(token, { complete: true }); + if (!decoded) { + throw new Error("jwt malformed"); + } + + // necessary to support multitenant apps + this.updateIssuer(decoded, options); + + const key = await this.getSigningKey(decoded.header.kid); + const verifiedToken = jwt.verify(token, key, options); + + if (!options) { + return verifiedToken; + } + + const validators = [ + TokenValidator.validateIdtyp, + TokenValidator.validateVer, + TokenValidator.validateScopesAndRoles, + TokenValidator.validateAllowedTenants, + ]; + validators.forEach((validator) => validator(verifiedToken, options)); + + return verifiedToken; + } + + static validateIdtyp(jwt, options) { + if (options.idtyp && options.idtyp !== jwt.idtyp) { + throw new Error(`jwt idtyp is invalid. Expected: ${options.idtyp}`); + } + } + + static validateVer(jwt, options) { + if (options.ver && options.ver !== jwt.ver) { + throw new Error(`jwt ver is invalid. Expected: ${options.ver}`); + } + } + + static validateScopesAndRoles(jwt, options) { + if (options.scp || options.roles) { + const validateClaims = (claimsFromTheToken, requiredClaims, claimsType) => { + const hasAnyRequiredClaim = requiredClaims.some((claim) => + claimsFromTheToken.includes(claim) + ); + if (!hasAnyRequiredClaim) { + throw new Error(`jwt does not contain any of the required ${claimsType}`); + } + }; + + if (options.scp && options.roles) { + if (jwt.scp) { + validateClaims(jwt.scp, options.scp, claimsType.scopes); + } else if (jwt.roles) { + validateClaims(jwt.roles, options.roles, claimsType.roles); + } + } else if (options.scp) { + validateClaims(jwt.scp ?? [], options.scp, claimsType.scopes); + } else if (options.roles) { + validateClaims(jwt.roles ?? [], options.roles, claimsType.roles); + } + } + } + + static validateAllowedTenants(jwt, options) { + if (options.allowedTenants && options.allowedTenants.length > 0) { + if (!jwt.tid || !options.allowedTenants.includes(jwt.tid)) { + throw new Error( + `jwt tid is not allowed. Allowed tenants: ${options.allowedTenants.join(", ")}` + ); + } + } + } + + clearCache() { + this.cacheWrapper?.cache.reset(); + } + + deleteKey(kid) { + this.cacheWrapper?.cache.del(kid); + } + + async getSigningKey(kid) { + const key = await this.client.getSigningKey(kid); + return key.getPublicKey(); + } + + updateIssuer(jwt, options) { + if (!options?.issuer || typeof jwt.payload !== "object" || !jwt.payload.tid) { + return; + } + + if (typeof options.issuer === "string") { + if (options.issuer.toLowerCase().indexOf("{tenantid}") > -1) { + options.issuer = options.issuer.replace(/{tenantid}/i, jwt.payload.tid); + } + return; + } + + if (Array.isArray(options.issuer)) { + options.issuer = options.issuer.map((issuer) => { + if (issuer.toLowerCase().indexOf("{tenantid}") > -1) { + return issuer.replace(/{tenantid}/i, jwt.payload.tid); + } + return issuer; + }); + return; + } + } +} + +module.exports = { TokenValidator }; diff --git a/templates/js/api-message-extension-sso/src/functions/middleware/utils.js b/templates/js/api-message-extension-sso/src/functions/middleware/utils.js new file mode 100644 index 0000000000..f23743ed7b --- /dev/null +++ b/templates/js/api-message-extension-sso/src/functions/middleware/utils.js @@ -0,0 +1,35 @@ +const CloudType = { + Public: 0, + Ppe: 1, + USGovernment: 2, + China: 3, +}; + +/** + * Retrieves the JWKS URI for the specified tenant. + * @param {string} [tenant='common'] - The tenant to retrieve the JWKS URI for. + * @param {number} [cloud=CloudType.Public] - The cloud to retrieve the JWKS URI for. + * @returns {Promise} - A promise that resolves with the JWKS URI. + */ +async function getEntraJwksUri(tenant = "common", cloud = CloudType.Public) { + let cloudUrl = ""; + switch (cloud) { + case CloudType.Public: + cloudUrl = "login.microsoftonline.com"; + break; + case CloudType.Ppe: + cloudUrl = "login.windows-ppe.net"; + break; + case CloudType.USGovernment: + cloudUrl = "login.microsoftonline.us"; + break; + case CloudType.China: + cloudUrl = "login.chinacloudapi.cn"; + break; + } + const res = await fetch(`https://${cloudUrl}/${tenant}/.well-known/openid-configuration`); + const data = await res.json(); + return data.jwks_uri; +} + +module.exports = { getEntraJwksUri, CloudType }; diff --git a/templates/js/api-message-extension-sso/src/functions/repair.js b/templates/js/api-message-extension-sso/src/functions/repair.js index ff14c11679..2c5940e99d 100644 --- a/templates/js/api-message-extension-sso/src/functions/repair.js +++ b/templates/js/api-message-extension-sso/src/functions/repair.js @@ -3,6 +3,8 @@ * complete Azure Functions developer guide. */ const { app } = require("@azure/functions"); +const { authMiddleware } = require("./middleware/authMiddleware"); + /** * This function handles the HTTP request and returns the repair information. * @@ -47,5 +49,16 @@ async function repair(req, context) { app.http("repair", { methods: ["GET"], authLevel: "anonymous", - handler: repair, + handler: async (req, context) => { + // Check if the request is authenticated + const isAuthenticated = await authMiddleware(req); + if (!isAuthenticated) { + return { + status: 401, + body: "Unauthorized", + }; + } + // Call the actual handler function + return repair(req, context); + }, }); diff --git a/templates/js/api-message-extension-sso/teamsapp.local.yml.tpl b/templates/js/api-message-extension-sso/teamsapp.local.yml.tpl index 62b46f50a6..1190079cf4 100644 --- a/templates/js/api-message-extension-sso/teamsapp.local.yml.tpl +++ b/templates/js/api-message-extension-sso/teamsapp.local.yml.tpl @@ -109,3 +109,11 @@ deploy: name: install dependencies with: args: install --no-audit + + # Generate runtime environment variables + - uses: file/createOrUpdateEnvironmentFile + with: + target: ./.localConfigs + envs: + aadAppClientId: ${{AAD_APP_CLIENT_ID}} + aadAppTenantId: ${{AAD_APP_TENANT_ID}} diff --git a/templates/js/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl b/templates/js/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl index ba4c8392f7..0508c02776 100644 --- a/templates/js/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl +++ b/templates/js/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/js/api-plugin-from-scratch-oauth/.tours/custom-token-validation-without-using-Easy-Auth.tour b/templates/js/api-plugin-from-scratch-oauth/.tours/custom-token-validation-without-using-Easy-Auth.tour new file mode 100644 index 0000000000..cc4bacc18f --- /dev/null +++ b/templates/js/api-plugin-from-scratch-oauth/.tours/custom-token-validation-without-using-Easy-Auth.tour @@ -0,0 +1,81 @@ +{ + "$schema": "https://aka.ms/codetour-schema", + "title": "custom-token-validation-without-using-Easy-Auth", + "steps": [ + { + "file": "src/functions/repairs.js", + "selection": { + "start": { + "line": 52, + "character": 3 + }, + "end": { + "line": 52, + "character": 26 + } + }, + "description": "The reason for custom token validation is that Azure Function Core Tools do not support authentication when running locally. This template is designed to demonstrate local debugging of authentication functionalities in the API Message Extension. Therefore, this approach was taken. In production, you should leverage the authentication capabilities of Azure Functions as they are more secure and reliable.", + "title": "Introduction" + }, + { + "file": "package.json", + "selection": { + "start": { + "line": 12, + "character": 9 + }, + "end": { + "line": 14, + "character": 33 + } + }, + "description": "Added dependencies for token validation.\r\n", + "title": "Add dependencies" + }, + { + "file": "teamsapp.local.yml", + "selection": { + "start": { + "line": 9, + "character": 1 + }, + "end": { + "line": 28, + "character": 50 + } + }, + "description": "Added new action for creating a Microsoft Entra app.", + "title": "Config yaml actions" + }, + { + "file": "src/functions/repairs.js", + "selection": { + "start": { + "line": 55, + "character": 1 + }, + "end": { + "line": 61, + "character": 6 + } + }, + "description": "Check if the request is authenticated. You can remove those code when deploying the project remotely because it already uses Azure's built-in authentication in production.", + "title": "Check request" + }, + { + "file": "src/functions/middleware/authMiddleware.js", + "selection": { + "start": { + "line": 27, + "character": 5 + }, + "end": { + "line": 34, + "character": 51 + } + }, + "description": "Validating tokens against specified options, including issuer, audience, scopes, roles, and allowed tenants, using a JWKS client for key retrieval and caching.", + "title": "Validate token" + } + ] +} \ No newline at end of file diff --git a/templates/js/api-plugin-from-scratch-oauth/.vscode/extensions.json b/templates/js/api-plugin-from-scratch-oauth/.vscode/extensions.json index aac0a6e347..2b65b67375 100644 --- a/templates/js/api-plugin-from-scratch-oauth/.vscode/extensions.json +++ b/templates/js/api-plugin-from-scratch-oauth/.vscode/extensions.json @@ -1,5 +1,6 @@ { "recommendations": [ - "TeamsDevApp.ms-teams-vscode-extension" + "TeamsDevApp.ms-teams-vscode-extension", + "vsls-contrib.codetour" ] } diff --git a/templates/js/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl b/templates/js/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl index 062034653d..e6586fe725 100644 --- a/templates/js/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl @@ -46,6 +46,7 @@ "access": "public", "writeToEnvironmentFile": { "endpoint": "OPENAPI_SERVER_URL", // output tunnel endpoint as OPENAPI_SERVER_URL + "domain": "OPENAPI_SERVER_DOMAIN" // output tunnel domain as OPENAPI_SERVER_DOMAIN } } ], diff --git a/templates/js/api-plugin-from-scratch-oauth/README.md.tpl b/templates/js/api-plugin-from-scratch-oauth/README.md.tpl index b9318e12fd..1433014df1 100644 --- a/templates/js/api-plugin-from-scratch-oauth/README.md.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/README.md.tpl @@ -64,17 +64,20 @@ You can extend declarative agents using plugins to retrieve data and execute tas The following files can be customized and demonstrate an example implementation to get you started. -| File | Contents | -| -------------------------------------------------- | ----------------------------------------------------------------------------------------------------- | -| `src/functions/repairs.js` | The main file of a function in Azure Functions. | -| `src/repairsData.json` | The data source for the repair API. | -| `appPackage/apiSpecificationFile/repair.dev.yml` | A file that describes the structure and behavior of the repair API. | -| `appPackage/apiSpecificationFile/repair.local.yml` | A file that describes the structure and behavior of the repair API for local execution and debugging. | -| `appPackage/manifest.json` | Teams application manifest that defines metadata for your plugin inside Microsoft Teams. | -| `appPackage/ai-plugin.dev.json` | The manifest file for your API Plugin that contains information for your API and used by LLM. | -| `appPackage/ai-plugin.local.json` | The manifest file for your API Plugin for local execution and debugging. | +| File | Contents | +| ----------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------- | +| `src/functions/repairs.js` | The main file of a function in Azure Functions. | +| `src/functions/middleware/tokenCacheWrapper.js` | A wrapper class that handles caching of JWT signing keys to improve performance of token validation. | +| `src/functions/middleware/tokenValidator.js` | Core class for validating JWT tokens from Microsoft Entra, including checks for claims, scopes, roles, and tenant validation. | +| `src/functions/middleware/authMiddleware.js` | Middleware function that handles authorization using JWT tokens, integrating with the token validator. | +| `src/functions/middleware/utils.js` | Utility functions for authentication, including retrieving JWKS URIs for different cloud environments. | +| `src/functions/middleware/config.js` | Configuration file that exports Microsoft Entra app settings from environment variables. | +| `src/repairsData.json` | The data source for the repair API. | +| `appPackage/apiSpecificationFile/repairs.yml` | A file that describes the structure and behavior of the repair API. | +| `appPackage/manifest.json` | Teams application manifest that defines metadata for your plugin inside Microsoft Teams. | +| `appPackage/ai-plugin.json` | The manifest file for your API Plugin that contains information for your API and used by LLM. | {{#DeclarativeCopilot}} -| `appPackage/repairDeclarativeAgent.json` | Define the behaviour and configurations of the declarative agent. | +| `appPackage/repairDeclarativeAgent.json` | Define the behaviour and configurations of the declarative agent. | {{/DeclarativeCopilot}} The following are Teams Toolkit specific project files. You can [visit a complete guide on Github](https://github.com/OfficeDev/TeamsFx/wiki/Teams-Toolkit-Visual-Studio-Code-v5-Guide#overview) to understand how Teams Toolkit works. @@ -89,8 +92,6 @@ The following are Teams Toolkit specific project files. You can [visit a complet ## How OAuth works in the API plugin ![oauth-flow](https://github.com/OfficeDev/teams-toolkit/assets/107838226/f074abbe-d9e3-4a46-8e08-feb66b17a539) - -> **Note**: The OAuth flow is only functional in remote environments. It cannot be tested in a local environment due to the lack of authentication support in Azure Function core tools. {{/MicrosoftEntra}} ## Addition information and references diff --git a/templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl b/templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.json.tpl similarity index 98% rename from templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl rename to templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.json.tpl index 1e73ae0853..4b4bb9c55b 100644 --- a/templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.json.tpl @@ -77,7 +77,7 @@ {{/MicrosoftEntra}} }, "spec": { - "url": "apiSpecificationFile/repair.dev.yml", + "url": "apiSpecificationFile/repair.yml", "progress_style": "ShowUsageWithInputAndOutput" }, "run_for_functions": ["listRepairs"] diff --git a/templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl b/templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl deleted file mode 100644 index ae9474d675..0000000000 --- a/templates/js/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl +++ /dev/null @@ -1,88 +0,0 @@ -{ - "$schema": "https://developer.microsoft.com/json-schemas/copilot/plugin/v2.1/schema.json", - "schema_version": "v2.1", - "namespace": "repairs", - "name_for_human": "{{appName}}${{APP_NAME_SUFFIX}}", - "description_for_human": "Track your repair records", - "description_for_model": "Plugin for searching a repair list, you can search by who's assigned to the repair.", - "functions": [ - { - "name": "listRepairs", - "description": "Returns a list of repairs with their details and images", - "capabilities": { - "response_semantics": { - "data_path": "$.results", - "properties": { - "title": "$.title", - "subtitle": "$.description", - "url": "$.image" - }, - "static_template": { - "type": "AdaptiveCard", - "$schema": "http://adaptivecards.io/schemas/adaptive-card.json", - "version": "1.5", - "body": [ - { - "type": "Container", - "$data": "${$root}", - "items": [ - { - "type": "TextBlock", - "text": "id: ${if(id, id, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "title: ${if(title, title, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "description: ${if(description, description, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "assignedTo: ${if(assignedTo, assignedTo, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "date: ${if(date, date, 'N/A')}", - "wrap": true - }, - { - "type": "Image", - "url": "${image}", - "$when": "${image != null}" - } - ] - } - ] - } - } - } - } - ], - "runtimes": [ - { - "type": "OpenApi", - "auth": { - "type": "None" - }, - "spec": { - "url": "apiSpecificationFile/repair.local.yml", - "progress_style": "ShowUsageWithInputAndOutput" - }, - "run_for_functions": ["listRepairs"] - } - ], - "capabilities": { - "localization": {}, - "conversation_starters": [ - { - "text": "List all repairs" - } - ] - } -} diff --git a/templates/js/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.local.yml b/templates/js/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.local.yml deleted file mode 100644 index 81c0f25839..0000000000 --- a/templates/js/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.local.yml +++ /dev/null @@ -1,55 +0,0 @@ -openapi: 3.0.0 -info: - title: Repair Service - description: A simple service to manage repairs - version: 1.0.0 -servers: - - url: ${{OPENAPI_SERVER_URL}}/api - description: The repair api server - -paths: - /repairs: - get: - operationId: listRepairs - summary: List all repairs - description: Returns a list of repairs with their details and images - parameters: - - name: assignedTo - in: query - description: Filter repairs by who they're assigned to - schema: - type: string - required: false - responses: - '200': - description: A list of repairs - content: - application/json: - schema: - type: object - properties: - results: - type: array - items: - type: object - properties: - id: - type: string - description: The unique identifier of the repair - title: - type: string - description: The short summary of the repair - description: - type: string - description: The detailed description of the repair - assignedTo: - type: string - description: The user who is responsible for the repair - date: - type: string - format: date-time - description: The date and time when the repair is scheduled or completed - image: - type: string - format: uri - description: The URL of the image of the item to be repaired or the repair process \ No newline at end of file diff --git a/templates/js/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.dev.yml.tpl b/templates/js/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.yml.tpl similarity index 100% rename from templates/js/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.dev.yml.tpl rename to templates/js/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.yml.tpl diff --git a/templates/js/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl b/templates/js/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl index 92cd70722c..5992d3592d 100644 --- a/templates/js/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl @@ -27,7 +27,7 @@ "plugins": [ { "id": "plugin_1", - "file": "ai-plugin.${{TEAMSFX_ENV}}.json" + "file": "ai-plugin.json" } ] {{/DeclarativeCopilot}} diff --git a/templates/js/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl b/templates/js/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl index 7453556968..a52919b2cd 100644 --- a/templates/js/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl @@ -17,7 +17,7 @@ "actions": [ { "id": "repairPlugin", - "file": "ai-plugin.${{TEAMSFX_ENV}}.json" + "file": "ai-plugin.json" } ] } \ No newline at end of file diff --git a/templates/js/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl b/templates/js/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl index b38273f91a..bb1e0dc172 100644 --- a/templates/js/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl @@ -45,6 +45,14 @@ resource functionApp 'Microsoft.Web/sites@2021-02-01' = { name: 'WEBSITE_NODE_DEFAULT_VERSION' value: '~18' // Set NodeJS version to 18.x } + { + name: 'aadAppClientId' + value: aadAppClientId + } + { + name: 'aadAppTenantId' + value: aadAppTenantId + } ] ftpsState: 'FtpsOnly' } diff --git a/templates/js/api-plugin-from-scratch-oauth/package.json.tpl b/templates/js/api-plugin-from-scratch-oauth/package.json.tpl index b16d0c06a8..bbf779ff8f 100644 --- a/templates/js/api-plugin-from-scratch-oauth/package.json.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/package.json.tpl @@ -8,7 +8,10 @@ "test": "echo \"Error: no test specified\" && exit 1" }, "dependencies": { - "@azure/functions": "^4.3.0" + "@azure/functions": "^4.3.0", + "jsonwebtoken": "^9.0.2", + "jwks-rsa": "^3.1.0", + "lru-memoizer": "^2.3.0" }, "devDependencies": { "env-cmd": "^10.1.0" diff --git a/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/authMiddleware.js b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/authMiddleware.js new file mode 100644 index 0000000000..0a18d5fcb7 --- /dev/null +++ b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/authMiddleware.js @@ -0,0 +1,44 @@ +const config = require("./config"); +const { TokenValidator } = require("./tokenValidator"); +const { getEntraJwksUri } = require("./utils"); + +/** + * Middleware function to handle authorization using JWT. + * + * @param req - The HTTP request. + * @returns A promise that resolves to a boolean value. + */ +async function authMiddleware(req) { + // Get the token from the request headers + const token = req.headers.get("authorization")?.split(" ")[1]; + if (!token) { + return false; + } + + try { + // Get the JWKS URL for the Microsoft Entra common tenant + const entraJwksUri = await getEntraJwksUri(); + + // Create a new token validator with the JWKS URL + const validator = new TokenValidator({ + jwksUri: entraJwksUri, + }); + + const options = { + allowedTenants: [config.aadAppTenantId], + audience: config.aadAppClientId, + issuer: `https://login.microsoftonline.com/${config.aadAppTenantId}/v2.0`, + scp: ["repairs_read"], + }; + // Validate the token + await validator.validateToken(token, options); + + return true; + } catch (err) { + // Handle JWT verification errors + console.error("Token is invalid:", err); + return false; + } +} + +module.exports = { authMiddleware }; diff --git a/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/config.js b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/config.js new file mode 100644 index 0000000000..13d27183ca --- /dev/null +++ b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/config.js @@ -0,0 +1,6 @@ +const config = { + aadAppClientId: process.env.aadAppClientId, + aadAppTenantId: process.env.aadAppTenantId, +}; + +module.exports = config; diff --git a/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/tokenCacheWrapper.js b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/tokenCacheWrapper.js new file mode 100644 index 0000000000..f8f99cad4b --- /dev/null +++ b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/tokenCacheWrapper.js @@ -0,0 +1,25 @@ +const createDebug = require("debug"); +const memoizer = require("lru-memoizer"); +const { callbackify, promisify } = require("util"); + +const logger = createDebug("jwt-validate"); + +// Based on https://github.com/auth0/node-jwks-rsa/blob/4fe372be935c2aa0882e0f1e58d33eead4be966d/src/wrappers/cache.js +// exposes cache to make it possible to clear cache and keys +class TokenCacheWrapper { + constructor(client, { cacheMaxEntries = 5, cacheMaxAge = 600000 } = {}) { + logger(`Configured caching of signing keys. Max: ${cacheMaxEntries} / Age: ${cacheMaxAge}`); + this.cache = memoizer({ + hash: (kid) => kid, + load: callbackify(client.getSigningKey.bind(client)), + maxAge: cacheMaxAge, + max: cacheMaxEntries, + }); + } + + getCacheWrapper() { + return promisify(this.cache); + } +} + +module.exports = { TokenCacheWrapper }; diff --git a/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/tokenValidator.js b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/tokenValidator.js new file mode 100644 index 0000000000..1504be9fed --- /dev/null +++ b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/tokenValidator.js @@ -0,0 +1,141 @@ +const jwt = require("jsonwebtoken"); +const jwksClient = require("jwks-rsa"); + +const { TokenCacheWrapper } = require("./tokenCacheWrapper.js"); + +const claimsType = Object.freeze({ + scopes: "scopes", + roles: "roles", +}); + +class TokenValidator { + constructor(options) { + if (!options) { + throw new Error("options is required"); + } + + const cache = options.cache ?? true; + + this.client = jwksClient({ + cache, + cacheMaxAge: options.cacheMaxAge ?? 24 * 60 * 60 * 1000, // 24 hours in milliseconds + jwksUri: options.jwksUri, + }); + if (cache) { + this.cacheWrapper = new TokenCacheWrapper(this.client, options); + this.client.getSigningKey = this.cacheWrapper.getCacheWrapper(); + } + } + + async validateToken(token, options) { + const decoded = jwt.decode(token, { complete: true }); + if (!decoded) { + throw new Error("jwt malformed"); + } + + // necessary to support multitenant apps + this.updateIssuer(decoded, options); + + const key = await this.getSigningKey(decoded.header.kid); + const verifiedToken = jwt.verify(token, key, options); + + if (!options) { + return verifiedToken; + } + + const validators = [ + TokenValidator.validateIdtyp, + TokenValidator.validateVer, + TokenValidator.validateScopesAndRoles, + TokenValidator.validateAllowedTenants, + ]; + validators.forEach((validator) => validator(verifiedToken, options)); + + return verifiedToken; + } + + static validateIdtyp(jwt, options) { + if (options.idtyp && options.idtyp !== jwt.idtyp) { + throw new Error(`jwt idtyp is invalid. Expected: ${options.idtyp}`); + } + } + + static validateVer(jwt, options) { + if (options.ver && options.ver !== jwt.ver) { + throw new Error(`jwt ver is invalid. Expected: ${options.ver}`); + } + } + + static validateScopesAndRoles(jwt, options) { + if (options.scp || options.roles) { + const validateClaims = (claimsFromTheToken, requiredClaims, claimsType) => { + const hasAnyRequiredClaim = requiredClaims.some((claim) => + claimsFromTheToken.includes(claim) + ); + if (!hasAnyRequiredClaim) { + throw new Error(`jwt does not contain any of the required ${claimsType}`); + } + }; + + if (options.scp && options.roles) { + if (jwt.scp) { + validateClaims(jwt.scp, options.scp, claimsType.scopes); + } else if (jwt.roles) { + validateClaims(jwt.roles, options.roles, claimsType.roles); + } + } else if (options.scp) { + validateClaims(jwt.scp ?? [], options.scp, claimsType.scopes); + } else if (options.roles) { + validateClaims(jwt.roles ?? [], options.roles, claimsType.roles); + } + } + } + + static validateAllowedTenants(jwt, options) { + if (options.allowedTenants && options.allowedTenants.length > 0) { + if (!jwt.tid || !options.allowedTenants.includes(jwt.tid)) { + throw new Error( + `jwt tid is not allowed. Allowed tenants: ${options.allowedTenants.join(", ")}` + ); + } + } + } + + clearCache() { + this.cacheWrapper?.cache.reset(); + } + + deleteKey(kid) { + this.cacheWrapper?.cache.del(kid); + } + + async getSigningKey(kid) { + const key = await this.client.getSigningKey(kid); + return key.getPublicKey(); + } + + updateIssuer(jwt, options) { + if (!options?.issuer || typeof jwt.payload !== "object" || !jwt.payload.tid) { + return; + } + + if (typeof options.issuer === "string") { + if (options.issuer.toLowerCase().indexOf("{tenantid}") > -1) { + options.issuer = options.issuer.replace(/{tenantid}/i, jwt.payload.tid); + } + return; + } + + if (Array.isArray(options.issuer)) { + options.issuer = options.issuer.map((issuer) => { + if (issuer.toLowerCase().indexOf("{tenantid}") > -1) { + return issuer.replace(/{tenantid}/i, jwt.payload.tid); + } + return issuer; + }); + return; + } + } +} + +module.exports = { TokenValidator }; diff --git a/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/utils.js b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/utils.js new file mode 100644 index 0000000000..f23743ed7b --- /dev/null +++ b/templates/js/api-plugin-from-scratch-oauth/src/functions/middleware/utils.js @@ -0,0 +1,35 @@ +const CloudType = { + Public: 0, + Ppe: 1, + USGovernment: 2, + China: 3, +}; + +/** + * Retrieves the JWKS URI for the specified tenant. + * @param {string} [tenant='common'] - The tenant to retrieve the JWKS URI for. + * @param {number} [cloud=CloudType.Public] - The cloud to retrieve the JWKS URI for. + * @returns {Promise} - A promise that resolves with the JWKS URI. + */ +async function getEntraJwksUri(tenant = "common", cloud = CloudType.Public) { + let cloudUrl = ""; + switch (cloud) { + case CloudType.Public: + cloudUrl = "login.microsoftonline.com"; + break; + case CloudType.Ppe: + cloudUrl = "login.windows-ppe.net"; + break; + case CloudType.USGovernment: + cloudUrl = "login.microsoftonline.us"; + break; + case CloudType.China: + cloudUrl = "login.chinacloudapi.cn"; + break; + } + const res = await fetch(`https://${cloudUrl}/${tenant}/.well-known/openid-configuration`); + const data = await res.json(); + return data.jwks_uri; +} + +module.exports = { getEntraJwksUri, CloudType }; diff --git a/templates/js/api-plugin-from-scratch-oauth/src/functions/repairs.js b/templates/js/api-plugin-from-scratch-oauth/src/functions/repairs.js index 00279139f3..680e0d0de4 100644 --- a/templates/js/api-plugin-from-scratch-oauth/src/functions/repairs.js +++ b/templates/js/api-plugin-from-scratch-oauth/src/functions/repairs.js @@ -3,6 +3,8 @@ * complete Azure Functions developer guide. */ const { app } = require("@azure/functions"); +const { authMiddleware } = require("./middleware/authMiddleware"); + /** * This function handles the HTTP request and returns the repair information. * @@ -48,5 +50,16 @@ async function repairs(req, context) { app.http("repairs", { methods: ["GET"], authLevel: "anonymous", - handler: repairs, + handler: async (req, context) => { + // Check if the request is authenticated + const isAuthenticated = await authMiddleware(req); + if (!isAuthenticated) { + return { + status: 401, + body: "Unauthorized", + }; + } + // Call the actual handler function + return repairs(req, context); + }, }); diff --git a/templates/js/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl b/templates/js/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl index 7b73365d09..172608fa79 100644 --- a/templates/js/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl @@ -4,6 +4,39 @@ version: v1.7 provision: + # Creates a new Microsoft Entra app to authenticate users if + # the environment variable that stores clientId is empty + - uses: aadApp/create + with: + # Note: when you run aadApp/update, the Microsoft Entra app name will be updated + # based on the definition in manifest. If you don't want to change the + # name, make sure the name in Microsoft Entra manifest is the same with the name + # defined here. + name: {{appName}}-aad + # If the value is false, the action will not generate client secret for you +{{#MicrosoftEntra}} + generateClientSecret: false +{{/MicrosoftEntra}} +{{^MicrosoftEntra}} + generateClientSecret: true +{{/MicrosoftEntra}} + # Authenticate users with a Microsoft work or school account in your + # organization's Microsoft Entra tenant (for example, single tenant). + signInAudience: AzureADMyOrg + # Write the information of created resources into environment file for the + # specified environment variable(s). + writeToEnvironmentFile: + clientId: AAD_APP_CLIENT_ID + # Environment variable that starts with `SECRET_` will be stored to the + # .env.{envName}.user environment file +{{^MicrosoftEntra}} + clientSecret: SECRET_AAD_APP_CLIENT_SECRET +{{/MicrosoftEntra}} + objectId: AAD_APP_OBJECT_ID + tenantId: AAD_APP_TENANT_ID + authority: AAD_APP_OAUTH_AUTHORITY + authorityHost: AAD_APP_OAUTH_AUTHORITY_HOST + # Creates a Teams app - uses: teamsApp/create with: @@ -21,6 +54,57 @@ provision: echo "::set-teamsfx-env FUNC_NAME=repair"; echo "::set-teamsfx-env FUNC_ENDPOINT=http://localhost:7071"; + # Apply the Microsoft Entra manifest to an existing Microsoft Entra app. Will use the object id in + # manifest file to determine which Microsoft Entra app to update. + - uses: aadApp/update + with: + # Relative path to this file. Environment variables in manifest will + # be replaced before apply to Microsoft Entra app + manifestPath: ./aad.manifest.json + outputFilePath: ./build/aad.manifest.${{TEAMSFX_ENV}}.json + + - uses: oauth/register + with: +{{#MicrosoftEntra}} + name: aadAuthCode + flow: authorizationCode + appId: ${{TEAMS_APP_ID}} + clientId: ${{AAD_APP_CLIENT_ID}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + identityProvider: MicrosoftEntra + writeToEnvironmentFile: + configurationId: AADAUTHCODE_CONFIGURATION_ID +{{/MicrosoftEntra}} +{{^MicrosoftEntra}} + name: oAuth2AuthCode + flow: authorizationCode + appId: ${{TEAMS_APP_ID}} + clientId: ${{AAD_APP_CLIENT_ID}} + clientSecret: ${{SECRET_AAD_APP_CLIENT_SECRET}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + writeToEnvironmentFile: + configurationId: OAUTH2AUTHCODE_CONFIGURATION_ID +{{/MicrosoftEntra}} + + - uses: oauth/update + with: +{{#MicrosoftEntra}} + name: aadAuthCode + appId: ${{TEAMS_APP_ID}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + configurationId: ${{AADAUTHCODE_CONFIGURATION_ID}} +{{/MicrosoftEntra}} +{{^MicrosoftEntra}} + name: oAuth2AuthCode + appId: ${{TEAMS_APP_ID}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + configurationId: ${{OAUTH2AUTHCODE_CONFIGURATION_ID}} +{{/MicrosoftEntra}} + # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -71,3 +155,11 @@ deploy: name: install dependencies with: args: install --no-audit + + # Generate runtime environment variables + - uses: file/createOrUpdateEnvironmentFile + with: + target: ./.localConfigs + envs: + aadAppClientId: ${{AAD_APP_CLIENT_ID}} + aadAppTenantId: ${{AAD_APP_TENANT_ID}} diff --git a/templates/js/api-plugin-from-scratch-oauth/teamsapp.yml.tpl b/templates/js/api-plugin-from-scratch-oauth/teamsapp.yml.tpl index b0bc5ff3e9..4dc6b52475 100644 --- a/templates/js/api-plugin-from-scratch-oauth/teamsapp.yml.tpl +++ b/templates/js/api-plugin-from-scratch-oauth/teamsapp.yml.tpl @@ -92,7 +92,7 @@ provision: appId: ${{TEAMS_APP_ID}} clientId: ${{AAD_APP_CLIENT_ID}} # Path to OpenAPI description document - apiSpecPath: ./appPackage/apiSpecificationFile/repair.${{TEAMSFX_ENV}}.yml + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml identityProvider: MicrosoftEntra writeToEnvironmentFile: configurationId: AADAUTHCODE_CONFIGURATION_ID @@ -104,7 +104,7 @@ provision: clientId: ${{AAD_APP_CLIENT_ID}} clientSecret: ${{SECRET_AAD_APP_CLIENT_SECRET}} # Path to OpenAPI description document - apiSpecPath: ./appPackage/apiSpecificationFile/repair.${{TEAMSFX_ENV}}.yml + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml writeToEnvironmentFile: configurationId: OAUTH2AUTHCODE_CONFIGURATION_ID {{/MicrosoftEntra}} diff --git a/templates/js/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl b/templates/js/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl index 68c0e9d958..f21d2fc7f5 100644 --- a/templates/js/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl +++ b/templates/js/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/js/command-and-response/.vscode/tasks.json b/templates/js/command-and-response/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/command-and-response/.vscode/tasks.json +++ b/templates/js/command-and-response/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/command-and-response/README.md.tpl b/templates/js/command-and-response/README.md.tpl index bc1cd3e7b8..cb33ea895d 100644 --- a/templates/js/command-and-response/README.md.tpl +++ b/templates/js/command-and-response/README.md.tpl @@ -10,7 +10,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the command bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} @@ -60,7 +60,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | - | - | -| `src/index.js` | Application entry point and `restify` handlers for command and response | +| `src/index.js` | Application entry point and `express` handlers for command and response | | `src/teamsBot.js` | An empty teams activity handler for bot customization | | `src/adaptiveCards/helloworldCommand.json` | A generated Adaptive Card that is sent to Teams | | `src/helloworldCommandHandler.js` | The business logic to handle a command | diff --git a/templates/js/command-and-response/appPackage/manifest.json.tpl b/templates/js/command-and-response/appPackage/manifest.json.tpl index cf2bbc13dc..84ea23d920 100644 --- a/templates/js/command-and-response/appPackage/manifest.json.tpl +++ b/templates/js/command-and-response/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/command-and-response/package.json.tpl b/templates/js/command-and-response/package.json.tpl index 57aebc7313..89c7c29459 100644 --- a/templates/js/command-and-response/package.json.tpl +++ b/templates/js/command-and-response/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Command and Response Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,13 +23,13 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/command-and-response/src/helloworldCommandHandler.js b/templates/js/command-and-response/src/helloworldCommandHandler.js index 6ca574b31d..2666725027 100644 --- a/templates/js/command-and-response/src/helloworldCommandHandler.js +++ b/templates/js/command-and-response/src/helloworldCommandHandler.js @@ -10,14 +10,12 @@ class HelloWorldCommandHandler { console.log(`App received message: ${message.text}`); // do something to process your command and return message activity as the response - - // render your adaptive card for reply message - const cardData = { - title: "Your Hello World App is Running", - body: "Congratulations! Your Hello World App is running. Open the documentation below to learn more about how to build applications with the Teams Toolkit.", - }; - - const cardJson = new ACData.Template(helloWorldCard).expand({ $root: cardData }); + const cardJson = new ACData.Template(helloWorldCard).expand({ + $root: { + title: "Your Hello World App is Running", + body: "Congratulations! Your Hello World App is running. Open the documentation below to learn more about how to build applications with the Teams Toolkit.", + }, + }); return MessageFactory.attachment(CardFactory.adaptiveCard(cardJson)); } } diff --git a/templates/js/command-and-response/src/index.js b/templates/js/command-and-response/src/index.js index 12ea9234cd..2aac1665fa 100644 --- a/templates/js/command-and-response/src/index.js +++ b/templates/js/command-and-response/src/index.js @@ -1,24 +1,25 @@ // Create HTTP server. -const restify = require("restify"); +const express = require("express"); const { commandApp } = require("./internal/initialize"); const { TeamsBot } = require("./teamsBot"); -// This template uses `restify` to serve HTTP responses. -// Create a restify server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nApp Started, ${server.name} listening to ${server.url}`); +// This template uses `express` to serve HTTP responses. +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Register an API endpoint with `restify`. Teams sends messages to your application +// Register an API endpoint with `express`. Teams sends messages to your application // through this endpoint. // // The Teams Toolkit bot registration configures the bot with `/api/messages` as the // Bot Framework endpoint. If you customize this route, update the Bot registration // in `templates/azure/provision/botservice.bicep`. const teamsBot = new TeamsBot(); -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await commandApp.requestHandler(req, res, async (context) => { await teamsBot.run(context); }); diff --git a/templates/js/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl b/templates/js/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl index 71bbc4d363..892ff8b82d 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl +++ b/templates/js/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/js/custom-copilot-assistant-assistants-api/.vscode/tasks.json b/templates/js/custom-copilot-assistant-assistants-api/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/.vscode/tasks.json +++ b/templates/js/custom-copilot-assistant-assistants-api/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/custom-copilot-assistant-assistants-api/README.md.tpl b/templates/js/custom-copilot-assistant-assistants-api/README.md.tpl index ea79d5ac57..7f2c40a7ef 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/README.md.tpl +++ b/templates/js/custom-copilot-assistant-assistants-api/README.md.tpl @@ -9,7 +9,7 @@ It showcases how to build an AI agent in Teams capable of helping users accompli > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl b/templates/js/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl index 68ec52c46e..cb1279f2c0 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl +++ b/templates/js/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/js/custom-copilot-assistant-assistants-api/package.json.tpl b/templates/js/custom-copilot-assistant-assistants-api/package.json.tpl index d32337d813..694b365e7c 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/package.json.tpl +++ b/templates/js/custom-copilot-assistant-assistants-api/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Assistant Bot sample with OpenAI Assistants API and Teams AI Library's built-in coordination", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,12 +26,12 @@ "url": "https://github.com" }, "dependencies": { - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/custom-copilot-assistant-assistants-api/src/index.js b/templates/js/custom-copilot-assistant-assistants-api/src/index.js index d1e686f00d..7f7ba3b9ad 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/src/index.js +++ b/templates/js/custom-copilot-assistant-assistants-api/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // This bot's adapter const adapter = require("./adapter"); @@ -7,16 +7,16 @@ const adapter = require("./adapter"); // This bot's main dialog. const app = require("./app/app"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl b/templates/js/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl index eab3d7b2d8..68d95a09e9 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl +++ b/templates/js/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/js/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl b/templates/js/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl index 435dd9ae91..26a05e3127 100644 --- a/templates/js/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl +++ b/templates/js/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/js/custom-copilot-assistant-new/.vscode/launch.json.tpl b/templates/js/custom-copilot-assistant-new/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/js/custom-copilot-assistant-new/.vscode/launch.json.tpl +++ b/templates/js/custom-copilot-assistant-new/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/js/custom-copilot-assistant-new/.vscode/tasks.json b/templates/js/custom-copilot-assistant-new/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/custom-copilot-assistant-new/.vscode/tasks.json +++ b/templates/js/custom-copilot-assistant-new/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/custom-copilot-assistant-new/README.md.tpl b/templates/js/custom-copilot-assistant-new/README.md.tpl index 1a460f0e0c..62592789a7 100644 --- a/templates/js/custom-copilot-assistant-new/README.md.tpl +++ b/templates/js/custom-copilot-assistant-new/README.md.tpl @@ -9,7 +9,7 @@ It showcases how to build an AI agent in Teams capable of chatting with users an > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/custom-copilot-assistant-new/appPackage/manifest.json.tpl b/templates/js/custom-copilot-assistant-new/appPackage/manifest.json.tpl index 4ab88823d5..296ef1734f 100644 --- a/templates/js/custom-copilot-assistant-new/appPackage/manifest.json.tpl +++ b/templates/js/custom-copilot-assistant-new/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/js/custom-copilot-assistant-new/package.json.tpl b/templates/js/custom-copilot-assistant-new/package.json.tpl index e13aeda8a5..e17959015e 100644 --- a/templates/js/custom-copilot-assistant-new/package.json.tpl +++ b/templates/js/custom-copilot-assistant-new/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Assistant Bot Sample with Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,12 +26,12 @@ "url": "https://github.com" }, "dependencies": { - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/custom-copilot-assistant-new/src/app/app.js.tpl b/templates/js/custom-copilot-assistant-new/src/app/app.js.tpl index bbd372771d..76e3b74f4b 100644 --- a/templates/js/custom-copilot-assistant-new/src/app/app.js.tpl +++ b/templates/js/custom-copilot-assistant-new/src/app/app.js.tpl @@ -22,6 +22,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/js/custom-copilot-assistant-new/src/index.js b/templates/js/custom-copilot-assistant-new/src/index.js index d1e686f00d..7f7ba3b9ad 100644 --- a/templates/js/custom-copilot-assistant-new/src/index.js +++ b/templates/js/custom-copilot-assistant-new/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // This bot's adapter const adapter = require("./adapter"); @@ -7,16 +7,16 @@ const adapter = require("./adapter"); // This bot's main dialog. const app = require("./app/app"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/custom-copilot-assistant-new/teamsapp.local.yml.tpl b/templates/js/custom-copilot-assistant-new/teamsapp.local.yml.tpl index 2c7fb58640..25cd75b5df 100644 --- a/templates/js/custom-copilot-assistant-new/teamsapp.local.yml.tpl +++ b/templates/js/custom-copilot-assistant-new/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/js/custom-copilot-assistant-new/teamsapp.yml.tpl b/templates/js/custom-copilot-assistant-new/teamsapp.yml.tpl index 435dd9ae91..26a05e3127 100644 --- a/templates/js/custom-copilot-assistant-new/teamsapp.yml.tpl +++ b/templates/js/custom-copilot-assistant-new/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/js/custom-copilot-basic/.vscode/launch.json.tpl b/templates/js/custom-copilot-basic/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/js/custom-copilot-basic/.vscode/launch.json.tpl +++ b/templates/js/custom-copilot-basic/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/js/custom-copilot-basic/.vscode/tasks.json b/templates/js/custom-copilot-basic/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/custom-copilot-basic/.vscode/tasks.json +++ b/templates/js/custom-copilot-basic/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/custom-copilot-basic/README.md.tpl b/templates/js/custom-copilot-basic/README.md.tpl index d5444fe502..ff69e8b237 100644 --- a/templates/js/custom-copilot-basic/README.md.tpl +++ b/templates/js/custom-copilot-basic/README.md.tpl @@ -9,7 +9,7 @@ It showcases a bot app that responds to user questions like ChatGPT, which enabl > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18. +> - [Node.js](https://nodejs.org/), supported versions: 18, 20. {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts). {{/enableTestToolByDefault}} diff --git a/templates/js/custom-copilot-basic/appPackage/manifest.json.tpl b/templates/js/custom-copilot-basic/appPackage/manifest.json.tpl index 3c0393e329..8caabac564 100644 --- a/templates/js/custom-copilot-basic/appPackage/manifest.json.tpl +++ b/templates/js/custom-copilot-basic/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", @@ -40,7 +57,7 @@ "commands": [ { "title": "How can you help me?", - "description": "A sample prompt" + "description": "How can you help me?" }, { "title": "How to develop TeamsToolkit app?", diff --git a/templates/js/custom-copilot-basic/package.json.tpl b/templates/js/custom-copilot-basic/package.json.tpl index b7dd716f7b..4ac7b4143a 100644 --- a/templates/js/custom-copilot-basic/package.json.tpl +++ b/templates/js/custom-copilot-basic/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Chat Bot Sample with Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -25,12 +25,12 @@ "url": "https://github.com" }, "dependencies": { - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/custom-copilot-basic/src/app/app.js.tpl b/templates/js/custom-copilot-basic/src/app/app.js.tpl index 3e1eb18294..6dfecfb866 100644 --- a/templates/js/custom-copilot-basic/src/app/app.js.tpl +++ b/templates/js/custom-copilot-basic/src/app/app.js.tpl @@ -19,6 +19,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/js/custom-copilot-basic/src/index.js b/templates/js/custom-copilot-basic/src/index.js index d1e686f00d..7f7ba3b9ad 100644 --- a/templates/js/custom-copilot-basic/src/index.js +++ b/templates/js/custom-copilot-basic/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // This bot's adapter const adapter = require("./adapter"); @@ -7,16 +7,16 @@ const adapter = require("./adapter"); // This bot's main dialog. const app = require("./app/app"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/custom-copilot-basic/teamsapp.local.yml.tpl b/templates/js/custom-copilot-basic/teamsapp.local.yml.tpl index 2c7fb58640..25cd75b5df 100644 --- a/templates/js/custom-copilot-basic/teamsapp.local.yml.tpl +++ b/templates/js/custom-copilot-basic/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/js/custom-copilot-basic/teamsapp.yml.tpl b/templates/js/custom-copilot-basic/teamsapp.yml.tpl index 435dd9ae91..26a05e3127 100644 --- a/templates/js/custom-copilot-basic/teamsapp.yml.tpl +++ b/templates/js/custom-copilot-basic/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/js/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl b/templates/js/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl +++ b/templates/js/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/js/custom-copilot-rag-azure-ai-search/.vscode/tasks.json b/templates/js/custom-copilot-rag-azure-ai-search/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/.vscode/tasks.json +++ b/templates/js/custom-copilot-rag-azure-ai-search/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/custom-copilot-rag-azure-ai-search/README.md.tpl b/templates/js/custom-copilot-rag-azure-ai-search/README.md.tpl index e9ea00a224..2503088205 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/README.md.tpl +++ b/templates/js/custom-copilot-rag-azure-ai-search/README.md.tpl @@ -12,7 +12,7 @@ This app template also demonstrates usage of techniques like: > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) {{#useOpenAI}} > - An account with [OpenAI](https://platform.openai.com/) and [Azure AI Search](https://azure.microsoft.com/en-us/products/ai-services/ai-search). diff --git a/templates/js/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl b/templates/js/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl index d9463cdd88..b37d09e04a 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl +++ b/templates/js/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/js/custom-copilot-rag-azure-ai-search/package.json.tpl b/templates/js/custom-copilot-rag-azure-ai-search/package.json.tpl index d73deb7d08..00d05c4627 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/package.json.tpl +++ b/templates/js/custom-copilot-rag-azure-ai-search/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit RAG Bot Sample with Azure AI Search and Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -28,12 +28,12 @@ }, "dependencies": { "@azure/search-documents": "^12.0.0", - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/custom-copilot-rag-azure-ai-search/src/app/app.js.tpl b/templates/js/custom-copilot-rag-azure-ai-search/src/app/app.js.tpl index 8ac268ffe8..634519a687 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/src/app/app.js.tpl +++ b/templates/js/custom-copilot-rag-azure-ai-search/src/app/app.js.tpl @@ -21,6 +21,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/js/custom-copilot-rag-azure-ai-search/src/index.js b/templates/js/custom-copilot-rag-azure-ai-search/src/index.js index d1e686f00d..7f7ba3b9ad 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/src/index.js +++ b/templates/js/custom-copilot-rag-azure-ai-search/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // This bot's adapter const adapter = require("./adapter"); @@ -7,16 +7,16 @@ const adapter = require("./adapter"); // This bot's main dialog. const app = require("./app/app"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl b/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl index b688445ca3..77ed1fa8a5 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl +++ b/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl b/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl index 435dd9ae91..26a05e3127 100644 --- a/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl +++ b/templates/js/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/js/custom-copilot-rag-custom-api/.vscode/tasks.json b/templates/js/custom-copilot-rag-custom-api/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/custom-copilot-rag-custom-api/.vscode/tasks.json +++ b/templates/js/custom-copilot-rag-custom-api/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/custom-copilot-rag-custom-api/README.md.tpl b/templates/js/custom-copilot-rag-custom-api/README.md.tpl index 96a6a1158c..ef228be6e6 100644 --- a/templates/js/custom-copilot-rag-custom-api/README.md.tpl +++ b/templates/js/custom-copilot-rag-custom-api/README.md.tpl @@ -9,7 +9,7 @@ The app template is built using the Teams AI library, which provides the capabil > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl b/templates/js/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl index d9463cdd88..0110a27ecc 100644 --- a/templates/js/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl +++ b/templates/js/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/custom-copilot-rag-custom-api/package.json.tpl b/templates/js/custom-copilot-rag-custom-api/package.json.tpl index a91ab100c0..d5cd3c38eb 100644 --- a/templates/js/custom-copilot-rag-custom-api/package.json.tpl +++ b/templates/js/custom-copilot-rag-custom-api/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Chat Bot Sample with Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,8 +26,8 @@ }, "dependencies": { "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0", + "botbuilder": "^4.23.1", + "express": "^5.0.1", "fs-extra": "^11.2.0", "js-yaml": "^4.1.0", "adaptivecards-templating": "^2.3.1", @@ -35,6 +35,6 @@ }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/custom-copilot-rag-custom-api/src/app/utility.js b/templates/js/custom-copilot-rag-custom-api/src/app/utility.js index 74b79ba94d..b92fb7d3ff 100644 --- a/templates/js/custom-copilot-rag-custom-api/src/app/utility.js +++ b/templates/js/custom-copilot-rag-custom-api/src/app/utility.js @@ -1,9 +1,6 @@ const { CardFactory } = require("botbuilder"); const ACData = require("adaptivecards-templating"); function generateAdaptiveCard(templatePath, result) { - if (!result || !result.data) { - throw new Error("Get empty result from api call."); - } const adaptiveCardTemplate = require(templatePath); const template = new ACData.Template(adaptiveCardTemplate); const cardContent = template.expand({ diff --git a/templates/js/custom-copilot-rag-custom-api/src/index.js b/templates/js/custom-copilot-rag-custom-api/src/index.js index d1e686f00d..7f7ba3b9ad 100644 --- a/templates/js/custom-copilot-rag-custom-api/src/index.js +++ b/templates/js/custom-copilot-rag-custom-api/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // This bot's adapter const adapter = require("./adapter"); @@ -7,16 +7,16 @@ const adapter = require("./adapter"); // This bot's main dialog. const app = require("./app/app"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/custom-copilot-rag-customize/.vscode/launch.json.tpl b/templates/js/custom-copilot-rag-customize/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/js/custom-copilot-rag-customize/.vscode/launch.json.tpl +++ b/templates/js/custom-copilot-rag-customize/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/js/custom-copilot-rag-customize/.vscode/tasks.json b/templates/js/custom-copilot-rag-customize/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/custom-copilot-rag-customize/.vscode/tasks.json +++ b/templates/js/custom-copilot-rag-customize/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/custom-copilot-rag-customize/README.md.tpl b/templates/js/custom-copilot-rag-customize/README.md.tpl index 601898476b..4769373295 100644 --- a/templates/js/custom-copilot-rag-customize/README.md.tpl +++ b/templates/js/custom-copilot-rag-customize/README.md.tpl @@ -11,7 +11,7 @@ This app template also demonstrates usage of techniques like: > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) {{#useOpenAI}} > - An account with [OpenAI](https://platform.openai.com/). diff --git a/templates/js/custom-copilot-rag-customize/appPackage/manifest.json.tpl b/templates/js/custom-copilot-rag-customize/appPackage/manifest.json.tpl index d9463cdd88..b37d09e04a 100644 --- a/templates/js/custom-copilot-rag-customize/appPackage/manifest.json.tpl +++ b/templates/js/custom-copilot-rag-customize/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/js/custom-copilot-rag-customize/package.json.tpl b/templates/js/custom-copilot-rag-customize/package.json.tpl index b5b6bf642d..97af6be391 100644 --- a/templates/js/custom-copilot-rag-customize/package.json.tpl +++ b/templates/js/custom-copilot-rag-customize/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit RAG Bot Sample with customize data source and Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,12 +26,12 @@ }, "dependencies": { "@azure/search-documents": "^12.0.0", - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/custom-copilot-rag-customize/src/app/app.js.tpl b/templates/js/custom-copilot-rag-customize/src/app/app.js.tpl index ebae7510b3..a222e3d8a0 100644 --- a/templates/js/custom-copilot-rag-customize/src/app/app.js.tpl +++ b/templates/js/custom-copilot-rag-customize/src/app/app.js.tpl @@ -21,6 +21,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/js/custom-copilot-rag-customize/src/index.js b/templates/js/custom-copilot-rag-customize/src/index.js index d1e686f00d..7f7ba3b9ad 100644 --- a/templates/js/custom-copilot-rag-customize/src/index.js +++ b/templates/js/custom-copilot-rag-customize/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // This bot's adapter const adapter = require("./adapter"); @@ -7,16 +7,16 @@ const adapter = require("./adapter"); // This bot's main dialog. const app = require("./app/app"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing diff --git a/templates/js/custom-copilot-rag-customize/teamsapp.local.yml.tpl b/templates/js/custom-copilot-rag-customize/teamsapp.local.yml.tpl index 2c7fb58640..25cd75b5df 100644 --- a/templates/js/custom-copilot-rag-customize/teamsapp.local.yml.tpl +++ b/templates/js/custom-copilot-rag-customize/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/js/custom-copilot-rag-customize/teamsapp.yml.tpl b/templates/js/custom-copilot-rag-customize/teamsapp.yml.tpl index 435dd9ae91..26a05e3127 100644 --- a/templates/js/custom-copilot-rag-customize/teamsapp.yml.tpl +++ b/templates/js/custom-copilot-rag-customize/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/js/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl b/templates/js/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl index 0fff774b87..f0d5680f24 100644 --- a/templates/js/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl +++ b/templates/js/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl @@ -2,24 +2,24 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 + "group": "1-Teams", + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 + "group": "1-Teams", + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +66,39 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 + "group": "1-Teams", + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "2-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "2-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -115,6 +139,34 @@ "order": 3 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "2-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "2-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/js/custom-copilot-rag-microsoft365/.vscode/tasks.json b/templates/js/custom-copilot-rag-microsoft365/.vscode/tasks.json index 615f0a126d..e6782df581 100644 --- a/templates/js/custom-copilot-rag-microsoft365/.vscode/tasks.json +++ b/templates/js/custom-copilot-rag-microsoft365/.vscode/tasks.json @@ -97,7 +97,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/custom-copilot-rag-microsoft365/README.md.tpl b/templates/js/custom-copilot-rag-microsoft365/README.md.tpl index 1d8ec1d5b5..9ccfe579a6 100644 --- a/templates/js/custom-copilot-rag-microsoft365/README.md.tpl +++ b/templates/js/custom-copilot-rag-microsoft365/README.md.tpl @@ -12,7 +12,7 @@ This app template also demonstrates usage of techniques like: > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A Microsoft 365 tenant in which you have permission to upload Teams apps. You can get a free Microsoft 365 developer tenant by joining the [Microsoft 365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program). > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli). {{#useOpenAI}} diff --git a/templates/js/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl b/templates/js/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl index 6857c90093..598ea44631 100644 --- a/templates/js/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl +++ b/templates/js/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/js/custom-copilot-rag-microsoft365/package.json.tpl b/templates/js/custom-copilot-rag-microsoft365/package.json.tpl index f1a9f2b25b..91116e0c7d 100644 --- a/templates/js/custom-copilot-rag-microsoft365/package.json.tpl +++ b/templates/js/custom-copilot-rag-microsoft365/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit RAG Bot Sample with Graph API and Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -27,12 +27,12 @@ "dependencies": { "@microsoft/microsoft-graph-client": "^3.0.1", "@azure/search-documents": "^12.0.0", - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/custom-copilot-rag-microsoft365/src/app/app.js.tpl b/templates/js/custom-copilot-rag-microsoft365/src/app/app.js.tpl index 9638833df2..61c1c876ec 100644 --- a/templates/js/custom-copilot-rag-microsoft365/src/app/app.js.tpl +++ b/templates/js/custom-copilot-rag-microsoft365/src/app/app.js.tpl @@ -21,6 +21,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/js/custom-copilot-rag-microsoft365/src/index.js b/templates/js/custom-copilot-rag-microsoft365/src/index.js index 98912b6f41..65eee21aa4 100644 --- a/templates/js/custom-copilot-rag-microsoft365/src/index.js +++ b/templates/js/custom-copilot-rag-microsoft365/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // This bot's adapter const adapter = require("./adapter"); @@ -7,17 +7,18 @@ const adapter = require("./adapter"); // This bot's main dialog. const app = require("./app/app"); const path = require("path"); +const send = require("send"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res, async (context) => { // Dispatch to application for routing @@ -25,9 +26,13 @@ server.post("/api/messages", async (req, res) => { }); }); -server.get( - "/auth-:name(start|end).html", - restify.plugins.serveStatic({ - directory: path.join(__dirname, "public"), - }) -); +expressApp.get(["/auth-start.html", "/auth-end.html"], async (req, res) => { + send( + req, + path.join( + __dirname, + "public", + req.url.includes("auth-start.html") ? "auth-start.html" : "auth-end.html" + ) + ).pipe(res); +}); diff --git a/templates/js/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl b/templates/js/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl index 996095a982..f9afd1921e 100644 --- a/templates/js/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl +++ b/templates/js/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl @@ -57,11 +57,13 @@ provision: manifestPath: ./aad.manifest.json # Relative path to teamsfx folder. Environment variables in manifest will be replaced before apply to AAD app outputFilePath: ./build/aad.manifest.${{TEAMSFX_ENV}}.json + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -70,11 +72,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -84,6 +88,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/js/custom-copilot-rag-microsoft365/teamsapp.yml.tpl b/templates/js/custom-copilot-rag-microsoft365/teamsapp.yml.tpl index 726421f253..9b58cf7600 100644 --- a/templates/js/custom-copilot-rag-microsoft365/teamsapp.yml.tpl +++ b/templates/js/custom-copilot-rag-microsoft365/teamsapp.yml.tpl @@ -60,11 +60,13 @@ provision: manifestPath: ./aad.manifest.json # Relative path to teamsfx folder. Environment variables in manifest will be replaced before apply to AAD app outputFilePath: ./build/aad.manifest.${{TEAMSFX_ENV}}.json + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -72,11 +74,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -84,6 +88,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -112,11 +127,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -124,11 +141,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/js/dashboard-tab/README.md b/templates/js/dashboard-tab/README.md index 79fffb69d2..61e75e29f1 100644 --- a/templates/js/dashboard-tab/README.md +++ b/templates/js/dashboard-tab/README.md @@ -11,7 +11,7 @@ This template showcases an app that embeds a canvas containing multiple cards th > **Prerequisites** > To run the dashboard template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Set up your dev environment for extending Teams apps across Microsoft 365](https://aka.ms/teamsfx-m365-apps-prerequisites) > Please note that after you enrolled your developer tenant in Office 365 Target Release, it may take couple days for the enrollment to take effect. diff --git a/templates/js/dashboard-tab/appPackage/manifest.json.tpl b/templates/js/dashboard-tab/appPackage/manifest.json.tpl index 1a8770d2ce..77152e67c5 100644 --- a/templates/js/dashboard-tab/appPackage/manifest.json.tpl +++ b/templates/js/dashboard-tab/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/dashboard-tab/package.json.tpl b/templates/js/dashboard-tab/package.json.tpl index 02d6fec293..6c2ad8178f 100644 --- a/templates/js/dashboard-tab/package.json.tpl +++ b/templates/js/dashboard-tab/package.json.tpl @@ -2,17 +2,17 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.1.0", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "type": "module", "private": true, "dependencies": { "@fluentui/react-charting": "^5.14.10", - "@fluentui/react-components": "^9.18.0", + "@fluentui/react-components": "^9.55.1", "@fluentui/react-icons": "^2.0.186", - "@microsoft/teams-js": "^2.19.0", - "@microsoft/teamsfx": "^2.2.0", - "@microsoft/teamsfx-react": "^3.0.0", + "@microsoft/teams-js": "^2.22.0", + "@microsoft/teamsfx": "^3.0.0-alpha", + "@microsoft/teamsfx-react": "^4.0.0-alpha", "react": "^18.2.0", "react-dom": "^18.2.0", "react-router-dom": "^6.8.0" diff --git a/templates/js/default-bot-message-extension/.vscode/tasks.json b/templates/js/default-bot-message-extension/.vscode/tasks.json index 585f86ae9a..5644df6240 100644 --- a/templates/js/default-bot-message-extension/.vscode/tasks.json +++ b/templates/js/default-bot-message-extension/.vscode/tasks.json @@ -97,7 +97,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/js/default-bot-message-extension/README.md b/templates/js/default-bot-message-extension/README.md index 1bf7b3c7a4..3941228418 100644 --- a/templates/js/default-bot-message-extension/README.md +++ b/templates/js/default-bot-message-extension/README.md @@ -10,7 +10,7 @@ This is a simple hello world application with both Bot and Message extension cap ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - An M365 account. If you do not have M365 account, apply one from [M365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -43,7 +43,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | :------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the Teams Toolkit and click `Provision` from DEPLOYMENT section or open the command palette and select: `Teams: Provision`.
  • Open the Teams Toolkit and click `Deploy` or open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision --env dev`.
  • Run command: `teamsapp deploy --env dev`.
| diff --git a/templates/js/default-bot-message-extension/appPackage/manifest.json.tpl b/templates/js/default-bot-message-extension/appPackage/manifest.json.tpl index 7484a37b0c..d60c820186 100644 --- a/templates/js/default-bot-message-extension/appPackage/manifest.json.tpl +++ b/templates/js/default-bot-message-extension/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/default-bot-message-extension/package.json.tpl b/templates/js/default-bot-message-extension/package.json.tpl index a045362026..2ac18702a5 100644 --- a/templates/js/default-bot-message-extension/package.json.tpl +++ b/templates/js/default-bot-message-extension/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit hello world Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -22,11 +22,11 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } diff --git a/templates/js/default-bot-message-extension/src/index.js b/templates/js/default-bot-message-extension/src/index.js index 119d4348bf..42cea37014 100644 --- a/templates/js/default-bot-message-extension/src/index.js +++ b/templates/js/default-bot-message-extension/src/index.js @@ -1,7 +1,7 @@ // index.js is used to setup and configure your bot // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -39,15 +39,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/js/default-bot/.vscode/tasks.json b/templates/js/default-bot/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/default-bot/.vscode/tasks.json +++ b/templates/js/default-bot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/default-bot/README.md.tpl b/templates/js/default-bot/README.md.tpl index e5790f7a82..298324bd98 100644 --- a/templates/js/default-bot/README.md.tpl +++ b/templates/js/default-bot/README.md.tpl @@ -14,7 +14,7 @@ A bot interaction can be a quick question and answer, or it can be a complex con > > To run the Basic Bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/default-bot/appPackage/manifest.json.tpl b/templates/js/default-bot/appPackage/manifest.json.tpl index 7e3b1973bb..58e66c293e 100644 --- a/templates/js/default-bot/appPackage/manifest.json.tpl +++ b/templates/js/default-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/default-bot/index.js b/templates/js/default-bot/index.js index 67bf7ca693..c638ce4840 100644 --- a/templates/js/default-bot/index.js +++ b/templates/js/default-bot/index.js @@ -1,7 +1,7 @@ // index.js is used to setup and configure your bot // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -42,15 +42,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/js/default-bot/package.json.tpl b/templates/js/default-bot/package.json.tpl index e16767e98a..18ee3455f5 100644 --- a/templates/js/default-bot/package.json.tpl +++ b/templates/js/default-bot/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit hello world Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -21,11 +21,11 @@ "test": "echo \"Error: no test specified\" && exit 1" }, "dependencies": { - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } diff --git a/templates/js/link-unfurling/.vscode/tasks.json b/templates/js/link-unfurling/.vscode/tasks.json index fdd3407c37..83ee7eb356 100644 --- a/templates/js/link-unfurling/.vscode/tasks.json +++ b/templates/js/link-unfurling/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/link-unfurling/README.md.tpl b/templates/js/link-unfurling/README.md.tpl index 10ae5f4799..61aa68be53 100644 --- a/templates/js/link-unfurling/README.md.tpl +++ b/templates/js/link-unfurling/README.md.tpl @@ -13,7 +13,7 @@ This template showcases an app that unfurls a link into an adaptive card when UR > **Prerequisites** > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A Microsoft 365 account. If you do not have Microsoft 365 account, apply one from [Microsoft 365 developer program](https://developer.microsoft.com/microsoft-365/dev-program) {{/enableMETestToolByDefault}} @@ -50,7 +50,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | --------------------------------------- | ---------------------------------------------- | -| `src/index.js` | Application entry point and `restify` handlers | +| `src/index.js` | Application entry point and `express` handlers | | `src/linkUnfurlingApp.js` | The teams activity handler | | `src/adaptiveCards/helloWorldCard.json` | The adaptive card | diff --git a/templates/js/link-unfurling/appPackage/manifest.json.tpl b/templates/js/link-unfurling/appPackage/manifest.json.tpl index 61044d2411..5922642ac1 100644 --- a/templates/js/link-unfurling/appPackage/manifest.json.tpl +++ b/templates/js/link-unfurling/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/link-unfurling/package.json.tpl b/templates/js/link-unfurling/package.json.tpl index f71a4912e2..87eaff76f2 100644 --- a/templates/js/link-unfurling/package.json.tpl +++ b/templates/js/link-unfurling/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit link unfurling sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -22,11 +22,11 @@ "url": "https://github.com" }, "dependencies": { - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/link-unfurling/src/index.js b/templates/js/link-unfurling/src/index.js index 900f15123d..79b41e8951 100644 --- a/templates/js/link-unfurling/src/index.js +++ b/templates/js/link-unfurling/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -37,15 +37,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const linkUnfurlingApp = new LinkUnfurlingApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await linkUnfurlingApp.run(context); }); diff --git a/templates/js/m365-message-extension/.vscode/tasks.json b/templates/js/m365-message-extension/.vscode/tasks.json index fdd3407c37..83ee7eb356 100644 --- a/templates/js/m365-message-extension/.vscode/tasks.json +++ b/templates/js/m365-message-extension/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/m365-message-extension/README.md.tpl b/templates/js/m365-message-extension/README.md.tpl index 7fcf410c56..50637942cd 100644 --- a/templates/js/m365-message-extension/README.md.tpl +++ b/templates/js/m365-message-extension/README.md.tpl @@ -8,7 +8,7 @@ This app template is a search-based [message extension](https://docs.microsoft.c > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Set up your dev environment for extending Teams apps across Microsoft 365](https://aka.ms/teamsfx-m365-apps-prerequisites) diff --git a/templates/js/m365-message-extension/appPackage/manifest.json.tpl b/templates/js/m365-message-extension/appPackage/manifest.json.tpl index ada4841ede..449ee0e13f 100644 --- a/templates/js/m365-message-extension/appPackage/manifest.json.tpl +++ b/templates/js/m365-message-extension/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/m365-message-extension/package.json.tpl b/templates/js/m365-message-extension/package.json.tpl index 0f7221863a..5b5810dbbc 100644 --- a/templates/js/m365-message-extension/package.json.tpl +++ b/templates/js/m365-message-extension/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit message extension search sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,11 +23,11 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } diff --git a/templates/js/m365-message-extension/src/index.js b/templates/js/m365-message-extension/src/index.js index d49c85762a..6d7cb11540 100644 --- a/templates/js/m365-message-extension/src/index.js +++ b/templates/js/m365-message-extension/src/index.js @@ -1,7 +1,7 @@ // index.js is used to setup and configure your bot // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -39,15 +39,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const searchApp = new SearchApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await searchApp.run(context); }); diff --git a/templates/js/message-extension-action/.vscode/tasks.json b/templates/js/message-extension-action/.vscode/tasks.json index fdd3407c37..83ee7eb356 100644 --- a/templates/js/message-extension-action/.vscode/tasks.json +++ b/templates/js/message-extension-action/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/message-extension-action/README.md.tpl b/templates/js/message-extension-action/README.md.tpl index ee68f04300..ccd33b3521 100644 --- a/templates/js/message-extension-action/README.md.tpl +++ b/templates/js/message-extension-action/README.md.tpl @@ -10,7 +10,7 @@ This app template implements action command that allows you to present your user > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableMETestToolByDefault}} diff --git a/templates/js/message-extension-action/appPackage/manifest.json.tpl b/templates/js/message-extension-action/appPackage/manifest.json.tpl index 5ce95fa567..6428e7842f 100644 --- a/templates/js/message-extension-action/appPackage/manifest.json.tpl +++ b/templates/js/message-extension-action/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/message-extension-action/package.json.tpl b/templates/js/message-extension-action/package.json.tpl index 285eaf703b..4d6d3d6d1e 100644 --- a/templates/js/message-extension-action/package.json.tpl +++ b/templates/js/message-extension-action/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit message extension action sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -25,11 +25,11 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/message-extension-action/src/index.js b/templates/js/message-extension-action/src/index.js index 58b6da0d2d..2b259cfbc6 100644 --- a/templates/js/message-extension-action/src/index.js +++ b/templates/js/message-extension-action/src/index.js @@ -1,5 +1,5 @@ // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -37,15 +37,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const actionApp = new ActionApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await actionApp.run(context); }); diff --git a/templates/js/message-extension-copilot/.vscode/tasks.json b/templates/js/message-extension-copilot/.vscode/tasks.json index 5a6577873d..2e9b16cefc 100644 --- a/templates/js/message-extension-copilot/.vscode/tasks.json +++ b/templates/js/message-extension-copilot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -220,7 +220,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/message-extension-copilot/README.md.tpl b/templates/js/message-extension-copilot/README.md.tpl index 36083b9b7c..60a9c618b6 100644 --- a/templates/js/message-extension-copilot/README.md.tpl +++ b/templates/js/message-extension-copilot/README.md.tpl @@ -8,7 +8,7 @@ This app template is a search-based [message extension](https://docs.microsoft.c > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Set up your dev environment for extending Teams apps across Microsoft 365](https://aka.ms/teamsfx-m365-apps-prerequisites) > Please note that after you enrolled your developer tenant in Office 365 Target Release, it may take couple days for the enrollment to take effect. diff --git a/templates/js/message-extension-copilot/package.json.tpl b/templates/js/message-extension-copilot/package.json.tpl index 3046e57cff..407e18cc7a 100644 --- a/templates/js/message-extension-copilot/package.json.tpl +++ b/templates/js/message-extension-copilot/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit message extension search sample", "engines": { - "node": "16 || 18 || 20" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,8 +23,8 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^11.1.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", diff --git a/templates/js/message-extension-copilot/src/index.js b/templates/js/message-extension-copilot/src/index.js index d49c85762a..6d7cb11540 100644 --- a/templates/js/message-extension-copilot/src/index.js +++ b/templates/js/message-extension-copilot/src/index.js @@ -1,7 +1,7 @@ // index.js is used to setup and configure your bot // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -39,15 +39,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const searchApp = new SearchApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await searchApp.run(context); }); diff --git a/templates/js/message-extension/.vscode/tasks.json b/templates/js/message-extension/.vscode/tasks.json index 53c41778d7..77ee69444c 100644 --- a/templates/js/message-extension/.vscode/tasks.json +++ b/templates/js/message-extension/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/js/message-extension/README.md.tpl b/templates/js/message-extension/README.md.tpl index b9de69853a..f1bbda095a 100644 --- a/templates/js/message-extension/README.md.tpl +++ b/templates/js/message-extension/README.md.tpl @@ -14,7 +14,7 @@ This app template has a search command, an action command and a link unfurling. > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableMETestToolByDefault}} diff --git a/templates/js/message-extension/appPackage/manifest.json.tpl b/templates/js/message-extension/appPackage/manifest.json.tpl index b5f111aed4..5b24b6bac6 100644 --- a/templates/js/message-extension/appPackage/manifest.json.tpl +++ b/templates/js/message-extension/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/message-extension/package.json.tpl b/templates/js/message-extension/package.json.tpl index bdff1a09c5..587611771b 100644 --- a/templates/js/message-extension/package.json.tpl +++ b/templates/js/message-extension/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit message extension Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -24,12 +24,12 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", + "botbuilder": "^4.23.1", "isomorphic-fetch": "^3.0.0", - "restify": "^10.0.0" + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/message-extension/src/index.js b/templates/js/message-extension/src/index.js index 119d4348bf..42cea37014 100644 --- a/templates/js/message-extension/src/index.js +++ b/templates/js/message-extension/src/index.js @@ -1,7 +1,7 @@ // index.js is used to setup and configure your bot // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -39,15 +39,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/js/non-sso-tab-default-bot/.vscode/tasks.json b/templates/js/non-sso-tab-default-bot/.vscode/tasks.json index 4557aa487b..9433f8bb8a 100644 --- a/templates/js/non-sso-tab-default-bot/.vscode/tasks.json +++ b/templates/js/non-sso-tab-default-bot/.vscode/tasks.json @@ -105,7 +105,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/non-sso-tab-default-bot/appPackage/manifest.json.tpl b/templates/js/non-sso-tab-default-bot/appPackage/manifest.json.tpl index 0976d52947..4970986dc9 100644 --- a/templates/js/non-sso-tab-default-bot/appPackage/manifest.json.tpl +++ b/templates/js/non-sso-tab-default-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/non-sso-tab-default-bot/bot/README.md b/templates/js/non-sso-tab-default-bot/bot/README.md index 82ef1d2ba4..ed2aac93e0 100644 --- a/templates/js/non-sso-tab-default-bot/bot/README.md +++ b/templates/js/non-sso-tab-default-bot/bot/README.md @@ -10,7 +10,7 @@ This is a simple hello world application with both Bot and Message extension cap ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - An M365 account. If you do not have M365 account, apply one from [M365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -43,7 +43,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | :------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the Teams Toolkit and click `Provision` from DEPLOYMENT section or open the command palette and select: `Teams: Provision`.
  • Open the Teams Toolkit and click `Deploy` or open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision --env dev`.
  • Run command: `teamsapp deploy --env dev`.
| @@ -125,4 +125,3 @@ To trigger these functions, there are multiple entry points: - [Search Command](https://docs.microsoft.com/en-us/microsoftteams/platform/messaging-extensions/how-to/search-commands/define-search-command) - [Action Command](https://docs.microsoft.com/en-us/microsoftteams/platform/messaging-extensions/how-to/action-commands/define-action-command) - [Link Unfurling](https://docs.microsoft.com/en-us/microsoftteams/platform/messaging-extensions/how-to/link-unfurling?tabs=dotnet) - diff --git a/templates/js/non-sso-tab-default-bot/bot/index.js b/templates/js/non-sso-tab-default-bot/bot/index.js index 67bf7ca693..c638ce4840 100644 --- a/templates/js/non-sso-tab-default-bot/bot/index.js +++ b/templates/js/non-sso-tab-default-bot/bot/index.js @@ -1,7 +1,7 @@ // index.js is used to setup and configure your bot // Import required packages -const restify = require("restify"); +const express = require("express"); // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -42,15 +42,16 @@ adapter.onTurnError = async (context, error) => { // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, function () { - console.log(`\nBot started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/js/non-sso-tab-default-bot/bot/package.json.tpl b/templates/js/non-sso-tab-default-bot/bot/package.json.tpl index 3616026cd7..ff5bac41bf 100644 --- a/templates/js/non-sso-tab-default-bot/bot/package.json.tpl +++ b/templates/js/non-sso-tab-default-bot/bot/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit hello world Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -21,11 +21,11 @@ "dependencies": { "adaptivecards-templating": "^2.3.1", "adaptive-expressions": "^4.22.3", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } diff --git a/templates/js/non-sso-tab-default-bot/package.json.tpl b/templates/js/non-sso-tab-default-bot/package.json.tpl index 83a9ab9a6b..c08e743dc1 100644 --- a/templates/js/non-sso-tab-default-bot/package.json.tpl +++ b/templates/js/non-sso-tab-default-bot/package.json.tpl @@ -2,7 +2,7 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.0.1", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", diff --git a/templates/js/non-sso-tab-default-bot/tab/README.md b/templates/js/non-sso-tab-default-bot/tab/README.md index df224d11c9..55da83bd21 100644 --- a/templates/js/non-sso-tab-default-bot/tab/README.md +++ b/templates/js/non-sso-tab-default-bot/tab/README.md @@ -4,7 +4,7 @@ Microsoft Teams supports the ability to run web-based UI inside "custom tabs" th ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - An M365 account. If you do not have M365 account, apply one from [M365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -29,7 +29,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the Teams Toolkit and click `Provision` from DEVELOPMENT section or open the command palette and select: `Teams: Provision`.
  • Open the Teams Toolkit and click `Deploy` or open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision --env dev`.
  • Run command: `teamsapp deploy --env dev`.
| @@ -71,4 +71,3 @@ Once deployed, you may want to distribute your application to your organization' Microsoft Teams provides a mechanism by which an application can obtain the signed-in Teams user token to access Microsoft Graph (and other APIs). Teams Toolkit facilitates this interaction by abstracting some of the Microsoft Entra flows and integrations behind some simple, high-level APIs. This enables you to add single sign-on (SSO) features easily to your Teams application. Please follow this [document](https://aka.ms/teamsfx-add-sso-new) to add single sign on for your project. - diff --git a/templates/js/non-sso-tab-default-bot/tab/package.json.tpl b/templates/js/non-sso-tab-default-bot/tab/package.json.tpl index 7591aaf8bd..f707dde8c3 100644 --- a/templates/js/non-sso-tab-default-bot/tab/package.json.tpl +++ b/templates/js/non-sso-tab-default-bot/tab/package.json.tpl @@ -2,14 +2,14 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.1.0", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "private": true, "dependencies": { - "@fluentui/react-components": "^9.18.0", - "@microsoft/teams-js": "^2.19.0", - "@microsoft/teamsfx": "^2.2.0", - "@microsoft/teamsfx-react": "^3.0.2", + "@fluentui/react-components": "^9.55.1", + "@microsoft/teams-js": "^2.22.0", + "@microsoft/teamsfx": "^3.0.0-alpha", + "@microsoft/teamsfx-react": "^4.0.0-alpha", "axios": "^0.21.1", "react": "^18.2.0", "react-dom": "^18.2.0", diff --git a/templates/js/non-sso-tab/README.md b/templates/js/non-sso-tab/README.md index 4dc09ecbf2..4537c2a600 100644 --- a/templates/js/non-sso-tab/README.md +++ b/templates/js/non-sso-tab/README.md @@ -40,7 +40,7 @@ The following files can be customized and demonstrate an example implementation | `src/static/scripts/teamsapp.js` | A script that calls `teamsjs` SDK to get the context of on which Microsoft 365 application your app is running. | | `src/static/styles/custom.css` | css file for the app. | | `src/static/views/hello.html` | html file for the app. | -| `src/app.js` | Starting a restify server. | +| `src/app.js` | Starting an `express` server. | The following are Teams Toolkit specific project files. You can [visit a complete guide on Github](https://github.com/OfficeDev/TeamsFx/wiki/Teams-Toolkit-Visual-Studio-Code-v5-Guide#overview) to understand how Teams Toolkit works. diff --git a/templates/js/non-sso-tab/appPackage/manifest.json.tpl b/templates/js/non-sso-tab/appPackage/manifest.json.tpl index 4199df99a3..009f2ff2cf 100644 --- a/templates/js/non-sso-tab/appPackage/manifest.json.tpl +++ b/templates/js/non-sso-tab/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/non-sso-tab/package.json.tpl b/templates/js/non-sso-tab/package.json.tpl index e2c7c176a3..f1237ada49 100644 --- a/templates/js/non-sso-tab/package.json.tpl +++ b/templates/js/non-sso-tab/package.json.tpl @@ -2,11 +2,11 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.1.0", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "private": true, "dependencies": { - "restify": "^11.1.0", + "express": "^4.21.1", "send": "^0.18.0" }, "devDependencies": { diff --git a/templates/js/non-sso-tab/src/app.js b/templates/js/non-sso-tab/src/app.js index 8eb03c099c..478d3e72cb 100644 --- a/templates/js/non-sso-tab/src/app.js +++ b/templates/js/non-sso-tab/src/app.js @@ -1,36 +1,38 @@ -const restify = require("restify"); -const send = require("send"); +const express = require("express"); const fs = require("fs"); +const https = require("https"); +const path = require("path"); +const send = require("send"); -//Create HTTP server. -const server = restify.createServer({ - key: process.env.SSL_KEY_FILE ? fs.readFileSync(process.env.SSL_KEY_FILE) : undefined, - certificate: process.env.SSL_CRT_FILE ? fs.readFileSync(process.env.SSL_CRT_FILE) : undefined, - formatters: { - "text/html": function (req, res, body) { - return body; - }, - }, -}); +const app = express(); -server.get( - "/static/*", - restify.plugins.serveStatic({ - directory: __dirname, - }) -); +const sslOptions = { + key: process.env.SSL_KEY_FILE ? fs.readFileSync(process.env.SSL_KEY_FILE) : undefined, + cert: process.env.SSL_CRT_FILE ? fs.readFileSync(process.env.SSL_CRT_FILE) : undefined, +}; -server.listen(process.env.port || process.env.PORT || 3333, function () { - console.log(`\n${server.name} listening to ${server.url}`); -}); +app.use("/static", express.static(path.join(__dirname, "static"))); // Adding tabs to our app. This will setup routes to various views // Setup home page -server.get("/", (req, res, next) => { - send(req, __dirname + "/views/hello.html").pipe(res); +app.get("/", (req, res) => { + send(req, path.join(__dirname, "views", "hello.html")).pipe(res); }); // Setup the static tab -server.get("/tab", (req, res, next) => { - send(req, __dirname + "/views/hello.html").pipe(res); +app.get("/tab", (req, res) => { + send(req, path.join(__dirname, "views", "hello.html")).pipe(res); }); + +// Create HTTP server +const port = process.env.port || process.env.PORT || 3333; + +if (sslOptions.key && sslOptions.cert) { + https.createServer(sslOptions, app).listen(port, () => { + console.log(`Express server listening on port ${port}`); + }); +} else { + app.listen(port, () => { + console.log(`Express server listening on port ${port}`); + }); +} diff --git a/templates/js/notification-restify/.appserviceignore b/templates/js/notification-express/.appserviceignore similarity index 100% rename from templates/js/notification-restify/.appserviceignore rename to templates/js/notification-express/.appserviceignore diff --git a/templates/js/notification-restify/.gitignore b/templates/js/notification-express/.gitignore similarity index 100% rename from templates/js/notification-restify/.gitignore rename to templates/js/notification-express/.gitignore diff --git a/templates/js/notification-restify/.localConfigs b/templates/js/notification-express/.localConfigs similarity index 100% rename from templates/js/notification-restify/.localConfigs rename to templates/js/notification-express/.localConfigs diff --git a/templates/js/notification-restify/.localConfigs.testTool b/templates/js/notification-express/.localConfigs.testTool similarity index 100% rename from templates/js/notification-restify/.localConfigs.testTool rename to templates/js/notification-express/.localConfigs.testTool diff --git a/templates/js/notification-restify/.vscode/extensions.json b/templates/js/notification-express/.vscode/extensions.json similarity index 100% rename from templates/js/notification-restify/.vscode/extensions.json rename to templates/js/notification-express/.vscode/extensions.json diff --git a/templates/js/notification-restify/.vscode/launch.json.tpl b/templates/js/notification-express/.vscode/launch.json.tpl similarity index 100% rename from templates/js/notification-restify/.vscode/launch.json.tpl rename to templates/js/notification-express/.vscode/launch.json.tpl diff --git a/templates/js/notification-restify/.vscode/settings.json b/templates/js/notification-express/.vscode/settings.json similarity index 100% rename from templates/js/notification-restify/.vscode/settings.json rename to templates/js/notification-express/.vscode/settings.json diff --git a/templates/js/notification-restify/.vscode/tasks.json b/templates/js/notification-express/.vscode/tasks.json similarity index 97% rename from templates/js/notification-restify/.vscode/tasks.json rename to templates/js/notification-express/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/notification-restify/.vscode/tasks.json +++ b/templates/js/notification-express/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/notification-restify/README.md.tpl b/templates/js/notification-express/README.md.tpl similarity index 97% rename from templates/js/notification-restify/README.md.tpl rename to templates/js/notification-express/README.md.tpl index 2f5fd36e8b..4a76f6fd51 100644 --- a/templates/js/notification-restify/README.md.tpl +++ b/templates/js/notification-express/README.md.tpl @@ -11,7 +11,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} @@ -66,7 +66,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | - | - | -| `src/index.js` | Application entry point and `restify` handlers for notifications | +| `src/index.js` | Application entry point and `express` handlers for notifications | | `src/teamsBot.js`| An empty teams activity handler for bot customization | | `src/adaptiveCards/notification-default.json` | A generated Adaptive Card that is sent to Teams | @@ -80,7 +80,7 @@ There are few customizations you can make to extend the template to fit your bus ### Step 1: Customize the trigger point from event source -By default Teams Toolkit scaffolds a single `restify` entry point in `src/index.js`. When a HTTP request is sent to this entry point, the default implementation sends a hard-coded Adaptive Card to Teams. You can customize this behavior by customizing `src/index.js`. A typical implementation might make an API call to retrieve some events and/or data, and then send an Adaptive Card as appropriate. +By default Teams Toolkit scaffolds a single `express` entry point in `src/index.js`. When a HTTP request is sent to this entry point, the default implementation sends a hard-coded Adaptive Card to Teams. You can customize this behavior by customizing `src/index.js`. A typical implementation might make an API call to retrieve some events and/or data, and then send an Adaptive Card as appropriate. You can also add additional triggers by: diff --git a/templates/js/notification-restify/appPackage/color.png b/templates/js/notification-express/appPackage/color.png similarity index 100% rename from templates/js/notification-restify/appPackage/color.png rename to templates/js/notification-express/appPackage/color.png diff --git a/templates/ts/notification-restify/appPackage/manifest.json.tpl b/templates/js/notification-express/appPackage/manifest.json.tpl similarity index 93% rename from templates/ts/notification-restify/appPackage/manifest.json.tpl rename to templates/js/notification-express/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/ts/notification-restify/appPackage/manifest.json.tpl +++ b/templates/js/notification-express/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/notification-restify/appPackage/outline.png b/templates/js/notification-express/appPackage/outline.png similarity index 100% rename from templates/js/notification-restify/appPackage/outline.png rename to templates/js/notification-express/appPackage/outline.png diff --git a/templates/js/notification-restify/env/.env.dev b/templates/js/notification-express/env/.env.dev similarity index 100% rename from templates/js/notification-restify/env/.env.dev rename to templates/js/notification-express/env/.env.dev diff --git a/templates/js/notification-restify/env/.env.dev.user b/templates/js/notification-express/env/.env.dev.user similarity index 100% rename from templates/js/notification-restify/env/.env.dev.user rename to templates/js/notification-express/env/.env.dev.user diff --git a/templates/js/notification-restify/env/.env.local b/templates/js/notification-express/env/.env.local similarity index 100% rename from templates/js/notification-restify/env/.env.local rename to templates/js/notification-express/env/.env.local diff --git a/templates/js/notification-restify/env/.env.local.user b/templates/js/notification-express/env/.env.local.user similarity index 100% rename from templates/js/notification-restify/env/.env.local.user rename to templates/js/notification-express/env/.env.local.user diff --git a/templates/js/notification-restify/env/.env.testtool b/templates/js/notification-express/env/.env.testtool similarity index 100% rename from templates/js/notification-restify/env/.env.testtool rename to templates/js/notification-express/env/.env.testtool diff --git a/templates/js/notification-restify/infra/azure.bicep b/templates/js/notification-express/infra/azure.bicep similarity index 100% rename from templates/js/notification-restify/infra/azure.bicep rename to templates/js/notification-express/infra/azure.bicep diff --git a/templates/js/notification-restify/infra/azure.parameters.json.tpl b/templates/js/notification-express/infra/azure.parameters.json.tpl similarity index 100% rename from templates/js/notification-restify/infra/azure.parameters.json.tpl rename to templates/js/notification-express/infra/azure.parameters.json.tpl diff --git a/templates/js/notification-restify/infra/botRegistration/azurebot.bicep b/templates/js/notification-express/infra/botRegistration/azurebot.bicep similarity index 100% rename from templates/js/notification-restify/infra/botRegistration/azurebot.bicep rename to templates/js/notification-express/infra/botRegistration/azurebot.bicep diff --git a/templates/js/notification-restify/infra/botRegistration/readme.md b/templates/js/notification-express/infra/botRegistration/readme.md similarity index 100% rename from templates/js/notification-restify/infra/botRegistration/readme.md rename to templates/js/notification-express/infra/botRegistration/readme.md diff --git a/templates/js/notification-restify/package.json.tpl b/templates/js/notification-express/package.json.tpl similarity index 81% rename from templates/js/notification-restify/package.json.tpl rename to templates/js/notification-express/package.json.tpl index c98dc0c0bd..45903cac85 100644 --- a/templates/js/notification-restify/package.json.tpl +++ b/templates/js/notification-express/package.json.tpl @@ -1,9 +1,9 @@ { "name": "{{SafeProjectNameLowerCase}}", "version": "1.0.0", - "description": "Microsoft Teams Toolkit Notification Bot Sample (Restify)", + "description": "Microsoft Teams Toolkit Notification Bot Sample (Express)", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,13 +23,13 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "env-cmd": "^10.1.0" } } diff --git a/templates/js/notification-restify/src/adaptiveCards/notification-default.json b/templates/js/notification-express/src/adaptiveCards/notification-default.json similarity index 100% rename from templates/js/notification-restify/src/adaptiveCards/notification-default.json rename to templates/js/notification-express/src/adaptiveCards/notification-default.json diff --git a/templates/js/notification-restify/src/index.js b/templates/js/notification-express/src/index.js similarity index 62% rename from templates/js/notification-restify/src/index.js rename to templates/js/notification-express/src/index.js index 698ec6ab72..173680f35a 100644 --- a/templates/js/notification-restify/src/index.js +++ b/templates/js/notification-express/src/index.js @@ -2,45 +2,42 @@ const notificationTemplate = require("./adaptiveCards/notification-default.json" const { notificationApp } = require("./internal/initialize"); const ACData = require("adaptivecards-templating"); const { TeamsBot } = require("./teamsBot"); -const restify = require("restify"); +const express = require("express"); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nApp Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // HTTP trigger to send notification. You need to add authentication / authorization for this API. Refer https://aka.ms/teamsfx-notification for more details. -server.post( - "/api/notification", - restify.plugins.queryParser(), - restify.plugins.bodyParser(), // Add more parsers if needed - async (req, res) => { - const pageSize = 100; - let continuationToken = undefined; - do { - const pagedData = await notificationApp.notification.getPagedInstallations( - pageSize, - continuationToken +expressApp.post("/api/notification", async (req, res) => { + const pageSize = 100; + let continuationToken = undefined; + do { + const pagedData = await notificationApp.notification.getPagedInstallations( + pageSize, + continuationToken + ); + const installations = pagedData.data; + continuationToken = pagedData.continuationToken; + + for (const target of installations) { + await target.sendAdaptiveCard( + new ACData.Template(notificationTemplate).expand({ + $root: { + title: "New Event Occurred!", + appName: "Contoso App Notification", + description: `This is a sample http-triggered notification to ${target.type}`, + notificationUrl: "https://aka.ms/teamsfx-notification-new", + }, + }) ); - const installations = pagedData.data; - continuationToken = pagedData.continuationToken; - - for (const target of installations) { - await target.sendAdaptiveCard( - new ACData.Template(notificationTemplate).expand({ - $root: { - title: "New Event Occurred!", - appName: "Contoso App Notification", - description: `This is a sample http-triggered notification to ${target.type}`, - notificationUrl: "https://aka.ms/teamsfx-notification-new", - }, - }) - ); - - /****** To distinguish different target types ******/ - /** "Channel" means this bot is installed to a Team (default to notify General channel) + + /****** To distinguish different target types ******/ + /** "Channel" means this bot is installed to a Team (default to notify General channel) if (target.type === NotificationTargetType.Channel) { // Directly notify the Team (to the default General channel) await target.sendAdaptiveCard(...); @@ -66,7 +63,7 @@ server.post( } **/ - /** "Group" means this bot is installed to a Group Chat + /** "Group" means this bot is installed to a Group Chat if (target.type === NotificationTargetType.Group) { // Directly notify the Group Chat await target.sendAdaptiveCard(...); @@ -86,23 +83,23 @@ server.post( } **/ - /** "Person" means this bot is installed as a Personal app + /** "Person" means this bot is installed as a Personal app if (target.type === NotificationTargetType.Person) { // Directly notify the individual person await target.sendAdaptiveCard(...); } **/ - } - } while (continuationToken); + } + } while (continuationToken); - /** You can also find someone and notify the individual person + /** You can also find someone and notify the individual person const member = await notificationApp.notification.findMember( async (m) => m.account.email === "someone@contoso.com" ); await member?.sendAdaptiveCard(...); **/ - /** Or find multiple people and notify them + /** Or find multiple people and notify them const members = await notificationApp.notification.findAllMembers( async (m) => m.account.email?.startsWith("test") ); @@ -111,13 +108,12 @@ server.post( } **/ - res.json({}); - } -); + res.json({}); +}); // Bot Framework message handler. const teamsBot = new TeamsBot(); -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await notificationApp.requestHandler(req, res, async (context) => { await teamsBot.run(context); }); diff --git a/templates/js/notification-restify/src/internal/config.js b/templates/js/notification-express/src/internal/config.js similarity index 100% rename from templates/js/notification-restify/src/internal/config.js rename to templates/js/notification-express/src/internal/config.js diff --git a/templates/js/notification-restify/src/internal/initialize.js b/templates/js/notification-express/src/internal/initialize.js similarity index 100% rename from templates/js/notification-restify/src/internal/initialize.js rename to templates/js/notification-express/src/internal/initialize.js diff --git a/templates/js/notification-restify/src/teamsBot.js b/templates/js/notification-express/src/teamsBot.js similarity index 100% rename from templates/js/notification-restify/src/teamsBot.js rename to templates/js/notification-express/src/teamsBot.js diff --git a/templates/js/notification-restify/teamsapp.local.yml.tpl b/templates/js/notification-express/teamsapp.local.yml.tpl similarity index 100% rename from templates/js/notification-restify/teamsapp.local.yml.tpl rename to templates/js/notification-express/teamsapp.local.yml.tpl diff --git a/templates/js/notification-restify/teamsapp.testtool.yml b/templates/js/notification-express/teamsapp.testtool.yml similarity index 100% rename from templates/js/notification-restify/teamsapp.testtool.yml rename to templates/js/notification-express/teamsapp.testtool.yml diff --git a/templates/js/notification-restify/teamsapp.yml.tpl b/templates/js/notification-express/teamsapp.yml.tpl similarity index 100% rename from templates/js/notification-restify/teamsapp.yml.tpl rename to templates/js/notification-express/teamsapp.yml.tpl diff --git a/templates/js/notification-restify/web.config b/templates/js/notification-express/web.config similarity index 100% rename from templates/js/notification-restify/web.config rename to templates/js/notification-express/web.config diff --git a/templates/js/notification-http-timer-trigger/README.md.tpl b/templates/js/notification-http-timer-trigger/README.md.tpl index 153ef48f6e..6bff7f24cf 100644 --- a/templates/js/notification-http-timer-trigger/README.md.tpl +++ b/templates/js/notification-http-timer-trigger/README.md.tpl @@ -11,7 +11,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/notification-http-timer-trigger/appPackage/manifest.json.tpl b/templates/js/notification-http-timer-trigger/appPackage/manifest.json.tpl index 60f6f4e8f5..66ce18c02c 100644 --- a/templates/js/notification-http-timer-trigger/appPackage/manifest.json.tpl +++ b/templates/js/notification-http-timer-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/notification-http-timer-trigger/package.json.tpl b/templates/js/notification-http-timer-trigger/package.json.tpl index ba2a726137..839ae8c333 100644 --- a/templates/js/notification-http-timer-trigger/package.json.tpl +++ b/templates/js/notification-http-timer-trigger/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Notification Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -22,9 +22,9 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1" }, "devDependencies": { "azurite": "^3.16.0", diff --git a/templates/js/notification-http-trigger/README.md.tpl b/templates/js/notification-http-trigger/README.md.tpl index 6704134bdf..c45a8c19de 100644 --- a/templates/js/notification-http-trigger/README.md.tpl +++ b/templates/js/notification-http-trigger/README.md.tpl @@ -11,7 +11,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/notification-http-trigger/appPackage/manifest.json.tpl b/templates/js/notification-http-trigger/appPackage/manifest.json.tpl index 60f6f4e8f5..66ce18c02c 100644 --- a/templates/js/notification-http-trigger/appPackage/manifest.json.tpl +++ b/templates/js/notification-http-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/notification-http-trigger/package.json.tpl b/templates/js/notification-http-trigger/package.json.tpl index ba2a726137..839ae8c333 100644 --- a/templates/js/notification-http-trigger/package.json.tpl +++ b/templates/js/notification-http-trigger/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Notification Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -22,9 +22,9 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1" }, "devDependencies": { "azurite": "^3.16.0", diff --git a/templates/js/notification-timer-trigger/README.md.tpl b/templates/js/notification-timer-trigger/README.md.tpl index 1acb4ea2a4..572c78b8cb 100644 --- a/templates/js/notification-timer-trigger/README.md.tpl +++ b/templates/js/notification-timer-trigger/README.md.tpl @@ -12,7 +12,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/js/notification-timer-trigger/appPackage/manifest.json.tpl b/templates/js/notification-timer-trigger/appPackage/manifest.json.tpl index 60f6f4e8f5..66ce18c02c 100644 --- a/templates/js/notification-timer-trigger/appPackage/manifest.json.tpl +++ b/templates/js/notification-timer-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/notification-timer-trigger/package.json.tpl b/templates/js/notification-timer-trigger/package.json.tpl index ba2a726137..839ae8c333 100644 --- a/templates/js/notification-timer-trigger/package.json.tpl +++ b/templates/js/notification-timer-trigger/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Notification Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -22,9 +22,9 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1" }, "devDependencies": { "azurite": "^3.16.0", diff --git a/templates/js/sso-tab-with-obo-flow/api/README.md b/templates/js/sso-tab-with-obo-flow/api/README.md index facb4a693d..0c0bc97fb2 100644 --- a/templates/js/sso-tab-with-obo-flow/api/README.md +++ b/templates/js/sso-tab-with-obo-flow/api/README.md @@ -4,7 +4,7 @@ Azure Functions are a great way to add server-side behaviors to any Teams applic ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - A Microsoft 365 account. If you do not have Microsoft 365 account, apply one from [Microsoft 365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -70,7 +70,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | :----------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the command palette and select: `Teams: Provision`.
  • Open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision`.
  • Run command `teamsapp deploy`.
| diff --git a/templates/js/sso-tab-with-obo-flow/api/package.json b/templates/js/sso-tab-with-obo-flow/api/package.json index 8d3afc1f33..7191eabe6d 100644 --- a/templates/js/sso-tab-with-obo-flow/api/package.json +++ b/templates/js/sso-tab-with-obo-flow/api/package.json @@ -13,7 +13,7 @@ }, "dependencies": { "@azure/functions": "^4.0.0", - "@microsoft/teamsfx": "^2.0.0", + "@microsoft/teamsfx": "^3.0.0-alpha", "@microsoft/microsoft-graph-client": "^3.0.1", "isomorphic-fetch": "^3.0.0" }, diff --git a/templates/js/sso-tab-with-obo-flow/appPackage/manifest.json.tpl b/templates/js/sso-tab-with-obo-flow/appPackage/manifest.json.tpl index c72a4e3223..22558e84a9 100644 --- a/templates/js/sso-tab-with-obo-flow/appPackage/manifest.json.tpl +++ b/templates/js/sso-tab-with-obo-flow/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/sso-tab-with-obo-flow/package.json.tpl b/templates/js/sso-tab-with-obo-flow/package.json.tpl index a7f23ec715..724aaa07f7 100644 --- a/templates/js/sso-tab-with-obo-flow/package.json.tpl +++ b/templates/js/sso-tab-with-obo-flow/package.json.tpl @@ -7,10 +7,10 @@ "type": "module", "private": true, "dependencies": { - "@fluentui/react-components": "^9.18.0", + "@fluentui/react-components": "^9.55.1", "@microsoft/teams-js": "^2.22.0", - "@microsoft/teamsfx": "^2.2.0", - "@microsoft/teamsfx-react": "^3.0.0", + "@microsoft/teamsfx": "^3.0.0-alpha", + "@microsoft/teamsfx-react": "^4.0.0-alpha", "axios": "^0.21.1", "react": "^18.2.0", "react-dom": "^18.2.0", diff --git a/templates/js/sso-tab-with-obo-flow/teamsapp.yml.tpl b/templates/js/sso-tab-with-obo-flow/teamsapp.yml.tpl index 7d453c65ac..7b7106a5d9 100644 --- a/templates/js/sso-tab-with-obo-flow/teamsapp.yml.tpl +++ b/templates/js/sso-tab-with-obo-flow/teamsapp.yml.tpl @@ -132,10 +132,10 @@ deploy: with: args: run build --if-present env: - REACT_APP_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - REACT_APP_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html - REACT_APP_FUNC_NAME: getUserProfile - REACT_APP_FUNC_ENDPOINT: ${{API_FUNCTION_ENDPOINT}} + VITE_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} + VITE_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html + VITE_FUNC_NAME: getUserProfile + VITE_FUNC_ENDPOINT: ${{API_FUNCTION_ENDPOINT}} # Deploy bits to Azure Static Web Apps - uses: cli/runNpxCommand name: deploy to Azure Static Web Apps diff --git a/templates/js/workflow/.vscode/tasks.json b/templates/js/workflow/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/js/workflow/.vscode/tasks.json +++ b/templates/js/workflow/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/js/workflow/README.md.tpl b/templates/js/workflow/README.md.tpl index 70900d996a..90e2c09d4b 100644 --- a/templates/js/workflow/README.md.tpl +++ b/templates/js/workflow/README.md.tpl @@ -10,7 +10,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the workflow bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} @@ -74,7 +74,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | - | - | -| `src/index.js`| Application entry point and `restify` handlers for the Workflow bot | +| `src/index.js`| Application entry point and `express` handlers for the Workflow bot | | `src/teamsBot.js` | An empty teams activity handler for bot customization | | `src/commands/helloworldCommandHandler.js` | Implementation that handles responding to a chat command | | `src/adaptiveCards/helloworldCommandResponse.json` | Defines the Adaptive Card (UI) that is displayed in response to a chat command | diff --git a/templates/js/workflow/appPackage/manifest.json.tpl b/templates/js/workflow/appPackage/manifest.json.tpl index cf2bbc13dc..84ea23d920 100644 --- a/templates/js/workflow/appPackage/manifest.json.tpl +++ b/templates/js/workflow/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/js/workflow/package.json.tpl b/templates/js/workflow/package.json.tpl index e923d5e4d8..42934c289c 100644 --- a/templates/js/workflow/package.json.tpl +++ b/templates/js/workflow/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Workflow Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,13 +23,13 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { "env-cmd": "^10.1.0", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/js/workflow/src/cardActions/doStuffActionHandler.js b/templates/js/workflow/src/cardActions/doStuffActionHandler.js index e911d03611..7152d71b60 100644 --- a/templates/js/workflow/src/cardActions/doStuffActionHandler.js +++ b/templates/js/workflow/src/cardActions/doStuffActionHandler.js @@ -13,11 +13,12 @@ class DoStuffActionHandler { /** * You can send an adaptive card to respond to the card action invoke. */ - const cardData = { - title: "Hello World Bot", - body: "Congratulations! Your task is processed successfully.", - }; - const cardJson = new ACData.Template(responseCard).expand({ $root: cardData }); + const cardJson = new ACData.Template(responseCard).expand({ + $root: { + title: "Hello World Bot", + body: "Congratulations! Your task is processed successfully.", + }, + }); return InvokeResponseFactory.adaptiveCard(cardJson); /** diff --git a/templates/js/workflow/src/commands/helloworldCommandHandler.js b/templates/js/workflow/src/commands/helloworldCommandHandler.js index acb9bd0511..ec61cae113 100644 --- a/templates/js/workflow/src/commands/helloworldCommandHandler.js +++ b/templates/js/workflow/src/commands/helloworldCommandHandler.js @@ -8,13 +8,12 @@ class HelloWorldCommandHandler { async handleCommandReceived(context, message) { console.log(`Bot received message: ${message.text}`); - // render your adaptive card for reply message - const cardData = { - title: "Your Hello World Bot is Running", - body: "Congratulations! Your hello world bot is running. Click the button below to trigger an action.", - }; - - const cardJson = new ACData.Template(helloWorldCard).expand({ $root: cardData }); + const cardJson = new ACData.Template(helloWorldCard).expand({ + $root: { + title: "Your Hello World Bot is Running", + body: "Congratulations! Your hello world bot is running. Click the button below to trigger an action.", + }, + }); return MessageFactory.attachment(CardFactory.adaptiveCard(cardJson)); } } diff --git a/templates/js/workflow/src/index.js b/templates/js/workflow/src/index.js index 4195f8dc0e..22f0eee8d2 100644 --- a/templates/js/workflow/src/index.js +++ b/templates/js/workflow/src/index.js @@ -1,24 +1,25 @@ // Create HTTP server. -const restify = require("restify"); +const express = require("express"); const { workflowApp } = require("./internal/initialize"); const { TeamsBot } = require("./teamsBot"); -// This template uses `restify` to serve HTTP responses. -// Create a restify server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nApp Started, ${server.name} listening to ${server.url}`); +// This template uses `express` to serve HTTP responses. +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Register an API endpoint with `restify`. Teams sends messages to your application +// Register an API endpoint with `express`. Teams sends messages to your application // through this endpoint. // // The Teams Toolkit bot registration configures the bot with `/api/messages` as the // Bot Framework endpoint. If you customize this route, update the Bot registration // in `templates/azure/provision/botservice.bicep`. const teamsBot = new TeamsBot(); -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await workflowApp.requestHandler(req, res, async (context) => { await teamsBot.run(context); }); diff --git a/templates/package.json b/templates/package.json index 8a1ae044e3..64d73d1020 100644 --- a/templates/package.json +++ b/templates/package.json @@ -6,10 +6,6 @@ "scripts": { "check-sensitive": "npx eslint --plugin 'no-secrets' --cache --ignore-pattern 'package.json' --ignore-pattern 'package-lock.json'", "precommit": "npm run check-sensitive && lint-staged", - "verify": "node ./scripts/yamlSolver.js verify", - "apply": "node ./scripts/yamlSolver.js apply", - "watch": "node ./scripts/watch.js", - "init": "node ./scripts/yamlSolver init", "upgrade-schema": "node ./scripts/yamlSolver upgrade-schema", "build": "node ./scripts/generateZip.js && node ./scripts/distributeZip.js", "version": "bash ../.github/scripts/pkg-version.sh template-sync && bash ../.github/scripts/pkg-version.sh core-template", @@ -23,7 +19,7 @@ "js/non-sso-tab-default-bot", "js/notification-http-timer-trigger", "js/notification-http-trigger", - "js/notification-restify", + "js/notification-express", "js/notification-timer-trigger", "js/workflow", "js/sso-tab-with-obo-flow", @@ -34,7 +30,7 @@ "ts/non-sso-tab-default-bot", "ts/notification-http-timer-trigger", "ts/notification-http-trigger", - "ts/notification-restify", + "ts/notification-express", "ts/notification-timer-trigger", "ts/workflow", "ts/sso-tab-with-obo-flow" diff --git a/templates/python/custom-copilot-assistant-assistants-api/.vscode/launch.json b/templates/python/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl similarity index 69% rename from templates/python/custom-copilot-assistant-assistants-api/.vscode/launch.json rename to templates/python/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl index a0c18a24f4..813d217530 100644 --- a/templates/python/custom-copilot-assistant-assistants-api/.vscode/launch.json +++ b/templates/python/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl @@ -7,8 +7,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 + "group": "1-Teams", + "order": 4 }, "internalConsoleOptions": "neverOpen" }, @@ -18,8 +18,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 + "group": "1-Teams", + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -29,8 +29,8 @@ "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 + "group": "1-Teams", + "order": 6 }, "internalConsoleOptions": "neverOpen" }, @@ -75,6 +75,30 @@ "cwd": "${workspaceFolder}", "console": "integratedTerminal", "internalConsoleOptions": "neverOpen" + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -84,7 +108,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 1 }, "stopAll": true @@ -95,7 +119,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 2 }, "stopAll": true @@ -105,7 +129,7 @@ "configurations": ["Start Python"], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 3 }, "stopAll": true @@ -125,6 +149,30 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": ["Launch Remote in Copilot (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": ["Launch Remote in Copilot (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/python/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl b/templates/python/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl index 523d3bc11f..62afc0eca5 100644 --- a/templates/python/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl +++ b/templates/python/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": " https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/python/custom-copilot-assistant-assistants-api/src/bot.py.tpl b/templates/python/custom-copilot-assistant-assistants-api/src/bot.py.tpl index 2372759869..6e4233e1ef 100644 --- a/templates/python/custom-copilot-assistant-assistants-api/src/bot.py.tpl +++ b/templates/python/custom-copilot-assistant-assistants-api/src/bot.py.tpl @@ -1,6 +1,7 @@ import os import sys import traceback +import json from typing import Any, Dict, Optional from botbuilder.core import MemoryStorage, TurnContext @@ -35,7 +36,7 @@ bot_app = Application[TurnState]( bot_app_id=config.APP_ID, storage=storage, adapter=TeamsAdapter(config), - ai=AIOptions(planner=planner), + ai=AIOptions(planner=planner, enable_feedback_loop=True), ) ) @@ -76,4 +77,9 @@ async def on_error(context: TurnContext, error: Exception): traceback.print_exc() # Send a message to the user - await context.send_activity("The bot encountered an error or bug.") \ No newline at end of file + await context.send_activity("The bot encountered an error or bug.") + +@bot_app.feedback_loop() +async def feedback_loop(_context: TurnContext, _state: TurnState, feedback_loop_data: FeedbackLoopData): + # Add custom feedback process logic here. + print(f"Your feedback is:\n{json.dumps(asdict(feedback_loop_data), indent=4)}") \ No newline at end of file diff --git a/templates/python/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl b/templates/python/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl index be6835e737..f1a707bce2 100644 --- a/templates/python/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl +++ b/templates/python/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -65,6 +69,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} deploy: # Generate runtime environment variables diff --git a/templates/python/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl b/templates/python/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl index 493c539d33..c11e25f91c 100644 --- a/templates/python/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl +++ b/templates/python/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl @@ -57,11 +57,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -69,11 +71,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -81,6 +85,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -100,11 +115,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -112,11 +129,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/python/custom-copilot-assistant-new/.vscode/launch.json b/templates/python/custom-copilot-assistant-new/.vscode/launch.json deleted file mode 100644 index ec88b37202..0000000000 --- a/templates/python/custom-copilot-assistant-new/.vscode/launch.json +++ /dev/null @@ -1,131 +0,0 @@ -{ - "version": "0.2.0", - "configurations": [ - { - "name": "Launch Remote (Edge)", - "type": "msedge", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "3-remote", - "order": 1 - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch Remote (Chrome)", - "type": "chrome", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "3-remote", - "order": 2 - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch Remote (Desktop)", - "type": "node", - "request": "launch", - "preLaunchTask": "Start Teams App in Desktop Client (Remote)", - "presentation": { - "group": "3-remote", - "order": 3 - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch App (Edge)", - "type": "msedge", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "all", - "hidden": true - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch App (Chrome)", - "type": "chrome", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "all", - "hidden": true - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Start Python", - "type": "debugpy", - "request": "launch", - "program": "${workspaceFolder}/src/app.py", - "cwd": "${workspaceFolder}/src", - "console": "integratedTerminal" - }, - { - "name": "Start Test Tool", - "type": "node", - "request": "launch", - "program": "${workspaceFolder}/devTools/teamsapptester/node_modules/@microsoft/teams-app-test-tool/cli.js", - "args": [ - "start" - ], - "cwd": "${workspaceFolder}", - "console": "integratedTerminal", - "internalConsoleOptions": "neverOpen" - } - ], - "compounds": [ - { - "name": "Debug in Teams (Edge)", - "configurations": ["Launch App (Edge)", "Start Python"], - "cascadeTerminateToConfigurations": ["Start Python"], - "preLaunchTask": "Start Teams App Locally", - "presentation": { - "group": "1-local", - "order": 1 - }, - "stopAll": true - }, - { - "name": "Debug in Teams (Chrome)", - "configurations": ["Launch App (Chrome)", "Start Python"], - "cascadeTerminateToConfigurations": ["Start Python"], - "preLaunchTask": "Start Teams App Locally", - "presentation": { - "group": "1-local", - "order": 2 - }, - "stopAll": true - }, - { - "name": "Debug in Teams (Desktop)", - "configurations": ["Start Python"], - "preLaunchTask": "Start Teams App in Desktop Client", - "presentation": { - "group": "1-local", - "order": 3 - }, - "stopAll": true - }, - { - "name": "Debug in Test Tool", - "configurations": [ - "Start Python", - "Start Test Tool" - ], - "cascadeTerminateToConfigurations": [ - "Start Test Tool" - ], - "preLaunchTask": "Deploy (Test Tool)", - "presentation": { - "group": "2-local", - "order": 1 - }, - "stopAll": true - } - ] - } - \ No newline at end of file diff --git a/templates/python/custom-copilot-rag-customize/.vscode/launch.json b/templates/python/custom-copilot-assistant-new/.vscode/launch.json.tpl similarity index 69% rename from templates/python/custom-copilot-rag-customize/.vscode/launch.json rename to templates/python/custom-copilot-assistant-new/.vscode/launch.json.tpl index a0c18a24f4..813d217530 100644 --- a/templates/python/custom-copilot-rag-customize/.vscode/launch.json +++ b/templates/python/custom-copilot-assistant-new/.vscode/launch.json.tpl @@ -7,8 +7,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 + "group": "1-Teams", + "order": 4 }, "internalConsoleOptions": "neverOpen" }, @@ -18,8 +18,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 + "group": "1-Teams", + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -29,8 +29,8 @@ "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 + "group": "1-Teams", + "order": 6 }, "internalConsoleOptions": "neverOpen" }, @@ -75,6 +75,30 @@ "cwd": "${workspaceFolder}", "console": "integratedTerminal", "internalConsoleOptions": "neverOpen" + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -84,7 +108,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 1 }, "stopAll": true @@ -95,7 +119,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 2 }, "stopAll": true @@ -105,7 +129,7 @@ "configurations": ["Start Python"], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 3 }, "stopAll": true @@ -125,6 +149,30 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": ["Launch Remote in Copilot (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": ["Launch Remote in Copilot (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/python/custom-copilot-assistant-new/appPackage/manifest.json.tpl b/templates/python/custom-copilot-assistant-new/appPackage/manifest.json.tpl index ee2c11b39f..53f241979a 100644 --- a/templates/python/custom-copilot-assistant-new/appPackage/manifest.json.tpl +++ b/templates/python/custom-copilot-assistant-new/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": " https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/python/custom-copilot-assistant-new/src/bot.py.tpl b/templates/python/custom-copilot-assistant-new/src/bot.py.tpl index 8a2b7c3278..444c020b5f 100644 --- a/templates/python/custom-copilot-assistant-new/src/bot.py.tpl +++ b/templates/python/custom-copilot-assistant-new/src/bot.py.tpl @@ -1,6 +1,7 @@ import os import sys import traceback +import json from typing import Any, Dict, Optional from botbuilder.core import MemoryStorage, TurnContext @@ -51,7 +52,7 @@ bot_app = Application[AppTurnState]( bot_app_id=config.APP_ID, storage=storage, adapter=TeamsAdapter(config), - ai=AIOptions(planner=planner), + ai=AIOptions(planner=planner, enable_feedback_loop=True), ) ) @@ -87,4 +88,9 @@ async def on_error(context: TurnContext, error: Exception): traceback.print_exc() # Send a message to the user - await context.send_activity("The bot encountered an error or bug.") \ No newline at end of file + await context.send_activity("The bot encountered an error or bug.") + +@bot_app.feedback_loop() +async def feedback_loop(_context: TurnContext, _state: TurnState, feedback_loop_data: FeedbackLoopData): + # Add custom feedback process logic here. + print(f"Your feedback is:\n{json.dumps(asdict(feedback_loop_data), indent=4)}") \ No newline at end of file diff --git a/templates/python/custom-copilot-assistant-new/teamsapp.local.yml.tpl b/templates/python/custom-copilot-assistant-new/teamsapp.local.yml.tpl index 7b6c4ba3b5..f65919fdf6 100644 --- a/templates/python/custom-copilot-assistant-new/teamsapp.local.yml.tpl +++ b/templates/python/custom-copilot-assistant-new/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -65,6 +69,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} deploy: # Generate runtime environment variables diff --git a/templates/python/custom-copilot-assistant-new/teamsapp.yml.tpl b/templates/python/custom-copilot-assistant-new/teamsapp.yml.tpl index ded62fa350..bb0b58d78d 100644 --- a/templates/python/custom-copilot-assistant-new/teamsapp.yml.tpl +++ b/templates/python/custom-copilot-assistant-new/teamsapp.yml.tpl @@ -57,11 +57,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -69,11 +71,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -81,6 +85,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsfx deploy' is executed deploy: @@ -100,11 +115,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -112,11 +129,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/python/custom-copilot-basic/.vscode/launch.json b/templates/python/custom-copilot-basic/.vscode/launch.json.tpl similarity index 69% rename from templates/python/custom-copilot-basic/.vscode/launch.json rename to templates/python/custom-copilot-basic/.vscode/launch.json.tpl index a0c18a24f4..813d217530 100644 --- a/templates/python/custom-copilot-basic/.vscode/launch.json +++ b/templates/python/custom-copilot-basic/.vscode/launch.json.tpl @@ -7,8 +7,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 + "group": "1-Teams", + "order": 4 }, "internalConsoleOptions": "neverOpen" }, @@ -18,8 +18,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 + "group": "1-Teams", + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -29,8 +29,8 @@ "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 + "group": "1-Teams", + "order": 6 }, "internalConsoleOptions": "neverOpen" }, @@ -75,6 +75,30 @@ "cwd": "${workspaceFolder}", "console": "integratedTerminal", "internalConsoleOptions": "neverOpen" + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -84,7 +108,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 1 }, "stopAll": true @@ -95,7 +119,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 2 }, "stopAll": true @@ -105,7 +129,7 @@ "configurations": ["Start Python"], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 3 }, "stopAll": true @@ -125,6 +149,30 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": ["Launch Remote in Copilot (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": ["Launch Remote in Copilot (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/python/custom-copilot-basic/appPackage/manifest.json.tpl b/templates/python/custom-copilot-basic/appPackage/manifest.json.tpl index bd84c2cacf..7ff52e2d56 100644 --- a/templates/python/custom-copilot-basic/appPackage/manifest.json.tpl +++ b/templates/python/custom-copilot-basic/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": " https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", @@ -40,7 +57,7 @@ "commands": [ { "title": "How can you help me?", - "description": "A sample prompt" + "description": "How can you help me?" }, { "title": "How to develop TeamsToolkit app?", diff --git a/templates/python/custom-copilot-basic/src/bot.py.tpl b/templates/python/custom-copilot-basic/src/bot.py.tpl index 1acb0a8275..7686349038 100644 --- a/templates/python/custom-copilot-basic/src/bot.py.tpl +++ b/templates/python/custom-copilot-basic/src/bot.py.tpl @@ -1,5 +1,6 @@ import os import sys +import json import traceback from dataclasses import asdict diff --git a/templates/python/custom-copilot-basic/teamsapp.local.yml.tpl b/templates/python/custom-copilot-basic/teamsapp.local.yml.tpl index 7b6c4ba3b5..f65919fdf6 100644 --- a/templates/python/custom-copilot-basic/teamsapp.local.yml.tpl +++ b/templates/python/custom-copilot-basic/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -65,6 +69,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} deploy: # Generate runtime environment variables diff --git a/templates/python/custom-copilot-basic/teamsapp.yml.tpl b/templates/python/custom-copilot-basic/teamsapp.yml.tpl index ded62fa350..bb0b58d78d 100644 --- a/templates/python/custom-copilot-basic/teamsapp.yml.tpl +++ b/templates/python/custom-copilot-basic/teamsapp.yml.tpl @@ -57,11 +57,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -69,11 +71,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -81,6 +85,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsfx deploy' is executed deploy: @@ -100,11 +115,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -112,11 +129,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/python/custom-copilot-rag-azure-ai-search/.vscode/launch.json b/templates/python/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl similarity index 69% rename from templates/python/custom-copilot-rag-azure-ai-search/.vscode/launch.json rename to templates/python/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl index a0c18a24f4..813d217530 100644 --- a/templates/python/custom-copilot-rag-azure-ai-search/.vscode/launch.json +++ b/templates/python/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl @@ -7,8 +7,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 + "group": "1-Teams", + "order": 4 }, "internalConsoleOptions": "neverOpen" }, @@ -18,8 +18,8 @@ "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 + "group": "1-Teams", + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -29,8 +29,8 @@ "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 + "group": "1-Teams", + "order": 6 }, "internalConsoleOptions": "neverOpen" }, @@ -75,6 +75,30 @@ "cwd": "${workspaceFolder}", "console": "integratedTerminal", "internalConsoleOptions": "neverOpen" + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -84,7 +108,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 1 }, "stopAll": true @@ -95,7 +119,7 @@ "cascadeTerminateToConfigurations": ["Start Python"], "preLaunchTask": "Start Teams App Locally", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 2 }, "stopAll": true @@ -105,7 +129,7 @@ "configurations": ["Start Python"], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "1-local", + "group": "1-Teams", "order": 3 }, "stopAll": true @@ -125,6 +149,30 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": ["Launch Remote in Copilot (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": ["Launch Remote in Copilot (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/python/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl b/templates/python/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl index 24691b562f..7864fcc2b2 100644 --- a/templates/python/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl +++ b/templates/python/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": " https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/python/custom-copilot-rag-azure-ai-search/src/bot.py.tpl b/templates/python/custom-copilot-rag-azure-ai-search/src/bot.py.tpl index 10a4eacb80..52547a7601 100644 --- a/templates/python/custom-copilot-rag-azure-ai-search/src/bot.py.tpl +++ b/templates/python/custom-copilot-rag-azure-ai-search/src/bot.py.tpl @@ -65,7 +65,7 @@ bot_app = Application[TurnState]( bot_app_id=config.APP_ID, storage=storage, adapter=TeamsAdapter(config), - ai=AIOptions(planner=planner), + ai=AIOptions(planner=planner, enable_feedback_loop=True), ) ) @@ -78,4 +78,9 @@ async def on_error(context: TurnContext, error: Exception): traceback.print_exc() # Send a message to the user - await context.send_activity("The bot encountered an error or bug.") \ No newline at end of file + await context.send_activity("The bot encountered an error or bug.") + +@bot_app.feedback_loop() +async def feedback_loop(_context: TurnContext, _state: TurnState, feedback_loop_data: FeedbackLoopData): + # Add custom feedback process logic here. + print(f"Your feedback is:\n{json.dumps(asdict(feedback_loop_data), indent=4)}") \ No newline at end of file diff --git a/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl b/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl index d186323670..fd4f37f5fb 100644 --- a/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl +++ b/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -65,6 +69,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} deploy: # Generate runtime environment variables diff --git a/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl b/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl index 34b81201e5..ecedb91eed 100644 --- a/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl +++ b/templates/python/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl @@ -57,11 +57,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -69,11 +71,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -81,6 +85,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsfx deploy' is executed deploy: @@ -100,11 +115,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -112,11 +129,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/python/custom-copilot-rag-custom-api/.vscode/launch.json b/templates/python/custom-copilot-rag-custom-api/.vscode/launch.json deleted file mode 100644 index 4ad28db3b2..0000000000 --- a/templates/python/custom-copilot-rag-custom-api/.vscode/launch.json +++ /dev/null @@ -1,130 +0,0 @@ -{ - "version": "0.2.0", - "configurations": [ - { - "name": "Launch Remote (Edge)", - "type": "msedge", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "3-remote", - "order": 1 - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch Remote (Chrome)", - "type": "chrome", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "3-remote", - "order": 2 - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch Remote (Desktop)", - "type": "node", - "request": "launch", - "preLaunchTask": "Start Teams App in Desktop Client (Remote)", - "presentation": { - "group": "3-remote", - "order": 3 - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch App (Edge)", - "type": "msedge", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "all", - "hidden": true - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Launch App (Chrome)", - "type": "chrome", - "request": "launch", - "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", - "presentation": { - "group": "all", - "hidden": true - }, - "internalConsoleOptions": "neverOpen" - }, - { - "name": "Start Python", - "type": "debugpy", - "request": "launch", - "program": "${workspaceFolder}/src/app.py", - "cwd": "${workspaceFolder}/src", - "console": "integratedTerminal" - }, - { - "name": "Start Test Tool", - "type": "node", - "request": "launch", - "program": "${workspaceFolder}/devTools/teamsapptester/node_modules/@microsoft/teams-app-test-tool/cli.js", - "args": [ - "start" - ], - "cwd": "${workspaceFolder}", - "console": "integratedTerminal", - "internalConsoleOptions": "neverOpen" - } - ], - "compounds": [ - { - "name": "Debug in Teams (Edge)", - "configurations": ["Launch App (Edge)", "Start Python"], - "cascadeTerminateToConfigurations": ["Start Python"], - "preLaunchTask": "Start Teams App Locally", - "presentation": { - "group": "1-local", - "order": 1 - }, - "stopAll": true - }, - { - "name": "Debug in Teams (Chrome)", - "configurations": ["Launch App (Chrome)", "Start Python"], - "cascadeTerminateToConfigurations": ["Start Python"], - "preLaunchTask": "Start Teams App Locally", - "presentation": { - "group": "1-local", - "order": 2 - }, - "stopAll": true - }, - { - "name": "Debug in Teams (Desktop)", - "configurations": ["Start Python"], - "preLaunchTask": "Start Teams App in Desktop Client", - "presentation": { - "group": "1-local", - "order": 3 - }, - "stopAll": true - }, - { - "name": "Debug in Test Tool", - "configurations": [ - "Start Python", - "Start Test Tool" - ], - "cascadeTerminateToConfigurations": [ - "Start Test Tool" - ], - "preLaunchTask": "Deploy (Test Tool)", - "presentation": { - "group": "2-local", - "order": 1 - }, - "stopAll": true - } - ] -} \ No newline at end of file diff --git a/templates/python/custom-copilot-rag-custom-api/.vscode/launch.json.tpl b/templates/python/custom-copilot-rag-custom-api/.vscode/launch.json.tpl new file mode 100644 index 0000000000..813d217530 --- /dev/null +++ b/templates/python/custom-copilot-rag-custom-api/.vscode/launch.json.tpl @@ -0,0 +1,178 @@ +{ + "version": "0.2.0", + "configurations": [ + { + "name": "Launch Remote (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "1-Teams", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "1-Teams", + "order": 5 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote (Desktop)", + "type": "node", + "request": "launch", + "preLaunchTask": "Start Teams App in Desktop Client (Remote)", + "presentation": { + "group": "1-Teams", + "order": 6 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch App (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "all", + "hidden": true + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch App (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "all", + "hidden": true + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Start Python", + "type": "debugpy", + "request": "launch", + "program": "${workspaceFolder}/src/app.py", + "cwd": "${workspaceFolder}/src", + "console": "integratedTerminal" + }, + { + "name": "Start Test Tool", + "type": "node", + "request": "launch", + "program": "${workspaceFolder}/devTools/teamsapptester/node_modules/@microsoft/teams-app-test-tool/cli.js", + "args": [ + "start" + ], + "cwd": "${workspaceFolder}", + "console": "integratedTerminal", + "internalConsoleOptions": "neverOpen" + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} + } + ], + "compounds": [ + { + "name": "Debug in Teams (Edge)", + "configurations": ["Launch App (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "1-Teams", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Teams (Chrome)", + "configurations": ["Launch App (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "1-Teams", + "order": 2 + }, + "stopAll": true + }, + { + "name": "Debug in Teams (Desktop)", + "configurations": ["Start Python"], + "preLaunchTask": "Start Teams App in Desktop Client", + "presentation": { + "group": "1-Teams", + "order": 3 + }, + "stopAll": true + }, + { + "name": "Debug in Test Tool", + "configurations": [ + "Start Python", + "Start Test Tool" + ], + "cascadeTerminateToConfigurations": [ + "Start Test Tool" + ], + "preLaunchTask": "Deploy (Test Tool)", + "presentation": { + "group": "2-local", + "order": 1 + }, + "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": ["Launch Remote in Copilot (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": ["Launch Remote in Copilot (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} + } + ] +} diff --git a/templates/python/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl b/templates/python/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl index 24691b562f..7864fcc2b2 100644 --- a/templates/python/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl +++ b/templates/python/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": " https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/python/custom-copilot-rag-custom-api/teamsapp.local.yml.tpl b/templates/python/custom-copilot-rag-custom-api/teamsapp.local.yml.tpl index 4ce626f09a..cd03e45ea4 100644 --- a/templates/python/custom-copilot-rag-custom-api/teamsapp.local.yml.tpl +++ b/templates/python/custom-copilot-rag-custom-api/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -65,6 +69,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} deploy: # Generate runtime environment variables diff --git a/templates/python/custom-copilot-rag-custom-api/teamsapp.yml.tpl b/templates/python/custom-copilot-rag-custom-api/teamsapp.yml.tpl index dd0c167375..bfa59110da 100644 --- a/templates/python/custom-copilot-rag-custom-api/teamsapp.yml.tpl +++ b/templates/python/custom-copilot-rag-custom-api/teamsapp.yml.tpl @@ -57,11 +57,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -69,11 +71,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -81,6 +85,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsfx deploy' is executed deploy: @@ -100,11 +115,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -112,11 +129,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/python/custom-copilot-rag-customize/.vscode/launch.json.tpl b/templates/python/custom-copilot-rag-customize/.vscode/launch.json.tpl new file mode 100644 index 0000000000..813d217530 --- /dev/null +++ b/templates/python/custom-copilot-rag-customize/.vscode/launch.json.tpl @@ -0,0 +1,178 @@ +{ + "version": "0.2.0", + "configurations": [ + { + "name": "Launch Remote (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "1-Teams", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "1-Teams", + "order": 5 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote (Desktop)", + "type": "node", + "request": "launch", + "preLaunchTask": "Start Teams App in Desktop Client (Remote)", + "presentation": { + "group": "1-Teams", + "order": 6 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch App (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "all", + "hidden": true + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch App (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://teams.microsoft.com/l/app/${{local:TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", + "presentation": { + "group": "all", + "hidden": true + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Start Python", + "type": "debugpy", + "request": "launch", + "program": "${workspaceFolder}/src/app.py", + "cwd": "${workspaceFolder}/src", + "console": "integratedTerminal" + }, + { + "name": "Start Test Tool", + "type": "node", + "request": "launch", + "program": "${workspaceFolder}/devTools/teamsapptester/node_modules/@microsoft/teams-app-test-tool/cli.js", + "args": [ + "start" + ], + "cwd": "${workspaceFolder}", + "console": "integratedTerminal", + "internalConsoleOptions": "neverOpen" + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} + } + ], + "compounds": [ + { + "name": "Debug in Teams (Edge)", + "configurations": ["Launch App (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "1-Teams", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Teams (Chrome)", + "configurations": ["Launch App (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "1-Teams", + "order": 2 + }, + "stopAll": true + }, + { + "name": "Debug in Teams (Desktop)", + "configurations": ["Start Python"], + "preLaunchTask": "Start Teams App in Desktop Client", + "presentation": { + "group": "1-Teams", + "order": 3 + }, + "stopAll": true + }, + { + "name": "Debug in Test Tool", + "configurations": [ + "Start Python", + "Start Test Tool" + ], + "cascadeTerminateToConfigurations": [ + "Start Test Tool" + ], + "preLaunchTask": "Deploy (Test Tool)", + "presentation": { + "group": "2-local", + "order": 1 + }, + "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": ["Launch Remote in Copilot (Edge)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": ["Launch Remote in Copilot (Chrome)", "Start Python"], + "cascadeTerminateToConfigurations": ["Start Python"], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} + } + ] +} diff --git a/templates/python/custom-copilot-rag-customize/appPackage/manifest.json.tpl b/templates/python/custom-copilot-rag-customize/appPackage/manifest.json.tpl index 24691b562f..7864fcc2b2 100644 --- a/templates/python/custom-copilot-rag-customize/appPackage/manifest.json.tpl +++ b/templates/python/custom-copilot-rag-customize/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": " https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/python/custom-copilot-rag-customize/src/bot.py.tpl b/templates/python/custom-copilot-rag-customize/src/bot.py.tpl index 84389926da..23e30c54eb 100644 --- a/templates/python/custom-copilot-rag-customize/src/bot.py.tpl +++ b/templates/python/custom-copilot-rag-customize/src/bot.py.tpl @@ -1,7 +1,7 @@ import os import sys import traceback - +import json from botbuilder.core import MemoryStorage, TurnContext from teams import Application, ApplicationOptions, TeamsAdapter from teams.ai import AIOptions @@ -53,7 +53,7 @@ bot_app = Application[TurnState]( bot_app_id=config.APP_ID, storage=storage, adapter=TeamsAdapter(config), - ai=AIOptions(planner=planner), + ai=AIOptions(planner=planner, enable_feedback_loop=True), ) ) @@ -66,4 +66,9 @@ async def on_error(context: TurnContext, error: Exception): traceback.print_exc() # Send a message to the user - await context.send_activity("The bot encountered an error or bug.") \ No newline at end of file + await context.send_activity("The bot encountered an error or bug.") + +@bot_app.feedback_loop() +async def feedback_loop(_context: TurnContext, _state: TurnState, feedback_loop_data: FeedbackLoopData): + # Add custom feedback process logic here. + print(f"Your feedback is:\n{json.dumps(asdict(feedback_loop_data), indent=4)}") \ No newline at end of file diff --git a/templates/python/custom-copilot-rag-customize/teamsapp.local.yml.tpl b/templates/python/custom-copilot-rag-customize/teamsapp.local.yml.tpl index 7af9c63f5c..3fee427043 100644 --- a/templates/python/custom-copilot-rag-customize/teamsapp.local.yml.tpl +++ b/templates/python/custom-copilot-rag-customize/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -65,6 +69,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} deploy: # Generate runtime environment variables diff --git a/templates/python/custom-copilot-rag-customize/teamsapp.yml.tpl b/templates/python/custom-copilot-rag-customize/teamsapp.yml.tpl index 34b81201e5..ecedb91eed 100644 --- a/templates/python/custom-copilot-rag-customize/teamsapp.yml.tpl +++ b/templates/python/custom-copilot-rag-customize/teamsapp.yml.tpl @@ -57,11 +57,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -69,11 +71,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -81,6 +85,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsfx deploy' is executed deploy: @@ -100,11 +115,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -112,11 +129,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/scripts/watch.js b/templates/scripts/watch.js deleted file mode 100644 index 37e60d7768..0000000000 --- a/templates/scripts/watch.js +++ /dev/null @@ -1,123 +0,0 @@ -const { writeFileSync, readFileSync, accessSync, watch, rm } = require("node:fs"); -const { join, basename } = require("node:path"); -const utils = require("./utils"); -const Mustache = require("mustache"); -const { Ext, Path } = require("./constants"); - -const snippetsFolder = Path.YmlSnippets; - -const ac = new AbortController(); -let tempFiles = []; - -function cleanup() { - ac.abort(); - try { - tempFiles.forEach((file) => { - console.log(`Deleting ${file}`); - rm(file, { force: true }, (error) => { - if (error) { - console.log(error.message); - } - }); - }); - } catch {} -} - -function writeTempFile(filepath, content) { - if (!tempFiles.includes(filepath)) { - tempFiles.push(filepath); - } - writeFileSync(filepath, content); -} - -function parseTokens(tokens, result = {}) { - for (const v of tokens) { - if (v[0] === "name") { - result[v[1]] = v[1]; - } - if (v[0] === "#" && !result[v[1]]) { - result[v[1]] = true; - result = { ...result, ...parseTokens(v[4], result) }; - } - } - return result; -} - -function renderVariablesFromTemplates(template) { - const parsed = Mustache.parse(template); - let tokens = JSON.parse(JSON.stringify(parsed)); // deep copy - return parseTokens(tokens); -} - -function loadVariables(varFile, template) { - // load variables from json file if exists - try { - accessSync(varFile); - return JSON.parse(readFileSync(varFile, "utf8")); - } catch (e) { - if (e.name === "SyntaxError") { - console.log(e.message); - return {}; - } - } - // render variables from mustache template if json file does not exist - const variables = renderVariablesFromTemplates(template); - writeTempFile(varFile, JSON.stringify(variables, null, 2)); - return variables; -} - -function previewMustache(mustacheName, dir = snippetsFolder) { - const mustacheFile = join(dir, `${mustacheName}${Ext.Mustache}`); - const varFile = join(dir, `${mustacheName}${Ext.Json}`); - const ymlFile = join(dir, `${mustacheName}${Ext.Yml}`); - - const template = readFileSync(mustacheFile, "utf8"); - if (!template) { - return; - } - const variables = loadVariables(varFile, template); - - const rendered = utils.renderMustache(template, variables); - writeTempFile(ymlFile, rendered); -} - -function handler(eventType, filename) { - if (eventType === "change") { - if (filename?.endsWith(Ext.Mustache)) { - const mustacheName = basename(filename, Ext.Mustache); - previewMustache(mustacheName); - } - if (filename?.endsWith(Ext.Json)) { - const mustacheName = basename(filename, Ext.Json); - previewMustache(mustacheName); - } - } -} - -function debounce(func, delay) { - let timer; - return (...args) => { - clearTimeout(timer); - timer = setTimeout(() => { - func.apply(this, args); - }, delay); - }; -} - -function main() { - try { - console.log(`Watching ${snippetsFolder}`); - watch( - snippetsFolder, - { persistent: true, encoding: "utf8", signal: ac.signal, recursive: false }, - // fs.watch could be triggered twice for a single file change, delay the event handler to avoid duplicate rendering - debounce(handler, 100) - ); - } catch (err) { - console.error(err); - } - - process.on("SIGINT", cleanup); // CTRL+C -} - -main(); diff --git a/templates/ts/ai-assistant-bot/.vscode/tasks.json b/templates/ts/ai-assistant-bot/.vscode/tasks.json index 1c3e241f27..ee29945797 100644 --- a/templates/ts/ai-assistant-bot/.vscode/tasks.json +++ b/templates/ts/ai-assistant-bot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/ts/ai-assistant-bot/README.md.tpl b/templates/ts/ai-assistant-bot/README.md.tpl index 63e0f08809..1fc733407b 100644 --- a/templates/ts/ai-assistant-bot/README.md.tpl +++ b/templates/ts/ai-assistant-bot/README.md.tpl @@ -15,7 +15,7 @@ It showcases how to build an intelligent chat bot in Teams capable of helping us > > To run the AI Assistant Bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/ai-assistant-bot/appPackage/manifest.json.tpl b/templates/ts/ai-assistant-bot/appPackage/manifest.json.tpl index ea7aad4540..b8fb3bed95 100644 --- a/templates/ts/ai-assistant-bot/appPackage/manifest.json.tpl +++ b/templates/ts/ai-assistant-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/ai-assistant-bot/package.json.tpl b/templates/ts/ai-assistant-bot/package.json.tpl index bbda4b843b..485cbe108a 100644 --- a/templates/ts/ai-assistant-bot/package.json.tpl +++ b/templates/ts/ai-assistant-bot/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Assistant Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -28,16 +28,16 @@ }, "dependencies": { "@microsoft/teams-ai": "^1.0.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/ai-assistant-bot/src/index.ts b/templates/ts/ai-assistant-bot/src/index.ts index d9fc3b3d9a..24d21c9448 100644 --- a/templates/ts/ai-assistant-bot/src/index.ts +++ b/templates/ts/ai-assistant-bot/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -48,16 +48,16 @@ const onTurnErrorHandler = async (context, error) => { // Set the onTurnError for the singleton CloudAdapter. adapter.onTurnError = onTurnErrorHandler; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/ai-bot/.vscode/tasks.json b/templates/ts/ai-bot/.vscode/tasks.json index 1c3e241f27..ee29945797 100644 --- a/templates/ts/ai-bot/.vscode/tasks.json +++ b/templates/ts/ai-bot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/ts/ai-bot/README.md.tpl b/templates/ts/ai-bot/README.md.tpl index 875efdc224..b34c31c284 100644 --- a/templates/ts/ai-bot/README.md.tpl +++ b/templates/ts/ai-bot/README.md.tpl @@ -17,7 +17,7 @@ The app template is built using the Teams AI library, which provides the capabil > > To run the AI Chat Bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/ai-bot/appPackage/manifest.json.tpl b/templates/ts/ai-bot/appPackage/manifest.json.tpl index 5f4b526f64..3501e3282c 100644 --- a/templates/ts/ai-bot/appPackage/manifest.json.tpl +++ b/templates/ts/ai-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/ai-bot/package.json.tpl b/templates/ts/ai-bot/package.json.tpl index e5ecde723b..d947c0086a 100644 --- a/templates/ts/ai-bot/package.json.tpl +++ b/templates/ts/ai-bot/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Chat Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -27,16 +27,16 @@ }, "dependencies": { "@microsoft/teams-ai": "^1.0.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/ai-bot/src/index.ts b/templates/ts/ai-bot/src/index.ts index d9fc3b3d9a..24d21c9448 100644 --- a/templates/ts/ai-bot/src/index.ts +++ b/templates/ts/ai-bot/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -48,16 +48,16 @@ const onTurnErrorHandler = async (context, error) => { // Set the onTurnError for the singleton CloudAdapter. adapter.onTurnError = onTurnErrorHandler; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/api-message-extension-sso/.tours/custom-token-validation-without-using-Easy-Auth.tour b/templates/ts/api-message-extension-sso/.tours/custom-token-validation-without-using-Easy-Auth.tour new file mode 100644 index 0000000000..28d37e60ff --- /dev/null +++ b/templates/ts/api-message-extension-sso/.tours/custom-token-validation-without-using-Easy-Auth.tour @@ -0,0 +1,81 @@ +{ + "$schema": "https://aka.ms/codetour-schema", + "title": "custom-token-validation-without-using-Easy-Auth", + "steps": [ + { + "file": "src/functions/repair.ts", + "selection": { + "start": { + "line": 55, + "character": 3 + }, + "end": { + "line": 55, + "character": 26 + } + }, + "description": "The reason for custom token validation is that Azure Function Core Tools do not support authentication when running locally. This template is designed to demonstrate local debugging of authentication functionalities in the API Message Extension. Therefore, this approach was taken. In production, you should leverage the authentication capabilities of Azure Functions as they are more secure and reliable.", + "title": "Introduction" + }, + { + "file": "package.json", + "selection": { + "start": { + "line": 16, + "character": 9 + }, + "end": { + "line": 18, + "character": 33 + } + }, + "description": "Added dependencies for token validation.\r\n", + "title": "Add dependencies" + }, + { + "file": "teamsapp.local.yml", + "selection": { + "start": { + "line": 9, + "character": 1 + }, + "end": { + "line": 28, + "character": 50 + } + }, + "description": "Added new action for creating a Microsoft Entra app.", + "title": "Config yaml actions" + }, + { + "file": "src/functions/repair.ts", + "selection": { + "start": { + "line": 58, + "character": 5 + }, + "end": { + "line": 64, + "character": 6 + } + }, + "description": "Check if the request is authenticated. You can remove those code when deploying the project remotely because it already uses Azure's built-in authentication in production.", + "title": "Check request" + }, + { + "file": "src/functions/middleware/authMiddleware.ts", + "selection": { + "start": { + "line": 29, + "character": 5 + }, + "end": { + "line": 36, + "character": 51 + } + }, + "description": "Validating tokens against specified options, including issuer, audience, scopes, roles, and allowed tenants, using a JWKS client for key retrieval and caching.", + "title": "Validate token" + } + ] +} \ No newline at end of file diff --git a/templates/ts/api-message-extension-sso/.vscode/extensions.json b/templates/ts/api-message-extension-sso/.vscode/extensions.json index aac0a6e347..2b65b67375 100644 --- a/templates/ts/api-message-extension-sso/.vscode/extensions.json +++ b/templates/ts/api-message-extension-sso/.vscode/extensions.json @@ -1,5 +1,6 @@ { "recommendations": [ - "TeamsDevApp.ms-teams-vscode-extension" + "TeamsDevApp.ms-teams-vscode-extension", + "vsls-contrib.codetour" ] } diff --git a/templates/ts/api-message-extension-sso/README.md b/templates/ts/api-message-extension-sso/README.md index a1d900969b..76a612c4a2 100644 --- a/templates/ts/api-message-extension-sso/README.md +++ b/templates/ts/api-message-extension-sso/README.md @@ -13,7 +13,7 @@ This app template allows Teams to interact directly with third-party data, apps, > > To run this app template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -35,12 +35,18 @@ This app template allows Teams to interact directly with third-party data, apps, The following files can be customized and demonstrate an example implementation to get you started. -| File | Contents | -| -------------------------------------------- | ------------------------------------------------------------------- | -| `src/functions/repair.ts` | The main file of a function in Azure Functions. | -| `src/repairsData.json` | The data source for the repair API. | -| `appPackage/apiSpecificationFile/repair.yml` | A file that describes the structure and behavior of the repair API. | -| `appPackage/responseTemplates/repair.json` | A generated Adaptive Card that used to render API response. | +| File | Contents | +| ----------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------- | +| `src/functions/repair.ts` | The main file of a function in Azure Functions. | +| `src/functions/middleware/tokenCacheWrapper.ts` | A wrapper class that handles caching of JWT signing keys to improve performance of token validation. | +| `src/functions/middleware/tokenValidator.ts` | Core class for validating JWT tokens from Microsoft Entra, including checks for claims, scopes, roles and tenant validation. | +| `src/functions/middleware/authMiddleware.ts` | Middleware function that handles authorization using JWT tokens, integrating with the token validator. | +| `src/functions/middleware/utils.ts` | Utility functions for authentication, including retrieving JWKS URIs for different cloud environments. | +| `src/functions/middleware/config.ts` | Configuration file that exports Microsoft Entra app settings from environment variables. | +| `src/functions/middleware/authMiddleware.ts` | A middleware function that implements Microsoft Entra authentication for Azure Functions. | +| `src/repairsData.json` | The data source for the repair API. | +| `appPackage/apiSpecificationFile/repair.yml` | A file that describes the structure and behavior of the repair API. | +| `appPackage/responseTemplates/repair.json` | A generated Adaptive Card that used to render API response. | The following are Teams Toolkit specific project files. You can [visit a complete guide on Github](https://github.com/OfficeDev/TeamsFx/wiki/Teams-Toolkit-Visual-Studio-Code-v5-Guide#overview) to understand how Teams Toolkit works. @@ -54,8 +60,6 @@ The following are Teams Toolkit specific project files. You can [visit a complet ![microsoft-entra-flow](https://github.com/OfficeDev/TeamsFx/assets/107838226/846e7a60-8cc1-4d8b-852e-2aec93b61fe9) -> **Note**: The Azure Active Directory (AAD) flow is only functional in remote environments. It cannot be tested in a local environment due to the lack of authentication support in Azure Function core tools. - ## Addition information and references - [Extend Teams platform with APIs](https://aka.ms/teamsfx-api-plugin) diff --git a/templates/ts/api-message-extension-sso/aad.manifest.json.tpl b/templates/ts/api-message-extension-sso/aad.manifest.json.tpl index ae843abc3b..b9a0822ad9 100644 --- a/templates/ts/api-message-extension-sso/aad.manifest.json.tpl +++ b/templates/ts/api-message-extension-sso/aad.manifest.json.tpl @@ -16,27 +16,16 @@ ], "saml2Token": [] }, - "requiredResourceAccess": [ - { - "resourceAppId": "Microsoft Graph", - "resourceAccess": [ - { - "id": "User.Read", - "type": "Scope" - } - ] - } - ], "oauth2Permissions": [ { - "adminConsentDescription": "Allows Teams to call the app's web APIs as the current user.", - "adminConsentDisplayName": "Teams can access app's web APIs", + "adminConsentDescription": "Allows Copilot to read repair records on your behalf.", + "adminConsentDisplayName": "Read repairs", "id": "${{AAD_APP_ACCESS_AS_USER_PERMISSION_ID}}", "isEnabled": true, "type": "User", - "userConsentDescription": "Enable Teams to call this app's web APIs with the same rights that you have", - "userConsentDisplayName": "Teams can access app's web APIs and make requests on your behalf", - "value": "access_as_user" + "userConsentDescription": "Allows Copilot to read repair records.", + "userConsentDisplayName": "Read repairs", + "value": "repairs_read" } ], "preAuthorizedApplications": [ diff --git a/templates/ts/api-message-extension-sso/infra/azure.bicep b/templates/ts/api-message-extension-sso/infra/azure.bicep index 158073502a..fe66f83a19 100644 --- a/templates/ts/api-message-extension-sso/infra/azure.bicep +++ b/templates/ts/api-message-extension-sso/infra/azure.bicep @@ -56,11 +56,11 @@ resource functionApp 'Microsoft.Web/sites@2021-02-01' = { value: '~18' // Set NodeJS version to 18.x } { - name: 'M365_CLIENT_ID' + name: 'aadAppClientId' value: aadAppClientId } { - name: 'M365_TENANT_ID' + name: 'aadAppTenantId' value: aadAppTenantId } { diff --git a/templates/ts/api-message-extension-sso/package.json.tpl b/templates/ts/api-message-extension-sso/package.json.tpl index db882e6b86..1f5d694a47 100644 --- a/templates/ts/api-message-extension-sso/package.json.tpl +++ b/templates/ts/api-message-extension-sso/package.json.tpl @@ -12,11 +12,15 @@ "test": "echo \"Error: no test specified\" && exit 1" }, "dependencies": { - "@azure/functions": "^4.3.0" + "@azure/functions": "^4.3.0", + "jsonwebtoken": "^9.0.2", + "jwks-rsa": "^3.1.0", + "lru-memoizer": "^2.3.0" }, "devDependencies": { - "env-cmd": "^10.1.0", "@types/node": "^20.11.26", + "@types/debug": "^4.1.12", + "env-cmd": "^10.1.0", "typescript": "^5.4.2" }, "main": "dist/src/functions/*.js" diff --git a/templates/ts/api-message-extension-sso/src/functions/middleware/authMiddleware.ts b/templates/ts/api-message-extension-sso/src/functions/middleware/authMiddleware.ts new file mode 100644 index 0000000000..34242ddd88 --- /dev/null +++ b/templates/ts/api-message-extension-sso/src/functions/middleware/authMiddleware.ts @@ -0,0 +1,44 @@ +import { HttpRequest } from "@azure/functions"; + +import config from "./config"; +import { TokenValidator } from "./tokenValidator"; +import { getEntraJwksUri } from "./utils"; + +/** + * Middleware function to handle authorization using JWT. + * + * @param {HttpRequest} req - The HTTP request. + * @returns {Promise} - A promise that resolves to a boolean value. + */ +export async function authMiddleware(req?: HttpRequest): Promise { + // Get the token from the request headers + const token = req.headers.get("authorization")?.split(" ")[1]; + if (!token) { + return false; + } + + try { + // Get the JWKS URL for the Microsoft Entra common tenant + const entraJwksUri = await getEntraJwksUri(); + + // Create a new token validator with the JWKS URL + const validator = new TokenValidator({ + jwksUri: entraJwksUri, + }); + + const options = { + allowedTenants: [config.aadAppTenantId], + audience: config.aadAppClientId, + issuer: `https://login.microsoftonline.com/${config.aadAppTenantId}/v2.0`, + scp: ["repairs_read"], + }; + // Validate the token + await validator.validateToken(token, options); + + return true; + } catch (err) { + // Handle JWT verification errors + console.error("Token is invalid:", err); + return false; + } +} diff --git a/templates/ts/api-message-extension-sso/src/functions/middleware/config.ts b/templates/ts/api-message-extension-sso/src/functions/middleware/config.ts new file mode 100644 index 0000000000..1a069a1cbe --- /dev/null +++ b/templates/ts/api-message-extension-sso/src/functions/middleware/config.ts @@ -0,0 +1,6 @@ +const config = { + aadAppClientId: process.env.aadAppClientId, + aadAppTenantId: process.env.aadAppTenantId, +}; + +export default config; diff --git a/templates/ts/api-message-extension-sso/src/functions/middleware/tokenCacheWrapper.ts b/templates/ts/api-message-extension-sso/src/functions/middleware/tokenCacheWrapper.ts new file mode 100644 index 0000000000..5f049fa1f6 --- /dev/null +++ b/templates/ts/api-message-extension-sso/src/functions/middleware/tokenCacheWrapper.ts @@ -0,0 +1,27 @@ +import createDebug from "debug"; +import { JwksClient, SigningKey } from "jwks-rsa"; +import memoizer from "lru-memoizer"; +import { IMemoized } from "lru-memoizer/lib/async"; +import { callbackify, promisify } from "util"; + +const logger = createDebug("jwt-validate"); + +// Based on https://github.com/auth0/node-jwks-rsa/blob/4fe372be935c2aa0882e0f1e58d33eead4be966d/src/wrappers/cache.js +// exposes cache to make it possible to clear cache and keys +export class TokenCacheWrapper { + public readonly cache: IMemoized; + + constructor(client: JwksClient, { cacheMaxEntries = 5, cacheMaxAge = 600000 }) { + logger(`Configured caching of signing keys. Max: ${cacheMaxEntries} / Age: ${cacheMaxAge}`); + this.cache = memoizer({ + hash: (kid: string) => kid, + load: callbackify(client.getSigningKey.bind(client)) as any, + maxAge: cacheMaxAge, + max: cacheMaxEntries, + } as any); + } + + getCacheWrapper(): (kid?: string | null | undefined) => Promise { + return promisify(this.cache as any); + } +} diff --git a/templates/ts/api-message-extension-sso/src/functions/middleware/tokenValidator.ts b/templates/ts/api-message-extension-sso/src/functions/middleware/tokenValidator.ts new file mode 100644 index 0000000000..6883bbc520 --- /dev/null +++ b/templates/ts/api-message-extension-sso/src/functions/middleware/tokenValidator.ts @@ -0,0 +1,194 @@ +import jwt, { Jwt, JwtPayload, VerifyOptions } from "jsonwebtoken"; +import jwksClient from "jwks-rsa"; + +import { TokenCacheWrapper } from "./tokenCacheWrapper.js"; + +const claimsType = Object.freeze({ + scopes: "scopes", + roles: "roles", +}); + +export interface TokenValidatorOptions { + cache?: boolean; + cacheMaxAge?: number; + jwksUri: string; +} + +export interface ValidateTokenOptions extends VerifyOptions { + allowedTenants?: string[]; + idtyp?: string; + roles?: string[]; + scp?: string[]; + ver?: string; +} + +export interface EntraJwtPayload extends JwtPayload { + idtyp?: string; + roles?: string[]; + scp?: string[]; + ver?: string; +} + +export class TokenValidator { + private client: jwksClient.JwksClient; + private cacheWrapper: TokenCacheWrapper; + + /** + * Constructs a new instance of TokenValidator. + * @param {Object} options Configuration options for the TokenValidator. + * @param {boolean} [options.cache=true] Whether to cache the JWKS keys. + * @param {number} [options.cacheMaxAge=86400000] The maximum age of the cache in milliseconds (default is 24 hours). + * @param {string} options.jwksUri The URI to fetch the JWKS keys from. + * @throws {Error} If the options parameter is not provided. + */ + constructor(options: TokenValidatorOptions) { + if (!options) { + throw new Error("options is required"); + } + + const cache = options.cache ?? true; + + this.client = jwksClient({ + cache, + cacheMaxAge: options.cacheMaxAge ?? 24 * 60 * 60 * 1000, // 24 hours in milliseconds + jwksUri: options.jwksUri, + }); + if (cache) { + this.cacheWrapper = new TokenCacheWrapper(this.client, options); + this.client.getSigningKey = this.cacheWrapper.getCacheWrapper() as any; + } + } + + /** + * Validates a JWT token. + * @param {string} token The JWT token to validate. + * @param {import('jsonwebtoken').VerifyOptions & { complete?: false } & { idtyp?: string, ver?: string, scp?: string[], roles?: string[] }} [options] Validation options. + * @property {string[]} [options.allowedTenants] The allowed tenants for the JWT token. Compared against the 'tid' claim. + * @property {string} [options.idtyp] The expected value of the 'idtyp' claim in the JWT token. + * @property {string[]} [options.roles] Roles expected in the 'roles' claim in the JWT token. + * @property {string[]} [options.scp] Scopes expected in the 'scp' claim in the JWT token. + * @property {string} [options.ver] The expected value of the 'ver' claim in the JWT token. + * @returns {Promise} The decoded and verified JWT token. + * @throws {Error} If the token is invalid or the validation fails. + */ + public async validateToken(token: string, options?: ValidateTokenOptions) { + const decoded = jwt.decode(token, { complete: true }); + if (!decoded) { + throw new Error("jwt malformed"); + } + + // necessary to support multitenant apps + this.updateIssuer(decoded, options); + + const key = await this.getSigningKey(decoded.header.kid); + const verifiedToken = jwt.verify(token, key, options) as EntraJwtPayload; + + if (!options) { + return verifiedToken; + } + + const validators = [ + TokenValidator.validateIdtyp, + TokenValidator.validateVer, + TokenValidator.validateScopesAndRoles, + TokenValidator.validateAllowedTenants, + ]; + validators.forEach((validator) => validator(verifiedToken, options)); + + return verifiedToken; + } + + private static validateIdtyp(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.idtyp && options.idtyp !== jwt.idtyp) { + throw new Error(`jwt idtyp is invalid. Expected: ${options.idtyp}`); + } + } + + private static validateVer(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.ver && options.ver !== jwt.ver) { + throw new Error(`jwt ver is invalid. Expected: ${options.ver}`); + } + } + + private static validateScopesAndRoles(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.scp || options.roles) { + const validateClaims = ( + claimsFromTheToken: string[], + requiredClaims: string[], + claimsType: string + ) => { + const hasAnyRequiredClaim = requiredClaims.some((claim) => + claimsFromTheToken.includes(claim) + ); + if (!hasAnyRequiredClaim) { + throw new Error(`jwt does not contain any of the required ${claimsType}`); + } + }; + + if (options.scp && options.roles) { + if (jwt.scp) { + validateClaims(jwt.scp, options.scp, claimsType.scopes); + } else if (jwt.roles) { + validateClaims(jwt.roles, options.roles, claimsType.roles); + } + } else if (options.scp) { + validateClaims(jwt.scp ?? [], options.scp, claimsType.scopes); + } else if (options.roles) { + validateClaims(jwt.roles ?? [], options.roles, claimsType.roles); + } + } + } + + private static validateAllowedTenants(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.allowedTenants && options.allowedTenants.length > 0) { + if (!jwt.tid || !options.allowedTenants.includes(jwt.tid)) { + throw new Error( + `jwt tid is not allowed. Allowed tenants: ${options.allowedTenants.join(", ")}` + ); + } + } + } + + /** + * Clears the cache used by the TokenValidator. + */ + public clearCache() { + this.cacheWrapper?.cache.reset(); + } + + /** + * Deletes a key from the cache. + * @param {string} kid The key ID to delete from the cache. + */ + public deleteKey(kid: string) { + this.cacheWrapper?.cache.del(kid); + } + + private async getSigningKey(kid?: string) { + const key = await this.client.getSigningKey(kid); + return key.getPublicKey(); + } + + private updateIssuer(jwt: Jwt, options?: ValidateTokenOptions) { + if (!options?.issuer || typeof jwt.payload !== "object" || !jwt.payload.tid) { + return; + } + + if (typeof options.issuer === "string") { + if (options.issuer.toLowerCase().indexOf("{tenantid}") > -1) { + options.issuer = options.issuer.replace(/{tenantid}/i, jwt.payload.tid); + } + return; + } + + if (Array.isArray(options.issuer)) { + options.issuer = options.issuer.map((issuer) => { + if (issuer.toLowerCase().indexOf("{tenantid}") > -1) { + return issuer.replace(/{tenantid}/i, (jwt.payload as JwtPayload).tid); + } + return issuer; + }); + return; + } + } +} diff --git a/templates/ts/api-message-extension-sso/src/functions/middleware/utils.ts b/templates/ts/api-message-extension-sso/src/functions/middleware/utils.ts new file mode 100644 index 0000000000..b17cab16a2 --- /dev/null +++ b/templates/ts/api-message-extension-sso/src/functions/middleware/utils.ts @@ -0,0 +1,40 @@ +interface OpenIdConfiguration { + jwks_uri: string; +} + +export enum CloudType { + Public, + Ppe, + USGovernment, + China, +} + +/** + * Retrieves the JWKS URI for the specified tenant. + * @param {string} [tenant='common'] - The tenant to retrieve the JWKS URI for. + * @param {CloudType} [cloud=CloudType.Public] - The cloud to retrieve the JWKS URI for. + * @returns {Promise} - A promise that resolves with the JWKS URI. + */ +export async function getEntraJwksUri( + tenant = "common", + cloud: CloudType = CloudType.Public +): Promise { + let cloudUrl = ""; + switch (cloud) { + case CloudType.Public: + cloudUrl = "login.microsoftonline.com"; + break; + case CloudType.Ppe: + cloudUrl = "login.windows-ppe.net"; + break; + case CloudType.USGovernment: + cloudUrl = "login.microsoftonline.us"; + break; + case CloudType.China: + cloudUrl = "login.chinacloudapi.cn"; + break; + } + const res = await fetch(`https://${cloudUrl}/${tenant}/.well-known/openid-configuration`); + const data = (await res.json()) as OpenIdConfiguration; + return data.jwks_uri; +} diff --git a/templates/ts/api-message-extension-sso/src/functions/repair.ts b/templates/ts/api-message-extension-sso/src/functions/repair.ts index a475e156c3..c9be644923 100644 --- a/templates/ts/api-message-extension-sso/src/functions/repair.ts +++ b/templates/ts/api-message-extension-sso/src/functions/repair.ts @@ -6,6 +6,7 @@ import { app, HttpRequest, HttpResponseInit, InvocationContext } from "@azure/functions"; import repairRecords from "../repairsData.json"; +import { authMiddleware } from "./middleware/authMiddleware"; /** * This function handles the HTTP request and returns the repair information. @@ -52,5 +53,16 @@ export async function repair( app.http("repair", { methods: ["GET"], authLevel: "anonymous", - handler: repair, + handler: async (req: HttpRequest, context: InvocationContext) => { + // Check if the request is authenticated + const isAuthenticated = await authMiddleware(req); + if (!isAuthenticated) { + return { + status: 401, + body: "Unauthorized", + }; + } + // Call the actual handler function + return repair(req, context); + }, }); diff --git a/templates/ts/api-message-extension-sso/teamsapp.local.yml.tpl b/templates/ts/api-message-extension-sso/teamsapp.local.yml.tpl index 62b46f50a6..1190079cf4 100644 --- a/templates/ts/api-message-extension-sso/teamsapp.local.yml.tpl +++ b/templates/ts/api-message-extension-sso/teamsapp.local.yml.tpl @@ -109,3 +109,11 @@ deploy: name: install dependencies with: args: install --no-audit + + # Generate runtime environment variables + - uses: file/createOrUpdateEnvironmentFile + with: + target: ./.localConfigs + envs: + aadAppClientId: ${{AAD_APP_CLIENT_ID}} + aadAppTenantId: ${{AAD_APP_TENANT_ID}} diff --git a/templates/ts/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl b/templates/ts/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl index ba4c8392f7..0508c02776 100644 --- a/templates/ts/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl +++ b/templates/ts/api-plugin-from-scratch-bearer/appPackage/ai-plugin.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/ts/api-plugin-from-scratch-oauth/.tours/custom-token-validation-without-using-Easy-Auth.tour b/templates/ts/api-plugin-from-scratch-oauth/.tours/custom-token-validation-without-using-Easy-Auth.tour new file mode 100644 index 0000000000..2573ac4feb --- /dev/null +++ b/templates/ts/api-plugin-from-scratch-oauth/.tours/custom-token-validation-without-using-Easy-Auth.tour @@ -0,0 +1,81 @@ +{ + "$schema": "https://aka.ms/codetour-schema", + "title": "custom-token-validation-without-using-Easy-Auth", + "steps": [ + { + "file": "src/functions/repairs.ts", + "selection": { + "start": { + "line": 55, + "character": 3 + }, + "end": { + "line": 55, + "character": 26 + } + }, + "description": "The reason for custom token validation is that Azure Function Core Tools do not support authentication when running locally. This template is designed to demonstrate local debugging of authentication functionalities in the API Message Extension. Therefore, this approach was taken. In production, you should leverage the authentication capabilities of Azure Functions as they are more secure and reliable.", + "title": "Introduction" + }, + { + "file": "package.json", + "selection": { + "start": { + "line": 16, + "character": 9 + }, + "end": { + "line": 18, + "character": 33 + } + }, + "description": "Added dependencies for token validation.\r\n", + "title": "Add dependencies" + }, + { + "file": "teamsapp.local.yml", + "selection": { + "start": { + "line": 9, + "character": 1 + }, + "end": { + "line": 28, + "character": 50 + } + }, + "description": "Added new action for creating a Microsoft Entra app.", + "title": "Config yaml actions" + }, + { + "file": "src/functions/repairs.ts", + "selection": { + "start": { + "line": 58, + "character": 5 + }, + "end": { + "line": 64, + "character": 6 + } + }, + "description": "Check if the request is authenticated. You can remove those code when deploying the project remotely because it already uses Azure's built-in authentication in production.", + "title": "Check request" + }, + { + "file": "src/functions/middleware/authMiddleware.ts", + "selection": { + "start": { + "line": 29, + "character": 5 + }, + "end": { + "line": 36, + "character": 51 + } + }, + "description": "Validating tokens against specified options, including issuer, audience, scopes, roles, and allowed tenants, using a JWKS client for key retrieval and caching.", + "title": "Validate token" + } + ] +} \ No newline at end of file diff --git a/templates/ts/api-plugin-from-scratch-oauth/.vscode/extensions.json b/templates/ts/api-plugin-from-scratch-oauth/.vscode/extensions.json index aac0a6e347..2b65b67375 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/.vscode/extensions.json +++ b/templates/ts/api-plugin-from-scratch-oauth/.vscode/extensions.json @@ -1,5 +1,6 @@ { "recommendations": [ - "TeamsDevApp.ms-teams-vscode-extension" + "TeamsDevApp.ms-teams-vscode-extension", + "vsls-contrib.codetour" ] } diff --git a/templates/ts/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl b/templates/ts/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl index 629762938a..8365244ba3 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/.vscode/tasks.json.tpl @@ -46,6 +46,7 @@ "access": "public", "writeToEnvironmentFile": { "endpoint": "OPENAPI_SERVER_URL", // output tunnel endpoint as OPENAPI_SERVER_URL + "domain": "OPENAPI_SERVER_DOMAIN" // output tunnel domain as OPENAPI_SERVER_DOMAIN } } ], diff --git a/templates/ts/api-plugin-from-scratch-oauth/README.md.tpl b/templates/ts/api-plugin-from-scratch-oauth/README.md.tpl index 3450714c6a..47dba740b9 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/README.md.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/README.md.tpl @@ -64,15 +64,18 @@ You can extend declarative agents using plugins to retrieve data and execute tas The following files can be customized and demonstrate an example implementation to get you started. -| File | Contents | -| -------------------------------------------------- | ----------------------------------------------------------------------------------------------------- | -| `src/functions/repairs.ts` | The main file of a function in Azure Functions. | -| `src/repairsData.json` | The data source for the repair API. | -| `appPackage/apiSpecificationFile/repair.dev.yml` | A file that describes the structure and behavior of the repair API. | -| `appPackage/apiSpecificationFile/repair.local.yml` | A file that describes the structure and behavior of the repair API for local execution and debugging. | -| `appPackage/manifest.json` | Teams application manifest that defines metadata for your plugin inside Microsoft Teams. | -| `appPackage/ai-plugin.dev.json` | The manifest file for your API plugin that contains information for your API and used by LLM. | -| `appPackage/ai-plugin.local.json` | The manifest file for your API plugin for local execution and debugging. | +| File | Contents | +| ----------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------- | +| `src/functions/repairs.ts` | The main file of a function in Azure Functions. | +| `src/functions/middleware/tokenCacheWrapper.ts` | A wrapper class that handles caching of JWT signing keys to improve performance of token validation. | +| `src/functions/middleware/tokenValidator.ts` | Core class for validating JWT tokens from Microsoft Entra, including checks for claims, scopes, roles and tenant validation. | +| `src/functions/middleware/authMiddleware.ts` | Middleware function that handles authorization using JWT tokens, integrating with the token validator. | +| `src/functions/middleware/utils.ts` | Utility functions for authentication, including retrieving JWKS URIs for different cloud environments. | +| `src/functions/middleware/config.ts` | Configuration file that exports Microsoft Entra app settings from environment variables. | +| `src/repairsData.json` | The data source for the repair API. | +| `appPackage/apiSpecificationFile/repair.yml` | A file that describes the structure and behavior of the repair API. | +| `appPackage/manifest.json` | Teams application manifest that defines metadata for your plugin inside Microsoft Teams. | +| `appPackage/ai-plugin.json` | The manifest file for your API plugin that contains information for your API and used by LLM. | {{#DeclarativeCopilot}} | `appPackage/repairDeclarativeAgent.json` | Define the behaviour and configurations of the declarative agent. | {{/DeclarativeCopilot}} @@ -89,8 +92,6 @@ The following are Teams Toolkit specific project files. You can [visit a complet ## How OAuth works in the API plugin ![oauth-flow](https://github.com/OfficeDev/teams-toolkit/assets/107838226/f074abbe-d9e3-4a46-8e08-feb66b17a539) - -> **Note**: The OAuth flow is only functional in remote environments. It cannot be tested in a local environment due to the lack of authentication support in Azure Function core tools. {{/MicrosoftEntra}} ## Addition information and references diff --git a/templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl b/templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.json.tpl similarity index 98% rename from templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl rename to templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.json.tpl index 1e73ae0853..4b4bb9c55b 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.dev.json.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.json.tpl @@ -77,7 +77,7 @@ {{/MicrosoftEntra}} }, "spec": { - "url": "apiSpecificationFile/repair.dev.yml", + "url": "apiSpecificationFile/repair.yml", "progress_style": "ShowUsageWithInputAndOutput" }, "run_for_functions": ["listRepairs"] diff --git a/templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl b/templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl deleted file mode 100644 index ae9474d675..0000000000 --- a/templates/ts/api-plugin-from-scratch-oauth/appPackage/ai-plugin.local.json.tpl +++ /dev/null @@ -1,88 +0,0 @@ -{ - "$schema": "https://developer.microsoft.com/json-schemas/copilot/plugin/v2.1/schema.json", - "schema_version": "v2.1", - "namespace": "repairs", - "name_for_human": "{{appName}}${{APP_NAME_SUFFIX}}", - "description_for_human": "Track your repair records", - "description_for_model": "Plugin for searching a repair list, you can search by who's assigned to the repair.", - "functions": [ - { - "name": "listRepairs", - "description": "Returns a list of repairs with their details and images", - "capabilities": { - "response_semantics": { - "data_path": "$.results", - "properties": { - "title": "$.title", - "subtitle": "$.description", - "url": "$.image" - }, - "static_template": { - "type": "AdaptiveCard", - "$schema": "http://adaptivecards.io/schemas/adaptive-card.json", - "version": "1.5", - "body": [ - { - "type": "Container", - "$data": "${$root}", - "items": [ - { - "type": "TextBlock", - "text": "id: ${if(id, id, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "title: ${if(title, title, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "description: ${if(description, description, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "assignedTo: ${if(assignedTo, assignedTo, 'N/A')}", - "wrap": true - }, - { - "type": "TextBlock", - "text": "date: ${if(date, date, 'N/A')}", - "wrap": true - }, - { - "type": "Image", - "url": "${image}", - "$when": "${image != null}" - } - ] - } - ] - } - } - } - } - ], - "runtimes": [ - { - "type": "OpenApi", - "auth": { - "type": "None" - }, - "spec": { - "url": "apiSpecificationFile/repair.local.yml", - "progress_style": "ShowUsageWithInputAndOutput" - }, - "run_for_functions": ["listRepairs"] - } - ], - "capabilities": { - "localization": {}, - "conversation_starters": [ - { - "text": "List all repairs" - } - ] - } -} diff --git a/templates/ts/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.local.yml b/templates/ts/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.local.yml deleted file mode 100644 index 81c0f25839..0000000000 --- a/templates/ts/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.local.yml +++ /dev/null @@ -1,55 +0,0 @@ -openapi: 3.0.0 -info: - title: Repair Service - description: A simple service to manage repairs - version: 1.0.0 -servers: - - url: ${{OPENAPI_SERVER_URL}}/api - description: The repair api server - -paths: - /repairs: - get: - operationId: listRepairs - summary: List all repairs - description: Returns a list of repairs with their details and images - parameters: - - name: assignedTo - in: query - description: Filter repairs by who they're assigned to - schema: - type: string - required: false - responses: - '200': - description: A list of repairs - content: - application/json: - schema: - type: object - properties: - results: - type: array - items: - type: object - properties: - id: - type: string - description: The unique identifier of the repair - title: - type: string - description: The short summary of the repair - description: - type: string - description: The detailed description of the repair - assignedTo: - type: string - description: The user who is responsible for the repair - date: - type: string - format: date-time - description: The date and time when the repair is scheduled or completed - image: - type: string - format: uri - description: The URL of the image of the item to be repaired or the repair process \ No newline at end of file diff --git a/templates/ts/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.dev.yml.tpl b/templates/ts/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.yml.tpl similarity index 100% rename from templates/ts/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.dev.yml.tpl rename to templates/ts/api-plugin-from-scratch-oauth/appPackage/apiSpecificationFile/repair.yml.tpl diff --git a/templates/ts/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl b/templates/ts/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl index 92cd70722c..5992d3592d 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/appPackage/manifest.json.tpl @@ -27,7 +27,7 @@ "plugins": [ { "id": "plugin_1", - "file": "ai-plugin.${{TEAMSFX_ENV}}.json" + "file": "ai-plugin.json" } ] {{/DeclarativeCopilot}} diff --git a/templates/ts/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl b/templates/ts/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl index 7453556968..a52919b2cd 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/appPackage/repairDeclarativeAgent.json.tpl @@ -17,7 +17,7 @@ "actions": [ { "id": "repairPlugin", - "file": "ai-plugin.${{TEAMSFX_ENV}}.json" + "file": "ai-plugin.json" } ] } \ No newline at end of file diff --git a/templates/ts/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl b/templates/ts/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl index b38273f91a..bb1e0dc172 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/infra/azure.bicep.tpl @@ -45,6 +45,14 @@ resource functionApp 'Microsoft.Web/sites@2021-02-01' = { name: 'WEBSITE_NODE_DEFAULT_VERSION' value: '~18' // Set NodeJS version to 18.x } + { + name: 'aadAppClientId' + value: aadAppClientId + } + { + name: 'aadAppTenantId' + value: aadAppTenantId + } ] ftpsState: 'FtpsOnly' } diff --git a/templates/ts/api-plugin-from-scratch-oauth/package.json.tpl b/templates/ts/api-plugin-from-scratch-oauth/package.json.tpl index 7237d4b900..cf03c778b2 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/package.json.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/package.json.tpl @@ -12,11 +12,16 @@ "test": "echo \"Error: no test specified\" && exit 1" }, "dependencies": { - "@azure/functions": "^4.3.0" + "@azure/functions": "^4.3.0", + "jsonwebtoken": "^9.0.2", + "jwks-rsa": "^3.1.0", + "lru-memoizer": "^2.3.0" }, "devDependencies": { + "@types/debug": "^4.1.12", + "@types/node": "^20.14.9", "env-cmd": "^10.1.0", - "@types/node": "^18.11.9", + "rimraf": "^5.0.7", "typescript": "^4.1.6" }, "main": "dist/src/functions/*.js" diff --git a/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/authMiddleware.ts b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/authMiddleware.ts new file mode 100644 index 0000000000..0cfc0142f6 --- /dev/null +++ b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/authMiddleware.ts @@ -0,0 +1,43 @@ +import { HttpRequest } from "@azure/functions"; +import { TokenValidator } from "./tokenValidator"; +import config from "./config"; +import { getEntraJwksUri, CloudType } from "./utils"; + +/** + * Middleware function to handle authorization using JWT. + * + * @param {HttpRequest} req - The HTTP request. + * @returns {Promise} - A promise that resolves to a boolean value. + */ +export async function authMiddleware(req?: HttpRequest): Promise { + // Get the token from the request headers + const token = req.headers.get("authorization")?.split(" ")[1]; + if (!token) { + return false; + } + + try { + // Get the JWKS URL for the Microsoft Entra common tenant + const entraJwksUri = await getEntraJwksUri(config.aadAppTenantId, CloudType.Public); + + // Create a new token validator with the JWKS URL + const validator = new TokenValidator({ + jwksUri: entraJwksUri, + }); + + const options = { + allowedTenants: [config.aadAppTenantId], + audience: config.aadAppClientId, + issuer: `https://login.microsoftonline.com/${config.aadAppTenantId}/v2.0`, + scp: ["repairs_read"], + }; + // Validate the token + await validator.validateToken(token, options); + + return true; + } catch (err) { + // Handle JWT verification errors + console.error("Token is invalid:", err); + return false; + } +} diff --git a/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/config.ts b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/config.ts new file mode 100644 index 0000000000..1a069a1cbe --- /dev/null +++ b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/config.ts @@ -0,0 +1,6 @@ +const config = { + aadAppClientId: process.env.aadAppClientId, + aadAppTenantId: process.env.aadAppTenantId, +}; + +export default config; diff --git a/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/tokenCacheWrapper.ts b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/tokenCacheWrapper.ts new file mode 100644 index 0000000000..5f049fa1f6 --- /dev/null +++ b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/tokenCacheWrapper.ts @@ -0,0 +1,27 @@ +import createDebug from "debug"; +import { JwksClient, SigningKey } from "jwks-rsa"; +import memoizer from "lru-memoizer"; +import { IMemoized } from "lru-memoizer/lib/async"; +import { callbackify, promisify } from "util"; + +const logger = createDebug("jwt-validate"); + +// Based on https://github.com/auth0/node-jwks-rsa/blob/4fe372be935c2aa0882e0f1e58d33eead4be966d/src/wrappers/cache.js +// exposes cache to make it possible to clear cache and keys +export class TokenCacheWrapper { + public readonly cache: IMemoized; + + constructor(client: JwksClient, { cacheMaxEntries = 5, cacheMaxAge = 600000 }) { + logger(`Configured caching of signing keys. Max: ${cacheMaxEntries} / Age: ${cacheMaxAge}`); + this.cache = memoizer({ + hash: (kid: string) => kid, + load: callbackify(client.getSigningKey.bind(client)) as any, + maxAge: cacheMaxAge, + max: cacheMaxEntries, + } as any); + } + + getCacheWrapper(): (kid?: string | null | undefined) => Promise { + return promisify(this.cache as any); + } +} diff --git a/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/tokenValidator.ts b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/tokenValidator.ts new file mode 100644 index 0000000000..6883bbc520 --- /dev/null +++ b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/tokenValidator.ts @@ -0,0 +1,194 @@ +import jwt, { Jwt, JwtPayload, VerifyOptions } from "jsonwebtoken"; +import jwksClient from "jwks-rsa"; + +import { TokenCacheWrapper } from "./tokenCacheWrapper.js"; + +const claimsType = Object.freeze({ + scopes: "scopes", + roles: "roles", +}); + +export interface TokenValidatorOptions { + cache?: boolean; + cacheMaxAge?: number; + jwksUri: string; +} + +export interface ValidateTokenOptions extends VerifyOptions { + allowedTenants?: string[]; + idtyp?: string; + roles?: string[]; + scp?: string[]; + ver?: string; +} + +export interface EntraJwtPayload extends JwtPayload { + idtyp?: string; + roles?: string[]; + scp?: string[]; + ver?: string; +} + +export class TokenValidator { + private client: jwksClient.JwksClient; + private cacheWrapper: TokenCacheWrapper; + + /** + * Constructs a new instance of TokenValidator. + * @param {Object} options Configuration options for the TokenValidator. + * @param {boolean} [options.cache=true] Whether to cache the JWKS keys. + * @param {number} [options.cacheMaxAge=86400000] The maximum age of the cache in milliseconds (default is 24 hours). + * @param {string} options.jwksUri The URI to fetch the JWKS keys from. + * @throws {Error} If the options parameter is not provided. + */ + constructor(options: TokenValidatorOptions) { + if (!options) { + throw new Error("options is required"); + } + + const cache = options.cache ?? true; + + this.client = jwksClient({ + cache, + cacheMaxAge: options.cacheMaxAge ?? 24 * 60 * 60 * 1000, // 24 hours in milliseconds + jwksUri: options.jwksUri, + }); + if (cache) { + this.cacheWrapper = new TokenCacheWrapper(this.client, options); + this.client.getSigningKey = this.cacheWrapper.getCacheWrapper() as any; + } + } + + /** + * Validates a JWT token. + * @param {string} token The JWT token to validate. + * @param {import('jsonwebtoken').VerifyOptions & { complete?: false } & { idtyp?: string, ver?: string, scp?: string[], roles?: string[] }} [options] Validation options. + * @property {string[]} [options.allowedTenants] The allowed tenants for the JWT token. Compared against the 'tid' claim. + * @property {string} [options.idtyp] The expected value of the 'idtyp' claim in the JWT token. + * @property {string[]} [options.roles] Roles expected in the 'roles' claim in the JWT token. + * @property {string[]} [options.scp] Scopes expected in the 'scp' claim in the JWT token. + * @property {string} [options.ver] The expected value of the 'ver' claim in the JWT token. + * @returns {Promise} The decoded and verified JWT token. + * @throws {Error} If the token is invalid or the validation fails. + */ + public async validateToken(token: string, options?: ValidateTokenOptions) { + const decoded = jwt.decode(token, { complete: true }); + if (!decoded) { + throw new Error("jwt malformed"); + } + + // necessary to support multitenant apps + this.updateIssuer(decoded, options); + + const key = await this.getSigningKey(decoded.header.kid); + const verifiedToken = jwt.verify(token, key, options) as EntraJwtPayload; + + if (!options) { + return verifiedToken; + } + + const validators = [ + TokenValidator.validateIdtyp, + TokenValidator.validateVer, + TokenValidator.validateScopesAndRoles, + TokenValidator.validateAllowedTenants, + ]; + validators.forEach((validator) => validator(verifiedToken, options)); + + return verifiedToken; + } + + private static validateIdtyp(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.idtyp && options.idtyp !== jwt.idtyp) { + throw new Error(`jwt idtyp is invalid. Expected: ${options.idtyp}`); + } + } + + private static validateVer(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.ver && options.ver !== jwt.ver) { + throw new Error(`jwt ver is invalid. Expected: ${options.ver}`); + } + } + + private static validateScopesAndRoles(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.scp || options.roles) { + const validateClaims = ( + claimsFromTheToken: string[], + requiredClaims: string[], + claimsType: string + ) => { + const hasAnyRequiredClaim = requiredClaims.some((claim) => + claimsFromTheToken.includes(claim) + ); + if (!hasAnyRequiredClaim) { + throw new Error(`jwt does not contain any of the required ${claimsType}`); + } + }; + + if (options.scp && options.roles) { + if (jwt.scp) { + validateClaims(jwt.scp, options.scp, claimsType.scopes); + } else if (jwt.roles) { + validateClaims(jwt.roles, options.roles, claimsType.roles); + } + } else if (options.scp) { + validateClaims(jwt.scp ?? [], options.scp, claimsType.scopes); + } else if (options.roles) { + validateClaims(jwt.roles ?? [], options.roles, claimsType.roles); + } + } + } + + private static validateAllowedTenants(jwt: EntraJwtPayload, options: ValidateTokenOptions) { + if (options.allowedTenants && options.allowedTenants.length > 0) { + if (!jwt.tid || !options.allowedTenants.includes(jwt.tid)) { + throw new Error( + `jwt tid is not allowed. Allowed tenants: ${options.allowedTenants.join(", ")}` + ); + } + } + } + + /** + * Clears the cache used by the TokenValidator. + */ + public clearCache() { + this.cacheWrapper?.cache.reset(); + } + + /** + * Deletes a key from the cache. + * @param {string} kid The key ID to delete from the cache. + */ + public deleteKey(kid: string) { + this.cacheWrapper?.cache.del(kid); + } + + private async getSigningKey(kid?: string) { + const key = await this.client.getSigningKey(kid); + return key.getPublicKey(); + } + + private updateIssuer(jwt: Jwt, options?: ValidateTokenOptions) { + if (!options?.issuer || typeof jwt.payload !== "object" || !jwt.payload.tid) { + return; + } + + if (typeof options.issuer === "string") { + if (options.issuer.toLowerCase().indexOf("{tenantid}") > -1) { + options.issuer = options.issuer.replace(/{tenantid}/i, jwt.payload.tid); + } + return; + } + + if (Array.isArray(options.issuer)) { + options.issuer = options.issuer.map((issuer) => { + if (issuer.toLowerCase().indexOf("{tenantid}") > -1) { + return issuer.replace(/{tenantid}/i, (jwt.payload as JwtPayload).tid); + } + return issuer; + }); + return; + } + } +} diff --git a/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/utils.ts b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/utils.ts new file mode 100644 index 0000000000..b17cab16a2 --- /dev/null +++ b/templates/ts/api-plugin-from-scratch-oauth/src/functions/middleware/utils.ts @@ -0,0 +1,40 @@ +interface OpenIdConfiguration { + jwks_uri: string; +} + +export enum CloudType { + Public, + Ppe, + USGovernment, + China, +} + +/** + * Retrieves the JWKS URI for the specified tenant. + * @param {string} [tenant='common'] - The tenant to retrieve the JWKS URI for. + * @param {CloudType} [cloud=CloudType.Public] - The cloud to retrieve the JWKS URI for. + * @returns {Promise} - A promise that resolves with the JWKS URI. + */ +export async function getEntraJwksUri( + tenant = "common", + cloud: CloudType = CloudType.Public +): Promise { + let cloudUrl = ""; + switch (cloud) { + case CloudType.Public: + cloudUrl = "login.microsoftonline.com"; + break; + case CloudType.Ppe: + cloudUrl = "login.windows-ppe.net"; + break; + case CloudType.USGovernment: + cloudUrl = "login.microsoftonline.us"; + break; + case CloudType.China: + cloudUrl = "login.chinacloudapi.cn"; + break; + } + const res = await fetch(`https://${cloudUrl}/${tenant}/.well-known/openid-configuration`); + const data = (await res.json()) as OpenIdConfiguration; + return data.jwks_uri; +} diff --git a/templates/ts/api-plugin-from-scratch-oauth/src/functions/repairs.ts b/templates/ts/api-plugin-from-scratch-oauth/src/functions/repairs.ts index fc81dfd57a..1cfac3058e 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/src/functions/repairs.ts +++ b/templates/ts/api-plugin-from-scratch-oauth/src/functions/repairs.ts @@ -6,6 +6,7 @@ import { app, HttpRequest, HttpResponseInit, InvocationContext } from "@azure/functions"; import repairRecords from "../repairsData.json"; +import { authMiddleware } from "./middleware/authMiddleware"; /** * This function handles the HTTP request and returns the repair information. @@ -52,5 +53,16 @@ export async function repairs( app.http("repairs", { methods: ["GET"], authLevel: "anonymous", - handler: repairs, + handler: async (req: HttpRequest, context: InvocationContext) => { + // Check if the request is authenticated + const isAuthenticated = await authMiddleware(req); + if (!isAuthenticated) { + return { + status: 401, + body: "Unauthorized", + }; + } + // Call the actual handler function + return repairs(req, context); + }, }); diff --git a/templates/ts/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl b/templates/ts/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl index b5c5812d25..cb790ce387 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/teamsapp.local.yml.tpl @@ -4,6 +4,39 @@ version: v1.7 provision: + # Creates a new Microsoft Entra app to authenticate users if + # the environment variable that stores clientId is empty + - uses: aadApp/create + with: + # Note: when you run aadApp/update, the Microsoft Entra app name will be updated + # based on the definition in manifest. If you don't want to change the + # name, make sure the name in Microsoft Entra manifest is the same with the name + # defined here. + name: {{appName}}-aad + # If the value is false, the action will not generate client secret for you +{{#MicrosoftEntra}} + generateClientSecret: false +{{/MicrosoftEntra}} +{{^MicrosoftEntra}} + generateClientSecret: true +{{/MicrosoftEntra}} + # Authenticate users with a Microsoft work or school account in your + # organization's Microsoft Entra tenant (for example, single tenant). + signInAudience: AzureADMyOrg + # Write the information of created resources into environment file for the + # specified environment variable(s). + writeToEnvironmentFile: + clientId: AAD_APP_CLIENT_ID + # Environment variable that starts with `SECRET_` will be stored to the + # .env.{envName}.user environment file +{{^MicrosoftEntra}} + clientSecret: SECRET_AAD_APP_CLIENT_SECRET +{{/MicrosoftEntra}} + objectId: AAD_APP_OBJECT_ID + tenantId: AAD_APP_TENANT_ID + authority: AAD_APP_OAUTH_AUTHORITY + authorityHost: AAD_APP_OAUTH_AUTHORITY_HOST + # Creates a Teams app - uses: teamsApp/create with: @@ -21,6 +54,57 @@ provision: echo "::set-teamsfx-env FUNC_NAME=repair"; echo "::set-teamsfx-env FUNC_ENDPOINT=http://localhost:7071"; + # Apply the Microsoft Entra manifest to an existing Microsoft Entra app. Will use the object id in + # manifest file to determine which Microsoft Entra app to update. + - uses: aadApp/update + with: + # Relative path to this file. Environment variables in manifest will + # be replaced before apply to Microsoft Entra app + manifestPath: ./aad.manifest.json + outputFilePath: ./build/aad.manifest.${{TEAMSFX_ENV}}.json + + - uses: oauth/register + with: +{{#MicrosoftEntra}} + name: aadAuthCode + flow: authorizationCode + appId: ${{TEAMS_APP_ID}} + clientId: ${{AAD_APP_CLIENT_ID}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + identityProvider: MicrosoftEntra + writeToEnvironmentFile: + configurationId: AADAUTHCODE_CONFIGURATION_ID +{{/MicrosoftEntra}} +{{^MicrosoftEntra}} + name: oAuth2AuthCode + flow: authorizationCode + appId: ${{TEAMS_APP_ID}} + clientId: ${{AAD_APP_CLIENT_ID}} + clientSecret: ${{SECRET_AAD_APP_CLIENT_SECRET}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + writeToEnvironmentFile: + configurationId: OAUTH2AUTHCODE_CONFIGURATION_ID +{{/MicrosoftEntra}} + + - uses: oauth/update + with: +{{#MicrosoftEntra}} + name: aadAuthCode + appId: ${{TEAMS_APP_ID}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + configurationId: ${{AADAUTHCODE_CONFIGURATION_ID}} +{{/MicrosoftEntra}} +{{^MicrosoftEntra}} + name: oAuth2AuthCode + appId: ${{TEAMS_APP_ID}} + # Path to OpenAPI description document + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml + configurationId: ${{OAUTH2AUTHCODE_CONFIGURATION_ID}} +{{/MicrosoftEntra}} + # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -71,3 +155,11 @@ deploy: name: install dependencies with: args: install --no-audit + + # Generate runtime environment variables + - uses: file/createOrUpdateEnvironmentFile + with: + target: ./.localConfigs + envs: + aadAppTenantId: ${{AAD_APP_TENANT_ID}} + aadAppClientId: ${{AAD_APP_CLIENT_ID}} \ No newline at end of file diff --git a/templates/ts/api-plugin-from-scratch-oauth/teamsapp.yml.tpl b/templates/ts/api-plugin-from-scratch-oauth/teamsapp.yml.tpl index 0c7a171b5a..a6831a1dd9 100644 --- a/templates/ts/api-plugin-from-scratch-oauth/teamsapp.yml.tpl +++ b/templates/ts/api-plugin-from-scratch-oauth/teamsapp.yml.tpl @@ -92,7 +92,7 @@ provision: appId: ${{TEAMS_APP_ID}} clientId: ${{AAD_APP_CLIENT_ID}} # Path to OpenAPI description document - apiSpecPath: ./appPackage/apiSpecificationFile/repair.${{TEAMSFX_ENV}}.yml + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml identityProvider: MicrosoftEntra writeToEnvironmentFile: configurationId: AADAUTHCODE_CONFIGURATION_ID @@ -104,7 +104,7 @@ provision: clientId: ${{AAD_APP_CLIENT_ID}} clientSecret: ${{SECRET_AAD_APP_CLIENT_SECRET}} # Path to OpenAPI description document - apiSpecPath: ./appPackage/apiSpecificationFile/repair.${{TEAMSFX_ENV}}.yml + apiSpecPath: ./appPackage/apiSpecificationFile/repair.yml writeToEnvironmentFile: configurationId: OAUTH2AUTHCODE_CONFIGURATION_ID {{/MicrosoftEntra}} diff --git a/templates/ts/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl b/templates/ts/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl index 8540c0dae1..88f9230faa 100644 --- a/templates/ts/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl +++ b/templates/ts/api-plugin-from-scratch/appPackage/ai-plugin.json.tpl @@ -14,8 +14,7 @@ "data_path": "$.results", "properties": { "title": "$.title", - "subtitle": "$.description", - "url": "$.image" + "subtitle": "$.description" }, "static_template": { "type": "AdaptiveCard", diff --git a/templates/ts/command-and-response/.vscode/tasks.json b/templates/ts/command-and-response/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/command-and-response/.vscode/tasks.json +++ b/templates/ts/command-and-response/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/command-and-response/README.md.tpl b/templates/ts/command-and-response/README.md.tpl index cdc54d5ea3..ba6aec7cd2 100644 --- a/templates/ts/command-and-response/README.md.tpl +++ b/templates/ts/command-and-response/README.md.tpl @@ -10,7 +10,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the command bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} @@ -60,7 +60,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | - | - | -| `src/index.ts` | Application entry point and `restify` handlers for command and response | +| `src/index.ts` | Application entry point and `express` handlers for command and response | | `src/teamsBot.ts` | An empty teams activity handler for bot customization | | `src/adaptiveCards/helloworldCommand.json` | A generated Adaptive Card that is sent to Teams | | `src/helloworldCommandHandler.ts` | The business logic to handle a command | diff --git a/templates/ts/command-and-response/appPackage/manifest.json.tpl b/templates/ts/command-and-response/appPackage/manifest.json.tpl index cf2bbc13dc..84ea23d920 100644 --- a/templates/ts/command-and-response/appPackage/manifest.json.tpl +++ b/templates/ts/command-and-response/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/command-and-response/package.json.tpl b/templates/ts/command-and-response/package.json.tpl index e3c2df66c4..1a4612d74b 100644 --- a/templates/ts/command-and-response/package.json.tpl +++ b/templates/ts/command-and-response/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Command and Response Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -24,17 +24,17 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/json-schema": "^7.0.15", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "ts-node": "^10.4.0", "typescript": "^4.4.4", "shx": "^0.3.4" diff --git a/templates/ts/command-and-response/src/cardModels.ts b/templates/ts/command-and-response/src/cardModels.ts deleted file mode 100644 index 024955f4de..0000000000 --- a/templates/ts/command-and-response/src/cardModels.ts +++ /dev/null @@ -1,8 +0,0 @@ -/** - * Adaptive Card data model. Properties can be referenced in an adaptive card via the `${var}` - * Adaptive Card syntax. - */ -export interface CardData { - title: string; - body: string; -} diff --git a/templates/ts/command-and-response/src/helloworldCommandHandler.ts b/templates/ts/command-and-response/src/helloworldCommandHandler.ts index ab63992e4e..b7d4a2164a 100644 --- a/templates/ts/command-and-response/src/helloworldCommandHandler.ts +++ b/templates/ts/command-and-response/src/helloworldCommandHandler.ts @@ -2,7 +2,6 @@ import { Activity, CardFactory, MessageFactory, TurnContext } from "botbuilder"; import { CommandMessage, TeamsFxBotCommandHandler, TriggerPatterns } from "@microsoft/teamsfx"; import * as ACData from "adaptivecards-templating"; import helloWorldCard from "./adaptiveCards/helloworldCommand.json"; -import { CardData } from "./cardModels"; /** * The `HelloWorldCommandHandler` registers a pattern with the `TeamsFxBotCommandHandler` and responds @@ -17,13 +16,12 @@ export class HelloWorldCommandHandler implements TeamsFxBotCommandHandler { ): Promise | void> { console.log(`App received message: ${message.text}`); - // Render your adaptive card for reply message - const cardData: CardData = { - title: "Your Hello World App is Running", - body: "Congratulations! Your Hello World App is running. Open the documentation below to learn more about how to build applications with the Teams Toolkit.", - }; - - const cardJson = new ACData.Template(helloWorldCard).expand({ $root: cardData }); + const cardJson = new ACData.Template(helloWorldCard).expand({ + $root: { + title: "Your Hello World App is Running", + body: "Congratulations! Your Hello World App is running. Open the documentation below to learn more about how to build applications with the Teams Toolkit.", + }, + }); return MessageFactory.attachment(CardFactory.adaptiveCard(cardJson)); } } diff --git a/templates/ts/command-and-response/src/index.ts b/templates/ts/command-and-response/src/index.ts index 805b7f49d4..edb5695c9a 100644 --- a/templates/ts/command-and-response/src/index.ts +++ b/templates/ts/command-and-response/src/index.ts @@ -1,23 +1,24 @@ -import * as restify from "restify"; +import express from "express"; import { commandApp } from "./internal/initialize"; import { TeamsBot } from "./teamsBot"; -// This template uses `restify` to serve HTTP responses. -// Create a restify server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nApp Started, ${server.name} listening to ${server.url}`); +// This template uses `express` to serve HTTP responses. +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Register an API endpoint with `restify`. Teams sends messages to your application +// Register an API endpoint with `express`. Teams sends messages to your application // through this endpoint. // // The Teams Toolkit bot registration configures the bot with `/api/messages` as the // Bot Framework endpoint. If you customize this route, update the Bot registration // in `templates/azure/provision/botservice.bicep`. const teamsBot = new TeamsBot(); -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await commandApp.requestHandler(req, res, async (context) => { await teamsBot.run(context); }); diff --git a/templates/ts/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl b/templates/ts/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl index 71bbc4d363..892ff8b82d 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl +++ b/templates/ts/custom-copilot-assistant-assistants-api/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/ts/custom-copilot-assistant-assistants-api/.vscode/tasks.json b/templates/ts/custom-copilot-assistant-assistants-api/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/.vscode/tasks.json +++ b/templates/ts/custom-copilot-assistant-assistants-api/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/custom-copilot-assistant-assistants-api/README.md.tpl b/templates/ts/custom-copilot-assistant-assistants-api/README.md.tpl index f60a780f98..0a9a8f3de9 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/README.md.tpl +++ b/templates/ts/custom-copilot-assistant-assistants-api/README.md.tpl @@ -10,7 +10,7 @@ It showcases how to build an AI agent in Teams capable of helping users accompli > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl b/templates/ts/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl index 68ec52c46e..cb1279f2c0 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl +++ b/templates/ts/custom-copilot-assistant-assistants-api/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/ts/custom-copilot-assistant-assistants-api/package.json.tpl b/templates/ts/custom-copilot-assistant-assistants-api/package.json.tpl index 0d289ccb78..95b97571e6 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/package.json.tpl +++ b/templates/ts/custom-copilot-assistant-assistants-api/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Assistant Bot sample with OpenAI Assistants API and Teams AI Library's built-in coordination", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -27,17 +27,17 @@ "url": "https://github.com" }, "dependencies": { - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^5.5.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/custom-copilot-assistant-assistants-api/src/index.ts b/templates/ts/custom-copilot-assistant-assistants-api/src/index.ts index 0db519818e..906a4db2be 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/src/index.ts +++ b/templates/ts/custom-copilot-assistant-assistants-api/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // This bot's adapter import adapter from "./adapter"; @@ -7,16 +7,16 @@ import adapter from "./adapter"; // This bot's main dialog. import app from "./app/app"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl b/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl index eab3d7b2d8..68d95a09e9 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl +++ b/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl b/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl index 435dd9ae91..26a05e3127 100644 --- a/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl +++ b/templates/ts/custom-copilot-assistant-assistants-api/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/ts/custom-copilot-assistant-new/.vscode/launch.json.tpl b/templates/ts/custom-copilot-assistant-new/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/ts/custom-copilot-assistant-new/.vscode/launch.json.tpl +++ b/templates/ts/custom-copilot-assistant-new/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/ts/custom-copilot-assistant-new/.vscode/tasks.json b/templates/ts/custom-copilot-assistant-new/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/custom-copilot-assistant-new/.vscode/tasks.json +++ b/templates/ts/custom-copilot-assistant-new/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/custom-copilot-assistant-new/README.md.tpl b/templates/ts/custom-copilot-assistant-new/README.md.tpl index e2142b7cf2..f14b52884b 100644 --- a/templates/ts/custom-copilot-assistant-new/README.md.tpl +++ b/templates/ts/custom-copilot-assistant-new/README.md.tpl @@ -9,7 +9,7 @@ It showcases how to build an AI agent in Teams capable of chatting with users an > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/custom-copilot-assistant-new/appPackage/manifest.json.tpl b/templates/ts/custom-copilot-assistant-new/appPackage/manifest.json.tpl index cd337382ba..1d0ea3401b 100644 --- a/templates/ts/custom-copilot-assistant-new/appPackage/manifest.json.tpl +++ b/templates/ts/custom-copilot-assistant-new/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/ts/custom-copilot-assistant-new/package.json.tpl b/templates/ts/custom-copilot-assistant-new/package.json.tpl index 4b8d19e4c5..ecbfc8567d 100644 --- a/templates/ts/custom-copilot-assistant-new/package.json.tpl +++ b/templates/ts/custom-copilot-assistant-new/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Chat Bot Sample with Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,17 +26,17 @@ "url": "https://github.com" }, "dependencies": { - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^5.5.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/custom-copilot-assistant-new/src/app/app.ts.tpl b/templates/ts/custom-copilot-assistant-new/src/app/app.ts.tpl index b77f65f7fb..9e4dc2cfa3 100644 --- a/templates/ts/custom-copilot-assistant-new/src/app/app.ts.tpl +++ b/templates/ts/custom-copilot-assistant-new/src/app/app.ts.tpl @@ -22,6 +22,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/ts/custom-copilot-assistant-new/src/index.ts b/templates/ts/custom-copilot-assistant-new/src/index.ts index 0db519818e..906a4db2be 100644 --- a/templates/ts/custom-copilot-assistant-new/src/index.ts +++ b/templates/ts/custom-copilot-assistant-new/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // This bot's adapter import adapter from "./adapter"; @@ -7,16 +7,16 @@ import adapter from "./adapter"; // This bot's main dialog. import app from "./app/app"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/custom-copilot-assistant-new/teamsapp.local.yml.tpl b/templates/ts/custom-copilot-assistant-new/teamsapp.local.yml.tpl index 2c7fb58640..4450b98a34 100644 --- a/templates/ts/custom-copilot-assistant-new/teamsapp.local.yml.tpl +++ b/templates/ts/custom-copilot-assistant-new/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/ts/custom-copilot-assistant-new/teamsapp.yml.tpl b/templates/ts/custom-copilot-assistant-new/teamsapp.yml.tpl index 435dd9ae91..6f956d86a3 100644 --- a/templates/ts/custom-copilot-assistant-new/teamsapp.yml.tpl +++ b/templates/ts/custom-copilot-assistant-new/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/ts/custom-copilot-basic/.vscode/launch.json.tpl b/templates/ts/custom-copilot-basic/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/ts/custom-copilot-basic/.vscode/launch.json.tpl +++ b/templates/ts/custom-copilot-basic/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/ts/custom-copilot-basic/.vscode/tasks.json b/templates/ts/custom-copilot-basic/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/custom-copilot-basic/.vscode/tasks.json +++ b/templates/ts/custom-copilot-basic/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/custom-copilot-basic/README.md.tpl b/templates/ts/custom-copilot-basic/README.md.tpl index efd053e949..e1118a6370 100644 --- a/templates/ts/custom-copilot-basic/README.md.tpl +++ b/templates/ts/custom-copilot-basic/README.md.tpl @@ -9,7 +9,7 @@ It showcases a bot app that responds to user questions like ChatGPT. This enable > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18. +> - [Node.js](https://nodejs.org/), supported versions: 18, 20. {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts). {{/enableTestToolByDefault}} diff --git a/templates/ts/custom-copilot-basic/appPackage/manifest.json.tpl b/templates/ts/custom-copilot-basic/appPackage/manifest.json.tpl index c43027c3a7..8caabac564 100644 --- a/templates/ts/custom-copilot-basic/appPackage/manifest.json.tpl +++ b/templates/ts/custom-copilot-basic/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/ts/custom-copilot-basic/package.json.tpl b/templates/ts/custom-copilot-basic/package.json.tpl index 4b8d19e4c5..ecbfc8567d 100644 --- a/templates/ts/custom-copilot-basic/package.json.tpl +++ b/templates/ts/custom-copilot-basic/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Chat Bot Sample with Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,17 +26,17 @@ "url": "https://github.com" }, "dependencies": { - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^5.5.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/custom-copilot-basic/src/app/app.ts.tpl b/templates/ts/custom-copilot-basic/src/app/app.ts.tpl index 8e8f345573..248729cd6c 100644 --- a/templates/ts/custom-copilot-basic/src/app/app.ts.tpl +++ b/templates/ts/custom-copilot-basic/src/app/app.ts.tpl @@ -19,6 +19,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/ts/custom-copilot-basic/src/index.ts b/templates/ts/custom-copilot-basic/src/index.ts index 0db519818e..906a4db2be 100644 --- a/templates/ts/custom-copilot-basic/src/index.ts +++ b/templates/ts/custom-copilot-basic/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // This bot's adapter import adapter from "./adapter"; @@ -7,16 +7,16 @@ import adapter from "./adapter"; // This bot's main dialog. import app from "./app/app"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/custom-copilot-basic/teamsapp.local.yml.tpl b/templates/ts/custom-copilot-basic/teamsapp.local.yml.tpl index 2c7fb58640..25cd75b5df 100644 --- a/templates/ts/custom-copilot-basic/teamsapp.local.yml.tpl +++ b/templates/ts/custom-copilot-basic/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/ts/custom-copilot-basic/teamsapp.yml.tpl b/templates/ts/custom-copilot-basic/teamsapp.yml.tpl index 435dd9ae91..09077c2121 100644 --- a/templates/ts/custom-copilot-basic/teamsapp.yml.tpl +++ b/templates/ts/custom-copilot-basic/teamsapp.yml.tpl @@ -41,12 +41,14 @@ provision: # Teams Toolkit will download this bicep CLI version from github for you, # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 - + + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl b/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl +++ b/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/tasks.json b/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/tasks.json +++ b/templates/ts/custom-copilot-rag-azure-ai-search/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/README.md.tpl b/templates/ts/custom-copilot-rag-azure-ai-search/README.md.tpl index 0d0a981571..fbdc2b7fce 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/README.md.tpl +++ b/templates/ts/custom-copilot-rag-azure-ai-search/README.md.tpl @@ -12,7 +12,7 @@ This app template also demonstrates usage of techniques like: > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) {{#useOpenAI}} > - An account with [OpenAI](https://platform.openai.com/) and [Azure AI Search](https://azure.microsoft.com/en-us/products/ai-services/ai-search). diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl b/templates/ts/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl index d9463cdd88..b37d09e04a 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl +++ b/templates/ts/custom-copilot-rag-azure-ai-search/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/package.json.tpl b/templates/ts/custom-copilot-rag-azure-ai-search/package.json.tpl index 194ca8260c..84db981ee6 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/package.json.tpl +++ b/templates/ts/custom-copilot-rag-azure-ai-search/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit RAG Bot Sample with Azure AI Search and Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -29,17 +29,17 @@ }, "dependencies": { "@azure/search-documents": "^12.0.0", - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^5.5.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/src/app/app.ts.tpl b/templates/ts/custom-copilot-rag-azure-ai-search/src/app/app.ts.tpl index 9e1fc263b7..ade18b2a6e 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/src/app/app.ts.tpl +++ b/templates/ts/custom-copilot-rag-azure-ai-search/src/app/app.ts.tpl @@ -21,6 +21,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/src/app/customSayCommand.ts b/templates/ts/custom-copilot-rag-azure-ai-search/src/app/customSayCommand.ts index 703d1aec22..7357a0bf38 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/src/app/customSayCommand.ts +++ b/templates/ts/custom-copilot-rag-azure-ai-search/src/app/customSayCommand.ts @@ -1,6 +1,6 @@ import { ActivityTypes, Channels, TurnContext } from "botbuilder"; -import { PredictedSayCommand, TurnState, Utilities, ClientCitation } from "@microsoft/teams-ai"; -import { AIEntity } from "@microsoft/teams-ai/lib/actions/SayCommand"; +import { PredictedSayCommand, TurnState, Utilities } from "@microsoft/teams-ai"; +import { AIEntity, ClientCitation } from "@microsoft/teams-ai/lib/types"; export function sayCommand(feedbackLoopEnabled = false) { return async (context: TurnContext, _state: TState, data: PredictedSayCommand) => { diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/src/index.ts b/templates/ts/custom-copilot-rag-azure-ai-search/src/index.ts index 0db519818e..906a4db2be 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/src/index.ts +++ b/templates/ts/custom-copilot-rag-azure-ai-search/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // This bot's adapter import adapter from "./adapter"; @@ -7,16 +7,16 @@ import adapter from "./adapter"; // This bot's main dialog. import app from "./app/app"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl b/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl index b688445ca3..ced20e7a80 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl +++ b/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl b/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl index 435dd9ae91..6f956d86a3 100644 --- a/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl +++ b/templates/ts/custom-copilot-rag-azure-ai-search/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/ts/custom-copilot-rag-custom-api/.vscode/tasks.json b/templates/ts/custom-copilot-rag-custom-api/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/custom-copilot-rag-custom-api/.vscode/tasks.json +++ b/templates/ts/custom-copilot-rag-custom-api/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/custom-copilot-rag-custom-api/README.md.tpl b/templates/ts/custom-copilot-rag-custom-api/README.md.tpl index 894afcab7a..c6e9ad74e8 100644 --- a/templates/ts/custom-copilot-rag-custom-api/README.md.tpl +++ b/templates/ts/custom-copilot-rag-custom-api/README.md.tpl @@ -9,7 +9,7 @@ The app template is built using the Teams AI library, which provides the capabil > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl b/templates/ts/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl index d9463cdd88..0110a27ecc 100644 --- a/templates/ts/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl +++ b/templates/ts/custom-copilot-rag-custom-api/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/custom-copilot-rag-custom-api/package.json.tpl b/templates/ts/custom-copilot-rag-custom-api/package.json.tpl index 9ced9bcd1e..38b6d2c5d7 100644 --- a/templates/ts/custom-copilot-rag-custom-api/package.json.tpl +++ b/templates/ts/custom-copilot-rag-custom-api/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit AI Chat Bot Sample with Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -27,20 +27,21 @@ }, "dependencies": { "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0", + "botbuilder": "^4.23.1", + "express": "^5.0.1", "fs-extra": "^11.2.0", "js-yaml": "^4.1.0", "adaptivecards-templating": "^2.3.1", "openapi-client-axios": "^7.4.0" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", + "@types/json-schema": "^7.0.15", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^5.5.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/custom-copilot-rag-custom-api/src/app/utility.ts b/templates/ts/custom-copilot-rag-custom-api/src/app/utility.ts index 00ae6c1c61..2e94b7b412 100644 --- a/templates/ts/custom-copilot-rag-custom-api/src/app/utility.ts +++ b/templates/ts/custom-copilot-rag-custom-api/src/app/utility.ts @@ -2,9 +2,6 @@ import { CardFactory } from "botbuilder"; const ACData = require("adaptivecards-templating"); import { OpenAPIClient } from "openapi-client-axios"; export function generateAdaptiveCard(templatePath: string, result: any) { - if (!result || !result.data) { - throw new Error("Get empty result from api call."); - } const adaptiveCardTemplate = require(templatePath); const template = new ACData.Template(adaptiveCardTemplate); const cardContent = template.expand({ diff --git a/templates/ts/custom-copilot-rag-custom-api/src/index.ts b/templates/ts/custom-copilot-rag-custom-api/src/index.ts index 0db519818e..906a4db2be 100644 --- a/templates/ts/custom-copilot-rag-custom-api/src/index.ts +++ b/templates/ts/custom-copilot-rag-custom-api/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // This bot's adapter import adapter from "./adapter"; @@ -7,16 +7,16 @@ import adapter from "./adapter"; // This bot's main dialog. import app from "./app/app"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/custom-copilot-rag-customize/.vscode/launch.json.tpl b/templates/ts/custom-copilot-rag-customize/.vscode/launch.json.tpl index 71bbc4d363..6eb45d4ae3 100644 --- a/templates/ts/custom-copilot-rag-customize/.vscode/launch.json.tpl +++ b/templates/ts/custom-copilot-rag-customize/.vscode/launch.json.tpl @@ -2,24 +2,34 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +76,44 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "3-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -87,10 +126,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 1 }, @@ -105,10 +144,10 @@ "preLaunchTask": "Start Teams App Locally", "presentation": { {{#enableTestToolByDefault}} - "group": "2-local", + "group": "2-Teams", {{/enableTestToolByDefault}} {{^enableTestToolByDefault}} - "group": "1-local", + "group": "1-Teams", {{/enableTestToolByDefault}} "order": 2 }, @@ -121,7 +160,12 @@ ], "preLaunchTask": "Start Teams App in Desktop Client", "presentation": { - "group": "2-local", +{{#enableTestToolByDefault}} + "group": "2-Teams", +{{/enableTestToolByDefault}} +{{^enableTestToolByDefault}} + "group": "1-Teams", +{{/enableTestToolByDefault}} "order": 3 }, "stopAll": true @@ -142,6 +186,34 @@ "order": 1 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "3-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/ts/custom-copilot-rag-customize/.vscode/tasks.json b/templates/ts/custom-copilot-rag-customize/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/custom-copilot-rag-customize/.vscode/tasks.json +++ b/templates/ts/custom-copilot-rag-customize/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/custom-copilot-rag-customize/README.md.tpl b/templates/ts/custom-copilot-rag-customize/README.md.tpl index 825a7e55f4..a10a83acbc 100644 --- a/templates/ts/custom-copilot-rag-customize/README.md.tpl +++ b/templates/ts/custom-copilot-rag-customize/README.md.tpl @@ -11,7 +11,7 @@ This app template also demonstrates usage of techniques like: > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) {{#useOpenAI}} > - An account with [OpenAI](https://platform.openai.com/). diff --git a/templates/ts/custom-copilot-rag-customize/appPackage/manifest.json.tpl b/templates/ts/custom-copilot-rag-customize/appPackage/manifest.json.tpl index d9463cdd88..b37d09e04a 100644 --- a/templates/ts/custom-copilot-rag-customize/appPackage/manifest.json.tpl +++ b/templates/ts/custom-copilot-rag-customize/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/ts/custom-copilot-rag-customize/package.json.tpl b/templates/ts/custom-copilot-rag-customize/package.json.tpl index b9e189c48c..8889c77f04 100644 --- a/templates/ts/custom-copilot-rag-customize/package.json.tpl +++ b/templates/ts/custom-copilot-rag-customize/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit RAG Bot Sample with customize data source and Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -27,17 +27,17 @@ }, "dependencies": { "@azure/search-documents": "^12.0.0", - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^5.5.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/custom-copilot-rag-customize/src/app/app.ts.tpl b/templates/ts/custom-copilot-rag-customize/src/app/app.ts.tpl index db6fb153aa..2080465df4 100644 --- a/templates/ts/custom-copilot-rag-customize/src/app/app.ts.tpl +++ b/templates/ts/custom-copilot-rag-customize/src/app/app.ts.tpl @@ -21,6 +21,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/ts/custom-copilot-rag-customize/src/app/customSayCommand.ts b/templates/ts/custom-copilot-rag-customize/src/app/customSayCommand.ts index 703d1aec22..7357a0bf38 100644 --- a/templates/ts/custom-copilot-rag-customize/src/app/customSayCommand.ts +++ b/templates/ts/custom-copilot-rag-customize/src/app/customSayCommand.ts @@ -1,6 +1,6 @@ import { ActivityTypes, Channels, TurnContext } from "botbuilder"; -import { PredictedSayCommand, TurnState, Utilities, ClientCitation } from "@microsoft/teams-ai"; -import { AIEntity } from "@microsoft/teams-ai/lib/actions/SayCommand"; +import { PredictedSayCommand, TurnState, Utilities } from "@microsoft/teams-ai"; +import { AIEntity, ClientCitation } from "@microsoft/teams-ai/lib/types"; export function sayCommand(feedbackLoopEnabled = false) { return async (context: TurnContext, _state: TState, data: PredictedSayCommand) => { diff --git a/templates/ts/custom-copilot-rag-customize/src/index.ts b/templates/ts/custom-copilot-rag-customize/src/index.ts index 0db519818e..906a4db2be 100644 --- a/templates/ts/custom-copilot-rag-customize/src/index.ts +++ b/templates/ts/custom-copilot-rag-customize/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // This bot's adapter import adapter from "./adapter"; @@ -7,16 +7,16 @@ import adapter from "./adapter"; // This bot's main dialog. import app from "./app/app"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing diff --git a/templates/ts/custom-copilot-rag-customize/teamsapp.local.yml.tpl b/templates/ts/custom-copilot-rag-customize/teamsapp.local.yml.tpl index 2c7fb58640..4450b98a34 100644 --- a/templates/ts/custom-copilot-rag-customize/teamsapp.local.yml.tpl +++ b/templates/ts/custom-copilot-rag-customize/teamsapp.local.yml.tpl @@ -39,11 +39,13 @@ provision: channels: - name: msteams + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -52,11 +54,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -66,6 +70,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/ts/custom-copilot-rag-customize/teamsapp.yml.tpl b/templates/ts/custom-copilot-rag-customize/teamsapp.yml.tpl index 435dd9ae91..6f956d86a3 100644 --- a/templates/ts/custom-copilot-rag-customize/teamsapp.yml.tpl +++ b/templates/ts/custom-copilot-rag-customize/teamsapp.yml.tpl @@ -42,11 +42,13 @@ provision: # will use bicep CLI in PATH if you remove this config. bicepCliVersion: v0.9.1 + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -54,11 +56,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -66,6 +70,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -94,11 +109,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -106,11 +123,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/ts/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl b/templates/ts/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl index 0fff774b87..f0d5680f24 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl +++ b/templates/ts/custom-copilot-rag-microsoft365/.vscode/launch.json.tpl @@ -2,24 +2,24 @@ "version": "0.2.0", "configurations": [ { - "name": "Launch Remote (Edge)", + "name": "Launch Remote in Teams (Edge)", "type": "msedge", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 1 + "group": "1-Teams", + "order": 4 }, "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Chrome)", + "name": "Launch Remote in Teams (Chrome)", "type": "chrome", "request": "launch", "url": "https://teams.microsoft.com/l/app/${{TEAMS_APP_ID}}?installAppPackage=true&webjoin=true&${account-hint}", "presentation": { - "group": "3-remote", - "order": 2 + "group": "1-Teams", + "order": 5 }, "internalConsoleOptions": "neverOpen" }, @@ -66,15 +66,39 @@ "internalConsoleOptions": "neverOpen" }, { - "name": "Launch Remote (Desktop)", + "name": "Launch Remote in Teams (Desktop)", "type": "node", "request": "launch", "preLaunchTask": "Start Teams App in Desktop Client (Remote)", "presentation": { - "group": "3-remote", - "order": 3 + "group": "1-Teams", + "order": 6 }, "internalConsoleOptions": "neverOpen", + {{#CEAEnabled}} + }, + { + "name": "Launch Remote in Copilot (Edge)", + "type": "msedge", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "2-M365", + "order": 3 + }, + "internalConsoleOptions": "neverOpen" + }, + { + "name": "Launch Remote in Copilot (Chrome)", + "type": "chrome", + "request": "launch", + "url": "https://www.office.com/chat?auth=2&${account-hint}", + "presentation": { + "group": "2-M365", + "order": 4 + }, + "internalConsoleOptions": "neverOpen" + {{/CEAEnabled}} } ], "compounds": [ @@ -115,6 +139,34 @@ "order": 3 }, "stopAll": true + {{#CEAEnabled}} + }, + { + "name": "Debug in Copilot (Edge)", + "configurations": [ + "Launch Remote in Copilot (Edge)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "2-M365", + "order": 1 + }, + "stopAll": true + }, + { + "name": "Debug in Copilot (Chrome)", + "configurations": [ + "Launch Remote in Copilot (Chrome)", + "Attach to Local Service" + ], + "preLaunchTask": "Start Teams App Locally", + "presentation": { + "group": "2-M365", + "order": 2 + }, + "stopAll": true + {{/CEAEnabled}} } ] } diff --git a/templates/ts/custom-copilot-rag-microsoft365/.vscode/tasks.json b/templates/ts/custom-copilot-rag-microsoft365/.vscode/tasks.json index 615f0a126d..e6782df581 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/.vscode/tasks.json +++ b/templates/ts/custom-copilot-rag-microsoft365/.vscode/tasks.json @@ -97,7 +97,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/custom-copilot-rag-microsoft365/README.md.tpl b/templates/ts/custom-copilot-rag-microsoft365/README.md.tpl index 02faa0330c..16d023fc7d 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/README.md.tpl +++ b/templates/ts/custom-copilot-rag-microsoft365/README.md.tpl @@ -12,7 +12,7 @@ This app template also demonstrates usage of techniques like: > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A Microsoft 365 tenant in which you have permission to upload Teams apps. You can get a free Microsoft 365 developer tenant by joining the [Microsoft 365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program). > - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli). {{#useOpenAI}} diff --git a/templates/ts/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl b/templates/ts/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl index 6857c90093..598ea44631 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl +++ b/templates/ts/custom-copilot-rag-microsoft365/appPackage/manifest.json.tpl @@ -1,7 +1,14 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + {{#CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/vdevPreview/MicrosoftTeams.schema.json", + "manifestVersion": "devPreview", "version": "1.0.0", + {{/CEAEnabled}} + {{^CEAEnabled}} + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", + "version": "1.0.0", + {{/CEAEnabled}} "id": "${{TEAMS_APP_ID}}", "developer": { "name": "Teams App, Inc.", @@ -22,6 +29,16 @@ "full": "full description for {{appName}}" }, "accentColor": "#FFFFFF", + {{#CEAEnabled}} + "copilotAgents": { + "customEngineAgents": [ + { + "type": "bot", + "id": "${{BOT_ID}}" + } + ] + }, + {{/CEAEnabled}} "bots": [ { "botId": "${{BOT_ID}}", diff --git a/templates/ts/custom-copilot-rag-microsoft365/package.json.tpl b/templates/ts/custom-copilot-rag-microsoft365/package.json.tpl index 866918a85c..ff4a4181a8 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/package.json.tpl +++ b/templates/ts/custom-copilot-rag-microsoft365/package.json.tpl @@ -6,7 +6,7 @@ }, "description": "Microsoft Teams Toolkit RAG Bot Sample with Graph API and Teams AI Library", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -28,17 +28,17 @@ "dependencies": { "@microsoft/microsoft-graph-client": "^3.0.1", "@azure/search-documents": "^12.0.0", - "@microsoft/teams-ai": "^1.1.0", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "@microsoft/teams-ai": "^1.5.3", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^5.5.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/custom-copilot-rag-microsoft365/src/app/app.ts.tpl b/templates/ts/custom-copilot-rag-microsoft365/src/app/app.ts.tpl index 191d077f28..f483716417 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/src/app/app.ts.tpl +++ b/templates/ts/custom-copilot-rag-microsoft365/src/app/app.ts.tpl @@ -21,6 +21,9 @@ const model = new OpenAIModel({ useSystemMessages: true, logRequests: true, + {{#CEAEnabled}} + stream: true, + {{/CEAEnabled}} }); const prompts = new PromptManager({ promptsFolder: path.join(__dirname, "../prompts"), diff --git a/templates/ts/custom-copilot-rag-microsoft365/src/app/customSayCommand.ts b/templates/ts/custom-copilot-rag-microsoft365/src/app/customSayCommand.ts index 703d1aec22..7357a0bf38 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/src/app/customSayCommand.ts +++ b/templates/ts/custom-copilot-rag-microsoft365/src/app/customSayCommand.ts @@ -1,6 +1,6 @@ import { ActivityTypes, Channels, TurnContext } from "botbuilder"; -import { PredictedSayCommand, TurnState, Utilities, ClientCitation } from "@microsoft/teams-ai"; -import { AIEntity } from "@microsoft/teams-ai/lib/actions/SayCommand"; +import { PredictedSayCommand, TurnState, Utilities } from "@microsoft/teams-ai"; +import { AIEntity, ClientCitation } from "@microsoft/teams-ai/lib/types"; export function sayCommand(feedbackLoopEnabled = false) { return async (context: TurnContext, _state: TState, data: PredictedSayCommand) => { diff --git a/templates/ts/custom-copilot-rag-microsoft365/src/index.ts b/templates/ts/custom-copilot-rag-microsoft365/src/index.ts index 7062c984ab..e333aefa15 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/src/index.ts +++ b/templates/ts/custom-copilot-rag-microsoft365/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // This bot's adapter import adapter from "./adapter"; @@ -7,17 +7,18 @@ import adapter from "./adapter"; // This bot's main dialog. import app from "./app/app"; import path from "path"; +import send from "send"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Listen for incoming server requests. -server.post("/api/messages", async (req, res) => { +// Listen for incoming requests. +expressApp.post("/api/messages", async (req, res) => { // Route received a request to adapter for processing await adapter.process(req, res as any, async (context) => { // Dispatch to application for routing @@ -25,9 +26,13 @@ server.post("/api/messages", async (req, res) => { }); }); -server.get( - "/auth-:name(start|end).html", - restify.plugins.serveStatic({ - directory: path.join(__dirname, "public"), - }) -); +expressApp.get(["/auth-start.html", "/auth-end.html"], async (req, res) => { + send( + req, + path.join( + __dirname, + "public", + req.url.includes("auth-start.html") ? "auth-start.html" : "auth-end.html" + ) + ).pipe(res); +}); diff --git a/templates/ts/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl b/templates/ts/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl index 996095a982..b1c1d7cd0f 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl +++ b/templates/ts/custom-copilot-rag-microsoft365/teamsapp.local.yml.tpl @@ -57,11 +57,13 @@ provision: manifestPath: ./aad.manifest.json # Relative path to teamsfx folder. Environment variables in manifest will be replaced before apply to AAD app outputFilePath: ./build/aad.manifest.${{TEAMSFX_ENV}}.json + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage @@ -70,11 +72,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. @@ -84,6 +88,18 @@ provision: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip +{{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID +{{/CEAEnabled}} + deploy: # Run npm command - uses: cli/runNpmCommand diff --git a/templates/ts/custom-copilot-rag-microsoft365/teamsapp.yml.tpl b/templates/ts/custom-copilot-rag-microsoft365/teamsapp.yml.tpl index 726421f253..e2a5ba4492 100644 --- a/templates/ts/custom-copilot-rag-microsoft365/teamsapp.yml.tpl +++ b/templates/ts/custom-copilot-rag-microsoft365/teamsapp.yml.tpl @@ -60,11 +60,13 @@ provision: manifestPath: ./aad.manifest.json # Relative path to teamsfx folder. Environment variables in manifest will be replaced before apply to AAD app outputFilePath: ./build/aad.manifest.${{TEAMSFX_ENV}}.json + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -72,11 +74,13 @@ provision: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. @@ -84,6 +88,17 @@ provision: with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{#CEAEnabled}} + - uses: teamsApp/extendToM365 + with: + # Relative path to the build app package. + appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + # Write the information of created resources into environment file for + # the specified environment variable(s). + writeToEnvironmentFile: + titleId: M365_TITLE_ID + appId: M365_APP_ID + {{/CEAEnabled}} # Triggered when 'teamsapp deploy' is executed deploy: @@ -112,11 +127,13 @@ deploy: # Triggered when 'teamsapp publish' is executed publish: + {{^CEAEnabled}} # Validate using manifest schema - uses: teamsApp/validateManifest with: # Path to manifest template manifestPath: ./appPackage/manifest.json + {{/CEAEnabled}} # Build Teams app package with latest env value - uses: teamsApp/zipAppPackage with: @@ -124,11 +141,13 @@ publish: manifestPath: ./appPackage/manifest.json outputZipPath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip outputFolder: ./appPackage/build + {{^CEAEnabled}} # Validate app package using validation rules - uses: teamsApp/validateAppPackage with: # Relative path to this file. This is the path for built zip file. appPackagePath: ./appPackage/build/appPackage.${{TEAMSFX_ENV}}.zip + {{/CEAEnabled}} # Apply the Teams app manifest to an existing Teams app in # Teams Developer Portal. # Will use the app id in manifest file to determine which Teams app to update. diff --git a/templates/ts/dashboard-tab/README.md b/templates/ts/dashboard-tab/README.md index d5f23aef09..95958b0dcb 100644 --- a/templates/ts/dashboard-tab/README.md +++ b/templates/ts/dashboard-tab/README.md @@ -11,7 +11,7 @@ This template showcases an app that embeds a canvas containing multiple cards th > **Prerequisites** > To run the dashboard template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Set up your dev environment for extending Teams apps across Microsoft 365](https://aka.ms/teamsfx-m365-apps-prerequisites) > Please note that after you enrolled your developer tenant in Office 365 Target Release, it may take couple days for the enrollment to take effect. diff --git a/templates/ts/dashboard-tab/appPackage/manifest.json.tpl b/templates/ts/dashboard-tab/appPackage/manifest.json.tpl index 8dcd0c16c4..e7952fea56 100644 --- a/templates/ts/dashboard-tab/appPackage/manifest.json.tpl +++ b/templates/ts/dashboard-tab/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/dashboard-tab/package.json.tpl b/templates/ts/dashboard-tab/package.json.tpl index b72a8cc4d6..8e0011bc3e 100644 --- a/templates/ts/dashboard-tab/package.json.tpl +++ b/templates/ts/dashboard-tab/package.json.tpl @@ -2,17 +2,17 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.1.0", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "type": "module", "private": true, "dependencies": { "@fluentui/react-charting": "^5.14.10", - "@fluentui/react-components": "^9.18.0", + "@fluentui/react-components": "^9.55.1", "@fluentui/react-icons": "^2.0.186", - "@microsoft/teams-js": "^2.19.0", - "@microsoft/teamsfx": "^2.2.0", - "@microsoft/teamsfx-react": "^3.0.0", + "@microsoft/teams-js": "^2.22.0", + "@microsoft/teamsfx": "^3.0.0-alpha", + "@microsoft/teamsfx-react": "^4.0.0-alpha", "react": "^18.2.0", "react-dom": "^18.2.0", "react-router-dom": "^6.8.0" diff --git a/templates/ts/default-bot-message-extension/.vscode/tasks.json b/templates/ts/default-bot-message-extension/.vscode/tasks.json index 585f86ae9a..5644df6240 100644 --- a/templates/ts/default-bot-message-extension/.vscode/tasks.json +++ b/templates/ts/default-bot-message-extension/.vscode/tasks.json @@ -97,7 +97,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/ts/default-bot-message-extension/README.md b/templates/ts/default-bot-message-extension/README.md index bb5ba693dd..6fd1a65178 100644 --- a/templates/ts/default-bot-message-extension/README.md +++ b/templates/ts/default-bot-message-extension/README.md @@ -10,7 +10,7 @@ This is a simple hello world application with both Bot and Message extension cap ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - An M365 account. If you do not have M365 account, apply one from [M365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -43,7 +43,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | :------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the Teams Toolkit and click `Provision` from DEPLOYMENT section or open the command palette and select: `Teams: Provision`.
  • Open the Teams Toolkit and click `Deploy` or open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision --env dev`.
  • Run command: `teamsapp deploy --env dev`.
| diff --git a/templates/ts/default-bot-message-extension/appPackage/manifest.json.tpl b/templates/ts/default-bot-message-extension/appPackage/manifest.json.tpl index 7484a37b0c..d60c820186 100644 --- a/templates/ts/default-bot-message-extension/appPackage/manifest.json.tpl +++ b/templates/ts/default-bot-message-extension/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/default-bot-message-extension/package.json.tpl b/templates/ts/default-bot-message-extension/package.json.tpl index 33dfaa1d77..4ef49fc73c 100644 --- a/templates/ts/default-bot-message-extension/package.json.tpl +++ b/templates/ts/default-bot-message-extension/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit hello world Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -24,15 +24,16 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", + "@types/json-schema": "^7.0.15", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7" + "nodemon": "^3.1.7" } } \ No newline at end of file diff --git a/templates/ts/default-bot-message-extension/src/index.ts b/templates/ts/default-bot-message-extension/src/index.ts index 5e1926a532..ab6308ee18 100644 --- a/templates/ts/default-bot-message-extension/src/index.ts +++ b/templates/ts/default-bot-message-extension/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -51,15 +51,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/ts/default-bot/.vscode/tasks.json b/templates/ts/default-bot/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/default-bot/.vscode/tasks.json +++ b/templates/ts/default-bot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/default-bot/README.md.tpl b/templates/ts/default-bot/README.md.tpl index 11dc8744a3..f8f63d47a2 100644 --- a/templates/ts/default-bot/README.md.tpl +++ b/templates/ts/default-bot/README.md.tpl @@ -14,7 +14,7 @@ A bot interaction can be a quick question and answer, or it can be a complex con > > To run the Basic Bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/default-bot/appPackage/manifest.json.tpl b/templates/ts/default-bot/appPackage/manifest.json.tpl index 7e3b1973bb..58e66c293e 100644 --- a/templates/ts/default-bot/appPackage/manifest.json.tpl +++ b/templates/ts/default-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/default-bot/index.ts b/templates/ts/default-bot/index.ts index 27c731da77..c8c6da2940 100644 --- a/templates/ts/default-bot/index.ts +++ b/templates/ts/default-bot/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -54,15 +54,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/ts/default-bot/package.json.tpl b/templates/ts/default-bot/package.json.tpl index f85f9d0e89..c7c68fbf76 100644 --- a/templates/ts/default-bot/package.json.tpl +++ b/templates/ts/default-bot/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit hello world Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,16 +23,16 @@ "url": "https://github.com" }, "dependencies": { - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/link-unfurling/.vscode/tasks.json b/templates/ts/link-unfurling/.vscode/tasks.json index fdd3407c37..83ee7eb356 100644 --- a/templates/ts/link-unfurling/.vscode/tasks.json +++ b/templates/ts/link-unfurling/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/link-unfurling/README.md.tpl b/templates/ts/link-unfurling/README.md.tpl index 8c3f1add09..40885a5e96 100644 --- a/templates/ts/link-unfurling/README.md.tpl +++ b/templates/ts/link-unfurling/README.md.tpl @@ -13,7 +13,7 @@ This template showcases an app that unfurls a link into an adaptive card when UR > **Prerequisites** > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A Microsoft 365 account. If you do not have Microsoft 365 account, apply one from [Microsoft 365 developer program](https://developer.microsoft.com/microsoft-365/dev-program) {{/enableMETestToolByDefault}} @@ -50,7 +50,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | --------------------------------------- | ---------------------------------------------- | -| `src/index.ts` | Application entry point and `restify` handlers | +| `src/index.ts` | Application entry point and `express` handlers | | `src/linkUnfurlingApp.ts` | The teams activity handler | | `src/adaptiveCards/helloWorldCard.json` | The adaptive card | diff --git a/templates/ts/link-unfurling/appPackage/manifest.json.tpl b/templates/ts/link-unfurling/appPackage/manifest.json.tpl index 61044d2411..5922642ac1 100644 --- a/templates/ts/link-unfurling/appPackage/manifest.json.tpl +++ b/templates/ts/link-unfurling/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/link-unfurling/package.json.tpl b/templates/ts/link-unfurling/package.json.tpl index 4b4164e710..85c4d995dc 100644 --- a/templates/ts/link-unfurling/package.json.tpl +++ b/templates/ts/link-unfurling/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit link unfurling sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,16 +23,16 @@ "url": "https://github.com" }, "dependencies": { - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/link-unfurling/src/index.ts b/templates/ts/link-unfurling/src/index.ts index ae446b9802..05bf628563 100644 --- a/templates/ts/link-unfurling/src/index.ts +++ b/templates/ts/link-unfurling/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; import { CloudAdapter, ConfigurationServiceClientCredentialFactory, @@ -46,15 +46,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the bot that will handle user pasted links. const linkUnfurlingApp = new LinkUnfurlingApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await linkUnfurlingApp.run(context); }); diff --git a/templates/ts/m365-message-extension/.vscode/tasks.json b/templates/ts/m365-message-extension/.vscode/tasks.json index fdd3407c37..83ee7eb356 100644 --- a/templates/ts/m365-message-extension/.vscode/tasks.json +++ b/templates/ts/m365-message-extension/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/m365-message-extension/README.md.tpl b/templates/ts/m365-message-extension/README.md.tpl index 27221970cd..006febe031 100644 --- a/templates/ts/m365-message-extension/README.md.tpl +++ b/templates/ts/m365-message-extension/README.md.tpl @@ -8,7 +8,7 @@ This app template is a search-based [message extension](https://docs.microsoft.c > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Set up your dev environment for extending Teams apps across Microsoft 365](https://aka.ms/teamsfx-m365-apps-prerequisites) diff --git a/templates/ts/m365-message-extension/appPackage/manifest.json.tpl b/templates/ts/m365-message-extension/appPackage/manifest.json.tpl index ada4841ede..449ee0e13f 100644 --- a/templates/ts/m365-message-extension/appPackage/manifest.json.tpl +++ b/templates/ts/m365-message-extension/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/m365-message-extension/package.json.tpl b/templates/ts/m365-message-extension/package.json.tpl index 99dbd13013..667d9cd809 100644 --- a/templates/ts/m365-message-extension/package.json.tpl +++ b/templates/ts/m365-message-extension/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit message extension search sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,16 +26,17 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", + "@types/json-schema": "^7.0.15", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/m365-message-extension/src/index.ts b/templates/ts/m365-message-extension/src/index.ts index a2568e3a08..d943241dd7 100644 --- a/templates/ts/m365-message-extension/src/index.ts +++ b/templates/ts/m365-message-extension/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -51,15 +51,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the bot that will handle incoming messages. const searchApp = new SearchApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await searchApp.run(context); }); diff --git a/templates/ts/message-extension-action/.vscode/tasks.json b/templates/ts/message-extension-action/.vscode/tasks.json index fdd3407c37..83ee7eb356 100644 --- a/templates/ts/message-extension-action/.vscode/tasks.json +++ b/templates/ts/message-extension-action/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/message-extension-action/README.md.tpl b/templates/ts/message-extension-action/README.md.tpl index 77002731fd..2643477986 100644 --- a/templates/ts/message-extension-action/README.md.tpl +++ b/templates/ts/message-extension-action/README.md.tpl @@ -10,7 +10,7 @@ This app template implements action command that allows you to present your user > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableMETestToolByDefault}} diff --git a/templates/ts/message-extension-action/appPackage/manifest.json.tpl b/templates/ts/message-extension-action/appPackage/manifest.json.tpl index 5ce95fa567..6428e7842f 100644 --- a/templates/ts/message-extension-action/appPackage/manifest.json.tpl +++ b/templates/ts/message-extension-action/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/message-extension-action/package.json.tpl b/templates/ts/message-extension-action/package.json.tpl index 4c2ba6cff5..341f331d40 100644 --- a/templates/ts/message-extension-action/package.json.tpl +++ b/templates/ts/message-extension-action/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit message extension action sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,16 +26,17 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", + "@types/json-schema": "^7.0.15", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/message-extension-action/src/index.ts b/templates/ts/message-extension-action/src/index.ts index 01d40a7422..3086d0e338 100644 --- a/templates/ts/message-extension-action/src/index.ts +++ b/templates/ts/message-extension-action/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; import { CloudAdapter, ConfigurationServiceClientCredentialFactory, @@ -46,15 +46,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the app that will handle action commands. const actionApp = new ActionApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await actionApp.run(context); }); diff --git a/templates/ts/message-extension-copilot/.vscode/tasks.json b/templates/ts/message-extension-copilot/.vscode/tasks.json index 5a6577873d..2e9b16cefc 100644 --- a/templates/ts/message-extension-copilot/.vscode/tasks.json +++ b/templates/ts/message-extension-copilot/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -220,7 +220,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/message-extension-copilot/README.md.tpl b/templates/ts/message-extension-copilot/README.md.tpl index 8956b6d3ab..bff9beea4a 100644 --- a/templates/ts/message-extension-copilot/README.md.tpl +++ b/templates/ts/message-extension-copilot/README.md.tpl @@ -8,7 +8,7 @@ This app template is a search-based [message extension](https://docs.microsoft.c > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) > - [Set up your dev environment for extending Teams apps across Microsoft 365](https://aka.ms/teamsfx-m365-apps-prerequisites) > Please note that after you enrolled your developer tenant in Office 365 Target Release, it may take couple days for the enrollment to take effect. diff --git a/templates/ts/message-extension-copilot/package.json.tpl b/templates/ts/message-extension-copilot/package.json.tpl index e4883775a8..2a05ceb95c 100644 --- a/templates/ts/message-extension-copilot/package.json.tpl +++ b/templates/ts/message-extension-copilot/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit message extension search sample", "engines": { - "node": "16 || 18 || 20" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,11 +26,12 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^11.1.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", + "@types/json-schema": "^7.0.15", "@types/node": "^20.8.9", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", diff --git a/templates/ts/message-extension-copilot/src/index.ts b/templates/ts/message-extension-copilot/src/index.ts index a2568e3a08..d943241dd7 100644 --- a/templates/ts/message-extension-copilot/src/index.ts +++ b/templates/ts/message-extension-copilot/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -51,15 +51,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the bot that will handle incoming messages. const searchApp = new SearchApp(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await searchApp.run(context); }); diff --git a/templates/ts/message-extension/.vscode/tasks.json b/templates/ts/message-extension/.vscode/tasks.json index 53c41778d7..77ee69444c 100644 --- a/templates/ts/message-extension/.vscode/tasks.json +++ b/templates/ts/message-extension/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } } diff --git a/templates/ts/message-extension/README.md.tpl b/templates/ts/message-extension/README.md.tpl index ed2760f416..2fb207ebaf 100644 --- a/templates/ts/message-extension/README.md.tpl +++ b/templates/ts/message-extension/README.md.tpl @@ -14,7 +14,7 @@ This app template has a search command, an action command and a link unfurling. > > To run the template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableMETestToolByDefault}} > - A [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableMETestToolByDefault}} diff --git a/templates/ts/message-extension/appPackage/manifest.json.tpl b/templates/ts/message-extension/appPackage/manifest.json.tpl index b5f111aed4..5b24b6bac6 100644 --- a/templates/ts/message-extension/appPackage/manifest.json.tpl +++ b/templates/ts/message-extension/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/message-extension/package.json.tpl b/templates/ts/message-extension/package.json.tpl index b91e0372e7..a47f8a518a 100644 --- a/templates/ts/message-extension/package.json.tpl +++ b/templates/ts/message-extension/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit message extension Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,16 +26,17 @@ "adaptive-expressions": "^4.20.0", "adaptivecards-templating": "^2.3.1", "adaptivecards": "^3.0.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", + "@types/json-schema": "^7.0.15", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/message-extension/src/index.ts b/templates/ts/message-extension/src/index.ts index 5e1926a532..ab6308ee18 100644 --- a/templates/ts/message-extension/src/index.ts +++ b/templates/ts/message-extension/src/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -51,15 +51,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/ts/non-sso-tab-default-bot/.vscode/tasks.json b/templates/ts/non-sso-tab-default-bot/.vscode/tasks.json index 0d868529e2..b0da907b12 100644 --- a/templates/ts/non-sso-tab-default-bot/.vscode/tasks.json +++ b/templates/ts/non-sso-tab-default-bot/.vscode/tasks.json @@ -105,7 +105,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/non-sso-tab-default-bot/appPackage/manifest.json.tpl b/templates/ts/non-sso-tab-default-bot/appPackage/manifest.json.tpl index 0976d52947..4970986dc9 100644 --- a/templates/ts/non-sso-tab-default-bot/appPackage/manifest.json.tpl +++ b/templates/ts/non-sso-tab-default-bot/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/non-sso-tab-default-bot/bot/README.md b/templates/ts/non-sso-tab-default-bot/bot/README.md index 489e8cfc0d..689fd2837b 100644 --- a/templates/ts/non-sso-tab-default-bot/bot/README.md +++ b/templates/ts/non-sso-tab-default-bot/bot/README.md @@ -10,7 +10,7 @@ This is a simple hello world application with both Bot and Message extension cap ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - An M365 account. If you do not have M365 account, apply one from [M365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -43,7 +43,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | :------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the Teams Toolkit and click `Provision` from DEPLOYMENT section or open the command palette and select: `Teams: Provision`.
  • Open the Teams Toolkit and click `Deploy` or open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision --env dev`.
  • Run command: `teamsapp deploy --env dev`.
| @@ -125,4 +125,3 @@ To trigger these functions, there are multiple entry points: - [Search Command](https://docs.microsoft.com/en-us/microsoftteams/platform/messaging-extensions/how-to/search-commands/define-search-command) - [Action Command](https://docs.microsoft.com/en-us/microsoftteams/platform/messaging-extensions/how-to/action-commands/define-action-command) - [Link Unfurling](https://docs.microsoft.com/en-us/microsoftteams/platform/messaging-extensions/how-to/link-unfurling?tabs=dotnet) - diff --git a/templates/ts/non-sso-tab-default-bot/bot/index.ts b/templates/ts/non-sso-tab-default-bot/bot/index.ts index 27c731da77..c8c6da2940 100644 --- a/templates/ts/non-sso-tab-default-bot/bot/index.ts +++ b/templates/ts/non-sso-tab-default-bot/bot/index.ts @@ -1,5 +1,5 @@ // Import required packages -import * as restify from "restify"; +import express from "express"; // Import required bot services. // See https://aka.ms/bot-services to learn more about the different parts of a bot. @@ -54,15 +54,16 @@ adapter.onTurnError = onTurnErrorHandler; // Create the bot that will handle incoming messages. const bot = new TeamsBot(); -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); // Listen for incoming requests. -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await adapter.process(req, res, async (context) => { await bot.run(context); }); diff --git a/templates/ts/non-sso-tab-default-bot/bot/package.json.tpl b/templates/ts/non-sso-tab-default-bot/bot/package.json.tpl index a52cdd6dde..ef539e6a34 100644 --- a/templates/ts/non-sso-tab-default-bot/bot/package.json.tpl +++ b/templates/ts/non-sso-tab-default-bot/bot/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit hello world Bot sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -23,17 +23,17 @@ "dependencies": { "adaptivecards-templating": "^2.3.1", "adaptive-expressions": "^4.22.3", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/json-schema": "^7.0.15", "@types/node": "^18.0.0", "env-cmd": "^10.1.0", "ts-node": "^10.4.0", "typescript": "^4.4.4", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.3" } } \ No newline at end of file diff --git a/templates/ts/non-sso-tab-default-bot/package.json.tpl b/templates/ts/non-sso-tab-default-bot/package.json.tpl index fc1385a3b9..4a0c245ea1 100644 --- a/templates/ts/non-sso-tab-default-bot/package.json.tpl +++ b/templates/ts/non-sso-tab-default-bot/package.json.tpl @@ -2,7 +2,7 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.0.1", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", diff --git a/templates/ts/non-sso-tab-default-bot/tab/README.md b/templates/ts/non-sso-tab-default-bot/tab/README.md index df224d11c9..55da83bd21 100644 --- a/templates/ts/non-sso-tab-default-bot/tab/README.md +++ b/templates/ts/non-sso-tab-default-bot/tab/README.md @@ -4,7 +4,7 @@ Microsoft Teams supports the ability to run web-based UI inside "custom tabs" th ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - An M365 account. If you do not have M365 account, apply one from [M365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -29,7 +29,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the Teams Toolkit and click `Provision` from DEVELOPMENT section or open the command palette and select: `Teams: Provision`.
  • Open the Teams Toolkit and click `Deploy` or open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision --env dev`.
  • Run command: `teamsapp deploy --env dev`.
| @@ -71,4 +71,3 @@ Once deployed, you may want to distribute your application to your organization' Microsoft Teams provides a mechanism by which an application can obtain the signed-in Teams user token to access Microsoft Graph (and other APIs). Teams Toolkit facilitates this interaction by abstracting some of the Microsoft Entra flows and integrations behind some simple, high-level APIs. This enables you to add single sign-on (SSO) features easily to your Teams application. Please follow this [document](https://aka.ms/teamsfx-add-sso-new) to add single sign on for your project. - diff --git a/templates/ts/non-sso-tab-default-bot/tab/package.json.tpl b/templates/ts/non-sso-tab-default-bot/tab/package.json.tpl index 3800e29ea4..cf75cad808 100644 --- a/templates/ts/non-sso-tab-default-bot/tab/package.json.tpl +++ b/templates/ts/non-sso-tab-default-bot/tab/package.json.tpl @@ -2,14 +2,14 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.1.0", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "private": true, "dependencies": { - "@fluentui/react-components": "^9.18.0", - "@microsoft/teams-js": "^2.19.0", - "@microsoft/teamsfx": "^2.2.0", - "@microsoft/teamsfx-react": "^3.0.0", + "@fluentui/react-components": "^9.55.1", + "@microsoft/teams-js": "^2.22.0", + "@microsoft/teamsfx": "^3.0.0-alpha", + "@microsoft/teamsfx-react": "^4.0.0-alpha", "axios": "^0.21.1", "react": "^18.2.0", "react-dom": "^18.2.0", diff --git a/templates/ts/non-sso-tab/README.md b/templates/ts/non-sso-tab/README.md index 482a88f83d..db1e1728d7 100644 --- a/templates/ts/non-sso-tab/README.md +++ b/templates/ts/non-sso-tab/README.md @@ -40,7 +40,7 @@ The following files can be customized and demonstrate an example implementation | `src/static/scripts/teamsapp.js` | A script that calls `teamsjs` SDK to get the context of on which Microsoft 365 application your app is running. | | `src/static/styles/custom.css` | css file for the app. | | `src/static/views/hello.html` | html file for the app. | -| `src/app.ts` | Starting a restify server. | +| `src/app.ts` | Starting an `express` server. | The following are Teams Toolkit specific project files. You can [visit a complete guide on Github](https://github.com/OfficeDev/TeamsFx/wiki/Teams-Toolkit-Visual-Studio-Code-v5-Guide#overview) to understand how Teams Toolkit works. diff --git a/templates/ts/non-sso-tab/appPackage/manifest.json.tpl b/templates/ts/non-sso-tab/appPackage/manifest.json.tpl index 4199df99a3..009f2ff2cf 100644 --- a/templates/ts/non-sso-tab/appPackage/manifest.json.tpl +++ b/templates/ts/non-sso-tab/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/non-sso-tab/package.json.tpl b/templates/ts/non-sso-tab/package.json.tpl index fa8b15cff4..892cf6d149 100644 --- a/templates/ts/non-sso-tab/package.json.tpl +++ b/templates/ts/non-sso-tab/package.json.tpl @@ -2,20 +2,20 @@ "name": "{{SafeProjectNameLowerCase}}", "version": "0.1.0", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "private": true, "main": "./lib/app.js", "dependencies": { - "restify": "^11.1.0", + "express": "^4.21.1", "send": "^0.18.0" }, "devDependencies": { "@types/node": "^18.0.0", - "@types/restify": "^8.5.6", + "@types/express": "^5.0.0", "@types/send": "^0.17.1", "env-cmd": "^10.1.0", - "nodemon": "^2.0.21", + "nodemon": "^3.1.7", "ts-node": "^10.9.1", "typescript": "^4.1.2", "shx": "^0.3.3" diff --git a/templates/ts/non-sso-tab/src/app.ts b/templates/ts/non-sso-tab/src/app.ts index 168059bc8c..00174d8ef7 100644 --- a/templates/ts/non-sso-tab/src/app.ts +++ b/templates/ts/non-sso-tab/src/app.ts @@ -1,36 +1,38 @@ -import * as restify from "restify"; +import express from "express"; import * as fs from "fs"; +import * as https from "https"; +import * as path from "path"; import send from "send"; -//Create HTTP server. -const server = restify.createServer({ - key: process.env.SSL_KEY_FILE ? fs.readFileSync(process.env.SSL_KEY_FILE) : undefined, - certificate: process.env.SSL_CRT_FILE ? fs.readFileSync(process.env.SSL_CRT_FILE) : undefined, - formatters: { - "text/html": (req, res, body) => { - return body; - }, - }, -}); +const app = express(); -server.get( - "/static/*", - restify.plugins.serveStatic({ - directory: __dirname, - }) -); +const sslOptions = { + key: process.env.SSL_KEY_FILE ? fs.readFileSync(process.env.SSL_KEY_FILE) : undefined, + cert: process.env.SSL_CRT_FILE ? fs.readFileSync(process.env.SSL_CRT_FILE) : undefined, +}; -server.listen(process.env.port || process.env.PORT || 3333, function () { - console.log(`\n${server.name} listening to ${server.url}`); -}); +app.use("/static", express.static(path.join(__dirname, "static"))); // Adding tabs to our app. This will setup routes to various views // Setup home page -server.get("/", (req, res, next) => { - send(req, __dirname + "/views/hello.html").pipe(res); +app.get("/", (req, res) => { + send(req, path.join(__dirname, "views", "hello.html")).pipe(res); }); // Setup the static tab -server.get("/tab", (req, res, next) => { - send(req, __dirname + "/views/hello.html").pipe(res); +app.get("/tab", (req, res) => { + send(req, path.join(__dirname, "views", "hello.html")).pipe(res); }); + +// Create HTTP server +const port = process.env.port || process.env.PORT || 3333; + +if (sslOptions.key && sslOptions.cert) { + https.createServer(sslOptions, app).listen(port, () => { + console.log(`Express server listening on port ${port}`); + }); +} else { + app.listen(port, () => { + console.log(`Express server listening on port ${port}`); + }); +} diff --git a/templates/ts/notification-restify/.appserviceignore b/templates/ts/notification-express/.appserviceignore similarity index 100% rename from templates/ts/notification-restify/.appserviceignore rename to templates/ts/notification-express/.appserviceignore diff --git a/templates/ts/notification-restify/.gitignore b/templates/ts/notification-express/.gitignore similarity index 100% rename from templates/ts/notification-restify/.gitignore rename to templates/ts/notification-express/.gitignore diff --git a/templates/ts/notification-restify/.localConfigs b/templates/ts/notification-express/.localConfigs similarity index 100% rename from templates/ts/notification-restify/.localConfigs rename to templates/ts/notification-express/.localConfigs diff --git a/templates/ts/notification-restify/.localConfigs.testTool b/templates/ts/notification-express/.localConfigs.testTool similarity index 100% rename from templates/ts/notification-restify/.localConfigs.testTool rename to templates/ts/notification-express/.localConfigs.testTool diff --git a/templates/ts/notification-restify/.vscode/extensions.json b/templates/ts/notification-express/.vscode/extensions.json similarity index 100% rename from templates/ts/notification-restify/.vscode/extensions.json rename to templates/ts/notification-express/.vscode/extensions.json diff --git a/templates/ts/notification-restify/.vscode/launch.json.tpl b/templates/ts/notification-express/.vscode/launch.json.tpl similarity index 100% rename from templates/ts/notification-restify/.vscode/launch.json.tpl rename to templates/ts/notification-express/.vscode/launch.json.tpl diff --git a/templates/ts/notification-restify/.vscode/settings.json b/templates/ts/notification-express/.vscode/settings.json similarity index 100% rename from templates/ts/notification-restify/.vscode/settings.json rename to templates/ts/notification-express/.vscode/settings.json diff --git a/templates/ts/notification-restify/.vscode/tasks.json b/templates/ts/notification-express/.vscode/tasks.json similarity index 97% rename from templates/ts/notification-restify/.vscode/tasks.json rename to templates/ts/notification-express/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/notification-restify/.vscode/tasks.json +++ b/templates/ts/notification-express/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/notification-restify/README.md.tpl b/templates/ts/notification-express/README.md.tpl similarity index 98% rename from templates/ts/notification-restify/README.md.tpl rename to templates/ts/notification-express/README.md.tpl index e2067d5b83..f420062a06 100644 --- a/templates/ts/notification-restify/README.md.tpl +++ b/templates/ts/notification-express/README.md.tpl @@ -11,7 +11,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} @@ -65,7 +65,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | - | - | -| `src/index.ts` | Application entry point and `restify` handlers for notifications | +| `src/index.ts` | Application entry point and `express` handlers for notifications | | `src/teamsBot.ts`| An empty teams activity handler for bot customization | | `src/adaptiveCards/notification-default.json` | A generated Adaptive Card that is sent to Teams | | `src/cardModels.ts` | The default Adaptive Card data model | @@ -80,7 +80,7 @@ There are few customizations you can make to extend the template to fit your bus ### Step 1: Customize the trigger point from event source -By default Teams Toolkit scaffolds a single `restify` entry point in `src/index.ts`. When a HTTP request is sent to this entry point, the default implementation sends a hard-coded Adaptive Card to Teams. You can customize this behavior by customizing `src/index.ts`. A typical implementation might make an API call to retrieve some events and/or data, and then send an Adaptive Card as appropriate. +By default Teams Toolkit scaffolds a single `express` entry point in `src/index.ts`. When a HTTP request is sent to this entry point, the default implementation sends a hard-coded Adaptive Card to Teams. You can customize this behavior by customizing `src/index.ts`. A typical implementation might make an API call to retrieve some events and/or data, and then send an Adaptive Card as appropriate. You can also add additional triggers by: diff --git a/templates/ts/notification-restify/appPackage/color.png b/templates/ts/notification-express/appPackage/color.png similarity index 100% rename from templates/ts/notification-restify/appPackage/color.png rename to templates/ts/notification-express/appPackage/color.png diff --git a/templates/js/notification-restify/appPackage/manifest.json.tpl b/templates/ts/notification-express/appPackage/manifest.json.tpl similarity index 93% rename from templates/js/notification-restify/appPackage/manifest.json.tpl rename to templates/ts/notification-express/appPackage/manifest.json.tpl index a84fb3dad2..c741c67b69 100644 --- a/templates/js/notification-restify/appPackage/manifest.json.tpl +++ b/templates/ts/notification-express/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/notification-restify/appPackage/outline.png b/templates/ts/notification-express/appPackage/outline.png similarity index 100% rename from templates/ts/notification-restify/appPackage/outline.png rename to templates/ts/notification-express/appPackage/outline.png diff --git a/templates/ts/notification-restify/env/.env.dev b/templates/ts/notification-express/env/.env.dev similarity index 100% rename from templates/ts/notification-restify/env/.env.dev rename to templates/ts/notification-express/env/.env.dev diff --git a/templates/ts/notification-restify/env/.env.dev.user b/templates/ts/notification-express/env/.env.dev.user similarity index 100% rename from templates/ts/notification-restify/env/.env.dev.user rename to templates/ts/notification-express/env/.env.dev.user diff --git a/templates/ts/notification-restify/env/.env.local b/templates/ts/notification-express/env/.env.local similarity index 100% rename from templates/ts/notification-restify/env/.env.local rename to templates/ts/notification-express/env/.env.local diff --git a/templates/ts/notification-restify/env/.env.local.user b/templates/ts/notification-express/env/.env.local.user similarity index 100% rename from templates/ts/notification-restify/env/.env.local.user rename to templates/ts/notification-express/env/.env.local.user diff --git a/templates/ts/notification-restify/env/.env.testtool b/templates/ts/notification-express/env/.env.testtool similarity index 100% rename from templates/ts/notification-restify/env/.env.testtool rename to templates/ts/notification-express/env/.env.testtool diff --git a/templates/ts/notification-restify/infra/azure.bicep b/templates/ts/notification-express/infra/azure.bicep similarity index 100% rename from templates/ts/notification-restify/infra/azure.bicep rename to templates/ts/notification-express/infra/azure.bicep diff --git a/templates/ts/notification-restify/infra/azure.parameters.json.tpl b/templates/ts/notification-express/infra/azure.parameters.json.tpl similarity index 100% rename from templates/ts/notification-restify/infra/azure.parameters.json.tpl rename to templates/ts/notification-express/infra/azure.parameters.json.tpl diff --git a/templates/ts/notification-restify/infra/botRegistration/azurebot.bicep b/templates/ts/notification-express/infra/botRegistration/azurebot.bicep similarity index 100% rename from templates/ts/notification-restify/infra/botRegistration/azurebot.bicep rename to templates/ts/notification-express/infra/botRegistration/azurebot.bicep diff --git a/templates/ts/notification-restify/infra/botRegistration/readme.md b/templates/ts/notification-express/infra/botRegistration/readme.md similarity index 100% rename from templates/ts/notification-restify/infra/botRegistration/readme.md rename to templates/ts/notification-express/infra/botRegistration/readme.md diff --git a/templates/ts/notification-restify/package.json.tpl b/templates/ts/notification-express/package.json.tpl similarity index 83% rename from templates/ts/notification-restify/package.json.tpl rename to templates/ts/notification-express/package.json.tpl index ae03bfe9cb..ddd96cce86 100644 --- a/templates/ts/notification-restify/package.json.tpl +++ b/templates/ts/notification-express/package.json.tpl @@ -1,9 +1,9 @@ { "name": "{{SafeProjectNameLowerCase}}", "version": "1.0.0", - "description": "Microsoft Teams Toolkit Notification Bot Sample (Restify)", + "description": "Microsoft Teams Toolkit Notification Bot Sample (Express)", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -24,17 +24,17 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "@types/json-schema": "^7.0.15", "env-cmd": "^10.1.0", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "ts-node": "^10.4.0", "typescript": "^4.4.4", "shx": "^0.3.4" diff --git a/templates/ts/notification-restify/src/adaptiveCards/notification-default.json b/templates/ts/notification-express/src/adaptiveCards/notification-default.json similarity index 100% rename from templates/ts/notification-restify/src/adaptiveCards/notification-default.json rename to templates/ts/notification-express/src/adaptiveCards/notification-default.json diff --git a/templates/ts/notification-restify/src/index.ts b/templates/ts/notification-express/src/index.ts similarity index 64% rename from templates/ts/notification-restify/src/index.ts rename to templates/ts/notification-express/src/index.ts index 74ac1932b5..12117ab0c5 100644 --- a/templates/ts/notification-restify/src/index.ts +++ b/templates/ts/notification-express/src/index.ts @@ -1,18 +1,18 @@ import * as ACData from "adaptivecards-templating"; -import * as restify from "restify"; +import express from "express"; import notificationTemplate from "./adaptiveCards/notification-default.json"; import { notificationApp } from "./internal/initialize"; -import { CardData } from "./cardModels"; import { TeamsBot } from "./teamsBot"; -// Create HTTP server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nApp Started, ${server.name} listening to ${server.url}`); +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Register an API endpoint with `restify`. +// Register an API endpoint with `express`. // // This endpoint is provided by your application to listen to events. You can configure // your IT processes, other applications, background tasks, etc - to POST events to this @@ -23,38 +23,34 @@ server.listen(process.env.port || process.env.PORT || 3978, () => { // // You can add authentication / authorization for this API. Refer to // https://aka.ms/teamsfx-notification for more details. -server.post( - "/api/notification", - restify.plugins.queryParser(), - restify.plugins.bodyParser(), // Add more parsers if needed - async (req, res) => { - // By default this function will iterate all the installation points and send an Adaptive Card - // to every installation. - const pageSize = 100; - let continuationToken: string | undefined = undefined; - do { - const pagedData = await notificationApp.notification.getPagedInstallations( - pageSize, - continuationToken - ); - const installations = pagedData.data; - continuationToken = pagedData.continuationToken; +expressApp.post("/api/notification", async (req, res) => { + // By default this function will iterate all the installation points and send an Adaptive Card + // to every installation. + const pageSize = 100; + let continuationToken: string | undefined = undefined; + do { + const pagedData = await notificationApp.notification.getPagedInstallations( + pageSize, + continuationToken + ); + const installations = pagedData.data; + continuationToken = pagedData.continuationToken; - for (const target of installations) { - await target.sendAdaptiveCard( - new ACData.Template(notificationTemplate).expand({ - $root: { - title: "New Event Occurred!", - appName: "Contoso App Notification", - description: `This is a sample http-triggered notification to ${target.type}`, - notificationUrl: "https://aka.ms/teamsfx-notification-new", - }, - }) - ); + for (const target of installations) { + await target.sendAdaptiveCard( + new ACData.Template(notificationTemplate).expand({ + $root: { + title: "New Event Occurred!", + appName: "Contoso App Notification", + description: `This is a sample http-triggered notification to ${target.type}`, + notificationUrl: "https://aka.ms/teamsfx-notification-new", + }, + }) + ); - // Note - you can filter the installations if you don't want to send the event to every installation. + // Note - you can filter the installations if you don't want to send the event to every installation. - /** For example, if the current target is a "Group" this means that the notification application is + /** For example, if the current target is a "Group" this means that the notification application is * installed in a Group Chat. if (target.type === NotificationTargetType.Group) { // You can send the Adaptive Card to the Group Chat @@ -76,7 +72,7 @@ server.post( } **/ - /** If the current target is "Channel" this means that the notification application is installed + /** If the current target is "Channel" this means that the notification application is installed * in a Team. if (target.type === NotificationTargetType.Channel) { // If you send an Adaptive Card to the Team (the target), it sends it to the `General` channel of the Team @@ -104,24 +100,24 @@ server.post( } **/ - /** If the current target is "Person" this means that the notification application is installed in a + /** If the current target is "Person" this means that the notification application is installed in a * personal chat. if (target.type === NotificationTargetType.Person) { // Directly notify the individual person await target.sendAdaptiveCard(...); } **/ - } - } while (continuationToken); + } + } while (continuationToken); - /** You can also find someone and notify the individual person + /** You can also find someone and notify the individual person const member = await notificationApp.notification.findMember( async (m) => m.account.email === "someone@contoso.com" ); await member?.sendAdaptiveCard(...); **/ - /** Or find multiple people and notify them + /** Or find multiple people and notify them const members = await notificationApp.notification.findAllMembers( async (m) => m.account.email?.startsWith("test") ); @@ -130,18 +126,17 @@ server.post( } **/ - res.json({}); - } -); + res.json({}); +}); -// Register an API endpoint with `restify`. Teams sends messages to your application +// Register an API endpoint with `express`. Teams sends messages to your application // through this endpoint. // // The Teams Toolkit bot registration configures the bot with `/api/messages` as the // Bot Framework endpoint. If you customize this route, update the Bot registration // in `/templates/provision/bot.bicep`. const teamsBot = new TeamsBot(); -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await notificationApp.requestHandler(req, res, async (context) => { await teamsBot.run(context); }); diff --git a/templates/ts/notification-restify/src/internal/config.ts b/templates/ts/notification-express/src/internal/config.ts similarity index 100% rename from templates/ts/notification-restify/src/internal/config.ts rename to templates/ts/notification-express/src/internal/config.ts diff --git a/templates/ts/notification-restify/src/internal/initialize.ts b/templates/ts/notification-express/src/internal/initialize.ts similarity index 100% rename from templates/ts/notification-restify/src/internal/initialize.ts rename to templates/ts/notification-express/src/internal/initialize.ts diff --git a/templates/ts/notification-restify/src/teamsBot.ts b/templates/ts/notification-express/src/teamsBot.ts similarity index 100% rename from templates/ts/notification-restify/src/teamsBot.ts rename to templates/ts/notification-express/src/teamsBot.ts diff --git a/templates/ts/notification-restify/teamsapp.local.yml.tpl b/templates/ts/notification-express/teamsapp.local.yml.tpl similarity index 100% rename from templates/ts/notification-restify/teamsapp.local.yml.tpl rename to templates/ts/notification-express/teamsapp.local.yml.tpl diff --git a/templates/ts/notification-restify/teamsapp.testtool.yml b/templates/ts/notification-express/teamsapp.testtool.yml similarity index 100% rename from templates/ts/notification-restify/teamsapp.testtool.yml rename to templates/ts/notification-express/teamsapp.testtool.yml diff --git a/templates/ts/notification-restify/teamsapp.yml.tpl b/templates/ts/notification-express/teamsapp.yml.tpl similarity index 100% rename from templates/ts/notification-restify/teamsapp.yml.tpl rename to templates/ts/notification-express/teamsapp.yml.tpl diff --git a/templates/ts/notification-restify/tsconfig.json b/templates/ts/notification-express/tsconfig.json similarity index 100% rename from templates/ts/notification-restify/tsconfig.json rename to templates/ts/notification-express/tsconfig.json diff --git a/templates/ts/notification-restify/web.config b/templates/ts/notification-express/web.config similarity index 100% rename from templates/ts/notification-restify/web.config rename to templates/ts/notification-express/web.config diff --git a/templates/ts/notification-http-timer-trigger/README.md.tpl b/templates/ts/notification-http-timer-trigger/README.md.tpl index 85ea4970b9..a2ebc38945 100644 --- a/templates/ts/notification-http-timer-trigger/README.md.tpl +++ b/templates/ts/notification-http-timer-trigger/README.md.tpl @@ -11,7 +11,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/notification-http-timer-trigger/appPackage/manifest.json.tpl b/templates/ts/notification-http-timer-trigger/appPackage/manifest.json.tpl index 60f6f4e8f5..66ce18c02c 100644 --- a/templates/ts/notification-http-timer-trigger/appPackage/manifest.json.tpl +++ b/templates/ts/notification-http-timer-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/notification-http-timer-trigger/package.json.tpl b/templates/ts/notification-http-timer-trigger/package.json.tpl index 558018472f..957171e2b2 100644 --- a/templates/ts/notification-http-timer-trigger/package.json.tpl +++ b/templates/ts/notification-http-timer-trigger/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Notification Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,9 +26,9 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1" }, "devDependencies": { "@azure/functions": "^3.5.0", diff --git a/templates/ts/notification-http-timer-trigger/src/cardModels.ts b/templates/ts/notification-http-timer-trigger/src/cardModels.ts deleted file mode 100644 index ef2daf802a..0000000000 --- a/templates/ts/notification-http-timer-trigger/src/cardModels.ts +++ /dev/null @@ -1,10 +0,0 @@ -/** - * Adaptive Card data model. Properties can be referenced in an adaptive card via the `${var}` - * Adaptive Card syntax. - */ -export interface CardData { - title: string; - appName: string; - description: string; - notificationUrl: string; -} diff --git a/templates/ts/notification-http-timer-trigger/src/httpTrigger.ts b/templates/ts/notification-http-timer-trigger/src/httpTrigger.ts index 43310161eb..bc2799843e 100644 --- a/templates/ts/notification-http-timer-trigger/src/httpTrigger.ts +++ b/templates/ts/notification-http-timer-trigger/src/httpTrigger.ts @@ -1,7 +1,6 @@ import { AzureFunction, Context, HttpRequest } from "@azure/functions"; import * as ACData from "adaptivecards-templating"; import notificationTemplate from "./adaptiveCards/notification-default.json"; -import { CardData } from "./cardModels"; import { notificationApp } from "./internal/initialize"; // An Azure Function HTTP trigger. diff --git a/templates/ts/notification-http-timer-trigger/src/timerTrigger.ts b/templates/ts/notification-http-timer-trigger/src/timerTrigger.ts index b07437a951..480852c143 100644 --- a/templates/ts/notification-http-timer-trigger/src/timerTrigger.ts +++ b/templates/ts/notification-http-timer-trigger/src/timerTrigger.ts @@ -1,7 +1,6 @@ import { AzureFunction, Context } from "@azure/functions"; import * as ACData from "adaptivecards-templating"; import notificationTemplate from "./adaptiveCards/notification-default.json"; -import { CardData } from "./cardModels"; import { notificationApp } from "./internal/initialize"; // An Azure Function timer trigger. diff --git a/templates/ts/notification-http-trigger/README.md.tpl b/templates/ts/notification-http-trigger/README.md.tpl index 85ea4970b9..a2ebc38945 100644 --- a/templates/ts/notification-http-trigger/README.md.tpl +++ b/templates/ts/notification-http-trigger/README.md.tpl @@ -11,7 +11,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/notification-http-trigger/appPackage/manifest.json.tpl b/templates/ts/notification-http-trigger/appPackage/manifest.json.tpl index 60f6f4e8f5..66ce18c02c 100644 --- a/templates/ts/notification-http-trigger/appPackage/manifest.json.tpl +++ b/templates/ts/notification-http-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/notification-http-trigger/package.json.tpl b/templates/ts/notification-http-trigger/package.json.tpl index 558018472f..957171e2b2 100644 --- a/templates/ts/notification-http-trigger/package.json.tpl +++ b/templates/ts/notification-http-trigger/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Notification Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,9 +26,9 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1" }, "devDependencies": { "@azure/functions": "^3.5.0", diff --git a/templates/ts/notification-http-trigger/src/cardModels.ts b/templates/ts/notification-http-trigger/src/cardModels.ts deleted file mode 100644 index ef2daf802a..0000000000 --- a/templates/ts/notification-http-trigger/src/cardModels.ts +++ /dev/null @@ -1,10 +0,0 @@ -/** - * Adaptive Card data model. Properties can be referenced in an adaptive card via the `${var}` - * Adaptive Card syntax. - */ -export interface CardData { - title: string; - appName: string; - description: string; - notificationUrl: string; -} diff --git a/templates/ts/notification-http-trigger/src/httpTrigger.ts b/templates/ts/notification-http-trigger/src/httpTrigger.ts index 43310161eb..bc2799843e 100644 --- a/templates/ts/notification-http-trigger/src/httpTrigger.ts +++ b/templates/ts/notification-http-trigger/src/httpTrigger.ts @@ -1,7 +1,6 @@ import { AzureFunction, Context, HttpRequest } from "@azure/functions"; import * as ACData from "adaptivecards-templating"; import notificationTemplate from "./adaptiveCards/notification-default.json"; -import { CardData } from "./cardModels"; import { notificationApp } from "./internal/initialize"; // An Azure Function HTTP trigger. diff --git a/templates/ts/notification-restify/src/cardModels.ts b/templates/ts/notification-restify/src/cardModels.ts deleted file mode 100644 index ef2daf802a..0000000000 --- a/templates/ts/notification-restify/src/cardModels.ts +++ /dev/null @@ -1,10 +0,0 @@ -/** - * Adaptive Card data model. Properties can be referenced in an adaptive card via the `${var}` - * Adaptive Card syntax. - */ -export interface CardData { - title: string; - appName: string; - description: string; - notificationUrl: string; -} diff --git a/templates/ts/notification-timer-trigger/README.md.tpl b/templates/ts/notification-timer-trigger/README.md.tpl index 85ea4970b9..a2ebc38945 100644 --- a/templates/ts/notification-timer-trigger/README.md.tpl +++ b/templates/ts/notification-timer-trigger/README.md.tpl @@ -11,7 +11,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the notification bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} diff --git a/templates/ts/notification-timer-trigger/appPackage/manifest.json.tpl b/templates/ts/notification-timer-trigger/appPackage/manifest.json.tpl index 60f6f4e8f5..66ce18c02c 100644 --- a/templates/ts/notification-timer-trigger/appPackage/manifest.json.tpl +++ b/templates/ts/notification-timer-trigger/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/notification-timer-trigger/package.json.tpl b/templates/ts/notification-timer-trigger/package.json.tpl index 558018472f..957171e2b2 100644 --- a/templates/ts/notification-timer-trigger/package.json.tpl +++ b/templates/ts/notification-timer-trigger/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Notification Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -26,9 +26,9 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1" }, "devDependencies": { "@azure/functions": "^3.5.0", diff --git a/templates/ts/notification-timer-trigger/src/cardModels.ts b/templates/ts/notification-timer-trigger/src/cardModels.ts deleted file mode 100644 index ef2daf802a..0000000000 --- a/templates/ts/notification-timer-trigger/src/cardModels.ts +++ /dev/null @@ -1,10 +0,0 @@ -/** - * Adaptive Card data model. Properties can be referenced in an adaptive card via the `${var}` - * Adaptive Card syntax. - */ -export interface CardData { - title: string; - appName: string; - description: string; - notificationUrl: string; -} diff --git a/templates/ts/notification-timer-trigger/src/timerTrigger.ts b/templates/ts/notification-timer-trigger/src/timerTrigger.ts index b07437a951..480852c143 100644 --- a/templates/ts/notification-timer-trigger/src/timerTrigger.ts +++ b/templates/ts/notification-timer-trigger/src/timerTrigger.ts @@ -1,7 +1,6 @@ import { AzureFunction, Context } from "@azure/functions"; import * as ACData from "adaptivecards-templating"; import notificationTemplate from "./adaptiveCards/notification-default.json"; -import { CardData } from "./cardModels"; import { notificationApp } from "./internal/initialize"; // An Azure Function timer trigger. diff --git a/templates/ts/office-addin/README.md b/templates/ts/office-addin/README.md index f35c2df59c..cce62e2434 100644 --- a/templates/ts/office-addin/README.md +++ b/templates/ts/office-addin/README.md @@ -4,7 +4,7 @@ Now you have the ability to create a single unit of distribution for all your Mi ## Prerequisites -- [NodeJS](https://nodejs.org/en/): version 16 or 18. +- [NodeJS](https://nodejs.org/en/): version 18 or 20 - Outlook for Windows: Beta Channel, Build 16320 or higher. Follow [this link](https://github.com/OfficeDev/TeamsFx/wiki/How-to-switch-Outlook-client-update-channel-and-verify-Outlook-client-build-version) for switching update channels and check your Outlook client build version. - Edge installed for debugging Outlook add-in. - An M365 account. If you do not have M365 account, apply one from [M365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) diff --git a/templates/ts/office-xml-addin-excel-cf/README.md b/templates/ts/office-xml-addin-excel-cf/README.md index 66341f582e..5c3c0a7de5 100644 --- a/templates/ts/office-xml-addin-excel-cf/README.md +++ b/templates/ts/office-xml-addin-excel-cf/README.md @@ -6,7 +6,7 @@ Excel add-ins are integrations built by third parties into Excel by using [Excel ## Custom functions in Excel -Custom functions enable you to add new functions to Excel by defining those functions in JavaScript as part of an add-in. Users within Excel can access custom functions just as they would any native function in Excel, such as `SUM()`. +Custom functions enable you to add new functions to Excel by defining those functions in JavaScript as part of an add-in. Users within Excel can access custom functions just as they would any native function in Excel, such as `SUM()`. You can use this repository as a sample to base your own custom functions project from if you choose not to use the generator. For more detailed information about custom functions in Excel, see the [Custom functions overview](https://learn.microsoft.com/office/dev/add-ins/excel/custom-functions-overview) article in the Office Add-ins documentation or see the [additional resources](#additional-resources) section of this repository. @@ -14,14 +14,10 @@ You can use this repository as a sample to base your own custom functions projec ### Prerequisites -- [Node.js](https://nodejs.org) 16, 18, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. -- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program]( -https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ]( -https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. -Alternatively, you can [sign up for a 1-month free trial]( -https://www.microsoft.com/microsoft-365/try?rtc=1) -or [purchase a Microsoft 365 plan]( -https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). +- [Node.js](https://nodejs.org) 18, 20, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. +- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program](https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ](https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. + Alternatively, you can [sign up for a 1-month free trial](https://www.microsoft.com/microsoft-365/try?rtc=1) + or [purchase a Microsoft 365 plan](https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). ### Run the add-in using Teams Toolkit @@ -30,24 +26,25 @@ You can use [Teams Tookit](https://marketplace.visualstudio.com/items?itemName=T 1. **Check and Install Dependencies** - Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. + Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. 1. **Preview Your Office Add-in (F5)** - Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. - - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) - - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) + Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors]( https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. + - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) + - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) - - You have installed dependencies. - - You have closed all Word/Excel/PowerPoint apps. - - You have stopped your last add-in previewing session. + **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors](https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + + - You have installed dependencies. + - You have closed all Word/Excel/PowerPoint apps. + - You have stopped your last add-in previewing session. 1. **Stop Previewing Your Office Add-in** - Select `Stop Previewing Your Office Add-in` to stop debugging. + Select `Stop Previewing Your Office Add-in` to stop debugging. ### Debugging custom functions @@ -61,7 +58,7 @@ This add-in project that you've created contains sample code for a basic task pa To explore the components of the add-in project, review the key files listed below. -- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. +- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. - The `./src/taskpane/taskpane.html` file contains the HTML markup for the task pane. - The `./src/taskpane/taskpane.css` file contains the CSS that's applied to content in the task pane. - The `./src/taskpane/taskpane.js` file contains the Office JavaScript API code that facilitates interaction between the task pane and the Excel application. @@ -71,11 +68,9 @@ To explore the components of the add-in project, review the key files listed bel **GitHub Copilot Extension for Office Add-ins:** 1. Type in `@office` to invoke the extension. -1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot]( -https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library -) to see how to write prompts for Office add-in development. +1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot](https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library) to see how to write prompts for Office add-in development. 1. Get the response from the extension and use the code. -
+
**Resources to learn more Office add-ins capabilities:** @@ -86,9 +81,7 @@ https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github- Did you experience any problems with the sample? [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out. -If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback]( -aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback -) and help us improve the product. +If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback](aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback) and help us improve the product. Want to learn more about new features, development practices, and additional information? [Join the Microsoft Office Add-ins community call.](https://learn.microsoft.com/office/dev/add-ins/overview/office-add-ins-community-call) @@ -98,4 +91,4 @@ Copyright (c) 2024 Microsoft Corporation. All rights reserved. ## Disclaimer -**THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** +**THIS CODE IS PROVIDED _AS IS_ WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** diff --git a/templates/ts/office-xml-addin-excel-taskpane/README.md b/templates/ts/office-xml-addin-excel-taskpane/README.md index eb6bec0d34..df07bcbaa4 100644 --- a/templates/ts/office-xml-addin-excel-taskpane/README.md +++ b/templates/ts/office-xml-addin-excel-taskpane/README.md @@ -8,14 +8,10 @@ Excel add-ins are integrations built by third parties into Excel by using [Excel ### Prerequisites -- [Node.js](https://nodejs.org) 16, 18, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. -- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program]( -https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ]( -https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. -Alternatively, you can [sign up for a 1-month free trial]( -https://www.microsoft.com/microsoft-365/try?rtc=1) -or [purchase a Microsoft 365 plan]( -https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). +- [Node.js](https://nodejs.org) 18, 20, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. +- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program](https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ](https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. + Alternatively, you can [sign up for a 1-month free trial](https://www.microsoft.com/microsoft-365/try?rtc=1) + or [purchase a Microsoft 365 plan](https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). ### Run the add-in using Teams Toolkit @@ -24,24 +20,25 @@ You can use [Teams Tookit](https://marketplace.visualstudio.com/items?itemName=T 1. **Check and Install Dependencies** - Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. + Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. 1. **Preview Your Office Add-in (F5)** - Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. - - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) - - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) + Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors]( https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. + - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) + - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) - - You have installed dependencies. - - You have closed all Word/Excel/PowerPoint apps. - - You have stopped your last add-in previewing session. + **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors](https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + + - You have installed dependencies. + - You have closed all Word/Excel/PowerPoint apps. + - You have stopped your last add-in previewing session. 1. **Stop Previewing Your Office Add-in** - Select `Stop Previewing Your Office Add-in` to stop debugging. + Select `Stop Previewing Your Office Add-in` to stop debugging. ## How to use this sample @@ -51,7 +48,7 @@ This add-in project contains sample code for a basic Excel task pane add-in. To explore the components of the add-in project, review the key files listed below. -- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. +- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. - The `./src/taskpane/taskpane.html` file contains the HTML markup for the task pane. - The `./src/taskpane/taskpane.css` file contains the CSS that's applied to content in the task pane. - The `./src/taskpane/taskpane.js` file contains the Office JavaScript API code that facilitates interaction between the task pane and the Excel application. @@ -61,11 +58,9 @@ To explore the components of the add-in project, review the key files listed bel **GitHub Copilot Extension for Office Add-ins:** 1. Type in `@office` to invoke the extension. -1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot]( -https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library -) to see how to write prompts for Office add-in development. +1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot](https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library) to see how to write prompts for Office add-in development. 1. Get the response from the extension and use the code. -
+
**Resources to learn more Office add-ins capabilities:** @@ -76,9 +71,7 @@ https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github- Did you experience any problems with the sample? [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out. -If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback]( -aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback -) and help us improve the product. +If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback](aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback) and help us improve the product. Want to learn more about new features, development practices, and additional information? [Join the Microsoft Office Add-ins community call.](https://learn.microsoft.com/office/dev/add-ins/overview/office-add-ins-community-call) @@ -88,4 +81,4 @@ Copyright (c) 2024 Microsoft Corporation. All rights reserved. ## Disclaimer -**THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** +**THIS CODE IS PROVIDED _AS IS_ WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** diff --git a/templates/ts/office-xml-addin-powerpoint-taskpane/README.md b/templates/ts/office-xml-addin-powerpoint-taskpane/README.md index 0d478f6cff..389bd3940b 100644 --- a/templates/ts/office-xml-addin-powerpoint-taskpane/README.md +++ b/templates/ts/office-xml-addin-powerpoint-taskpane/README.md @@ -8,14 +8,10 @@ PowerPoint add-ins are integrations built by third parties into PowerPoint by us ### Prerequisites -- [Node.js](https://nodejs.org) 16, 18, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. -- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program]( -https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ]( -https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. -Alternatively, you can [sign up for a 1-month free trial]( -https://www.microsoft.com/microsoft-365/try?rtc=1) -or [purchase a Microsoft 365 plan]( -https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). +- [Node.js](https://nodejs.org) 18, 20, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. +- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program](https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ](https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. + Alternatively, you can [sign up for a 1-month free trial](https://www.microsoft.com/microsoft-365/try?rtc=1) + or [purchase a Microsoft 365 plan](https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). ### Run the add-in using Teams Toolkit @@ -24,24 +20,25 @@ You can use [Teams Tookit](https://marketplace.visualstudio.com/items?itemName=T 1. **Check and Install Dependencies** - Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. + Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. 1. **Preview Your Office Add-in (F5)** - Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. - - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) - - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) + Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors]( https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. + - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) + - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) - - You have installed dependencies. - - You have closed all Word/Excel/PowerPoint apps. - - You have stopped your last add-in previewing session. + **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors](https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + + - You have installed dependencies. + - You have closed all Word/Excel/PowerPoint apps. + - You have stopped your last add-in previewing session. 1. **Stop Previewing Your Office Add-in** - Select `Stop Previewing Your Office Add-in` to stop debugging. + Select `Stop Previewing Your Office Add-in` to stop debugging. ## How to use this sample @@ -51,7 +48,7 @@ This add-in project contains sample code for a basic PowerPoint task pane add-in To explore the components of the add-in project, review the key files listed below. -- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. +- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. - The `./src/taskpane/taskpane.html` file contains the HTML markup for the task pane. - The `./src/taskpane/taskpane.css` file contains the CSS that's applied to content in the task pane. - The `./src/taskpane/taskpane.js` file contains the Office JavaScript API code that facilitates interaction between the task pane and the PowerPoint application. @@ -61,11 +58,9 @@ To explore the components of the add-in project, review the key files listed bel **GitHub Copilot Extension for Office Add-ins:** 1. Type in `@office` to invoke the extension. -1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot]( -https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library -) to see how to write prompts for Office add-in development. +1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot](https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library) to see how to write prompts for Office add-in development. 1. Get the response from the extension and use the code. -
+
**Resources to learn more Office add-ins capabilities:** @@ -76,9 +71,7 @@ https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github- Did you experience any problems with the sample? [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out. -If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback]( -aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback -) and help us improve the product. +If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback](aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback) and help us improve the product. Want to learn more about new features, development practices, and additional information? [Join the Microsoft Office Add-ins community call.](https://learn.microsoft.com/office/dev/add-ins/overview/office-add-ins-community-call) @@ -88,4 +81,4 @@ Copyright (c) 2024 Microsoft Corporation. All rights reserved. ## Disclaimer -**THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** +**THIS CODE IS PROVIDED _AS IS_ WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** diff --git a/templates/ts/office-xml-addin-word-taskpane/README.md b/templates/ts/office-xml-addin-word-taskpane/README.md index 6c6ba33661..e67eeed395 100644 --- a/templates/ts/office-xml-addin-word-taskpane/README.md +++ b/templates/ts/office-xml-addin-word-taskpane/README.md @@ -8,14 +8,10 @@ Word add-ins are integrations built by third parties into Word by using [Word Ja ### Prerequisites -- [Node.js](https://nodejs.org) 16, 18, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. -- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program]( -https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ]( -https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. -Alternatively, you can [sign up for a 1-month free trial]( -https://www.microsoft.com/microsoft-365/try?rtc=1) -or [purchase a Microsoft 365 plan]( -https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). +- [Node.js](https://nodejs.org) 18, 20, or 20 (18 is preferred) and [npm](https://www.npmjs.com/get-npm). To verify if you've already installed these tools, run the commands `node -v` and `npm -v` in your terminal. +- Office connected to a Microsoft 365 subscription. You might qualify for a Microsoft 365 E5 developer subscription through the [Microsoft 365 Developer Program](https://developer.microsoft.com/microsoft-365/dev-program), see [FAQ](https://learn.microsoft.com/office/developer-program/microsoft-365-developer-program-faq#who-qualifies-for-a-microsoft-365-e5-developer-subscription-) for details. + Alternatively, you can [sign up for a 1-month free trial](https://www.microsoft.com/microsoft-365/try?rtc=1) + or [purchase a Microsoft 365 plan](https://www.microsoft.com/microsoft-365/buy/compare-all-microsoft-365-products). ### Run the add-in using Teams Toolkit @@ -24,24 +20,25 @@ You can use [Teams Tookit](https://marketplace.visualstudio.com/items?itemName=T 1. **Check and Install Dependencies** - Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. + Select `Check and Install Dependencies` to check your environment and install necessary dependencies in order to run and debug the add-in code. 1. **Preview Your Office Add-in (F5)** - Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. - - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) - - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) + Select `Preview Your Office Add-in(F5)` on the side panel to start running and debugging the add-in code. A Word/Excel/PowerPoint app will launch with the add-in sample side-loaded. - **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors]( https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + - You can also start debugging by hitting the `F5` key or running `npm run start` command in the terminal. + - To debug on Office on the web, go to [Sideload Office Add-ins to Office on the web](https://learn.microsoft.com/office/dev/add-ins/testing/sideload-office-add-ins-for-testing) + - To debug in Desktop (Edge Legacy), go to [Debug Edge Legacy Webview](https://learn.microsoft.com/office/dev/add-ins/testing/debug-add-ins-using-devtools-edge-legacy) - - You have installed dependencies. - - You have closed all Word/Excel/PowerPoint apps. - - You have stopped your last add-in previewing session. + **If you meet sideload errors, please first confirm the following items and check [troubleshoot development errors](https://learn.microsoft.com/en-us/office/dev/add-ins/testing/troubleshoot-development-errors) for common issues. If you still have problems, [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out.** + + - You have installed dependencies. + - You have closed all Word/Excel/PowerPoint apps. + - You have stopped your last add-in previewing session. 1. **Stop Previewing Your Office Add-in** - Select `Stop Previewing Your Office Add-in` to stop debugging. + Select `Stop Previewing Your Office Add-in` to stop debugging. ## How to use this sample @@ -51,7 +48,7 @@ This add-in project contains sample code for a basic Word task pane add-in. To explore the components of the add-in project, review the key files listed below. -- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. +- The `./manifest.xml` file in the root directory of the project defines the settings and capabilities of the add-in.
You can check whether your manifest file is valid by selecting `Validate Manifest File` in the `Teams Toolkit` extension tree view. - The `./src/taskpane/taskpane.html` file contains the HTML markup for the task pane. - The `./src/taskpane/taskpane.css` file contains the CSS that's applied to content in the task pane. - The `./src/taskpane/taskpane.js` file contains the Office JavaScript API code that facilitates interaction between the task pane and the Word application. @@ -61,11 +58,9 @@ To explore the components of the add-in project, review the key files listed bel **GitHub Copilot Extension for Office Add-ins:** 1. Type in `@office` to invoke the extension. -1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot]( -https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library -) to see how to write prompts for Office add-in development. +1. Type in `/generatecode` and describe the feature you would like to build, then send the request to Copilot. You can [view prompt examples for GitHub Copilot](https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github-copilot-prompt-library) to see how to write prompts for Office add-in development. 1. Get the response from the extension and use the code. -
+
**Resources to learn more Office add-ins capabilities:** @@ -76,9 +71,7 @@ https://learn.microsoft.com/en-us/office/dev/add-ins/resources/resources-github- Did you experience any problems with the sample? [Create an issue](https://github.com/OfficeDev/office-js/issues/new/choose) and we'll help you out. -If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback]( -aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback -) and help us improve the product. +If you have suggestions for GitHub Copilot Extension for Office Add-ins, [give us feedback](aka.ms/GitHubCopilotextensionforOfficeAddinsFeedback) and help us improve the product. Want to learn more about new features, development practices, and additional information? [Join the Microsoft Office Add-ins community call.](https://learn.microsoft.com/office/dev/add-ins/overview/office-add-ins-community-call) @@ -88,4 +81,4 @@ Copyright (c) 2024 Microsoft Corporation. All rights reserved. ## Disclaimer -**THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** +**THIS CODE IS PROVIDED _AS IS_ WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.** diff --git a/templates/ts/spfx-tab/appPackage/manifest.json.tpl b/templates/ts/spfx-tab/appPackage/manifest.json.tpl index 47f53c74e6..c397349612 100644 --- a/templates/ts/spfx-tab/appPackage/manifest.json.tpl +++ b/templates/ts/spfx-tab/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "id": "${{TEAMS_APP_ID}}", "version": "1.0.0", "developer": { diff --git a/templates/ts/spfx-tab/appPackage/manifest.local.json.tpl b/templates/ts/spfx-tab/appPackage/manifest.local.json.tpl index 4edac3942e..9ad8067572 100644 --- a/templates/ts/spfx-tab/appPackage/manifest.local.json.tpl +++ b/templates/ts/spfx-tab/appPackage/manifest.local.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "id": "${{TEAMS_APP_ID}}", "version": "1.0.0", "developer": { diff --git a/templates/ts/sso-tab-with-obo-flow/api/README.md b/templates/ts/sso-tab-with-obo-flow/api/README.md index a15a015e6d..32c5b90cf9 100644 --- a/templates/ts/sso-tab-with-obo-flow/api/README.md +++ b/templates/ts/sso-tab-with-obo-flow/api/README.md @@ -4,7 +4,7 @@ Azure Functions are a great way to add server-side behaviors to any Teams applic ## Prerequisites -- [Node.js](https://nodejs.org/), supported versions: 16, 18 +- [Node.js](https://nodejs.org/), supported versions: 18, 20 - A Microsoft 365 account. If you do not have Microsoft 365 account, apply one from [Microsoft 365 developer program](https://developer.microsoft.com/en-us/microsoft-365/dev-program) - [Teams Toolkit Visual Studio Code Extension](https://aka.ms/teams-toolkit) version 5.0.0 and higher or [Teams Toolkit CLI](https://aka.ms/teamsfx-toolkit-cli) @@ -70,7 +70,7 @@ This file contains template arguments with `${{...}}` statements which will be r Deploy your project to Azure by following these steps: -| From Visual Studio Code | From Teams Toolkit CLI | +| From Visual Studio Code | From Teams Toolkit CLI | | :--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | :---------------------------------------------------------------------------------------------------------------------------------------------- | |
  • Open Teams Toolkit, and sign into Azure by clicking the `Sign in to Azure` under the `ACCOUNTS` section from sidebar.
  • After you signed in, select a subscription under your account.
  • Open the command palette and select: `Teams: Provision`.
  • Open the command palette and select: `Teams: Deploy`.
|
  • Run command `teamsapp auth login azure`.
  • Run command `teamsapp provision`.
  • Run command `teamsapp deploy`.
| diff --git a/templates/ts/sso-tab-with-obo-flow/api/package.json b/templates/ts/sso-tab-with-obo-flow/api/package.json index f01b580a08..0c57a6afba 100644 --- a/templates/ts/sso-tab-with-obo-flow/api/package.json +++ b/templates/ts/sso-tab-with-obo-flow/api/package.json @@ -17,7 +17,7 @@ }, "dependencies": { "@azure/functions": "^4.0.0", - "@microsoft/teamsfx": "^2.0.0", + "@microsoft/teamsfx": "^3.0.0-alpha", "@microsoft/microsoft-graph-client": "^3.0.1", "isomorphic-fetch": "^3.0.0" }, diff --git a/templates/ts/sso-tab-with-obo-flow/appPackage/manifest.json.tpl b/templates/ts/sso-tab-with-obo-flow/appPackage/manifest.json.tpl index c72a4e3223..22558e84a9 100644 --- a/templates/ts/sso-tab-with-obo-flow/appPackage/manifest.json.tpl +++ b/templates/ts/sso-tab-with-obo-flow/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/sso-tab-with-obo-flow/package.json.tpl b/templates/ts/sso-tab-with-obo-flow/package.json.tpl index 42ac2e1446..057ccdc5b3 100644 --- a/templates/ts/sso-tab-with-obo-flow/package.json.tpl +++ b/templates/ts/sso-tab-with-obo-flow/package.json.tpl @@ -7,10 +7,10 @@ "type": "module", "private": true, "dependencies": { - "@fluentui/react-components": "^9.18.0", + "@fluentui/react-components": "^9.55.1", "@microsoft/teams-js": "^2.22.0", - "@microsoft/teamsfx": "^2.2.0", - "@microsoft/teamsfx-react": "^3.0.0", + "@microsoft/teamsfx": "^3.0.0-alpha", + "@microsoft/teamsfx-react": "^4.0.0-alpha", "axios": "^0.21.1", "react": "^18.2.0", "react-dom": "^18.2.0", diff --git a/templates/ts/sso-tab-with-obo-flow/teamsapp.yml.tpl b/templates/ts/sso-tab-with-obo-flow/teamsapp.yml.tpl index 448e96f6a3..c95d8b0b9c 100644 --- a/templates/ts/sso-tab-with-obo-flow/teamsapp.yml.tpl +++ b/templates/ts/sso-tab-with-obo-flow/teamsapp.yml.tpl @@ -132,10 +132,10 @@ deploy: with: args: run build --if-present env: - REACT_APP_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} - REACT_APP_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html - REACT_APP_FUNC_NAME: getUserProfile - REACT_APP_FUNC_ENDPOINT: ${{API_FUNCTION_ENDPOINT}} + VITE_CLIENT_ID: ${{AAD_APP_CLIENT_ID}} + VITE_START_LOGIN_PAGE_URL: ${{TAB_ENDPOINT}}/auth-start.html + VITE_FUNC_NAME: getUserProfile + VITE_FUNC_ENDPOINT: ${{API_FUNCTION_ENDPOINT}} # Deploy bits to Azure Static Web Apps - uses: cli/runNpxCommand name: deploy to Azure Static Web Apps diff --git a/templates/ts/workflow/.vscode/tasks.json b/templates/ts/workflow/.vscode/tasks.json index 9034316c43..953e988587 100644 --- a/templates/ts/workflow/.vscode/tasks.json +++ b/templates/ts/workflow/.vscode/tasks.json @@ -62,7 +62,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, @@ -196,7 +196,7 @@ "background": { "activeOnStart": true, "beginsPattern": "[nodemon] starting", - "endsPattern": "restify listening to|Bot/ME service listening at|[nodemon] app crashed" + "endsPattern": "app listening to|Bot/ME service listening at|[nodemon] app crashed" } } }, diff --git a/templates/ts/workflow/README.md.tpl b/templates/ts/workflow/README.md.tpl index 043b45698b..6dc9b39531 100644 --- a/templates/ts/workflow/README.md.tpl +++ b/templates/ts/workflow/README.md.tpl @@ -10,7 +10,7 @@ The app template is built using the TeamsFx SDK, which provides a simple set of > > To run the workflow bot template in your local dev machine, you will need: > -> - [Node.js](https://nodejs.org/), supported versions: 16, 18 +> - [Node.js](https://nodejs.org/), supported versions: 18, 20 {{^enableTestToolByDefault}} > - An [Microsoft 365 account for development](https://docs.microsoft.com/microsoftteams/platform/toolkit/accounts) {{/enableTestToolByDefault}} @@ -72,7 +72,7 @@ The following files can be customized and demonstrate an example implementation | File | Contents | | - | - | -| `src/index.ts`| Application entry point and `restify` handlers for the Workflow bot | +| `src/index.ts`| Application entry point and `express` handlers for the Workflow bot | | `src/teamsBot.ts` | An empty teams activity handler for bot customization | | `src/commands/helloworldCommandHandler.ts` | Implementation that handles responding to a chat command | | `src/adaptiveCards/helloworldCommandResponse.json` | Defines the Adaptive Card (UI) that is displayed in response to a chat command | diff --git a/templates/ts/workflow/appPackage/manifest.json.tpl b/templates/ts/workflow/appPackage/manifest.json.tpl index cf2bbc13dc..84ea23d920 100644 --- a/templates/ts/workflow/appPackage/manifest.json.tpl +++ b/templates/ts/workflow/appPackage/manifest.json.tpl @@ -1,6 +1,6 @@ { - "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.17/MicrosoftTeams.schema.json", - "manifestVersion": "1.17", + "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.19/MicrosoftTeams.schema.json", + "manifestVersion": "1.19", "version": "1.0.0", "id": "${{TEAMS_APP_ID}}", "developer": { diff --git a/templates/ts/workflow/package.json.tpl b/templates/ts/workflow/package.json.tpl index 7acd160f38..495b58b3fe 100644 --- a/templates/ts/workflow/package.json.tpl +++ b/templates/ts/workflow/package.json.tpl @@ -3,7 +3,7 @@ "version": "1.0.0", "description": "Microsoft Teams Toolkit Workflow Bot Sample", "engines": { - "node": "16 || 18" + "node": "18 || 20" }, "author": "Microsoft", "license": "MIT", @@ -24,17 +24,17 @@ }, "dependencies": { "adaptivecards-templating": "^2.3.1", - "adaptive-expressions": "^4.22.3", - "@microsoft/teamsfx": "^2.3.1", - "botbuilder": "^4.20.0", - "restify": "^10.0.0" + "adaptive-expressions": "^4.23.1", + "@microsoft/teamsfx": "^3.0.0-alpha", + "botbuilder": "^4.23.1", + "express": "^5.0.1" }, "devDependencies": { - "@types/restify": "^8.5.5", + "@types/express": "^5.0.0", "@types/node": "^18.0.0", "@types/json-schema": "^7.0.15", "env-cmd": "^10.1.0", - "nodemon": "^2.0.7", + "nodemon": "^3.1.7", "shx": "^0.3.4", "ts-node": "^10.4.0", "typescript": "^4.4.4" diff --git a/templates/ts/workflow/src/cardActions/doStuffActionHandler.ts b/templates/ts/workflow/src/cardActions/doStuffActionHandler.ts index 8cc2533bdb..824bc695de 100644 --- a/templates/ts/workflow/src/cardActions/doStuffActionHandler.ts +++ b/templates/ts/workflow/src/cardActions/doStuffActionHandler.ts @@ -2,7 +2,6 @@ import * as ACData from "adaptivecards-templating"; import { TurnContext, InvokeResponse } from "botbuilder"; import { TeamsFxAdaptiveCardActionHandler, InvokeResponseFactory } from "@microsoft/teamsfx"; import responseCard from "../adaptiveCards/doStuffActionResponse.json"; -import { CardData } from "../cardModels"; /** * The `DoStuffActionHandler` registers an action with the `TeamsFxBotActionHandler` and responds @@ -19,12 +18,12 @@ export class DoStuffActionHandler implements TeamsFxAdaptiveCardActionHandler { /** * You can send an adaptive card to respond to the card action invoke. */ - const cardData: CardData = { - title: "Hello World Bot", - body: "Congratulations! Your task is processed successfully.", - }; - - const cardJson = new ACData.Template(responseCard).expand({ $root: cardData }); + const cardJson = new ACData.Template(responseCard).expand({ + $root: { + title: "Hello World Bot", + body: "Congratulations! Your task is processed successfully.", + }, + }); return InvokeResponseFactory.adaptiveCard(cardJson); /** diff --git a/templates/ts/workflow/src/cardModels.ts b/templates/ts/workflow/src/cardModels.ts deleted file mode 100644 index 024955f4de..0000000000 --- a/templates/ts/workflow/src/cardModels.ts +++ /dev/null @@ -1,8 +0,0 @@ -/** - * Adaptive Card data model. Properties can be referenced in an adaptive card via the `${var}` - * Adaptive Card syntax. - */ -export interface CardData { - title: string; - body: string; -} diff --git a/templates/ts/workflow/src/commands/helloworldCommandHandler.ts b/templates/ts/workflow/src/commands/helloworldCommandHandler.ts index e50becd59c..cded8b6576 100644 --- a/templates/ts/workflow/src/commands/helloworldCommandHandler.ts +++ b/templates/ts/workflow/src/commands/helloworldCommandHandler.ts @@ -2,7 +2,6 @@ import { Activity, CardFactory, MessageFactory, TurnContext } from "botbuilder"; import { CommandMessage, TeamsFxBotCommandHandler, TriggerPatterns } from "@microsoft/teamsfx"; import * as ACData from "adaptivecards-templating"; import helloWorldCard from "../adaptiveCards/helloworldCommandResponse.json"; -import { CardData } from "../cardModels"; /** * The `HelloWorldCommandHandler` registers a pattern with the `TeamsFxBotCommandHandler` and responds @@ -17,13 +16,12 @@ export class HelloWorldCommandHandler implements TeamsFxBotCommandHandler { ): Promise | void> { console.log(`Bot received message: ${message.text}`); - // Render your adaptive card for reply message - const cardData: CardData = { - title: "Your Hello World Bot is Running", - body: "Congratulations! Your hello world bot is running. Click the button below to trigger an action.", - }; - - const cardJson = new ACData.Template(helloWorldCard).expand({ $root: cardData }); + const cardJson = new ACData.Template(helloWorldCard).expand({ + $root: { + title: "Your Hello World Bot is Running", + body: "Congratulations! Your hello world bot is running. Click the button below to trigger an action.", + }, + }); return MessageFactory.attachment(CardFactory.adaptiveCard(cardJson)); } } diff --git a/templates/ts/workflow/src/index.ts b/templates/ts/workflow/src/index.ts index 0d474c1ab5..e674dec112 100644 --- a/templates/ts/workflow/src/index.ts +++ b/templates/ts/workflow/src/index.ts @@ -1,23 +1,24 @@ -import * as restify from "restify"; +import express from "express"; import { workflowApp } from "./internal/initialize"; import { TeamsBot } from "./teamsBot"; -// This template uses `restify` to serve HTTP responses. -// Create a restify server. -const server = restify.createServer(); -server.use(restify.plugins.bodyParser()); -server.listen(process.env.port || process.env.PORT || 3978, () => { - console.log(`\nBot Started, ${server.name} listening to ${server.url}`); +// This template uses `express` to serve HTTP responses. +// Create express application. +const expressApp = express(); +expressApp.use(express.json()); + +const server = expressApp.listen(process.env.port || process.env.PORT || 3978, () => { + console.log(`\nBot Started, ${expressApp.name} listening to`, server.address()); }); -// Register an API endpoint with `restify`. Teams sends messages to your application +// Register an API endpoint with `express`. Teams sends messages to your application // through this endpoint. // // The Teams Toolkit bot registration configures the bot with `/api/messages` as the // Bot Framework endpoint. If you customize this route, update the Bot registration // in `/templates/provision/bot.bicep`. const teamsBot = new TeamsBot(); -server.post("/api/messages", async (req, res) => { +expressApp.post("/api/messages", async (req, res) => { await workflowApp.requestHandler(req, res, async (context) => { await teamsBot.run(context); });
- Application entry point and restify handlers for + Application entry point and express handlers for notifications
- Application entry point and restify handlers for the + Application entry point and express handlers for the Workflow bot