{"id":15014296,"url":"https://github.com/monkeywie/proxyee","last_synced_at":"2025-05-15T03:06:55.388Z","repository":{"id":39459082,"uuid":"102307552","full_name":"monkeyWie/proxyee","owner":"monkeyWie","description":"HTTP proxy server,support HTTPS\u0026websocket.MITM impl,intercept and tamper HTTPS traffic.","archived":false,"fork":false,"pushed_at":"2025-04-07T04:09:49.000Z","size":484,"stargazers_count":1589,"open_issues_count":113,"forks_count":582,"subscribers_count":59,"default_branch":"master","last_synced_at":"2025-05-15T03:06:49.497Z","etag":null,"topics":["http","https","java","mitm","mitmproxy","netty","proxy","proxy-server"],"latest_commit_sha":null,"homepage":"","language":"Java","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/monkeyWie.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null},"funding":{"ko_fi":"monkeywie","custom":"https://github.com/monkeyWie/proxyee/blob/master/.donate/index.md"}},"created_at":"2017-09-04T01:50:06.000Z","updated_at":"2025-05-10T04:41:17.000Z","dependencies_parsed_at":"2024-09-20T10:01:20.563Z","dependency_job_id":"c6d37c86-5429-4aa4-993e-dafdab9e5fdc","html_url":"https://github.com/monkeyWie/proxyee","commit_stats":{"total_commits":211,"total_committers":14,"mean_commits":"15.071428571428571","dds":"0.36492890995260663","last_synced_commit":"cddd02ad0d5a00fb152a8839f7356c1b17d62ff4"},"previous_names":[],"tags_count":36,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/monkeyWie%2Fproxyee","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/monkeyWie%2Fproxyee/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/monkeyWie%2Fproxyee/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/monkeyWie%2Fproxyee/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/monkeyWie","download_url":"https://codeload.github.com/monkeyWie/proxyee/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":254264766,"owners_count":22041793,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["http","https","java","mitm","mitmproxy","netty","proxy","proxy-server"],"created_at":"2024-09-24T19:45:26.042Z","updated_at":"2025-05-15T03:06:50.369Z","avatar_url":"https://github.com/monkeyWie.png","language":"Java","readme":"\u003cdiv align=\"center\"\u003e\n  \u003ch1\u003eProxyee\u003c/h1\u003e\n  \u003cp\u003e\n  \n[![maven](https://img.shields.io/maven-central/v/com.github.monkeywie/proxyee.svg)](https://search.maven.org/search?q=com.github.monkeywie)\n[![license](https://img.shields.io/github/license/monkeywie/proxyee.svg)](https://opensource.org/licenses/MIT)\n\n  \u003c/p\u003e\n  \u003cp\u003e\n\n[English](/README.md) | [中文](/README_zh-CN.md)\n\n  \u003c/p\u003e\n\u003c/div\u003e\n\n---\n\n## Introduction\n\nProxyee is a JAVA written HTTP proxy server library that supports HTTP, HTTPS, Websocket protocols, and supports MITM (Man-in-the-middle), which can capture and tamper with HTTP, HTTPS packet.\n\n## Usage\n\n```xml\n\u003cdependency\u003e\n    \u003cgroupId\u003ecom.github.monkeywie\u003c/groupId\u003e\n    \u003cartifactId\u003eproxyee\u003c/artifactId\u003e\n    \u003cversion\u003e1.7.7\u003c/version\u003e\n\u003c/dependency\u003e\n```\n\n## Demo\n\n- Normal HTTP proxy\n\n```java\nnew HttpProxyServer().start(9999);\n```\n\n- MITM HTTP proxy\n\nThe following is a demonstration of a MITM attack that modifies the response header and response body when visiting the Baidu homepage, as shown in the figure below：\n\n![20200724152245](https://raw.githubusercontent.com/monkeyWie/pic-bed/master/proxyee/20200724152245.png)\n\nCode：\n\n```java\nHttpProxyServerConfig config =  new HttpProxyServerConfig();\n//enable HTTPS support\n//If not enabled, HTTPS will not be intercepted, but forwarded directly to the raw packet.\nconfig.setHandleSsl(true);\nnew HttpProxyServer()\n    .serverConfig(config)\n    .proxyInterceptInitializer(new HttpProxyInterceptInitializer() {\n      @Override\n      public void init(HttpProxyInterceptPipeline pipeline) {\n        pipeline.addLast(new FullResponseIntercept() {\n\n          @Override\n          public boolean match(HttpRequest httpRequest, HttpResponse httpResponse, HttpProxyInterceptPipeline pipeline) {\n            //Insert js when matching to Baidu homepage\n            return HttpUtil.checkUrl(pipeline.getHttpRequest(), \"^www.baidu.com$\")\n                \u0026\u0026 isHtml(httpRequest, httpResponse);\n          }\n\n          @Override\n          public void handleResponse(HttpRequest httpRequest, FullHttpResponse httpResponse, HttpProxyInterceptPipeline pipeline) {\n            //Print raw packet\n            System.out.println(httpResponse.toString());\n            System.out.println(httpResponse.content().toString(Charset.defaultCharset()));\n            //Edit response header and response body\n            httpResponse.headers().set(\"handel\", \"edit head\");\n            httpResponse.content().writeBytes(\"\u003cscript\u003ealert('hello proxyee')\u003c/script\u003e\".getBytes());\n          }\n        });\n      }\n    })\n    .start(9999);\n```\n\n\u003e Note: When https support is enabled, you need to install the CA certificate (`src/resources/ca.crt`) to a trusted root certificate authority.\n\nMore demo code can be found in the test package.\n\n## HTTPS support\n\nThe CA certificate (src/resources/ca.crt) from the project needs to be imported to a trusted root certificate authority.\nYou can use the CertDownIntercept interceptor to enable the web certificate download feature, visit http://serverIP:serverPort to access.\n\n\u003e Note 1: If the certificate installation on Android phones pops up the password stored in your credentials, just enter the lock screen password.\n\u003e\n\u003e Note 2: Android 7 and above, the system no longer trusts user-installed certificates, you need to root and use the\n\u003e cat ca.crt \u003e $(openssl x509 -inform PEM -subject_hash_old -in ca.crt | head -1).0\n\u003e command generates the d1488b25.0 file, and then moves the file to the\n\u003e /system/etc/security/cacerts/\n\u003e And give 644 access.\n\u003e\n\u003e Note 3: In Android 7 and above, even if you add the certificate to the system certificate, this certificate does not work in chrome. The reason is that chrome will only trust certificates with validity less than 27 months from 2018 (https://www.entrustdatacard.com/blog/2018/february/chrome-requires-ct-after-april-2018). So you need to generate the certificate file yourself.\n\n### Custom CA\n\nSince the root certificate and private key attached to the project are public, they are only suitable for local development and debugging, please generate your own root certificate and private key when using in the official environment, otherwise there will be risks.\n\n- running the main method of the`com.github.monkeywie.proxyee.crt.CertUtil` class\n\n- use openssl\n\n```sh\nopenssl genrsa -out ca.key 2048\nopenssl pkcs8 -topk8 -nocrypt -inform PEM -outform DER -in ca.key -out ca_private.der\nopenssl req -sha256 -new -x509 -days 365 -key ca.key -out ca.crt \\\n    -subj \"/C=CN/ST=GD/L=SZ/O=lee/OU=study/CN=testRoot\"\n```\n\nCopy `ca.crt` and `ca_private.der` to the project src/resources/ after generation, or implement the HttpProxyCACertFactory interface to custom load the root certificate and private key.\n\n### Rules for MITM\n\nIf you only want to perform MITM attacks on certain domains, you can use the `HttpProxyServerConfig.setMitmMatcher` method to set the matching rule, for example:\n\n```java\nHttpProxyServerConfig config = new HttpProxyServerConfig();\nconfig.setHandleSsl(true);\n// only MITM on www.baidu.com\nconfig.setMitmMatcher(new DomainHttpProxyMitmMatcher(Arrays.asList(\"www.baidu.com\")));\n```\n\nNow the built-in `DomainHttpProxyMitmMatcher` is an exact match for the request domain. If you have other requirements, you can implement the `HttpProxyMitmMatcher` interface to customize the matching rules.\n\n## Authentication\n\nCurrently only basic authentication are supported.\n\n- Basic\n\n```java\n// curl -i -x 127.0.0.1:9999 -U admin:123456 http://www.baidu.com\nHttpProxyServerConfig config = new HttpProxyServerConfig();\n        config.setAuthenticationProvider(new BasicHttpProxyAuthenticationProvider() {\n            @Override\n            protected BasicHttpToken authenticate(String usr, String pwd) {\n                if (\"admin\".equals(usr) \u0026\u0026 \"123456\".equals(pwd)) {\n                    return new BasicHttpToken(usr, pwd);\n                }\n                return null;\n            }\n        });\nnew HttpProxyServer()\n        .serverConfig(config)\n        .start(9999);\n```\n\n- Custom\n\nCustomize authentication by implementing the `HttpProxyAuthenticationProvider` interface.\n\n### Authentication context\n\nAfter the authorization, the token returned from the verification pass can be obtained in the pipeline.\n\n```java\nHttpToken token = HttpAuthContext.getToken(clientChannel);\n```\n\n## Pre-proxy support\n\nPre-proxy can be set,support http,socks4,socks5 protocol.\n\n```java\nnew HttpProxyServer()\n    .proxyConfig(new ProxyConfig(ProxyType.SOCKS5, \"127.0.0.1\", 1085))\n    .start(9999);\n```\n\n## Donate\n\nIf you like this project, please consider [donating](/.donate/index.md) to support the development of this project, thank you!\n\n## Flow\n\nSSL handshake\n![SSL握手](https://raw.githubusercontent.com/monkeyWie/pic-bed/master/proxyee/20190918134332.png)\n\nHTTP communication\n\n![HTTP通讯](https://raw.githubusercontent.com/monkeyWie/pic-bed/master/proxyee/20190918134232.png)\n\n## How it works\n\n- [JAVA 写 HTTP 代理服务器(一)-socket 实现](https://segmentfault.com/a/1190000011810997)\n- [JAVA 写 HTTP 代理服务器(二)-netty 实现](https://segmentfault.com/a/1190000011811082)\n- [JAVA 写 HTTP 代理服务器(三)-https 明文捕获](https://segmentfault.com/a/1190000011811150)\n\n## Thanks\n\n[![intellij-idea](idea.svg)](https://www.jetbrains.com/?from=proxyee)\n","funding_links":["https://ko-fi.com/monkeywie","https://github.com/monkeyWie/proxyee/blob/master/.donate/index.md"],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmonkeywie%2Fproxyee","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmonkeywie%2Fproxyee","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmonkeywie%2Fproxyee/lists"}