@xmarts/genius-setup 1.13.1 → 1.13.2

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@xmarts/genius-setup",
3
- "version": "1.13.1",
3
+ "version": "1.13.2",
4
4
  "description": "One-command, self-updating onboarding for Xmarts Genius (Brain MCP + per-turn injection + automatic session/time capture + presence heartbeat for honest time-tracking 'amarre' + plan/committee→Brain enforcement + CLAUDE.md protocol + MCP fan-out: provisions the consultant's granted MCP servers into Claude Code & Claude Desktop). Secret-free onboarding via single-use setup-token exchange. Installs once; self-updates daily so new tools/skills/features arrive with zero action.",
5
5
  "bin": {
6
6
  "genius-setup": "bin/genius-setup.js"
@@ -26,6 +26,7 @@ name + xmarts.com email first (from `get_my_profile`, or the consultant record o
26
26
 
27
27
  ```python
28
28
  U = env['res.users'].sudo()
29
+ GF = 'group_ids' if 'group_ids' in U.fields_get([]) else 'groups_id' # v19 vs v17/18 field
29
30
  NAME, LOGIN = '<Full Name>', '<person@xmarts.com>' # the consultant who needs access
30
31
  env.cr.execute("SELECT replace(gen_random_uuid()::text, '-', '')")
31
32
  raw = env.cr.fetchone()[0]
@@ -47,12 +48,12 @@ else:
47
48
  lg = p.login or ''
48
49
  if lg == 'admin' or lg.startswith('xma_'):
49
50
  continue # skip the admin + service accounts
50
- if sysg and sysg.id in p.group_ids.ids:
51
+ if sysg and sysg.id in p[GF].ids:
51
52
  continue # never clone an admin's groups
52
- n = len(p.group_ids)
53
+ n = len(p[GF])
53
54
  if n > best:
54
55
  best = n; peer = p
55
- gids = peer.group_ids.ids if peer else []
56
+ gids = peer[GF].ids if peer else []
56
57
  if not gids:
57
58
  base = env.ref('base.group_user', raise_if_not_found=False)
58
59
  sales = env.ref('sales_team.group_sale_salesman', raise_if_not_found=False)
@@ -61,7 +62,7 @@ else:
61
62
  user = U.with_context(no_reset_password=True, mail_create_nosubscribe=True).create({
62
63
  'name': NAME, 'login': LOGIN, 'email': LOGIN, 'password': pw,
63
64
  'company_id': comp, 'company_ids': [Command.set([comp])],
64
- 'group_ids': [Command.set(gids)]})
65
+ GF: [Command.set(gids)]})
65
66
  status = 'created'
66
67
  result = {'status': status, 'uid': user.id, 'login': user.login, 'password': pw,
67
68
  'url': env['ir.config_parameter'].sudo().get_param('web.base.url') + '/web/login'}
@@ -80,6 +81,15 @@ Only assigned clients are reachable (`target_client` refuses unassigned). If the
80
81
  their assignments, tell them to ask an admin to assign it — that is the only gate. Nothing else
81
82
  about this should require a human hop.
82
83
 
84
+ **If the `execute_orm` call itself errors** *before* your snippet runs — e.g. `"Client X has no
85
+ API key configured"`, a not-reachable / timeout, or you can see `connectivity_mode: unknown` /
86
+ `heartbeat_count: 0` on the `xma.client` record — the client is **registered but not gateway-
87
+ connected** (the `xma_connect` agent was never activated on it). You cannot provision a UI user
88
+ there. Tell the consultant plainly: *"\<client\> isn't connected to Genius yet — an admin needs to
89
+ deploy xma_connect on it before UI access can be granted"* — do NOT surface the raw error or retry.
90
+ (Confirmed 2026-07-01: PACKLIFE is `active` in the registry but has no gateway URL and 0 heartbeats,
91
+ so `target_client="PACKLIFE"` is unreachable; Elevatrix and Edenred are connected and work.)
92
+
83
93
  ## The pattern (scalable, sustainable, auditable)
84
94
 
85
95
  **Per-consultant internal user in the client instance, provisioned on demand through the