conduct-cli 0.4.22__tar.gz → 0.4.24__tar.gz
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.
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/PKG-INFO +18 -15
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/README.md +17 -14
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/pyproject.toml +1 -1
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli/guard.py +82 -1
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli/guardmcp.py +2 -1
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli.egg-info/PKG-INFO +18 -15
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/setup.cfg +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/setup.py +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli/__init__.py +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli/api.py +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli/main.py +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli.egg-info/SOURCES.txt +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli.egg-info/dependency_links.txt +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli.egg-info/entry_points.txt +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli.egg-info/requires.txt +0 -0
- {conduct_cli-0.4.22 → conduct_cli-0.4.24}/src/conduct_cli.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: conduct-cli
|
|
3
|
-
Version: 0.4.
|
|
3
|
+
Version: 0.4.24
|
|
4
4
|
Summary: CLI for Conduct AI — install agents, manage projects, run tests
|
|
5
5
|
Author-email: Conduct AI <hello@conductai.ai>
|
|
6
6
|
License: MIT
|
|
@@ -110,13 +110,14 @@ ConductGuard is AI tool fleet management — your security team sets policies on
|
|
|
110
110
|
### How it works
|
|
111
111
|
|
|
112
112
|
```
|
|
113
|
-
|
|
114
|
-
└─
|
|
113
|
+
Admin configures policies and budgets in the Guard dashboard
|
|
114
|
+
└─ developers are workspace members automatically — no invite step needed
|
|
115
115
|
|
|
116
|
-
Developer runs: conduct guard
|
|
117
|
-
├─
|
|
118
|
-
├─ writes PreToolUse hook → ~/.
|
|
119
|
-
|
|
116
|
+
Developer runs: conduct guard sync
|
|
117
|
+
├─ pulls latest policy to ~/.conductguard/policy.json
|
|
118
|
+
├─ writes PreToolUse hook → ~/.conductguard/hook.py
|
|
119
|
+
├─ registers hook → ~/.claude/settings.json
|
|
120
|
+
└─ registers conductguard-mcp → ~/.claude/settings.json (mcpServers) + Codex
|
|
120
121
|
|
|
121
122
|
Every Claude Code tool call:
|
|
122
123
|
├─ PreToolUse hook fires (hook.py) → checks policy → block / warn / audit
|
|
@@ -126,10 +127,13 @@ Every Claude Code tool call:
|
|
|
126
127
|
### Developer setup
|
|
127
128
|
|
|
128
129
|
```bash
|
|
129
|
-
|
|
130
|
-
|
|
130
|
+
pip install conduct-cli
|
|
131
|
+
|
|
132
|
+
# Authenticate (already done if you use Conduct)
|
|
133
|
+
conduct login --server https://api.conductai.ai --api-key <api-key>
|
|
131
134
|
|
|
132
|
-
#
|
|
135
|
+
# Sync Guard — installs hook + MCP, pulls policies
|
|
136
|
+
conduct guard sync
|
|
133
137
|
```
|
|
134
138
|
|
|
135
139
|
That's it. Policy enforcement is active from the next tool call.
|
|
@@ -138,14 +142,13 @@ That's it. Policy enforcement is active from the next tool call.
|
|
|
138
142
|
|
|
139
143
|
| Command | Description |
|
|
140
144
|
|---------|-------------|
|
|
141
|
-
| `conduct guard
|
|
142
|
-
| `conduct guard sync` | Pull latest policy from server (run after security team updates rules) |
|
|
145
|
+
| `conduct guard sync` | Pull latest policy, write hook to `~/.conductguard/hook.py`, register hook + MCP |
|
|
143
146
|
| `conduct guard status` | Show today's spend, session count, and violations |
|
|
144
147
|
| `conduct guard audit [--since 7d]` | Print recent guard events in a table |
|
|
145
148
|
|
|
146
149
|
### How the PreToolUse hook works
|
|
147
150
|
|
|
148
|
-
When you run `conduct guard
|
|
151
|
+
When you run `conduct guard sync`, the CLI writes a Python script to `~/.conductguard/hook.py` and registers it as a `PreToolUse` hook in `~/.claude/settings.json`:
|
|
149
152
|
|
|
150
153
|
```json
|
|
151
154
|
{
|
|
@@ -173,7 +176,7 @@ Before every tool call, Claude Code runs the hook. The hook:
|
|
|
173
176
|
|
|
174
177
|
### How conductguard-mcp works
|
|
175
178
|
|
|
176
|
-
`conduct guard
|
|
179
|
+
`conduct guard sync` also registers an MCP server entry in `~/.claude/settings.json`:
|
|
177
180
|
|
|
178
181
|
```json
|
|
179
182
|
{
|
|
@@ -244,7 +247,7 @@ Policy is stored at `~/.conductguard/policy.json` and synced from the server:
|
|
|
244
247
|
|
|
245
248
|
### Keeping policy up to date
|
|
246
249
|
|
|
247
|
-
|
|
250
|
+
Run `conduct guard sync` after your security team updates rules in the ConductGuard dashboard. The sync command pulls the latest policy, rewrites the hook, and re-registers the MCP entry in any newly detected AI tool configs.
|
|
248
251
|
|
|
249
252
|
```bash
|
|
250
253
|
# Add to a daily cron or run manually after policy changes
|
|
@@ -86,13 +86,14 @@ ConductGuard is AI tool fleet management — your security team sets policies on
|
|
|
86
86
|
### How it works
|
|
87
87
|
|
|
88
88
|
```
|
|
89
|
-
|
|
90
|
-
└─
|
|
89
|
+
Admin configures policies and budgets in the Guard dashboard
|
|
90
|
+
└─ developers are workspace members automatically — no invite step needed
|
|
91
91
|
|
|
92
|
-
Developer runs: conduct guard
|
|
93
|
-
├─
|
|
94
|
-
├─ writes PreToolUse hook → ~/.
|
|
95
|
-
|
|
92
|
+
Developer runs: conduct guard sync
|
|
93
|
+
├─ pulls latest policy to ~/.conductguard/policy.json
|
|
94
|
+
├─ writes PreToolUse hook → ~/.conductguard/hook.py
|
|
95
|
+
├─ registers hook → ~/.claude/settings.json
|
|
96
|
+
└─ registers conductguard-mcp → ~/.claude/settings.json (mcpServers) + Codex
|
|
96
97
|
|
|
97
98
|
Every Claude Code tool call:
|
|
98
99
|
├─ PreToolUse hook fires (hook.py) → checks policy → block / warn / audit
|
|
@@ -102,10 +103,13 @@ Every Claude Code tool call:
|
|
|
102
103
|
### Developer setup
|
|
103
104
|
|
|
104
105
|
```bash
|
|
105
|
-
|
|
106
|
-
|
|
106
|
+
pip install conduct-cli
|
|
107
|
+
|
|
108
|
+
# Authenticate (already done if you use Conduct)
|
|
109
|
+
conduct login --server https://api.conductai.ai --api-key <api-key>
|
|
107
110
|
|
|
108
|
-
#
|
|
111
|
+
# Sync Guard — installs hook + MCP, pulls policies
|
|
112
|
+
conduct guard sync
|
|
109
113
|
```
|
|
110
114
|
|
|
111
115
|
That's it. Policy enforcement is active from the next tool call.
|
|
@@ -114,14 +118,13 @@ That's it. Policy enforcement is active from the next tool call.
|
|
|
114
118
|
|
|
115
119
|
| Command | Description |
|
|
116
120
|
|---------|-------------|
|
|
117
|
-
| `conduct guard
|
|
118
|
-
| `conduct guard sync` | Pull latest policy from server (run after security team updates rules) |
|
|
121
|
+
| `conduct guard sync` | Pull latest policy, write hook to `~/.conductguard/hook.py`, register hook + MCP |
|
|
119
122
|
| `conduct guard status` | Show today's spend, session count, and violations |
|
|
120
123
|
| `conduct guard audit [--since 7d]` | Print recent guard events in a table |
|
|
121
124
|
|
|
122
125
|
### How the PreToolUse hook works
|
|
123
126
|
|
|
124
|
-
When you run `conduct guard
|
|
127
|
+
When you run `conduct guard sync`, the CLI writes a Python script to `~/.conductguard/hook.py` and registers it as a `PreToolUse` hook in `~/.claude/settings.json`:
|
|
125
128
|
|
|
126
129
|
```json
|
|
127
130
|
{
|
|
@@ -149,7 +152,7 @@ Before every tool call, Claude Code runs the hook. The hook:
|
|
|
149
152
|
|
|
150
153
|
### How conductguard-mcp works
|
|
151
154
|
|
|
152
|
-
`conduct guard
|
|
155
|
+
`conduct guard sync` also registers an MCP server entry in `~/.claude/settings.json`:
|
|
153
156
|
|
|
154
157
|
```json
|
|
155
158
|
{
|
|
@@ -220,7 +223,7 @@ Policy is stored at `~/.conductguard/policy.json` and synced from the server:
|
|
|
220
223
|
|
|
221
224
|
### Keeping policy up to date
|
|
222
225
|
|
|
223
|
-
|
|
226
|
+
Run `conduct guard sync` after your security team updates rules in the ConductGuard dashboard. The sync command pulls the latest policy, rewrites the hook, and re-registers the MCP entry in any newly detected AI tool configs.
|
|
224
227
|
|
|
225
228
|
```bash
|
|
226
229
|
# Add to a daily cron or run manually after policy changes
|
|
@@ -482,7 +482,7 @@ def _register_mcp(workspace_id: str, member_token: str, api_url: str) -> None:
|
|
|
482
482
|
"""Write conductguard MCP entry into every AI tool config found on this machine.
|
|
483
483
|
|
|
484
484
|
Credentials are NOT stored in the MCP config — the server reads them from
|
|
485
|
-
~/.conductguard/config.json at startup, which is
|
|
485
|
+
~/.conductguard/config.json at startup, which is written by guard sync.
|
|
486
486
|
"""
|
|
487
487
|
entry = {"command": "conductguard-mcp"}
|
|
488
488
|
found_any = False
|
|
@@ -840,9 +840,90 @@ def cmd_guard_sync(args):
|
|
|
840
840
|
_register_mcp(workspace_id, cfg2.get("member_token", ""), base_url)
|
|
841
841
|
print(f" {GREEN}Hook script updated{RESET}")
|
|
842
842
|
|
|
843
|
+
# Capture savings from RTK and Agent Booster
|
|
844
|
+
_report_savings(cfg, base_url, api_key)
|
|
845
|
+
|
|
843
846
|
print(f"\n{BOLD}Policy refreshed ({rule_count} rule(s)).{RESET}")
|
|
844
847
|
|
|
845
848
|
|
|
849
|
+
def _report_savings(cfg: dict, base_url: str, api_key: str) -> None:
|
|
850
|
+
import subprocess
|
|
851
|
+
|
|
852
|
+
rtk_data = {}
|
|
853
|
+
booster_data = {}
|
|
854
|
+
|
|
855
|
+
# Read RTK savings — rtk gain -f json nests under "summary" key
|
|
856
|
+
try:
|
|
857
|
+
r = subprocess.run(["rtk", "gain", "-f", "json"], capture_output=True, text=True, timeout=10)
|
|
858
|
+
if r.returncode == 0:
|
|
859
|
+
raw = json.loads(r.stdout)
|
|
860
|
+
summary = raw.get("summary", raw)
|
|
861
|
+
rtk_data = {
|
|
862
|
+
"saved_tokens": summary.get("total_saved", 0),
|
|
863
|
+
"savings_pct": summary.get("avg_savings_pct", 0.0),
|
|
864
|
+
"total_commands": summary.get("total_commands", 0),
|
|
865
|
+
}
|
|
866
|
+
except Exception:
|
|
867
|
+
pass
|
|
868
|
+
|
|
869
|
+
# Read Agent Booster savings
|
|
870
|
+
try:
|
|
871
|
+
r = subprocess.run(["booster", "gain", "-f", "json"], capture_output=True, text=True, timeout=10)
|
|
872
|
+
if r.returncode == 0:
|
|
873
|
+
raw = json.loads(r.stdout)
|
|
874
|
+
booster_data = {
|
|
875
|
+
"saved_tokens": raw.get("saved_tokens", 0),
|
|
876
|
+
"savings_pct": raw.get("savings_pct", 0.0),
|
|
877
|
+
"total_reads": raw.get("total_reads", 0),
|
|
878
|
+
}
|
|
879
|
+
except Exception:
|
|
880
|
+
pass
|
|
881
|
+
|
|
882
|
+
# If neither tool returned data, skip silently
|
|
883
|
+
if not rtk_data and not booster_data:
|
|
884
|
+
return
|
|
885
|
+
|
|
886
|
+
# Load baseline to compute period_start
|
|
887
|
+
baseline_path = GUARD_DIR / "savings_baseline.json"
|
|
888
|
+
period_start = None
|
|
889
|
+
try:
|
|
890
|
+
if baseline_path.exists():
|
|
891
|
+
baseline = json.loads(baseline_path.read_text())
|
|
892
|
+
period_start = baseline.get("recorded_at")
|
|
893
|
+
except Exception:
|
|
894
|
+
pass
|
|
895
|
+
|
|
896
|
+
now_iso = datetime.now(timezone.utc).isoformat()
|
|
897
|
+
|
|
898
|
+
payload = {
|
|
899
|
+
"workspace_id": cfg.get("workspace_id", ""),
|
|
900
|
+
"member_email": cfg.get("user_email", ""),
|
|
901
|
+
"rtk": rtk_data,
|
|
902
|
+
"booster": booster_data,
|
|
903
|
+
"period_start": period_start,
|
|
904
|
+
"period_end": now_iso,
|
|
905
|
+
}
|
|
906
|
+
|
|
907
|
+
try:
|
|
908
|
+
headers = {"Content-Type": "application/json"}
|
|
909
|
+
if api_key:
|
|
910
|
+
headers["X-Api-Key"] = api_key
|
|
911
|
+
data = json.dumps(payload).encode()
|
|
912
|
+
req = urllib.request.Request(
|
|
913
|
+
f"{base_url}/guard/savings",
|
|
914
|
+
data=data,
|
|
915
|
+
headers=headers,
|
|
916
|
+
method="POST",
|
|
917
|
+
)
|
|
918
|
+
with urllib.request.urlopen(req, timeout=15) as resp:
|
|
919
|
+
resp.read()
|
|
920
|
+
# Save baseline for next diff
|
|
921
|
+
baseline_path.write_text(json.dumps({"recorded_at": now_iso, "rtk": rtk_data, "booster": booster_data}))
|
|
922
|
+
print(f" {GREEN}Savings reported{RESET}")
|
|
923
|
+
except Exception:
|
|
924
|
+
pass # Never fail sync because savings POST failed
|
|
925
|
+
|
|
926
|
+
|
|
846
927
|
def cmd_guard_status(args):
|
|
847
928
|
cfg = _require_guard_config()
|
|
848
929
|
workspace_id = cfg.get("workspace_id")
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
conductguard-mcp — ConductGuard MCP server.
|
|
4
4
|
|
|
5
5
|
Runs as a subprocess started by Claude Code / Cursor / Windsurf via the
|
|
6
|
-
mcpServers config written by `conduct guard
|
|
6
|
+
mcpServers config written by `conduct guard sync`. Communicates over
|
|
7
7
|
stdin/stdout using JSON-RPC 2.0 (MCP stdio transport).
|
|
8
8
|
|
|
9
9
|
Exposes three tools:
|
|
@@ -11,6 +11,7 @@ Exposes three tools:
|
|
|
11
11
|
guard_check — check whether a tool call would be blocked by policy
|
|
12
12
|
guard_sync — pull latest policy from the ConductGuard API
|
|
13
13
|
"""
|
|
14
|
+
from __future__ import annotations
|
|
14
15
|
import argparse
|
|
15
16
|
import json
|
|
16
17
|
import re
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: conduct-cli
|
|
3
|
-
Version: 0.4.
|
|
3
|
+
Version: 0.4.24
|
|
4
4
|
Summary: CLI for Conduct AI — install agents, manage projects, run tests
|
|
5
5
|
Author-email: Conduct AI <hello@conductai.ai>
|
|
6
6
|
License: MIT
|
|
@@ -110,13 +110,14 @@ ConductGuard is AI tool fleet management — your security team sets policies on
|
|
|
110
110
|
### How it works
|
|
111
111
|
|
|
112
112
|
```
|
|
113
|
-
|
|
114
|
-
└─
|
|
113
|
+
Admin configures policies and budgets in the Guard dashboard
|
|
114
|
+
└─ developers are workspace members automatically — no invite step needed
|
|
115
115
|
|
|
116
|
-
Developer runs: conduct guard
|
|
117
|
-
├─
|
|
118
|
-
├─ writes PreToolUse hook → ~/.
|
|
119
|
-
|
|
116
|
+
Developer runs: conduct guard sync
|
|
117
|
+
├─ pulls latest policy to ~/.conductguard/policy.json
|
|
118
|
+
├─ writes PreToolUse hook → ~/.conductguard/hook.py
|
|
119
|
+
├─ registers hook → ~/.claude/settings.json
|
|
120
|
+
└─ registers conductguard-mcp → ~/.claude/settings.json (mcpServers) + Codex
|
|
120
121
|
|
|
121
122
|
Every Claude Code tool call:
|
|
122
123
|
├─ PreToolUse hook fires (hook.py) → checks policy → block / warn / audit
|
|
@@ -126,10 +127,13 @@ Every Claude Code tool call:
|
|
|
126
127
|
### Developer setup
|
|
127
128
|
|
|
128
129
|
```bash
|
|
129
|
-
|
|
130
|
-
|
|
130
|
+
pip install conduct-cli
|
|
131
|
+
|
|
132
|
+
# Authenticate (already done if you use Conduct)
|
|
133
|
+
conduct login --server https://api.conductai.ai --api-key <api-key>
|
|
131
134
|
|
|
132
|
-
#
|
|
135
|
+
# Sync Guard — installs hook + MCP, pulls policies
|
|
136
|
+
conduct guard sync
|
|
133
137
|
```
|
|
134
138
|
|
|
135
139
|
That's it. Policy enforcement is active from the next tool call.
|
|
@@ -138,14 +142,13 @@ That's it. Policy enforcement is active from the next tool call.
|
|
|
138
142
|
|
|
139
143
|
| Command | Description |
|
|
140
144
|
|---------|-------------|
|
|
141
|
-
| `conduct guard
|
|
142
|
-
| `conduct guard sync` | Pull latest policy from server (run after security team updates rules) |
|
|
145
|
+
| `conduct guard sync` | Pull latest policy, write hook to `~/.conductguard/hook.py`, register hook + MCP |
|
|
143
146
|
| `conduct guard status` | Show today's spend, session count, and violations |
|
|
144
147
|
| `conduct guard audit [--since 7d]` | Print recent guard events in a table |
|
|
145
148
|
|
|
146
149
|
### How the PreToolUse hook works
|
|
147
150
|
|
|
148
|
-
When you run `conduct guard
|
|
151
|
+
When you run `conduct guard sync`, the CLI writes a Python script to `~/.conductguard/hook.py` and registers it as a `PreToolUse` hook in `~/.claude/settings.json`:
|
|
149
152
|
|
|
150
153
|
```json
|
|
151
154
|
{
|
|
@@ -173,7 +176,7 @@ Before every tool call, Claude Code runs the hook. The hook:
|
|
|
173
176
|
|
|
174
177
|
### How conductguard-mcp works
|
|
175
178
|
|
|
176
|
-
`conduct guard
|
|
179
|
+
`conduct guard sync` also registers an MCP server entry in `~/.claude/settings.json`:
|
|
177
180
|
|
|
178
181
|
```json
|
|
179
182
|
{
|
|
@@ -244,7 +247,7 @@ Policy is stored at `~/.conductguard/policy.json` and synced from the server:
|
|
|
244
247
|
|
|
245
248
|
### Keeping policy up to date
|
|
246
249
|
|
|
247
|
-
|
|
250
|
+
Run `conduct guard sync` after your security team updates rules in the ConductGuard dashboard. The sync command pulls the latest policy, rewrites the hook, and re-registers the MCP entry in any newly detected AI tool configs.
|
|
248
251
|
|
|
249
252
|
```bash
|
|
250
253
|
# Add to a daily cron or run manually after policy changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|