shieldcortex 4.13.1 → 4.14.1

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 (233) hide show
  1. package/dashboard/.next/standalone/dashboard/.next/BUILD_ID +1 -1
  2. package/dashboard/.next/standalone/dashboard/.next/build-manifest.json +2 -2
  3. package/dashboard/.next/standalone/dashboard/.next/server/app/_global-error.html +2 -2
  4. package/dashboard/.next/standalone/dashboard/.next/server/app/_global-error.rsc +1 -1
  5. package/dashboard/.next/standalone/dashboard/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  6. package/dashboard/.next/standalone/dashboard/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  7. package/dashboard/.next/standalone/dashboard/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  8. package/dashboard/.next/standalone/dashboard/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  9. package/dashboard/.next/standalone/dashboard/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  10. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.html +1 -1
  11. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.rsc +1 -1
  12. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.segments/_full.segment.rsc +1 -1
  13. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.segments/_head.segment.rsc +1 -1
  14. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.segments/_index.segment.rsc +1 -1
  15. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
  16. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
  17. package/dashboard/.next/standalone/dashboard/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
  18. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.html +1 -1
  19. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.rsc +1 -1
  20. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.segments/!KGRhc2hib2FyZCk/admin/__PAGE__.segment.rsc +1 -1
  21. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.segments/!KGRhc2hib2FyZCk/admin.segment.rsc +1 -1
  22. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  23. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.segments/_full.segment.rsc +1 -1
  24. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.segments/_head.segment.rsc +1 -1
  25. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.segments/_index.segment.rsc +1 -1
  26. package/dashboard/.next/standalone/dashboard/.next/server/app/admin.segments/_tree.segment.rsc +1 -1
  27. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.html +1 -1
  28. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.rsc +1 -1
  29. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.segments/!KGRhc2hib2FyZCk/cloud/__PAGE__.segment.rsc +1 -1
  30. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.segments/!KGRhc2hib2FyZCk/cloud.segment.rsc +1 -1
  31. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  32. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.segments/_full.segment.rsc +1 -1
  33. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.segments/_head.segment.rsc +1 -1
  34. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.segments/_index.segment.rsc +1 -1
  35. package/dashboard/.next/standalone/dashboard/.next/server/app/cloud.segments/_tree.segment.rsc +1 -1
  36. package/dashboard/.next/standalone/dashboard/.next/server/app/index.html +1 -1
  37. package/dashboard/.next/standalone/dashboard/.next/server/app/index.rsc +1 -1
  38. package/dashboard/.next/standalone/dashboard/.next/server/app/index.segments/__PAGE__.segment.rsc +1 -1
  39. package/dashboard/.next/standalone/dashboard/.next/server/app/index.segments/_full.segment.rsc +1 -1
  40. package/dashboard/.next/standalone/dashboard/.next/server/app/index.segments/_head.segment.rsc +1 -1
  41. package/dashboard/.next/standalone/dashboard/.next/server/app/index.segments/_index.segment.rsc +1 -1
  42. package/dashboard/.next/standalone/dashboard/.next/server/app/index.segments/_tree.segment.rsc +1 -1
  43. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.html +1 -1
  44. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.rsc +1 -1
  45. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/!KGRhc2hib2FyZCk/memory/capture/__PAGE__.segment.rsc +1 -1
  46. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/!KGRhc2hib2FyZCk/memory/capture.segment.rsc +1 -1
  47. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/!KGRhc2hib2FyZCk/memory.segment.rsc +1 -1
  48. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  49. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/_full.segment.rsc +1 -1
  50. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/_head.segment.rsc +1 -1
  51. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/_index.segment.rsc +1 -1
  52. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/capture.segments/_tree.segment.rsc +1 -1
  53. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.html +1 -1
  54. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.rsc +1 -1
  55. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/!KGRhc2hib2FyZCk/memory/graph/__PAGE__.segment.rsc +1 -1
  56. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/!KGRhc2hib2FyZCk/memory/graph.segment.rsc +1 -1
  57. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/!KGRhc2hib2FyZCk/memory.segment.rsc +1 -1
  58. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  59. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/_full.segment.rsc +1 -1
  60. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/_head.segment.rsc +1 -1
  61. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/_index.segment.rsc +1 -1
  62. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/graph.segments/_tree.segment.rsc +1 -1
  63. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.html +1 -1
  64. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.rsc +1 -1
  65. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/!KGRhc2hib2FyZCk/memory/recall/__PAGE__.segment.rsc +1 -1
  66. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/!KGRhc2hib2FyZCk/memory/recall.segment.rsc +1 -1
  67. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/!KGRhc2hib2FyZCk/memory.segment.rsc +1 -1
  68. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  69. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/_full.segment.rsc +1 -1
  70. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/_head.segment.rsc +1 -1
  71. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/_index.segment.rsc +1 -1
  72. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/recall.segments/_tree.segment.rsc +1 -1
  73. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.html +1 -1
  74. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.rsc +1 -1
  75. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/!KGRhc2hib2FyZCk/memory/review/__PAGE__.segment.rsc +1 -1
  76. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/!KGRhc2hib2FyZCk/memory/review.segment.rsc +1 -1
  77. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/!KGRhc2hib2FyZCk/memory.segment.rsc +1 -1
  78. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  79. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/_full.segment.rsc +1 -1
  80. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/_head.segment.rsc +1 -1
  81. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/_index.segment.rsc +1 -1
  82. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/review.segments/_tree.segment.rsc +1 -1
  83. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.html +1 -1
  84. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.rsc +1 -1
  85. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/!KGRhc2hib2FyZCk/memory/timeline/__PAGE__.segment.rsc +1 -1
  86. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/!KGRhc2hib2FyZCk/memory/timeline.segment.rsc +1 -1
  87. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/!KGRhc2hib2FyZCk/memory.segment.rsc +1 -1
  88. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  89. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/_full.segment.rsc +1 -1
  90. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/_head.segment.rsc +1 -1
  91. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/_index.segment.rsc +1 -1
  92. package/dashboard/.next/standalone/dashboard/.next/server/app/memory/timeline.segments/_tree.segment.rsc +1 -1
  93. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.html +1 -1
  94. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.rsc +1 -1
  95. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.segments/!KGRhc2hib2FyZCk/memory/__PAGE__.segment.rsc +1 -1
  96. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.segments/!KGRhc2hib2FyZCk/memory.segment.rsc +1 -1
  97. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  98. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.segments/_full.segment.rsc +1 -1
  99. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.segments/_head.segment.rsc +1 -1
  100. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.segments/_index.segment.rsc +1 -1
  101. package/dashboard/.next/standalone/dashboard/.next/server/app/memory.segments/_tree.segment.rsc +1 -1
  102. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.html +1 -1
  103. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.rsc +1 -1
  104. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.segments/!KGRhc2hib2FyZCk/overview/__PAGE__.segment.rsc +1 -1
  105. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.segments/!KGRhc2hib2FyZCk/overview.segment.rsc +1 -1
  106. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  107. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.segments/_full.segment.rsc +1 -1
  108. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.segments/_head.segment.rsc +1 -1
  109. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.segments/_index.segment.rsc +1 -1
  110. package/dashboard/.next/standalone/dashboard/.next/server/app/overview.segments/_tree.segment.rsc +1 -1
  111. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.html +1 -1
  112. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.rsc +1 -1
  113. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/!KGRhc2hib2FyZCk/protection/audit/__PAGE__.segment.rsc +1 -1
  114. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/!KGRhc2hib2FyZCk/protection/audit.segment.rsc +1 -1
  115. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/!KGRhc2hib2FyZCk/protection.segment.rsc +1 -1
  116. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  117. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/_full.segment.rsc +1 -1
  118. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/_head.segment.rsc +1 -1
  119. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/_index.segment.rsc +1 -1
  120. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/audit.segments/_tree.segment.rsc +1 -1
  121. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.html +1 -1
  122. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.rsc +1 -1
  123. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/!KGRhc2hib2FyZCk/protection/intercepts/__PAGE__.segment.rsc +1 -1
  124. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/!KGRhc2hib2FyZCk/protection/intercepts.segment.rsc +1 -1
  125. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/!KGRhc2hib2FyZCk/protection.segment.rsc +1 -1
  126. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  127. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/_full.segment.rsc +1 -1
  128. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/_head.segment.rsc +1 -1
  129. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/_index.segment.rsc +1 -1
  130. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/intercepts.segments/_tree.segment.rsc +1 -1
  131. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.html +1 -1
  132. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.rsc +1 -1
  133. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/!KGRhc2hib2FyZCk/protection/iron-dome/__PAGE__.segment.rsc +1 -1
  134. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/!KGRhc2hib2FyZCk/protection/iron-dome.segment.rsc +1 -1
  135. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/!KGRhc2hib2FyZCk/protection.segment.rsc +1 -1
  136. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  137. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/_full.segment.rsc +1 -1
  138. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/_head.segment.rsc +1 -1
  139. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/_index.segment.rsc +1 -1
  140. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/iron-dome.segments/_tree.segment.rsc +1 -1
  141. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.html +1 -1
  142. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.rsc +1 -1
  143. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/!KGRhc2hib2FyZCk/protection/policies/__PAGE__.segment.rsc +1 -1
  144. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/!KGRhc2hib2FyZCk/protection/policies.segment.rsc +1 -1
  145. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/!KGRhc2hib2FyZCk/protection.segment.rsc +1 -1
  146. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  147. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/_full.segment.rsc +1 -1
  148. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/_head.segment.rsc +1 -1
  149. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/_index.segment.rsc +1 -1
  150. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/policies.segments/_tree.segment.rsc +1 -1
  151. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.html +1 -1
  152. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.rsc +1 -1
  153. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/!KGRhc2hib2FyZCk/protection/quarantine/__PAGE__.segment.rsc +1 -1
  154. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/!KGRhc2hib2FyZCk/protection/quarantine.segment.rsc +1 -1
  155. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/!KGRhc2hib2FyZCk/protection.segment.rsc +1 -1
  156. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  157. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/_full.segment.rsc +1 -1
  158. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/_head.segment.rsc +1 -1
  159. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/_index.segment.rsc +1 -1
  160. package/dashboard/.next/standalone/dashboard/.next/server/app/protection/quarantine.segments/_tree.segment.rsc +1 -1
  161. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.html +1 -1
  162. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.rsc +1 -1
  163. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.segments/!KGRhc2hib2FyZCk/protection/__PAGE__.segment.rsc +1 -1
  164. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.segments/!KGRhc2hib2FyZCk/protection.segment.rsc +1 -1
  165. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  166. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.segments/_full.segment.rsc +1 -1
  167. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.segments/_head.segment.rsc +1 -1
  168. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.segments/_index.segment.rsc +1 -1
  169. package/dashboard/.next/standalone/dashboard/.next/server/app/protection.segments/_tree.segment.rsc +1 -1
  170. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.html +1 -1
  171. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.rsc +1 -1
  172. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.segments/!KGRhc2hib2FyZCk/settings/__PAGE__.segment.rsc +1 -1
  173. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.segments/!KGRhc2hib2FyZCk/settings.segment.rsc +1 -1
  174. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  175. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.segments/_full.segment.rsc +1 -1
  176. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.segments/_head.segment.rsc +1 -1
  177. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.segments/_index.segment.rsc +1 -1
  178. package/dashboard/.next/standalone/dashboard/.next/server/app/settings.segments/_tree.segment.rsc +1 -1
  179. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.html +1 -1
  180. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.rsc +1 -1
  181. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/!KGRhc2hib2FyZCk/supply-chain/xray/__PAGE__.segment.rsc +1 -1
  182. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/!KGRhc2hib2FyZCk/supply-chain/xray.segment.rsc +1 -1
  183. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/!KGRhc2hib2FyZCk/supply-chain.segment.rsc +1 -1
  184. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  185. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/_full.segment.rsc +1 -1
  186. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/_head.segment.rsc +1 -1
  187. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/_index.segment.rsc +1 -1
  188. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain/xray.segments/_tree.segment.rsc +1 -1
  189. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.html +1 -1
  190. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.rsc +1 -1
  191. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.segments/!KGRhc2hib2FyZCk/supply-chain/__PAGE__.segment.rsc +1 -1
  192. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.segments/!KGRhc2hib2FyZCk/supply-chain.segment.rsc +1 -1
  193. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  194. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.segments/_full.segment.rsc +1 -1
  195. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.segments/_head.segment.rsc +1 -1
  196. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.segments/_index.segment.rsc +1 -1
  197. package/dashboard/.next/standalone/dashboard/.next/server/app/supply-chain.segments/_tree.segment.rsc +1 -1
  198. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.html +1 -1
  199. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.rsc +1 -1
  200. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.segments/!KGRhc2hib2FyZCk/xray/__PAGE__.segment.rsc +1 -1
  201. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.segments/!KGRhc2hib2FyZCk/xray.segment.rsc +1 -1
  202. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.segments/!KGRhc2hib2FyZCk.segment.rsc +1 -1
  203. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.segments/_full.segment.rsc +1 -1
  204. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.segments/_head.segment.rsc +1 -1
  205. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.segments/_index.segment.rsc +1 -1
  206. package/dashboard/.next/standalone/dashboard/.next/server/app/xray.segments/_tree.segment.rsc +1 -1
  207. package/dashboard/.next/standalone/dashboard/.next/server/pages/404.html +1 -1
  208. package/dashboard/.next/standalone/dashboard/.next/server/pages/500.html +2 -2
  209. package/dist/cli/doctor.d.ts +1 -0
  210. package/dist/cli/doctor.js +244 -8
  211. package/dist/cli/migrate-legacy.d.ts +30 -0
  212. package/dist/cli/migrate-legacy.js +199 -0
  213. package/dist/context/derive-project-key.d.ts +36 -0
  214. package/dist/context/derive-project-key.js +150 -0
  215. package/dist/context/project-context.d.ts +8 -5
  216. package/dist/context/project-context.js +16 -32
  217. package/dist/index.js +16 -1
  218. package/dist/setup/settings-hooks.d.ts +6 -0
  219. package/dist/setup/settings-hooks.js +14 -1
  220. package/dist/worker/brain-worker.d.ts +13 -5
  221. package/dist/worker/brain-worker.js +80 -40
  222. package/dist/worker/types.d.ts +19 -0
  223. package/dist/worker/types.js +7 -0
  224. package/package.json +1 -1
  225. package/plugins/openclaw/dist/openclaw.plugin.json +1 -1
  226. package/scripts/lib/auto-memory-config.mjs +11 -1
  227. package/scripts/lib/project-key.mjs +6 -0
  228. package/scripts/pre-compact-hook.mjs +2 -34
  229. package/scripts/session-end-hook.mjs +2 -24
  230. package/scripts/stop-hook.mjs +48 -43
  231. /package/dashboard/.next/standalone/dashboard/.next/static/{2JvJZkELhPQRzhTlgun1M → Pdjj9nsNg0WgiX_EeomqY}/_buildManifest.js +0 -0
  232. /package/dashboard/.next/standalone/dashboard/.next/static/{2JvJZkELhPQRzhTlgun1M → Pdjj9nsNg0WgiX_EeomqY}/_clientMiddlewareManifest.json +0 -0
  233. /package/dashboard/.next/standalone/dashboard/.next/static/{2JvJZkELhPQRzhTlgun1M → Pdjj9nsNg0WgiX_EeomqY}/_ssgManifest.js +0 -0
@@ -545,8 +545,12 @@ async function checkDiskUsage() {
545
545
  }
546
546
  }
547
547
  // ── Check 7: Lock file ───────────────────────────────────
548
- async function checkLockFile() {
549
- const scDir = getShieldCortexDir();
548
+ //
549
+ // A lock is stale only if its recorded PID is no longer running. Pure mtime age
550
+ // is unreliable: a long-running daemon (e.g. `shieldcortex dashboard` started
551
+ // at boot) holds the same lock for days, and flagging it stale tells the user
552
+ // to delete a file that is still in active use.
553
+ export async function checkLockFile(scDir = getShieldCortexDir()) {
550
554
  if (!fs.existsSync(scDir)) {
551
555
  return { label: 'Lock', status: 'pass', message: 'clean' };
552
556
  }
@@ -561,18 +565,45 @@ async function checkLockFile() {
561
565
  if (lockFiles.length === 0) {
562
566
  return { label: 'Lock', status: 'pass', message: 'clean' };
563
567
  }
564
- // Check if lock files are stale (older than 1 hour)
565
568
  const stale = [];
566
569
  const active = [];
567
- const oneHourAgo = Date.now() - 60 * 60 * 1000;
570
+ // Fallback only used when the lock file is unparseable or has no PID.
571
+ const oneDayAgo = Date.now() - 24 * 60 * 60 * 1000;
568
572
  for (const lockFile of lockFiles) {
569
573
  const lockPath = path.join(scDir, lockFile);
570
- const stat = fs.statSync(lockPath);
571
- if (stat.mtimeMs < oneHourAgo) {
572
- stale.push(lockFile);
574
+ let pid = null;
575
+ try {
576
+ const parsed = JSON.parse(fs.readFileSync(lockPath, 'utf-8'));
577
+ if (typeof parsed.pid === 'number' && Number.isFinite(parsed.pid)) {
578
+ pid = parsed.pid;
579
+ }
580
+ }
581
+ catch {
582
+ // Unparseable lock — fall through to mtime fallback below.
583
+ }
584
+ if (pid !== null) {
585
+ try {
586
+ process.kill(pid, 0);
587
+ active.push(lockFile);
588
+ }
589
+ catch (err) {
590
+ if (err.code === 'ESRCH') {
591
+ stale.push(lockFile);
592
+ }
593
+ else {
594
+ // EPERM = process exists, owned by another user. Treat as active.
595
+ active.push(lockFile);
596
+ }
597
+ }
573
598
  }
574
599
  else {
575
- active.push(lockFile);
600
+ const stat = fs.statSync(lockPath);
601
+ if (stat.mtimeMs < oneDayAgo) {
602
+ stale.push(lockFile);
603
+ }
604
+ else {
605
+ active.push(lockFile);
606
+ }
576
607
  }
577
608
  }
578
609
  if (stale.length > 0) {
@@ -626,6 +657,207 @@ async function checkOpenClawResidue() {
626
657
  return { label: 'OpenClaw residue', status: 'warn', message: `check failed — ${msg}` };
627
658
  }
628
659
  }
660
+ // ── Check 9: Auto-memory sampling rate (#44) ──────────────
661
+ /**
662
+ * Reports the resolved `autoMemory.stopHookSamplingTurns` and salience-bypass
663
+ * setting. Defaults dropped 10 → 5 (and salience bypass added) in v4.14.0;
664
+ * warn if a user pinned a sparser cadence likely to under-feed LTM.
665
+ *
666
+ * Reads the config file directly rather than importing the .mjs helper so
667
+ * doctor doesn't depend on path layout between dist/ and scripts/.
668
+ */
669
+ async function checkAutoMemorySampling() {
670
+ try {
671
+ const configPath = path.join(getShieldCortexDir(), 'config.json');
672
+ let raw = {};
673
+ if (fs.existsSync(configPath)) {
674
+ try {
675
+ raw = JSON.parse(fs.readFileSync(configPath, 'utf-8'));
676
+ }
677
+ catch {
678
+ /* fall through to defaults */
679
+ }
680
+ }
681
+ const overrides = raw.autoMemory ?? {};
682
+ const sampling = typeof overrides.stopHookSamplingTurns === 'number' &&
683
+ Number.isFinite(overrides.stopHookSamplingTurns) &&
684
+ overrides.stopHookSamplingTurns > 0
685
+ ? Math.floor(overrides.stopHookSamplingTurns)
686
+ : 5; // default in auto-memory-config.mjs as of v4.14.0
687
+ const bypassEnabled = typeof overrides.stopHookSalienceBypass === 'boolean' ? overrides.stopHookSalienceBypass : true;
688
+ const bypass = bypassEnabled ? 'on' : 'off';
689
+ if (sampling <= 5) {
690
+ return {
691
+ label: 'Auto-memory sampling',
692
+ status: 'pass',
693
+ message: `every ${sampling} turn(s), salience-bypass ${bypass}`,
694
+ };
695
+ }
696
+ return {
697
+ label: 'Auto-memory sampling',
698
+ status: 'warn',
699
+ message: `every ${sampling} turn(s), salience-bypass ${bypass} — sparser than recommended`,
700
+ fix: 'Edit ~/.shieldcortex/config.json autoMemory.stopHookSamplingTurns (≤ 5 recommended)',
701
+ };
702
+ }
703
+ catch (err) {
704
+ const msg = err instanceof Error ? err.message : String(err);
705
+ return { label: 'Auto-memory sampling', status: 'info', message: `check skipped — ${msg}` };
706
+ }
707
+ }
708
+ // ── Check 10: Brain-worker freshness (#45) ────────────────
709
+ /**
710
+ * The MCP server starts a lite-profile brain worker on connect (v4.14.0).
711
+ * Each light tick writes to ~/.shieldcortex/state/worker.json. If the
712
+ * timestamp is missing or older than 30 min, consolidation has likely
713
+ * stalled — STM won't graduate to LTM.
714
+ */
715
+ async function checkBrainWorker() {
716
+ if (process.env.SHIELDCORTEX_DISABLE_WORKER === '1') {
717
+ return {
718
+ label: 'Brain worker',
719
+ status: 'info',
720
+ message: 'disabled via SHIELDCORTEX_DISABLE_WORKER=1',
721
+ };
722
+ }
723
+ const statePath = path.join(getShieldCortexDir(), 'state', 'worker.json');
724
+ if (!fs.existsSync(statePath)) {
725
+ return {
726
+ label: 'Brain worker',
727
+ status: 'warn',
728
+ message: 'no worker.json — worker has not run yet',
729
+ fix: 'Start an MCP-bound session (Claude Code) or run `shieldcortex worker` to drive consolidation',
730
+ };
731
+ }
732
+ try {
733
+ const raw = JSON.parse(fs.readFileSync(statePath, 'utf-8'));
734
+ const last = raw.lastLightTick ? new Date(raw.lastLightTick) : null;
735
+ if (!last || Number.isNaN(last.getTime())) {
736
+ return {
737
+ label: 'Brain worker',
738
+ status: 'warn',
739
+ message: 'worker.json present but lastLightTick missing/invalid',
740
+ fix: 'Restart Claude Code to spawn a fresh MCP server',
741
+ };
742
+ }
743
+ const ageMs = Date.now() - last.getTime();
744
+ const ageMin = Math.round(ageMs / 60000);
745
+ if (ageMs > 30 * 60 * 1000) {
746
+ return {
747
+ label: 'Brain worker',
748
+ status: 'warn',
749
+ message: `last tick ${ageMin}m ago (profile=${raw.profile ?? '?'}, pid=${raw.pid ?? '?'})`,
750
+ fix: 'Restart Claude Code or run `shieldcortex worker` to resume consolidation',
751
+ };
752
+ }
753
+ return {
754
+ label: 'Brain worker',
755
+ status: 'pass',
756
+ message: `last tick ${ageMin}m ago (profile=${raw.profile ?? '?'}, pid=${raw.pid ?? '?'})`,
757
+ };
758
+ }
759
+ catch (err) {
760
+ const msg = err instanceof Error ? err.message : String(err);
761
+ return { label: 'Brain worker', status: 'warn', message: `check failed — ${msg}` };
762
+ }
763
+ }
764
+ // ── Check 11: Project-key consistency (#42) ───────────────
765
+ /**
766
+ * Detects rows tagged with both legacy basename keys and canonical
767
+ * owner-repo keys (the symptom of pre-v4.14.0 stop-hook writes). If any
768
+ * basename collides with a `<something>-<basename>` form already in the
769
+ * DB, point the user at `repair-project-keys`.
770
+ */
771
+ async function checkProjectKeyConsistency() {
772
+ const dbPath = getDbPath();
773
+ if (!fs.existsSync(dbPath)) {
774
+ return { label: 'Project keys', status: 'info', message: 'skipped (no DB yet)' };
775
+ }
776
+ try {
777
+ const Database = require('better-sqlite3');
778
+ const db = new Database(dbPath, { readonly: true });
779
+ try {
780
+ const rows = db
781
+ .prepare("SELECT DISTINCT project FROM memories WHERE project IS NOT NULL AND project != ''")
782
+ .all();
783
+ const keys = rows.map((r) => r.project);
784
+ const collisions = [];
785
+ for (const candidate of keys) {
786
+ // A candidate is "legacy-looking" if it has no hyphen (cwd basename).
787
+ if (candidate.includes('-'))
788
+ continue;
789
+ const suffix = `-${candidate}`;
790
+ const matched = keys.find((k) => k !== candidate && k.endsWith(suffix));
791
+ if (matched)
792
+ collisions.push({ legacy: candidate, canonical: matched });
793
+ }
794
+ if (collisions.length === 0) {
795
+ return { label: 'Project keys', status: 'pass', message: `${keys.length} distinct, no legacy/canonical collisions` };
796
+ }
797
+ const example = collisions.slice(0, 3).map((c) => `${c.legacy} ↔ ${c.canonical}`).join('; ');
798
+ const more = collisions.length > 3 ? ` (+${collisions.length - 3} more)` : '';
799
+ return {
800
+ label: 'Project keys',
801
+ status: 'warn',
802
+ message: `${collisions.length} legacy/canonical collision(s): ${example}${more}`,
803
+ fix: 'Run `shieldcortex memories repair-project-keys --scan-paths <root>` (dry-run by default)',
804
+ };
805
+ }
806
+ finally {
807
+ db.close();
808
+ }
809
+ }
810
+ catch (err) {
811
+ const msg = err instanceof Error ? err.message : String(err);
812
+ return { label: 'Project keys', status: 'warn', message: `check failed — ${msg}` };
813
+ }
814
+ }
815
+ // ── Check 12: Hook timeouts (#43) ─────────────────────────
816
+ /**
817
+ * Compares each ShieldCortex hook's timeout in ~/.claude/settings.json
818
+ * against the canonical values written by `shieldcortex setup`. Catches
819
+ * the v4.13.x silent-recall failure mode where users on a hand-edited
820
+ * settings.json still ran with `UserPromptSubmit.timeout: 2`.
821
+ */
822
+ async function checkHookTimeouts() {
823
+ const settingsPath = path.join(os.homedir(), '.claude', 'settings.json');
824
+ if (!fs.existsSync(settingsPath)) {
825
+ return { label: 'Hook timeouts', status: 'info', message: 'skipped (settings.json not found)' };
826
+ }
827
+ try {
828
+ const { CANONICAL_HOOK_TIMEOUTS } = await import('../setup/settings-hooks.js');
829
+ const settings = JSON.parse(fs.readFileSync(settingsPath, 'utf-8'));
830
+ const hooks = settings.hooks ?? {};
831
+ const drift = [];
832
+ for (const [name, expected] of Object.entries(CANONICAL_HOOK_TIMEOUTS)) {
833
+ const entries = hooks[name];
834
+ if (!Array.isArray(entries))
835
+ continue;
836
+ for (const entry of entries) {
837
+ for (const h of entry.hooks ?? []) {
838
+ if (typeof h.command !== 'string' || !h.command.includes('shieldcortex'))
839
+ continue;
840
+ if (typeof h.timeout === 'number' && h.timeout < expected) {
841
+ drift.push(`${name}=${h.timeout}s (canonical ${expected}s)`);
842
+ }
843
+ }
844
+ }
845
+ }
846
+ if (drift.length === 0) {
847
+ return { label: 'Hook timeouts', status: 'pass', message: 'all canonical' };
848
+ }
849
+ return {
850
+ label: 'Hook timeouts',
851
+ status: 'warn',
852
+ message: `below canonical: ${drift.join(', ')}`,
853
+ fix: 'Re-run `shieldcortex install` to restore canonical timeouts',
854
+ };
855
+ }
856
+ catch (err) {
857
+ const msg = err instanceof Error ? err.message : String(err);
858
+ return { label: 'Hook timeouts', status: 'info', message: `check skipped — ${msg}` };
859
+ }
860
+ }
629
861
  // ── Check 8: Model cache ─────────────────────────────────
630
862
  async function checkModelCache() {
631
863
  const cacheDir = path.join(os.homedir(), '.cache', 'shieldcortex', 'models', 'Xenova', 'all-MiniLM-L6-v2');
@@ -672,7 +904,11 @@ export async function runDoctor() {
672
904
  checkWritePath, // Smoke test: real INSERT/SELECT/DELETE round-trip — catches silent schema drift
673
905
  checkMemoryStats,
674
906
  checkHooks,
907
+ checkHookTimeouts,
675
908
  checkAutoMemoryHooks,
909
+ checkAutoMemorySampling,
910
+ checkBrainWorker,
911
+ checkProjectKeyConsistency,
676
912
  checkProcesses,
677
913
  checkDiskUsage,
678
914
  checkLockFile,
@@ -25,4 +25,34 @@ interface MigrationReport {
25
25
  }
26
26
  export declare function migrateLegacy(options?: MigrateOptions): MigrationReport;
27
27
  export declare function handleMemoriesCommand(args: string[]): Promise<void>;
28
+ interface RepairOptions {
29
+ /** Path to memories.db (defaults to ~/.shieldcortex/memories.db) */
30
+ dbPath?: string;
31
+ /** Walk these dev roots one level deep, propose mappings unambiguously */
32
+ scanPaths?: string[];
33
+ /** Explicit overrides; basename → canonical-key */
34
+ map?: Record<string, string>;
35
+ /** Limit the scan to a single legacy project key */
36
+ onlyProject?: string;
37
+ /** Include short-term rows (default: long-term + episodic only) */
38
+ includeStm?: boolean;
39
+ /** Default false — must be true to actually write */
40
+ execute?: boolean;
41
+ /** When true, never prompt (used by tests). Defaults to interactive. */
42
+ noConfirm?: boolean;
43
+ }
44
+ interface RepairProposal {
45
+ legacy: string;
46
+ canonical: string;
47
+ count: number;
48
+ source: 'map' | 'scan';
49
+ }
50
+ interface RepairReport {
51
+ dryRun: boolean;
52
+ proposals: RepairProposal[];
53
+ applied: number;
54
+ logPath?: string;
55
+ backupPath?: string;
56
+ }
57
+ export declare function repairProjectKeys(opts?: RepairOptions): Promise<RepairReport>;
28
58
  export {};
@@ -2,7 +2,9 @@ import fs from 'fs';
2
2
  import path from 'path';
3
3
  import os from 'os';
4
4
  import { randomUUID } from 'crypto';
5
+ import readline from 'readline';
5
6
  import Database from 'better-sqlite3';
7
+ import { deriveProjectKey } from '../context/derive-project-key.js';
6
8
  const DEFAULT_LEGACY_SOURCES = [
7
9
  path.join(os.homedir(), '.claude-cortex', 'memories.db'),
8
10
  path.join(os.homedir(), '.claude-memory', 'memories.db'),
@@ -265,6 +267,14 @@ function printUsage() {
265
267
  console.log(' Cluster near-duplicate long-term memories and keep the highest-');
266
268
  console.log(' salience representative. DRY-RUN BY DEFAULT — pass --execute.');
267
269
  console.log(' Backup auto-saved before any merge.');
270
+ console.log('');
271
+ console.log(' repair-project-keys [--scan-paths <dir,dir,...>]');
272
+ console.log(' [--map basename=canonical] (repeatable)');
273
+ console.log(' [--project <key>] [--include-stm] [--execute]');
274
+ console.log(' Relabel memories tagged under a legacy basename project key');
275
+ console.log(' to their canonical owner-repo key (#42). DRY-RUN BY DEFAULT.');
276
+ console.log(' Backup auto-saved before any rewrite; per-rewrite log written');
277
+ console.log(' to ~/.shieldcortex/logs/project-key-repair-<ts>.json.');
268
278
  }
269
279
  export async function handleMemoriesCommand(args) {
270
280
  const sub = args[0];
@@ -286,6 +296,195 @@ export async function handleMemoriesCommand(args) {
286
296
  await runDedupe(args.slice(1));
287
297
  return;
288
298
  }
299
+ if (sub === 'repair-project-keys') {
300
+ await runRepairProjectKeys(args.slice(1));
301
+ return;
302
+ }
289
303
  printUsage();
290
304
  process.exit(1);
291
305
  }
306
+ function parseMapFlags(args) {
307
+ const map = {};
308
+ for (let i = 0; i < args.length; i++) {
309
+ if (args[i] === '--map' && args[i + 1]) {
310
+ const pair = args[i + 1];
311
+ const eq = pair.indexOf('=');
312
+ if (eq <= 0 || eq === pair.length - 1) {
313
+ throw new Error(`--map expects 'basename=canonical', got '${pair}'`);
314
+ }
315
+ const k = pair.slice(0, eq).trim();
316
+ const v = pair.slice(eq + 1).trim();
317
+ if (!k || !v)
318
+ throw new Error(`--map basename and canonical must be non-empty: '${pair}'`);
319
+ map[k] = v;
320
+ i++;
321
+ }
322
+ }
323
+ return map;
324
+ }
325
+ function parseScanPaths(args) {
326
+ const v = flagValue(args, '--scan-paths');
327
+ if (!v)
328
+ return [];
329
+ return v
330
+ .split(',')
331
+ .map((s) => s.trim().replace(/^~(?=\/|$)/, os.homedir()))
332
+ .filter(Boolean);
333
+ }
334
+ async function confirmExecute(prompt) {
335
+ if (!process.stdin.isTTY)
336
+ return false;
337
+ const rl = readline.createInterface({ input: process.stdin, output: process.stdout });
338
+ try {
339
+ const answer = await new Promise((resolve) => rl.question(prompt, resolve));
340
+ return /^y(es)?$/i.test(answer.trim());
341
+ }
342
+ finally {
343
+ rl.close();
344
+ }
345
+ }
346
+ export async function repairProjectKeys(opts = {}) {
347
+ const dbPath = opts.dbPath ?? DEFAULT_TARGET;
348
+ if (!fs.existsSync(dbPath)) {
349
+ throw new Error(`memories DB not found at ${dbPath} — run \`shieldcortex setup\` first`);
350
+ }
351
+ const explicit = opts.map ?? {};
352
+ const scanPaths = opts.scanPaths ?? [];
353
+ const includeStm = opts.includeStm === true;
354
+ const dryRun = opts.execute !== true;
355
+ const db = new Database(dbPath);
356
+ db.pragma('busy_timeout = 10000');
357
+ let report;
358
+ try {
359
+ // 1. Distinct legacy project keys in the DB.
360
+ const typeFilter = includeStm ? '' : "AND type IN ('long_term', 'episodic')";
361
+ const distinct = db
362
+ .prepare(`SELECT DISTINCT project FROM memories WHERE project IS NOT NULL ${typeFilter}`)
363
+ .all();
364
+ const dbProjects = new Set(distinct.map((r) => r.project));
365
+ // 2. Build the proposal set.
366
+ const proposals = [];
367
+ const seen = new Set();
368
+ const addProposal = (legacy, canonical, source) => {
369
+ if (legacy === canonical)
370
+ return;
371
+ if (opts.onlyProject && legacy !== opts.onlyProject)
372
+ return;
373
+ if (!dbProjects.has(legacy))
374
+ return;
375
+ const key = `${legacy}${canonical}`;
376
+ if (seen.has(key))
377
+ return;
378
+ seen.add(key);
379
+ const countQ = db
380
+ .prepare(`SELECT COUNT(*) AS n FROM memories WHERE project = ? ${typeFilter}`)
381
+ .get(legacy);
382
+ proposals.push({ legacy, canonical, count: countQ.n, source });
383
+ };
384
+ // 2a. --map overrides win.
385
+ for (const [legacy, canonical] of Object.entries(explicit)) {
386
+ addProposal(legacy, canonical, 'map');
387
+ }
388
+ // 2b. --scan-paths: walk one level deep, run deriveProjectKey, match by basename.
389
+ for (const root of scanPaths) {
390
+ let entries = [];
391
+ try {
392
+ entries = fs.readdirSync(root);
393
+ }
394
+ catch {
395
+ continue;
396
+ }
397
+ for (const name of entries) {
398
+ const child = path.join(root, name);
399
+ let isDir = false;
400
+ try {
401
+ isDir = fs.statSync(child).isDirectory();
402
+ }
403
+ catch {
404
+ continue;
405
+ }
406
+ if (!isDir)
407
+ continue;
408
+ const canonical = deriveProjectKey(child);
409
+ if (!canonical || canonical === name)
410
+ continue;
411
+ addProposal(name, canonical, 'scan');
412
+ }
413
+ }
414
+ report = {
415
+ dryRun,
416
+ proposals,
417
+ applied: 0,
418
+ };
419
+ // 3. Print proposal table.
420
+ const banner = dryRun ? '[DRY RUN] ' : '';
421
+ console.log(`${banner}Project-key repair plan (${dbPath}):`);
422
+ if (proposals.length === 0) {
423
+ console.log(' No proposed rewrites — nothing to do.');
424
+ console.log('');
425
+ console.log('Tip: pass `--scan-paths ~/Development` (or `--map old=new`) so the');
426
+ console.log(' repair tool can match legacy basename keys against canonical');
427
+ console.log(' owner-repo keys derived from the git origin.');
428
+ return report;
429
+ }
430
+ for (const p of proposals) {
431
+ console.log(` ${p.legacy.padEnd(40)} → ${p.canonical.padEnd(48)} (${p.count} rows, source: ${p.source})`);
432
+ }
433
+ const totalRows = proposals.reduce((s, p) => s + p.count, 0);
434
+ console.log('');
435
+ console.log(`Total: ${totalRows} rows across ${proposals.length} project key(s).`);
436
+ if (dryRun) {
437
+ console.log('');
438
+ console.log('Re-run with --execute to apply. To undo later:');
439
+ console.log(' shieldcortex memories repair-project-keys \\');
440
+ console.log(' ' + proposals.map((p) => `--map ${p.canonical}=${p.legacy}`).join(' \\\n ') + ' --execute');
441
+ return report;
442
+ }
443
+ // 4. Confirm + backup + write.
444
+ if (!opts.noConfirm) {
445
+ const ok = await confirmExecute(`\nApply ${proposals.length} rewrite(s) to ${totalRows} rows? [y/N] `);
446
+ if (!ok) {
447
+ console.log('Aborted — no changes written.');
448
+ return report;
449
+ }
450
+ }
451
+ const backupPath = `${dbPath}.bak.${new Date().toISOString().replace(/[:.]/g, '-')}`;
452
+ fs.copyFileSync(dbPath, backupPath);
453
+ report.backupPath = backupPath;
454
+ console.log(`Backup: ${backupPath}`);
455
+ const update = db.prepare(`UPDATE memories SET project = ? WHERE project = ? ${typeFilter}`);
456
+ const txn = db.transaction(() => {
457
+ for (const p of proposals) {
458
+ const r = update.run(p.canonical, p.legacy);
459
+ report.applied += r.changes;
460
+ }
461
+ });
462
+ txn();
463
+ // 5. Per-rewrite JSON log under ~/.shieldcortex/logs/.
464
+ const logsDir = path.join(os.homedir(), '.shieldcortex', 'logs');
465
+ fs.mkdirSync(logsDir, { recursive: true });
466
+ const logPath = path.join(logsDir, `project-key-repair-${new Date().toISOString().replace(/[:.]/g, '-')}.json`);
467
+ fs.writeFileSync(logPath, JSON.stringify({
468
+ dbPath,
469
+ backupPath,
470
+ appliedAt: new Date().toISOString(),
471
+ rewrites: proposals,
472
+ totalRowsAffected: report.applied,
473
+ }, null, 2), 'utf-8');
474
+ report.logPath = logPath;
475
+ console.log(`Applied: ${report.applied} rows`);
476
+ console.log(`Log: ${logPath}`);
477
+ }
478
+ finally {
479
+ db.close();
480
+ }
481
+ return report;
482
+ }
483
+ async function runRepairProjectKeys(args) {
484
+ const map = parseMapFlags(args);
485
+ const scanPaths = parseScanPaths(args);
486
+ const onlyProject = flagValue(args, '--project');
487
+ const includeStm = args.includes('--include-stm');
488
+ const execute = args.includes('--execute');
489
+ await repairProjectKeys({ map, scanPaths, onlyProject, includeStm, execute });
490
+ }
@@ -0,0 +1,36 @@
1
+ /**
2
+ * TypeScript port of scripts/lib/project-key.mjs.
3
+ *
4
+ * Both the MCP-server side (this module) and the hook scripts must agree on
5
+ * how a cwd maps to a project key — otherwise writes and reads fall under
6
+ * different scopes and recall silently misses (issue #42).
7
+ *
8
+ * Resolution order:
9
+ * 1. SHIELDCORTEX_PROJECT_KEY env override
10
+ * 2. CLAUDE_MEMORY_PROJECT env override (legacy alias for SC env var)
11
+ * 3. ~/.shieldcortex/config.json projectKey
12
+ * 4. ~/.shieldcortex/config.json projectAliases[basename]
13
+ * 5. Git origin owner-repo (walk up from cwd)
14
+ * 6. Cwd basename (legacy behaviour), skipping noise directories
15
+ */
16
+ export declare function basenameFromCwd(path: string | null | undefined): string | null;
17
+ declare function parseOriginUrl(url: string): {
18
+ owner: string;
19
+ repo: string;
20
+ } | null;
21
+ declare function readOriginFromGitConfig(gitPath: string): {
22
+ owner: string;
23
+ repo: string;
24
+ } | null;
25
+ /**
26
+ * Derive the project key for a given working directory. Mirrors
27
+ * scripts/lib/project-key.mjs::deriveProjectKey so MCP-server-side and
28
+ * hook-side keys agree.
29
+ */
30
+ export declare function deriveProjectKey(cwd: string | null | undefined): string | null;
31
+ export declare const __internal: {
32
+ parseOriginUrl: typeof parseOriginUrl;
33
+ basenameFromCwd: typeof basenameFromCwd;
34
+ readOriginFromGitConfig: typeof readOriginFromGitConfig;
35
+ };
36
+ export {};