• Jump To … +
    server.coffee src/actionknob.coffee src/autosem.coffee src/bitbucket_kba.coffee src/browserlog.coffee src/datareduction.coffee src/dci.coffee src/dciknob.coffee src/deeseeeye.coffee src/dnd.coffee src/doof.coffee src/formurla-mngr.coffee src/fractalpanel.coffee src/fractalpanel_test.coffee src/front.coffee src/ingestor.coffee src/kbabitbucket.coffee src/knobctrl.coffee src/lib_test.coffee src/nanoclock.coffee src/noodb.coffee src/noodbabstract.coffee src/noodbbrowser.coffee src/noodbbrowser_test.coffee src/noodbsec.coffee src/noorauth.coffee src/noorplugin.coffee src/noorquery.coffee src/noorvm.coffee src/noorwrite.coffee src/quadparser.coffee src/quadparsern3.coffee src/rbac.coffee src/reactor.coffee src/rebase.coffee src/rsrcidx.coffee src/sandboxactions.coffee src/screen_ctx.coffee src/spogi.coffee src/tabular_widget.coffee src/visctrl.coffee src/voicesknob.coffee src/whowhen.coffee src/xsd2native.coffee
  • server.coffee

  • ¶

    http://nickdesaulniers.github.io/blog/2013/08/28/making-great-node-dot-js-modules-with-coffeescript/

  • ¶

    The subtleties of module loading are documented here: https://nodejs.org/api/modules.html

    fs = require('fs')
    path = require('path')
    
    favicon = require('serve-favicon')
    bodyParser = require("body-parser")
    parseForm = bodyParser.urlencoded({ extended: false })
    Log = require('./lib/browserlog').BrowserLog
    cookieParser = require("cookie-parser")
    cookie = require('cookie')
    csrf = require('csurf')
    ejs = require("ejs")
    express = require("express")
    morgan = require("morgan")
  • ¶

    ensure that Proxy is working

    assert = require("assert")
    assert(!!(typeof Proxy), "Proxy is #{typeof Proxy}, start with 'node --harmnony-proxies'")
    Proxy = require('harmony-proxy') # https://github.com/Swatinem/proxy
    assert(new Proxy({},{}),"the harmony-proxy module failed to enable: 'new Proxy({},{}) --> #{new Proxy({}, {})}")
    
    KBABitBucket = require("./lib/kbabitbucket").KBABitBucket
    NooDB = require("./lib/noodbsec").NooDBSecure
    NoorPlugin = require("./lib/noorplugin").NoorPlugin
    permeate = require("./lib/noorplugin").permeate
    NoorAuth = require("./lib/noorauth").NoorAuth
    NoorQuery = require("./lib/noorquery").NoorQuery
    NoorVM = require("./lib/noorvm").NoorVM
    NoorPersist = require("./lib/noorpersist").NoorPersist
    NoorWrite = require("./lib/noorwrite").NoorWrite  # TODO remove this (or use it for RBAC write security?)
    RBAC = require("./lib/rbac") # yup, grab the whole module
    WhoWhen = require("./lib/whowhen").WhoWhen
    
    jsonParser = bodyParser.json()
    urlencodedParser = bodyParser.urlencoded({ extended: false })
    
    make_server = (nopts) ->
      default_opts =
        meta_db: "test_db.nq"
        db_path: "noorondb.sqlite"
        hostname: process.env.NOORON_HOSTNAME or 'localhost'
        PORT: process.env.PORT
  • ¶
    • log_level: “EMERGENCY” # 0
    • log_level: “ALERT” # 1
    • log_level: “CRITICAL” # 2
    • log_level: “ERROR” # 3
    • log_level: “WARNING” # 4
    • log_level: “NOTICE” # 5
    • log_level: “INFO” # 6
    • log_level: “DEBUG” # 7
        log_level: process.env.LOG_LEVEL or "NOTICE"
        use_logging: false
        file_root: process.cwd()
    
      for k,v of default_opts
        if not nopts[k]?
          nopts[k] = v
    
      port = nopts.PORT
      server_uri = process.env.SERVER_URI or nopts.server_uri or  "http://#{nopts.hostname}#{port is 80 or ':' + port}/"
      meta_db = process.env.META_DB or nopts.meta_db
      app = express()
    
      if nopts.use_logging
        app.use(morgan('combined'))
    
      server = require('http').createServer(app)
      sio = require('socket.io')(server)
    
      setUpVHostOrRedir = (templatePath, req, clientArgs) ->
  • ¶

    Returns

    [redirLocation, templateSrc] with possible changes to clientArgs

    SideEffects

    modifies clientArgs by adding properties for the VHost

    Notes:

    The theory of operation here is that ultimately this behaviour will be driven by knowledge, but for now… If a templatePath is sent to us we find the templateSrc and return it. We permit template resolution on the basis of hostname or req.path or whatever, so VHosts can have their own static pages if desired. If no templatePath is resolved then we redirect to the nooron generated content by returning [“/__/“] If templateSrc is calculated for a vhost then return it for rendering If templateSrc is returned then arguments for the template should be placed on clientArgs as a side-effect.

  • ¶

    This works with lines in /etc/hosts like:

    127.0.0.1       nooron.com.localhost
    127.0.0.1       diversus.nooron.com.localhost
    

    Developers surfing to http://diversus.nooron.com.localhost:9998/ can now access their camera

        hostname = req.headers.host.split(':')[0]
        normalized_hostname = hostname.replace(/.localhost$/,'')
        clientArgs.vhost_name = normalized_hostname
        clientArgs.enable_login = true
        clientArgs.close_login_panel ?= false
        clientArgs.default_formurla = "print(\"<h1>setUpVHost(#{hostname}) called</h1>\")"
        clientArgs.speedOverFeatures = false
        clientArgs.suppress_fracpanel_buttons_by_default = false # leave buttons on
  • ¶

    Now permit unique handling on the basis of which site has been hit. Either, calculate a templatePath, or templateSrc, or override the redirLocation

        redirLocation = "/__/"
        if normalized_hostname in ['nooron.com','localhost']
          templatePath ?= "/views/static.html.ejs"
          clientArgs['default_div'] = 'blurb'
          clientArgs.default_formurla = "subjects(g=nrn:metaKB)"
        if normalized_hostname in ['diversus.nooron.com']
  • ¶

    FIXME clean this up

          default_formurla = "above(provid(g=nrn:dvrsdata),listmedia(g=nrn:dvrsdata))"
          default_formurla = "listmedia(g=nrn:dvrsdata)"
          if req.path.length > '/__/'.length
            if not req.path.toString().includes('(')
              video_id = req.path.replace('/__/','')
          else
            redirLocation = "/__/" + default_formurla
            tempatePath = undefined
          video_id ?= 'big_buck_bunny_720p_5mb'
          clientArgs.use_huviz_flower = true
  • ¶

    clientArgs.default_formurla = “listmedia(g=nrn:twentyOldestVideos)”

          clientArgs.default_formurla = default_formurla
          clientArgs.read_kb_qrys = [ # these kbs should be loaded into the client noodb
            [{g: 'nrn:dvrsont'}],
            [{g: 'nrn:oa'}]
          ] # a list of qrys (each a list of terms)
  • ¶

    these kbs should be subscribed to by default if no other kb is specified

          clientArgs.subscribe_kb_qrys = [
  • ¶

    [{g: ‘nrn:dvrsdata’}]

          ] # a list of qrys (each a list of terms)
          clientArgs.write_kb = 'nrn:dvrsdata'
          clientArgs.enable_login = true
          clientArgs.close_login_panel = true
          clientArgs.speedOverFeatures = true
          clientArgs.suppress_fracpanel_buttons_by_default = true # ie on all panels by default
        else if normalized_hostname in ['spangler.gig.gl', 'spangler.nooron.com']
          clientArgs.default_formurla = "spangler()"
  • ¶

    redirLocation = “http://spangler.gig.gl" # we can cause a redirect from here

        if templatePath? and not templateSrc?
  • ¶

    FIXME this should be cached

          templateFullpath = path.join(process.cwd(), templatePath)
          return [null, null, templateFullpath]
          templateSrc = fs.readFileSync(__dirname + templatePath, "utf-8")
        if not templateSrc
          return [redirLocation, null]
        return [null, templateSrc]
  • ¶

    https://www.npmjs.com/package/ejs

      makeResponder = (templatePath, initialArgs) ->
        responder = (req, res) =>
  • ¶

    clone initialArgs as clientArgs so responders for VHosts are unique

          clientArgs = Object.assign({}, initialArgs)
          if req.csrfToken
  • ¶

    FIXME this should likely NOT be shared across VHosts REVIEW(smurp) does this work?

            clientArgs.csrfToken = req.csrfToken()
          clientArgs.__proto__ = nopts # fail back to nopts
          [redirLocation, templateSrc, templateFullpath]  = setUpVHostOrRedir(templatePath, req, clientArgs)
          ejsData = {clientArgs: clientArgs}
          if redirLocation
            res.redirect(redirLocation)
          else if templateFullpath
            ejs.renderFile(templateFullpath, ejsData, {}, (err, str) =>
              if err
                console.log(err)
                res.send(err)
              else
                res.send(str)
              )
          else if templateSrc
            res.send(ejs.render(templateSrc, ejsData))
  • ¶

    SEE https://ejs.co/ under usage options (about half way down the page)

          else
            throw new Error("responder failed for templatePath: #{templatePath}")
        return responder
    
      sister_module_path = path.join(__dirname, "node_modules")
      huviz_module_path = process.env.HUVIZ_PATH or path.join(sister_module_path, 'huviz')
      blossom_module_path =  process.env.BLOSSOM_PATH or path.join(sister_module_path, 'blossom')
      email_login_module_path =  process.env.EMAILLOGIN_PATH or path.join(sister_module_path, 'email-login')
      diversus_flower_module_path = process.env.DIVERSUSFLOWER_PATH or
        __dirname + '/node_modules/diversus-flower/src'
      for k,v of {'HUVIZ_PATH': huviz_module_path, EMAILLOGIN_PATH: email_login_module_path}
        try
          fs.statSync(v).isDirectory()
        catch e
          console.log(k, v)
          throw e
  • ¶

    This is how to access sister modules (huviz, email-login) during local development of them if process.env.NODE_ENV is “development” sister_module_path = “/..”

  • ¶

    TODO https://coffeescript-cookbook.github.io/chapters/classes_and_objects/mixins

      noodb = new NooDB(meta_db, server_uri, nopts)
      noorauth = new NoorAuth(noodb, app)
      noorquery = new NoorQuery(noodb, app) # TODO can this be removed?
      noorwrite = new NoorWrite(noodb, app)
      permeate(NoorVM, noodb)
      noorpersist = new NoorPersist(noodb, app)
    
      THE_SECRET = "BaadSpelingIzLikZekresee" # TODO get secret from env
      cookie_parser = cookieParser(THE_SECRET)
      csrfProtection = csrf({cookie: true})
    
      class AuthCookieParser
        constructor: (@signed_str) ->
          @cookies = cookie.parse(@signed_str)
          @signedCookies = cookieParser.signedCookies(@cookies, THE_SECRET)
          @signedCookies = cookieParser.JSONCookies(@signedCookies)
        get_user: () ->
  • ¶

    token looks like: ‘nooron:session:xf4Jk4n4h_A23932k44’ <--CONSTANT--->_<sess_no>

          if not @user?
            @user = {}
            method_and_contact = @signedCookies.auth.person_uri.split(':')
            contact = {}
            contact[method_and_contact[0]] = method_and_contact[1]
            @user.contacts = [contact]
            @user.userId = @signedCookies.auth.token.split(":")[2].split("_")[0]
            @user.userCURIE = 'nrn:' + @user.userId
          return @user
        get_session_id: () ->
          if not @session_id?
            @session_id = @signedCookies.auth.token.split(":")[2] # eg xf4Jk4n4h_A23932k44'
          return @session_id
  • ¶

    put favicon before logger so it does not get logged app.use(favicon(path.join(__dirname,’public’,’img’,’favicon.ico’)))

      app.set("views", __dirname + "/views") # TODO delete?
  • ¶

    This is an experimental link to permit access to diversus static content

      app.use("/vhost", express.static(path.join(__dirname,'vhosts','diversus.nooron.com','public')))
      app.use("/tmpl", express.static(path.join(__dirname,'vhosts','diversus.nooron.com','tmpl')))
      app.use("/img", express.static(path.join(__dirname,'public','img')))
      app.use("/huviz", express.static(path.join(huviz_module_path, 'lib')))
      app.use("/huviz/docs", express.static(path.join(huviz_module_path, 'docs')))
      app.use("/huviz/doc", express.static(path.join(huviz_module_path, 'doc')))
      app.use("/async", express.static(__dirname + '/node_modules/async/lib'))
      app.use("/underscore", express.static(__dirname + '/node_modules/underscore'))
      app.use("/css/huviz", express.static(path.join(huviz_module_path,"css")))
  • ¶

    app.use(“/vendor/huviz”, express.static(__dirname + “#{{sister_module_path}}/huviz/vendor”))

      app.use("/vendor/huviz", express.static(path.join(huviz_module_path,"vendor")))
      app.use("/jquery-ui", express.static(__dirname + '/vendor/jquery-ui-1.8.20'))
      app.use("/jquery-layout", express.static(__dirname + '/vendor/jquery-layout-1.4.0'))
      app.use("/blockly", express.static(__dirname + '/node_modules/node-blockly/blockly'))
      app.use("/leaflet", express.static(__dirname + '/node_modules/leaflet'))
      app.use("/diversus-flower", express.static(diversus_flower_module_path))
      app.use("/closure-library", express.static(__dirname + '/node_modules/google-closure-library'))
  • ¶

    app.use(“/split-pane”, express.static(__dirname + ‘/node_modules/split-pane’))

      app.use("/bower_components", express.static(__dirname + '/bower_components'))
      app.use(cookie_parser)
      app.use(noorauth.session_middleware)
      app.get("/email-login/login", noorauth.join_handler)
      app.get("/email-login/verify/:person_uri/:verif_token", noorauth.verification_handler)
      app.use("/email-login", express.static(email_login_module_path))
      app.use("/blossom", express.static(blossom_module_path))
      app.use(express.static(__dirname))
      app.use('/mocha', express.static(__dirname + '/node_modules/mocha'))
      app.use('/chai', express.static(__dirname + '/node_modules/chai'))
  • ¶

    app.get “/tests”, makeResponder(“/views/tests.html.ejs”, nopts.is_local)

  • ¶

    app.get “/“, (req, res) -> res.redirect “/__/“

      app.get "/",
        makeResponder(null, {isLocal: nopts.is_local})
      app.get "/dump/typeof.Proxy", (req, res) ->
        res.send(typeof Proxy)
      app.get "/dump/process.version", (req, res) ->
        res.send(process.version)
      app.get "/now", (req, res) ->
        res.send(noodb.now_baseXX())
      app.get "/dump/headers", (req, res) ->
        res.setHeader('content-type', 'text/plain')
        res.write(JSON.stringify(req.headers,null,4))
        res.end()
      app.set("trust proxy", true)
      app.get "/dump/", (req, res) ->
        if req.path.endsWith('dump')
          res.redirect('/dump/')
          return
        res.send("""
      These are various little windows into the back-end which should not stay available after alpha.
      <dl>
        <dt><a href="/__/">/__/</a>
          <dd>experience Nooron visualizations of data, ie the nooron app experience
        <dt><a href="by/s">/dump/by/s</a>
          <dd>subject
        <dt><a href="by/p">/dump/by/p</a>
          <dd>predicate
        <dt><a href="by/o">/dump/by/o</a>
          <dd>object
        <dt><a href="by/g">/dump/by/g</a>
          <dd>graph
        <dt><a href="by/i">/dump/by/i</a>
          <dd>idx
        <dt><a href="expand/">/dump/expand/:curie</a>
          <dd>expands <i>:curie</i> eg. <a href="/dump/expand/rdf:type">/dump/noicetrie/rdf:type</a>
        <dt><a href="headers">/dump/headers</a>
          <dd>req.headers
        <dt><a href="ips">/dump/ips</a>
          <dd>req.ips
        <dt><a href="noicetrie">/dump/noicetrie</a>
          <dd>dump the whole noodb.prefixdb.prefixes tree
        <dt><a href="noicetrie/nrn">/dump/noicetrie/:prfx</a>
          <dd>expands <i>:prfx</i> eg. <a href="/dump/noicetrie/rdf">/dump/noicetrie/rdf</a>
        <dt><a href="typeof.Proxy">/dump/typeof.Proxy</a>
          <dd>is ES6 Proxy supported on the server?
        <dt><a href="process.version">/dump/process.version</a>
          <dd>process.version (ie the version of nodejs aka node --version)
        <dt><a href="/now">/now</a>
          <dd>the current time (to the second) in Nooron's time format
        <dt><a href="/dev/fractalpanel_sandbox.html">/dev/fractalpanel_sandbox.html</a></dt>
          <dd>a place to play with FractalPanel</dd>
      </dl>
        """)
      app.get "/dump/details/:abbrev?", (req, res) ->
        res.setHeader('content-type', 'text/html')
        subj = req.params.abbrev
        res.write("WOOT:#{subj}")
        for pred in noodb.query({s: subj})
          res.write(pred.toString())
        res.end()
      app.get "/dump/ips", (req, res) ->
        res.send(req.ips.length and req.ips[0] or req.ip)
      app.get "/dump/noicetrie", (req, res) ->
        res.setHeader('content-type', 'text/plain')
        res.send(noodb.prefixdb.prefixes.tree())
      app.get "/dump/noicetrie/:prfx", (req, res) ->
        res.setHeader('content-type', 'text/plain')
        res.send(noodb.prefixdb.prefixes.getValue(req.params.prfx))
      app.get "/dump/by/:term?", (req, res) ->
        res.setHeader('content-type', 'text/plain')
        if req.params.term
          buffer = "by.#{req.params.term}\n"
          buffer += noodb.by[req.params.term].dump()
          res.send(buffer)
        else
          res.send('spogi'.split('').join("\n"))
      app.get "/dump/expand/:curie?", (req, res) ->
        if req.params.curie
  • ¶

    res.send(req.params.curie)

          res.send(noodb.prefixdb.prefixes.expand(req.params.curie))
        else
          res.send("/dump/expand/<i>prfx:local</i>")
      public_vm_settings =
        prefix: 'http://nooron.com/_/BetaInvite.ttl#'
        caching: true
      public_vm = noodb.make_vm(public_vm_settings, {})
      app.get "/betainvite", csrfProtection,
        makeResponder("/views/betainvite.html.ejs", {clientArgs: {isLocal:nopts.is_local}})
      app.post "/betainvite", parseForm, csrfProtection, (req, res) ->
        handler = () ->
          ip_address = req.ips.length and req.ips[0] or req.ip
          if typeof Object.create isnt 'function'
            console.log "Object.create() is missing"
          trusted_fields = {'nrn:fromIPAddress': ip_address}
          Object.setPrototypeOf(trusted_fields, req.body)
  • ¶

    TODO(smurp) convert to use of Object.create() WIP iteration of properties trusted_fields = Object.create( # dominate the req.body values with properties req.body, {‘nrn:fromIPAddress’: {value: ip_address}})

          pbir_resp = noodb.apply_by_name('post_betainvite_request',
             public_vm, [trusted_fields])
  • ¶

    console.log pbir_resp[1]

          res.redirect "/betainvite##{pbir_resp[0]}"
        noodb.at_log_level_run(3,handler)
    
      ejsData = {clientArgs: {isLocal: nopts.is_local}}
  • ¶

    TODO expose these dev toys and inspection points only during development

      app.get /\/__\/.*/, makeResponder('/views/front.html.ejs', ejsData)
      app.get "/tests/fractalpanel.html", makeResponder("/views/fractalpanel_test.html.ejs", ejsData)
      app.get "/dev/fractalpanel_sandbox.html", makeResponder("/views/fractalpanel_sandbox.html.ejs", ejsData)
      app.use("/tests", express.static(__dirname + "/views/tests"))
      app.get("/quads/:g", noorquery.qAsN4WithIdAsContext)
      app.get("/qq/", noorquery.qqAsN5) # /qq/?p=nrn:inheritsPermissionsFrom&s=nrn:LeanUXKB
      app.get("/contexts", noorquery.contextsAsLines)
      app.get("/q/:k1/:v1/:k2?/:v2?/:k3?/:v3?/:k4?/:v4?", noorquery.queryAsNq)
    
      app.get("/yc-demo/", (req, res) -> res.redirect("http://tabular.ponderate.com/pndr8/5515b0724ae9531c35648f63"))
      app.use("/demokbs", express.static(__dirname + '/kbs'))
      app.use("/ontos", express.static(__dirname + '/ontos'))
      app.use("/docs/:d.md", express.static(__dirname + '/docs')) # serve /doc/SUMUT.md files as raw markdown
      app.use("/docs/:d", makeResponder("/views/render_docs.html.ejs", {})) # at /doc/SUMUT render /doc/SUMUT.md
      app.use("/srcdocs/:d.md", express.static(__dirname + '/srcdocs')) # serve /doc/SUMUT.md files as raw markdown
      app.use("/srcdocs/:d", makeResponder("/views/render_srcdocs.html.ejs", {}))
      app.get("/srcdocs/", (req, res) -> res.redirect("/srcdocs/index"))
    
      app.use(bodyParser.json())
  • ¶

    https://medium.com/@gwilakers/structuring-your-node-js-app-67d20c2ab8a3

      require("./api/vidhandlers")( app, path.join(process.cwd(), 'uploads'),
              () -> noodb.synthetic_key_factory_next() )
    
      kbaBitBucket = new KBABitBucket(noodb)
      app.post("/kba/bitbucket/:capability?", kbaBitBucket.webhook)
    
      app.use (err, req, res, next) ->
        if (err.code isnt 'EBADCSRFTOKEN')
          return next(err)
  • ¶

    handle CSRF token errors here

        res.status(403)
        res.send('form tampered with')
    
      sio.on 'connection', (socket) ->
        noodb.log.info "socket.id: #{socket.id} connected"
        socket.on 'error', (err) ->
          noodb.log.error "error() socket:", socket.id, "err:", err
          return
        socket.on 'disconnect', () ->
          noodb.log.info "socket.id: #{socket.id} disconnected"
          return
        socket.on 'query', (msg) ->
          noodb.log.info "query() socket.id: #{socket.id} query:", msg, "TBD..."
          return
        socket.on 'register_session', (msg) ->
          acp = new AuthCookieParser(msg)
          socket.user = acp.get_user()
          noodb.log.info "socket.id: #{socket.id} verified:", socket.verified, "user",socket.user, "msg", msg
  • ¶

    for eventual RBACification of write security…

          socket.rbac_session = new RBAC.Session(acp.get_session_id(),new RBAC.Actor(socket.user.userId))
          socket.emit('set_server_session', acp.get_session_id())
          return
        socket.on 'subscribe', (qry) ->
          noodb.log.info("subscribe(#{qry}) socket.id: #{socket.id} user: #{socket.user}")
          noodb.subscribe_socket(socket, qry)
          return
        socket.on 'allege_transaction', (quads, skip_echo) ->
          try
  • ¶

    console.log(“allege_transaction(#{JSON.stringify(quads,null,4)})”)

            placeHolder2Curie = {}
            context =
              try_writing: true # TODO(shawn) add base_prefix and blank_prefix properties
  • ¶

    context = {}

            for quad in quads
              quad.forEach (term, i) =>
                context.blank_prefix = quad[3].split(':')[1] + '_' # REVIEW unprincipled and no guards
  • ¶

    Generate an actualCure for each placeholder the fisrt time it is encountered. Substitute the actualCurie for each placeholder wherever it is encountered.

                if not term?
  • ¶

    REIVEW why is the quad missing a term?

                  return
                placeHolder = (term.match(/^\?(.*)\?$/) or [null, ''])[1]
                if placeHolder
                  prefix = (placeHolder.match(/^(.*\:).*/) or [null,''])[1] # ==> 'somePrefix:' or ''
  • ¶

    get or create actualCurie expansion of placeHolder REVIEW too cute?

                  actualCurie = placeHolder2Curie[placeHolder] ?= (prefix + noodb.next_entity_id(9))
                  quad[i] = actualCurie
  • ¶

    console.log(“ QUAD: “,quad.join(“, “))

              spogi = noodb.allege_securely(quad[0], quad[1], quad[2], quad[3], null, null, context, socket)
  • ¶

    console.log(“ SPOGI: “,spogi.asTTL().join(“, “),”\n”)

              noodb.log.info("allege_upstream() socket.id: #{socket.id} quad:", quad)
              if not skip_echo
                spogi_terms = spogi.forWire()
                socket.emit('from_upstream', spogi_terms) # might duplicate a subscription .send()
  • ¶

    FIXME for some reason the client gags on transaction_response socket.emit(‘transaction_response’, {placeHolder2Curie: placeHolder2Curie}) console.log(JSON.stringify(placeHolder2Curie,null,4))

          catch e
            console.log("allege_upstream e:",e)
          return
        socket.on 'allege_upstream', (quad) -> # quad is a 4-tuple for brevity
          context = {} # TODO(shawn) add base_prefix and blank_prefix properties
          context =
            try_writing: true # TODO(shawn) add base_prefix and blank_prefix properties
          try
            console.log("allege_upstream(#{quad})")
            spogi = noodb.allege_securely(quad[0], quad[1], quad[2], quad[3], null, null, context, socket)
            noodb.log.info("allege_upstream() socket.id: #{socket.id} quad:", quad)
            spogi_terms = spogi.forWire()
            socket.emit('from_upstream', spogi_terms) # might duplicate a subscription .send()
          catch e
            console.log "allege_upstream e:",e
          return
        socket.on 'get_prefix', (prefix) ->
          val = noodb.prefixdb.prefixes.getValue(prefix)
          if val
            socket.emit('set_prefix', [prefix, val])
        socket.on "make_new_kb", (args) ->
  • ¶

    REVIEW do we really need make_new_kb ????!?

          context = {} # TODO(shawn) add base_prefix and blank_prefix properties
          try
            console.log("make_new_kb()",args)
            spogi = noodb.allege_securely(
                'nrn:'+args.kbName,
                'rdf:type',
                'nrn:WriteableKB',
                'nrn:metaKB',
                null,
                null,
                context,
                socket)
            terms = spogi.forWire()
            socket.emit('from_upstream', terms)
          catch e
            console.log("make_new_kb e:", e)
          return
        global.noodb = noodb
        return
      return server
    
    (exports ? this).server = make_server