@mmmbuto/anthmorph 0.1.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.
package/Cargo.toml ADDED
@@ -0,0 +1,61 @@
1
+ [package]
2
+ name = "AnthMorph"
3
+ version = "0.1.0"
4
+ edition = "2021"
5
+ description = "Anthropic to OpenAI-compatible proxy"
6
+ license = "MIT"
7
+ repository = "https://github.com/DioNanos/AnthMorph"
8
+ homepage = "https://github.com/DioNanos/AnthMorph"
9
+ authors = ["DioNanos <noreply@github.com>"]
10
+
11
+ [[bin]]
12
+ name = "anthmorph"
13
+ path = "src/main.rs"
14
+
15
+ [dependencies]
16
+ # Async runtime
17
+ tokio = { version = "1.42", features = ["rt-multi-thread", "macros"] }
18
+
19
+ # Web framework
20
+ axum = { version = "0.7", features = ["http2"] }
21
+
22
+ # HTTP client
23
+ reqwest = { version = "0.12", features = ["json", "stream", "rustls-tls"], default-features = false }
24
+
25
+ # Serialization
26
+ serde = { version = "1.0", features = ["derive"] }
27
+ serde_json = "1.0"
28
+
29
+ # Async utilities
30
+ futures = "0.3"
31
+ tokio-stream = "0.1"
32
+
33
+ # Observability
34
+ tracing = "0.1"
35
+ tracing-subscriber = { version = "0.3", features = ["env-filter"] }
36
+
37
+ # Error handling
38
+ anyhow = "1.0"
39
+ thiserror = "2.0"
40
+
41
+ # Environment variables
42
+ dotenvy = "0.15"
43
+
44
+ # CLI argument parsing
45
+ clap = { version = "4.5", features = ["derive"] }
46
+
47
+ # Server utilities
48
+ tower = { version = "0.5", features = ["util"] }
49
+ tower-http = { version = "0.6", features = ["trace", "cors"] }
50
+
51
+ # Async streams
52
+ async-stream = "0.3"
53
+ bytes = "1.9"
54
+ pin-project = "1.1"
55
+
56
+ [profile.release]
57
+ opt-level = "z"
58
+ lto = true
59
+ codegen-units = 1
60
+ strip = true
61
+ panic = "abort"
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 DioNanos
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,184 @@
1
+ # AnthMorph
2
+
3
+ [![Status](https://img.shields.io/badge/Status-0.1.0-blue.svg)](#project-status)
4
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](LICENSE)
5
+ [![Rust](https://img.shields.io/badge/Rust-1.94%2B-orange.svg)](https://www.rust-lang.org)
6
+ [![Target](https://img.shields.io/badge/Target-Termux%20%2F%20Linux-green.svg)](https://termux.dev)
7
+ [![npm](https://img.shields.io/npm/v/@mmmbuto/anthmorph?style=flat-square&logo=npm)](https://www.npmjs.com/package/@mmmbuto/anthmorph)
8
+
9
+ AnthMorph is a Chutes-first Anthropic `/v1/messages` proxy written in Rust.
10
+ It lets Claude-style clients talk to Chutes or other OpenAI-compatible backends through a safer, profile-aware translation layer.
11
+
12
+ Core capabilities:
13
+ - Anthropic `/v1/messages` ingress with OpenAI-compatible upstream translation
14
+ - `chutes` profile optimized for Chutes-specific compatibility, including `top_k` and reasoning handling
15
+ - `openai_generic` profile for conservative compatibility with generic OpenAI-style providers
16
+ - Streaming SSE translation with fragmented tool-call handling
17
+ - Local control CLI for init, start, stop, restart, status, and logs
18
+ - Termux-friendly workflow with optional npm distribution
19
+
20
+ ## Project Status
21
+
22
+ - Current line: `0.1.0`
23
+ - Primary target: `chutes.ai`
24
+ - Secondary target: generic OpenAI-compatible endpoints
25
+ - Tested locally against Chutes, MiniMax, and Alibaba Coding Plan rejection handling
26
+ - Distribution paths: source build and npm package under `@mmmbuto/anthmorph`
27
+ - Repository metadata is aligned for GitHub and npm publication
28
+
29
+ ## Quickstart
30
+
31
+ 1. Install
32
+
33
+ Source build:
34
+
35
+ ```bash
36
+ cargo build --release
37
+ ```
38
+
39
+ Global npm install:
40
+
41
+ ```bash
42
+ npm install -g @mmmbuto/anthmorph
43
+ ```
44
+
45
+ 2. Initialize Chutes profile
46
+
47
+ ```bash
48
+ export CHUTES_API_KEY=your_key_here
49
+ anthmorphctl init chutes --port 3107
50
+ ```
51
+
52
+ 3. Start proxy
53
+
54
+ ```bash
55
+ anthmorphctl start
56
+ anthmorphctl status
57
+ ```
58
+
59
+ 4. Stop proxy
60
+
61
+ ```bash
62
+ anthmorphctl stop
63
+ ```
64
+
65
+ ## CLI Control
66
+
67
+ `anthmorphctl` is the operator entrypoint.
68
+ It stores runtime state under `.anthmorph/` in the project root.
69
+
70
+ Common commands:
71
+
72
+ ```bash
73
+ anthmorphctl init chutes
74
+ anthmorphctl init minimax
75
+ anthmorphctl init openai --backend-url https://api.example.com/v1 --model my-model --key-env EXAMPLE_API_KEY
76
+ anthmorphctl start
77
+ anthmorphctl status
78
+ anthmorphctl logs
79
+ anthmorphctl stop
80
+ ```
81
+
82
+ Direct binary usage is also available:
83
+
84
+ ```bash
85
+ anthmorph --port 3107 --backend-profile chutes --backend-url https://llm.chutes.ai/v1 --model Qwen/Qwen3-Coder-Next-TEE --api-key "$CHUTES_API_KEY"
86
+ ```
87
+
88
+ ## Architecture
89
+
90
+ - `Ingress`: accepts Anthropic `/v1/messages` requests and validates profile-safe behavior.
91
+ - `Transform`: converts Anthropic messages, tools, and stop reasons into OpenAI-compatible payloads.
92
+ - `Streaming`: translates upstream SSE chunks back into Anthropic-style streaming events.
93
+ - `Profiles`: selects `chutes` or `openai_generic` behavior for request and response handling.
94
+ - `Control CLI`: manages local config, runtime state, start/stop/status, and operator logs.
95
+
96
+ ## API Key Policy
97
+
98
+ Preferred mode:
99
+ - Store only the environment variable name with `anthmorphctl set key-env ENV_NAME`
100
+ - Keep the secret in your shell environment
101
+
102
+ Optional mode:
103
+ - Persist the key locally with `anthmorphctl set key VALUE --save`
104
+
105
+ Recommendation:
106
+ - Do not save API keys in the repo by default
107
+ - Use env vars for daily operation and CI
108
+
109
+ ## Backend Profiles
110
+
111
+ - `chutes`: optimized path for Chutes, including `top_k` pass-through and reasoning support
112
+ - `openai_generic`: strips nonstandard fields and fails conservatively when the backend cannot represent Anthropic semantics safely
113
+
114
+ ## Safety Rules
115
+
116
+ - Assistant thinking blocks in request history are rejected instead of being downgraded to plain text
117
+ - Generic mode rejects backend reasoning content that cannot be represented safely
118
+ - Streaming tool-call deltas support contiguous fragments and fail closed on unsafe interleaving
119
+ - Optional ingress auth supports `Authorization: Bearer ...` or `x-api-key`
120
+ - CORS is disabled unless explicitly configured
121
+
122
+ ## Real Backend Coverage
123
+
124
+ Current integration coverage:
125
+ - `chutes.ai`: positive end-to-end smoke test
126
+ - `MiniMax`: positive end-to-end smoke test in generic mode
127
+ - `Alibaba Coding Plan`: negative expected test documenting upstream rejection for generic chat-completions flow
128
+
129
+ ## npm Packaging
130
+
131
+ This repository already includes npm packaging files:
132
+ - `package.json`
133
+ - `bin/anthmorph`
134
+ - `scripts/postinstall.js`
135
+
136
+ Packaging behavior:
137
+ - `npm install -g @mmmbuto/anthmorph` exposes `anthmorph` and `anthmorphctl`
138
+ - `postinstall` tries to build the Rust binary with `cargo build --release`
139
+ - if the binary is missing later, the `anthmorph` shim will try to build it on demand
140
+
141
+ ## Build And Test
142
+
143
+ ```bash
144
+ cargo test
145
+ npm pack --dry-run
146
+ ```
147
+
148
+ Real backend smoke tests:
149
+
150
+ ```bash
151
+ ./scripts/smoke_test.sh chutes
152
+ ./scripts/smoke_test.sh minimax
153
+ ./scripts/smoke_test.sh alibaba
154
+ ```
155
+
156
+ ## Repository Layout
157
+
158
+ ```text
159
+ src/ Rust proxy implementation
160
+ bin/ npm-exposed executable shims
161
+ scripts/ control CLI, smoke tests, npm postinstall
162
+ tests/ protocol and real-backend integration tests
163
+ ```
164
+
165
+ ## Documentation
166
+
167
+ - Repository: https://github.com/DioNanos/AnthMorph
168
+ - npm package: https://www.npmjs.com/package/@mmmbuto/anthmorph
169
+ - Issue tracker: https://github.com/DioNanos/AnthMorph/issues
170
+
171
+ ## Roadmap
172
+
173
+ 1. Broader compatibility validation across more OpenAI-compatible providers
174
+ 2. End-to-end validation against real Claude-style clients
175
+ 3. Public-deployment hardening with rate limits and clearer auth policy
176
+ 4. Better streaming coverage for complex multi-tool interleaving
177
+
178
+ ## License
179
+
180
+ MIT License
181
+ <p>
182
+ Copyright (c) 2026 DioNanos<br>
183
+ Made in Italy
184
+ </p>
package/bin/anthmorph ADDED
@@ -0,0 +1,22 @@
1
+ #!/bin/sh
2
+ set -eu
3
+
4
+ ROOT_DIR=$(CDPATH= cd -- "$(dirname -- "$0")/.." && pwd)
5
+ RELEASE_BIN=$ROOT_DIR/target/release/anthmorph
6
+ DEBUG_BIN=$ROOT_DIR/target/debug/anthmorph
7
+
8
+ if [ -x "$RELEASE_BIN" ]; then
9
+ exec "$RELEASE_BIN" "$@"
10
+ fi
11
+
12
+ if [ -x "$DEBUG_BIN" ]; then
13
+ exec "$DEBUG_BIN" "$@"
14
+ fi
15
+
16
+ if command -v cargo >/dev/null 2>&1; then
17
+ (cd "$ROOT_DIR" && cargo build --release --quiet)
18
+ exec "$RELEASE_BIN" "$@"
19
+ fi
20
+
21
+ echo "anthmorph binary not found and cargo is unavailable" >&2
22
+ exit 1
package/package.json ADDED
@@ -0,0 +1,52 @@
1
+ {
2
+ "name": "@mmmbuto/anthmorph",
3
+ "version": "0.1.0",
4
+ "description": "Chutes-first Anthropic /v1/messages proxy for Chutes and OpenAI-compatible backends",
5
+ "license": "MIT",
6
+ "author": "DioNanos <noreply@github.com>",
7
+ "bin": {
8
+ "anthmorph": "bin/anthmorph",
9
+ "anthmorphctl": "scripts/anthmorphctl"
10
+ },
11
+ "files": [
12
+ "bin/",
13
+ "scripts/anthmorphctl",
14
+ "scripts/postinstall.js",
15
+ "scripts/smoke_test.sh",
16
+ "src/",
17
+ "tests/",
18
+ "Cargo.toml",
19
+ "Cargo.lock",
20
+ "README.md",
21
+ "LICENSE"
22
+ ],
23
+ "scripts": {
24
+ "postinstall": "node scripts/postinstall.js",
25
+ "build:rust": "cargo build --release",
26
+ "test": "cargo test",
27
+ "pack:dry-run": "npm pack --dry-run"
28
+ },
29
+ "keywords": [
30
+ "anthropic",
31
+ "claude",
32
+ "proxy",
33
+ "chutes",
34
+ "openai-compatible",
35
+ "termux",
36
+ "rust"
37
+ ],
38
+ "repository": {
39
+ "type": "git",
40
+ "url": "git+https://github.com/DioNanos/AnthMorph.git"
41
+ },
42
+ "homepage": "https://github.com/DioNanos/AnthMorph#readme",
43
+ "bugs": {
44
+ "url": "https://github.com/DioNanos/AnthMorph/issues"
45
+ },
46
+ "publishConfig": {
47
+ "access": "public"
48
+ },
49
+ "engines": {
50
+ "node": ">=18"
51
+ }
52
+ }