local2public 0.1.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
local2public/__init__.py
ADDED
|
File without changes
|
local2public/cli.py
ADDED
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
from argparse import ArgumentParser
|
|
2
|
+
import asyncio
|
|
3
|
+
import httpx
|
|
4
|
+
|
|
5
|
+
SERVER_URL = "https://l2p-beige.vercel.app" # change to your deployed server
|
|
6
|
+
|
|
7
|
+
def parse_args():
|
|
8
|
+
parser = ArgumentParser(description="ltp - local to public")
|
|
9
|
+
parser.add_argument("-p", "--port", type=int, required=True)
|
|
10
|
+
parser.add_argument("-n", "--name", type=str, required=True)
|
|
11
|
+
parser.add_argument("-v", "--verbose", action="store_true")
|
|
12
|
+
return parser.parse_args()
|
|
13
|
+
|
|
14
|
+
async def tunnel(local_port: int, name: str, verbose: bool):
|
|
15
|
+
print(f"Tunnel open: {SERVER_URL}/join/{name}/")
|
|
16
|
+
print("Ctrl+C to stop")
|
|
17
|
+
|
|
18
|
+
async with httpx.AsyncClient() as client:
|
|
19
|
+
while True:
|
|
20
|
+
try:
|
|
21
|
+
# poll for pending requests
|
|
22
|
+
resp = await client.get(f"{SERVER_URL}/poll/{name}", timeout=5)
|
|
23
|
+
requests = resp.json()
|
|
24
|
+
|
|
25
|
+
for request_id, req in requests.items():
|
|
26
|
+
if verbose:
|
|
27
|
+
print(f"→ {req['method']} {req['path']}")
|
|
28
|
+
|
|
29
|
+
try:
|
|
30
|
+
# forward to local server
|
|
31
|
+
local_resp = await client.request(
|
|
32
|
+
method=req["method"],
|
|
33
|
+
url=f"http://localhost:{local_port}{req['path']}",
|
|
34
|
+
content=req["body"],
|
|
35
|
+
timeout=10,
|
|
36
|
+
)
|
|
37
|
+
# send response back to server
|
|
38
|
+
await client.post(f"{SERVER_URL}/respond/{request_id}", json={
|
|
39
|
+
"status": local_resp.status_code,
|
|
40
|
+
"body": local_resp.text,
|
|
41
|
+
})
|
|
42
|
+
except Exception as e:
|
|
43
|
+
await client.post(f"{SERVER_URL}/respond/{request_id}", json={
|
|
44
|
+
"status": 502,
|
|
45
|
+
"body": str(e),
|
|
46
|
+
})
|
|
47
|
+
|
|
48
|
+
except Exception as e:
|
|
49
|
+
print(f"Poll error: {e}")
|
|
50
|
+
|
|
51
|
+
await asyncio.sleep(0.5)
|
|
52
|
+
|
|
53
|
+
def main():
|
|
54
|
+
args = parse_args()
|
|
55
|
+
try:
|
|
56
|
+
asyncio.run(tunnel(args.port, args.name, args.verbose))
|
|
57
|
+
except KeyboardInterrupt:
|
|
58
|
+
print("\nTunnel closed")
|
|
59
|
+
|
|
60
|
+
if __name__ == "__main__":
|
|
61
|
+
main()
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
local2public/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
2
|
+
local2public/cli.py,sha256=mRf1M8_hIVvuXf7eg22AWI15qN5gL2mBnX87YtQb1to,2296
|
|
3
|
+
local2public-0.1.0.dist-info/METADATA,sha256=2UKWzIVAeo-qAjENr8tRg_eCh0Aj0Ac3JL5p_5bDI5c,133
|
|
4
|
+
local2public-0.1.0.dist-info/WHEEL,sha256=mffPy8wBnZQn2VnJUU5jE99KsxaSfiyMHV9Yt0aLVxs,87
|
|
5
|
+
local2public-0.1.0.dist-info/entry_points.txt,sha256=WG-GZ4jSN544Ysmh1EC1RHPGrXIfuazWCJzjvL9AL0Y,37
|
|
6
|
+
local2public-0.1.0.dist-info/RECORD,,
|