Merge pull request #4012 from kkazala/features/clienttype

This commit is contained in:
Hugo Bernier 2023-09-04 13:13:41 -04:00 committed by GitHub
commit 53608b5c93
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
13 changed files with 65929 additions and 74 deletions

View File

@ -26,6 +26,8 @@ This sample is optimally compatible with the following environment configuration
![Hosted Workbench Compatible](https://img.shields.io/badge/Hosted%20Workbench-Compatible-green.svg)
![Compatible with Remote Containers](https://img.shields.io/badge/Remote%20Containers-Compatible-green.svg)
Tested with Node 16.14.2
## Applies to
- [SharePoint Framework](https://aka.ms/spfx)
@ -42,6 +44,7 @@ This sample is optimally compatible with the following environment configuration
| Version | Date | Comments |
| ------- | ---------------- | --------------- |
| 1.0 | May 30, 2023 | Initial release |
|1.0.1 | August 10, 2023 | `clienttype` header to avoid using tenant rate limits |
## Prerequisites
@ -53,6 +56,13 @@ This sample is optimally compatible with the following environment configuration
- Windows Azure Service Management API: user_impersonation
- Application Insights API: user_impersonation
### Required Permissions
| resource | scope|
|-|-|
|Windows Azure Service Management API|user_impersonation|
|Application Insights API|user_impersonation|
## Minimal Path to Awesome
- Clone this repository
@ -129,6 +139,19 @@ By default, caching duration is set to:
Cache duration for **Application Insights Dashboard** may be extended or disabled using web part properties panel. In case you want to delete the cache manually, the key names for this solution start with **spfxDashboard**.
### Rate Limit
This solution is using `clienttype` header to avoid using general tenant limits and to avoid the error 429 `Too many requests. Please retry.`
The **default rate limits** when querying cost management API **with/without** the `clienttype` parameter are:
| Response header |without `clienttype`| with `clienttype`|
|-|-|-|
|x-ms-ratelimit-remaining-microsoft.costmanagement-`clienttype-requests`|0|1995|
|x-ms-ratelimit-remaining-microsoft.costmanagement-`entity-requests`|2|0|
|x-ms-ratelimit-remaining-microsoft.costmanagement-`tenant-requests`|18|15|
The Cost Management API requests are still a subject to the rate limits. The above response headers, along with `x-ms-ratelimit-microsoft.costmanagement-qpu-consumed` (QPUs consumed by an API call) and `x-ms-ratelimit-microsoft.costmanagement-qpu-remaining` (list of remaining quotas) are printed in the browser console whenever a request to the API has been made
## Accessing Application Insights Data
@ -201,6 +224,12 @@ For questions regarding this sample, [create a new question](https://github.com/
Finally, if you have an idea for improvement, [make a suggestion](https://github.com/pnp/sp-dev-fx-webparts/issues/new?assignees=&labels=Needs%3A+Triage+%3Amag%3A%2Ctype%3Aenhancement%2Csample%3A%20react-dashboards&template=suggestion.yml&sample=react-dashboards&authors=@kkazala&title=react-dashboards%20-%20).
#### Developer resources
- [Build your first app with SPFx (Teams)](https://learn.microsoft.com/en-us/microsoftteams/platform/sbs-gs-spfx?tabs=vscode%2Cviscode)
- [Microsoft 365 Developer Proxy](https://github.com/microsoft/m365-developer-proxy)
- [How to use SPFx powered Microsoft Teams apps in Outlook and Office](https://pnp.github.io/blog/post/spfx-08-spfx-powered-teams-solutions-outlook-office/)
## 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.**

View File

@ -2,8 +2,9 @@
"$schema": "https://developer.microsoft.com/json-schemas/spfx-build/package-solution.schema.json",
"solution": {
"name": "Application Insights and Cost Management dashboards",
"iconPath": "assets/appLogo.png",
"id": "09af0554-67db-4a65-baa6-872dee7117a8",
"version": "1.0.0.0",
"version": "1.0.1.0",
"includeClientSideAssets": true,
"skipFeatureDeployment": true,
"isDomainIsolated": false,
@ -16,14 +17,6 @@
"resource": "Application Insights API",
"scope": "user_impersonation"
}
// {
// "resource": "Microsoft Graph", //Microsoft Graph
// "scope": "user_impersonation"
// },
// {
// "resource": "Office 365 SharePoint Online", //Office 365 SharePoint Online
// "scope": "user_impersonation"
// }
],
"developer": {
"name": "Kinga Kazala (ETHZ)",

65582
samples/react-dashboards/package-lock.json generated Normal file

File diff suppressed because it is too large Load Diff

View File

@ -1,6 +1,6 @@
{
"name": "spfx-applicationinsights",
"version": "1.0.0",
"version": "1.0.1",
"private": true,
"engines": {
"node": ">=16.13.0 <17.0.0"
@ -28,6 +28,7 @@
"chart.js": "2.9.4",
"color": "4.2.3",
"moment": "^2.29.4",
"pnp-appinsights-listener": "^1.0.0",
"react": "17.0.1",
"react-dom": "17.0.1",
"tslib": "2.3.1"

View File

@ -53,6 +53,9 @@ dependencies:
moment:
specifier: ^2.29.4
version: 2.29.4
pnp-appinsights-listener:
specifier: ^1.0.0
version: 1.0.0(react@17.0.1)(tslib@2.3.1)(typescript@4.5.5)
react:
specifier: 17.0.1
version: 17.0.1
@ -1456,6 +1459,165 @@ packages:
typescript: 4.2.4
dev: true
/@microsoft/applicationinsights-analytics-js@3.0.2(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-vrgEiT6cKC2Yb0Y6rCp9CXjFStlRZLI/IhIiBEGYaUfzoytLxUj6F/AizUDYBuNQfE+CTYe0jNyqf+RJgEMkJQ==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-common': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-core-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-shims': 3.0.1(typescript@4.5.5)
'@microsoft/dynamicproto-js': 2.0.2(typescript@4.5.5)
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
tslib: 2.3.1
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/applicationinsights-channel-js@3.0.2(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-jDBNKbCHsJgmpv0CKNhJ/uN9ZphvfGdb93Svk+R4LjO8L3apNNMbDDPxBvXXi0uigRmA1TBcmyBG4IRKjabGhw==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-common': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-core-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-shims': 3.0.1(typescript@4.5.5)
'@microsoft/dynamicproto-js': 2.0.2(typescript@4.5.5)
'@nevware21/ts-async': 0.2.6(typescript@4.5.5)
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
tslib: 2.3.1
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/applicationinsights-common@2.8.15(tslib@2.3.1):
resolution: {integrity: sha512-OZV8pzq2pAa9oRk7PFDQxs7bhAZB1l9CCFU/WYmqtwFyqZGtJDxkigkD/SLnGsg3KzFpk+avsjUGzSPhqeAydA==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-core-js': 2.8.15(tslib@2.3.1)
'@microsoft/applicationinsights-shims': 2.0.2
'@microsoft/dynamicproto-js': 1.1.9
tslib: 2.3.1
dev: false
/@microsoft/applicationinsights-common@3.0.2(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-y+WXWop+OVim954Cu1uyYMnNx6PWO8okHpZIQi/1YSqtqaYdtJVPv4P0AVzwJdohxzVfgzKvqj9nec/VWqE2Zg==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-core-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-shims': 3.0.1(typescript@4.5.5)
'@microsoft/dynamicproto-js': 2.0.2(typescript@4.5.5)
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
tslib: 2.3.1
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/applicationinsights-core-js@2.8.15(tslib@2.3.1):
resolution: {integrity: sha512-yYAs9MyjGr2YijQdUSN9mVgT1ijI1FPMgcffpaPmYbHAVbQmF7bXudrBWHxmLzJlwl5rfep+Zgjli2e67lwUqQ==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-shims': 2.0.2
'@microsoft/dynamicproto-js': 1.1.9
tslib: 2.3.1
dev: false
/@microsoft/applicationinsights-core-js@3.0.2(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-WQhVhzlRlLDrQzn3OShCW/pL3BW5WC57t0oywSknX3q7lMzI3jDg7Ihh0iuIcNTzGCTbDkuqr4d6IjEDWIMtJQ==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-shims': 3.0.1(typescript@4.5.5)
'@microsoft/dynamicproto-js': 2.0.2(typescript@4.5.5)
'@nevware21/ts-async': 0.2.6(typescript@4.5.5)
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
tslib: 2.3.1
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/applicationinsights-dependencies-js@3.0.2(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-b/YTonnbghg9DOFsLg4zdbYPafW8fPIzV+nZxfPPpxjA1LGvPhZz/zVx9YYWJg2RBXjojLQoJxLf1ro5eNGVig==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-common': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-core-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-shims': 3.0.1(typescript@4.5.5)
'@microsoft/dynamicproto-js': 2.0.2(typescript@4.5.5)
'@nevware21/ts-async': 0.2.6(typescript@4.5.5)
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
tslib: 2.3.1
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/applicationinsights-properties-js@3.0.2(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-PFqicp8q4Tc0hqfPjwfqKo12gEqTk1l4lMyUUIU7ugE1XOuDkZcMPha05KnZWKj+F4zQXJcetcAHoVkyoyCFQw==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-common': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-core-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-shims': 3.0.1(typescript@4.5.5)
'@microsoft/dynamicproto-js': 2.0.2(typescript@4.5.5)
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
tslib: 2.3.1
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/applicationinsights-react-js@3.4.3(history@5.3.0)(react@17.0.1)(tslib@2.3.1):
resolution: {integrity: sha512-+IIPDYU7DKBwByN7lK/mkMGrnWMGdyIsEZfDzBh/fKDZgGGGgH9B3WHej+vIpdwBcVaPbYx++lonTshn56C9/A==}
peerDependencies:
history: '>= 4.10.1'
react: '>= 17.0.1'
tslib: '*'
dependencies:
'@microsoft/applicationinsights-common': 2.8.15(tslib@2.3.1)
'@microsoft/applicationinsights-core-js': 2.8.15(tslib@2.3.1)
'@microsoft/applicationinsights-shims': 2.0.2
'@microsoft/dynamicproto-js': 1.1.9
history: 5.3.0
react: 17.0.1
tslib: 2.3.1
dev: false
/@microsoft/applicationinsights-shims@2.0.2:
resolution: {integrity: sha512-PoHEgsnmcqruLNHZ/amACqdJ6YYQpED0KSRe6J7gIJTtpZC1FfFU9b1fmDKDKtFoUSrPzEh1qzO3kmRZP0betg==}
dev: false
/@microsoft/applicationinsights-shims@3.0.1(typescript@4.5.5):
resolution: {integrity: sha512-DKwboF47H1nb33rSUfjqI6ryX29v+2QWcTrRvcQDA32AZr5Ilkr7whOOSsD1aBzwqX0RJEIP1Z81jfE3NBm/Lg==}
dependencies:
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/applicationinsights-web@3.0.2(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-pf2zz/3mmGy1RoyaiLZwhHoE2mFZ+AWR3Zf7xPW7HjTG7dEE4BnovNyW3f9Eu6WWkcHUAHmS/ATzqvVlpB3W6A==}
peerDependencies:
tslib: '*'
dependencies:
'@microsoft/applicationinsights-analytics-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-channel-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-common': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-core-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-dependencies-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-properties-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-shims': 3.0.1(typescript@4.5.5)
'@microsoft/dynamicproto-js': 2.0.2(typescript@4.5.5)
'@nevware21/ts-async': 0.2.6(typescript@4.5.5)
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
tslib: 2.3.1
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/decorators@1.16.1:
resolution: {integrity: sha512-MBvt/cUmOdrnkH8No7KgatmLhJrAIVKUpg1tPv+fAkgtiJ4fPgogwMhzRhpe6iEM0oexQN8GcEAsF99GHI9Kdg==}
engines: {node: '>=12.13.0 <13.0.0 || >=14.15.0 <15.0.0 || >=16.13.0 <17.0.0'}
@ -1463,6 +1625,18 @@ packages:
tslib: 2.3.1
dev: false
/@microsoft/dynamicproto-js@1.1.9:
resolution: {integrity: sha512-n1VPsljTSkthsAFYdiWfC+DKzK2WwcRp83Y1YAqdX552BstvsDjft9YXppjUzp11BPsapDoO1LDgrDB0XVsfNQ==}
dev: false
/@microsoft/dynamicproto-js@2.0.2(typescript@4.5.5):
resolution: {integrity: sha512-MB8trWaFREpmb037k/d0bB7T2BP7Ai24w1e1tbz3ASLB0/lwphsq3Nq8S9I5AsI5vs4zAQT+SB5nC5/dLYTiOg==}
dependencies:
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
transitivePeerDependencies:
- typescript
dev: false
/@microsoft/eslint-config-spfx@1.16.1(eslint@8.7.0)(typescript@4.5.5):
resolution: {integrity: sha512-WJVgoqTUQdlX2r6dY2ETmssXXNr5XwakBdvvPA9KM0Smu9quSbrsyka1fNDRrsuku5pOp5zwfpHn+aK9qg9C9w==}
engines: {node: '>=12.13.0 <13.0.0 || >=14.15.0 <15.0.0 || >=16.13.0 <17.0.0'}
@ -2492,6 +2666,23 @@ packages:
state-local: 1.0.7
dev: false
/@nevware21/ts-async@0.2.6(typescript@4.5.5):
resolution: {integrity: sha512-NCUqEZSbsy7LVtKlUScd/eTst6djkWauLlzoIPVKCOxalEBdO8lrgNRIm4Xy68JNudNN5faqa2WA12X8m0BVhA==}
peerDependencies:
typescript: '>=1'
dependencies:
'@nevware21/ts-utils': 0.9.8(typescript@4.5.5)
typescript: 4.5.5
dev: false
/@nevware21/ts-utils@0.9.8(typescript@4.5.5):
resolution: {integrity: sha512-kZ8s8hcn9jPVX/M7kSsBYrOGlHjqLahmxrG7QeKTk5paeVwfgKdvVCjj5Acb4UGb/ukU1G34U1Z3eb7bbVanyA==}
peerDependencies:
typescript: '>=1'
dependencies:
typescript: 4.5.5
dev: false
/@nodelib/fs.scandir@2.1.5:
resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==}
engines: {node: '>= 8'}
@ -2547,6 +2738,13 @@ packages:
tslib: 2.4.1
dev: false
/@pnp/core@3.17.0:
resolution: {integrity: sha512-h+nu1eHEQ0VpiRcLDQjPyVJHnrHruFJ/v8ZsSbJx1Vg2EoP/X5wDaZNXSjEmF3Xy3yD9aURDkdMw7eVb7PMfEw==}
engines: {node: '>=14.15.1'}
dependencies:
tslib: 2.4.1
dev: false
/@pnp/logging@2.5.0:
resolution: {integrity: sha512-SnmMCN6oADjiHKAIR23FfTqXeQZeXPBnWeVfyZAgzJfRn9uEQoUlkyET3jHjl9kkrFOVkiOD1CRI7TWMIxURbA==}
dependencies:
@ -2560,6 +2758,13 @@ packages:
tslib: 2.4.1
dev: false
/@pnp/logging@3.16.0:
resolution: {integrity: sha512-GzxPnF5BVdY5BBEEd7mdfKQyE7w5ZvoL7uTQ8qwLEy0RGgbdXfiZz649jmwDAbhI69K5vnxrwBc/UEv9Gfz1bw==}
engines: {node: '>=14.15.1'}
dependencies:
tslib: 2.4.1
dev: false
/@pnp/odata@2.5.0:
resolution: {integrity: sha512-AeP01jDvnkiUVn7V+4FT07chz+G/yzrJDH0Gk+qzujJ393ZO6FwJpJEiOCRh9cxF48gqSj/f7r/IIyDHe0+IpQ==}
dependencies:
@ -2568,6 +2773,14 @@ packages:
tslib: 2.2.0
dev: false
/@pnp/queryable@3.17.0:
resolution: {integrity: sha512-kF2fi1pRZr70jGi9qrlA7wLi9Eh1AS+szPGT8C665cko18pahY8OLd8ra8d08Cw8TTuNG/AvJ6Z4BU1I3kSWYg==}
engines: {node: '>=14.15.1'}
dependencies:
'@pnp/core': 3.17.0
tslib: 2.4.1
dev: false
/@pnp/sp@2.5.0:
resolution: {integrity: sha512-4s2p+X5qvkXR72NViKb8DIfC+pvj/a3psZ3Im5PRIan2ErMtu9ch3Lb9nkSaMCF3NTJxWOhkUQ/R6tx8ApaUkg==}
dependencies:
@ -4959,6 +5172,7 @@ packages:
/binary-extensions@2.2.0:
resolution: {integrity: sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==}
engines: {node: '>=8'}
requiresBuild: true
dev: true
/bindings@1.5.0:
@ -7547,6 +7761,7 @@ packages:
/fill-range@7.0.1:
resolution: {integrity: sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==}
engines: {node: '>=8'}
requiresBuild: true
dependencies:
to-regex-range: 5.0.1
dev: true
@ -8385,6 +8600,12 @@ packages:
resolution: {integrity: sha512-l9sfDFsuqtOqKDsQdqrMRk0U85RZc0RtOR9yPI7mRVOa4FsR/BVnZ0shmQRM96Ji99kYZP/7hn1cedc1+ApsTQ==}
dev: true
/history@5.3.0:
resolution: {integrity: sha512-ZqaKwjjrAYUYfLG+htGaIIZ4nioX2L70ZUMIFysS3xvBsSG4x/n1V6TXV3N8ZYNuFGlDirFg32T7B6WOUPDYcQ==}
dependencies:
'@babel/runtime': 7.21.0
dev: false
/hmac-drbg@1.0.1:
resolution: {integrity: sha512-Tti3gMqLdZfhOQY1Mzf/AanLiqh1WTiJgEj26ZuYQ9fbkLomzGchCws4FyrSd4VkpBfiNhaE1On+lOz894jvXg==}
dependencies:
@ -9072,6 +9293,7 @@ packages:
/is-number@7.0.0:
resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==}
engines: {node: '>=0.12.0'}
requiresBuild: true
dev: true
/is-obj@2.0.0:
@ -11777,6 +11999,23 @@ packages:
resolution: {integrity: sha512-2qHaIQr2VLRFoxe2nASzsV6ef4yOOH+Fi9FBOVH6cqeSgUnoyySPZkxzLuzd+RYOQTRpROA0ztTMqxROKSb/nA==}
dev: true
/pnp-appinsights-listener@1.0.0(react@17.0.1)(tslib@2.3.1)(typescript@4.5.5):
resolution: {integrity: sha512-T3eeOk3i6DZVfQ+78iZXDQrwYo1QVd3LtApY+rBnqAtyg6qLg8n7fvV+xym0lwv+KG4sLn7CngPDvztbtB3n3g==}
engines: {node: '>=16.13.0 <17.0.0'}
dependencies:
'@microsoft/applicationinsights-analytics-js': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@microsoft/applicationinsights-react-js': 3.4.3(history@5.3.0)(react@17.0.1)(tslib@2.3.1)
'@microsoft/applicationinsights-web': 3.0.2(tslib@2.3.1)(typescript@4.5.5)
'@pnp/core': 3.17.0
'@pnp/logging': 3.16.0
'@pnp/queryable': 3.17.0
history: 5.3.0
transitivePeerDependencies:
- react
- tslib
- typescript
dev: false
/posix-character-classes@0.1.1:
resolution: {integrity: sha512-xTgYBc3fuo7Yt7JbiuFxSYGToMoz8fLoE6TC9Wx1P/u+LfeThMOAqmuyECnlBaaJb+u1m9hHiXUEtwW4OzfUJg==}
engines: {node: '>=0.10.0'}
@ -12701,6 +12940,7 @@ packages:
/readdirp@3.6.0:
resolution: {integrity: sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==}
engines: {node: '>=8.10.0'}
requiresBuild: true
dependencies:
picomatch: 2.3.1
dev: true
@ -13979,7 +14219,7 @@ packages:
peerDependencies:
react: '>=16.8.3'
dependencies:
'@babel/runtime': 7.4.5
'@babel/runtime': 7.21.0
invariant: 2.2.4
react: 17.0.1
dev: false
@ -14289,6 +14529,7 @@ packages:
/to-regex-range@5.0.1:
resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==}
engines: {node: '>=8.0'}
requiresBuild: true
dependencies:
is-number: 7.0.0
dev: true
@ -14486,7 +14727,6 @@ packages:
resolution: {integrity: sha512-TCTIul70LyWe6IJWT8QSYeA54WQe8EjQFU4wY52Fasj5UKx88LNYKCgBEHcOMOrFF1rKGbD8v/xcNWVUq9SymA==}
engines: {node: '>=4.2.0'}
hasBin: true
dev: true
/uc.micro@1.0.6:
resolution: {integrity: sha512-8Y75pvTYkLJW2hWQHXxoqRgV7qb9B+9vFEtidML+7koHUFapnVJAZ6cKs+Qjz5Aw3aZWHMC6u0wJE3At+nSGwA==}

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.5 KiB

View File

@ -19,6 +19,7 @@ export class AppInsightsHelperSSO {
this.aadHttpClientFactory = config.aadHttpClientFactory;
this._postUrl = AppInsightsQueryHelper.GetAPIEndpoint(config.appId, config.endpoint);
this.requestHeaders.append("Content-type", "application/json; charset=utf-8");
this.requestHeaders.append("clienttype", "pnp.apps.appinsights");
this.httpClientOptions = { headers: this.requestHeaders };
this.endpointType = config.endpoint;
this.cacheDuration = cache.cacheDuration;
@ -105,6 +106,7 @@ export default class AppInsightsHelper {
this._postUrl = AppInsightsQueryHelper.GetAPIEndpoint(config.appId, config.endpoint);
this.requestHeaders.append("Content-type", "application/json; charset=utf-8");
this.requestHeaders.append("x-api-key", config.appKey);
this.requestHeaders.append("clienttype", "pnp.apps.appinsights");
this.httpClientOptions = { headers: this.requestHeaders };
this.endpointType = config.endpoint;
this.cacheDuration = cache.cacheDuration;

View File

@ -1,8 +1,8 @@
/* eslint-disable @typescript-eslint/no-explicit-any */
import { cloneDeep, merge, uniq } from "@microsoft/sp-lodash-subset";
import { ChartType, PaletteGenerator } from "@pnp/spfx-controls-react";
import { ChartData, ChartDataSets, ChartOptions, TimeUnit } from "chart.js";
import stringsCommon from "CommonDasboardWebPartStrings";
import { ChartData, ChartDataSets, ChartOptions, TimeUnit } from "chart.js";
import moment from "moment";
import { ColumnsInfo, DataTypesInfo } from "../components/InsightsChart/IInsightsChartProps";
import ApiHelper from "./ApiHelper";
@ -214,7 +214,6 @@ export default class ChartHelper {
}
dataSets.push(dataSet);
});
console.log(dataSets);
return {
datasets: dataSets
}

View File

@ -83,9 +83,11 @@ export interface IDashboardConfig{
export interface IAppInsightsWebPartProps extends IAppInsightsConfig, IAppInsightsQuery, ICacheConfig, ILayoutConfig, IDashboardConfig {
isDevMode: boolean;
logLevel?: number;
appInsightsConnString?: string;
}
export interface ICostManagementWebPartProps extends ICostManagementConfig, ICostManagementQuery, ICacheConfig, ILayoutConfig, IDashboardConfig {
logLevel?: number;
appInsightsConnString?: string;
}

View File

@ -7,8 +7,12 @@ const theme = (process.env.NODE_ENV !== 'production')
})
: getTheme();
const padding4px = theme.spacing.s2;
const padding8px = theme.spacing.s1;
const spacing4px = theme.spacing.s2;
const spacing8px = theme.spacing.s1;
const spacing16px = theme.spacing.m;
const spacing20px = theme.spacing.l1;
// const spacing32px = theme.spacing.l2;
const fontSmall = theme.fonts.small.fontSize;
const minWidth=280;
@ -21,7 +25,9 @@ const getColorRGBA = (color: string, opacity: string | number): string => {
return `rgba(${col.r},${col.g},${col.b},${opacity})`;
}
const stackTokens: IStackTokens = { childrenGap: `${padding8px} ${padding8px}` }; //rowGap columnGap 8px 4px
const teamsPadding = `0px ${spacing16px} 0px ${spacing20px}`
const stackTokens: IStackTokens = { childrenGap: `${spacing8px} ${spacing8px}` }; //rowGap columnGap 8px 4px
const stackStylesMain: Partial<IStackStyles> = {
root: {
backgroundColor: 'inherit'
@ -40,8 +46,8 @@ const stackStylesDatePicker: Partial<IStackStyles> = {
backgroundColor: theme.palette.neutralQuaternary,
paddingTop: 1,
paddingBottom: 1,
paddingLeft: padding8px,
paddingRight: padding8px
paddingLeft: spacing8px,
paddingRight: spacing8px
},
}
@ -62,17 +68,17 @@ const stackItemStyles100: Partial<IStackItemStyles> = {
}
const stackItemStyles50: Partial<IStackItemStyles> = {
root: {
width: `calc(50% - ${padding8px})`,
width: `calc(50% - ${spacing8px})`,
}
}
const stackItemStyles66: Partial<IStackItemStyles> = {
root: {
width: `calc(60% - ${padding4px})`,
width: `calc(60% - ${spacing4px})`,
}
}
const stackItemStyles33: Partial<IStackItemStyles> = {
root: {
width: `calc(30% - ${padding4px})`,
width: `calc(30% - ${spacing4px})`,
}
}
@ -95,7 +101,7 @@ const pivotStylesDashboard: Partial<IPivotStyles> = {
flexFlow:'wrap'
},
itemContainer: {
padding: padding8px,
padding: spacing8px,
paddingTop:0,
backgroundColor: theme.palette.neutralTertiaryAlt
}
@ -184,20 +190,8 @@ const colorPickerStyles: Partial<IChoiceGroupStyles> = {
}
export {
theme,
stackTokens,
heatmapStyles,
datePickerStyles,
dashboardStyles,
stackStyles,
stackStylesMain,
shimmerStyleChart,
transparentTheme,
chartTheme,
disabledPickerStyle,
colorPickerStyles,
linkStyles,
getColorRGB,
getColorRGBA,
chartTheme, colorPickerStyles, dashboardStyles, datePickerStyles, disabledPickerStyle, getColorRGB,
getColorRGBA, heatmapStyles, linkStyles, shimmerStyleChart, stackStyles,
stackStylesMain, stackTokens, teamsPadding, theme, transparentTheme
};

View File

@ -26,6 +26,7 @@ export default class CostMngmtHelper {
}
);
this.requestHeaders.append("Content-type", "application/json; charset=utf-8");
this.requestHeaders.append("clienttype", "pnp.apps.costmanagement");
this.httpClientOptions = { headers: this.requestHeaders };
this.cacheDuration = cache.cacheDuration;
this.cacheKey = `${config.subscriptionId ?? ''}-${config.resourceGroupName ?? ''}-${config.managementGroupId ?? ''}-${cache.userLoginName}`

View File

@ -5,42 +5,42 @@ import {
import { BaseClientSideWebPart } from '@microsoft/sp-webpart-base';
import * as ReactDom from 'react-dom';
import { ConsoleListener, Logger } from '@pnp/logging';
import PnPTelemetry from "@pnp/telemetry-js";
import strings from 'AppInsightsDasboardWebPartStrings';
import { AppInsights, setLogger } from 'pnp-appinsights-listener';
import * as React from 'react';
import { ThemedPalette } from '../../common/ColorsHelper';
import { CacheExpiration, IAppInsightsQuery, IAppInsightsWebPartProps } from '../../common/CommonProps';
import { teamsPadding } from '../../common/ComponentStyles';
import { ChartStyles, LayoutStyles, ListStyles } from '../../common/DashboardHelper';
import ApplicationInsightsLogs from './components/ApplicationInsightsLogs';
import { IApplicationInsightsLogsProps } from './components/IApplicationInsightsLogsProps';
const telemetry = PnPTelemetry.getInstance();
telemetry.optOut();
const LOG_SOURCE: string = 'Application Insights Logs WebPart';
export default class ApplicationInsightsLogsWebPart extends BaseClientSideWebPart<IAppInsightsWebPartProps> {
public onInit(): Promise<void> {
const _setLogger = (): void => {
// eslint-disable-next-line @typescript-eslint/no-explicit-any
Logger.subscribe(new (ConsoleListener as any)());
//default is 2 - Warning
if (this.properties.logLevel && this.properties.logLevel in [0, 1, 2, 3, 99]) {
Logger.activeLogLevel = this.properties.logLevel;
if (this.properties.appInsightsConnString) {
const ai = AppInsights(this.properties.appInsightsConnString);
setLogger({
appInsights: ai,
logLevel: this.properties.logLevel,
console: true
});
}
Logger.write(`${LOG_SOURCE} ${this.manifest.version} activated`);
Logger.write(`${LOG_SOURCE} Initialized with properties:`);
Logger.write(`${LOG_SOURCE} ${JSON.stringify(this.properties, undefined, 2)}`);
else {
setLogger({
logLevel: this.properties.logLevel,
console: true
});
}
_setLogger();
return Promise.resolve();
}
public render(): void {
let dashboard: React.ReactElement;
const element: React.ReactElement<IApplicationInsightsLogsProps> = React.createElement(ApplicationInsightsLogs, {
...this.properties,
@ -58,7 +58,14 @@ export default class ApplicationInsightsLogsWebPart extends BaseClientSideWebPar
onConfigureTimePicker: this._onConfigureTimePicker,
onConfigureLayoutSettings: this._onConfigureLayoutSettings,
});
ReactDom.render(element, this.domElement);
if (!!this.context.sdks.microsoftTeams) { // running in Teams, office.com or Outlook
dashboard = React.createElement('div', { style: { padding: teamsPadding }}, element);
}
else{
dashboard=element
}
ReactDom.render(dashboard, this.domElement);
}
//#region WebPart Properties
public _onPivotItemChange = (key: string): void => {
@ -106,7 +113,6 @@ export default class ApplicationInsightsLogsWebPart extends BaseClientSideWebPar
text: CacheExpiration[value as keyof typeof CacheExpiration]
};
});
console.log(this.properties.cacheDuration)
return {
pages: [

View File

@ -1,13 +1,14 @@
import { Version } from '@microsoft/sp-core-library';
import { IPropertyPaneConfiguration, PropertyPaneLabel } from '@microsoft/sp-property-pane';
import { BaseClientSideWebPart } from '@microsoft/sp-webpart-base';
import { ConsoleListener, Logger } from '@pnp/logging';
import PnPTelemetry from "@pnp/telemetry-js";
import stringsCommon from 'CommonDasboardWebPartStrings';
import { AppInsights, setLogger } from 'pnp-appinsights-listener';
import React from 'react';
import * as ReactDom from 'react-dom';
import { ThemedPalette } from '../../common/ColorsHelper';
import { ICostManagementConfig, ICostManagementQuery, ICostManagementWebPartProps } from '../../common/CommonProps';
import { teamsPadding } from '../../common/ComponentStyles';
import { ChartStyles, LayoutStyles, ListStyles } from '../../common/DashboardHelper';
import CostInsightsDashboard from './components/CostInsightsDashboard';
import { ICostInsightsDashboardProps } from './components/ICostInsightsDashboardProps';
@ -15,30 +16,29 @@ import { ICostInsightsDashboardProps } from './components/ICostInsightsDashboard
const telemetry = PnPTelemetry.getInstance();
telemetry.optOut();
const LOG_SOURCE: string = 'Cost Insights WebPart';
export default class CostInsightsWebPart extends BaseClientSideWebPart<ICostManagementWebPartProps> {
public onInit(): Promise<void> {
const _setLogger = (): void => {
// eslint-disable-next-line @typescript-eslint/no-explicit-any
Logger.subscribe(new (ConsoleListener as any)());
//default is 2 - Warning
if (this.properties.logLevel && this.properties.logLevel in [0, 1, 2, 3, 99]) {
Logger.activeLogLevel = this.properties.logLevel;
if (this.properties.appInsightsConnString) {
const ai = AppInsights(this.properties.appInsightsConnString);
setLogger({
appInsights: ai,
logLevel: this.properties.logLevel,
console: true
});
}
Logger.write(`${LOG_SOURCE} ${this.manifest.version} activated`);
Logger.write(`${LOG_SOURCE} Initialized with properties:`);
Logger.write(`${LOG_SOURCE} ${JSON.stringify(this.properties, undefined, 2)}`);
else {
setLogger({
logLevel: this.properties.logLevel,
console: true
});
}
_setLogger();
return Promise.resolve();
}
public render(): void {
let dashboard: React.ReactElement;
const element: React.ReactElement<ICostInsightsDashboardProps> = React.createElement(
CostInsightsDashboard,
{
@ -58,7 +58,13 @@ export default class CostInsightsWebPart extends BaseClientSideWebPart<ICostMana
onConfigureLayoutSettings: this._onConfigureLayoutSettings,
}
);
ReactDom.render(element, this.domElement);
if (!!this.context.sdks.microsoftTeams) { // running in Teams, office.com or Outlook
dashboard = React.createElement('div', { style: { padding: teamsPadding } }, element);
}
else {
dashboard = element
}
ReactDom.render(dashboard, this.domElement);
}
public _onPivotItemChange = (key: string): void => {
this.properties.pivotKey = key