diff options
author | dormando <dormando@rydia.net> | 2022-03-01 12:51:47 -0800 |
---|---|---|
committer | dormando <dormando@rydia.net> | 2022-03-01 12:51:47 -0800 |
commit | fa745db8fffe7d13438fe2437bdf8fcb1372bc96 (patch) | |
tree | 15bd7946d2d9ac6631c635f5c7ac12228e078f0b /proxy_await.c | |
parent | 2a903f04d1b395cd60c1b7357a9b733e19eb7973 (diff) | |
download | memcached-fa745db8fffe7d13438fe2437bdf8fcb1372bc96.tar.gz |
proxy: hacky method of supporting noreply/quiet
avoids sending the response to the client, in most cases. works by
stripping the noreply status from the request before sending it along,
so the proxy itself knows when to move the request forward.
has sharp edges:
- only looking at the request object that's actually sent to the
backend, instead of the request object that created the coroutine.
- overriding tokens in lua to re-set the noreply mode would break the
protocol.
So this change helps us validate the feature but solidifying it requires
moving it to the "edges" of processing; before the coroutine and after
any command assembly (or within the command assembly).
Diffstat (limited to 'proxy_await.c')
-rw-r--r-- | proxy_await.c | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/proxy_await.c b/proxy_await.c index f69e7df..c504b9a 100644 --- a/proxy_await.c +++ b/proxy_await.c @@ -91,6 +91,27 @@ static void mcp_queue_await_io(conn *c, lua_State *Lc, mcp_request_t *rq, int aw mcp_resp_t *r = lua_newuserdatauv(Lc, sizeof(mcp_resp_t), 1); memset(r, 0, sizeof(mcp_resp_t)); r->start = rq->start; + // Set noreply mode. + // TODO (v2): the response "inherits" the request's noreply mode, which isn't + // strictly correct; we should inherit based on the request that spawned + // the coroutine but the structure doesn't allow that yet. + // Should also be able to settle this exact mode from the parser so we + // don't have to re-branch here. + if (rq->pr.noreply) { + if (rq->pr.cmd_type == CMD_TYPE_META) { + r->mode = RESP_MODE_METAQUIET; + for (int x = 2; x < rq->pr.ntokens; x++) { + if (rq->request[rq->pr.tokens[x]] == 'q') { + rq->request[rq->pr.tokens[x]] = ' '; + } + } + } else { + r->mode = RESP_MODE_NOREPLY; + rq->request[rq->pr.reqlen - 3] = 'Y'; + } + } else { + r->mode = RESP_MODE_NORMAL; + } int x; int end = rq->pr.reqlen-2 > RESP_CMD_MAX ? RESP_CMD_MAX : rq->pr.reqlen-2; |