mic.git


mic

~ proxy for JA4-TLS fingerprinting evasion
git clone https://github.com/djnnvx/mic.git
log | files | refs | archive | README | LICENSE

commit 7184eee9743ad85dd4fdd0cf64760a5050a09085
parent 0e039eed56aa25e9fb48235cfbe27188f86a60a1
Author: djnn <[email protected]>
Date: Fri, 20 Feb 2026 11:12:05 +0900

refactor(cmd): replace TOML config with CLI subcommands

Diffstat:
Acmd/client.go | 70++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Mcmd/root.go | 86+++++++------------------------------------------------------------------------
Acmd/server.go | 72++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Dcmd/types.go | 11-----------
Dconfig/config.go | 63---------------------------------------------------------------
Dconfig/config_test.go | 94-------------------------------------------------------------------------------
Mgo.mod | 3+--
Mgo.sum | 2--
Dmic.example.toml | 33---------------------------------

9 files changed, 150 insertions(+), 284 deletions(-)

diff --git a/cmd/client.go b/cmd/client.go
@@ -0,0 +1,70 @@
+package cmd
+
+import (
+	"crypto/x509"
+	"log"
+	"os"
+
+	"github.com/djnnvx/mic/fingerprint"
+	"github.com/djnnvx/mic/proxy"
+	"github.com/spf13/cobra"
+)
+
+func newClientCmd() *cobra.Command {
+	var (
+		listen        string
+		fpName        string
+		caPath        string
+		interceptCert string
+		interceptKey  string
+	)
+
+	cmd := &cobra.Command{
+		Use:   "client",
+		Short: "HTTP CONNECT proxy with optional MitM interception",
+		RunE: func(cmd *cobra.Command, args []string) error {
+			p := &proxy.Proxy{ListenAddr: listen}
+
+			if caPath != "" {
+				caCert, err := os.ReadFile(caPath)
+				if err != nil {
+					log.Fatalf("[!] Failed to read CA certificate: %v", err)
+				}
+				pool := x509.NewCertPool()
+				pool.AppendCertsFromPEM(caCert)
+				p.CAPool = pool
+			}
+
+			if fpName != "" {
+				fp, err := fingerprint.ByName(fpName)
+				if err != nil {
+					log.Fatalf("[!] Failed to load fingerprint: %v", err)
+				}
+				p.Fingerprint = fp
+				log.Printf("[+] Using TLS fingerprint: %s", fp.Name())
+			}
+
+			if interceptCert != "" || interceptKey != "" {
+				ca, err := proxy.LoadOrGenerateCA(interceptCert, interceptKey)
+				if err != nil {
+					log.Fatalf("[!] Failed to load/generate intercept CA: %v", err)
+				}
+				p.LocalCA = ca
+				log.Printf("[+] MitM CA ready — import %s, then: curl --cacert %s -x http://localhost%s https://<target>",
+					interceptCert, interceptCert, listen)
+			}
+
+			log.Printf("[+] Mode: client (HTTP CONNECT proxy on %s)", listen)
+			p.RegisterHandler(proxy.HttpsHandler)
+			return p.Run()
+		},
+	}
+
+	cmd.Flags().StringVarP(&listen, "listen", "l", ":8080", "listen address")
+	cmd.Flags().StringVarP(&fpName, "fingerprint", "f", "", "TLS fingerprint profile name (e.g. chrome-120)")
+	cmd.Flags().StringVar(&caPath, "ca", "", "path to upstream CA certificate")
+	cmd.Flags().StringVar(&interceptCert, "intercept-cert", "", "MitM CA cert path (enables interception)")
+	cmd.Flags().StringVar(&interceptKey, "intercept-key", "", "MitM CA key path (enables interception)")
+
+	return cmd
+}
diff --git a/cmd/root.go b/cmd/root.go
@@ -1,14 +1,9 @@
 package cmd
 
 import (
-	"crypto/x509"
 	"fmt"
-	"log"
 	"os"
 
-	"github.com/djnnvx/mic/config"
-	"github.com/djnnvx/mic/fingerprint"
-	"github.com/djnnvx/mic/proxy"
 	"github.com/spf13/cobra"
 )
 
@@ -16,7 +11,6 @@ var SKID_ASCII_ART = `
 
 
 
-
         ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢀⣤⣤⣤⣤⣤⣤⣤⣄⣀⡀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀
     ⠀              ⠀⠀⠀⠀⠀⠀⠀⠀⠉⠉⠛⠻⠿⢿⣿⣿⣿⣿⣿⣶⣤⣀⡀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀
                ⠀⠀⠀⢀⡀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠈⠙⠻⣿⣿⣿⣿⣿⣿⣶⣄⡀⠀⠀⠀⠀⠀⠀⠀⠀⠀
@@ -24,7 +18,7 @@ var SKID_ASCII_ART = `
       --------  ⠀⠀⢸⣿⣿⣿⣿⣷⣄⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⣀⣀⣀⣀⣀⣙⢿⣿⣿⣿⣿⣿⣿⣦⡀⠀⠀⠀⠀⠀
         ⠀⠀⠀⠀  ⠀⠀⠀⠀⠀⢿⣿⣿⣿⣿⣿⣿⣿⣿⣶⣶⣶⣶⣿⣿⣿⣿⣿⣿⣿⣿⣿⠀⠻⣿⣿⣿⣿⣿⣿⣿⣄⠀⠀⠀⠀
         djnn.sh⠀⠀⠀⠀⠘⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠇⠀⠀⢹⣿⣿⣿⣿⣿⣿⣿⣆⠀⠀⠀
-        ⠀v0.0.1  ⠀⠀⢠⣿⣿⣿⣿⡟⠹⠿⠟⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡏⠀⠀⠀⠀⢿⣿⣿⣿⣿⣿⣿⣿⡆⠀⠀
+        ⠀v0.0.2  ⠀⠀⢠⣿⣿⣿⣿⡟⠹⠿⠟⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡏⠀⠀⠀⠀⢿⣿⣿⣿⣿⣿⣿⣿⡆⠀⠀
         ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⡿⠋⡬⢿⣿⣷⣤⣤⣴⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠀⠀⠀⠀⠀⠸⣿⣿⣿⣿⣿⣿⣿⣿⡀⠀
         ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠰⡇⢸⡇⢸⣿⣿⣿⠟⠁⢀⣬⢽⣿⣿⣿⣿⣿⣿⠋⠀⠀⠀⠀⠀⠀⠀⣿⣿⣿⣿⣿⣿⣿⣿⣧⠀
         ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⣼⣧⣈⣛⣿⣿⣿⡇⠀⠀⣾⠁⢀⢻⣿⣿⣿⣿⠇⠀⠀⠀⠀⠀⠀⠀⠀⣿⣿⣿⣿⣿⣿⣿⣿⣿⡀
@@ -35,7 +29,7 @@ var SKID_ASCII_ART = `
         ⠸⣿⣿⣄⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢰⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣦⡀⠀⠀⠀⢀⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠃⠀
         ⠀⢹⣿⣿⣧⡀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢸⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣷⣄⣴⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠏⠀⠀
         ⠀⠀⠹⣿⣿⣿⣷⣄⠀⠀⠀⠀⠀⠀⠀⠀⣾⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠏⠀⠀⠀
-        ⠀⠀⠀⠙⣿⣿⣿⣿⣿⣶⣤⣀⠀⠀⠀⠀⣿⣿⣿⣿⣿⣿mina is cute⣿⣿⣿⣿⣿⣿⣿⣿⠋⠀⠀⠀⠀
+        ⠀⠀⠀⠙⣿⣿⣿⣿⣿⣶⣤⣀⠀⠀⠀⠀⣿⣿⣿⣿⣿⣿⣿mina is cute⣿⣿⣿⣿⣿⣿⣿⣿⠋⠀⠀⠀⠀
         ⠀⠀⠀⠀⠈⠻⣿⣿⣿⣿⣿⣿⣿⣷⣶⣶⣾⣿⣿⣿⣿⣿⣿⣿⣿<3:)⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠁⠀⠀⠀⠀⠀
         ⠀⠀⠀⠀⠀⠀⠉⠻⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠁⠀⠀⠀⠀⠀⠀⠀
         ⠀⠀⠀⠀⠀⠀⠀⠀⠈⠛⠿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠿⠋⠅⠀⠀⠀⠀⠀⠀⠀⠀⠀
@@ -46,86 +40,20 @@ var SKID_ASCII_ART = `
 
 `
 
-func getParser(opts *MicCliOptions) *cobra.Command {
-	var rootCmd = &cobra.Command{
+func newRootCmd() *cobra.Command {
+	rootCmd := &cobra.Command{
 		Use:   "mic",
 		Short: "modular proxy for network-fingerprinting evasion",
 		Long:  "mic (mina-is-cute) is a HTTPS proxy to evade networking fingerprinting detection",
-		Run: func(cmd *cobra.Command, args []string) {
-			cfg, err := config.Load(opts.ConfigPath)
-			if err != nil {
-				log.Fatalf("[!] Failed to load config: %v", err)
-			}
-
-			p := &proxy.Proxy{
-				ListenAddr:  cfg.Listen.Addr,
-				BackendAddr: cfg.Backend.Addr,
-			}
-
-			// Load optional custom CA pool.
-			if cfg.CA.Cert != "" {
-				caCert, err := os.ReadFile(cfg.CA.Cert)
-				if err != nil {
-					log.Fatalf("[!] Failed to read CA certificate: %v", err)
-				}
-				pool := x509.NewCertPool()
-				pool.AppendCertsFromPEM(caCert)
-				p.CAPool = pool
-			}
-
-			// Load TLS fingerprint if a JA4 hash is configured.
-			if cfg.Fingerprint.TLS.JA4 != "" {
-				fp, err := fingerprint.NewTLS(cfg.Fingerprint.TLS.JA4)
-				if err != nil {
-					log.Fatalf("[!] Failed to load fingerprint: %v", err)
-				}
-				p.Fingerprint = fp
-				log.Printf("[+] Using TLS fingerprint: %s", fp.Name())
-			}
-
-			switch cfg.Mode {
-			case "client-front":
-				log.Printf("[+] Mode: client-front (HTTP CONNECT proxy)")
-				if cfg.CA.Intercept.Cert != "" || cfg.CA.Intercept.Key != "" {
-					ca, err := proxy.LoadOrGenerateCA(cfg.CA.Intercept.Cert, cfg.CA.Intercept.Key)
-					if err != nil {
-						log.Fatalf("[!] Failed to load/generate intercept CA: %v", err)
-					}
-					p.LocalCA = ca
-					log.Printf("[+] MitM CA ready — import %s, then: curl --cacert %s -x http://localhost%s https://<target>",
-						cfg.CA.Intercept.Cert, cfg.CA.Intercept.Cert, cfg.Listen.Addr)
-				}
-				p.RegisterHandler(proxy.HttpsHandler)
-			case "server-front":
-				log.Printf("[+] Mode: server-front (TLS termination → backend %s)", cfg.Backend.Addr)
-				certFile := cfg.Fingerprint.TLS.Termination.Cert
-				keyFile := cfg.Fingerprint.TLS.Termination.Key
-				if certFile == "" || keyFile == "" {
-					log.Fatalf("[!] server-front mode requires fingerprint.tls.termination.cert and .key")
-				}
-				p.RegisterHandler(proxy.ServerFrontHandler(certFile, keyFile))
-			default:
-				log.Fatalf("[!] Unknown mode %q; expected \"client-front\" or \"server-front\"", cfg.Mode)
-			}
-
-			if err := p.Run(); err != nil {
-				log.Fatalf("[!] Proxy error: %v", err)
-			}
-		},
 	}
-
-	defaults := GetDefaultOptions()
-	rootCmd.Flags().StringVarP(&opts.ConfigPath, "config", "c", defaults.ConfigPath, "path to TOML config file")
-
+	rootCmd.AddCommand(newClientCmd())
+	rootCmd.AddCommand(newServerCmd())
 	return rootCmd
 }
 
 func Execute() {
 	fmt.Println(SKID_ASCII_ART)
-
-	opts := GetDefaultOptions()
-	cliParser := getParser(&opts)
-	if err := cliParser.Execute(); err != nil {
+	if err := newRootCmd().Execute(); err != nil {
 		fmt.Printf("[!] Error: %s\n", err.Error())
 		os.Exit(1)
 	}
diff --git a/cmd/server.go b/cmd/server.go
@@ -0,0 +1,72 @@
+package cmd
+
+import (
+	"crypto/x509"
+	"log"
+	"os"
+
+	"github.com/djnnvx/mic/fingerprint"
+	"github.com/djnnvx/mic/proxy"
+	"github.com/spf13/cobra"
+)
+
+func newServerCmd() *cobra.Command {
+	var (
+		listen  string
+		backend string
+		fpName  string
+		caPath  string
+		cert    string
+		key     string
+	)
+
+	cmd := &cobra.Command{
+		Use:   "server",
+		Short: "TLS termination proxy with upstream fingerprinting",
+		RunE: func(cmd *cobra.Command, args []string) error {
+			if backend == "" {
+				log.Fatal("[!] --backend is required for server mode")
+			}
+			if cert == "" || key == "" {
+				log.Fatal("[!] --cert and --key are required for server mode")
+			}
+
+			p := &proxy.Proxy{
+				ListenAddr:  listen,
+				BackendAddr: backend,
+			}
+
+			if caPath != "" {
+				caCert, err := os.ReadFile(caPath)
+				if err != nil {
+					log.Fatalf("[!] Failed to read CA certificate: %v", err)
+				}
+				pool := x509.NewCertPool()
+				pool.AppendCertsFromPEM(caCert)
+				p.CAPool = pool
+			}
+
+			if fpName != "" {
+				fp, err := fingerprint.ByName(fpName)
+				if err != nil {
+					log.Fatalf("[!] Failed to load fingerprint: %v", err)
+				}
+				p.Fingerprint = fp
+				log.Printf("[+] Using TLS fingerprint: %s", fp.Name())
+			}
+
+			log.Printf("[+] Mode: server (TLS termination → backend %s)", backend)
+			p.RegisterHandler(proxy.ServerFrontHandler(cert, key))
+			return p.Run()
+		},
+	}
+
+	cmd.Flags().StringVarP(&listen, "listen", "l", ":8080", "listen address")
+	cmd.Flags().StringVarP(&backend, "backend", "b", "", "backend host:port (required)")
+	cmd.Flags().StringVarP(&fpName, "fingerprint", "f", "", "TLS fingerprint profile name (e.g. chrome-120)")
+	cmd.Flags().StringVar(&caPath, "ca", "", "path to upstream CA certificate")
+	cmd.Flags().StringVar(&cert, "cert", "", "TLS certificate for incoming termination (required)")
+	cmd.Flags().StringVar(&key, "key", "", "TLS key for incoming termination (required)")
+
+	return cmd
+}
diff --git a/cmd/types.go b/cmd/types.go
@@ -1,11 +0,0 @@
-package cmd
-
-type MicCliOptions struct {
-	ConfigPath string
-}
-
-func GetDefaultOptions() MicCliOptions {
-	return MicCliOptions{
-		ConfigPath: "mic.toml",
-	}
-}
diff --git a/config/config.go b/config/config.go
@@ -1,63 +0,0 @@
-package config
-
-import (
-	"fmt"
-	"os"
-
-	"github.com/pelletier/go-toml/v2"
-)
-
-type Config struct {
-	Mode        string  `toml:"mode"`
-	Listen      Listen  `toml:"listen"`
-	Backend     Backend `toml:"backend"`
-	Fingerprint FpConf  `toml:"fingerprint"`
-	CA          CAConf  `toml:"ca"`
-}
-
-type Listen struct {
-	Addr string `toml:"addr"`
-}
-
-type Backend struct {
-	Addr string `toml:"addr"`
-}
-
-type CAConf struct {
-	Cert      string          `toml:"cert"`      // upstream CA cert for verifying targets
-	Intercept InterceptCAConf `toml:"intercept"` // client-front: local MitM CA
-}
-
-type InterceptCAConf struct {
-	Cert string `toml:"cert"` // path to local CA cert (created if absent)
-	Key  string `toml:"key"`  // path to local CA key  (created if absent)
-}
-
-type FpConf struct {
-	TLS TLSConf `toml:"tls"`
-}
-
-type TLSConf struct {
-	JA4         string         `toml:"ja4"`
-	Termination TLSTermination `toml:"termination"`
-}
-
-type TLSTermination struct {
-	Cert string `toml:"cert"`
-	Key  string `toml:"key"`
-}
-
-// Load reads and parses a TOML config file from path.
-func Load(path string) (*Config, error) {
-	data, err := os.ReadFile(path)
-	if err != nil {
-		return nil, fmt.Errorf("reading config file %q: %w", path, err)
-	}
-
-	var cfg Config
-	if err := toml.Unmarshal(data, &cfg); err != nil {
-		return nil, fmt.Errorf("parsing config file %q: %w", path, err)
-	}
-
-	return &cfg, nil
-}
diff --git a/config/config_test.go b/config/config_test.go
@@ -1,94 +0,0 @@
-package config_test
-
-import (
-	"os"
-	"testing"
-
-	"github.com/djnnvx/mic/config"
-)
-
-const validTOML = `
-mode = "client-front"
-
-[listen]
-addr = ":8080"
-
-[backend]
-addr = "127.0.0.1:443"
-
-[fingerprint]
-[fingerprint.tls]
-ja4 = "t13d1516h2_8daaf6152771_b0da82dd1658"
-
-[fingerprint.tls.termination]
-cert = "/path/to/cert.pem"
-key  = "/path/to/key.pem"
-
-[ca]
-cert = "/path/to/ca.pem"
-`
-
-func writeTempFile(t *testing.T, content string) string {
-	t.Helper()
-	f, err := os.CreateTemp("", "mic-config-*.toml")
-	if err != nil {
-		t.Fatalf("creating temp file: %v", err)
-	}
-	defer f.Close()
-	if _, err := f.WriteString(content); err != nil {
-		t.Fatalf("writing temp file: %v", err)
-	}
-	return f.Name()
-}
-
-func TestLoad_Valid(t *testing.T) {
-	path := writeTempFile(t, validTOML)
-	defer os.Remove(path)
-
-	cfg, err := config.Load(path)
-	if err != nil {
-		t.Fatalf("Load returned error: %v", err)
-	}
-
-	if cfg.Mode != "client-front" {
-		t.Errorf("Mode = %q; want %q", cfg.Mode, "client-front")
-	}
-	if cfg.Listen.Addr != ":8080" {
-		t.Errorf("Listen.Addr = %q; want %q", cfg.Listen.Addr, ":8080")
-	}
-	if cfg.Backend.Addr != "127.0.0.1:443" {
-		t.Errorf("Backend.Addr = %q; want %q", cfg.Backend.Addr, "127.0.0.1:443")
-	}
-	if cfg.Fingerprint.TLS.JA4 != "t13d1516h2_8daaf6152771_b0da82dd1658" {
-		t.Errorf("Fingerprint.TLS.JA4 = %q; want %q",
-			cfg.Fingerprint.TLS.JA4, "t13d1516h2_8daaf6152771_b0da82dd1658")
-	}
-	if cfg.Fingerprint.TLS.Termination.Cert != "/path/to/cert.pem" {
-		t.Errorf("Termination.Cert = %q; want %q",
-			cfg.Fingerprint.TLS.Termination.Cert, "/path/to/cert.pem")
-	}
-	if cfg.Fingerprint.TLS.Termination.Key != "/path/to/key.pem" {
-		t.Errorf("Termination.Key = %q; want %q",
-			cfg.Fingerprint.TLS.Termination.Key, "/path/to/key.pem")
-	}
-	if cfg.CA.Cert != "/path/to/ca.pem" {
-		t.Errorf("CA.Cert = %q; want %q", cfg.CA.Cert, "/path/to/ca.pem")
-	}
-}
-
-func TestLoad_MissingFile(t *testing.T) {
-	_, err := config.Load("/nonexistent/path/to/config.toml")
-	if err == nil {
-		t.Fatal("expected error for missing file, got nil")
-	}
-}
-
-func TestLoad_InvalidTOML(t *testing.T) {
-	path := writeTempFile(t, "this is not valid = toml [[[")
-	defer os.Remove(path)
-
-	_, err := config.Load(path)
-	if err == nil {
-		t.Fatal("expected error for invalid TOML, got nil")
-	}
-}
diff --git a/go.mod b/go.mod
@@ -3,9 +3,9 @@ module github.com/djnnvx/mic
 go 1.24.4
 
 require (
-	github.com/pelletier/go-toml/v2 v2.2.4
 	github.com/refraction-networking/utls v1.8.0
 	github.com/spf13/cobra v1.9.1
+	golang.org/x/net v0.38.0
 )
 
 require (
@@ -14,7 +14,6 @@ require (
 	github.com/klauspost/compress v1.17.4 // indirect
 	github.com/spf13/pflag v1.0.6 // indirect
 	golang.org/x/crypto v0.36.0 // indirect
-	golang.org/x/net v0.38.0 // indirect
 	golang.org/x/sys v0.31.0 // indirect
 	golang.org/x/text v0.23.0 // indirect
 )
diff --git a/go.sum b/go.sum
@@ -5,8 +5,6 @@ github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2
 github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw=
 github.com/klauspost/compress v1.17.4 h1:Ej5ixsIri7BrIjBkRZLTo6ghwrEtHFk7ijlczPW4fZ4=
 github.com/klauspost/compress v1.17.4/go.mod h1:/dCuZOvVtNoHsyb+cuJD3itjs3NbnF6KH9zAO4BDxPM=
-github.com/pelletier/go-toml/v2 v2.2.4 h1:mye9XuhQ6gvn5h28+VilKrrPoQVanw5PMw/TB0t5Ec4=
-github.com/pelletier/go-toml/v2 v2.2.4/go.mod h1:2gIqNv+qfxSVS7cM2xJQKtLSTLUE9V8t9Stt+h56mCY=
 github.com/refraction-networking/utls v1.8.0 h1:L38krhiTAyj9EeiQQa2sg+hYb4qwLCqdMcpZrRfbONE=
 github.com/refraction-networking/utls v1.8.0/go.mod h1:jkSOEkLqn+S/jtpEHPOsVv/4V4EVnelwbMQl4vCWXAM=
 github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
diff --git a/mic.example.toml b/mic.example.toml
@@ -1,33 +0,0 @@
-mode = "client-front"   # "client-front" | "server-front"
-
-[listen]
-addr = ":8080"
-
-[backend]
-# Used in server-front mode; client-front uses the CONNECT target directly.
-addr = "127.0.0.1:443"
-
-[fingerprint]
-[fingerprint.tls]
-ja4 = "t13d1516h2_8daaf6152771_02713d6af862"   # Chrome 120 (utls.HelloChrome_120)
-
-# server-front only: certificate for terminating incoming TLS
-[fingerprint.tls.termination]
-cert = "/path/to/cert.pem"
-key  = "/path/to/key.pem"
-
-[ca]
-cert = ""   # optional custom CA for upstream verification
-
-# client-front only: MitM interception CA.
-# mic will create the files on first run, then reuse them across restarts.
-# Import ca.pem into curl / your browser / system trust store.
-[ca.intercept]
-cert = "ca.pem"
-key  = "ca-key.pem"
-
-# Future:
-# [fingerprint.tcp]
-# window_size = 65535
-# ttl = 64
-# mss = 1460