File size: 3,039 Bytes
8ab393a 79ab57a 8ab393a 5ef8210 c205946 01ed253 8ab393a c205946 5ba3fb4 c205946 5ba3fb4 8ab393a 79ab57a c205946 5ef8210 8ab393a 5ef8210 8ab393a c205946 89ed75b 8ab393a 5ba3fb4 c205946 8ab393a 5ef8210 8ab393a 5ef8210 c205946 5ef8210 5ba3fb4 8ab393a 5ef8210 c205946 5ba3fb4 8ab393a 5ba3fb4 5ef8210 5ba3fb4 1030457 5ef8210 1030457 5ef8210 c205946 5ef8210 5ba3fb4 5ef8210 5ba3fb4 5ef8210 1030457 5ef8210 5ba3fb4 8ab393a 5ef8210 8ab393a c205946 ceb0229 4b45739 1030457 c205946 1030457 5ba3fb4 8590964 5ba3fb4 79ab57a c205946 5ef8210 c205946 5ef8210 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 | from fastapi import FastAPI, Request
from fastapi.responses import RedirectResponse
from user_agents import parse
import geoip2.database
from pathlib import Path
import os
import httpx
app = FastAPI()
# ================== ENV ==================
GOOGLE_SHEET_WEBHOOK = os.getenv("GOOGLE_SHEET_WEBHOOK")
if not GOOGLE_SHEET_WEBHOOK:
raise RuntimeError("GOOGLE_SHEET_WEBHOOK environment variable not set")
REDIRECT_URL = os.getenv("REDIRECT_URL")
if not REDIRECT_URL:
raise RuntimeError("REDIRECT_URL environment variable not set")
# ================== GEO DB ==================
BASE_DIR = Path(__file__).resolve().parent
CITY_DB_PATH = BASE_DIR / "databases" / "GeoLite2-City.mmdb"
ASN_DB_PATH = BASE_DIR / "databases" / "GeoLite2-ASN.mmdb"
city_reader = geoip2.database.Reader(str(CITY_DB_PATH))
asn_reader = geoip2.database.Reader(str(ASN_DB_PATH))
# ================== TRACK ==================
@app.get("/offer")
async def track_ip(request: Request):
# -------- Client IP --------
client_ip = request.headers.get("X-Forwarded-For")
if client_ip:
client_ip = client_ip.split(",")[0].strip()
else:
client_ip = request.client.host
# -------- User Agent --------
ua_string = request.headers.get("User-Agent", "Unknown")
ua = parse(ua_string)
browser_info = {
"browser": ua.browser.family,
"version": ua.browser.version_string,
"os": ua.os.family,
"os_version": ua.os.version_string,
"device": ua.device.family,
"is_mobile": ua.is_mobile,
"is_bot": ua.is_bot
}
# -------- Geo --------
geo_data = {}
try:
city = city_reader.city(client_ip)
geo_data = {
"country": city.country.name,
"city": city.city.name,
"region": city.subdivisions.most_specific.name,
"latitude": city.location.latitude,
"longitude": city.location.longitude
}
except Exception as e:
print("Geo error:", e)
# -------- ASN --------
asn_data = {}
try:
asn = asn_reader.asn(client_ip)
asn_data = {
"asn": asn.autonomous_system_number,
"org": asn.autonomous_system_organization
}
except Exception as e:
print("ASN error:", e)
payload = {
"ip": client_ip,
"browser": browser_info,
"geolocation": geo_data,
"asn": asn_data
}
# -------- Send to Google Sheet --------
try:
async with httpx.AsyncClient(timeout=5, follow_redirects=True) as client:
await client.post(
GOOGLE_SHEET_WEBHOOK,
json=payload,
headers={"Content-Type": "application/json"}
)
except Exception as e:
print("Sheet error:", e)
'''return payload'''
# -------- Redirect --------
return RedirectResponse(
url=REDIRECT_URL,
status_code=302
)
@app.on_event("shutdown")
def shutdown():
city_reader.close()
asn_reader.close() |