Files
MusicPlayer/tests/fakes/fake_http_transport.gd
T

92 lines
2.9 KiB
GDScript

class_name FakeHttpTransport
extends HttpTransport
## Stands in for the MusicServer in tests.
##
## Register canned responses per path with [method respond_json] or
## [method respond_bytes], then install it with [method install]. Requests to paths
## without a response get a 404. Responses are delivered immediately.
## Paths requested so far, relative to [code]Settings.default_path[/code].
var requested_paths: Array[String] = []
## HTTP method of each request, in the same order as [member requested_paths].
var requested_methods: Array[int] = []
var _responses: Dictionary = {}
var _successes_left: Dictionary = {}
var _held_paths: Dictionary = {}
var _previous_transport: HttpTransport
func _init() -> void:
super(null)
## Replaces the MusicServerClient transport with this fake.
func install() -> FakeHttpTransport:
_previous_transport = MusicServerClient.transport
MusicServerClient.transport = self
return self
## Restores the transport that was active before [method install].
func uninstall() -> void:
MusicServerClient.transport = _previous_transport
## Answers requests to [param path] with [param data] encoded as JSON.
func respond_json(path: String, data: Variant, response_code: int = 200) -> void:
respond_bytes(path, JSON.stringify(data).to_utf8_buffer(), response_code)
## Answers requests to [param path] with [param body] as-is.
func respond_bytes(path: String, body: PackedByteArray, response_code: int = 200) -> void:
_responses[path] = {"code": response_code, "body": body}
_successes_left.erase(path)
## Lets [param successes] more requests to [param path] succeed, then answers 503 until
## a new response is registered for the path.
func fail_after(path: String, successes: int) -> void:
_successes_left[path] = successes
## Holds back responses to [param path] until [method release] is called, like a slow
## server.
func hold(path: String) -> void:
_held_paths[path] = []
## Delivers the responses held back for [param path] and stops holding it.
func release(path: String) -> void:
var waiting: Array = _held_paths.get(path, [])
_held_paths.erase(path)
for pending: Callable in waiting:
pending.call()
## Returns how many times [param path] has been requested.
func count(path: String) -> int:
return requested_paths.count(path)
func request(url: String, method: int, on_complete: Callable) -> void:
var path: String = url.trim_prefix(Settings.default_path)
requested_paths.append(path)
requested_methods.append(method)
if _held_paths.has(path):
_held_paths[path].append(_answer.bind(path, on_complete))
return
_answer(path, on_complete)
func _answer(path: String, on_complete: Callable) -> void:
if _successes_left.has(path):
if _successes_left[path] == 0:
on_complete.call(503, PackedByteArray())
return
_successes_left[path] -= 1
if _responses.has(path):
on_complete.call(_responses[path].code, _responses[path].body)
else:
on_complete.call(404, PackedByteArray())