diff --git a/appPackage/manifest.json b/appPackage/manifest.json index c5e1740..79ed5d9 100644 --- a/appPackage/manifest.json +++ b/appPackage/manifest.json @@ -1,9 +1,9 @@ { "$schema": "https://developer.microsoft.com/en-us/json-schemas/teams/v1.16/MicrosoftTeams.schema.json", "manifestVersion": "1.16", - "version": "1.0.2", + "version": "1.0.4", "id": "${{TEAMS_APP_ID}}", - "packageName": "com.microsoft.teams.extension", + "packageName": "com.microsoft.teams.capabilitychecker", "developer": { "name": "Teams App, Inc.", "websiteUrl": "${{TAB_ENDPOINT}}/index.html", diff --git a/package-lock.json b/package-lock.json index 9d87ca2..8f66c54 100644 --- a/package-lock.json +++ b/package-lock.json @@ -14,7 +14,7 @@ "@microsoft/mgt-react": "^2.9.2", "@microsoft/mgt-teamsfx-provider": "^2.9.2", "@microsoft/microsoft-graph-client": "^3.0.1", - "@microsoft/teams-js": "^2.17.0", + "@microsoft/teams-js": "^2.25.0", "@microsoft/teamsfx": "^2.0.0", "@microsoft/teamsfx-react": "^2.1.1", "axios": "^0.21.1", @@ -4030,10 +4030,11 @@ } }, "node_modules/@microsoft/teams-js": { - "version": "2.17.0", - "resolved": "https://registry.npmjs.org/@microsoft/teams-js/-/teams-js-2.17.0.tgz", - "integrity": "sha512-lqFs5nUO+C11hgDkrkbiuQJP8sdPQ8/VmM0iyf2LtPsDdWHTJRWYtRcsC81DEKpwsGb24hg8r4qcJUi5GLydSg==", + "version": "2.25.0", + "resolved": "https://registry.npmjs.org/@microsoft/teams-js/-/teams-js-2.25.0.tgz", + "integrity": "sha512-dPlVltR7f3+cwYowBd5D4pgjY8h+WyQk1Nw5FvN/deXHVkqSs3tW7GJbwofP/gNUsnIRy84VxKZIETfTQ4MA/w==", "dependencies": { + "base64-js": "^1.3.1", "debug": "^4.3.3" } }, @@ -7021,148 +7022,6 @@ "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==" }, - "node_modules/concurrently": { - "version": "7.6.0", - "resolved": "https://registry.npmjs.org/concurrently/-/concurrently-7.6.0.tgz", - "integrity": "sha512-BKtRgvcJGeZ4XttiDiNcFiRlxoAeZOseqUvyYRUp/Vtd+9p1ULmeoSqGsDA+2ivdeDFpqrJvGvmI+StKfKl5hw==", - "dependencies": { - "chalk": "^4.1.0", - "date-fns": "^2.29.1", - "lodash": "^4.17.21", - "rxjs": "^7.0.0", - "shell-quote": "^1.7.3", - "spawn-command": "^0.0.2-1", - "supports-color": "^8.1.0", - "tree-kill": "^1.2.2", - "yargs": "^17.3.1" - }, - "bin": { - "conc": "dist/bin/concurrently.js", - "concurrently": "dist/bin/concurrently.js" - }, - "engines": { - "node": "^12.20.0 || ^14.13.0 || >=16.0.0" - }, - "funding": { - "url": "https://github.com/open-cli-tools/concurrently?sponsor=1" - } - }, - "node_modules/concurrently/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/concurrently/node_modules/chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "dependencies": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/chalk?sponsor=1" - } - }, - "node_modules/concurrently/node_modules/chalk/node_modules/supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=8" - } - }, - "node_modules/concurrently/node_modules/cliui": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", - "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", - "dependencies": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.1", - "wrap-ansi": "^7.0.0" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/concurrently/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/concurrently/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "node_modules/concurrently/node_modules/has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "engines": { - "node": ">=8" - } - }, - "node_modules/concurrently/node_modules/supports-color": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "dependencies": { - "has-flag": "^4.0.0" - }, - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/chalk/supports-color?sponsor=1" - } - }, - "node_modules/concurrently/node_modules/yargs": { - "version": "17.7.2", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", - "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", - "dependencies": { - "cliui": "^8.0.1", - "escalade": "^3.1.1", - "get-caller-file": "^2.0.5", - "require-directory": "^2.1.1", - "string-width": "^4.2.3", - "y18n": "^5.0.5", - "yargs-parser": "^21.1.1" - }, - "engines": { - "node": ">=12" - } - }, - "node_modules/concurrently/node_modules/yargs-parser": { - "version": "21.1.1", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", - "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", - "engines": { - "node": ">=12" - } - }, "node_modules/confusing-browser-globals": { "version": "1.0.11", "resolved": "https://registry.npmjs.org/confusing-browser-globals/-/confusing-browser-globals-1.0.11.tgz", @@ -7768,21 +7627,6 @@ "node": ">=10" } }, - "node_modules/date-fns": { - "version": "2.30.0", - "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-2.30.0.tgz", - "integrity": "sha512-fnULvOpxnC5/Vg3NCiWelDsLiUc9bRwAPs/+LfTLNvetFCtCTN+yQz15C/fs4AwX1R9K5GLtLfn8QW+dWisaAw==", - "dependencies": { - "@babel/runtime": "^7.21.0" - }, - "engines": { - "node": ">=0.11" - }, - "funding": { - "type": "opencollective", - "url": "https://opencollective.com/date-fns" - } - }, "node_modules/dayjs": { "version": "1.11.10", "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.10.tgz", @@ -17075,19 +16919,6 @@ "queue-microtask": "^1.2.2" } }, - "node_modules/rxjs": { - "version": "7.8.1", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz", - "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==", - "dependencies": { - "tslib": "^2.1.0" - } - }, - "node_modules/rxjs/node_modules/tslib": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.2.tgz", - "integrity": "sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==" - }, "node_modules/safe-array-concat": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.0.1.tgz", @@ -17574,11 +17405,6 @@ "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==", "deprecated": "Please use @jridgewell/sourcemap-codec instead" }, - "node_modules/spawn-command": { - "version": "0.0.2-1", - "resolved": "https://registry.npmjs.org/spawn-command/-/spawn-command-0.0.2-1.tgz", - "integrity": "sha512-n98l9E2RMSJ9ON1AKisHzz7V42VDiBQGY6PB1BwRglz99wpVsSuGzQ+jOi6lFXBGVTCrRpltvjm+/XA+tpeJrg==" - }, "node_modules/spdy": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/spdy/-/spdy-4.0.2.tgz", @@ -18460,14 +18286,6 @@ "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==" }, - "node_modules/tree-kill": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", - "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==", - "bin": { - "tree-kill": "cli.js" - } - }, "node_modules/trim-repeated": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/trim-repeated/-/trim-repeated-1.0.0.tgz", @@ -22828,10 +22646,11 @@ } }, "@microsoft/teams-js": { - "version": "2.17.0", - "resolved": "https://registry.npmjs.org/@microsoft/teams-js/-/teams-js-2.17.0.tgz", - "integrity": "sha512-lqFs5nUO+C11hgDkrkbiuQJP8sdPQ8/VmM0iyf2LtPsDdWHTJRWYtRcsC81DEKpwsGb24hg8r4qcJUi5GLydSg==", + "version": "2.25.0", + "resolved": "https://registry.npmjs.org/@microsoft/teams-js/-/teams-js-2.25.0.tgz", + "integrity": "sha512-dPlVltR7f3+cwYowBd5D4pgjY8h+WyQk1Nw5FvN/deXHVkqSs3tW7GJbwofP/gNUsnIRy84VxKZIETfTQ4MA/w==", "requires": { + "base64-js": "^1.3.1", "debug": "^4.3.3" } }, @@ -25125,105 +24944,6 @@ "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==" }, - "concurrently": { - "version": "https://registry.npmjs.org/concurrently/-/concurrently-7.6.0.tgz", - "integrity": "sha512-BKtRgvcJGeZ4XttiDiNcFiRlxoAeZOseqUvyYRUp/Vtd+9p1ULmeoSqGsDA+2ivdeDFpqrJvGvmI+StKfKl5hw==", - "requires": { - "chalk": "^4.1.0", - "date-fns": "^2.29.1", - "lodash": "^4.17.21", - "rxjs": "^7.0.0", - "shell-quote": "^1.7.3", - "spawn-command": "^0.0.2-1", - "supports-color": "^8.1.0", - "tree-kill": "^1.2.2", - "yargs": "^17.3.1" - }, - "dependencies": { - "ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "requires": { - "color-convert": "^2.0.1" - } - }, - "chalk": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", - "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", - "requires": { - "ansi-styles": "^4.1.0", - "supports-color": "^7.1.0" - }, - "dependencies": { - "supports-color": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", - "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", - "requires": { - "has-flag": "^4.0.0" - } - } - } - }, - "cliui": { - "version": "8.0.1", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", - "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", - "requires": { - "string-width": "^4.2.0", - "strip-ansi": "^6.0.1", - "wrap-ansi": "^7.0.0" - } - }, - "color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "requires": { - "color-name": "~1.1.4" - } - }, - "color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, - "has-flag": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" - }, - "supports-color": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", - "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "requires": { - "has-flag": "^4.0.0" - } - }, - "yargs": { - "version": "17.7.2", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", - "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", - "requires": { - "cliui": "^8.0.1", - "escalade": "^3.1.1", - "get-caller-file": "^2.0.5", - "require-directory": "^2.1.1", - "string-width": "^4.2.3", - "y18n": "^5.0.5", - "yargs-parser": "^21.1.1" - } - }, - "yargs-parser": { - "version": "21.1.1", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", - "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==" - } - } - }, "confusing-browser-globals": { "version": "1.0.11", "resolved": "https://registry.npmjs.org/confusing-browser-globals/-/confusing-browser-globals-1.0.11.tgz", @@ -25634,14 +25354,6 @@ } } }, - "date-fns": { - "version": "2.30.0", - "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-2.30.0.tgz", - "integrity": "sha512-fnULvOpxnC5/Vg3NCiWelDsLiUc9bRwAPs/+LfTLNvetFCtCTN+yQz15C/fs4AwX1R9K5GLtLfn8QW+dWisaAw==", - "requires": { - "@babel/runtime": "^7.21.0" - } - }, "dayjs": { "version": "1.11.10", "resolved": "https://registry.npmjs.org/dayjs/-/dayjs-1.11.10.tgz", @@ -32266,21 +31978,6 @@ "queue-microtask": "^1.2.2" } }, - "rxjs": { - "version": "7.8.1", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz", - "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==", - "requires": { - "tslib": "^2.1.0" - }, - "dependencies": { - "tslib": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.2.tgz", - "integrity": "sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==" - } - } - }, "safe-array-concat": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.0.1.tgz", @@ -32645,11 +32342,6 @@ "resolved": "https://registry.npmjs.org/sourcemap-codec/-/sourcemap-codec-1.4.8.tgz", "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==" }, - "spawn-command": { - "version": "0.0.2-1", - "resolved": "https://registry.npmjs.org/spawn-command/-/spawn-command-0.0.2-1.tgz", - "integrity": "sha512-n98l9E2RMSJ9ON1AKisHzz7V42VDiBQGY6PB1BwRglz99wpVsSuGzQ+jOi6lFXBGVTCrRpltvjm+/XA+tpeJrg==" - }, "spdy": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/spdy/-/spdy-4.0.2.tgz", @@ -33314,11 +33006,6 @@ "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==" }, - "tree-kill": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", - "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==" - }, "trim-repeated": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/trim-repeated/-/trim-repeated-1.0.0.tgz", diff --git a/package.json b/package.json index e237bf5..ae70d1f 100644 --- a/package.json +++ b/package.json @@ -10,7 +10,7 @@ "@microsoft/mgt-react": "^2.9.2", "@microsoft/mgt-teamsfx-provider": "^2.9.2", "@microsoft/microsoft-graph-client": "^3.0.1", - "@microsoft/teams-js": "^2.17.0", + "@microsoft/teams-js": "^2.25.0", "@microsoft/teamsfx": "^2.0.0", "@microsoft/teamsfx-react": "^2.1.1", "axios": "^0.21.1", diff --git a/readme.md b/readme.md index b08130c..f08b925 100644 --- a/readme.md +++ b/readme.md @@ -1,5 +1,11 @@ # TeamsJS Capability Checker +This is a sample app that allows developers to verify what Capabilities work on which hub using a matrix of isSupported values. These are updated using the isSupported() check in TeamsJS. In addition, there are quick code demos for some of the APIs. Some of these outputs are shown in console as there is no UI change. This should help to better understand how to call these APIs in your own sample app after looking at how these APIs are implemented. + +Try opening the app in other hubs including mobile hubs and you can see the isSupported values there as well. + +Feel free to add any suggestions at the link below. + # Personal Tabs Tabs are Teams-aware webpages embedded in Microsoft Teams. A channel/group tab delivers content to channels and group chats, and are a great way to create collaborative spaces around dedicated web-based content. diff --git a/src/components/App.css b/src/components/App.css index e578b67..1689589 100644 --- a/src/components/App.css +++ b/src/components/App.css @@ -3,7 +3,7 @@ } .ui_action .ui-flex { - width: max-content; + width: 100%; } .ui-icon { @@ -14,10 +14,23 @@ width: 18px; } +.app-getcontext .align-top { + vertical-align: top; +} + +.app-getcontext { + width: 69%; +} + +.app-openlink { + width: 50%; +} + .ui_action, .ui-table__cell__content { display: flex; align-items: center; + width: 100%; } .ui-pagessegment { @@ -55,7 +68,7 @@ .ui_action .ui-table__cell__content .ui_app { height: 100px; - width: 600px; + width: 400px; } .ui_location { @@ -81,6 +94,7 @@ .ui_input { width: 70%; + margin-right: 5px; } .ui_input div { @@ -128,6 +142,8 @@ align-self: center; } +.btn_stageview {} + @media screen and (min-width: 700px) { .ui-table__cell:not(:last-child) { max-width: 12%; @@ -154,6 +170,6 @@ } .ui-table__cell:first-child { - max-width: 12%; + max-width: 14%; } } \ No newline at end of file diff --git a/src/components/Host.tsx b/src/components/Host.tsx index 1724c3e..c9e8fc6 100644 --- a/src/components/Host.tsx +++ b/src/components/Host.tsx @@ -8,22 +8,24 @@ import { app } from "@microsoft/teams-js"; import { useData } from "@microsoft/teamsfx-react"; export const Host = () => { - const hostName = useData(async () => { + const host = useData(async () => { await app.initialize(); const context = await app.getContext(); - return context.app.host.name; + return { hostName: context.app.host.name, frameContext: context.page.frameContext }; })?.data; return ( - {hostName && ( - Current Host: {hostName} + {host && ( + Current Host: {host.hostName} )} Current Browser: {browserName} - + + Frame Context: {host?.frameContext} + {isMobile ? "Mobile device" : "Desktop device"} diff --git a/src/components/Modules.tsx b/src/components/Modules.tsx index 6ce3bc0..755182a 100644 --- a/src/components/Modules.tsx +++ b/src/components/Modules.tsx @@ -9,27 +9,74 @@ import { AppIsSupported } from "./capabilities"; export const AllModules = () => { let createdModules: any = []; + // array of capabilities from TeamsJs SDK with isSupported funtion const msTeamsSdk = Object.entries(teamsJs).filter(([_, value]) => isModule(value) ) as [string, IModule[]][]; if (typeof capabilities === "object") { + // array of functions created mannually const capabs = Object.entries(capabilities); + // filtering isSupported functions which are created mannually createdModules = capabs.filter((value, index) => { return value[0].search("IsSupported") !== -1 ? false : value }) as []; } - msTeamsSdk.unshift(["app", [{ isSupported: AppIsSupported }]]); + // created a new array to consolidate both main capabilities and their corresponding sub-capabilities + // at an equal level, optimizing the loop iteration process. + let newMsTeamsSdk: [string, IModule[]][] = []; - const dataTable = msTeamsSdk.map((module: any) => { + msTeamsSdk.forEach(([parentModuleName, module]: any) => { + + newMsTeamsSdk.push([parentModuleName, module]); + + // filtering sub-capabilities based on isSupported function + const entries = Object.entries(module).filter(([_, value]) => isModule(value)) as [string, IModule[]][]; + + if (entries && entries.length > 0) { + const filteredEntries = entries.map(([subModuleName, entry]: any) => { + + // naming the sub-capability for example dialog.url + const moduleName = `${parentModuleName}.${subModuleName}`; + + return [moduleName, entry] as [string, IModule[]]; + }); + + if (filteredEntries.length > 0) { + newMsTeamsSdk = [...newMsTeamsSdk, ...filteredEntries]; + + // Filtering capabilities inside sub capabilities based on isSupported function + filteredEntries.forEach(([moduleName, subModule]: any) => { + + const filteredSubModule = Object.entries(subModule).filter(([_, value]) => isModule(value)) as [string, IModule[]][];; + + if (filteredSubModule && filteredSubModule.length > 0) { + const filteredArray = filteredSubModule.map(([subModuleName, arrayItem]: any) => { + + // naming the final sub-capability for example dialog.url.bot + const finalName = `${moduleName}.${subModuleName}`; + return [finalName, arrayItem] as [string, IModule[]]; + }); + newMsTeamsSdk = [...newMsTeamsSdk, ...filteredArray]; + } + }); + + } + } + }) + + // Adding 'app' on the top of the list to show its functionality in the table. + newMsTeamsSdk.unshift(["app", [{ isSupported: AppIsSupported }]]); + + const dataTable = newMsTeamsSdk.map((module: any) => { try { const moduleName = module[0] as string; const isSupported = module[1] && safeIsSupported(module[1]); - const moduleDetails = getModuleDetails(moduleName.toLowerCase()); + const moduleDetails = getModuleDetails(moduleName.replaceAll(".", "").toLowerCase()); let iconName: any = []; @@ -39,12 +86,18 @@ export const AllModules = () => { ); } - const Icon = iconName && iconName[1]; + let Icon = iconName && iconName[1]; + + // setting default icon + if (!Icon) { + Icon = Fluent.AppsIcon; + } - const isModulePresent = createdModules.filter((capabs: any) => { return capabs[0].toLowerCase() === moduleName.toLowerCase() }); + const isModulePresent = createdModules.filter((capabs: any) => { return capabs[0].toLowerCase() === moduleName.replaceAll(".", "").toLowerCase() }); let element: Function = empty; + // checking module if its functions are implemented else setting it to a blank row if (isModulePresent && isModulePresent.length === 0) { element = empty; } else { @@ -53,6 +106,7 @@ export const AllModules = () => { const Capability = element as Function; + // setting the capabilityName and Icon const capabilityName: JSX.Element | string = <> @@ -79,7 +133,7 @@ export const AllModules = () => { content: capabilityName }, { key: `${moduleName}-2`, content: isSupported }, - { key: `${moduleName}-3`, content: , className: `ui_action ${moduleName === 'AppOpenLink' ? 'ui_openlink' : ''}` }, + { key: `${moduleName}-3`, content: , className: `ui_action` }, ], } } catch (error) { diff --git a/src/components/Nav.tsx b/src/components/Nav.tsx deleted file mode 100644 index df53752..0000000 --- a/src/components/Nav.tsx +++ /dev/null @@ -1,32 +0,0 @@ -import { } from "react-router-dom"; - -import * as Fluent from "@fluentui/react-northstar"; - -export const Nav = () => { - //const navigate = useNavigate(); - - const handleClick = (link: string) => { - // navigate(`/${link}`); - }; - - return ( - - - handleClick("tab"), - }, - { - key: 1, - content: "Pages", - onClick: () => handleClick("pagesTab"), - }, - ]} - /> - - - ); -}; diff --git a/src/components/Tab.tsx b/src/components/Tab.tsx index 6b1cc68..d747e3c 100644 --- a/src/components/Tab.tsx +++ b/src/components/Tab.tsx @@ -1,11 +1,9 @@ import * as Fluent from "@fluentui/react-northstar"; -import { Button, Text } from "@fluentui/react-northstar"; import { ClientType, ICapabilityStatus, ICapabilityTable } from "../helpers/utils"; import { useContext, useEffect, useState } from "react"; import { AllModules } from "./Modules"; -import { AppOpenLink } from "./capabilities"; import { Host } from "./Host"; import { MobileView } from "../helpers/MobileView"; import { TeamsFxContext } from "./Context"; @@ -48,7 +46,7 @@ const Tab = () => { const setData = async (): Promise => { await app.initialize(); - return await AllModules() as ICapabilityTable[]; + return AllModules() as ICapabilityTable[]; }; /** @@ -159,16 +157,6 @@ const Tab = () => { - - - - - - - - - - {!isMobile && { {isMobile && MobileView(tableRows, showSupportedOnly)} - + Suggestions diff --git a/src/components/capabilities/App.OpenLink.tsx b/src/components/capabilities/App.OpenLink.tsx deleted file mode 100644 index 49ec8c6..0000000 --- a/src/components/capabilities/App.OpenLink.tsx +++ /dev/null @@ -1,75 +0,0 @@ -import { Button, Flex, Input, Tooltip } from "@fluentui/react-northstar"; - -import { CapabilityStatus } from "../../helpers/constants"; -import { app } from "@microsoft/teams-js"; -import { isMobile } from "react-device-detect"; -import { useState } from "react"; - -/** - * This component return button to get context and displays the - * information/ context in the resizeable text area - */ -export const AppOpenLink = () => { - const [inputVal, setInputVal] = useState(""); - const [isValidUrl, setIsValidUrl] = useState(false); - const [showError, setShowError] = useState(false); - const [errorText, setErrorText] = useState(""); - // check to see if app has been initialized - if (app.isInitialized()) { - app.registerOnThemeChangeHandler(() => { - console.log("Theme changed"); - }); - - const isValidHttpUrl = (inputString: string) => { - let url; - try { - url = new URL(inputString); - } catch (e) { - return false; - } - return url.protocol === "http:" || url.protocol === "https:"; - } - - return ( - - { - const event = e as React.ChangeEvent; - const isValid = isValidHttpUrl(event.target.value); - if (!isValid) { - setInputVal(""); - setErrorText("Url is not valid"); - setShowError(true); - } - setInputVal(event.target.value); - setIsValidUrl(isValid); - if (isValid) { - setErrorText(""); - setShowError(false); - } - }} /> - { - await app.initialize(); - if (app.isInitialized()) { - app.openLink(inputVal); - } - }}> - App OpenLink - } - content="app.openLink()" - /> - {showError && - } - - ); - } - // return's if app is not initialized - return <>{CapabilityStatus.NotInitialized}; -}; \ No newline at end of file diff --git a/src/components/capabilities/App.tsx b/src/components/capabilities/App.tsx index 84f7fff..cc117e2 100644 --- a/src/components/capabilities/App.tsx +++ b/src/components/capabilities/App.tsx @@ -1,4 +1,4 @@ -import { Button, Flex, TextArea, Tooltip } from "@fluentui/react-northstar"; +import { Button, Flex, Input, TextArea, Tooltip } from "@fluentui/react-northstar"; import { CapabilityStatus } from "../../helpers/constants"; import { app } from "@microsoft/teams-js"; @@ -12,34 +12,93 @@ import { useState } from "react"; export const App = () => { const [text, setText] = useState(""); const [showText, setShowText] = useState(false); + const [contextClass, setContextClass] = useState(""); + + const [inputVal, setInputVal] = useState(""); + const [showError, setShowError] = useState(false); + const [errorText, setErrorText] = useState(""); // check to see if app has been initialized if (app.isInitialized()) { app.registerOnThemeChangeHandler(() => { console.log("Theme changed"); }); + const isValidHttpUrl = (inputString: string) => { + let url; + try { + url = new URL(inputString); + } catch (e) { + return false; + } + return url.protocol === "http:" || url.protocol === "https:"; + } + return ( - { - const context = await app.getContext(); - const contextString = JSON.stringify(context, null, 3); - setText(contextString); - setShowText(true); - console.log(context); - }}> - Get Context - } - content="app.getContext()" - /> - {showText && ( - <> -