Hex Artifact Content
Not logged in

Artifact bd32e22952848f4bf913eb79c6b5d8c24f33968e:


0000: 69 6d 70 6f 72 74 20 72 65 64 75 63 74 20 3d 20  import reduct = 
0010: 72 65 71 75 69 72 65 28 27 72 65 64 75 63 74 27  require('reduct'
0020: 29 0a 69 6d 70 6f 72 74 20 43 6f 6e 66 69 67 20  ).import Config 
0030: 66 72 6f 6d 20 27 2e 2f 63 6f 6e 66 69 67 27 0a  from './config'.
0040: 69 6d 70 6f 72 74 20 52 6f 75 74 69 6e 67 54 61  import RoutingTa
0050: 62 6c 65 20 66 72 6f 6d 20 27 2e 2f 72 6f 75 74  ble from './rout
0060: 69 6e 67 2d 74 61 62 6c 65 27 0a 69 6d 70 6f 72  ing-table'.impor
0070: 74 20 52 6f 75 74 65 42 72 6f 61 64 63 61 73 74  t RouteBroadcast
0080: 65 72 20 66 72 6f 6d 20 27 2e 2f 72 6f 75 74 65  er from './route
0090: 2d 62 72 6f 61 64 63 61 73 74 65 72 27 0a 69 6d  -broadcaster'.im
00a0: 70 6f 72 74 20 7b 20 66 6f 72 6d 61 74 52 6f 75  port { formatRou
00b0: 74 69 6e 67 54 61 62 6c 65 41 73 4a 73 6f 6e 20  tingTableAsJson 
00c0: 7d 20 66 72 6f 6d 20 27 2e 2e 2f 72 6f 75 74 69  } from '../routi
00d0: 6e 67 2f 75 74 69 6c 73 27 0a 69 6d 70 6f 72 74  ng/utils'.import
00e0: 20 7b 20 53 65 72 76 65 72 2c 20 53 65 72 76 65   { Server, Serve
00f0: 72 52 65 71 75 65 73 74 2c 20 53 65 72 76 65 72  rRequest, Server
0100: 52 65 73 70 6f 6e 73 65 20 7d 20 66 72 6f 6d 20  Response } from 
0110: 27 68 74 74 70 27 0a 0a 69 6d 70 6f 72 74 20 7b  'http'..import {
0120: 20 63 72 65 61 74 65 20 61 73 20 63 72 65 61 74   create as creat
0130: 65 4c 6f 67 67 65 72 20 7d 20 66 72 6f 6d 20 27  eLogger } from '
0140: 2e 2e 2f 63 6f 6d 6d 6f 6e 2f 6c 6f 67 27 0a 63  ../common/log'.c
0150: 6f 6e 73 74 20 6c 6f 67 20 3d 20 63 72 65 61 74  onst log = creat
0160: 65 4c 6f 67 67 65 72 28 27 61 64 6d 69 6e 2d 61  eLogger('admin-a
0170: 70 69 27 29 0a 0a 65 78 70 6f 72 74 20 64 65 66  pi')..export def
0180: 61 75 6c 74 20 63 6c 61 73 73 20 41 64 6d 69 6e  ault class Admin
0190: 41 70 69 20 7b 0a 20 20 70 72 69 76 61 74 65 20  Api {.  private 
01a0: 63 6f 6e 66 69 67 3a 20 43 6f 6e 66 69 67 0a 20  config: Config. 
01b0: 20 70 72 69 76 61 74 65 20 72 6f 75 74 69 6e 67   private routing
01c0: 54 61 62 6c 65 3a 20 52 6f 75 74 69 6e 67 54 61  Table: RoutingTa
01d0: 62 6c 65 0a 20 20 70 72 69 76 61 74 65 20 72 6f  ble.  private ro
01e0: 75 74 65 42 72 6f 61 64 63 61 73 74 65 72 3a 20  uteBroadcaster: 
01f0: 52 6f 75 74 65 42 72 6f 61 64 63 61 73 74 65 72  RouteBroadcaster
0200: 0a 0a 20 20 70 72 69 76 61 74 65 20 73 65 72 76  ..  private serv
0210: 65 72 3f 3a 20 53 65 72 76 65 72 0a 0a 20 20 63  er?: Server..  c
0220: 6f 6e 73 74 72 75 63 74 6f 72 20 28 64 65 70 73  onstructor (deps
0230: 3a 20 72 65 64 75 63 74 2e 49 6e 6a 65 63 74 6f  : reduct.Injecto
0240: 72 29 20 7b 0a 20 20 20 20 74 68 69 73 2e 63 6f  r) {.    this.co
0250: 6e 66 69 67 20 3d 20 64 65 70 73 28 43 6f 6e 66  nfig = deps(Conf
0260: 69 67 29 0a 20 20 20 20 74 68 69 73 2e 72 6f 75  ig).    this.rou
0270: 74 69 6e 67 54 61 62 6c 65 20 3d 20 64 65 70 73  tingTable = deps
0280: 28 52 6f 75 74 69 6e 67 54 61 62 6c 65 29 0a 20  (RoutingTable). 
0290: 20 20 20 74 68 69 73 2e 72 6f 75 74 65 42 72 6f     this.routeBro
02a0: 61 64 63 61 73 74 65 72 20 3d 20 64 65 70 73 28  adcaster = deps(
02b0: 52 6f 75 74 65 42 72 6f 61 64 63 61 73 74 65 72  RouteBroadcaster
02c0: 29 0a 20 20 7d 0a 0a 20 20 6c 69 73 74 65 6e 20  ).  }..  listen 
02d0: 28 29 20 7b 0a 20 20 20 20 63 6f 6e 73 74 20 7b  () {.    const {
02e0: 0a 20 20 20 20 20 20 61 64 6d 69 6e 41 70 69 20  .      adminApi 
02f0: 3d 20 66 61 6c 73 65 2c 0a 20 20 20 20 20 20 61  = false,.      a
0300: 64 6d 69 6e 41 70 69 48 6f 73 74 20 3d 20 27 31  dminApiHost = '1
0310: 32 37 2e 30 2e 30 2e 31 27 2c 0a 20 20 20 20 20  27.0.0.1',.     
0320: 20 61 64 6d 69 6e 41 70 69 50 6f 72 74 20 3d 20   adminApiPort = 
0330: 37 37 38 30 0a 20 20 20 20 7d 20 3d 20 74 68 69  7780.    } = thi
0340: 73 2e 63 6f 6e 66 69 67 0a 0a 20 20 20 20 6c 6f  s.config..    lo
0350: 67 2e 69 6e 66 6f 28 27 6c 69 73 74 65 6e 20 63  g.info('listen c
0360: 61 6c 6c 65 64 27 29 0a 0a 20 20 20 20 69 66 20  alled')..    if 
0370: 28 61 64 6d 69 6e 41 70 69 29 20 7b 0a 20 20 20  (adminApi) {.   
0380: 20 20 20 6c 6f 67 2e 69 6e 66 6f 28 27 61 64 6d     log.info('adm
0390: 69 6e 20 61 70 69 20 6c 69 73 74 65 6e 69 6e 67  in api listening
03a0: 2e 20 68 6f 73 74 3d 25 73 20 70 6f 72 74 3d 25  . host=%s port=%
03b0: 73 27 2c 20 61 64 6d 69 6e 41 70 69 48 6f 73 74  s', adminApiHost
03c0: 2c 20 61 64 6d 69 6e 41 70 69 50 6f 72 74 29 0a  , adminApiPort).
03d0: 20 20 20 20 20 20 74 68 69 73 2e 73 65 72 76 65        this.serve
03e0: 72 20 3d 20 6e 65 77 20 53 65 72 76 65 72 28 29  r = new Server()
03f0: 0a 20 20 20 20 20 20 74 68 69 73 2e 73 65 72 76  .      this.serv
0400: 65 72 2e 6c 69 73 74 65 6e 28 61 64 6d 69 6e 41  er.listen(adminA
0410: 70 69 50 6f 72 74 2c 20 61 64 6d 69 6e 41 70 69  piPort, adminApi
0420: 48 6f 73 74 29 0a 20 20 20 20 20 20 74 68 69 73  Host).      this
0430: 2e 73 65 72 76 65 72 2e 6f 6e 28 27 72 65 71 75  .server.on('requ
0440: 65 73 74 27 2c 20 74 68 69 73 2e 68 61 6e 64 6c  est', this.handl
0450: 65 52 65 71 75 65 73 74 2e 62 69 6e 64 28 74 68  eRequest.bind(th
0460: 69 73 29 29 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a  is)).    }.  }..
0470: 20 20 70 72 69 76 61 74 65 20 68 61 6e 64 6c 65    private handle
0480: 52 65 71 75 65 73 74 20 28 72 65 71 3a 20 53 65  Request (req: Se
0490: 72 76 65 72 52 65 71 75 65 73 74 2c 20 72 65 73  rverRequest, res
04a0: 3a 20 53 65 72 76 65 72 52 65 73 70 6f 6e 73 65  : ServerResponse
04b0: 29 20 7b 0a 20 20 20 20 72 65 71 2e 73 65 74 45  ) {.    req.setE
04c0: 6e 63 6f 64 69 6e 67 28 27 75 74 66 38 27 29 0a  ncoding('utf8').
04d0: 0a 20 20 20 20 6c 65 74 20 62 6f 64 79 20 3d 20  .    let body = 
04e0: 27 27 0a 20 20 20 20 72 65 71 2e 6f 6e 28 27 64  ''.    req.on('d
04f0: 61 74 61 27 2c 20 64 61 74 61 20 3d 3e 20 62 6f  ata', data => bo
0500: 64 79 20 2b 3d 20 64 61 74 61 29 0a 20 20 20 20  dy += data).    
0510: 72 65 71 2e 6f 6e 28 27 65 6e 64 27 2c 20 28 29  req.on('end', ()
0520: 20 3d 3e 20 7b 0a 20 20 20 20 20 20 74 72 79 20   => {.      try 
0530: 7b 0a 20 20 20 20 20 20 20 20 73 77 69 74 63 68  {.        switch
0540: 20 28 72 65 71 2e 75 72 6c 29 20 7b 0a 20 20 20   (req.url) {.   
0550: 20 20 20 20 20 20 20 63 61 73 65 20 27 2f 73 74         case '/st
0560: 61 74 75 73 27 3a 0a 20 20 20 20 20 20 20 20 20  atus':.         
0570: 20 20 20 72 65 73 2e 73 74 61 74 75 73 43 6f 64     res.statusCod
0580: 65 20 3d 20 32 30 30 0a 20 20 20 20 20 20 20 20  e = 200.        
0590: 20 20 20 20 72 65 73 2e 73 65 74 48 65 61 64 65      res.setHeade
05a0: 72 28 27 43 6f 6e 74 65 6e 74 2d 54 79 70 65 27  r('Content-Type'
05b0: 2c 20 27 61 70 70 6c 69 63 61 74 69 6f 6e 2f 6a  , 'application/j
05c0: 73 6f 6e 27 29 0a 20 20 20 20 20 20 20 20 20 20  son').          
05d0: 20 20 72 65 73 2e 65 6e 64 28 4a 53 4f 4e 2e 73    res.end(JSON.s
05e0: 74 72 69 6e 67 69 66 79 28 74 68 69 73 2e 67 65  tringify(this.ge
05f0: 74 53 74 61 74 75 73 28 29 29 29 0a 20 20 20 20  tStatus())).    
0600: 20 20 20 20 20 20 20 20 62 72 65 61 6b 0a 20 20          break.  
0610: 20 20 20 20 20 20 20 20 63 61 73 65 20 27 2f 72          case '/r
0620: 6f 75 74 69 6e 67 27 3a 0a 20 20 20 20 20 20 20  outing':.       
0630: 20 20 20 20 20 72 65 73 2e 73 74 61 74 75 73 43       res.statusC
0640: 6f 64 65 20 3d 20 32 30 30 0a 20 20 20 20 20 20  ode = 200.      
0650: 20 20 20 20 20 20 72 65 73 2e 73 65 74 48 65 61        res.setHea
0660: 64 65 72 28 27 43 6f 6e 74 65 6e 74 2d 54 79 70  der('Content-Typ
0670: 65 27 2c 20 27 61 70 70 6c 69 63 61 74 69 6f 6e  e', 'application
0680: 2f 6a 73 6f 6e 27 29 0a 20 20 20 20 20 20 20 20  /json').        
0690: 20 20 20 20 72 65 73 2e 65 6e 64 28 4a 53 4f 4e      res.end(JSON
06a0: 2e 73 74 72 69 6e 67 69 66 79 28 74 68 69 73 2e  .stringify(this.
06b0: 67 65 74 52 6f 75 74 69 6e 67 53 74 61 74 75 73  getRoutingStatus
06c0: 28 29 29 29 0a 20 20 20 20 20 20 20 20 20 20 20  ())).           
06d0: 20 62 72 65 61 6b 0a 20 20 20 20 20 20 20 20 20   break.         
06e0: 20 64 65 66 61 75 6c 74 3a 0a 20 20 20 20 20 20   default:.      
06f0: 20 20 20 20 20 20 72 65 73 2e 73 74 61 74 75 73        res.status
0700: 43 6f 64 65 20 3d 20 34 30 34 0a 20 20 20 20 20  Code = 404.     
0710: 20 20 20 20 20 20 20 72 65 73 2e 73 65 74 48 65         res.setHe
0720: 61 64 65 72 28 27 43 6f 6e 74 65 6e 74 2d 54 79  ader('Content-Ty
0730: 70 65 27 2c 20 27 74 65 78 74 2f 70 6c 61 69 6e  pe', 'text/plain
0740: 27 29 0a 20 20 20 20 20 20 20 20 20 20 20 20 72  ').            r
0750: 65 73 2e 65 6e 64 28 27 4e 6f 74 20 46 6f 75 6e  es.end('Not Foun
0760: 64 27 29 0a 20 20 20 20 20 20 20 20 7d 0a 20 20  d').        }.  
0770: 20 20 20 20 7d 20 63 61 74 63 68 20 28 65 29 20      } catch (e) 
0780: 7b 0a 20 20 20 20 20 20 20 20 6c 65 74 20 65 72  {.        let er
0790: 72 20 3d 20 65 0a 20 20 20 20 20 20 20 20 69 66  r = e.        if
07a0: 20 28 21 65 20 7c 7c 20 74 79 70 65 6f 66 20 65   (!e || typeof e
07b0: 20 21 3d 3d 20 27 6f 62 6a 65 63 74 27 29 20 7b   !== 'object') {
07c0: 0a 20 20 20 20 20 20 20 20 20 20 65 72 72 20 3d  .          err =
07d0: 20 6e 65 77 20 45 72 72 6f 72 28 27 6e 6f 6e 2d   new Error('non-
07e0: 6f 62 6a 65 63 74 20 74 68 72 6f 77 6e 2e 20 65  object thrown. e
07f0: 72 72 6f 72 3d 27 20 2b 20 65 29 0a 20 20 20 20  rror=' + e).    
0800: 20 20 20 20 7d 0a 0a 20 20 20 20 20 20 20 20 6c      }..        l
0810: 6f 67 2e 77 61 72 6e 28 27 65 72 72 6f 72 20 69  og.warn('error i
0820: 6e 20 61 64 6d 69 6e 20 61 70 69 20 72 65 71 75  n admin api requ
0830: 65 73 74 20 68 61 6e 64 6c 65 72 2e 20 65 72 72  est handler. err
0840: 6f 72 3d 25 73 27 2c 20 65 72 72 2e 73 74 61 63  or=%s', err.stac
0850: 6b 20 3f 20 65 72 72 2e 73 74 61 63 6b 20 3a 20  k ? err.stack : 
0860: 65 72 72 29 0a 20 20 20 20 20 20 20 20 72 65 73  err).        res
0870: 2e 73 74 61 74 75 73 43 6f 64 65 20 3d 20 35 30  .statusCode = 50
0880: 30 0a 20 20 20 20 20 20 20 20 72 65 73 2e 73 65  0.        res.se
0890: 74 48 65 61 64 65 72 28 27 43 6f 6e 74 65 6e 74  tHeader('Content
08a0: 2d 54 79 70 65 27 2c 20 27 74 65 78 74 2f 70 6c  -Type', 'text/pl
08b0: 61 69 6e 27 29 0a 20 20 20 20 20 20 20 20 72 65  ain').        re
08c0: 73 2e 65 6e 64 28 53 74 72 69 6e 67 28 65 72 72  s.end(String(err
08d0: 29 29 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 7d  )).      }.    }
08e0: 29 0a 20 20 7d 0a 0a 20 20 70 72 69 76 61 74 65  ).  }..  private
08f0: 20 67 65 74 53 74 61 74 75 73 20 28 29 20 7b 0a   getStatus () {.
0900: 20 20 20 20 72 65 74 75 72 6e 20 7b 0a 20 20 20      return {.   
0910: 20 20 20 6c 6f 63 61 6c 52 6f 75 74 69 6e 67 54     localRoutingT
0920: 61 62 6c 65 3a 20 66 6f 72 6d 61 74 52 6f 75 74  able: formatRout
0930: 69 6e 67 54 61 62 6c 65 41 73 4a 73 6f 6e 28 74  ingTableAsJson(t
0940: 68 69 73 2e 72 6f 75 74 69 6e 67 54 61 62 6c 65  his.routingTable
0950: 29 0a 20 20 20 20 7d 0a 20 20 7d 0a 0a 20 20 70  ).    }.  }..  p
0960: 72 69 76 61 74 65 20 67 65 74 52 6f 75 74 69 6e  rivate getRoutin
0970: 67 53 74 61 74 75 73 20 28 29 20 7b 0a 20 20 20  gStatus () {.   
0980: 20 72 65 74 75 72 6e 20 74 68 69 73 2e 72 6f 75   return this.rou
0990: 74 65 42 72 6f 61 64 63 61 73 74 65 72 2e 67 65  teBroadcaster.ge
09a0: 74 53 74 61 74 75 73 28 29 0a 20 20 7d 0a 7d 0a  tStatus().  }.}.