codeapp-js 1.0.2 → 1.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (128) hide show
  1. package/AI/skills/autoreview/SKILL.md +69 -0
  2. package/AI/skills/connections/SKILL.md +4 -4
  3. package/AI/skills/dataverse/SKILL.md +4 -2
  4. package/AI/skills/keyvault/SKILL.md +139 -0
  5. package/AI/skills/office365-groups/SKILL.md +46 -25
  6. package/AI/skills/office365-outlook/SKILL.md +56 -25
  7. package/AI/skills/office365-users/SKILL.md +41 -36
  8. package/AI/skills/sharepoint/SKILL.md +174 -31
  9. package/AI/skills/start/SKILL.md +1 -0
  10. package/codeApp/dist/connectors/autoreview.js +1654 -0
  11. package/codeApp/dist/connectors/office365groups.js +2995 -432
  12. package/{examples/outlook Demo/.power/schemas/office365/office365.Schema.json → codeApp/dist/connectors/office365outlook.js} +7439 -16
  13. package/codeApp/dist/connectors/office365users.js +2990 -349
  14. package/codeApp/dist/connectors/sharepoint.js +529 -308
  15. package/examples/combined demo/dist/connectors/office365outlook.js +28521 -0
  16. package/examples/combined demo/dist/connectors/office365users.js +3154 -0
  17. package/examples/combined demo/dist/index.js +2 -6
  18. package/examples/combined demo/power.config.json +1 -1
  19. package/examples/groups Demo/{.power/schemas/office365groups/office365groups.Schema.json → dist/connectors/office365groups.js } +3205 -2204
  20. package/examples/groups Demo/dist/index.js +1 -5
  21. package/examples/groups Demo/power.config.json +1 -1
  22. package/examples/myProfile/dist/connectors/office365users.js +3154 -0
  23. package/examples/myProfile/dist/index.js +1 -5
  24. package/examples/myProfile/power.config.json +1 -1
  25. package/examples/outlook Demo/dist/connectors/office365outlook.js +28521 -0
  26. package/examples/outlook Demo/dist/index.js +2 -5
  27. package/examples/outlook Demo/power.config.json +1 -1
  28. package/examples/sharePoint Demo/dist/connectors/sharepoint.js +687 -0
  29. package/examples/sharePoint Demo/dist/index.js +86 -127
  30. package/examples/sharePoint Demo/power.config.json +1 -1
  31. package/package.json +1 -1
  32. package/codeApp/.power/schemas/appschemas/dataSourcesInfo.ts +0 -6275
  33. package/codeApp/.power/schemas/jira/jira.Schema.json +0 -6903
  34. package/codeApp/.power/schemas/keyvault/keyvault.Schema.json +0 -1600
  35. package/codeApp/.power/schemas/office365groups/office365groups.Schema.json +0 -2204
  36. package/codeApp/.power/schemas/teams/teams.Schema.json +0 -11112
  37. package/codeApp/dist/connectors/outlook.js +0 -1393
  38. package/codeApp/src/generated/models/AzureKeyVaultModel.ts +0 -107
  39. package/codeApp/src/generated/models/JiraModel.ts +0 -501
  40. package/codeApp/src/generated/models/Office365GroupsModel.ts +0 -363
  41. package/codeApp/src/generated/models/Office365OutlookModel.ts +0 -2046
  42. package/codeApp/src/generated/models/Office365UsersModel.ts +0 -254
  43. package/codeApp/src/generated/services/AzureKeyVaultService.ts +0 -257
  44. package/codeApp/src/generated/services/JiraService.ts +0 -1124
  45. package/codeApp/src/generated/services/Office365GroupsService.ts +0 -326
  46. package/codeApp/src/generated/services/Office365OutlookService.ts +0 -2476
  47. package/codeApp/src/generated/services/Office365UsersService.ts +0 -358
  48. package/examples/apps/kanban/dist/dataverse.js +0 -94
  49. package/examples/apps/kanban/dist/environmentVar.js +0 -55
  50. package/examples/apps/kanban/dist/index.css +0 -605
  51. package/examples/apps/kanban/dist/index.html +0 -21
  52. package/examples/apps/kanban/dist/index.js +0 -860
  53. package/examples/apps/kanban/dist/office365groups.js +0 -97
  54. package/examples/apps/kanban/dist/office365users.js +0 -451
  55. package/examples/apps/kanban/dist/outlook.js +0 -162
  56. package/examples/apps/kanban/dist/power-apps-data.js +0 -2953
  57. package/examples/apps/kanban/dist/sharepoint.js +0 -435
  58. package/examples/apps/kanban/power.config.json +0 -35
  59. package/examples/apps/kanban/src/generated/index.ts +0 -14
  60. package/examples/apps/kanban/src/generated/models/Office365GroupsModel.ts +0 -363
  61. package/examples/apps/kanban/src/generated/models/Office365OutlookModel.ts +0 -2046
  62. package/examples/apps/kanban/src/generated/models/Office365UsersModel.ts +0 -254
  63. package/examples/apps/kanban/src/generated/services/Office365GroupsService.ts +0 -326
  64. package/examples/apps/kanban/src/generated/services/Office365OutlookService.ts +0 -2476
  65. package/examples/apps/kanban/src/generated/services/Office365UsersService.ts +0 -358
  66. package/examples/apps/planning Poker/additional files/AgilePoker_1_0_0_1.zip +0 -0
  67. package/examples/apps/planning Poker/additional files/PokerTables_1_0_0_1.zip +0 -0
  68. package/examples/apps/planning Poker/additional files/customizations (tables).xml +0 -6429
  69. package/examples/apps/planning Poker/additional files/dataverse-tables.json +0 -165
  70. package/examples/apps/planning Poker/additional files/readme.md +0 -122
  71. package/examples/apps/planning Poker/dist/dataverse.js +0 -78
  72. package/examples/apps/planning Poker/dist/index.html +0 -198
  73. package/examples/apps/planning Poker/dist/index.js +0 -955
  74. package/examples/apps/planning Poker/dist/power-apps-data.js +0 -2953
  75. package/examples/apps/planning Poker/dist/styles.css +0 -815
  76. package/examples/apps/planning Poker/power.config.json +0 -50
  77. package/examples/apps/solution explorer/dist/codeapp.js +0 -1098
  78. package/examples/apps/solution explorer/dist/icon-512.png +0 -0
  79. package/examples/apps/solution explorer/dist/index.html +0 -80
  80. package/examples/apps/solution explorer/dist/index.js +0 -735
  81. package/examples/apps/solution explorer/dist/power-apps-data.js +0 -3007
  82. package/examples/apps/solution explorer/dist/styles.css +0 -571
  83. package/examples/apps/solution explorer/power.config.json +0 -151
  84. package/examples/apps/todo/dist/dataverse.js +0 -64
  85. package/examples/apps/todo/dist/icon192.png +0 -0
  86. package/examples/apps/todo/dist/index.html +0 -75
  87. package/examples/apps/todo/dist/index.js +0 -9
  88. package/examples/apps/todo/dist/power-apps-data.js +0 -2953
  89. package/examples/apps/todo/dist/renderer.js +0 -375
  90. package/examples/apps/todo/dist/styles.css +0 -691
  91. package/examples/apps/todo/power.config.json +0 -35
  92. package/examples/combined demo/.power/schemas/appschemas/dataSourcesInfo.ts +0 -6275
  93. package/examples/combined demo/.power/schemas/jira/jira.Schema.json +0 -6903
  94. package/examples/combined demo/.power/schemas/keyvault/keyvault.Schema.json +0 -1600
  95. package/examples/combined demo/.power/schemas/teams/teams.Schema.json +0 -11112
  96. package/examples/combined demo/dist/office365users.js +0 -513
  97. package/examples/combined demo/dist/outlook.js +0 -1393
  98. package/examples/combined demo/src/generated/index.ts +0 -12
  99. package/examples/combined demo/src/generated/models/AzureKeyVaultModel.ts +0 -107
  100. package/examples/combined demo/src/generated/models/JiraModel.ts +0 -501
  101. package/examples/combined demo/src/generated/models/Office365GroupsModel.ts +0 -363
  102. package/examples/combined demo/src/generated/models/Office365OutlookModel.ts +0 -2046
  103. package/examples/combined demo/src/generated/models/Office365UsersModel.ts +0 -254
  104. package/examples/combined demo/src/generated/services/AzureKeyVaultService.ts +0 -257
  105. package/examples/combined demo/src/generated/services/JiraService.ts +0 -1124
  106. package/examples/combined demo/src/generated/services/Office365GroupsService.ts +0 -326
  107. package/examples/combined demo/src/generated/services/Office365OutlookService.ts +0 -2476
  108. package/examples/combined demo/src/generated/services/Office365UsersService.ts +0 -358
  109. package/examples/groups Demo/.power/schemas/appschemas/dataSourcesInfo.ts +0 -613
  110. package/examples/groups Demo/dist/office365groups.js +0 -642
  111. package/examples/groups Demo/src/generated/index.ts +0 -10
  112. package/examples/groups Demo/src/generated/models/Office365GroupsModel.ts +0 -363
  113. package/examples/groups Demo/src/generated/services/Office365GroupsService.ts +0 -326
  114. package/examples/myProfile/dist/office365users.js +0 -517
  115. package/examples/outlook Demo/.power/schemas/appschemas/dataSourcesInfo.ts +0 -6512
  116. package/examples/outlook Demo/dist/outlook.js +0 -1393
  117. package/examples/outlook Demo/src/generated/index.ts +0 -10
  118. package/examples/outlook Demo/src/generated/models/Office365OutlookModel.ts +0 -2046
  119. package/examples/outlook Demo/src/generated/services/Office365OutlookService.ts +0 -2476
  120. package/examples/sharePoint Demo/dist/sharepoint.js +0 -466
  121. package/examples/sharePoint Demo/src/generated/index.ts +0 -14
  122. package/examples/sharePoint Demo/src/generated/models/Office365GroupsModel.ts +0 -363
  123. package/examples/sharePoint Demo/src/generated/models/Office365OutlookModel.ts +0 -2046
  124. package/examples/sharePoint Demo/src/generated/models/Office365UsersModel.ts +0 -254
  125. package/examples/sharePoint Demo/src/generated/services/Office365GroupsService.ts +0 -326
  126. package/examples/sharePoint Demo/src/generated/services/Office365OutlookService.ts +0 -2476
  127. package/examples/sharePoint Demo/src/generated/services/Office365UsersService.ts +0 -358
  128. package/readme.md +0 -590
@@ -3,22 +3,42 @@ name: sharepoint
3
3
  description: "Use when: building or debugging SharePoint list, library, file, or HTTP-request flows in a Power Apps Code App, including list-id or environment-variable-based setup."
4
4
  ---
5
5
 
6
- # SharePoint Connector Guide
6
+ # SharePoint App Builder Guide
7
7
 
8
- > Agent limitation: do not use CLI commands directly from chat for SharePoint setup. Use the built-in Sync Connections and Deploy buttons instead.
8
+ Use this skill when an app needs SharePoint list CRUD, file operations, library metadata, or a last-resort SharePoint HTTP request through `./connectors/sharepoint.js`.
9
9
 
10
- ## Workflow
10
+ Use the working OG-style SharePoint wrapper pattern from this repo as the reference: siteUrl-based connector paths, wrapper-side site URL encoding, `GetTables` lookup for the connector table token, and standard CRUD after resolution.
11
11
 
12
- Before writing code, prefer these connection approaches:
12
+ Do not use CLI setup flows from chat. Use the built-in Auth, Sync Connections, and Deploy buttons.
13
+
14
+ ## First Questions To Ask
15
+
16
+ Ask only the minimum needed to choose the right setup and write working code:
17
+
18
+ 1. Is this app working with a SharePoint list, files in a document library, or a custom SharePoint HTTP endpoint?
19
+ 2. What is the exact SharePoint site URL?
20
+ 3. Do you already have the SharePoint list ID?
21
+ 4. If not, do you at least know the list name for one-time resolution?
22
+ 5. Should config come from hardcoded app config or Dataverse environment variables?
23
+ 6. Does the current `power.config.json` already contain `connectionReferences.sharepointonline`?
24
+ 7. Which operations are required: read, create, update, delete, file create/move/delete, or custom request only?
25
+ 8. Are there complex SharePoint fields involved such as person, lookup, or multi-value choice columns?
26
+
27
+ Preferred configuration order:
13
28
 
14
29
  - A: site URL + list ID
15
- - B: environment variables that resolve the site URL and list ID
30
+ - B: environment variables that resolve site URL + list ID
31
+ - C: site URL + list name only, resolved once through `resolveSharePointList(...)`
32
+
33
+ Do not ask for a list name as the primary CRUD identifier. If the user only knows the list name, use it only as a lookup hint.
16
34
 
17
- Do not ask the user for a list name as the primary CRUD identifier. If they only know the list name, use `listTables(...)` once to discover the connector table ID and then continue with list-ID operations.
35
+ Schemas are often stored in the 'agent' folder.
18
36
 
19
37
  ## power.config.json
20
38
 
21
- Expose `sharepointonline` in `connectionReferences`.
39
+ Always read the current `power.config.json` before editing it.
40
+
41
+ Ensure `"id": "/providers/Microsoft.PowerApps/apis/shared_sharepointonline"` exists and ` "dataSources": ["sharepointonline"]`.
22
42
 
23
43
  ```json
24
44
  {
@@ -33,45 +53,168 @@ Expose `sharepointonline` in `connectionReferences`.
33
53
  }
34
54
  ```
35
55
 
36
- No Dataverse tables are needed unless the app also uses environment variables.
37
-
38
- ## Helper Surface
56
+ Rules for editing `power.config.json`:
39
57
 
40
- The wrapper in `dev files/sharepoint.js` exports:
58
+ - Preserve existing keys such as `sharedConnectionId`, `authenticationType`, and other working connection metadata.
59
+ - No Dataverse tables are needed for basic SharePoint-only apps.
60
+ - If the app uses Dataverse environment variables, also load the environment-variables skill and add the two Dataverse environment-variable tables there.
41
61
 
42
- - List ID pattern: `getItems`, `getSpItem`, `createSpItem`, `updateSpItem`, `deleteSpItem`
43
- - Generic helpers: `callSharePointOperation`, `sendHttpRequest`, `listTables`, `listLibrary`
44
- - File helpers: `createFile`, `updateFile`, `deleteFile`, `moveFile`, `getFileMetadata`
62
+ ## Core App Rules
45
63
 
46
- The list-ID helpers use the SharePoint connector table API. `sendHttpRequest(...)` remains available only as an advanced escape hatch when there is no dedicated helper for the operation you need.
64
+ - Prefer dedicated SharePoint helpers over raw HTTP.
65
+ - Keep SharePoint list discovery inside `sharepoint.js`, not in app pages or components.
66
+ - Do not pre-encode the site URL. Pass the raw URL string and let the wrapper encode it.
67
+ - If a list ID is known, still prefer resolving through `resolveSharePointList(...)` once at startup so the wrapper can match the connector table token.
68
+ - If the app only knows a list name, use `resolveSharePointList(...)` or a by-list helper and let the wrapper do `listTables(...)` lookup.
47
69
 
48
- ## Important Corrections
70
+ When generating or fixing a local `dist/connectors/sharepoint.js` wrapper:
49
71
 
50
- - The single-item and CRUD helpers for the list-ID path are `getSpItem`, `createSpItem`, `updateSpItem`, and `deleteSpItem` in this repo.
51
- - `sharepoint.js` encodes `siteUrl` internally with `encodeURIComponent(...)`. Do not pre-encode the URL before passing it in.
52
- - For environment-variable based setup, import `getEnvironmentVariable(...)` from `./codeapp.js`, not from a separate `environmentVar.js` helper.
72
+ - initialize the connector client with `getClient(dataSourcesInfo)`
73
+ - keep the working SharePoint action parameter names aligned with the OG contract: `siteUrl`, `table`, `item`, and the standard CRUD/query names
74
+ - keep reusable list-resolution helpers in the wrapper
75
+ - preserve `callSharePointOperation(...)` as the escape hatch for supported actions
76
+ - use `sendHttpRequest(...)` only when no dedicated helper exists
53
77
 
54
- ## Example Imports
78
+ ## Recommended Startup Pattern
55
79
 
56
- Approach A:
80
+ For list-backed apps, resolve the list once during startup and keep the returned access object in app state.
57
81
 
58
82
  ```js
59
- import { getItems, getSpItem, createSpItem, updateSpItem, deleteSpItem, listTables } from './sharepoint.js';
83
+ import {
84
+ createSpItemByList,
85
+ deleteSpItemByList,
86
+ getItemsByList,
87
+ resolveSharePointList,
88
+ updateSpItemByList,
89
+ } from './connectors/sharepoint.js';
90
+
91
+ const oAppConfig = {
92
+ sSiteUrl: 'https://tenant.sharepoint.com/sites/example',
93
+ sListId: '00000000-0000-0000-0000-000000000000',
94
+ sListName: 'Tasks',
95
+ };
96
+
97
+ const oListAccess = await resolveSharePointList(oAppConfig.sSiteUrl, {
98
+ listId: oAppConfig.sListId,
99
+ listName: oAppConfig.sListName,
100
+ });
101
+
102
+ const aItems = await getItemsByList(oListAccess.sSiteUrl, oListAccess, { top: 200 });
103
+ await createSpItemByList(oListAccess.sSiteUrl, oListAccess, { Title: 'New item' });
104
+ await updateSpItemByList(oListAccess.sSiteUrl, oListAccess, 1, { Title: 'Updated item' });
105
+ await deleteSpItemByList(oListAccess.sSiteUrl, oListAccess, 1);
60
106
  ```
61
107
 
62
- Approach B:
108
+ Why this is the preferred pattern:
63
109
 
64
- ```js
65
- import { getItems, getSpItem, createSpItem, updateSpItem, deleteSpItem } from './sharepoint.js';
66
- ```
110
+ - it keeps list lookup and fallback logic inside the wrapper
111
+ - it works whether the connector resolves a table token or falls back to the configured list ID
112
+ - it matches the working SharePoint demo app in this repo
113
+
114
+ ## Function Surface And Correct Usage
115
+
116
+ Generic helpers:
117
+
118
+ - `callSharePointOperation(operationName, parameters)`
119
+ - `sendHttpRequest({ method, uri, headers, body })`
120
+ - `listTables(siteUrl)`
121
+ - `listLibrary(siteUrl)`
122
+ - `resolveSharePointList(siteUrl, listReference)`
123
+
124
+ List-ID CRUD helpers:
125
+
126
+ - `getItems(siteUrl, listId, { filter, orderBy, top, skip })`
127
+ - `getSpItem(siteUrl, listId, itemId)`
128
+ - `createSpItem(siteUrl, listId, fields)`
129
+ - `updateSpItem(siteUrl, listId, itemId, changedFields)`
130
+ - `deleteSpItem(siteUrl, listId, itemId)`
131
+
132
+ By-list CRUD helpers:
133
+
134
+ - `getItemsByList(siteUrl, listReference, queryOptions)`
135
+ - `getSpItemByList(siteUrl, listReference, itemId)`
136
+ - `createSpItemByList(siteUrl, listReference, fields)`
137
+ - `updateSpItemByList(siteUrl, listReference, itemId, changedFields)`
138
+ - `deleteSpItemByList(siteUrl, listReference, itemId)`
139
+
140
+ File helpers:
67
141
 
68
- Approach C:
142
+ - `createFile(siteUrl, folderPath, fileName, fileContent)`
143
+ - `updateFile(siteUrl, fileId, fileContent)`
144
+ - `deleteFile(siteUrl, fileId)`
145
+ - `moveFile(siteUrl, sourceFileId, destinationFolderPath, newFileName)`
146
+ - `getFileMetadata(siteUrl, fileId)`
147
+
148
+ Important behavior:
149
+
150
+ - `resolveSharePointList(...)` returns both generic keys and app-friendly aliases: `siteUrl`, `listId`, `listName`, `sSiteUrl`, `sListId`, `sListName`, plus `table` and lookup metadata.
151
+ - `getItemsByList(...)` and the other by-list helpers accept a list name, list ID object, or resolved access object.
152
+ - Create and update payloads must be plain objects.
153
+ - Item IDs can be strings or numbers.
154
+ - Query options such as `top` and `skip` must be numeric if supplied.
155
+ - `moveFile(...)` can rename during the move when `newFileName` is supplied.
156
+ - `sendHttpRequest(...)` expects `{ method, uri, headers, body }` on the OG SharePoint wrapper contract.
157
+
158
+ ## Response Handling In App Code
159
+
160
+ SharePoint item reads may come back as an array or inside a nested result shape. Normalize collections in app code before rendering tables or computing counts.
69
161
 
70
162
  ```js
71
- import { getEnvironmentVariable } from './codeapp.js';
72
- import { getItems, createSpItem, updateSpItem, deleteSpItem } from './sharepoint.js';
163
+ function normalizeCollection(oPayload) {
164
+ if (Array.isArray(oPayload)) {
165
+ return oPayload;
166
+ }
167
+
168
+ const aCandidates = [
169
+ oPayload && oPayload.value,
170
+ oPayload && oPayload.items,
171
+ oPayload && oPayload.results,
172
+ oPayload && oPayload.body,
173
+ oPayload && oPayload.data,
174
+ oPayload && oPayload.result,
175
+ oPayload && oPayload.response,
176
+ oPayload && oPayload.d && oPayload.d.results,
177
+ ];
178
+
179
+ return aCandidates.find(Array.isArray) || [];
180
+ }
73
181
  ```
74
182
 
75
- ## Additional Build Nudge
183
+ ## Environment Variable Pattern
184
+
185
+ If the app should not hardcode the site URL or list ID, load the environment-variables skill too.
186
+
187
+ Rules:
188
+
189
+ - Ask for the exact existing schema names.
190
+ - Read values through `getEnvironmentVariable(...)` from `./codeapp.js`.
191
+ - Update `power.config.json` with the Dataverse environment-variable tables only when the app actually uses them.
192
+ - If a Data Source environment variable stores JSON, parse it before extracting the site URL or list ID.
193
+
194
+ ## Error Handling
195
+
196
+ The wrapper already converts many connector failures into readable errors such as `SharePoint GetItems failed: ...`, so app code should display those messages rather than swallowing them.
197
+
198
+ Keep separate loading and submit flags in UI state so refresh, create, update, and delete actions do not overlap silently.
199
+
200
+ ## Debugging Checklist
201
+
202
+ - If the failure happens before any connector call, verify `initSharePointClient()` returns `getClient(dataSourcesInfo)` and the wrapper was not replaced with a stub.
203
+ - If SharePoint calls suddenly return 404 after switching wrapper style, fall back to the OG siteUrl-based contract instead of a generated dataset or OData-style surface.
204
+ - If you see `Provide a SharePoint listId or listName.`, the app never supplied startup list configuration.
205
+ - If you see `SharePoint item payload must be an object.`, the app passed a string, `FormData`, or another invalid payload.
206
+ - If you see `SharePoint site URL is required.`, the config source is empty or malformed.
207
+ - If list resolution fails, confirm the site URL and list ID belong to the same site.
208
+ - If the user only knows a list name, let the wrapper perform `listTables(...)` lookup instead of building lookup logic in the page.
209
+ - Do not manually call `encodeURIComponent(siteUrl)` before passing the site URL to the wrapper.
210
+ - Use `enableDebugger()` during app development so `_dbgWrap(...)` traces are available.
211
+ - Use `sendHttpRequest(...)` only as an escape hatch when there is no dedicated SharePoint helper.
212
+
213
+ ## Summary Rules
76
214
 
77
- When a SharePoint build introduces or depends on specific lists and columns, create an `agent/listSchema.json` artifact so the user can recreate the list structure correctly.
215
+ - Ask for site URL and list ID first.
216
+ - Treat list name as a fallback lookup hint, not the primary identifier.
217
+ - Update `power.config.json` by merging in `connectionReferences.sharepointonline`, not by overwriting working connection metadata.
218
+ - Resolve the list once at startup and keep the resolved access object in app state.
219
+ - Prefer by-list helpers in app code and keep list lookup inside `sharepoint.js`.
220
+ - Show connector error messages directly in the UI.
@@ -21,6 +21,7 @@ When interactive user input is available, ask through the interactive question f
21
21
  Only stop and wait for a later run when interactive user input is not available.
22
22
  3. If the user says to decide yourself, choose a bold and distinctive visual direction. Do **not** ask again.
23
23
  4. Record the chosen style and colour direction in `agent/decision-log.md` under **Custom Requirements**.
24
+ 5. Use the frontend-design skill when creating the UI, including for any mockups.
24
25
 
25
26
  **Important:** The agent must have colour and style direction before building. Never start building a creative UI without it — either the user provides it or you decide it.
26
27