@aspalagin/openclaw-max 0.8.0 → 0.8.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.
@@ -5,7 +5,7 @@
5
5
  import { resolveToolsBySender } from 'openclaw/plugin-sdk/channel-policy';
6
6
  import { PAIRING_APPROVED_MESSAGE } from 'openclaw/plugin-sdk/channel-status';
7
7
  import { DEFAULT_ACCOUNT_ID, formatPairingApproveHint } from 'openclaw/plugin-sdk/core';
8
- import { resolveMaxAccount } from './accounts.js';
8
+ import { readMaxAccount, resolveMaxAccount } from './accounts.js';
9
9
  import { sendMaxMessage } from './send.js';
10
10
  // ── MAX group policy helpers ──
11
11
  // These mirror resolveChannelGroupRequireMention/resolveChannelGroupToolsPolicy
@@ -69,18 +69,30 @@ function resolveMaxGroupToolPolicy(params) {
69
69
  return defaultConfig.tools;
70
70
  return undefined;
71
71
  }
72
+ /**
73
+ * Account config for the security adapter. Since OpenClaw 2026.9.7 `security audit`
74
+ * (and doctor) hand the adapter the read-only `config.inspectAccount` status, which
75
+ * carries no `config` — re-read the account section from cfg (side-effect free) in that case.
76
+ */
77
+ function resolveMaxPolicyAccountConfig(cfg, accountId, account) {
78
+ const config = account?.config;
79
+ if (config && typeof config === 'object')
80
+ return config;
81
+ return readMaxAccount({ cfg, accountId }).config;
82
+ }
72
83
  /** DM policy (default pairing) and warnings for open group policy. */
73
84
  export const maxSecurityAdapter = {
74
85
  resolveDmPolicy: ({ cfg, accountId, account }) => {
75
- const resolvedAccountId = accountId ?? account.accountId ?? DEFAULT_ACCOUNT_ID;
86
+ const resolvedAccountId = accountId ?? account?.accountId ?? DEFAULT_ACCOUNT_ID;
87
+ const config = resolveMaxPolicyAccountConfig(cfg, resolvedAccountId, account);
76
88
  const maxSection = cfg.channels?.max;
77
89
  const useAccountPath = Boolean(maxSection?.accounts?.[resolvedAccountId]);
78
90
  const basePath = useAccountPath
79
91
  ? `channels.max.accounts.${resolvedAccountId}.`
80
92
  : 'channels.max.';
81
93
  return {
82
- policy: account.config.dmPolicy ?? 'pairing',
83
- allowFrom: account.config.allowFrom ?? [],
94
+ policy: config.dmPolicy ?? 'pairing',
95
+ allowFrom: config.allowFrom ?? [],
84
96
  policyPath: `${basePath}dmPolicy`,
85
97
  allowFromPath: basePath,
86
98
  approveHint: formatPairingApproveHint('max'),
@@ -88,12 +100,13 @@ export const maxSecurityAdapter = {
88
100
  };
89
101
  },
90
102
  collectWarnings: ({ account, cfg }) => {
103
+ const config = resolveMaxPolicyAccountConfig(cfg, account?.accountId ?? DEFAULT_ACCOUNT_ID, account);
91
104
  const defaultGroupPolicy = cfg.channels?.defaults?.groupPolicy;
92
- const groupPolicy = account.config.groupPolicy ?? defaultGroupPolicy ?? 'allowlist';
105
+ const groupPolicy = config.groupPolicy ?? defaultGroupPolicy ?? 'allowlist';
93
106
  if (groupPolicy !== 'open') {
94
107
  return [];
95
108
  }
96
- const groupAllowlistConfigured = account.config.groups && Object.keys(account.config.groups).length > 0;
109
+ const groupAllowlistConfigured = config.groups && Object.keys(config.groups).length > 0;
97
110
  if (groupAllowlistConfigured) {
98
111
  return [
99
112
  `- MAX groups: groupPolicy="open" allows any member in allowed groups to trigger (mention-gated). Set channels.max.groupPolicy="allowlist" + channels.max.groupAllowFrom to restrict senders.`,
@@ -2,7 +2,7 @@
2
2
  "id": "openclaw-max",
3
3
  "name": "MAX",
4
4
  "description": "MAX messenger (max.ru) channel for OpenClaw: private and group chats over webhook or long polling; media, voice messages with transcription and voice replies; inline keyboards and command menus; message edits and pins; several bot accounts",
5
- "version": "0.8.0",
5
+ "version": "0.8.1",
6
6
  "categories": [
7
7
  "channels"
8
8
  ],
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aspalagin/openclaw-max",
3
- "version": "0.8.0",
3
+ "version": "0.8.1",
4
4
  "description": "MAX messenger (max.ru) channel for OpenClaw: private and group chats over webhook or long polling; media, voice messages with transcription and voice replies; inline keyboards and command menus; message edits and pins; several bot accounts",
5
5
  "keywords": [
6
6
  "openclaw",
@@ -10,7 +10,7 @@ import { PAIRING_APPROVED_MESSAGE } from 'openclaw/plugin-sdk/channel-status';
10
10
  import type { OpenClawConfig } from 'openclaw/plugin-sdk/core';
11
11
  import { DEFAULT_ACCOUNT_ID, formatPairingApproveHint } from 'openclaw/plugin-sdk/core';
12
12
 
13
- import { type ResolvedMaxAccount, resolveMaxAccount } from './accounts.js';
13
+ import { readMaxAccount, type ResolvedMaxAccount, resolveMaxAccount } from './accounts.js';
14
14
  import { sendMaxMessage } from './send.js';
15
15
 
16
16
  type MaxChannelPlugin = ChannelPlugin<ResolvedMaxAccount>;
@@ -109,10 +109,26 @@ function resolveMaxGroupToolPolicy(params: {
109
109
  return undefined;
110
110
  }
111
111
 
112
+ /**
113
+ * Account config for the security adapter. Since OpenClaw 2026.9.7 `security audit`
114
+ * (and doctor) hand the adapter the read-only `config.inspectAccount` status, which
115
+ * carries no `config` — re-read the account section from cfg (side-effect free) in that case.
116
+ */
117
+ function resolveMaxPolicyAccountConfig(
118
+ cfg: OpenClawConfig,
119
+ accountId: string,
120
+ account: Pick<ResolvedMaxAccount, 'config'> | { config?: undefined } | null | undefined,
121
+ ): ResolvedMaxAccount['config'] {
122
+ const config = (account as { config?: ResolvedMaxAccount['config'] } | null | undefined)?.config;
123
+ if (config && typeof config === 'object') return config;
124
+ return readMaxAccount({ cfg, accountId }).config;
125
+ }
126
+
112
127
  /** DM policy (default pairing) and warnings for open group policy. */
113
128
  export const maxSecurityAdapter: NonNullable<MaxChannelPlugin['security']> = {
114
129
  resolveDmPolicy: ({ cfg, accountId, account }) => {
115
- const resolvedAccountId = accountId ?? account.accountId ?? DEFAULT_ACCOUNT_ID;
130
+ const resolvedAccountId = accountId ?? account?.accountId ?? DEFAULT_ACCOUNT_ID;
131
+ const config = resolveMaxPolicyAccountConfig(cfg, resolvedAccountId, account);
116
132
  const maxSection = (cfg.channels as Record<string, unknown>)?.max as
117
133
  Record<string, unknown> | undefined;
118
134
  const useAccountPath = Boolean(
@@ -122,8 +138,8 @@ export const maxSecurityAdapter: NonNullable<MaxChannelPlugin['security']> = {
122
138
  ? `channels.max.accounts.${resolvedAccountId}.`
123
139
  : 'channels.max.';
124
140
  return {
125
- policy: account.config.dmPolicy ?? 'pairing',
126
- allowFrom: account.config.allowFrom ?? [],
141
+ policy: config.dmPolicy ?? 'pairing',
142
+ allowFrom: config.allowFrom ?? [],
127
143
  policyPath: `${basePath}dmPolicy`,
128
144
  allowFromPath: basePath,
129
145
  approveHint: formatPairingApproveHint('max'),
@@ -131,13 +147,17 @@ export const maxSecurityAdapter: NonNullable<MaxChannelPlugin['security']> = {
131
147
  };
132
148
  },
133
149
  collectWarnings: ({ account, cfg }) => {
150
+ const config = resolveMaxPolicyAccountConfig(
151
+ cfg,
152
+ account?.accountId ?? DEFAULT_ACCOUNT_ID,
153
+ account,
154
+ );
134
155
  const defaultGroupPolicy = cfg.channels?.defaults?.groupPolicy;
135
- const groupPolicy = account.config.groupPolicy ?? defaultGroupPolicy ?? 'allowlist';
156
+ const groupPolicy = config.groupPolicy ?? defaultGroupPolicy ?? 'allowlist';
136
157
  if (groupPolicy !== 'open') {
137
158
  return [];
138
159
  }
139
- const groupAllowlistConfigured =
140
- account.config.groups && Object.keys(account.config.groups).length > 0;
160
+ const groupAllowlistConfigured = config.groups && Object.keys(config.groups).length > 0;
141
161
  if (groupAllowlistConfigured) {
142
162
  return [
143
163
  `- MAX groups: groupPolicy="open" allows any member in allowed groups to trigger (mention-gated). Set channels.max.groupPolicy="allowlist" + channels.max.groupAllowFrom to restrict senders.`,