Up tonight, I continue in my effort to get node-spdy working with SPDY version 3. I have Chrome speaking SPDY v3 by virtue of
about:flags
settings. I have begun SPDY v3 implementation in the node-spdy server by copying the v2 implementation to v3, updating the compression dictionary, and making a change or two to the header parsing. As of last night, I am able to parse headers from the incoming session, but that is about it. No response is ever sent and I can see no evidence that the request listener ever sees the request.
The headers look like:
headers: { ':host': 'localhost:3000', ':method': 'GET', ':path': '/', ':scheme': 'https', ':version': 'HTTP/1.1', accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8', 'accept-charset': 'ISO-8859-1,utf-8;q=0.7,*;q=0.3', 'accept-encoding': 'gzip,deflate,sdch', 'accept-language': 'en-US,en;q=0.8', 'cache-control': 'no-cache', pragma: 'no-cache', 'user-agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/536.8 (KHTML, like Gecko) Chrome/20.0.1105.0 Safari/536.8' } }Now that I think about it, I have no idea why some of those headers begin with a colon (e.g. ':host'). That seems like it must be coming from Chrome. If it were a zlib inflation error, the values would have additional characters as well. Besides, a bit or two offset would cause the whole thing to crash.
The
spdy/2
version of the headers definitely does not include the prepended colon:headers: { accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8', 'accept-charset': 'ISO-8859-1,utf-8;q=0.7,*;q=0.3', 'accept-encoding': 'gzip,deflate,sdch', 'accept-language': 'en-US,en;q=0.8', 'cache-control': 'no-cache', host: 'localhost:3000', method: 'GET', pragma: 'no-cache', scheme: 'https', url: '/', 'user-agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/536.8 (KHTML, like Gecko) Chrome/20.0.1105.0 Safari/536.8', version: 'HTTP/1.1' }So, I manually remove the colons from the header names in spdy/3:
protocol.parseHeaders = function parseHeaders(pairs) { // ... while(count > 0) { var k = readString(), v = readString(); k = k.replace(/:/, ''); headers[k] = v; count--; } return headers; };That gives me better headers:
headers: { host: 'localhost:3000', method: 'GET', path: '/', scheme: 'https', version: 'HTTP/1.1', accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8', 'accept-charset': 'ISO-8859-1,utf-8;q=0.7,*;q=0.3', 'accept-encoding': 'gzip,deflate,sdch', 'accept-language': 'en-US,en;q=0.8', 'cache-control': 'no-cache', pragma: 'no-cache', 'user-agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/536.8 (KHTML, like Gecko) Chrome/20.0.1105.0 Safari/536.8' }But still no response or even an attempt at a response.
Hrm... the spdy/3 SYN_STREAM does not have a url—could that be it?
protocol.parseHeaders = function parseHeaders(pairs) { // ... while(count > 0) { var k = readString(), v = readString(); k = k.replace(/:/, ''); headers[k] = v; if (k == 'path') { headers['url'] = v; } count--; } return headers; };As expected, that does produce a url request header:
headers: { host: 'localhost:3000', method: 'GET', path: '/', url: '/', scheme: 'https', version: 'HTTP/1.1', // ... }But, more importantly, I finally move past my block. The response is now being sent back to the browser:
writeHead replyFrame writeHead write <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"><html><head><title>Express</title><link rel="stylesheet" href="/stylesheets/style.css"/><script src="/main.js"></script></head><body><h1>Express</h1><p>Welcome to Express</p></body></html> ...Unfortunately, this does not quite work as a server error still arises. But at least it is a different error this time. Tantalizingly close, I have to call it a night.
Update: The colon headers are, of course, part of the spec. Folding them back into a new
url
header is necessary, but removing the colons was not. It seems that the response also needs colon headers—hopefully that accounts for most of my remaining problems.Day #366
No comments:
Post a Comment