I “think” the root of the problem might be that sync gateway is ignoring my SyncGatewaySession cookie as it thinks hasn’t originated from the right location, due to my dev / testing setup. From the docs: “For the cookie to be recognized, your site must be configured so that your app’s API and the gateway appear on the same public host name and port.”
See this line: https://github.com/couchbase/sync_gateway/blob/d0d514107b60cf56b19aa5089306de06459cbf3b/src/github.com/couchbase/sync_gateway/rest/routing.go#L229
My sync gateway runs on sync.mydomain.com, port 80 and is obviously also available on localhost from that box. The current sg config is this gist: https://gist.github.com/derekdon/349ff3d95197e2d66578. I’ve just added some CORS entries in an effort to make this work.
"CORS": {
"Origin": ["http://localhost:8080", "http://localhost:9000", "http://localhost:3000"],
"LoginOrigin": ["http://localhost:8080", "http://localhost:9000", "http://localhost:3000"],
"Headers": ["Content-Type"],
"MaxAge": 17280000
}
Current dev / testing setup and flow:
I ssh into the box with port forwarding to the sg ports.
ssh d2 -L localhost:4985:localhost:4985 -L localhost:4984:localhost:4984
1: Ionic / Angular running on localhost:8080 on my laptop.
2: App makes a request to a local cors enabled node server running on localhost:3000 to register a user.
3: Node app does some custom auth stuff, sets a jwt, and posts to sg http://localhost:4985/mybucket/_user which creates the user just fine. It then posts to sg http://localhost:4985/mybucket/_session to create a session just fine, and sets the resulting cookie on the response header.
4: Now my app can use privileged apis due to the Bearer token, and I can see the Cookie in the header… So now I can create some local pouchdb docs, and try to replicate to sg, and on doing so always get prompted for a login, the same way I would if I visited sync.mydomain.com/mybucket directly via the browser.
I tied replicating the app local pouchdb to http://localhost:4984/mybucket and to sync.mydomain.com/mybucket. (didn’t really expect the latter to work anyway.)
What I really want and what I’ve started to do now is create a proxy in the node app to sg. So the ionic app hits http://localhost:3000/api/v0/auth to login / register, followed by http://localhost:3000/api/v0/sync to replicate. To proxy the requests I’ve installed node-http-proxy, and I’m hoping to be able to route all the syncing via this and update the headers if needed.
'use strict';
var express = require('express'),
router = express.Router(),
config = require('module/config'),
httpProxy = require('http-proxy'),
syncProxy = httpProxy.createProxyServer();
// To modify the proxy connection before data is sent
syncProxy.on('proxyReq', function(proxyReq, req, res, options) {
// Try anything...
proxyReq.setHeader('Host', 'http://localhost:8080');
proxyReq.setHeader('Origin', 'http://localhost:8080');
proxyReq.setHeader('X-Special-Proxy-Header', 'foobar');
});
router.all('/*', function(req, res){
syncProxy.web(req, res, { target: config.SG_CONFIG.PUBLIC_ENDPOINT});
});
module.exports = router;
So if I just use the REST client in intellij with the Cookie set manually (just grabbing them from the browser), and do a GET on http://localhost:3000/api/v0/sync, I get:
HTTP/1.1 401 Unauthorized
X-Powered-By: Express
Vary: Origin
access-control-allow-credentials: true
access-control-allow-headers: Content-Type
access-control-allow-origin: http://localhost:3000 (<< This can be 8080 either depending on what I try...)
content-type: application/json
server: Couchbase Sync Gateway/unofficial
www-authenticate: Basic realm="Couchbase Sync Gateway"
date: Thu, 23 Jul 2015 21:40:34 GMT
content-length: 50
connection: close
I know this is a bit funky re port forwarding etc… but I don’t want to have to deploy it to see it working if I can help it. Any ideas?