apexrest 1.3.0-beta.1 → 1.3.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 (182) hide show
  1. package/README.md +90 -140
  2. package/dist/codex-compat/.claude-plugin/marketplace.json +20 -0
  3. package/dist/codex-compat/plugins/apexrest-apex/.claude-plugin/plugin.json +28 -0
  4. package/dist/codex-compat/plugins/apexrest-apex/.codex-plugin/plugin.json +7 -7
  5. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/generator.json +1 -1
  6. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/manifest.json +6 -6
  7. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/packages/analytics/status-summary/1.0.0/block.yaml +1 -1
  8. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/packages/crud/report-dialog/1.0.0/block.yaml +1 -1
  9. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/packages/read/detail/1.0.0/block.yaml +1 -1
  10. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/packages/read/filtered-list/1.0.0/block.yaml +1 -1
  11. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/packages/read/history/1.0.0/block.yaml +1 -1
  12. package/dist/codex-compat/plugins/apexrest-apex/resources/blocks/packages/read/master-detail/1.0.0/block.yaml +1 -1
  13. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/composer-blueprint.schema.json +5 -4
  14. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/composer-contract.schema.json +2 -2
  15. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/composer-entity.schema.json +2 -1
  16. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/composer-field.schema.json +2 -1
  17. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/composer-instance.schema.json +1 -1
  18. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/composer-operation.schema.json +1 -1
  19. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/composer-plan.schema.json +5 -4
  20. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/deploy-plan.schema.json +18 -24
  21. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/operations.schema.json +352 -569
  22. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/policy.schema.json +21 -0
  23. package/dist/codex-compat/plugins/apexrest-apex/resources/schemas/project.schema.json +4 -7
  24. package/dist/codex-compat/plugins/apexrest-apex/resources/templates/blank-app/README.md +0 -2
  25. package/dist/codex-compat/plugins/apexrest-apex/resources/templates/customer-crm/README.md +1 -3
  26. package/dist/codex-compat/plugins/apexrest-apex/resources/templates/existing-app/README.md +0 -2
  27. package/dist/codex-compat/plugins/apexrest-apex/runtime/apexrest.mjs +70 -44
  28. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-5PCC7GZM.mjs +4090 -0
  29. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-BVPAS3TD.mjs +18 -0
  30. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-CVMECW6D.mjs +65 -0
  31. package/dist/codex-compat/plugins/apexrest-apex/runtime/{chunk-EBBEN4AV.mjs → chunk-JYN3YHP3.mjs} +4220 -10639
  32. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-KGTE7Q5Y.mjs +23 -0
  33. package/dist/{runtime/chunk-33GE2NWZ.mjs → codex-compat/plugins/apexrest-apex/runtime/chunk-KKRFM7Q7.mjs} +21 -4
  34. package/dist/codex-compat/plugins/apexrest-apex/runtime/{chunk-2VBZESVC.mjs → chunk-MNU54A7W.mjs} +7 -1
  35. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-N4C2SKCN.mjs +6912 -0
  36. package/dist/{runtime/chunk-KQ5IDT7Z.mjs → codex-compat/plugins/apexrest-apex/runtime/chunk-P3CVQAZW.mjs} +822 -102
  37. package/dist/{runtime/chunk-BAHECVGO.mjs → codex-compat/plugins/apexrest-apex/runtime/chunk-QKYF6N6U.mjs} +192 -114
  38. package/dist/codex-compat/plugins/apexrest-apex/runtime/{chunk-G3KR57BY.mjs → chunk-RBJJNQ5O.mjs} +7 -7
  39. package/dist/codex-compat/plugins/apexrest-apex/runtime/{chunk-YPLIIQ4Y.mjs → chunk-TMSMKVRP.mjs} +486 -352
  40. package/dist/codex-compat/plugins/apexrest-apex/runtime/{chunk-2Z3BZF66.mjs → chunk-WPS3CSQJ.mjs} +124 -11
  41. package/dist/codex-compat/plugins/apexrest-apex/runtime/mcp.mjs +5 -10
  42. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-apexlang/SKILL.md +22 -25
  43. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-apexlang/agents/openai.yaml +3 -3
  44. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-apexlang/references/component-routes.md +1 -5
  45. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-pattern-catalog/SKILL.md +4 -4
  46. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-pattern-catalog/agents/openai.yaml +1 -1
  47. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-pattern-catalog/references/capture-and-curation.md +2 -2
  48. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-safety/SKILL.md +18 -0
  49. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-safety/agents/openai.yaml +4 -0
  50. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-setup/SKILL.md +20 -10
  51. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-setup/agents/openai.yaml +3 -3
  52. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-work/SKILL.md +11 -8
  53. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-work/agents/openai.yaml +3 -3
  54. package/dist/resources/blocks/generator.json +1 -1
  55. package/dist/resources/blocks/manifest.json +6 -6
  56. package/dist/resources/blocks/packages/analytics/status-summary/1.0.0/block.yaml +1 -1
  57. package/dist/resources/blocks/packages/crud/report-dialog/1.0.0/block.yaml +1 -1
  58. package/dist/resources/blocks/packages/read/detail/1.0.0/block.yaml +1 -1
  59. package/dist/resources/blocks/packages/read/filtered-list/1.0.0/block.yaml +1 -1
  60. package/dist/resources/blocks/packages/read/history/1.0.0/block.yaml +1 -1
  61. package/dist/resources/blocks/packages/read/master-detail/1.0.0/block.yaml +1 -1
  62. package/dist/resources/schemas/composer-blueprint.schema.json +5 -4
  63. package/dist/resources/schemas/composer-contract.schema.json +2 -2
  64. package/dist/resources/schemas/composer-entity.schema.json +2 -1
  65. package/dist/resources/schemas/composer-field.schema.json +2 -1
  66. package/dist/resources/schemas/composer-instance.schema.json +1 -1
  67. package/dist/resources/schemas/composer-operation.schema.json +1 -1
  68. package/dist/resources/schemas/composer-plan.schema.json +5 -4
  69. package/dist/resources/schemas/deploy-plan.schema.json +18 -24
  70. package/dist/resources/schemas/operations.schema.json +352 -569
  71. package/dist/resources/schemas/policy.schema.json +21 -0
  72. package/dist/resources/schemas/project.schema.json +4 -7
  73. package/dist/resources/templates/blank-app/README.md +0 -2
  74. package/dist/resources/templates/customer-crm/README.md +1 -3
  75. package/dist/resources/templates/existing-app/README.md +0 -2
  76. package/dist/runtime/apexrest.mjs +70 -44
  77. package/dist/runtime/chunk-5PCC7GZM.mjs +4090 -0
  78. package/dist/runtime/chunk-BVPAS3TD.mjs +18 -0
  79. package/dist/runtime/chunk-CVMECW6D.mjs +65 -0
  80. package/dist/runtime/{chunk-EBBEN4AV.mjs → chunk-JYN3YHP3.mjs} +4220 -10639
  81. package/dist/runtime/chunk-KGTE7Q5Y.mjs +23 -0
  82. package/dist/{codex-compat/plugins/apexrest-apex/runtime/chunk-33GE2NWZ.mjs → runtime/chunk-KKRFM7Q7.mjs} +21 -4
  83. package/dist/runtime/{chunk-2VBZESVC.mjs → chunk-MNU54A7W.mjs} +7 -1
  84. package/dist/runtime/chunk-N4C2SKCN.mjs +6912 -0
  85. package/dist/{codex-compat/plugins/apexrest-apex/runtime/chunk-KQ5IDT7Z.mjs → runtime/chunk-P3CVQAZW.mjs} +822 -102
  86. package/dist/{codex-compat/plugins/apexrest-apex/runtime/chunk-BAHECVGO.mjs → runtime/chunk-QKYF6N6U.mjs} +192 -114
  87. package/dist/runtime/{chunk-G3KR57BY.mjs → chunk-RBJJNQ5O.mjs} +7 -7
  88. package/dist/runtime/{chunk-YPLIIQ4Y.mjs → chunk-TMSMKVRP.mjs} +486 -352
  89. package/dist/runtime/{chunk-2Z3BZF66.mjs → chunk-WPS3CSQJ.mjs} +124 -11
  90. package/dist/runtime/mcp.mjs +5 -10
  91. package/package.json +6 -6
  92. package/README.uk.md +0 -212
  93. package/dist/codex-compat/plugins/apexrest-apex/resources/panel/index.html +0 -68
  94. package/dist/codex-compat/plugins/apexrest-apex/resources/panel/panel.css +0 -627
  95. package/dist/codex-compat/plugins/apexrest-apex/resources/panel/panel.js +0 -861
  96. package/dist/codex-compat/plugins/apexrest-apex/resources/templates/blank-app/README.uk.md +0 -5
  97. package/dist/codex-compat/plugins/apexrest-apex/resources/templates/customer-crm/README.uk.md +0 -7
  98. package/dist/codex-compat/plugins/apexrest-apex/resources/templates/database-control/install.sql +0 -17
  99. package/dist/codex-compat/plugins/apexrest-apex/resources/templates/existing-app/README.uk.md +0 -9
  100. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__@playwright__test__LICENSE +0 -202
  101. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__@playwright__test__NOTICE +0 -5
  102. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__@types__node__LICENSE +0 -21
  103. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__@types__yauzl__LICENSE +0 -21
  104. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__@typescript__typescript-darwin-arm64__LICENSE +0 -55
  105. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__@typescript__typescript-darwin-arm64__NOTICE.txt +0 -436
  106. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__esbuild__LICENSE.md +0 -21
  107. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__fflate__LICENSE +0 -21
  108. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__marked__LICENSE +0 -44
  109. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__playwright-core__LICENSE +0 -202
  110. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__playwright-core__NOTICE +0 -5
  111. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__playwright__LICENSE +0 -202
  112. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__playwright__NOTICE +0 -5
  113. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__prettier__LICENSE +0 -7
  114. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__typescript__LICENSE +0 -55
  115. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__typescript__NOTICE.txt +0 -436
  116. package/dist/codex-compat/plugins/apexrest-apex/resources/third-party/node_modules__undici-types__LICENSE +0 -21
  117. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-2BBNJVKW.mjs +0 -1996
  118. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-5JI3XEAK.mjs +0 -14
  119. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-CYPFCUNE.mjs +0 -150
  120. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-ESDVN7DS.mjs +0 -14
  121. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-FTTPESNK.mjs +0 -203
  122. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-HKJVCGQQ.mjs +0 -1302
  123. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-RWGJITHZ.mjs +0 -992
  124. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-TLYYCRQA.mjs +0 -329
  125. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-WXP75UUP.mjs +0 -18
  126. package/dist/codex-compat/plugins/apexrest-apex/runtime/chunk-YQHHPRJH.mjs +0 -14
  127. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-compose/SKILL.md +0 -18
  128. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-compose/agents/openai.yaml +0 -4
  129. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-compose/references/workflow.md +0 -15
  130. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-database/SKILL.md +0 -9
  131. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-database/agents/openai.yaml +0 -4
  132. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-debug/SKILL.md +0 -9
  133. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-debug/agents/openai.yaml +0 -4
  134. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-deploy/SKILL.md +0 -21
  135. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-deploy/agents/openai.yaml +0 -4
  136. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-install-dependencies/SKILL.md +0 -38
  137. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-install-dependencies/agents/openai.yaml +0 -4
  138. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-menu/SKILL.md +0 -30
  139. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-menu/agents/openai.yaml +0 -4
  140. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-menu/references/cli-catalog.md +0 -30
  141. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-panel/SKILL.md +0 -14
  142. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-panel/agents/openai.yaml +0 -4
  143. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-project/SKILL.md +0 -11
  144. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-project/agents/openai.yaml +0 -4
  145. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-review/SKILL.md +0 -11
  146. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-review/agents/openai.yaml +0 -4
  147. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-test/SKILL.md +0 -29
  148. package/dist/codex-compat/plugins/apexrest-apex/skills/apexrest-test/agents/openai.yaml +0 -4
  149. package/dist/resources/panel/index.html +0 -68
  150. package/dist/resources/panel/panel.css +0 -627
  151. package/dist/resources/panel/panel.js +0 -861
  152. package/dist/resources/templates/blank-app/README.uk.md +0 -5
  153. package/dist/resources/templates/customer-crm/README.uk.md +0 -7
  154. package/dist/resources/templates/database-control/install.sql +0 -17
  155. package/dist/resources/templates/existing-app/README.uk.md +0 -9
  156. package/dist/resources/third-party/node_modules__@playwright__test__LICENSE +0 -202
  157. package/dist/resources/third-party/node_modules__@playwright__test__NOTICE +0 -5
  158. package/dist/resources/third-party/node_modules__@types__node__LICENSE +0 -21
  159. package/dist/resources/third-party/node_modules__@types__yauzl__LICENSE +0 -21
  160. package/dist/resources/third-party/node_modules__@typescript__typescript-darwin-arm64__LICENSE +0 -55
  161. package/dist/resources/third-party/node_modules__@typescript__typescript-darwin-arm64__NOTICE.txt +0 -436
  162. package/dist/resources/third-party/node_modules__esbuild__LICENSE.md +0 -21
  163. package/dist/resources/third-party/node_modules__fflate__LICENSE +0 -21
  164. package/dist/resources/third-party/node_modules__marked__LICENSE +0 -44
  165. package/dist/resources/third-party/node_modules__playwright-core__LICENSE +0 -202
  166. package/dist/resources/third-party/node_modules__playwright-core__NOTICE +0 -5
  167. package/dist/resources/third-party/node_modules__playwright__LICENSE +0 -202
  168. package/dist/resources/third-party/node_modules__playwright__NOTICE +0 -5
  169. package/dist/resources/third-party/node_modules__prettier__LICENSE +0 -7
  170. package/dist/resources/third-party/node_modules__typescript__LICENSE +0 -55
  171. package/dist/resources/third-party/node_modules__typescript__NOTICE.txt +0 -436
  172. package/dist/resources/third-party/node_modules__undici-types__LICENSE +0 -21
  173. package/dist/runtime/chunk-2BBNJVKW.mjs +0 -1996
  174. package/dist/runtime/chunk-5JI3XEAK.mjs +0 -14
  175. package/dist/runtime/chunk-CYPFCUNE.mjs +0 -150
  176. package/dist/runtime/chunk-ESDVN7DS.mjs +0 -14
  177. package/dist/runtime/chunk-FTTPESNK.mjs +0 -203
  178. package/dist/runtime/chunk-HKJVCGQQ.mjs +0 -1302
  179. package/dist/runtime/chunk-RWGJITHZ.mjs +0 -992
  180. package/dist/runtime/chunk-TLYYCRQA.mjs +0 -329
  181. package/dist/runtime/chunk-WXP75UUP.mjs +0 -18
  182. package/dist/runtime/chunk-YQHHPRJH.mjs +0 -14
@@ -1,861 +0,0 @@
1
- (() => {
2
- // plugins/apexrest-apex/assets/apexrest-logo.svg
3
- var apexrest_logo_default = `data:image/svg+xml,<?xml version='1.0' encoding='utf-8'?>%0A<svg xmlns="http://www.w3.org/2000/svg" version="1.1" x="0px" y="0px" viewBox="100 66 98 98" xml:space="preserve" width="98" height="98" role="img" aria-labelledby="logo-title">%0A <title id="logo-title">APEXREST pencil and ruler symbol</title>%0A <style type="text/css">%0A%09.st0{fill:%2331BEF9;}%0A%09.st1{fill:%23FFD541;}%0A%09.st2{fill:%23FF4141;}%0A%09.st3{fill:%231E1E1E;}%0A</style>%0A <g id="\u0421\u043B\u043E\u0439_2">%0A <polygon class="st0" points="133,149 177,106 160,89 116,132 " />%0A </g>%0A <g id="\u0421\u043B\u043E\u0439_3">%0A <polygon class="st1" points="128,114 147,95 128,76 126,75 123,76 108,91 107,93 110,97 127,114 " />%0A <polygon class="st1" points="151,137 170,118 189,137 190,140 189,142 186,146 173,157 170,157 " />%0A </g>%0A <g id="\u0421\u043B\u043E\u0439_4">%0A <path class="st2" d="M166,83l16,16l4-3l2-5v-4c0,0-1-2-1-3s-3-4-3-4l-5-3h-3h-3l-3,2l-2,2L166,83L166,83z" />%0A </g>%0A <g id="\u0421\u043B\u043E\u0439_1">%0A <g>%0A <path class="st3" d="M126.7,115.5l1.7-1.7l-2.2-2.2l4.3-4.3c0.5-0.5,0.4-1.3-0.1-1.7c-0.5-0.4-1.2-0.4-1.7,0l-4.3,4.3l-4.1-4.1 l4.3-4.3c0.5-0.5,0.4-1.3-0.1-1.7c-0.5-0.4-1.2-0.4-1.7,0l-4.3,4.3l-4.1-4.1l9.4-9.5c0.5-0.5,0.4-1.3-0.1-1.7 c-0.5-0.4-1.2-0.4-1.7,0l-9.5,9.5l-3.6-3.6c-0.8-0.8-0.8-2,0-2.8L123.9,77c0.8-0.8,2-0.8,2.8,0L146,96.2l1.7-1.7l-19.2-19.2 c-1.7-1.7-4.6-1.7-6.3,0L107.5,90c-1.7,1.7-1.7,4.6,0,6.3L126.7,115.5z" />%0A <path class="st3" d="M182.7,100.8l3-3c5-5.1,4.9-13.3-0.2-18.3c-5-5-13.1-5-18.2,0l-51.9,51.9c-0.1,0.1-0.2,0.2-0.2,0.4v0.1 l-7.2,23.8c-0.2,0.6,0.2,1.3,0.8,1.5c0.2,0.1,0.5,0.1,0.7,0l23.8-7.2h0.1c0.1-0.1,0.2-0.1,0.4-0.2L182.7,100.8L182.7,100.8z M159.3,91l6.6,6.6l-41.3,41.3l-6.6-6.6L159.3,91z M110.9,154.2l1-3.5c1.1,0.5,2,1.3,2.5,2.4L110.9,154.2z M116.9,152.4 c-0.8-1.8-2.4-3.2-4.2-4l4.2-13.9l13.7,13.7L116.9,152.4z M132.9,147.1l-6.6-6.6l41.3-41.3l6.6,6.6L132.9,147.1z M175.9,104.1 l-7.4-7.4l-7.4-7.4l4.2-4.2l14.9,14.9L175.9,104.1z M167,83.3l2.1-2.1c4.3-4,10.9-3.7,14.9,0.6c3.7,4,3.7,10.3,0,14.3l-2.1,2.1 L167,83.3z" />%0A <path class="st3" d="M189.9,136.7l-19.2-19.2l-1.7,1.7l19.2,19.2c0.8,0.8,0.8,2,0,2.8l-14.7,14.7c-0.8,0.8-2.1,0.8-2.8,0l-3.6-3.6 l9.5-9.5c0.5-0.4,0.6-1.2,0.2-1.7c-0.4-0.5-1.2-0.6-1.7-0.2c-0.1,0.1-0.1,0.1-0.2,0.2l-9.5,9.5l-4.1-4.1l4.3-4.3 c0.5-0.5,0.5-1.2,0.1-1.7c-0.5-0.5-1.2-0.5-1.7-0.1c0,0,0,0-0.1,0.1l-4.3,4.3l-4.1-4.1l4.3-4.3c0.5-0.5,0.4-1.3-0.1-1.7 c-0.5-0.4-1.2-0.4-1.7,0l-4.3,4.3l-2.2-2.2l-1.8,1.7l19.2,19.2c1.7,1.7,4.6,1.7,6.3,0l14.7-14.7 C191.6,141.3,191.6,138.4,189.9,136.7C189.9,136.7,189.9,136.7,189.9,136.7z" />%0A </g>%0A </g>%0A</svg>%0A`;
4
-
5
- // packages/panel/src/composer-jobs.ts
6
- var ReviewRequests = class {
7
- revision = 0;
8
- invalidate() {
9
- this.revision++;
10
- }
11
- async run(read) {
12
- const revision = ++this.revision;
13
- const result = await read();
14
- return revision === this.revision ? result : void 0;
15
- }
16
- };
17
- var CompositionJobs = class {
18
- constructor(read, observed, changed, failed, wait = () => new Promise((resolve) => setTimeout(resolve, 1500))) {
19
- this.read = read;
20
- this.observed = observed;
21
- this.changed = changed;
22
- this.failed = failed;
23
- this.wait = wait;
24
- }
25
- read;
26
- observed;
27
- changed;
28
- failed;
29
- wait;
30
- running = false;
31
- pending;
32
- revision = 0;
33
- invalidate() {
34
- this.revision++;
35
- }
36
- async run(start) {
37
- if (this.running) return;
38
- this.running = true;
39
- this.changed();
40
- try {
41
- if (!this.pending) {
42
- const revision = this.revision;
43
- this.pending = { id: await start(), revision };
44
- this.changed();
45
- }
46
- const job = this.pending;
47
- let failures = 0;
48
- for (; ; ) {
49
- let response;
50
- try {
51
- response = await this.read(job.id);
52
- failures = 0;
53
- } catch (error) {
54
- const paused = ++failures >= 3;
55
- this.failed(error, paused);
56
- if (paused) return;
57
- await this.wait();
58
- continue;
59
- }
60
- this.observed(response);
61
- if (!["queued", "running", "cancelling"].includes(response.job.status)) {
62
- this.pending = void 0;
63
- return { response, current: job.revision === this.revision };
64
- }
65
- await this.wait();
66
- }
67
- } finally {
68
- this.running = false;
69
- this.changed();
70
- }
71
- }
72
- };
73
-
74
- // packages/panel/src/panel.ts
75
- var $ = (id) => document.getElementById(id);
76
- var input = (id) => $(id);
77
- var node = (tag, cls = "", text = "") => {
78
- const element = document.createElement(tag);
79
- element.className = cls;
80
- element.textContent = text;
81
- return element;
82
- };
83
- var human = (value) => value.replaceAll("_", " ").replaceAll("-", " ").replace(/\b\w/g, (c) => c.toUpperCase());
84
- var active = (status) => ["running", "queued", "cancelling"].includes(status);
85
- var badge = (value) => node(
86
- "span",
87
- "badge " + (["completed", "pass", "passed", "approve", "succeeded", "live"].includes(value) ? "good" : active(value) ? "running" : ["failed", "fail", "blocked", "verification_failed", "outcome_unknown", "unavailable"].includes(
88
- value
89
- ) ? "bad" : ["not_run", "cancelled"].includes(value) ? "warn" : ""),
90
- human(value)
91
- );
92
- var empty = (message) => node("div", "empty", message);
93
- var card = (title, content, subtitle) => {
94
- const box = node("div", "card"), heading = node("div", "section-heading"), label = node("div");
95
- label.append(node("h2", "", title));
96
- if (subtitle) label.append(node("p", "subtle", subtitle));
97
- heading.append(label);
98
- box.append(heading, content);
99
- return box;
100
- };
101
- var kv = (items) => {
102
- const dl = node("dl");
103
- for (const [key, value] of items) {
104
- const row = node("div", "kv");
105
- row.append(node("dt", "", key), node("dd", "", value == null ? "Not available" : String(value)));
106
- dl.append(row);
107
- }
108
- return dl;
109
- };
110
- var codeDetails = (title, value) => {
111
- const d = node("details");
112
- d.append(node("summary", "", title), node("pre", "", JSON.stringify(value, null, 2)));
113
- return d;
114
- };
115
- var notice = (message, error = false) => {
116
- const box = $("notice");
117
- box.hidden = !message;
118
- box.classList.toggle("error", error);
119
- box.textContent = message;
120
- };
121
- var launch = new URLSearchParams(location.hash.slice(1));
122
- var snapshot;
123
- var busy = false;
124
- var connected = false;
125
- var initialized = false;
126
- var sqlclDirty = false;
127
- var sqlclSignature = "";
128
- var preferencesDirty = false;
129
- var preferencesSignature = "";
130
- var bridgeProject;
131
- var bridgeReady = false;
132
- var requestId = 0;
133
- var currentView = "overview";
134
- var savedConnectionsState = "idle";
135
- var savedConnectionNames = [];
136
- var savedConnectionsError = "";
137
- var embedded = window.parent !== window;
138
- var token = launch.get("session") ?? "";
139
- var pending = /* @__PURE__ */ new Map();
140
- function bridge(method, params) {
141
- const id = ++requestId;
142
- return new Promise((resolve, reject) => {
143
- const timer = setTimeout(() => {
144
- pending.delete(id);
145
- reject(new Error("Codex did not answer the panel request."));
146
- }, 2e4);
147
- pending.set(id, { resolve, reject, timer });
148
- window.parent.postMessage({ jsonrpc: "2.0", id, method, params }, "*");
149
- });
150
- }
151
- window.addEventListener("message", (event) => {
152
- if (event.source !== window.parent || !embedded || !event.data || event.data.jsonrpc !== "2.0") return;
153
- const message = event.data;
154
- const waiter = pending.get(message.id);
155
- if (waiter) {
156
- clearTimeout(waiter.timer);
157
- pending.delete(message.id);
158
- if (message.error) waiter.reject(new Error(String(message.error.message)));
159
- else waiter.resolve(message.result);
160
- }
161
- if (message.method === "ui/notifications/tool-input" && typeof message.params?.arguments?.project === "string")
162
- bridgeProject = message.params.arguments.project;
163
- if (message.method === "ui/notifications/tool-result") {
164
- const result = message.params?._meta?.["apexrest/panelResult"] ?? message.params?.structuredContent;
165
- if (typeof result?.data?.project === "string") bridgeProject = result.data.project;
166
- if (bridgeProject) void refresh();
167
- }
168
- });
169
- async function api(action) {
170
- if (embedded) {
171
- if (action?.kind === "connection" && action.password)
172
- throw new Error("Enter the password in the local dashboard or use CLI --password-file.");
173
- if (!bridgeReady || !bridgeProject) throw new Error("Waiting for the Codex workspace context.");
174
- const response2 = await bridge("tools/call", {
175
- name: action ? "apexrest_panel_action" : "apexrest_panel_status",
176
- arguments: {
177
- project: bridgeProject,
178
- ...action ? { action } : {}
179
- }
180
- });
181
- const envelope = response2._meta?.["apexrest/panelResult"] ?? response2.structuredContent ?? JSON.parse(response2.content?.find((c) => c.type === "text")?.text ?? "{}");
182
- if (!envelope.ok) throw new Error(envelope.summary ?? "Codex rejected this panel action.");
183
- return envelope.data;
184
- }
185
- const response = await fetch(action ? "/api/action" : "/api/status", {
186
- method: action ? "POST" : "GET",
187
- headers: {
188
- Authorization: "Bearer " + token,
189
- ...action ? { "Content-Type": "application/json" } : {}
190
- },
191
- ...action ? { body: JSON.stringify(action) } : {},
192
- signal: AbortSignal.timeout(action?.kind === "saved-connections" ? 6e4 : 15e3)
193
- });
194
- const result = await response.json();
195
- if (!response.ok) throw new Error(result.summary ?? result.error ?? "The local panel request failed.");
196
- return result;
197
- }
198
- function renderSavedConnections(selected = input("connection-direct").value) {
199
- const select = $("connection-direct"), current = snapshot?.connections[input("connection-ref").value.trim()]?.name, selectedCurrent = !!current && selected === current, names = [
200
- .../* @__PURE__ */ new Set([...savedConnectionNames, ...current ? [current] : [], ...selected ? [selected] : []])
201
- ];
202
- const placeholder = node("option", "", "Choose a saved connection");
203
- placeholder.value = "";
204
- select.replaceChildren(
205
- placeholder,
206
- ...names.map((name) => {
207
- const retained = !savedConnectionNames.includes(name);
208
- const label = retained && savedConnectionsState === "loaded" ? `${name} \xB7 ${name === current ? "current mapping" : "previous selection"} (not in SQLcl list)` : retained && name === current ? `${name} \xB7 current mapping` : name;
209
- const option = node("option", "", label);
210
- option.value = name;
211
- return option;
212
- })
213
- );
214
- select.value = selected;
215
- select.disabled = savedConnectionsState === "loading";
216
- const status = $("saved-connections-status");
217
- status.dataset.state = savedConnectionsState;
218
- status.textContent = savedConnectionsState === "loading" ? "Loading saved connections from SQLcl\u2026" : savedConnectionsState === "error" ? "Could not load saved SQLcl connections. " + savedConnectionsError + " Use Retry to try again." : savedConnectionsState === "loaded" ? savedConnectionNames.length ? `${savedConnectionNames.length} saved SQLcl connection${savedConnectionNames.length === 1 ? "" : "s"} loaded.${selectedCurrent && !savedConnectionNames.includes(current) ? " The current mapping is retained even though SQLcl did not list it." : ""}` : "No saved SQLcl connections found. Save a direct connection in SQLcl, then refresh." + (selectedCurrent ? " The current mapping is retained." : "") : snapshot && !snapshot.trusted ? "Trust this project before loading saved SQLcl connections." : "Saved connections load when you open Direct connection settings.";
219
- $("saved-connections-refresh").textContent = savedConnectionsState === "loading" ? "Loading\u2026" : savedConnectionsState === "error" ? "Retry" : savedConnectionsState === "idle" ? "Load saved connections" : "Refresh saved connections";
220
- controls();
221
- }
222
- async function loadSavedConnections(force = false) {
223
- if (!connected || !snapshot?.trusted || busy || savedConnectionsState === "loading" || !force && savedConnectionsState === "loaded")
224
- return;
225
- savedConnectionsState = "loading";
226
- savedConnectionsError = "";
227
- renderSavedConnections();
228
- try {
229
- const result = await api({ kind: "saved-connections" });
230
- if (result.source !== "sqlcl-store" || !Array.isArray(result.connections) || result.connections.some((connection) => typeof connection?.name !== "string" || !connection.name))
231
- throw new Error("SQLcl returned an invalid connection list.");
232
- savedConnectionNames = result.connections.map((connection) => connection.name);
233
- savedConnectionsState = "loaded";
234
- } catch (error) {
235
- savedConnectionsState = "error";
236
- savedConnectionsError = error instanceof Error ? error.message : String(error);
237
- }
238
- renderSavedConnections();
239
- }
240
- var selectedBlock = "";
241
- var blueprintReview;
242
- var composeJob = "";
243
- var reviewedPlan;
244
- var compositionJobs = new CompositionJobs(
245
- async (id) => await api({ kind: "compose-status", id }),
246
- (response) => {
247
- notice("");
248
- $("compose-review").textContent = JSON.stringify(response.job, null, 2);
249
- },
250
- controls,
251
- (error, paused) => {
252
- notice(
253
- (error instanceof Error ? error.message : String(error)) + (paused ? " Job outcome is unknown. Retry job status to continue observing the same operation." : " Retrying the existing job status."),
254
- true
255
- );
256
- }
257
- );
258
- var blueprintReviews = new ReviewRequests();
259
- function controls() {
260
- const canAct = connected && !!snapshot?.trusted && !busy;
261
- for (const id of ["validate", "run-tests", "plan", "open-browser"])
262
- $(id).disabled = !canAct || !snapshot?.configured;
263
- for (const form of ["catalog-search", "catalog-add", "sqlcl-form", "connection-form", "preferences-form"])
264
- $(form).querySelectorAll("button[type=submit]").forEach((button) => {
265
- button.disabled = !canAct;
266
- });
267
- $("compose-plan").disabled = !canAct || !snapshot?.configured || compositionJobs.running;
268
- $("compose-plan").textContent = compositionJobs.pending ? "Retry job status" : "Plan and compile offline";
269
- $("compose-materialize").disabled = !canAct || !reviewedPlan || compositionJobs.running || !!compositionJobs.pending;
270
- $("compose-cancel").disabled = !canAct || !compositionJobs.pending;
271
- $("blueprint-apply").disabled = !canAct || !blueprintReview;
272
- $("saved-connections-refresh").disabled = !canAct || savedConnectionsState === "loading";
273
- $("connection-save").disabled = !canAct || input("sqlcl-transport").value === "direct" && savedConnectionsState === "loading";
274
- }
275
- async function act(action) {
276
- if (busy || !connected) return;
277
- busy = true;
278
- controls();
279
- try {
280
- const result = await api(action);
281
- notice(
282
- action.kind === "browser" ? result.status === "host_action_required" ? "Open this application in the Codex in-app browser: " + result.url + ". Opening it does not verify the application." : "Verification browser opened. Inspect the affected behavior; opening it does not verify the application." : ["sqlcl", "connection", "preferences"].includes(action.kind) ? "Settings saved." : action.kind === "cancel-job" ? "Stop requested. Existing changes are not rolled back." : "Operation accepted. Follow its actual status below."
283
- );
284
- if (action.kind === "preferences") preferencesDirty = false;
285
- if (action.kind === "sqlcl") sqlclDirty = false;
286
- if (action.kind === "connection") input("connection-ords-password").value = "";
287
- await refresh();
288
- } catch (error) {
289
- notice(error instanceof Error ? error.message : String(error), true);
290
- } finally {
291
- busy = false;
292
- controls();
293
- }
294
- }
295
- var rendered = /* @__PURE__ */ new Map();
296
- function draw(id, data, render2) {
297
- const key = JSON.stringify(data);
298
- if (rendered.get(id) === key) return;
299
- if ($(id).contains(document.activeElement) && document.activeElement !== document.body) return;
300
- $(id).replaceChildren(...render2());
301
- rendered.set(id, key);
302
- }
303
- function operations(data) {
304
- const box = node("div", "table-wrap");
305
- if (!data.jobs.length) box.append(empty("No APEX operation jobs recorded for this project."));
306
- else {
307
- const table = node("table"), head = node("tr");
308
- ["Operation", "Status", "Result", ""].forEach((s) => head.append(node("th", "", s)));
309
- const thead = node("thead");
310
- thead.append(head);
311
- table.append(thead);
312
- const body = node("tbody");
313
- for (const job of data.jobs) {
314
- const row = node("tr"), state = node("td"), summary = node("td"), action = node("td");
315
- state.append(badge(job.status));
316
- summary.append(node("p", "", job.summary || "Awaiting a result"));
317
- if (job.diagnostics.length || job.artifacts.length)
318
- summary.append(
319
- codeDetails("Diagnostics & artifacts", { diagnostics: job.diagnostics, artifacts: job.artifacts })
320
- );
321
- if (active(job.status)) {
322
- const stop = node("button", "danger", "Stop");
323
- stop.disabled = !connected || busy || !data.trusted;
324
- stop.onclick = () => {
325
- void act({ kind: "cancel-job", id: job.id });
326
- };
327
- action.append(stop);
328
- }
329
- row.append(node("td", "", job.operation), state, summary, action);
330
- body.append(row);
331
- }
332
- table.append(body);
333
- box.append(table);
334
- }
335
- const output = [card("Operation jobs", box, "Compile, export, tests and deployment work")];
336
- const sync = node("div");
337
- for (const entry of data.sync) {
338
- const row = node("div", "journal-entry");
339
- row.append(badge(entry.status), node("p", "", entry.environment));
340
- if ("exportedAt" in entry) row.append(node("p", "subtle", "Initial export: " + entry.exportedAt));
341
- if ("lastSuccessfulImport" in entry && entry.lastSuccessfulImport)
342
- row.append(node("p", "subtle", "Latest successful import: " + entry.lastSuccessfulImport.at));
343
- if ("blockedReason" in entry && entry.blockedReason) row.append(node("p", "", entry.blockedReason));
344
- if ("dirty" in entry)
345
- row.append(node("p", "", entry.dirty ? "Local edits present" : "Local checkpoint matches"));
346
- sync.append(row);
347
- }
348
- output.push(card("Working-copy sync", sync, "Local status only; server freshness is not checked"));
349
- const deployments = node("div");
350
- if (!data.deployments.length) deployments.append(empty("No deployment runs recorded."));
351
- for (const deployment of data.deployments) {
352
- const row = node("div", "journal-entry");
353
- row.append(
354
- badge(deployment.status),
355
- node("p", "subtle", new Date(deployment.at).toLocaleString()),
356
- node("pre", "", deployment.details)
357
- );
358
- deployments.append(row);
359
- }
360
- output.push(
361
- card(
362
- "Deployment & import journal",
363
- deployments,
364
- "Actual durable runtime state; an unknown outcome remains unknown"
365
- )
366
- );
367
- return output;
368
- }
369
- function render(data) {
370
- const connectionsChanged = JSON.stringify(snapshot?.connections) !== JSON.stringify(data.connections);
371
- snapshot = data;
372
- connected = true;
373
- $("project-name").textContent = data.configuration?.application.alias ?? "Unconfigured workspace";
374
- $("project-path").textContent = data.project;
375
- $("version").textContent = data.version;
376
- $("connection").className = "badge good";
377
- $("connection").textContent = "Live";
378
- $("updated").textContent = "Updated " + new Date(data.updatedAt).toLocaleTimeString();
379
- $("connection-error").hidden = true;
380
- document.body.dataset.disconnected = "false";
381
- const nextPreferences = JSON.stringify(data.preferences);
382
- const nextSqlcl = JSON.stringify(data.sqlcl);
383
- if (!sqlclDirty && nextSqlcl !== sqlclSignature) {
384
- input("sqlcl-mode").value = data.sqlcl.mode;
385
- input("sqlcl-level").value = data.sqlcl.mcpRestrictLevel;
386
- input("sqlcl-transport").value = data.sqlcl.databaseTransport ?? "direct";
387
- sqlclControls();
388
- sqlclSignature = nextSqlcl;
389
- }
390
- if (!preferencesDirty && nextPreferences !== preferencesSignature) {
391
- input("default-browser-mode").value = data.preferences.browserMode;
392
- preferencesSignature = nextPreferences;
393
- }
394
- if (!initialized) {
395
- initialized = true;
396
- if (embedded) {
397
- input("connection-ords-password").disabled = true;
398
- $("connection-password-note").textContent = "Set the password in the local dashboard opened by apexrest panel open, or use CLI --password-file. Passwords are never sent through the embedded Codex panel.";
399
- }
400
- const environment = $("environment");
401
- for (const [name, env] of Object.entries(data.configuration?.environments ?? {})) {
402
- const option = node("option", "", name + " \xB7 " + env.kind);
403
- option.value = name;
404
- environment.append(option);
405
- }
406
- if (!data.configured)
407
- notice(
408
- "This folder has no apexrest.json. Initialize or open an APEXREST application project to run APEX operations."
409
- );
410
- else if (!data.trusted)
411
- notice(
412
- "This project is not trusted in APEXREST. The panel can display its state; actions require the existing project trust setup."
413
- );
414
- }
415
- draw(
416
- "connection-refs",
417
- [data.connections, data.configuration?.environments],
418
- () => Array.from(
419
- /* @__PURE__ */ new Set([
420
- ...Object.keys(data.connections),
421
- ...Object.values(data.configuration?.environments ?? {}).flatMap((env) => [
422
- env.readConnectionRef,
423
- env.deployConnectionRef
424
- ])
425
- ])
426
- ).map((name) => {
427
- const option = node("option");
428
- option.value = name;
429
- return option;
430
- })
431
- );
432
- draw(
433
- "metrics",
434
- [data.sqlcl, data.jobs, data.deployments, data.trusted],
435
- () => [
436
- ["APEX operations", String(data.jobs.filter((job) => active(job.status)).length), "Running or queued"],
437
- ["Recorded deployments", String(data.deployments.length), "Recent deployment journal entries"],
438
- ["Project access", data.trusted ? "Trusted" : "Read only", "Existing authorization gates apply"],
439
- [
440
- "Database connectivity",
441
- data.sqlcl.databaseTransport === "ords" ? "ORDS HTTP(S)" : "Direct Oracle",
442
- data.sqlcl.mode === "mcp" ? "SQLcl MCP \xB7 restriction " + data.sqlcl.mcpRestrictLevel : "SQLcl CLI"
443
- ]
444
- ].map(([label, value, sub]) => {
445
- const box = node("div", "metric");
446
- box.append(node("div", "subtle", label), node("div", "value", value), node("div", "subtle", sub));
447
- return box;
448
- })
449
- );
450
- draw("overview-live", [data.changes, data.configuration, data.trusted], () => {
451
- const columns = node("div", "two-columns"), changeBox = node("div");
452
- changeBox.append(
453
- data.changes.files.length ? node("pre", "", data.changes.files.join("\n")) : empty(
454
- data.changes.status === "available" ? "No uncommitted Git changes." : "Git status is unavailable for this folder."
455
- )
456
- );
457
- columns.append(
458
- card(
459
- "Project context",
460
- kv([
461
- ["Application", data.configuration?.application.alias],
462
- ["Source", data.configuration?.application.sourceDir],
463
- [
464
- "Environments",
465
- Object.keys(data.configuration?.environments ?? {}).join(", ") || "None configured"
466
- ],
467
- ["Required suites", data.configuration?.tests.requiredSuites.join(", ") || "None declared"],
468
- ["Trust", data.trusted ? "Trusted project" : "Not granted"]
469
- ])
470
- ),
471
- card("Working changes", changeBox)
472
- );
473
- return [
474
- card(
475
- "Current Codex session",
476
- node(
477
- "p",
478
- "subtle",
479
- "Describe changes and review results in your open Codex conversation. This panel runs APEX operations and manages project settings."
480
- )
481
- ),
482
- columns
483
- ];
484
- });
485
- draw("operations-live", [data.jobs, data.deployments, data.sync, busy], () => operations(data));
486
- draw(
487
- "settings-live",
488
- [data.preferences, data.configuration, data.connections, data.toolchain, data.permissions],
489
- () => {
490
- const box = node("div");
491
- box.append(
492
- card(
493
- "Project & target settings",
494
- kv([
495
- ["Project", data.project],
496
- ["Source directory", data.configuration?.application.sourceDir],
497
- ["Artifacts", data.configuration?.artifacts.directory],
498
- [
499
- "Artifact retention",
500
- data.configuration ? data.configuration.artifacts.retentionDays + " days" : null
501
- ],
502
- ["Required suites", data.configuration?.tests.requiredSuites.join(", ") || "None declared"],
503
- ["Automated browser", data.configuration?.tests.defaultBrowser],
504
- [
505
- "Verification browser",
506
- data.preferences.browserMode === "external" ? "External system browser" : "Codex in-app browser"
507
- ],
508
- ["Active deploy/test grants", data.permissions.activeGrants.length]
509
- ])
510
- )
511
- );
512
- for (const [name, env] of Object.entries(data.configuration?.environments ?? {}))
513
- box.append(
514
- card(
515
- name + " \xB7 " + human(env.kind),
516
- kv([
517
- ["Application ID", env.applicationId],
518
- ["Workspace", env.workspace],
519
- ["Parsing schema", env.parsingSchema],
520
- ["Database", env.databaseIdentity.dbUniqueName],
521
- ["Service", env.databaseIdentity.serviceName],
522
- ["Read connection", env.readConnectionRef],
523
- ["Deploy connection", env.deployConnectionRef],
524
- ["Control mode", env.deploymentControl ?? "local"],
525
- ["Application URL", env.baseUrl]
526
- ])
527
- )
528
- );
529
- box.append(
530
- card(
531
- "Configuration details",
532
- codeDetails("Project, toolchain and connection references", {
533
- configuration: data.configuration,
534
- toolchain: data.toolchain,
535
- connectionReferences: data.connections,
536
- authorization: data.permissions
537
- })
538
- )
539
- );
540
- return [box];
541
- }
542
- );
543
- if (connectionsChanged) renderSavedConnections();
544
- controls();
545
- if (currentView === "settings" && input("sqlcl-transport").value === "direct" && savedConnectionsState === "idle")
546
- void loadSavedConnections();
547
- }
548
- var refreshing = false;
549
- async function refresh() {
550
- if (refreshing) return;
551
- refreshing = true;
552
- try {
553
- render(await api());
554
- if (reviewedPlan && composeJob) {
555
- const assessed = await api({ kind: "compose-status", id: composeJob });
556
- if (!assessed.materializable) {
557
- reviewedPlan = void 0;
558
- $("compose-materialize").disabled = true;
559
- }
560
- }
561
- } catch (error) {
562
- connected = false;
563
- $("connection").textContent = "Disconnected";
564
- $("connection").className = "badge bad";
565
- $("connection-error").hidden = false;
566
- $("connection-error").textContent = (error instanceof Error ? error.message : String(error)) + (snapshot ? " Showing the last received state." : "");
567
- document.body.dataset.disconnected = "true";
568
- controls();
569
- } finally {
570
- refreshing = false;
571
- }
572
- }
573
- var views = {
574
- overview: ["Workspace overview", "Project settings and APEX operations for your current Codex session."],
575
- operations: ["APEX operations", "Compile, verify and follow deployment state."],
576
- catalog: ["Composer catalog", "Find blocks, review bindings and compile a local application plan."],
577
- settings: ["Workspace settings", "Inspect configuration, database connections and browser preferences."]
578
- };
579
- function view(name) {
580
- currentView = name;
581
- document.querySelectorAll("[data-page]").forEach((page) => {
582
- page.hidden = page.dataset.page !== name;
583
- });
584
- document.querySelectorAll("[data-view]").forEach((button) => {
585
- if (button.dataset.view === name) button.setAttribute("aria-current", "page");
586
- else button.removeAttribute("aria-current");
587
- });
588
- const titles = views[name];
589
- $("view-title").textContent = titles[0];
590
- $("view-subtitle").textContent = titles[1];
591
- if (name === "settings" && input("sqlcl-transport").value === "direct") void loadSavedConnections();
592
- }
593
- document.querySelectorAll("[data-view]").forEach((button) => {
594
- button.onclick = () => view(button.dataset.view);
595
- });
596
- $("refresh").onclick = () => {
597
- void refresh();
598
- };
599
- $("preferences-form").oninput = () => {
600
- preferencesDirty = true;
601
- };
602
- $("preferences-form").onsubmit = (event) => {
603
- event.preventDefault();
604
- void act({
605
- kind: "preferences",
606
- settings: {
607
- browserMode: input("default-browser-mode").value
608
- }
609
- });
610
- };
611
- $("sqlcl-form").onsubmit = (event) => {
612
- event.preventDefault();
613
- void act({
614
- kind: "sqlcl",
615
- settings: {
616
- schemaVersion: 1,
617
- mode: input("sqlcl-mode").value,
618
- mcpRestrictLevel: input("sqlcl-level").value,
619
- databaseTransport: input("sqlcl-transport").value
620
- }
621
- });
622
- };
623
- function sqlclControls() {
624
- const ords = input("sqlcl-transport").value === "ords";
625
- if (ords) input("sqlcl-mode").value = "cli";
626
- $("sqlcl-mode").querySelector("option[value=mcp]").disabled = ords;
627
- input("sqlcl-level").disabled = input("sqlcl-mode").value !== "mcp";
628
- $("sqlcl-transport-note").textContent = ords ? "Connect through ORDS over HTTP(S) when the Oracle listener is unavailable. Uses SQLcl CLI and the ORDS settings for each connection reference below." : "Connect through the Oracle listener using saved SQLcl connections.";
629
- for (const [id, enabled] of [
630
- ["connection-direct-group", !ords],
631
- ["connection-ords-group", ords]
632
- ]) {
633
- const group = $(id);
634
- group.hidden = !enabled;
635
- group.disabled = !enabled;
636
- }
637
- input("connection-ords-password").disabled = embedded;
638
- $("connection-mode-note").textContent = ords ? "Editing ORDS HTTP(S) settings for the selected connection reference." : "Editing the direct Oracle connection for the selected connection reference.";
639
- $("connection-save").textContent = ords ? "Save ORDS connection" : "Save direct connection";
640
- controls();
641
- }
642
- $("sqlcl-form").oninput = (event) => {
643
- sqlclDirty = true;
644
- sqlclControls();
645
- if (event.target.id === "sqlcl-transport" && input("sqlcl-transport").value === "direct" && currentView === "settings")
646
- void loadSavedConnections();
647
- };
648
- $("saved-connections-refresh").onclick = () => {
649
- void loadSavedConnections(true);
650
- };
651
- input("connection-direct").onchange = () => renderSavedConnections();
652
- input("connection-ref").onchange = () => {
653
- const connection = snapshot?.connections[input("connection-ref").value.trim()];
654
- renderSavedConnections(connection?.name ?? "");
655
- input("connection-ords-url").value = connection?.ords?.url ?? "";
656
- input("connection-ords-user").value = connection?.ords?.username ?? "";
657
- input("connection-ords-password").value = "";
658
- };
659
- $("connection-form").onsubmit = (event) => {
660
- event.preventDefault();
661
- const ords = input("sqlcl-transport").value === "ords", sqlclName = input("connection-direct").value, ordsUrl = input("connection-ords-url").value.trim(), ordsUsername = input("connection-ords-user").value.trim(), password = input("connection-ords-password").value;
662
- if (ords && embedded && password) {
663
- notice("Enter the password in the local dashboard or use CLI --password-file.", true);
664
- return;
665
- }
666
- if (!ords && !sqlclName) {
667
- notice("Choose a saved SQLcl connection for this reference.", true);
668
- return;
669
- }
670
- if (ords && (!ordsUrl || !ordsUsername)) {
671
- notice("Enter the ORDS schema URL and your database username.", true);
672
- return;
673
- }
674
- void act({
675
- kind: "connection",
676
- name: input("connection-ref").value.trim(),
677
- ...!ords ? { sqlclName } : { ordsUrl, ordsUsername, ...password ? { password } : {} }
678
- });
679
- };
680
- $("validate").onclick = () => {
681
- void act({ kind: "validate" });
682
- };
683
- $("open-browser").onclick = () => {
684
- const env = input("environment").value;
685
- if (!env) {
686
- notice("Choose an explicit environment before opening its application.", true);
687
- return;
688
- }
689
- void act({ kind: "browser", env });
690
- };
691
- $("plan").onclick = () => {
692
- const env = input("environment").value;
693
- if (!env) {
694
- notice("Choose an explicit environment before planning a deployment.", true);
695
- return;
696
- }
697
- void act({ kind: "plan", env });
698
- };
699
- $("run-tests").onclick = () => {
700
- const suite = input("suite").value, env = input("environment").value;
701
- if (suite !== "unit" && !env) {
702
- notice("Choose an explicit environment for this test suite.", true);
703
- return;
704
- }
705
- void act({ kind: "test", suite, ...env ? { env } : {} });
706
- };
707
- controls();
708
- var initialView = launch.get("view");
709
- if (initialView && views[initialView]) view(initialView);
710
- var mark = document.querySelector(".brand-mark");
711
- if (mark) {
712
- const icon = node("img");
713
- icon.src = apexrest_logo_default;
714
- icon.alt = "";
715
- icon.width = 38;
716
- icon.height = 38;
717
- mark.replaceChildren(icon);
718
- }
719
- if (embedded) {
720
- void bridge("ui/initialize", {
721
- protocolVersion: "2026-01-26",
722
- appInfo: { name: "apexrest-panel", version: "1.0.0" },
723
- appCapabilities: {}
724
- }).then(() => {
725
- bridgeReady = true;
726
- window.parent.postMessage({ jsonrpc: "2.0", method: "ui/notifications/initialized", params: {} }, "*");
727
- void refresh();
728
- }).catch((error) => notice(String(error), true));
729
- } else void refresh();
730
- function scheduleRefresh() {
731
- setTimeout(
732
- () => {
733
- if (!document.hidden) void refresh();
734
- scheduleRefresh();
735
- },
736
- snapshot?.jobs.some((job) => active(job.status)) ? 2e3 : 1e4
737
- );
738
- }
739
- scheduleRefresh();
740
- document.addEventListener("visibilitychange", () => {
741
- if (!document.hidden) void refresh();
742
- });
743
- function invalidateBlueprintReview() {
744
- blueprintReviews.invalidate();
745
- blueprintReview = void 0;
746
- controls();
747
- }
748
- async function catalogAction(action) {
749
- try {
750
- return await api(action);
751
- } catch (error) {
752
- notice(error instanceof Error ? error.message : String(error), true);
753
- throw error;
754
- }
755
- }
756
- $("catalog-search").onsubmit = (event) => {
757
- event.preventDefault();
758
- void (async () => {
759
- const result = await catalogAction({ kind: "catalog-search", query: input("catalog-query").value });
760
- $("catalog-hits").replaceChildren();
761
- for (const hit of result.results) {
762
- const b = node("button", "quiet", hit.title + " \xB7 " + hit.status);
763
- b.type = "button";
764
- b.onclick = () => {
765
- selectedBlock = hit.id;
766
- invalidateBlueprintReview();
767
- void catalogAction({ kind: "catalog-read", id: hit.id, offset: 0 }).then((data) => {
768
- $("catalog-detail").textContent = data.content;
769
- });
770
- };
771
- $("catalog-hits").append(b);
772
- }
773
- })();
774
- };
775
- $("catalog-add").onsubmit = (event) => {
776
- event.preventDefault();
777
- invalidateBlueprintReview();
778
- void (async () => {
779
- if (!selectedBlock) throw new Error("Select a block from the catalog.");
780
- const blueprint = input("compose-blueprint").value, instanceId = input("compose-instance").value, instance = {
781
- ...JSON.parse($("compose-parameters").value),
782
- use: selectedBlock
783
- };
784
- const reviewed = await blueprintReviews.run(async () => {
785
- const state = await catalogAction({ kind: "blueprint-read", blueprint });
786
- const action = {
787
- kind: "blueprint-add",
788
- blueprint,
789
- instanceId,
790
- instance,
791
- expectedDigest: state.digest,
792
- apply: false
793
- };
794
- const diff = await catalogAction(action);
795
- return { action, diff };
796
- });
797
- if (!reviewed) return;
798
- blueprintReview = { ...reviewed.action, apply: true };
799
- $("blueprint-diff").textContent = "BEFORE\n" + reviewed.diff.before + "\nAFTER\n" + reviewed.diff.after;
800
- controls();
801
- })().catch((error) => notice(String(error), true));
802
- };
803
- $("blueprint-apply").onclick = () => {
804
- if (blueprintReview)
805
- void catalogAction(blueprintReview).then(() => {
806
- blueprintReview = void 0;
807
- blueprintReviews.invalidate();
808
- reviewedPlan = void 0;
809
- compositionJobs.invalidate();
810
- $("blueprint-apply").disabled = true;
811
- $("compose-materialize").disabled = true;
812
- notice("Blueprint updated. Create and review a new plan.");
813
- });
814
- };
815
- async function startComposition(action) {
816
- if (compositionJobs.running) return;
817
- reviewedPlan = void 0;
818
- controls();
819
- try {
820
- const completed = await compositionJobs.run(async () => {
821
- composeJob = (await catalogAction(action)).jobId;
822
- return composeJob;
823
- });
824
- const result = completed?.response.job.result?.data;
825
- reviewedPlan = completed?.current && completed.response.materializable && result?.planDigest ? { plan: result.plan, planDigest: result.planDigest } : void 0;
826
- } catch (error) {
827
- notice(error instanceof Error ? error.message : String(error), true);
828
- } finally {
829
- controls();
830
- }
831
- }
832
- input("compose-blueprint").oninput = () => {
833
- invalidateBlueprintReview();
834
- reviewedPlan = void 0;
835
- compositionJobs.invalidate();
836
- controls();
837
- };
838
- input("compose-instance").oninput = invalidateBlueprintReview;
839
- $("compose-parameters").oninput = invalidateBlueprintReview;
840
- $("compose-plan").onclick = () => {
841
- void startComposition({
842
- kind: "compose-plan",
843
- blueprint: input("compose-blueprint").value,
844
- out: ".apexrest/composer/panel-plan.json",
845
- mode: "offline",
846
- validation: "compiler",
847
- action: "compose"
848
- });
849
- };
850
- $("compose-materialize").onclick = () => {
851
- if (reviewedPlan)
852
- void startComposition({
853
- kind: "compose-materialize",
854
- plan: reviewedPlan.plan,
855
- expectedDigest: reviewedPlan.planDigest
856
- });
857
- };
858
- $("compose-cancel").onclick = () => {
859
- if (composeJob) void catalogAction({ kind: "cancel-job", id: composeJob });
860
- };
861
- })();