def addCompletionData(self, req: RequestWrapper) -> None: try: data = NetworkService.decode(req) except ValueError: # Query was canceled return #self.beginResetModel() self.layoutAboutToBeChanged.emit() #self.dataCache = [] initial = not self.dataCache for skel in data["skellist"]: skel["__descr__"] = self.safeEval.execute(self.ast, { "value": {"dest": skel, "rel": None}, "structure": self.structure, "language": config.conf.adminConfig.get("language", "en") }) if self.dataCache: for s in self.dataCache: if s["key"] == skel["key"]: break else: self.dataCache.append(skel) changed = True else: self.dataCache.append(skel) changed = True #self.endResetModel() self.layoutChanged.emit() if initial: self.parent().complete()
def addCacheData(self, req: RequestWrapper) -> None: data = NetworkService.decode(req) cursor = None if "cursor" in data: cursor = data["cursor"] if data["action"] == "list": self.queryCache[req.wrapperCbCacheKey] = { "ctime": time(), "skelkeys": [ x["key"] for x in data["skellist"] if x["key"] not in self.pendingDeletes ], "cursor": cursor } for skel in data["skellist"]: if skel["key"] in self.pendingDeletes: continue self.entryCache[skel["key"]] = skel elif data["action"] == "view": self.entryCache[data["values"]["key"]] = data["values"] self.entityAvailable.emit(data["values"]) if hasattr(req, "wrapperCbCacheKey"): self.queryResultAvailable.emit(req.wrapperCbCacheKey) self.checkBusyStatus()
def onRootNodesAvailable(self, req: RequestWrapper) -> None: tmp = NetworkService.decode(req) if isinstance(tmp, list): self.rootNodes = tmp else: self.rootNodes = [] self.rootNodesAvailable.emit() self.checkBusyStatus()
def onRootNodesAvailable(self, req: RequestWrapper) -> None: tmp = NetworkService.decode(req) if isinstance(tmp, list): self.rootNodes = tmp self.clearCache() self.rootNodesAvailable.emit() self.checkBusyStatus() logger.debug("TreeWrapper.onRootNodesAvailable: %r", tmp)
def onTreeAddFinished(self, req): try: data = NetworkService.decode(req) except: self.hasFinished = True self.failed.emit() return self.hasFinished = True self.succeeded.emit(data)
def setRepos(self, req: RequestWrapper) -> None: data = NetworkService.decode(req) self.tmp_obj.deleteLater() self.tmp_obj = None self.repos = data if len(self.repos) > 1: for repo in self.repos: d = HierarchyRepoHandler(self.module, repo) self.addChild(d)
def onLoadConfig(self, request: RequestWrapper) -> None: logger.debug("Checkpoint: onLoadConfig") try: conf.serverConfig = NetworkService.decode(request) except: self.onError(msg="Unable to parse portalconfig!") return event.emit("configDownloaded") if conf.currentUserEntry is not None: self.setup()
def onSetDefaultRootNode(self, request: RequestWrapper) -> None: data = NetworkService.decode(request) logger.debug("onSetDefaultRootNode: %r", data) self.rootNodes = data if not self.rootNode: try: self.rootNode = self.rootNodes[0]["key"] except: self.rootNode = None return self.loadData()
def onViurAuth(self, req: RequestWrapper) -> None: res = NetworkService.decode(req) if isinstance(res, dict) and "action" in res and res["action"] == "edit": msg = QtWidgets.QMessageBox.warning( self, "Invalid token", "Your token did not verify. Please try again") self.startRun() elif isinstance(res, str) and res.lower() == "okay": self.loginSucceeded.emit() logger.debug("VerifyOtp.onViurAuth: %r", res)
def addCacheData(self, req: RequestWrapper) -> None: data = NetworkService.decode(req) logger.debug("TreeWrapper.addCacheData: %r, %r", req.skelType, req.queryArgs) if req.queryArgs: # This was a custom request key = self.cacheKeyFromFilter(req.node, req.queryArgs) if key not in self.dataCache or not self.dataCache[key]: self.dataCache[key] = [] assert data["action"] == "list" for skel in data["skellist"]: if not skel["key"] in [x["key"] for x in self.dataCache[key]]: skel["_type"] = req.skelType self.dataCache[key].append(skel) self.customQueryFinished.emit(key) cursor = None if "cursor" in data: cursor = data["cursor"] hasChanged = False addedData = list() if data["action"] == "list": if len(data["skellist"]): hasChanged = True for skel in data["skellist"]: skel["_type"] = req.skelType self.dataCache[skel["key"]] = skel addedData.append(skel) # logger.debug("TreeWrapper.addCacheData: %r, %r", skel["name"], req.skelType) if len(data["skellist"] ) == self.batchSize: # There might be more results if "cursor" in data and cursor: # We have a cursor (we can continue this query) # Fetch the next batch tmp = {k: v for k, v in req.queryArgs.items()} tmp["parententry"] = req.node tmp["cursor"] = cursor tmp["skelType"] = req.skelType tmp["amount"] = self.batchSize r = NetworkService.request( "/%s/list" % self.module, tmp, successHandler=self.addCacheData) r.wrapperCacheKey = req.wrapperCacheKey r.skelType = req.skelType r.node = req.node r.queryArgs = req.queryArgs elif data["action"] == "view": skel = data["values"] skel["_type"] = req.skelType self.dataCache[skel["key"]] = skel self.entityAvailable.emit(skel) if self.dataCache.get(req.wrapperCacheKey, False) is None: del self.dataCache[req.wrapperCacheKey] if hasChanged: self.entitiesAppended.emit(req.node, addedData) self.checkBusyStatus()
def onSaveResult(self, req: RequestWrapper) -> None: try: data = NetworkService.decode(req) except: # Something went wrong, call ErrorHandler self.updatingFailedError.emit(str(id(req))) return if data["action"] in ["addSuccess", "editSuccess", "deleteSuccess"]: # Saving succeeded QtCore.QTimer.singleShot(self.updateDelay, self.emitEntriesChanged) self.updatingSucceeded.emit(str(id(req))) else: # There were missing fields self.updatingDataAvailable.emit(str(id(req)), data, req.wasInitial) self.checkBusyStatus()
def authStatusCallback(self, nsReq: RequestWrapper) -> None: data = NetworkService.decode(nsReq) logger.debug("authStatusCallback: %r", data) okayFound = data.find("OKAY") logger.debug("checkAuthenticationStatus: %r", okayFound) if okayFound != -1: self.loginSucceeded.emit() elif data.find("X-VIUR-2FACTOR-") != -1: html = self.webView.page().mainFrame().toHtml() startPos = html.find("X-VIUR-2FACTOR-") secondFactorType = html[startPos, html.find("\"", startPos + 1)] secondFactorType = secondFactorType.replace("X-VIUR-2FACTOR-", "") self.secondFactorRequired.emit(secondFactorType)
def onAuthMethodsKnown(self, req: RequestWrapper) -> None: data = NetworkService.decode(req) logger.debug("onAuthMethodsKnown: %r", data) self.ui.cbAuthSelector.clear() seenList: List[str] = [] self.validAuthMethods = {} for authMethod, verificationMethod in data: if authMethod not in seenList: seenList.append(authMethod) self.validAuthMethods[authMethod] = authMethod self.ui.cbAuthSelector.addItem(authMethod) self.setDisabled(False) self.forcePageFlip = True self.next()
def onCheckSuccessAuth(self, request: RequestWrapper) -> None: """Login credentials aka cookies are still valid, so we can progress with admin startup :param req: :return: """ try: currentUserEntry = NetworkService.decode(request)["values"] logger.debug("MainWindow.onLoadUser: %r", currentUserEntry) except Exception as err: return self.onNotLoggedInYet(request) else: logger.debug("onCheckSuccessAuth success: %r", request) self.loginTask.loginSucceeded.emit()
def addCacheData(self, req: RequestWrapper) -> None: data = NetworkService.decode(req) cursor = None if "cursor" in data: cursor = data["cursor"] if data["action"] == "list": self.dataCache[req.wrapperCbCacheKey] = (time(), data["skellist"], cursor) for skel in data["skellist"]: self.dataCache[skel["key"]] = skel self.childrenAvailable.emit(req.node) elif data["action"] == "view": self.dataCache[data["values"]["key"]] = data["values"] self.entityAvailable.emit(data["values"]) self.checkBusyStatus()
def onLoadUser(self, request: RequestWrapper) -> None: if conf.currentUserEntry: return try: conf.currentUserEntry = NetworkService.decode(request)["values"] logger.debug(repr(conf.currentUserEntry)) except Exception as err: logger.exception(err) self.onError(msg="Unable to parse user entry!") return else: if conf.serverConfig is not None: self.setup()
def onStructureAvailable(self, req: RequestWrapper) -> None: tmp = NetworkService.decode(req) if tmp is None: self.checkBusyStatus() return for stype, structlist in tmp.items(): structure: OrderedDict = OrderedDict() for k, v in structlist: structure[k] = v if stype == "viewSkel": self.viewStructure = structure elif stype == "editSkel": self.editStructure = structure self.modulStructureAvailable.emit() self.checkBusyStatus()
def onPreflightDataAvailable(self, req): print("onPreflightDataAvailable") data = NetworkService.decode(req) errors = data["errors"] newTabIcons: Dict[QtWidgets.QWidget, List[int]] = {} for key, bone in self.bones.items(): if key not in self.editedBones: continue boneErrors = collectBoneErrors(errors, key) bone.setErrors(boneErrors) tab = self.boneToTabMap[bone] if tab not in newTabIcons: newTabIcons[tab] = [] newTabIcons[tab].append(bone.getEffectiveMaximumBoneError(False)) for tab, errList in newTabIcons.items(): self.ui.tabWidget.setTabIcon(tab, boneErrorCodeToIcon(max(errList)))
def onDirListAvailable(self, req: RequestWrapper) -> None: logger.debug("onDirListAvailable") self.runningTasks -= 1 if self.isCanceled: return data = NetworkService.decode(req) for skel in data["skellist"]: if skel["name"] is None: continue if skel["name"].lower() == self.getDirName( req.uploadDirName).lower(): logger.debug("onDirListAvailable: directory %r already exists", skel["name"]) self.stats["dirsDone"] += 1 task = { "type": "rekul", "args": [[ os.path.join(req.uploadDirName, x) for x in os.listdir(req.uploadDirName) ], skel["key"], self.module, None], "kwargs": { "parent": self } } self.taskQueue.append(task) else: task = { "type": "netreq", "args": [ "/%s/add/" % self.module, { "node": self.node, "name": self.getDirName(req.uploadDirName), "skelType": "node" } ], "kwargs": { "secure": True, "finishedHandler": self.onMkDir }, "uploadDirName": req.uploadDirName } self.taskQueue.append(task) self.launchNextRequest()
def onAuthMethodsKnown(self, req: RequestWrapper): data = NetworkService.decode(req) userPassword = google = False try: for authMethod in data: if authMethod[0] == "X-VIUR-AUTH-Google-Account": google = True elif authMethod[0] == "X-VIUR-AUTH-User-Password": userPassword = True except: raise if google and userPassword: # FIXME: Button to login with both? self.onLoginFailed("2 Auth Methods") self.ui.googleLoginBtn.setDisabled(False) elif google: self.onBtnGoogleLoginReleased() else: # Either neither - or user-password self.ui.googleLoginBtn.setDisabled(True) self.setDisabled(False)
def onMkDir(self, req: RequestWrapper) -> None: if self.isCanceled: return data = NetworkService.decode(req) assert data["action"] == "addSuccess" self.stats["dirsDone"] += 1 self.stats["bytesDone"] += self.directorySize self.runningTasks -= 1 task = { "type": "rekul", "args": [[ os.path.join(req.uploadDirName, x) for x in os.listdir(req.uploadDirName) ], data["values"]["key"], self.module, None], "kwargs": { "parent": self } } self.taskQueue.append(task) self.launchNextRequest()
def onHasSession(self, req): data = NetworkService.decode(req) if data["values"] and data["values"]["access"] and "root" in data[ "values"]["access"]: event.emit("loginSucceeded") self.hide() else: try: userName = data["values"]["name"] except: userName = "******" self.requestLogoutBox = QtWidgets.QMessageBox( QtWidgets.QMessageBox.Question, QtCore.QCoreApplication.translate("SimpleLogin", "Logout?"), QtCore.QCoreApplication.translate( "SimpleLogin", "This user (%s) cannot be used with ViUR Admin. Do you want to log out?" ) % userName, (QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No), self) self.requestLogoutBox.buttonClicked.connect(self.reqLogoutCallback) self.requestLogoutBox.open() QtGui.QGuiApplication.processEvents() self.requestLogoutBox.adjustSize()
def onHtmlUploadUrlAvailable(self, req): import js data = NetworkService.decode(req)["values"] fileObj, dirKey = req.fileUploadTask["args"] if "uploadKey" in data: # New Resumeable upload format self.currentHtmlUpload = { "key": data["uploadKey"], "node": dirKey, "skelType": "leaf", "fileSize": fileObj.size } js.window.fetch(data["uploadUrl"], { "method": "POST", "body": fileObj, "mode": "no-cors" }).then(self.onHtmlBucketUploadFinished) else: formData = js.eval("new FormData();") for key, value in data["params"].items(): if key == "key": targetKey = value[:-16] # Truncate source/file.dat fileName = fileObj.name value = value.replace("file.dat", fileName) formData.append(key, value) formData.append("file", fileObj) self.currentHtmlUpload = { "key": targetKey, "node": dirKey, "skelType": "leaf", "fileSize": fileObj.size } js.window.fetch(data["url"], { "method": "POST", "body": formData, "mode": "no-cors" }).then(self.onHtmlBucketUploadFinished)
def startUpload(self, req: RequestWrapper) -> None: self.uploadProgress.emit(0, 1) getUploadUrlResponse = NetworkService.decode(req)["values"] if "uploadKey" in getUploadUrlResponse: # New Resumeable upload format fileObj = open(self.fileName.encode(sys.getfilesystemencoding()), "rb") self.targetFileKey = getUploadUrlResponse["uploadKey"] req = NetworkService.request(getUploadUrlResponse["uploadUrl"], fileObj, successHandler=self.onUploadFinished, failureHandler=self.onUploadFailed) else: # vvvv REMOVE AFTER 01.07.2021 (API SHUTDOWN DATE) vvvv params = getUploadUrlResponse["params"] params["file"] = open( self.fileName.encode(sys.getfilesystemencoding()), "rb") self.targetFileKey = params["key"][:-16] params["key"] = params["key"].replace( "file.dat", os.path.basename(self.fileName)) # params["node"] = self.node req = NetworkService.request(getUploadUrlResponse["url"], params, successHandler=self.onUploadFinished, failureHandler=self.onUploadFailed) req.uploadProgress.connect(self.onProgress)
def onTaskList(self, req: RequestWrapper) -> None: self.tasks = NetworkService.decode(req) for task in self.tasks["skellist"]: item = TaskItem(task) self.ui.listWidget.addItem(item) self.overlay.clear()
def onError(self, req: RequestWrapper) -> None: res = NetworkService.decode(req) logger.debug("VerifyOtp.onError: %r", res)
def setData( self, request: RequestWrapper = None, data: Dict[str, Any] = None, ignoreMissing: bool = False) -> None: """ Rebuilds the UI according to the skeleton received from server :param request: the request to handle :param data: The data received :param ignoreMissing: if missing data should be reported as errors """ assert request or data if request: data = NetworkService.decode(request) # Clear the UI while self.ui.tabWidget.count(): item = self.ui.tabWidget.widget(0) if item and item.widget(): if "remove" in dir(item.widget()): item.widget().remove() self.ui.tabWidget.removeTab(0) self.bones = {} self.boneToTabMap = {} self.dataCache = data tmpDict = {} tabs: Dict[str, QtWidgets.QFormLayout] = dict() tmpTabs: List[Tuple[QtWidgets.QScrollArea, str]] = list() # Sort tabs by their description tabMaxError: Dict[str, int] = {} # Map of max-error code per tap for key, bone in data["structure"]: tmpDict[key] = bone for key, bone in data["structure"]: if not bone["visible"]: continue if "params" in bone and bone["params"] and "category" in bone["params"]: tabName = bone["params"]["category"] else: tabName = QtCore.QCoreApplication.translate("EditWidget", "General") if tabName not in tabs: scrollArea = QtWidgets.QScrollArea() outerContainer = QtWidgets.QWidget(scrollArea) outerLayout = QtWidgets.QVBoxLayout(outerContainer) scrollArea.setWidget(outerContainer) containerWidget = QtWidgets.QWidget(outerContainer) outerLayout.addWidget(containerWidget, 1) formLayout = QtWidgets.QFormLayout(containerWidget) formLayout.setFieldGrowthPolicy(QtWidgets.QFormLayout.AllNonFixedFieldsGrow) formLayout.setLabelAlignment(QtCore.Qt.AlignLeft) formLayout.setAlignment(QtCore.Qt.AlignTop) tabs[tabName] = formLayout containerWidget.setLayout(formLayout) containerWidget.setSizePolicy( QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Preferred)) tmpTabs.append((scrollArea, tabName)) outerLayout.addStretch(100) scrollArea.setWidgetResizable(True) for error in data["errors"]: if error["fieldPath"] and error["fieldPath"][0] == key: severity = error["severity"] if severity == 2 and bone.get("required"): severity = 3 if severity > tabMaxError.get(tabName, 0): tabMaxError[tabName] = severity tmpTabs.sort(key=lambda x: x[1]) for scrollArea, tabName in tmpTabs: tabIndex = self.ui.tabWidget.addTab(scrollArea, tabName) maxErrCode = tabMaxError.get(tabName, 0) if maxErrCode == 1: self.ui.tabWidget.setTabIcon(tabIndex, loadIcon("bone-invalidates-other")) elif maxErrCode == 2: self.ui.tabWidget.setTabIcon(tabIndex, loadIcon("bone-empty")) elif maxErrCode == 3: self.ui.tabWidget.setTabIcon(tabIndex, loadIcon("bone-error")) else: self.ui.tabWidget.setTabIcon(tabIndex, loadIcon("bone-valid")) for key, bone in data["structure"]: if bone["visible"] == False: continue if "params" in bone and bone["params"] and "category" in bone["params"]: tabName = bone["params"]["category"] else: tabName = QtCore.QCoreApplication.translate("EditWidget", "General") wdgGen = editBoneSelector.select(self.module, key, tmpDict) widget = wdgGen.fromSkelStructure(self.module, key, tmpDict, editWidget=self) widget.setSizePolicy( QtWidgets.QSizePolicy(QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Expanding)) dataWidget = widget # TODO: Temporary MacOS Fix if sys.platform.startswith("darwin"): dataWidget.setMaximumWidth(500) dataWidget.setMinimumWidth(500) # TODO: Temporary MacOS Fix lblWidget = QtWidgets.QWidget(self) layout = QtWidgets.QHBoxLayout(lblWidget) if "params" in bone and isinstance(bone["params"], dict) and "tooltip" in bone["params"]: lblWidget.setToolTip(self.parseHelpText(bone["params"]["tooltip"])) descrLbl = QtWidgets.QLabel(bone["descr"], lblWidget) descrLbl.setWordWrap(True) if bone["required"]: font = descrLbl.font() font.setBold(True) font.setUnderline(True) descrLbl.setFont(font) layout.addWidget(descrLbl) tabs[tabName].addRow(lblWidget, dataWidget) dataWidget.show() self.bones[key] = widget self.boneToTabMap[dataWidget] = [x[1] for x in tmpTabs].index(tabName) self.unserialize(data["values"], data["errors"]) # self._lastData = data # logger.debug("setData _lastData: %r", self._lastData) event.emit("rebuildBreadCrumbs()")
def onHtmlFileModuleUploadFinished(self, req): # we sucessfully notified ViUR of that new file fileData = NetworkService.decode(req) self.uploadResults.append(fileData["values"]) self.onRequestFinished()