forked from coolaj86/telebit.js
		
	working: manage token with client
This commit is contained in:
		
							parent
							
								
									fce8e366c6
								
							
						
					
					
						commit
						5584638907
					
				
							
								
								
									
										1
									
								
								.gitignore
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										1
									
								
								.gitignore
									
									
									
									
										vendored
									
									
								
							| @ -1,5 +1,6 @@ | |||||||
| node_modules.* | node_modules.* | ||||||
| *.*.sw* | *.*.sw* | ||||||
|  | etc/acme/ | ||||||
| bin/node | bin/node | ||||||
| bin/npm | bin/npm | ||||||
| bin/npx | bin/npx | ||||||
|  | |||||||
| @ -264,7 +264,8 @@ function askForConfig(state, mainCb) { | |||||||
|         var jwt = require('jsonwebtoken'); |         var jwt = require('jsonwebtoken'); | ||||||
|         resp = (resp || '').trim(); |         resp = (resp || '').trim(); | ||||||
|         try { |         try { | ||||||
|           state.config.token = jwt.decode(resp); |           jwt.decode(resp); | ||||||
|  |           state.config.token = resp; | ||||||
|         } catch(e) { |         } catch(e) { | ||||||
|           // is not jwt
 |           // is not jwt
 | ||||||
|         } |         } | ||||||
| @ -474,6 +475,13 @@ function makeRpc(key) { | |||||||
| function packConfig(config) { | function packConfig(config) { | ||||||
|   return Object.keys(config).map(function (key) { |   return Object.keys(config).map(function (key) { | ||||||
|     var val = config[key]; |     var val = config[key]; | ||||||
|  |     if ('undefined' === val) { | ||||||
|  |       throw new Error("'undefined' used as a string value"); | ||||||
|  |     } | ||||||
|  |     if ('undefined' === typeof val) { | ||||||
|  |       //console.warn('[DEBUG]', key, 'is present but undefined');
 | ||||||
|  |       return; | ||||||
|  |     } | ||||||
|     if (val && 'object' === typeof val && !Array.isArray(val)) { |     if (val && 'object' === typeof val && !Array.isArray(val)) { | ||||||
|       val = JSON.stringify(val); |       val = JSON.stringify(val); | ||||||
|     } |     } | ||||||
| @ -495,19 +503,18 @@ function getToken(err, state) { | |||||||
|       return; |       return; | ||||||
|     } |     } | ||||||
|   , directory: function (dir, next) { |   , directory: function (dir, next) { | ||||||
|       //console.log('Telebit Relay Discovered:');
 |       //console.log('[directory] Telebit Relay Discovered:');
 | ||||||
|       state._apiDirectory = dir; |  | ||||||
|       //console.log(dir);
 |       //console.log(dir);
 | ||||||
|       //console.log();
 |       state._apiDirectory = dir; | ||||||
|       next(); |       next(); | ||||||
|     } |     } | ||||||
|   , tunnelUrl: function (tunnelUrl, next) { |   , tunnelUrl: function (tunnelUrl, next) { | ||||||
|       //console.log('Telebit Relay Tunnel Socket:', tunnelUrl);
 |       //console.log('[tunnelUrl] Telebit Relay Tunnel Socket:', tunnelUrl);
 | ||||||
|       state.wss = tunnelUrl; |       state.wss = tunnelUrl; | ||||||
|       next(); |       next(); | ||||||
|     } |     } | ||||||
|   , requested: function (authReq, next) { |   , requested: function (authReq, next) { | ||||||
|       //console.log("Pairing Requested");
 |       //console.log("[requested] Pairing Requested");
 | ||||||
|       state.config._otp = state.config._otp = authReq.otp; |       state.config._otp = state.config._otp = authReq.otp; | ||||||
| 
 | 
 | ||||||
|       if (!state.config.token && state._can_pair) { |       if (!state.config.token && state._can_pair) { | ||||||
| @ -527,12 +534,11 @@ function getToken(err, state) { | |||||||
|       next(); |       next(); | ||||||
|     } |     } | ||||||
|   , connect: function (pretoken, next) { |   , connect: function (pretoken, next) { | ||||||
|       //console.log("Enabling Pairing Locally...");
 |       //console.log("[connect] Enabling Pairing Locally...");
 | ||||||
|       state.config.pretoken = pretoken; |       state.config.pretoken = pretoken; | ||||||
|       state._connecting = true; |       state._connecting = true; | ||||||
| 
 | 
 | ||||||
|       // TODO use php-style object querification
 |       // TODO use php-style object querification
 | ||||||
| // TODO XXX
 |  | ||||||
|       utils.putConfig('config', packConfig(state.config), function (err/*, body*/) { |       utils.putConfig('config', packConfig(state.config), function (err/*, body*/) { | ||||||
|         if (err) { |         if (err) { | ||||||
|           state._error = err; |           state._error = err; | ||||||
| @ -545,15 +551,19 @@ function getToken(err, state) { | |||||||
|       }); |       }); | ||||||
|     } |     } | ||||||
|   , offer: function (token, next) { |   , offer: function (token, next) { | ||||||
|       //console.log("Pairing Enabled by Relay");
 |       //console.log("[offer] Pairing Enabled by Relay");
 | ||||||
|       state.config.token = token; |       state.config.token = token; | ||||||
|       if (state._error) { |       if (state._error) { | ||||||
|         return; |         return; | ||||||
|       } |       } | ||||||
|       if (state._connecting) { |  | ||||||
|         return; |  | ||||||
|       } |  | ||||||
|       state._connecting = true; |       state._connecting = true; | ||||||
|  |       console.log("Token Offered:"); | ||||||
|  |       console.log(token); | ||||||
|  |       try { | ||||||
|  |         console.log(require('jsonwebtoken').decode(token)); | ||||||
|  |       } catch(e) { | ||||||
|  |         console.warn("[warning] could not decode token"); | ||||||
|  |       } | ||||||
|       utils.putConfig('config', packConfig(state.config), function (err/*, body*/) { |       utils.putConfig('config', packConfig(state.config), function (err/*, body*/) { | ||||||
|         if (err) { |         if (err) { | ||||||
|           state._error = err; |           state._error = err; | ||||||
| @ -566,13 +576,13 @@ function getToken(err, state) { | |||||||
|       }); |       }); | ||||||
|     } |     } | ||||||
|   , granted: function (_, next) { |   , granted: function (_, next) { | ||||||
|       //console.log("Pairing complete!");
 |       //console.log("[grant] Pairing complete!");
 | ||||||
|       next(); |       next(); | ||||||
|     } |     } | ||||||
|   , end: function () { |   , end: function () { | ||||||
|       utils.putConfig('enable', [], function (err) { |       utils.putConfig('enable', [], function (err) { | ||||||
|         if (err) { console.error(err); return; } |         if (err) { console.error(err); return; } | ||||||
|         //console.info("Success");
 |         console.info("[end] Success"); | ||||||
| 
 | 
 | ||||||
|         // workaround for https://github.com/nodejs/node/issues/21319
 |         // workaround for https://github.com/nodejs/node/issues/21319
 | ||||||
|         if (state._useTty) { |         if (state._useTty) { | ||||||
| @ -644,7 +654,7 @@ function handleConfig(err, config) { | |||||||
|       state.config.relay = 'telebit.cloud'; |       state.config.relay = 'telebit.cloud'; | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     console.log("question the user?", Date.now()); |     //console.log("question the user?", Date.now());
 | ||||||
|     askForConfig(state, function (err, state) { |     askForConfig(state, function (err, state) { | ||||||
|       // no errors actually get passed, so this is just future-proofing
 |       // no errors actually get passed, so this is just future-proofing
 | ||||||
|       if (err) { throw err; } |       if (err) { throw err; } | ||||||
| @ -653,7 +663,7 @@ function handleConfig(err, config) { | |||||||
|         state.config._otp = common.otp(); |         state.config._otp = common.otp(); | ||||||
|       } |       } | ||||||
| 
 | 
 | ||||||
|       console.log("done questioning:", Date.now()); |       //console.log("done questioning:", Date.now());
 | ||||||
|       state.relay = state.config.relay; |       state.relay = state.config.relay; | ||||||
|       if (!state.token && !state.config.token) { |       if (!state.token && !state.config.token) { | ||||||
|         getToken(err, state); |         getToken(err, state); | ||||||
| @ -664,7 +674,7 @@ function handleConfig(err, config) { | |||||||
|     return; |     return; | ||||||
|   } |   } | ||||||
| 
 | 
 | ||||||
|   console.log("no questioning:"); |   //console.log("no questioning:");
 | ||||||
|   parseCli(state); |   parseCli(state); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | |||||||
| @ -70,6 +70,7 @@ var tokenpath = path.join(path.dirname(confpath), 'access_token.txt'); | |||||||
| var token; | var token; | ||||||
| try { | try { | ||||||
|   token = fs.readFileSync(tokenpath, 'ascii').trim(); |   token = fs.readFileSync(tokenpath, 'ascii').trim(); | ||||||
|  |   console.log('[DEBUG] access_token', typeof token, token); | ||||||
| } catch(e) { | } catch(e) { | ||||||
|   // ignore
 |   // ignore
 | ||||||
| } | } | ||||||
| @ -129,6 +130,8 @@ function serveControlsHelper() { | |||||||
|     // without proper config
 |     // without proper config
 | ||||||
|     //
 |     //
 | ||||||
|     function saveAndReport(err, _tun) { |     function saveAndReport(err, _tun) { | ||||||
|  |       console.log('[DEBUG] saveAndReport config write', confpath); | ||||||
|  |       console.log(YAML.safeDump(snakeCopy(state.config))); | ||||||
|       if (err) { throw err; } |       if (err) { throw err; } | ||||||
|       tun = _tun; |       tun = _tun; | ||||||
|       fs.writeFile(confpath, YAML.safeDump(snakeCopy(state.config)), function (err) { |       fs.writeFile(confpath, YAML.safeDump(snakeCopy(state.config)), function (err) { | ||||||
| @ -174,15 +177,27 @@ function serveControlsHelper() { | |||||||
|       } |       } | ||||||
|       state.otp = conf._otp || '0000'; // this should only be done on the client side
 |       state.otp = conf._otp || '0000'; // this should only be done on the client side
 | ||||||
|       state.config.relay = conf.relay || state.config.relay || ''; |       state.config.relay = conf.relay || state.config.relay || ''; | ||||||
|  |       console.log(); | ||||||
|  |       console.log('conf.token', typeof conf.token, conf.token); | ||||||
|  |       console.log('state.config.token', typeof state.config.token, state.config.token); | ||||||
|       state.config.token = conf.token || state.config.token || null; |       state.config.token = conf.token || state.config.token || null; | ||||||
|       state.config.secret = conf.secret || state.config.secret || null; |       state.config.secret = conf.secret || state.config.secret || null; | ||||||
|       state.pretoken = conf.pretoken || state.config.pretoken || null; |       state.pretoken = conf.pretoken || state.config.pretoken || null; | ||||||
|       if (state.secret) { |       if (state.secret) { | ||||||
|  |         console.log('state.secret'); | ||||||
|         state.token = common.signToken(state); |         state.token = common.signToken(state); | ||||||
|       } |       } | ||||||
|       if (!state.token) { |       if (!state.token) { | ||||||
|  |         console.log('!state.token'); | ||||||
|         state.token = conf._token; |         state.token = conf._token; | ||||||
|       } |       } | ||||||
|  |       console.log(); | ||||||
|  |       console.log('JSON.stringify(conf)'); | ||||||
|  |       console.log(JSON.stringify(conf)); | ||||||
|  |       console.log(); | ||||||
|  |       console.log('JSON.stringify(state)'); | ||||||
|  |       console.log(JSON.stringify(state)); | ||||||
|  |       console.log(); | ||||||
|       if ('undefined' !== typeof conf.newsletter) { |       if ('undefined' !== typeof conf.newsletter) { | ||||||
|         state.config.newsletter = conf.newsletter; |         state.config.newsletter = conf.newsletter; | ||||||
|       } |       } | ||||||
| @ -209,6 +224,7 @@ function serveControlsHelper() { | |||||||
|       } |       } | ||||||
| 
 | 
 | ||||||
|       if (!state.config.relay || !state.config.email || !state.config.agreeTos) { |       if (!state.config.relay || !state.config.email || !state.config.agreeTos) { | ||||||
|  |         console.log('aborting for some reason'); | ||||||
|         res.statusCode = 400; |         res.statusCode = 400; | ||||||
| 
 | 
 | ||||||
|         res.setHeader('Content-Type', 'application/json'); |         res.setHeader('Content-Type', 'application/json'); | ||||||
| @ -225,16 +241,20 @@ function serveControlsHelper() { | |||||||
|       } |       } | ||||||
| 
 | 
 | ||||||
|       if (tun) { |       if (tun) { | ||||||
|  |         console.log('ending existing tunnel, starting anew'); | ||||||
|         tun.end(function () { |         tun.end(function () { | ||||||
|  |           console.log('success ending'); | ||||||
|           rawTunnel(saveAndReport); |           rawTunnel(saveAndReport); | ||||||
|         }); |         }); | ||||||
|         tun = null; |         tun = null; | ||||||
|         setTimeout(function () { |         setTimeout(function () { | ||||||
|           if (!tun) { |           if (!tun) { | ||||||
|  |             console.log('failed to end, but starting anyway'); | ||||||
|             rawTunnel(saveAndReport); |             rawTunnel(saveAndReport); | ||||||
|           } |           } | ||||||
|         }, 3000); |         }, 3000); | ||||||
|       } else { |       } else { | ||||||
|  |         console.log('no tunnel, starting anew'); | ||||||
|         rawTunnel(saveAndReport); |         rawTunnel(saveAndReport); | ||||||
|       } |       } | ||||||
|       return; |       return; | ||||||
| @ -602,6 +622,7 @@ function rawTunnel(rawCb) { | |||||||
|     state.insecure = state.config.relay_ignore_invalid_certificates; |     state.insecure = state.config.relay_ignore_invalid_certificates; | ||||||
|     // { relay, config, servernames, ports, sortingHat, net, insecure, token, handlers, greenlockConfig }
 |     // { relay, config, servernames, ports, sortingHat, net, insecure, token, handlers, greenlockConfig }
 | ||||||
| 
 | 
 | ||||||
|  |     console.log("[DEBUG] token", typeof token, token); | ||||||
|     tun = remote.connect({ |     tun = remote.connect({ | ||||||
|       relay: state.relay |       relay: state.relay | ||||||
|     , wss: state.wss |     , wss: state.wss | ||||||
| @ -659,8 +680,13 @@ state.handlers = { | |||||||
|     }); |     }); | ||||||
|   } |   } | ||||||
| , access_token: function (opts) { | , access_token: function (opts) { | ||||||
|     state.token = opts.jwt; |     if ('undefined' === opts.jwt || !opts.jwt) { | ||||||
|     state.config.token = opts.jwt; |       console.error("Granted empty access token... ??"); | ||||||
|  |       console.error(JSON.stringify(opts)); | ||||||
|  |       return; | ||||||
|  |     } | ||||||
|  |     state.token = opts.jwt || opts.access_token; | ||||||
|  |     state.config.token = opts.jwt || opts.access_token; | ||||||
|     console.info("Updating '" + tokenpath + "' with new token:"); |     console.info("Updating '" + tokenpath + "' with new token:"); | ||||||
|     try { |     try { | ||||||
|       require('fs').writeFileSync(tokenpath, opts.jwt); |       require('fs').writeFileSync(tokenpath, opts.jwt); | ||||||
|  | |||||||
| @ -32,6 +32,9 @@ function _connect(state) { | |||||||
|     state.sortingHat = "./sorting-hat.js"; |     state.sortingHat = "./sorting-hat.js"; | ||||||
|   } |   } | ||||||
|   if (state.token) { |   if (state.token) { | ||||||
|  |     if ('undefined' === state.token) { | ||||||
|  |       throw new Error("passed string 'undefined' as token"); | ||||||
|  |     } | ||||||
|     tokens.push(state.token); |     tokens.push(state.token); | ||||||
|   } |   } | ||||||
| 
 | 
 | ||||||
| @ -569,6 +572,12 @@ function _connect(state) { | |||||||
|       } |       } | ||||||
|     } |     } | ||||||
|   , append: function (token) { |   , append: function (token) { | ||||||
|  |       if (!token) { | ||||||
|  |         throw new Error("attempted to append empty token"); | ||||||
|  |       } | ||||||
|  |       if ('undefined' === token) { | ||||||
|  |         throw new Error("attempted to append token as the string 'undefined'"); | ||||||
|  |       } | ||||||
|       if (tokens.indexOf(token) >= 0) { |       if (tokens.indexOf(token) >= 0) { | ||||||
|         return PromiseA.resolve(); |         return PromiseA.resolve(); | ||||||
|       } |       } | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user