Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion micropython/uaiohttpclient/manifest.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
metadata(description="HTTP client module for MicroPython asyncio module", version="0.5.2")
metadata(description="HTTP client module for MicroPython asyncio module", version="0.5.3")

# Originally written by Paul Sokolovsky.

Expand Down
108 changes: 108 additions & 0 deletions micropython/uaiohttpclient/test_uaiohttpclient.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
import io
import sys

_MP_STREAM_POLL = 3
_SERVER_RESPONSE_200_OK = b"HTTP/1.1 200 OK\r\n\r\n"


class Socket(io.IOBase):
def __init__(self, read_data):
self._write_buffer = io.BytesIO()
self._read_buffer = io.BytesIO(read_data)

def ioctl(self, cmd, arg):
if cmd == _MP_STREAM_POLL:
return arg
return -1

def setblocking(self, value):
pass

def connect(self, address):
pass

def write(self, buf):
self._write_buffer.write(buf)
return len(buf)

def readline(self):
return self._read_buffer.readline()

def read(self, size=-1):
return self._read_buffer.read(size)

def readinto(self, buf):
return self._read_buffer.readinto(buf)

def close(self):
pass


class socket:
AF_INET = 2
SOCK_STREAM = 1
IPPROTO_TCP = 6

@staticmethod
def _set_responses(r):
socket._responses = r

@staticmethod
def getaddrinfo(host, port, af=0, type=0, flags=0):
return [(socket.AF_INET, socket.SOCK_STREAM, socket.IPPROTO_TCP, "", ("127.0.0.1", 80))]

def socket(af=AF_INET, type=SOCK_STREAM, proto=IPPROTO_TCP):
return Socket(socket._responses.pop(0))


# Patch the socket module with a mock one for testing.
sys.modules["socket"] = socket

# ruff: noqa: E402
import asyncio
import uaiohttpclient
import unittest


class Test(unittest.TestCase):
async def do_request(self, url):
resp = await uaiohttpclient.request("GET", url)
body = await resp.read()
return resp, body

def test_request(self):
BODY_DATA = b"body"
socket._set_responses([_SERVER_RESPONSE_200_OK + BODY_DATA])

resp, body = asyncio.run(self.do_request("http://example.com"))
request_data = resp.content.s._write_buffer.getvalue()
self.assertEqual(
request_data,
b"GET / HTTP/1.0\r\nHost: example.com\r\nConnection: close\r\nUser-Agent: compat\r\n\r\n",
)
self.assertEqual(resp.status, 200)
self.assertEqual(resp.headers, [])
self.assertEqual(body, BODY_DATA)

def test_redirect_absolute(self):
BODY_DATA = b"body"
socket._set_responses(
[
b"HTTP/1.1 301 OK\r\nLocation: http://example.com/index\r\n\r\n",
_SERVER_RESPONSE_200_OK + BODY_DATA,
]
)

resp, body = asyncio.run(self.do_request("http://example.com"))
request_data = resp.content.s._write_buffer.getvalue()
self.assertEqual(
request_data,
b"GET /index HTTP/1.0\r\nHost: example.com\r\nConnection: close\r\nUser-Agent: compat\r\n\r\n",
)
self.assertEqual(resp.status, 200)
self.assertEqual(resp.headers, [])
self.assertEqual(body, BODY_DATA)


if __name__ == "__main__":
unittest.main()
4 changes: 2 additions & 2 deletions micropython/uaiohttpclient/uaiohttpclient.py
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ async def request_raw(method, url):
path,
host,
)
await writer.awrite(query.encode("latin-1"))
await writer.awrite(query.encode("utf8"))
return reader


Expand All @@ -87,7 +87,7 @@ async def request(method, url):
if b"chunked" in line:
chunked = True
elif line.startswith(b"Location:"):
url = line.rstrip().split(None, 1)[1].decode("latin-1")
url = line.rstrip().split(None, 1)[1].decode("utf8")

if 301 <= status <= 303:
redir_cnt += 1
Expand Down
1 change: 1 addition & 0 deletions tools/ci.sh
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,7 @@ function ci_package_tests_run {
done

for path in \
micropython/uaiohttpclient \
micropython/ucontextlib \
python-stdlib/colorsys \
python-stdlib/contextlib \
Expand Down
Loading