Skip to content

Instantly share code, notes, and snippets.

@KasumigaokaUtaha
Created May 7, 2020 13:47
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save KasumigaokaUtaha/40c5f5c4831e9099e469a49c4a74cc7e to your computer and use it in GitHub Desktop.
Save KasumigaokaUtaha/40c5f5c4831e9099e469a49c4a74cc7e to your computer and use it in GitHub Desktop.
package main
import (
"bufio"
"bytes"
"flag"
"fmt"
"github.com/elazarl/goproxy"
"io/ioutil"
"log"
"net"
"net/http"
"os"
"strings"
)
const(
iOSServerListHost = "gfcn-transit.ios.sunborngame.com"
iOSServerListPath = "/index.php"
adrServerListPath = "/index.php"
adrServerListHost = "gfcn-transit.gw.sunborngame.com"
)
var (
verbose bool
src string
dst string
listenPort int
)
func init() {
flag.BoolVar(&verbose, "v", false, "enable verbose output")
flag.StringVar(&src, "src", "adr", "source platform, default ios")
flag.StringVar(&dst, "dst", "ios", "destination platform, default adr")
flag.IntVar(&listenPort, "port", 8080, "port on which the proxy server listens to")
flag.Parse()
}
func main() {
proxy := goproxy.NewProxyHttpServer()
proxy.Verbose = verbose
if src == "ios" && dst == "adr" {
proxy.OnRequest(Req4AdrServerList()).DoFunc(ReplaceServerListParams4AdrServer)
} else if src == "adr" && dst == "ios"{
proxy.OnRequest(Req4iOSServerList()).DoFunc(ReplaceServerListParams4iOSServer)
} else {
fmt.Printf("src 与 dst 不匹配,请指定正确的 src 以及 dst 参数。\n比如 src: ios, dst: adr。\n")
}
localIP := GetLocalIP()
fmt.Printf("监听本机地址: %s, 端口: %d\n", localIP, listenPort)
fmt.Printf("Girsfrontline-transfer %s -> %s 启动\n", src, dst)
log.Fatal(http.ListenAndServe(fmt.Sprintf(":%d", listenPort), proxy))
}
func GetLocalIP() string {
host, _ := os.Hostname()
addrs, _ := net.LookupIP(host)
found := false
var rst string
for _, addr := range addrs {
if ipv4 := addr.To4(); ipv4 != nil && ipv4.String() != "127.0.0.1" {
found = true
rst = ipv4.String()
}
}
if found {
return rst
}
log.Fatal("No IPv4 addr found")
os.Exit(1)
return ""
}
func Req4AdrServerList() goproxy.ReqConditionFunc {
return func(req *http.Request, ctx *goproxy.ProxyCtx) bool {
//log.Printf("Method: %s, Host: %s, Path: %s\n", req.Method, req.URL.Host, req.URL.Path)
return req.URL.Host == iOSServerListHost && req.URL.Path == iOSServerListPath && req.Method == "POST"
}
}
func ReplaceServerListParams4AdrServer(req *http.Request, ctx *goproxy.ProxyCtx) (*http.Request, *http.Response) {
//log.Printf("Start to replace server list params")
body, err := ioutil.ReadAll(req.Body)
if err != nil {
return req, nil // TODO examine the effect of this error
}
req.Body.Close()
if strings.Contains(string(body), "channel=cn_appstore") {
//log.Printf("channel == cn_appstore")
// replace host
req.URL.Host = adrServerListHost
req.Host = adrServerListHost
req.Header.Set("Host", adrServerListHost)
// replace params in the request body
bodyStr := string(body)
bodyStr = strings.Replace(bodyStr, "channel=cn_appstore", "channel=cn_mica", -1)
bodyStr = strings.Replace(bodyStr, "platformChannelId=ios", "platformChannelId=GWGW", -1)
bodyStr = strings.Replace(bodyStr, "device=ios", "device=adr", -1)
//bodyStr = strings.Replace(bodyStr, "check_version=20500", "check_version=20501&device=adr", -1)
newBody := ioutil.NopCloser(bufio.NewReader(strings.NewReader(bodyStr)))
req.ContentLength = int64(len([]byte(bodyStr)))
req.Header.Set("Content-Length", fmt.Sprintf("%d", req.ContentLength))
req.Body = newBody
} else {
//log.Printf("channel != ios_appstore")
req.Body = ioutil.NopCloser(bufio.NewReader(bytes.NewReader(body)))
}
return req, nil
}
func Req4iOSServerList() goproxy.ReqConditionFunc {
return func(req *http.Request, ctx *goproxy.ProxyCtx) bool {
return req.URL.Host == adrServerListHost && req.URL.Path == adrServerListPath && req.Method == "POST"
}
}
func ReplaceServerListParams4iOSServer(req *http.Request, ctx *goproxy.ProxyCtx) (*http.Request, *http.Response) {
body, err := ioutil.ReadAll(req.Body)
if err != nil {
return req, nil // TODO examine the effect of this error
}
req.Body.Close()
if strings.Contains(string(body), "channel=cn_mica") {
//log.Printf("channel == cn_appstore")
// replace host
req.URL.Host = iOSServerListHost
req.Host = iOSServerListHost
req.Header.Set("Host", iOSServerListHost)
// replace params in the request body
bodyStr := string(body)
bodyStr = strings.Replace(bodyStr, "channel=cn_mica", "channel=cn_appstore", -1)
bodyStr = strings.Replace(bodyStr, "platformChannelId=GWGW", "platformChannelId=ios", -1)
bodyStr = strings.Replace(bodyStr, "device=adr", "device=ios", -1)
newBody := ioutil.NopCloser(bufio.NewReader(strings.NewReader(bodyStr)))
req.ContentLength = int64(len([]byte(bodyStr)))
req.Header.Set("Content-Length", fmt.Sprintf("%d", req.ContentLength))
req.Body = newBody
} else {
//log.Printf("channel != ios_appstore")
req.Body = ioutil.NopCloser(bufio.NewReader(bytes.NewReader(body)))
}
return req, nil
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment