six-degrees 0.2.1 → 0.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 (470) hide show
  1. package/.next/standalone/.next/BUILD_ID +1 -1
  2. package/.next/standalone/.next/app-path-routes-manifest.json +10 -0
  3. package/.next/standalone/.next/build-manifest.json +3 -3
  4. package/.next/standalone/.next/prerender-manifest.json +39 -11
  5. package/.next/standalone/.next/required-server-files.json +4 -1
  6. package/.next/standalone/.next/routes-manifest.json +60 -0
  7. package/.next/standalone/.next/server/app/_global-error/page.js.nft.json +1 -1
  8. package/.next/standalone/.next/server/app/_global-error/page_client-reference-manifest.js +1 -1
  9. package/.next/standalone/.next/server/app/_global-error.html +1 -1
  10. package/.next/standalone/.next/server/app/_global-error.rsc +1 -1
  11. package/.next/standalone/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  12. package/.next/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  13. package/.next/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  14. package/.next/standalone/.next/server/app/_not-found/page.js.nft.json +1 -1
  15. package/.next/standalone/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  16. package/.next/standalone/.next/server/app/_not-found.html +1 -1
  17. package/.next/standalone/.next/server/app/_not-found.rsc +10 -10
  18. package/.next/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +10 -10
  19. package/.next/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +9 -9
  20. package/.next/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
  21. package/.next/standalone/.next/server/app/api/admin-delete/route.js +3 -2
  22. package/.next/standalone/.next/server/app/api/admin-delete/route.js.nft.json +1 -1
  23. package/.next/standalone/.next/server/app/api/admin-update/route.js +3 -2
  24. package/.next/standalone/.next/server/app/api/admin-update/route.js.nft.json +1 -1
  25. package/.next/standalone/.next/server/app/api/bridges/route.js +3 -2
  26. package/.next/standalone/.next/server/app/api/bridges/route.js.nft.json +1 -1
  27. package/.next/standalone/.next/server/app/api/bulk-import/route.js +3 -2
  28. package/.next/standalone/.next/server/app/api/bulk-import/route.js.nft.json +1 -1
  29. package/.next/standalone/.next/server/app/api/company-scores/legacy/route/app-paths-manifest.json +3 -0
  30. package/.next/standalone/.next/server/app/api/company-scores/legacy/route/build-manifest.json +12 -0
  31. package/.next/standalone/.next/server/app/api/company-scores/legacy/route/server-reference-manifest.json +4 -0
  32. package/.next/standalone/.next/server/app/api/company-scores/legacy/route.js +9 -0
  33. package/.next/standalone/.next/server/app/api/company-scores/legacy/route.js.map +5 -0
  34. package/.next/standalone/.next/server/app/api/company-scores/legacy/route.js.nft.json +1 -0
  35. package/.next/standalone/.next/server/app/api/company-scores/legacy/route_client-reference-manifest.js +3 -0
  36. package/.next/standalone/.next/server/app/api/company-scores/route.js +3 -2
  37. package/.next/standalone/.next/server/app/api/company-scores/route.js.nft.json +1 -1
  38. package/.next/standalone/.next/server/app/api/connections/route.js +3 -2
  39. package/.next/standalone/.next/server/app/api/connections/route.js.nft.json +1 -1
  40. package/.next/standalone/.next/server/app/api/data/export/route/app-paths-manifest.json +3 -0
  41. package/.next/standalone/.next/server/app/api/data/export/route/build-manifest.json +12 -0
  42. package/.next/standalone/.next/server/app/api/data/export/route/server-reference-manifest.json +4 -0
  43. package/.next/standalone/.next/server/app/api/data/export/route.js +7 -0
  44. package/.next/standalone/.next/server/app/api/data/export/route.js.map +5 -0
  45. package/.next/standalone/.next/server/app/api/data/export/route.js.nft.json +1 -0
  46. package/.next/standalone/.next/server/app/api/data/export/route_client-reference-manifest.js +3 -0
  47. package/.next/standalone/.next/server/app/api/data/import/route/app-paths-manifest.json +3 -0
  48. package/.next/standalone/.next/server/app/api/data/import/route/build-manifest.json +12 -0
  49. package/.next/standalone/.next/server/app/api/data/import/route/server-reference-manifest.json +4 -0
  50. package/.next/standalone/.next/server/app/api/data/import/route.js +8 -0
  51. package/.next/standalone/.next/server/app/api/data/import/route.js.map +5 -0
  52. package/.next/standalone/.next/server/app/api/data/import/route.js.nft.json +1 -0
  53. package/.next/standalone/.next/server/app/api/data/import/route_client-reference-manifest.js +3 -0
  54. package/.next/standalone/.next/server/app/api/data/restart/route/app-paths-manifest.json +3 -0
  55. package/.next/standalone/.next/server/app/api/data/restart/route/build-manifest.json +12 -0
  56. package/.next/standalone/.next/server/app/api/data/restart/route/server-reference-manifest.json +4 -0
  57. package/.next/standalone/.next/server/app/api/data/restart/route.js +8 -0
  58. package/.next/standalone/.next/server/app/api/data/restart/route.js.map +5 -0
  59. package/.next/standalone/.next/server/app/api/data/restart/route.js.nft.json +1 -0
  60. package/.next/standalone/.next/server/app/api/data/restart/route_client-reference-manifest.js +3 -0
  61. package/.next/standalone/.next/server/app/api/data/reveal/route/app-paths-manifest.json +3 -0
  62. package/.next/standalone/.next/server/app/api/data/reveal/route/build-manifest.json +12 -0
  63. package/.next/standalone/.next/server/app/api/data/reveal/route/server-reference-manifest.json +4 -0
  64. package/.next/standalone/.next/server/app/api/data/reveal/route.js +7 -0
  65. package/.next/standalone/.next/server/app/api/data/reveal/route.js.map +5 -0
  66. package/.next/standalone/.next/server/app/api/data/reveal/route.js.nft.json +1 -0
  67. package/.next/standalone/.next/server/app/api/data/reveal/route_client-reference-manifest.js +3 -0
  68. package/.next/standalone/.next/server/app/api/data/route/app-paths-manifest.json +3 -0
  69. package/.next/standalone/.next/server/app/api/data/route/build-manifest.json +12 -0
  70. package/.next/standalone/.next/server/app/api/data/route/server-reference-manifest.json +4 -0
  71. package/.next/standalone/.next/server/app/api/data/route.js +7 -0
  72. package/.next/standalone/.next/server/app/api/data/route.js.map +5 -0
  73. package/.next/standalone/.next/server/app/api/data/route.js.nft.json +1 -0
  74. package/.next/standalone/.next/server/app/api/data/route_client-reference-manifest.js +3 -0
  75. package/.next/standalone/.next/server/app/api/delete-cluster/route.js +3 -2
  76. package/.next/standalone/.next/server/app/api/delete-cluster/route.js.nft.json +1 -1
  77. package/.next/standalone/.next/server/app/api/ingest/route.js +2 -2
  78. package/.next/standalone/.next/server/app/api/ingest/route.js.nft.json +1 -1
  79. package/.next/standalone/.next/server/app/api/network/route.js +3 -2
  80. package/.next/standalone/.next/server/app/api/network/route.js.nft.json +1 -1
  81. package/.next/standalone/.next/server/app/api/notifications/route.js +3 -2
  82. package/.next/standalone/.next/server/app/api/notifications/route.js.nft.json +1 -1
  83. package/.next/standalone/.next/server/app/api/outreach/route.js +3 -2
  84. package/.next/standalone/.next/server/app/api/outreach/route.js.nft.json +1 -1
  85. package/.next/standalone/.next/server/app/api/queue/route.js +3 -2
  86. package/.next/standalone/.next/server/app/api/queue/route.js.nft.json +1 -1
  87. package/.next/standalone/.next/server/app/api/scraper/route.js +3 -2
  88. package/.next/standalone/.next/server/app/api/scraper/route.js.nft.json +1 -1
  89. package/.next/standalone/.next/server/app/api/settings/route/app-paths-manifest.json +3 -0
  90. package/.next/standalone/.next/server/app/api/settings/route/build-manifest.json +12 -0
  91. package/.next/standalone/.next/server/app/api/settings/route/server-reference-manifest.json +4 -0
  92. package/.next/standalone/.next/server/app/api/settings/route.js +9 -0
  93. package/.next/standalone/.next/server/app/api/settings/route.js.map +5 -0
  94. package/.next/standalone/.next/server/app/api/settings/route.js.nft.json +1 -0
  95. package/.next/standalone/.next/server/app/api/settings/route_client-reference-manifest.js +3 -0
  96. package/.next/standalone/.next/server/app/api/settings/sector-preview/route/app-paths-manifest.json +3 -0
  97. package/.next/standalone/.next/server/app/api/settings/sector-preview/route/build-manifest.json +12 -0
  98. package/.next/standalone/.next/server/app/api/settings/sector-preview/route/server-reference-manifest.json +4 -0
  99. package/.next/standalone/.next/server/app/api/settings/sector-preview/route.js +8 -0
  100. package/.next/standalone/.next/server/app/api/settings/sector-preview/route.js.map +5 -0
  101. package/.next/standalone/.next/server/app/api/settings/sector-preview/route.js.nft.json +1 -0
  102. package/.next/standalone/.next/server/app/api/settings/sector-preview/route_client-reference-manifest.js +3 -0
  103. package/.next/standalone/.next/server/app/api/settings/sector-suggestions/route/app-paths-manifest.json +3 -0
  104. package/.next/standalone/.next/server/app/api/settings/sector-suggestions/route/build-manifest.json +12 -0
  105. package/.next/standalone/.next/server/app/api/settings/sector-suggestions/route/server-reference-manifest.json +4 -0
  106. package/.next/standalone/.next/server/app/api/settings/sector-suggestions/route.js +8 -0
  107. package/.next/standalone/.next/server/app/api/settings/sector-suggestions/route.js.map +5 -0
  108. package/.next/standalone/.next/server/app/api/settings/sector-suggestions/route.js.nft.json +1 -0
  109. package/.next/standalone/.next/server/app/api/settings/sector-suggestions/route_client-reference-manifest.js +3 -0
  110. package/.next/standalone/.next/server/app/api/setup-profile/route.js +3 -2
  111. package/.next/standalone/.next/server/app/api/setup-profile/route.js.nft.json +1 -1
  112. package/.next/standalone/.next/server/app/api/unlock/route.js +3 -2
  113. package/.next/standalone/.next/server/app/api/unlock/route.js.nft.json +1 -1
  114. package/.next/standalone/.next/server/app/api/update/route.js +1 -1
  115. package/.next/standalone/.next/server/app/api/update/route.js.nft.json +1 -1
  116. package/.next/standalone/.next/server/app/api/update-images/route.js +3 -2
  117. package/.next/standalone/.next/server/app/api/update-images/route.js.nft.json +1 -1
  118. package/.next/standalone/.next/server/app/api/users/route.js +3 -2
  119. package/.next/standalone/.next/server/app/api/users/route.js.nft.json +1 -1
  120. package/.next/standalone/.next/server/app/avatars/[file]/route.js +2 -1
  121. package/.next/standalone/.next/server/app/avatars/[file]/route.js.nft.json +1 -1
  122. package/.next/standalone/.next/server/app/favicon.ico/route.js +2 -1
  123. package/.next/standalone/.next/server/app/favicon.ico/route.js.nft.json +1 -1
  124. package/.next/standalone/.next/server/app/import/page.js.nft.json +1 -1
  125. package/.next/standalone/.next/server/app/import/page_client-reference-manifest.js +1 -1
  126. package/.next/standalone/.next/server/app/import.html +1 -1
  127. package/.next/standalone/.next/server/app/import.rsc +12 -12
  128. package/.next/standalone/.next/server/app/import.segments/_full.segment.rsc +12 -12
  129. package/.next/standalone/.next/server/app/import.segments/_tree.segment.rsc +1 -1
  130. package/.next/standalone/.next/server/app/import.segments/import/__PAGE__.segment.rsc +11 -11
  131. package/.next/standalone/.next/server/app/index.html +1 -1
  132. package/.next/standalone/.next/server/app/index.rsc +12 -12
  133. package/.next/standalone/.next/server/app/index.segments/__PAGE__.segment.rsc +11 -11
  134. package/.next/standalone/.next/server/app/index.segments/_full.segment.rsc +12 -12
  135. package/.next/standalone/.next/server/app/index.segments/_tree.segment.rsc +1 -1
  136. package/.next/standalone/.next/server/app/launch/page.js.nft.json +1 -1
  137. package/.next/standalone/.next/server/app/launch/page_client-reference-manifest.js +1 -1
  138. package/.next/standalone/.next/server/app/launch.html +2 -2
  139. package/.next/standalone/.next/server/app/launch.rsc +12 -12
  140. package/.next/standalone/.next/server/app/launch.segments/_full.segment.rsc +12 -12
  141. package/.next/standalone/.next/server/app/launch.segments/_tree.segment.rsc +1 -1
  142. package/.next/standalone/.next/server/app/launch.segments/launch/__PAGE__.segment.rsc +11 -11
  143. package/.next/standalone/.next/server/app/page.js.nft.json +1 -1
  144. package/.next/standalone/.next/server/app/page_client-reference-manifest.js +1 -1
  145. package/.next/standalone/.next/server/app/paths/page.js.nft.json +1 -1
  146. package/.next/standalone/.next/server/app/paths/page_client-reference-manifest.js +1 -1
  147. package/.next/standalone/.next/server/app/paths.html +1 -1
  148. package/.next/standalone/.next/server/app/paths.rsc +12 -12
  149. package/.next/standalone/.next/server/app/paths.segments/_full.segment.rsc +12 -12
  150. package/.next/standalone/.next/server/app/paths.segments/_tree.segment.rsc +1 -1
  151. package/.next/standalone/.next/server/app/paths.segments/paths/__PAGE__.segment.rsc +11 -11
  152. package/.next/standalone/.next/server/app/profile/page.js.nft.json +1 -1
  153. package/.next/standalone/.next/server/app/profile/page_client-reference-manifest.js +1 -1
  154. package/.next/standalone/.next/server/app/profile.html +1 -1
  155. package/.next/standalone/.next/server/app/profile.rsc +12 -12
  156. package/.next/standalone/.next/server/app/profile.segments/_full.segment.rsc +12 -12
  157. package/.next/standalone/.next/server/app/profile.segments/_tree.segment.rsc +1 -1
  158. package/.next/standalone/.next/server/app/profile.segments/profile/__PAGE__.segment.rsc +11 -11
  159. package/.next/standalone/.next/server/app/queue/page.js.nft.json +1 -1
  160. package/.next/standalone/.next/server/app/queue/page_client-reference-manifest.js +1 -1
  161. package/.next/standalone/.next/server/app/queue.html +1 -1
  162. package/.next/standalone/.next/server/app/queue.rsc +12 -12
  163. package/.next/standalone/.next/server/app/queue.segments/_full.segment.rsc +12 -12
  164. package/.next/standalone/.next/server/app/queue.segments/_tree.segment.rsc +1 -1
  165. package/.next/standalone/.next/server/app/queue.segments/queue/__PAGE__.segment.rsc +11 -11
  166. package/.next/standalone/.next/server/app/settings/page/app-paths-manifest.json +3 -0
  167. package/.next/standalone/.next/server/app/settings/page/build-manifest.json +20 -0
  168. package/.next/standalone/.next/server/app/settings/page/next-font-manifest.json +11 -0
  169. package/.next/standalone/.next/server/app/settings/page/react-loadable-manifest.json +1 -0
  170. package/.next/standalone/.next/server/app/settings/page/server-reference-manifest.json +4 -0
  171. package/.next/standalone/.next/server/app/settings/page.js +13 -0
  172. package/.next/standalone/.next/server/app/settings/page.js.map +5 -0
  173. package/.next/standalone/.next/server/app/settings/page.js.nft.json +1 -0
  174. package/.next/standalone/.next/server/app/settings/page_client-reference-manifest.js +3 -0
  175. package/.next/standalone/.next/server/app/settings.html +1 -0
  176. package/.next/standalone/.next/server/app/settings.meta +26 -0
  177. package/.next/standalone/.next/server/app/settings.rsc +24 -0
  178. package/.next/standalone/.next/server/app/settings.segments/_full.segment.rsc +24 -0
  179. package/.next/standalone/.next/server/app/settings.segments/_tree.segment.rsc +4 -0
  180. package/.next/standalone/.next/server/app/settings.segments/settings/__PAGE__.segment.rsc +28 -0
  181. package/.next/standalone/.next/server/app/setup/page.js.nft.json +1 -1
  182. package/.next/standalone/.next/server/app/setup/page_client-reference-manifest.js +1 -1
  183. package/.next/standalone/.next/server/app/setup.html +1 -1
  184. package/.next/standalone/.next/server/app/setup.rsc +12 -12
  185. package/.next/standalone/.next/server/app/setup.segments/_full.segment.rsc +12 -12
  186. package/.next/standalone/.next/server/app/setup.segments/_tree.segment.rsc +1 -1
  187. package/.next/standalone/.next/server/app/setup.segments/setup/__PAGE__.segment.rsc +11 -11
  188. package/.next/standalone/.next/server/app-paths-manifest.json +10 -0
  189. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0-rnla2._.js +3 -0
  190. package/.next/standalone/.next/server/chunks/[root-of-the-server]__00la_y0._.js +3 -0
  191. package/.next/standalone/.next/server/chunks/[root-of-the-server]__07t47cm._.js +3 -0
  192. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0cj5jqc._.js +3 -0
  193. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0e0fei3._.js +3 -0
  194. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0i5hdu4._.js +3 -0
  195. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0ljcioj._.js +3 -0
  196. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0ljnyho._.js +3 -0
  197. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0o5-tcg._.js +3 -0
  198. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0qrnous._.js +3 -0
  199. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0t3v1a1._.js +3 -0
  200. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0uag-k5._.js +8 -0
  201. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0um1uey._.js +3 -0
  202. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0wmexuc._.js +3 -0
  203. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0xu34sz._.js +3 -0
  204. package/.next/standalone/.next/server/chunks/[root-of-the-server]__133knx1._.js +3 -0
  205. package/.next/standalone/.next/server/chunks/[root-of-the-server]__14ou7j5._.js +3 -0
  206. package/.next/standalone/.next/server/chunks/[root-of-the-server]__15-17hl._.js +3 -0
  207. package/.next/standalone/.next/server/chunks/[root-of-the-server]__16iu0hv._.js +3 -0
  208. package/.next/standalone/.next/server/chunks/[root-of-the-server]__19b7mig._.js +3 -0
  209. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1bbcwub._.js +8 -0
  210. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1eris29._.js +3 -0
  211. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1gjo_cq._.js +3 -0
  212. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1kbl21f._.js +3 -0
  213. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1qcm08_._.js +3 -0
  214. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1rphsdk._.js +3 -0
  215. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1t3rugi._.js +3 -0
  216. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1w25q0m._.js +3 -0
  217. package/.next/standalone/.next/server/chunks/_072jl0y._.js +3 -0
  218. package/.next/standalone/.next/server/chunks/_0lw8_i0._.js +3 -0
  219. package/.next/standalone/.next/server/chunks/_1_fynia._.js +21 -3
  220. package/.next/standalone/.next/server/chunks/_1fn30_l._.js +3 -0
  221. package/.next/standalone/.next/server/chunks/_1itd1o_._.js +2 -1
  222. package/.next/standalone/.next/server/chunks/_1iwkh8t._.js +1 -1
  223. package/.next/standalone/.next/server/chunks/_1mxn_lb._.js +3 -0
  224. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_company-scores_legacy_route_actions_1ncspu_.js +3 -0
  225. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_data_export_route_actions_1lkimty.js +3 -0
  226. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_data_import_route_actions_1eji0kd.js +3 -0
  227. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_data_restart_route_actions_00_-u6o.js +3 -0
  228. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_data_reveal_route_actions_0-moqtn.js +3 -0
  229. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_data_route_actions_0j0w5ep.js +3 -0
  230. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_settings_route_actions_1bpm9ac.js +3 -0
  231. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_settings_sector-preview_route_actions_0w79454.js +3 -0
  232. package/.next/standalone/.next/server/chunks/_next-internal_server_app_api_settings_sector-suggestions_route_actions_1eoqugp.js +3 -0
  233. package/.next/standalone/.next/server/chunks/lib_db-client_15le7cw.js +155 -0
  234. package/.next/standalone/.next/server/chunks/{lib_rpc_0mc73lk.js → lib_rpc_00tx2sm.js} +1 -1
  235. package/.next/standalone/.next/server/chunks/lib_rpc_02-qa4d.js +3 -0
  236. package/.next/standalone/.next/server/chunks/lib_rpc_02ndsg2.js +3 -0
  237. package/.next/standalone/.next/server/chunks/lib_rpc_08q5vp6.js +3 -0
  238. package/.next/standalone/.next/server/chunks/lib_rpc_0_8i3ft.js +3 -0
  239. package/.next/standalone/.next/server/chunks/lib_rpc_0c9d9ti.js +5 -2
  240. package/.next/standalone/.next/server/chunks/lib_rpc_0huvw-3.js +3 -0
  241. package/.next/standalone/.next/server/chunks/lib_rpc_0ip2vdh.js +3 -0
  242. package/.next/standalone/.next/server/chunks/lib_rpc_0jzisgh.js +3 -0
  243. package/.next/standalone/.next/server/chunks/lib_rpc_0yi9xvd.js +3 -0
  244. package/.next/standalone/.next/server/chunks/lib_rpc_1jyhd0o.js +3 -0
  245. package/.next/standalone/.next/server/chunks/lib_rpc_1kn59-i.js +3 -0
  246. package/.next/standalone/.next/server/chunks/lib_rpc_1q2jkza.js +3 -0
  247. package/.next/standalone/.next/server/chunks/lib_rpc_1vpm1sk.js +3 -0
  248. package/.next/standalone/.next/server/chunks/lib_rpc_1x6p_31.js +3 -0
  249. package/.next/standalone/.next/server/chunks/node_modules_next_1zc5q0a._.js +158 -0
  250. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__0mocm6d._.js → [root-of-the-server]__0an6blh._.js} +3 -3
  251. package/.next/standalone/.next/server/chunks/ssr/[root-of-the-server]__1m0255u._.js +3 -0
  252. package/.next/standalone/.next/server/chunks/ssr/{[root-of-the-server]__0bipr5s._.js → [root-of-the-server]__1z1j3ek._.js} +2 -2
  253. package/.next/standalone/.next/server/chunks/ssr/_07u8byv._.js +3 -0
  254. package/.next/standalone/.next/server/chunks/ssr/_08r_mlf._.js +3 -0
  255. package/.next/standalone/.next/server/chunks/ssr/{_0ggabjc._.js → _0942v8n._.js} +1 -1
  256. package/.next/standalone/.next/server/chunks/ssr/{_1djpk8t._.js → _0hl_t7r._.js} +2 -2
  257. package/.next/standalone/.next/server/chunks/ssr/_0tb83dw._.js +132 -0
  258. package/.next/standalone/.next/server/chunks/ssr/_1-87bs1._.js +3 -0
  259. package/.next/standalone/.next/server/chunks/ssr/_17gui6a._.js +1 -1
  260. package/.next/standalone/.next/server/chunks/ssr/_next-internal_server_app_settings_page_actions_11x4dq5.js +3 -0
  261. package/.next/standalone/.next/server/chunks/ssr/app_launch_page_19t0dyd.js +2 -2
  262. package/.next/standalone/.next/server/chunks/ssr/app_page_1fazqbf.js +4 -4
  263. package/.next/standalone/.next/server/chunks/ssr/app_profile_page_0u3-l5y.js +1 -1
  264. package/.next/standalone/.next/server/chunks/ssr/app_queue_page_0c6znd6.js +5 -5
  265. package/.next/standalone/.next/server/chunks/ssr/app_settings_page_1f8mjj_.js +3 -0
  266. package/.next/standalone/.next/server/chunks/ssr/app_setup_page_1-282zx.js +2 -2
  267. package/.next/standalone/.next/server/chunks/ssr/lib_0i8v-s3._.js +1 -1
  268. package/.next/standalone/.next/server/chunks/ssr/node_modules_1f8t_rp._.js +23 -0
  269. package/.next/standalone/.next/server/chunks/ssr/node_modules_1nkgb45._.js +2 -2
  270. package/.next/standalone/.next/server/chunks/ssr/{node_modules_01xbj_9._.js → node_modules_1wax83z._.js} +3 -3
  271. package/.next/standalone/.next/server/chunks/ssr/{node_modules_next_dist_00nap8h._.js → node_modules_next_dist_1bunoni._.js} +2 -2
  272. package/.next/standalone/.next/server/edge/chunks/[root-of-the-server]__0pco7a6._.js +2 -2
  273. package/.next/standalone/.next/server/middleware-build-manifest.js +3 -3
  274. package/.next/standalone/.next/server/middleware-manifest.json +15 -7
  275. package/.next/standalone/.next/server/next-font-manifest.js +1 -1
  276. package/.next/standalone/.next/server/next-font-manifest.json +4 -0
  277. package/.next/standalone/.next/server/pages/404.html +1 -1
  278. package/.next/standalone/.next/server/pages/500.html +1 -1
  279. package/.next/standalone/.next/server/prefetch-hints.json +14 -0
  280. package/.next/standalone/.next/server/server-reference-manifest.js +1 -1
  281. package/.next/standalone/.next/server/server-reference-manifest.json +1 -1
  282. package/.next/standalone/.next/static/chunks/06x3jiiz96m5t.js +1 -0
  283. package/.next/standalone/.next/static/chunks/{34at5d2ifl62i.js → 0ngx9s6-zgshe.js} +5 -5
  284. package/.next/standalone/.next/static/chunks/0q-_khndfxubv.js +2 -0
  285. package/.next/standalone/.next/static/chunks/1c79veqedvubt.js +1 -0
  286. package/.next/standalone/.next/static/chunks/1chp3nx45meg5.js +44 -0
  287. package/.next/standalone/.next/static/chunks/1irqj0lf-fu3d.js +1 -0
  288. package/.next/standalone/.next/static/chunks/1uadqylrod5_v.js +1 -0
  289. package/.next/standalone/.next/static/chunks/23u0zclgwpc4d.js +1 -0
  290. package/.next/standalone/.next/static/chunks/289ktj97di6zg.js +1 -0
  291. package/.next/standalone/.next/static/chunks/2b3lmf8e6uj8m.js +16 -0
  292. package/.next/standalone/.next/static/chunks/2jz311xl1pp_8.js +1 -0
  293. package/.next/standalone/.next/static/chunks/3npq5yd7c4dmn.js +2 -0
  294. package/.next/standalone/.next/static/qqqcxvzBUizkECrT4swyK/_clientMiddlewareManifest.js +14 -0
  295. package/.next/standalone/CHANGELOG.md +298 -0
  296. package/.next/standalone/CONTRIBUTING.md +5 -2
  297. package/.next/standalone/README.md +138 -30
  298. package/.next/standalone/SECURITY.md +117 -10
  299. package/.next/standalone/app/api/company-scores/legacy/route.js +32 -0
  300. package/.next/standalone/app/api/company-scores/route.js +20 -11
  301. package/.next/standalone/app/api/data/export/route.js +49 -0
  302. package/.next/standalone/app/api/data/import/route.js +83 -0
  303. package/.next/standalone/app/api/data/restart/route.js +37 -0
  304. package/.next/standalone/app/api/data/reveal/route.js +14 -0
  305. package/.next/standalone/app/api/data/route.js +39 -0
  306. package/.next/standalone/app/api/ingest/route.js +15 -47
  307. package/.next/standalone/app/api/scraper/route.js +264 -125
  308. package/.next/standalone/app/api/settings/route.js +58 -0
  309. package/.next/standalone/app/api/settings/sector-preview/route.js +38 -0
  310. package/.next/standalone/app/api/settings/sector-suggestions/route.js +20 -0
  311. package/.next/standalone/app/api/update/route.js +188 -23
  312. package/.next/standalone/app/avatars/[file]/route.js +4 -2
  313. package/.next/standalone/app/components/CompanyScores.js +28 -7
  314. package/.next/standalone/app/components/EmptyState.js +8 -0
  315. package/.next/standalone/app/components/ForceGraph.js +39 -35
  316. package/.next/standalone/app/components/LegacyScoresCard.js +129 -0
  317. package/.next/standalone/app/components/Sidebar.js +11 -10
  318. package/.next/standalone/app/components/UpdatePanel.js +306 -119
  319. package/.next/standalone/app/components/UserProvider.js +4 -3
  320. package/.next/standalone/app/components/settings/DataSection.js +437 -0
  321. package/.next/standalone/app/components/settings/SectorSection.js +445 -0
  322. package/.next/standalone/app/components/ui.js +62 -0
  323. package/.next/standalone/app/launch/page.js +30 -20
  324. package/.next/standalone/app/page.js +13 -0
  325. package/.next/standalone/app/paths/page.js +12 -4
  326. package/.next/standalone/app/profile/page.js +41 -8
  327. package/.next/standalone/app/queue/page.js +8 -2
  328. package/.next/standalone/app/settings/page.js +96 -0
  329. package/.next/standalone/app/setup/page.js +32 -16
  330. package/.next/standalone/bin/args.mjs +44 -0
  331. package/.next/standalone/bin/six-degrees.mjs +9 -15
  332. package/.next/standalone/lib/companies.js +44 -119
  333. package/.next/standalone/lib/csv.js +8 -0
  334. package/.next/standalone/lib/data-export.js +170 -0
  335. package/.next/standalone/lib/data-folder.js +238 -0
  336. package/.next/standalone/lib/data-import.js +878 -0
  337. package/.next/standalone/lib/db-client.js +48 -3
  338. package/.next/standalone/lib/durable.js +73 -0
  339. package/.next/standalone/lib/gate.js +90 -1
  340. package/.next/standalone/lib/ingest.js +40 -0
  341. package/.next/standalone/lib/legacy-offer.js +185 -0
  342. package/.next/standalone/lib/legacy-scores.js +77 -0
  343. package/.next/standalone/lib/linkedin-limits.js +124 -1
  344. package/.next/standalone/lib/rpc.js +121 -13
  345. package/.next/standalone/lib/sample-stats.js +16 -0
  346. package/.next/standalone/lib/scan-progress.js +13 -0
  347. package/.next/standalone/lib/scan-state.js +53 -0
  348. package/.next/standalone/lib/scanner-python.js +685 -0
  349. package/.next/standalone/lib/scanner-setup.js +104 -0
  350. package/.next/standalone/lib/scoring.js +747 -138
  351. package/.next/standalone/lib/scraper-client.js +9 -5
  352. package/.next/standalone/lib/sector-directory.js +1532 -0
  353. package/.next/standalone/lib/sector-focus.js +163 -0
  354. package/.next/standalone/lib/sector-labels.js +81 -0
  355. package/.next/standalone/lib/settings-effects.js +59 -0
  356. package/.next/standalone/lib/settings.js +83 -0
  357. package/.next/standalone/lib/updater-job.js +838 -0
  358. package/.next/standalone/lib/updater.js +494 -0
  359. package/.next/standalone/middleware.js +25 -28
  360. package/.next/standalone/next.config.mjs +19 -3
  361. package/.next/standalone/package-lock.json +2 -2
  362. package/.next/standalone/package.json +1 -2
  363. package/.next/standalone/scripts/apply-update.sh +482 -0
  364. package/.next/standalone/scripts/build-app.mjs +251 -9
  365. package/.next/standalone/scripts/requirements.txt +106 -4
  366. package/.next/standalone/scripts/test-release-server.mjs +143 -0
  367. package/.next/standalone/server.js +1 -1
  368. package/.next/static/chunks/06x3jiiz96m5t.js +1 -0
  369. package/.next/static/chunks/{34at5d2ifl62i.js → 0ngx9s6-zgshe.js} +5 -5
  370. package/.next/static/chunks/0q-_khndfxubv.js +2 -0
  371. package/.next/static/chunks/1c79veqedvubt.js +1 -0
  372. package/.next/static/chunks/1chp3nx45meg5.js +44 -0
  373. package/.next/static/chunks/1irqj0lf-fu3d.js +1 -0
  374. package/.next/static/chunks/1uadqylrod5_v.js +1 -0
  375. package/.next/static/chunks/23u0zclgwpc4d.js +1 -0
  376. package/.next/static/chunks/289ktj97di6zg.js +1 -0
  377. package/.next/static/chunks/2b3lmf8e6uj8m.js +16 -0
  378. package/.next/static/chunks/2jz311xl1pp_8.js +1 -0
  379. package/.next/static/chunks/3npq5yd7c4dmn.js +2 -0
  380. package/.next/static/qqqcxvzBUizkECrT4swyK/_clientMiddlewareManifest.js +14 -0
  381. package/CHANGELOG.md +298 -0
  382. package/README.md +138 -30
  383. package/SECURITY.md +117 -10
  384. package/bin/args.mjs +44 -0
  385. package/bin/six-degrees.mjs +9 -15
  386. package/lib/companies.js +44 -119
  387. package/lib/csv.js +8 -0
  388. package/lib/data-export.js +170 -0
  389. package/lib/data-folder.js +238 -0
  390. package/lib/data-import.js +878 -0
  391. package/lib/db-client.js +48 -3
  392. package/lib/durable.js +73 -0
  393. package/lib/gate.js +90 -1
  394. package/lib/ingest.js +40 -0
  395. package/lib/legacy-offer.js +185 -0
  396. package/lib/legacy-scores.js +77 -0
  397. package/lib/linkedin-limits.js +124 -1
  398. package/lib/rpc.js +121 -13
  399. package/lib/sample-stats.js +16 -0
  400. package/lib/scan-progress.js +13 -0
  401. package/lib/scan-state.js +53 -0
  402. package/lib/scanner-python.js +685 -0
  403. package/lib/scanner-setup.js +104 -0
  404. package/lib/scoring.js +747 -138
  405. package/lib/scraper-client.js +9 -5
  406. package/lib/sector-directory.js +1532 -0
  407. package/lib/sector-focus.js +163 -0
  408. package/lib/sector-labels.js +81 -0
  409. package/lib/settings-effects.js +59 -0
  410. package/lib/settings.js +83 -0
  411. package/lib/updater-job.js +838 -0
  412. package/lib/updater.js +494 -0
  413. package/package.json +1 -2
  414. package/scripts/requirements.txt +106 -4
  415. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0jrmmj-._.js +0 -150
  416. package/.next/standalone/.next/server/chunks/[root-of-the-server]__0qx548g._.js +0 -151
  417. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1an3leo._.js +0 -150
  418. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1m8zedk._.js +0 -155
  419. package/.next/standalone/.next/server/chunks/[root-of-the-server]__1zor0ys._.js +0 -3
  420. package/.next/standalone/.next/server/chunks/_0_rp-01._.js +0 -3
  421. package/.next/standalone/.next/server/chunks/_0hzdk79._.js +0 -3
  422. package/.next/standalone/.next/server/chunks/_0ow7u5r._.js +0 -3
  423. package/.next/standalone/.next/server/chunks/_0t0zc2d._.js +0 -3
  424. package/.next/standalone/.next/server/chunks/_0wa631d._.js +0 -3
  425. package/.next/standalone/.next/server/chunks/_13ccnao._.js +0 -3
  426. package/.next/standalone/.next/server/chunks/_13es063._.js +0 -3
  427. package/.next/standalone/.next/server/chunks/_142872j._.js +0 -3
  428. package/.next/standalone/.next/server/chunks/_18wsb_a._.js +0 -8
  429. package/.next/standalone/.next/server/chunks/_1e-4h5h._.js +0 -3
  430. package/.next/standalone/.next/server/chunks/_1gvvd7n._.js +0 -158
  431. package/.next/standalone/.next/server/chunks/_1moda66._.js +0 -3
  432. package/.next/standalone/.next/server/chunks/_1p6ghzv._.js +0 -3
  433. package/.next/standalone/.next/server/chunks/_1xmmi_v._.js +0 -3
  434. package/.next/standalone/.next/server/chunks/_1z-yrlf._.js +0 -3
  435. package/.next/standalone/.next/server/chunks/ssr/_0bf3x4q._.js +0 -3
  436. package/.next/standalone/.next/server/chunks/ssr/app_paths_page_1ol90m7.js +0 -4
  437. package/.next/standalone/.next/static/ZGTiDrZ5NHGETgGdlhssu/_clientMiddlewareManifest.js +0 -6
  438. package/.next/standalone/.next/static/chunks/0jk64vo17avsb.js +0 -1
  439. package/.next/standalone/.next/static/chunks/0s65dsrthylo6.js +0 -2
  440. package/.next/standalone/.next/static/chunks/0uyfdhi8dek85.js +0 -16
  441. package/.next/standalone/.next/static/chunks/220-ne82aus0c.js +0 -44
  442. package/.next/standalone/.next/static/chunks/229haorf0f19b.js +0 -2
  443. package/.next/standalone/.next/static/chunks/2g54uafnwuakc.js +0 -1
  444. package/.next/standalone/.next/static/chunks/2spwqs6b6dx13.js +0 -1
  445. package/.next/standalone/.next/static/chunks/38dlepuubiox0.js +0 -1
  446. package/.next/standalone/scripts/score-connections.sql +0 -80
  447. package/.next/standalone/scripts/score_new_connections.sql +0 -77
  448. package/.next/standalone/site/app.js +0 -84
  449. package/.next/standalone/site/index.html +0 -221
  450. package/.next/standalone/site/style.css +0 -155
  451. package/.next/standalone/site/video/install-mac-poster.jpg +0 -0
  452. package/.next/standalone/site/video/install-mac.mp4 +0 -0
  453. package/.next/standalone/site/video/linux-poster.jpg +0 -0
  454. package/.next/standalone/site/video/linux.mp4 +0 -0
  455. package/.next/standalone/site/video/scan-poster.jpg +0 -0
  456. package/.next/standalone/site/video/scan.mp4 +0 -0
  457. package/.next/static/ZGTiDrZ5NHGETgGdlhssu/_clientMiddlewareManifest.js +0 -6
  458. package/.next/static/chunks/0jk64vo17avsb.js +0 -1
  459. package/.next/static/chunks/0s65dsrthylo6.js +0 -2
  460. package/.next/static/chunks/0uyfdhi8dek85.js +0 -16
  461. package/.next/static/chunks/220-ne82aus0c.js +0 -44
  462. package/.next/static/chunks/229haorf0f19b.js +0 -2
  463. package/.next/static/chunks/2g54uafnwuakc.js +0 -1
  464. package/.next/static/chunks/2spwqs6b6dx13.js +0 -1
  465. package/.next/static/chunks/38dlepuubiox0.js +0 -1
  466. package/scripts/score_new_connections.sql +0 -77
  467. /package/.next/standalone/.next/static/{ZGTiDrZ5NHGETgGdlhssu → qqqcxvzBUizkECrT4swyK}/_buildManifest.js +0 -0
  468. /package/.next/standalone/.next/static/{ZGTiDrZ5NHGETgGdlhssu → qqqcxvzBUizkECrT4swyK}/_ssgManifest.js +0 -0
  469. /package/.next/static/{ZGTiDrZ5NHGETgGdlhssu → qqqcxvzBUizkECrT4swyK}/_buildManifest.js +0 -0
  470. /package/.next/static/{ZGTiDrZ5NHGETgGdlhssu → qqqcxvzBUizkECrT4swyK}/_ssgManifest.js +0 -0
@@ -0,0 +1,494 @@
1
+ // One-click updates for the Mac app: the decisions, with no side effects.
2
+ //
3
+ // The work happens in two places. lib/updater-job.js downloads the new version,
4
+ // checks it and puts a copy beside the running app, all while the old version
5
+ // keeps working. scripts/apply-update.sh then waits for the app to quit, swaps
6
+ // the two, and opens the new one. Everything that decides something lives here,
7
+ // so tests/updater.test.mjs can check each decision without a network, a disk
8
+ // image or a Mac.
9
+ //
10
+ // Nothing here runs on its own. Checking is a click, and installing is a second
11
+ // click (spec invariant 2).
12
+
13
+ import path from 'node:path';
14
+ import { compareVersions } from './release.js';
15
+
16
+ /** The Mac app's bundle identifier (scripts/build-app.mjs). A download that says otherwise isn't used. */
17
+ export const BUNDLE_ID = 'com.blakeburford.sixdegrees';
18
+
19
+ /** What the disk image holds, and what the running copy is normally called. */
20
+ export const APP_BUNDLE_NAME = 'Six Degrees.app';
21
+
22
+ /** The checksum file every release carries (.github/workflows/release.yml). */
23
+ export const SUMS_NAME = 'SHA256SUMS';
24
+
25
+ /**
26
+ * The exit code the server ends with once the update helper has started. The
27
+ * Mac app reads it as "quit quietly": a crash's exit code shows the "Six
28
+ * Degrees stopped" error, and a SIGTERM to itself isn't used because Next
29
+ * catches it and exits with 143 (TRAPS §39), which says "stopped from outside",
30
+ * not "an update follows". desktop/lib.mjs has the same number, since the shell
31
+ * can't import from lib/; tests/updater.test.mjs checks that the two agree.
32
+ * Node and Next never exit with 76 themselves. (Not 75: that is
33
+ * RESTART_EXIT_CODE in desktop/lib.mjs, "start the server again", which the
34
+ * data import uses.)
35
+ */
36
+ export const UPDATE_HANDOFF_EXIT_CODE = 76;
37
+
38
+ /** Where releases come from: GitHub's API, and GitHub's release downloads. */
39
+ export const GITHUB = Object.freeze({ apiBase: 'https://api.github.com', downloadBase: 'https://github.com' });
40
+
41
+ /**
42
+ * Where to read releases and download them from. Always GitHub, except in a
43
+ * test: SIX_DEGREES_TEST_RELEASES=http://127.0.0.1:<port> points both at a
44
+ * fixture server on this computer (the browser check, and a CI step that
45
+ * updates one build to the next). Nothing in the app sets it, and only
46
+ * 127.0.0.1 is honoured (the fixture server listens there and nowhere else),
47
+ * so it can never send an update to another machine; anything else is ignored
48
+ * and GitHub is used.
49
+ */
50
+ export function releaseSource(env = {}) {
51
+ const raw = env?.SIX_DEGREES_TEST_RELEASES;
52
+ if (!raw) return { ...GITHUB, test: false };
53
+ let url = null;
54
+ try { url = new URL(String(raw)); } catch { /* ignored below */ }
55
+ const loopback = url && url.protocol === 'http:' && url.hostname === '127.0.0.1'
56
+ && url.port !== '' && url.pathname === '/' && !url.search && !url.hash && !url.username && !url.password;
57
+ if (!loopback) return { ...GITHUB, test: false };
58
+ return { apiBase: url.origin, downloadBase: url.origin, test: true };
59
+ }
60
+
61
+ /** How long the last update's outcome stays on the Settings page. */
62
+ export const REPORT_DAYS = 7;
63
+
64
+ /** No release of this app is anywhere near this size (about 220 MB since the scanner's Python went inside, 0.3.0). */
65
+ export const MAX_DMG_BYTES = 1024 * 1024 * 1024;
66
+
67
+ const refuse = (code, message) => ({ refusal: { code, message } });
68
+
69
+ /**
70
+ * Which build this Mac needs: 'arm64' (Apple Silicon) or 'x64' (Intel).
71
+ *
72
+ * Asked the way install.sh asks. `hw.optional.arm64` is the hardware: it says 1
73
+ * on Apple Silicon even when this process runs under Rosetta and calls itself
74
+ * x64 (TRAPS §30), which is why neither process.arch nor `uname -m` decides.
75
+ * The one thing process.arch can add: a process that *is* arm64 can only be
76
+ * on Apple Silicon, so it covers a sysctl that failed to answer. It can never
77
+ * turn an Apple Silicon Mac into an Intel one.
78
+ */
79
+ export function chipOf({ sysctlArm64, processArch } = {}) {
80
+ if (String(sysctlArm64 ?? '').trim() === '1') return 'arm64';
81
+ if (processArch === 'arm64') return 'arm64';
82
+ return 'x64';
83
+ }
84
+
85
+ export const CHIP_LABEL = { arm64: 'Apple Silicon', x64: 'Intel' };
86
+
87
+ /** The disk image's exact file name, as scripts/build-app.mjs names it. */
88
+ export function dmgName(version, chip) {
89
+ return `Six-Degrees-${version}-${chip}.dmg`;
90
+ }
91
+
92
+ /**
93
+ * From GitHub's answer to releases/latest, exactly what to download, or why
94
+ * not. Returns { plan } or { refusal: { code, message } }.
95
+ *
96
+ * Every name and address is worked out here from the release and this Mac;
97
+ * nothing comes from the page. The download must be this repository's own
98
+ * release asset, by its exact name: install.sh's "first file ending in
99
+ * -arm64.dmg" would also have taken a fixed-name copy or anything else added
100
+ * to a release later.
101
+ */
102
+ export function planFromRelease(release, { currentVersion, chip, slug, downloadBase = GITHUB.downloadBase }) {
103
+ if (!release || typeof release !== 'object' || !release.tag_name) {
104
+ return refuse('no-release', 'GitHub did not describe a release.');
105
+ }
106
+ const tag = String(release.tag_name);
107
+ const version = tag.replace(/^v/i, '');
108
+ // releases/latest never returns a pre-release, and a tag with a hyphen is one
109
+ // (release.yml). Checked here as well, so a beta can't be installed by accident
110
+ // whatever GitHub answers (DESKTOP.md rule 4).
111
+ if (release.draft || release.prerelease || version.includes('-')) {
112
+ return refuse('prerelease', `Version ${version} is a test version, so it isn't installed from here.`);
113
+ }
114
+ if (!/^\d+(\.\d+){1,3}$/.test(version)) {
115
+ return refuse('bad-version', `GitHub's newest release has a version this app doesn't understand (${tag}).`);
116
+ }
117
+ if (compareVersions(version, currentVersion) <= 0) {
118
+ return refuse('not-newer', `You already have ${currentVersion}, and the newest version is ${version}.`);
119
+ }
120
+
121
+ const assets = Array.isArray(release.assets) ? release.assets : [];
122
+ const find = (name) => assets.find((a) => a && a.name === name) || null;
123
+ const dmg = find(dmgName(version, chip));
124
+ if (!dmg) {
125
+ return refuse('no-download', `Version ${version} has no download for this Mac (${CHIP_LABEL[chip] || chip}).`);
126
+ }
127
+ const sums = find(SUMS_NAME);
128
+ if (!sums) {
129
+ return refuse('no-checksums', `Version ${version} was published without its checksum file (${SUMS_NAME}), so its download can't be checked.`);
130
+ }
131
+ const base = `${downloadBase}/${slug}/releases/download/${encodeURIComponent(tag)}/`;
132
+ for (const asset of [dmg, sums]) {
133
+ if (asset.browser_download_url !== base + encodeURIComponent(asset.name)) {
134
+ return refuse('unexpected-address', `GitHub listed ${asset.name} at an unexpected address, so it wasn't downloaded.`);
135
+ }
136
+ }
137
+ const size = Number(dmg.size) > 0 ? Number(dmg.size) : null;
138
+ if (size && size > MAX_DMG_BYTES) {
139
+ return refuse('too-large', `The download for version ${version} is unexpectedly large, so it wasn't downloaded.`);
140
+ }
141
+ return {
142
+ plan: {
143
+ version,
144
+ tag,
145
+ notes: typeof release.html_url === 'string' ? release.html_url : null,
146
+ dmg: { name: dmg.name, url: dmg.browser_download_url, size },
147
+ sums: { name: sums.name, url: sums.browser_download_url },
148
+ },
149
+ };
150
+ }
151
+
152
+ /**
153
+ * SHA256SUMS as release.yml writes it (`sha256sum *.dmg`): "<64 hex> <name>",
154
+ * or " *<name>" in binary mode. Returns Map name → lowercase hex. A name listed
155
+ * twice with different sums is ambiguous and maps to null, which is treated as
156
+ * missing: better to refuse than to guess which line is right.
157
+ */
158
+ export function parseSha256Sums(text) {
159
+ const sums = new Map();
160
+ for (const raw of String(text || '').split('\n')) {
161
+ const line = raw.replace(/\r$/, '');
162
+ const m = line.match(/^([0-9a-fA-F]{64}) [ *](.+)$/);
163
+ if (!m) continue;
164
+ const [, hex, name] = m;
165
+ const sum = hex.toLowerCase();
166
+ if (sums.has(name) && sums.get(name) !== sum) sums.set(name, null);
167
+ else sums.set(name, sum);
168
+ }
169
+ return sums;
170
+ }
171
+
172
+ /** Do two SHA-256 digests (hex) name the same bytes? */
173
+ export function digestsMatch(expected, actual) {
174
+ const a = String(expected || '').toLowerCase();
175
+ const b = String(actual || '').toLowerCase();
176
+ return /^[0-9a-f]{64}$/.test(a) && a === b;
177
+ }
178
+
179
+ /**
180
+ * The running app bundle. The Mac app says where it is (SIX_DEGREES_APP, from
181
+ * Electron's own executable path, desktop/main.mjs). A copy that doesn't say is
182
+ * worked out from its server folder: <bundle>/Contents/Resources/server for the
183
+ * Electron app, …/Resources/app for the classic launcher.
184
+ */
185
+ export function runningBundle({ app, root } = {}) {
186
+ const absolute = (p) => (typeof p === 'string' && path.isAbsolute(p) ? path.resolve(p) : null);
187
+ const declared = absolute(app);
188
+ if (declared) return declared;
189
+ const r = absolute(root);
190
+ const m = r && r.match(/^(.+\.app)\/Contents\/Resources\/(?:server|app)$/);
191
+ return m ? m[1] : null;
192
+ }
193
+
194
+ /**
195
+ * Can this copy replace itself where it is? null when it can, or the reason it
196
+ * can't, in words for the Settings page. The page then offers the Terminal
197
+ * line, saying what it would do here (terminalFallback), or says what to do
198
+ * where the line wouldn't help.
199
+ */
200
+ export function bundleRefusal(bundle, { exists = true, parentWritable = true, ownerUid, uid } = {}) {
201
+ if (!bundle || !exists) {
202
+ return { code: 'unknown-location', message: "This copy can't tell where it is installed, so it can't replace itself." };
203
+ }
204
+ if (!/\.app$/.test(bundle)) {
205
+ return { code: 'not-app', message: "This copy isn't running from an app in a folder, so it can't replace itself." };
206
+ }
207
+ if (bundle.startsWith('/Volumes/')) {
208
+ return {
209
+ code: 'disk-image',
210
+ message: 'Six Degrees is running from its disk image (or another drive). Drag it to your Applications folder, open it from there, then update.',
211
+ };
212
+ }
213
+ if (bundle.includes('/AppTranslocation/')) {
214
+ return {
215
+ code: 'translocated',
216
+ message: "macOS is running this copy from a temporary, read-only place, because it was opened where it was downloaded. Move Six Degrees to your Applications folder, open it from there, then update.",
217
+ };
218
+ }
219
+ if (!parentWritable) {
220
+ return {
221
+ code: 'not-writable',
222
+ message: `Your user can't change ${path.dirname(bundle)}, so Six Degrees can't replace itself there.`,
223
+ };
224
+ }
225
+ if (Number.isInteger(ownerUid) && Number.isInteger(uid) && ownerUid !== uid) {
226
+ return {
227
+ code: 'not-owner',
228
+ message: 'Six Degrees was installed by another user of this Mac, so only they can replace it. Ask them to update it (Settings → Updates, in their account).',
229
+ };
230
+ }
231
+ return null;
232
+ }
233
+
234
+ /**
235
+ * The data this copy uses must be data a reopened copy will use too.
236
+ *
237
+ * The data folder must not be inside the app. It can be: a relative --data-dir
238
+ * resolved against the server's working folder, which is inside the bundle.
239
+ * Replacing the app would then carry the network away with the old version,
240
+ * and the Terminal line (install.sh deletes the old app) would delete it, so
241
+ * neither is offered: the network has to be moved out first.
242
+ *
243
+ * And SIX_DEGREES_DB, which puts the database somewhere of its own, can't be
244
+ * passed on: `open` starts the new version with no environment, and it has no
245
+ * option for it. It would open another database.
246
+ */
247
+ export function dataRefusal({ dataDir, bundle, dbFile = null }) {
248
+ if (dataDir && bundle) {
249
+ const dir = path.resolve(dataDir);
250
+ if (dir === bundle || dir.startsWith(`${bundle}/`)) {
251
+ return {
252
+ code: 'data-inside-app',
253
+ message: `Your network is stored inside the app itself (${dir}), so replacing the app would delete it, whether from here or with the Terminal line. Quit Six Degrees, move that folder out of the app (to your home folder, say), open Six Degrees again with --data-dir and the folder's new place, then update.`,
254
+ };
255
+ }
256
+ }
257
+ if (dbFile && dataDir && path.resolve(dbFile) !== path.join(path.resolve(dataDir), 'six-degrees.sqlite')) {
258
+ return {
259
+ code: 'database-elsewhere',
260
+ message: `This copy was started with its database outside its data folder (SIX_DEGREES_DB), which a reopened app can't be told, so it won't replace itself. Replace it by hand and start it again the same way.`,
261
+ };
262
+ }
263
+ return null;
264
+ }
265
+
266
+ /** Where install.sh (the Terminal line) puts the app: /Applications, or ~/Applications when this user can't change /Applications. */
267
+ export function installerTarget({ applicationsWritable = true, home = '' } = {}) {
268
+ return applicationsWritable
269
+ ? path.join('/Applications', APP_BUNDLE_NAME)
270
+ : path.join(home, 'Applications', APP_BUNDLE_NAME);
271
+ }
272
+
273
+ /**
274
+ * What the Terminal line (install.sh) would do for this copy, so the page can
275
+ * say it accurately, or null when it mustn't be offered at all:
276
+ * { mode: 'replace' } it stops this copy, puts the new version
277
+ * in its place and opens it
278
+ * { mode: 'elsewhere', installsTo } it installs at installsTo and leaves this
279
+ * copy alone. So quit this one first:
280
+ * otherwise the new one finds it running,
281
+ * hands over to it and closes (one copy at a
282
+ * time, desktop/main.mjs)
283
+ * null the line would delete a network kept inside
284
+ * the app, can't delete another user's app,
285
+ * or can't carry a database kept elsewhere
286
+ * `dataDir`, when this copy uses a data folder of its own: install.sh opens the
287
+ * new version without it, on the usual one.
288
+ */
289
+ export function terminalFallback({ bundle, refusalCode = null, installsTo, dataDir = null }) {
290
+ if (refusalCode === 'data-inside-app' || refusalCode === 'database-elsewhere') return null;
291
+ if (refusalCode === 'not-owner' && bundle === installsTo) return null;
292
+ const own = dataDir ? { dataDir } : {};
293
+ if (bundle && bundle === installsTo) return { mode: 'replace', ...own };
294
+ return { mode: 'elsewhere', installsTo, ...own };
295
+ }
296
+
297
+ /** Where the new version waits beside the running one: same folder, so moving it in is a rename. */
298
+ export function stagingPath(bundle) {
299
+ return path.join(path.dirname(bundle), `.${path.basename(bundle)}.incoming`);
300
+ }
301
+
302
+ /**
303
+ * What the new version is opened with. `open` starts an app with neither this
304
+ * process's environment nor its arguments, so the data folder this copy uses
305
+ * is always passed on as --data-dir, the default one too. A copy started with
306
+ * --data-dir, or with SIX_DEGREES_HOME (a shell, or launchctl setenv), comes
307
+ * back on the same data, never on whatever a plain launch would choose.
308
+ * --after-update opens Settings, where the outcome is shown.
309
+ */
310
+ export function relaunchArgs({ dataDir } = {}) {
311
+ const args = ['--after-update'];
312
+ if (dataDir) args.push('--data-dir', path.resolve(dataDir));
313
+ return args;
314
+ }
315
+
316
+ /**
317
+ * The helper's command line (scripts/apply-update.sh documents each one).
318
+ * Everything after "--" is handed to the new app when it is opened.
319
+ */
320
+ export function helperArgs({
321
+ target, staged, keepDir, statusFile, from, to, pids = [], waitSeconds = 30, logFile, work, relaunch = [],
322
+ confirmFile, confirmWaitSeconds = 600,
323
+ }) {
324
+ const args = [
325
+ '--target', target,
326
+ '--staged', staged,
327
+ '--keep', keepDir,
328
+ '--status', statusFile,
329
+ '--from', from,
330
+ '--to', to,
331
+ '--wait', String(waitSeconds),
332
+ ];
333
+ for (const pid of pids) {
334
+ // 1 is launchd: a server whose app has already gone is re-parented to it.
335
+ if (Number.isInteger(pid) && pid > 1) args.push('--pid', String(pid));
336
+ }
337
+ if (confirmFile) args.push('--confirm', confirmFile, '--confirm-wait', String(confirmWaitSeconds));
338
+ if (logFile) args.push('--log', logFile);
339
+ if (work) args.push('--work', work);
340
+ return [...args, '--', ...relaunch];
341
+ }
342
+
343
+ /**
344
+ * Other users' processes running this app, from `ps -axo uid=,pid=,comm=`
345
+ * (comm is the program as it was started: the full path, for an app). This
346
+ * user can't stop them, and the helper can't even see them (lsof shows only
347
+ * this user's processes), so an app another user has open must not be swapped
348
+ * from under them. Their pids; `bundles` is the app's path, and its real path
349
+ * when a link leads to it.
350
+ */
351
+ export function foreignAppProcesses(psText, { bundles = [], uid }) {
352
+ const insides = bundles.filter(Boolean).map((b) => `${b}/Contents/`);
353
+ if (!insides.length || !Number.isInteger(uid)) return [];
354
+ const found = [];
355
+ for (const line of String(psText || '').split('\n')) {
356
+ const m = line.match(/^\s*(\d+)\s+(\d+)\s+(.+)$/);
357
+ if (!m || Number(m[1]) === uid) continue;
358
+ if (insides.some((inside) => m[3].startsWith(inside))) found.push(Number(m[2]));
359
+ }
360
+ return found;
361
+ }
362
+
363
+ /**
364
+ * What an update that was cut off (the server or the helper stopped half-way)
365
+ * can leave beside the app, by name: the old version moved aside
366
+ * (.<app>.previous-<pid>[-n]), a new version taken out again
367
+ * (.<app>.failed-<pid>[-n]) and the staged copy (.<app>.incoming). Only this
368
+ * app's own names, never anything else in the folder. `pid` is the helper's,
369
+ * to tell whether it still runs.
370
+ */
371
+ export function leftoversBeside(names, bundleBase) {
372
+ const prefix = `.${bundleBase}.`;
373
+ const found = [];
374
+ for (const name of names) {
375
+ if (typeof name !== 'string' || !name.startsWith(prefix)) continue;
376
+ const rest = name.slice(prefix.length);
377
+ if (rest === 'incoming') {
378
+ found.push({ name, kind: 'incoming', pid: null });
379
+ continue;
380
+ }
381
+ const m = rest.match(/^(previous|failed)-(\d+)(?:-\d+)?$/);
382
+ if (m) found.push({ name, kind: m[1], pid: Number(m[2]) });
383
+ }
384
+ return found;
385
+ }
386
+
387
+ /** Is this macOS version at least `need`? */
388
+ export function versionAtLeast(have, need) {
389
+ return compareVersions(have, need) >= 0;
390
+ }
391
+
392
+ const CPU = { 0x01000007: 'x64', 0x0100000c: 'arm64' };
393
+
394
+ /**
395
+ * Which chips a Mach-O executable runs on, from its first bytes: 'arm64',
396
+ * 'x64', both (a universal binary) or neither (not a Mach-O, e.g. the classic
397
+ * app's bash launcher). Read here rather than with `lipo`, which on a Mac
398
+ * without the developer tools is a stub that asks to install them.
399
+ */
400
+ export function machoArchs(buf) {
401
+ const found = new Set();
402
+ if (!buf || buf.length < 8) return found;
403
+ const add = (cputype) => { if (CPU[cputype >>> 0]) found.add(CPU[cputype >>> 0]); };
404
+ const le = buf.readUInt32LE(0);
405
+ if (le === 0xfeedfacf || le === 0xfeedface) { // a thin binary, stored little-endian
406
+ add(buf.readUInt32LE(4));
407
+ return found;
408
+ }
409
+ const be = buf.readUInt32BE(0);
410
+ if (be === 0xcafebabe || be === 0xcafebabf) { // universal: a big-endian table of slices
411
+ const count = buf.readUInt32BE(4);
412
+ const size = be === 0xcafebabf ? 32 : 20;
413
+ // A Java class file starts with the same four bytes; its "count" is a
414
+ // version number in the dozens. No universal binary has that many slices.
415
+ if (count < 1 || count > 16) return found;
416
+ for (let i = 0; i < count; i++) {
417
+ const at = 8 + i * size;
418
+ if (at + 4 > buf.length) break;
419
+ add(buf.readUInt32BE(at));
420
+ }
421
+ }
422
+ return found;
423
+ }
424
+
425
+ /**
426
+ * What to say about the last update, on the next launch. `status` is the file
427
+ * the server and scripts/apply-update.sh write (outcome, from, to, at, reason,
428
+ * previous, log). null when there is nothing to say: no update, one more than
429
+ * REPORT_DAYS ago, or one this copy has moved past. `previous` is where the old
430
+ * version went: a zip of it after an update that worked, the old app itself
431
+ * when it couldn't be put back.
432
+ *
433
+ * The running version decides as much as the outcome does. A copy already at
434
+ * the version a failed update was for got there another way (the Terminal line,
435
+ * most likely), and a copy past the version an update installed was updated
436
+ * again since: either report would be old news, and wrong.
437
+ */
438
+ export function lastUpdateReport(status, { runningVersion, now = Date.now(), maxAgeDays = REPORT_DAYS } = {}) {
439
+ if (!status || typeof status !== 'object' || typeof status.to !== 'string') return null;
440
+ const at = Date.parse(status.at);
441
+ if (!Number.isFinite(at) || now - at > maxAgeDays * 86400000) return null;
442
+ const to = status.to;
443
+ const reason = typeof status.reason === 'string' && status.reason.trim() ? status.reason.trim().replace(/\.$/, '') : null;
444
+ const base = {
445
+ at: new Date(at).toISOString(),
446
+ from: status.from || null,
447
+ to,
448
+ previous: typeof status.previous === 'string' ? status.previous : null,
449
+ };
450
+ // This copy against the version the update was for: <0 older, 0 the same, >0 newer.
451
+ const cmp = runningVersion ? compareVersions(runningVersion, to) : null;
452
+ const didnt = `The update to ${to} didn't finish${reason ? `: ${reason}` : ''}.`;
453
+
454
+ switch (status.outcome) {
455
+ case 'installed':
456
+ case 'started':
457
+ // "started": the server handed over and the helper never wrote its answer.
458
+ // The version that is running says how it went.
459
+ if (cmp === 0) return { ...base, tone: 'ok', text: `Updated to ${to}.` };
460
+ if (cmp > 0) return null;
461
+ if (status.outcome === 'installed') {
462
+ return {
463
+ ...base,
464
+ tone: 'bad',
465
+ text: `Version ${to} was installed, but this copy is ${runningVersion}. If you have two copies of Six Degrees, open the one in Applications.`,
466
+ };
467
+ }
468
+ return {
469
+ ...base,
470
+ tone: 'bad',
471
+ text: `The update to ${to} didn't finish, and it didn't say why.${status.log ? ` Its log is ${status.log}.` : ''}`,
472
+ };
473
+ case 'not-applied':
474
+ if (cmp !== null && cmp >= 0) return null;
475
+ return { ...base, tone: 'bad', text: `${didnt} Nothing was changed.` };
476
+ case 'rolled-back':
477
+ if (cmp !== null && cmp >= 0) return null;
478
+ return { ...base, tone: 'bad', text: `${didnt} Your previous version was put back.` };
479
+ case 'failed':
480
+ // The one outcome that needs a hand: the old version was moved aside and
481
+ // couldn't be moved back. It is whole, just renamed, and the name starts
482
+ // with a dot, which Finder hides.
483
+ if (cmp !== null && cmp >= 0) return null;
484
+ return {
485
+ ...base,
486
+ tone: 'bad',
487
+ text: `${didnt}${status.previous
488
+ ? ` Your previous version is safe, in a hidden folder: ${status.previous}. To use it again, rename it to ${APP_BUNDLE_NAME} (in Finder, Shift-Command-. shows hidden files). Or install the newest version: Check for updates, below.`
489
+ : ''}`,
490
+ };
491
+ default:
492
+ return null;
493
+ }
494
+ }
@@ -1,7 +1,8 @@
1
1
  import { NextResponse } from 'next/server';
2
- import { isDestructive, gateDecision, isCrossSiteWrite } from './lib/gate';
2
+ import { requestRefusal } from './lib/gate';
3
3
 
4
- // Two separate protections.
4
+ // Two separate protections, decided in lib/gate.js requestRefusal (covered by
5
+ // tests/gate.test.mjs).
5
6
  //
6
7
  // 1. Cross-site writes, on EVERY mutating request. Binding to 127.0.0.1 stops
7
8
  // other machines but not the browser on this one — a page on any website can
@@ -9,40 +10,36 @@ import { isDestructive, gateDecision, isCrossSiteWrite } from './lib/gate';
9
10
  // preflight. The response is hidden from that page, but the write lands, and
10
11
  // data written this way is later rendered by the app. Sec-Fetch-Site is set
11
12
  // by the browser and cannot be forged from script; curl and the scraper send
12
- // no such header and are unaffected.
13
+ // no such header and are unaffected. Before that, a request addressed to some
14
+ // other name (DNS rebinding) is refused, reads included: lib/gate.js isRebound.
13
15
  //
14
- // 2. The four routes that irreversibly destroy or rewrite data. Allowed when the
16
+ // 2. The routes that destroy, replace or hand over data, start processes, or
17
+ // change the code (DESTRUCTIVE_ROUTES in lib/gate.js). Allowed when the
15
18
  // server is bound to loopback, since the operator can open the SQLite file
16
19
  // directly anyway; otherwise ADMIN_TOKEN is required and they fail closed.
17
- // The rule lives in lib/gate.js and is covered by tests/gate.test.mjs.
18
20
 
19
21
  export function middleware(request) {
20
- const { pathname } = request.nextUrl;
21
-
22
- if (isCrossSiteWrite({
22
+ const refused = requestRefusal({
23
23
  method: request.method,
24
- secFetchSite: request.headers.get('sec-fetch-site'),
25
- origin: request.headers.get('origin'),
26
- host: request.headers.get('host'),
27
- })) {
28
- return Response.json(
29
- { error: 'Cross-site requests are not accepted. This app only answers to pages it serves.' },
30
- { status: 403 }
31
- );
32
- }
33
-
34
- if (!isDestructive(pathname)) return NextResponse.next();
35
-
36
- const decision = gateDecision({
37
- bind: process.env.SIX_DEGREES_BIND || process.env.HOSTNAME,
38
- token: process.env.ADMIN_TOKEN,
39
- bearer: (request.headers.get('authorization') || '').replace(/^Bearer\s+/i, ''),
24
+ pathname: request.nextUrl.pathname,
25
+ headers: request.headers,
26
+ env: process.env,
40
27
  });
41
-
42
- if (decision.allow) return NextResponse.next();
43
- return Response.json({ error: decision.reason }, { status: decision.status });
28
+ if (refused) return Response.json({ error: refused.error }, { status: refused.status });
29
+ return NextResponse.next();
44
30
  }
45
31
 
46
32
  export const config = {
47
- matcher: ['/api/:path*'],
33
+ // /avatars serves the photos of the people in the network, so it gets the
34
+ // same rebinding check as the API.
35
+ //
36
+ // Every /api route but one: POST /api/data/import (Settings → Your data). Next
37
+ // copies a request's body into memory before it runs middleware, the whole of
38
+ // it up to experimental.proxyClientMaxBodySize, even when middleware then
39
+ // refuses it, and an import is one file of up to 256 MB. So that route is left
40
+ // out here, keeps Next's 10 MB default for everyone else, and makes the same
41
+ // checks itself (requestRefusal) before it reads a byte, then writes the body
42
+ // to disk as it arrives. The pattern leaves out that exact path and nothing
43
+ // else; tests/gate.test.mjs pins it with Next's own matcher.
44
+ matcher: ['/api', '/api/((?!data/import$).*)', '/avatars/:path*'],
48
45
  };
@@ -13,14 +13,22 @@ const nextConfig = {
13
13
  // directory for the scraper), so anything sitting in it rides along unless it
14
14
  // is named here. `.git` above all: inside the Mac app it made the installed
15
15
  // copy look like a checkout, so its Updates panel would have tried to
16
- // `git pull` into the app bundle. Logs carry local paths and are never needed.
16
+ // `git pull` into the app bundle. In a git worktree `.git` is a file, not a
17
+ // folder, which '.git/**' doesn't match, so both are named. Logs carry local
18
+ // paths and are never needed.
17
19
  //
18
20
  // The desktop shell (desktop/) and Electron itself are packed around the
19
21
  // server, never inside it: Electron alone is ~250 MB.
22
+ //
23
+ // scripts/pin-python-packages.mjs is a developer's tool that asks PyPI
24
+ // about packages; nothing the app runs uses it, so it doesn't ship.
20
25
  outputFileTracingExcludes: {
21
26
  '*': ['dist/*.app/**', 'dist/*.dmg', 'dist/staging/**', 'dist/electron-stage/**', 'docs/**', 'tests/**',
22
- '.git/**', '*.log', 'scripts/dmg/**', 'desktop/**',
23
- 'node_modules/electron/**', 'node_modules/@electron/**'],
27
+ '.git', '.git/**', '*.log', 'scripts/dmg/**', 'scripts/pin-python-packages.mjs', 'desktop/**',
28
+ 'node_modules/electron/**', 'node_modules/@electron/**',
29
+ // The download website (site/, published by pages.yml from the repo) is
30
+ // never read by the app; tracing swept its 17 MB of videos in.
31
+ 'site/**'],
24
32
  },
25
33
  // Emits .next/standalone with a server and only the dependencies actually
26
34
  // reached, so the published package can run without node_modules being
@@ -30,6 +38,14 @@ const nextConfig = {
30
38
  // node:sqlite is a built-in, but bundling would rewrite the import; leave it
31
39
  // to be required at runtime.
32
40
  serverExternalPackages: ['node:sqlite'],
41
+
42
+ // experimental.proxyClientMaxBodySize stays at Next's 10 MB on purpose. Next
43
+ // copies the body of every request middleware.js sees into memory, up to that
44
+ // size, before middleware decides anything, so raising it for the one big
45
+ // upload (an import) would let any request, a refused cross-site one
46
+ // included, make the server hold that much. The import route is left out of
47
+ // middleware.js instead, and writes its body to disk as it arrives
48
+ // (docs/brain/ENDPOINTS.md, "Request bodies over 10 MB").
33
49
  };
34
50
 
35
51
  export default nextConfig;
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "six-degrees",
3
- "version": "0.2.1",
3
+ "version": "0.3.0",
4
4
  "lockfileVersion": 3,
5
5
  "requires": true,
6
6
  "packages": {
7
7
  "": {
8
8
  "name": "six-degrees",
9
- "version": "0.2.1",
9
+ "version": "0.3.0",
10
10
  "license": "MIT",
11
11
  "os": [
12
12
  "darwin",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "six-degrees",
3
- "version": "0.2.1",
3
+ "version": "0.3.0",
4
4
  "description": "Map your professional network as a galaxy — leverage tiers, bridges into new circles, and the shortest path to anyone. Runs locally on your own data.",
5
5
  "license": "MIT",
6
6
  "author": "Blake Burford",
@@ -43,7 +43,6 @@
43
43
  "scripts/scrape.py",
44
44
  "scripts/image_store.py",
45
45
  "scripts/requirements.txt",
46
- "scripts/score_new_connections.sql",
47
46
  "README.md",
48
47
  "LICENSE",
49
48
  "CHANGELOG.md",