def load_doc(self, docid): url = urlparse.urljoin(self.root_url,"/bokeh/getdocapikey/%s" % docid) resp = self.http_session.get(url, verify=False) if resp.status_code == 401: raise Exception('HTTP Unauthorized accessing DocID "%s"' % docid) apikey = utils.get_json(resp) if 'apikey' in apikey: self.docid = docid self.apikey = apikey['apikey'] logger.info('got read write apikey') else: self.docid = docid self.apikey = apikey['readonlyapikey'] logger.info('got read only apikey') url = urlparse.urljoin(self.root_url, "/bokeh/bb/") # TODO: Load the full document. For now, just load the PlotContext url = urlparse.urljoin(self.base_url, self.docid+"/PlotContext/") attrs = protocol.deserialize_json(self.http_session.get(url).content) if len(attrs) == 0: logger.warning("Unable to load PlotContext for doc ID %s" % self.docid) else: self.plotcontext = PlotServerSession.PlotContext(id=attrs[0]["id"]) if len(attrs) > 1: logger.warning("Found more than one PlotContext for doc ID %s; " \ "Using PlotContext ID %s" % (self.docid, attrs[0]["id"])) return
def load_obj(self, ref, asdict=False, modelattrs={}): """loads an object from the server. if asdict: only the json is returned. else: update the existing copy in _models if it is present instantiate a new one if it is not and make sure to convert all references into models in the conversion from json to objects, sometimes references to models need to be resolved. If there are any json attributes being processed, you can pass them in as modelattrs """ typename = ref["type"] ref_id = ref["id"] url = utils.urljoin(self.base_url, self.docid + "/" + ref["type"] +\ "/" + ref["id"] + "/") attr = protocol.deserialize_json(self.http_session.get(url).content) if not asdict: m = PlotObject.get_obj(typename, attr) self.add(m) m.finalize(self._models) m.dirty = False return m else: return attr
def bulk_upsert(request): ''' Update or insert new objects for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update or insert into :status 200: when user is authorized :status 401: when user is not authorized ''' # endpoint is only used by python, therefore we don't process # callbacks here docid = request.matchdict['docid'] client = request.headers.get('client', 'python') servermodel_storage = request.registry.servermodel_storage doc = docs.Doc.load(servermodel_storage, docid) bokehuser = request.current_user() temporary_docid = get_temporary_docid(request, docid) t = BokehServerTransaction( request, bokehuser, doc, 'rw', temporary_docid=temporary_docid ) t.load() clientdoc = t.clientdoc data = protocol.deserialize_json(request.data.decode('utf-8')) if client == 'python': clientdoc.load(*data, events='none', dirty=True) else: clientdoc.load(*data, events='existing', dirty=True) t.save() msg = ws_update(request, clientdoc, t.write_docid, t.changed) return msg
def bulk_upsert(docid): ''' Update or insert new objects for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update or insert into :status 200: when user is authorized :status 401: when user is not authorized ''' client = request.headers.get('client', 'python') doc = docs.Doc.load(bokeh_app.servermodel_storage, docid) bokehuser = bokeh_app.current_user() temporary_docid = get_temporary_docid(request, docid) t = BokehServerTransaction( bokehuser, doc, 'rw', temporary_docid=temporary_docid ) t.load() clientdoc = t.clientdoc data = protocol.deserialize_json(request.data.decode('utf-8')) if client == 'python': clientdoc.load(*data, events='none', dirty=True) else: clientdoc.load(*data, events='existing', dirty=True) t.save() msg = ws_update(clientdoc, t.write_docid, t.changed) return make_json(msg)
def update(request, docid, typename, id): """we need to distinguish between writing and patching models namely in writing, we shouldn't remove unspecified attrs (we currently don't handle this correctly) """ doc = docs.Doc.load(request.registry.servermodel_storage, docid) bokehuser = request.current_user() temporary_docid = get_temporary_docid(request, docid) t = BokehServerTransaction( request, bokehuser, doc, 'rw', temporary_docid=temporary_docid ) t.load() modeldata = protocol.deserialize_json(request.body.decode('utf-8')) ### horrible hack, we need to pop off the noop object if it exists modeldata.pop('noop', None) clientdoc = t.clientdoc log.info("loading done %s", len(clientdoc._models.values())) # patch id is not passed... modeldata['id'] = id modeldata = {'type' : typename, 'attributes' : modeldata} clientdoc.load(modeldata, events='existing', dirty=True) t.save() ws_update(request, clientdoc, t.write_docid, t.changed) # backbone expects us to send back attrs of this model, but it doesn't # make sense to do so because we modify other models, and we want this to # all go out over the websocket channel return make_json(protocol.serialize_json({'noop' : True}))
def bulk_upsert(docid): ''' Update or insert new objects for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update or insert into :status 200: when user is authorized :status 401: when user is not authorized ''' client = request.headers.get('client', 'python') doc = docs.Doc.load(bokeh_app.servermodel_storage, docid) bokehuser = bokeh_app.current_user() temporary_docid = get_temporary_docid(request, docid) t = BokehServerTransaction(bokehuser, doc, 'rw', temporary_docid=temporary_docid) t.load() clientdoc = t.clientdoc data = protocol.deserialize_json(request.data.decode('utf-8')) if client == 'python': clientdoc.load(*data, events='none', dirty=True) else: clientdoc.load(*data, events='existing', dirty=True) t.save() msg = ws_update(clientdoc, t.write_docid, t.changed) return make_json(msg)
def update(docid, typename, id): """we need to distinguish between writing and patching models namely in writing, we shouldn't remove unspecified attrs (we currently don't handle this correctly) """ clientdoc = bokeh_app.backbone_storage.get_document(docid) log.info("loading done %s", len(clientdoc._models.values())) prune(clientdoc) init_bokeh(clientdoc) log.info("updating") modeldata = protocol.deserialize_json(request.data.decode('utf-8')) # patch id is not passed... modeldata['id'] = id modeldata = {'type' : typename, 'attributes' : modeldata} clientdoc.load(modeldata, events='existing', dirty=True) log.info("done") log.info("saving") changed = bokeh_app.backbone_storage.store_document(clientdoc) log.debug("changed, %s", str(changed)) ws_update(clientdoc, changed) log.debug("update, %s, %s", docid, typename) # backbone expects us to send back attrs of this model, but it doesn't # make sense to do so because we modify other models, and we want this to # all go out over the websocket channel return make_json(protocol.serialize_json({'noop' : True}))
def create(request): ''' Update or insert new objects for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update or insert into :status 200: when user is authorized :status 401: when user is not authorized ''' docid, typename = request.POST['docid'], request.POST['typename'] doc = docs.Doc.load(request.registry.servermodel_storage, docid) bokehuser = request.current_user() temporary_docid = get_temporary_docid(request, docid) t = BokehServerTransaction( request, bokehuser, doc, 'rw', temporary_docid=temporary_docid ) t.load() modeldata = protocol.deserialize_json(request.body.decode('utf-8')) modeldata = [{'type' : typename, 'attributes' : modeldata}] t.clientdoc.load(*modeldata, dirty=True) t.save() ws_update(request, t.clientdoc, t.write_docid, modeldata) return make_json(protocol.serialize_json(modeldata[0]['attributes']))
def update(docid, typename, id): """we need to distinguish between writing and patching models namely in writing, we shouldn't remove unspecified attrs (we currently don't handle this correctly) """ doc = docs.Doc.load(bokeh_app.servermodel_storage, docid) bokehuser = bokeh_app.current_user() temporary_docid = get_temporary_docid(request, docid) t = BokehServerTransaction(bokehuser, doc, 'rw', temporary_docid=temporary_docid) t.load() modeldata = protocol.deserialize_json(request.data.decode('utf-8')) ### horrible hack, we need to pop off the noop object if it exists modeldata.pop('noop', None) clientdoc = t.clientdoc log.info("loading done %s", len(clientdoc._models.values())) # patch id is not passed... modeldata['id'] = id modeldata = {'type': typename, 'attributes': modeldata} clientdoc.load(modeldata, events='existing', dirty=True) t.save() ws_update(clientdoc, t.write_docid, t.changed) # backbone expects us to send back attrs of this model, but it doesn't # make sense to do so because we modify other models, and we want this to # all go out over the websocket channel return make_json(protocol.serialize_json({'noop': True}))
def connect(sock, addr, topic, auth): sock.timeout = 2.0 sock.connect(addr) msgobj = dict(msgtype='subscribe', topic=topic, auth=auth) sock.send(protocol.serialize_json(msgobj)) msg = sock.recv() msg = msg.split(":", 2)[-1] msgobj = protocol.deserialize_json(msg) assert msgobj['status'][:2] == ['subscribesuccess', topic]
def load_all_callbacks(self, get_json=False): """get_json = return json of callbacks, rather than loading them into models """ url = utils.urljoin(self.base_url, self.docid + "/", "callbacks") data = protocol.deserialize_json(self.http_session.get(url).content) if get_json: return data self.load_callbacks_json(data)
def callbacks(docid): #broken... clientdoc = bokeh_app.backbone_storage.get_document(docid) prune(clientdoc) if request.method == 'POST': jsondata = protocol.deserialize_json(request.data.decode('utf-8')) bokeh_app.backbone_storage.push_callbacks(jsondata) else: jsondata = bokeh_app.backbone_storage.load_callbacks() return make_json(protocol.serialize_json(jsondata))
def create(docid, typename): clientdoc = bokeh_app.backbone_storage.get_document(docid) prune(clientdoc) modeldata = protocol.deserialize_json(request.data.decode('utf-8')) modeldata = {'type' : typename, 'attributes' : modeldata} clientdoc.load(modeldata, dirty=True) bokeh_app.backbone_storage.store_document(clientdoc) ws_update(clientdoc, modeldata) return protocol.serialize_json(modeldata[0]['attributes'])
def load_type(self, typename, asdict=False): url = utils.urljoin(self.base_url, self.docid + "/", typename + "/") attrs = protocol.deserialize_json(self.http_session.get(url).content) if not asdict: models = self.load_attrs(typename, attrs) for m in models: m._dirty = False return models else: models = attrs return models
def load_type(self, typename, asdict=False): url = utils.urljoin(self.base_url, self.docid +"/", typename + "/") attrs = protocol.deserialize_json(self.http_session.get(url).content) if not asdict: models = self.load_attrs(typename, attrs) for m in models: m._dirty = False return models else: models = attrs return models
def load_all_callbacks(self, get_json=False): """get_json = return json of callbacks, rather than loading them into models """ doc_keys = self.r.smembers(dockey(self.docid)) callback_keys = [x.replace("bbmodel", "bbcallback") for x in doc_keys] callbacks = self.r.mget(callback_keys) callbacks = [x for x in callbacks if x] callbacks = [protocol.deserialize_json(x) for x in callbacks] if get_json: return callbacks self.load_callbacks_json(callbacks)
def connect(sock, addr, topic, auth): sock.timeout = 2.0 sock.connect(addr) msgobj = dict(msgtype='subscribe', topic=topic, auth=auth ) sock.send(protocol.serialize_json(msgobj)) msg = sock.recv() msg = msg.split(":", 2)[-1] msgobj = protocol.deserialize_json(msg) assert msgobj['status'][:2] == ['subscribesuccess', topic]
def rpc(docid, typename, id, funcname): clientdoc = bokeh_app.backbone_storage.get_document(docid) prune(clientdoc) model = clientdoc._models[id] data = protocol.deserialize_json(request.data.decode('utf-8')) args = data.get('args', []) kwargs = data.get('kwargs', {}) result = getattr(model, funcname)(*args, **kwargs) log.debug("rpc, %s, %s", docid, typename) changed = bokeh_app.backbone_storage.store_document(clientdoc) ws_update(clientdoc, changed) return make_json(protocol.serialize_json(result))
def connect(sock, addr, topic, auth): # TODO (bev) increasing timeout due to failing TravisCI tests # investigate if this is the real solution or if there is a # deeper problem sock.timeout = 4.0 sock.connect(addr) msgobj = dict(msgtype='subscribe', topic=topic, auth=auth) sock.send(protocol.serialize_json(msgobj)) msg = sock.recv() msg = msg.split(":", 2)[-1] msgobj = protocol.deserialize_json(msg) assert msgobj['status'][:2] == ['subscribesuccess', topic]
def pull(self, docid, typename=None, objid=None): """you need to call this with either typename AND objid or leave out both. leaving them out means retrieve all otherwise, retrieves a specific object """ doc_keys = self.smembers(dockey(docid)) attrs = self.mget(doc_keys) data = [] for k, attr in zip(doc_keys, attrs): typename, _, modelid = parse_modelkey(k) attr = protocol.deserialize_json(decode_utf8(attr)) data.append({'type': typename, 'attributes': attr}) return data
def load_all(self, asdict=False): doc_keys = self.r.smembers(dockey(self.docid)) attrs = self.r.mget(doc_keys) if asdict: return attrs data = [] for k, attr in zip(doc_keys, attrs): typename, _, modelid = parse_modelkey(k) attr = protocol.deserialize_json(attr) data.append({'type': typename, 'attributes': attr}) models = self.load_broadcast_attrs(data, events=None) for m in models: m._dirty = False return models
def bulk_upsert(docid): # endpoint is only used by python, therefore we don't process # callbacks here client = request.headers.get('client', 'python') clientdoc = bokeh_app.backbone_storage.get_document(docid) prune(clientdoc) data = protocol.deserialize_json(request.data.decode('utf-8')) if client == 'python': clientdoc.load(*data, events='none', dirty=True) else: clientdoc.load(*data, events='existing', dirty=True) changed = bokeh_app.backbone_storage.store_document(clientdoc) msg = ws_update(clientdoc, changed) return make_json(msg)
def load_all(self, asdict=False): doc_keys = self.r.smembers(dockey(self.docid)) attrs = self.r.mget(doc_keys) if asdict: return attrs data = [] for k, attr in zip(doc_keys, attrs): typename, _, modelid = parse_modelkey(k) attr = protocol.deserialize_json(attr) data.append({"type": typename, "attributes": attr}) models = self.load_broadcast_attrs(data, events=None) for m in models: m._dirty = False return models
def load_all(self, asdict=False): """the json coming out of this looks different than that coming out of load_type, because it contains id, type, attributes, whereas the other one just contains attributes directly """ url = utils.urljoin(self.base_url, self.docid + "/") attrs = protocol.deserialize_json(self.http_session.get(url).content) if not asdict: models = self.load_broadcast_attrs(attrs) for m in models: m._dirty = False return models else: models = attrs return models
def on_message(self, message): msgobj = protocol.deserialize_json(message) msgtype = msgobj.get('msgtype') if msgtype == 'subscribe': auth = msgobj['auth'] topic = msgobj['topic'] if self.manager.auth(auth, topic): self.manager.subscribe(self.clientid, topic) msg = protocol.serialize_json( protocol.status_obj(['subscribesuccess', topic, self.clientid]) ) self.write_message(topic + ":" + msg) else: msg = protocol.serialize_web(protocol.error_obj('unauthorized')) self.write_message(topic + ":" + msg)
def connect(sock, addr, topic, auth): # TODO (bev) increasing timeout due to failing TravisCI tests # investigate if this is the real solution or if there is a # deeper problem sock.timeout = 4.0 sock.connect(addr) msgobj = dict(msgtype='subscribe', topic=topic, auth=auth ) sock.send(protocol.serialize_json(msgobj)) msg = sock.recv() msg = msg.split(":", 2)[-1] msgobj = protocol.deserialize_json(msg) assert msgobj['status'][:2] == ['subscribesuccess', topic]
def test_merge(self): d1 = document.Document() d2 = document.Document() p1 = circle([1], [2]) p2 = circle([1], [2]) d1.add(p1) d2.add(p2) json_objs = d1.dump() json_objs = protocol.deserialize_json(protocol.serialize_json(json_objs)) d2.merge(json_objs) assert d2.context._id == d1.context._id assert len(d2.context.children) == 2 assert d2.context is d2._models[d2.context._id] pcs = [x for x in d2._models.values() if x.__view_model__ == "PlotContext"] assert len(pcs) == 1
def load_all(self, asdict=False): """the json coming out of this looks different than that coming out of load_type, because it contains id, type, attributes, whereas the other one just contains attributes directly """ url = utils.urljoin(self.base_url, self.docid +"/") attrs = protocol.deserialize_json(self.http_session.get(url).content) if not asdict: models = self.load_broadcast_attrs(attrs) for m in models: m._dirty = False return models else: models = attrs return models
def callbacks_post(docid): ''' Update callbacks for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update callbacks for :status 200: when user is authorized :status 401: when user is not authorized ''' # broken... clientdoc = bokeh_app.backbone_storage.get_document(docid) prune(clientdoc) jsondata = protocol.deserialize_json(request.data.decode('utf-8')) bokeh_app.backbone_storage.push_callbacks(jsondata) return make_json(protocol.serialize_json(jsondata))
def create(docid, typename): ''' Update or insert new objects for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update or insert into :status 200: when user is authorized :status 401: when user is not authorized ''' clientdoc = bokeh_app.backbone_storage.get_document(docid) prune(clientdoc) modeldata = protocol.deserialize_json(request.data.decode('utf-8')) modeldata = {'type' : typename, 'attributes' : modeldata} clientdoc.load(modeldata, dirty=True) bokeh_app.backbone_storage.store_document(clientdoc) ws_update(clientdoc, modeldata) return protocol.serialize_json(modeldata[0]['attributes'])
def load_obj(self, ref, asdict=False): """ Unserializes the object given by **ref**, into a new object of the type in the serialization. If **asdict** is True, then the raw dictionary (including object type and ref) is returned, and no new object is instantiated. """ # TODO: Do URL and path stuff to read json data from persistence # backend into jsondata string jsondata = None attrs = protocol.deserialize_json(jsondata) if asdict: return attrs else: from bokeh.objects import PlotObject objtype = attrs["type"] ref_id = attrs["id"] cls = PlotObject.get_class(objtype) newobj = cls(id=ref_id) # TODO: finish this... return newobj
def bulk_upsert(docid): ''' Update or insert new objects for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update or insert into :status 200: when user is authorized :status 401: when user is not authorized ''' # endpoint is only used by python, therefore we don't process # callbacks here client = request.headers.get('client', 'python') clientdoc = bokeh_app.backbone_storage.get_document(docid) prune(clientdoc) data = protocol.deserialize_json(request.data.decode('utf-8')) if client == 'python': clientdoc.load(*data, events='none', dirty=True) else: clientdoc.load(*data, events='existing', dirty=True) changed = bokeh_app.backbone_storage.store_document(clientdoc) msg = ws_update(clientdoc, changed) return make_json(msg)
def create(docid, typename): ''' Update or insert new objects for a given :class:`Document <bokeh.document.Document>`. :param docid: id of the :class:`Document <bokeh.document.Document>` to update or insert into :status 200: when user is authorized :status 401: when user is not authorized ''' doc = docs.Doc.load(bokeh_app.servermodel_storage, docid) bokehuser = bokeh_app.current_user() temporary_docid = get_temporary_docid(request, docid) t = BokehServerTransaction(bokehuser, doc, 'rw', temporary_docid=temporary_docid) t.load() modeldata = protocol.deserialize_json(request.data.decode('utf-8')) modeldata = [{'type': typename, 'attributes': modeldata}] t.clientdoc.load(*modeldata, dirty=True) t.save() ws_update(t.clientdoc, t.write_docid, modeldata) return protocol.serialize_json(modeldata[0]['attributes'])