Files
hadrian/handlers/proxy.go
2023-11-02 22:06:16 +01:00

95 lines
2.4 KiB
Go

package handlers
import (
"fmt"
"io"
"log"
"net/http"
"net/url"
"os"
"regexp"
"strings"
"github.com/gofiber/fiber/v2"
)
var UserAgent = getenv("USER_AGENT", "Mozilla/5.0 (compatible; Googlebot/2.1; +http://www.google.com/bot.html)")
var ForwardedFor = getenv("X_FORWARDED_FOR", "66.249.66.1")
func ProxySite(c *fiber.Ctx) error {
// Get the url from the URL
urlQuery := c.Params("*")
body, _, resp, err := fetchSite(urlQuery)
if err != nil {
log.Println("ERROR:", err)
c.SendStatus(500)
return c.SendString(err.Error())
}
c.Set("Content-Type", resp.Header.Get("Content-Type"))
return c.SendString(body)
}
func fetchSite(urlQuery string) (string, *http.Request, *http.Response, error) {
u, err := url.Parse(urlQuery)
if err != nil {
return "", nil, nil, err
}
log.Println(u.String())
// Fetch the site
client := &http.Client{}
req, _ := http.NewRequest("GET", u.String(), nil)
req.Header.Set("User-Agent", UserAgent)
req.Header.Set("X-Forwarded-For", ForwardedFor)
req.Header.Set("Referer", u.String())
req.Header.Set("Host", u.Host)
resp, err := client.Do(req)
if err != nil {
return "", nil, nil, err
}
defer resp.Body.Close()
bodyB, err := io.ReadAll(resp.Body)
if err != nil {
return "", nil, nil, err
}
body := rewriteHtml(bodyB, u)
return body, req, resp, nil
}
func rewriteHtml(bodyB []byte, u *url.URL) string {
// Rewrite the HTML
body := string(bodyB)
// images
imagePattern := `<img\s+([^>]*\s+)?src="(/)([^"]*)"`
re := regexp.MustCompile(imagePattern)
body = re.ReplaceAllString(body, fmt.Sprintf(`<img $1 src="%s$3"`, "/https://"+u.Host+"/"))
// scripts
scriptPattern := `<script\s+([^>]*\s+)?src="(/)([^"]*)"`
reScript := regexp.MustCompile(scriptPattern)
body = reScript.ReplaceAllString(body, fmt.Sprintf(`<script $1 script="%s$3"`, "/https://"+u.Host+"/"))
//body = strings.ReplaceAll(body, "srcset=\"/", "srcset=\"/https://"+u.Host+"/") // TODO: Needs a regex to rewrite the URL's
body = strings.ReplaceAll(body, "href=\"/", "href=\"/https://"+u.Host+"/")
body = strings.ReplaceAll(body, "url('/", "url('/https://"+u.Host+"/")
body = strings.ReplaceAll(body, "url(/", "url(/https://"+u.Host+"/")
body = strings.ReplaceAll(body, "href=\"https://"+u.Host, "href=\"/https://"+u.Host+"/")
return body
}
func getenv(key, fallback string) string {
value := os.Getenv(key)
if len(value) == 0 {
return fallback
}
return value
}