wsemi 1.9.19 → 1.9.21
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/wsemi.umd.js +5 -5
- package/dist/wsemi.umd.js.map +1 -1
- package/docs/-_class.mjs.html +1 -1
- package/docs/-_const.mjs.html +1 -1
- package/docs/-_detector.mjs.html +1 -1
- package/docs/-_errToStr.mjs.html +1 -1
- package/docs/-_execThrownMsg.mjs.html +1 -1
- package/docs/-_isRealError.mjs.html +1 -1
- package/docs/-_optNum.mjs.html +1 -1
- package/docs/-_pmMarkHandled.mjs.html +1 -1
- package/docs/-_pmReadItems.mjs.html +1 -1
- package/docs/-_pmSettleByState.mjs.html +1 -1
- package/docs/-_realErrorToStr.mjs.html +1 -1
- package/docs/-_toResultError.mjs.html +1 -1
- package/docs/ab2blob.mjs.html +1 -1
- package/docs/ab2u8arr.mjs.html +1 -1
- package/docs/addExcelWorksheetFromData.mjs.html +1 -1
- package/docs/addMonth.mjs.html +1 -1
- package/docs/aes2str.mjs.html +1 -1
- package/docs/alive.mjs.html +1 -1
- package/docs/arr2dt.mjs.html +1 -1
- package/docs/arrAccum.mjs.html +1 -1
- package/docs/arrAdd.mjs.html +1 -1
- package/docs/arrAt.mjs.html +1 -1
- package/docs/arrDiff.mjs.html +1 -1
- package/docs/arrFilterByKeywords.mjs.html +1 -1
- package/docs/arrFilterByNum.mjs.html +1 -1
- package/docs/arrFilterByPnum.mjs.html +1 -1
- package/docs/arrFilterByPnumAndToLog.mjs.html +1 -1
- package/docs/arrFind.mjs.html +1 -1
- package/docs/arrGroupByMaxmin.mjs.html +1 -1
- package/docs/arrHas.mjs.html +1 -1
- package/docs/arrInsert.mjs.html +1 -1
- package/docs/arrLookupByMaxmin.mjs.html +1 -1
- package/docs/arrMax.mjs.html +1 -1
- package/docs/arrMin.mjs.html +1 -1
- package/docs/arrMulti.mjs.html +1 -1
- package/docs/arrNorm.mjs.html +1 -1
- package/docs/arrProduct.mjs.html +1 -1
- package/docs/arrPull.mjs.html +1 -1
- package/docs/arrPullAt.mjs.html +1 -1
- package/docs/arrReduce.mjs.html +1 -1
- package/docs/arrReverse.mjs.html +1 -1
- package/docs/arrSep.mjs.html +1 -1
- package/docs/arrSort.mjs.html +1 -1
- package/docs/asind.mjs.html +1 -1
- package/docs/atan2d.mjs.html +1 -1
- package/docs/atand.mjs.html +1 -1
- package/docs/attstr.mjs.html +1 -1
- package/docs/b642obj.mjs.html +1 -1
- package/docs/b642str.mjs.html +1 -1
- package/docs/b642u16arr.mjs.html +1 -1
- package/docs/b642u8arr.mjs.html +1 -1
- package/docs/binstr.mjs.html +1 -1
- package/docs/blob2ab.mjs.html +1 -1
- package/docs/blob2b64.mjs.html +1 -1
- package/docs/blob2str.mjs.html +1 -1
- package/docs/blob2u8arr.mjs.html +1 -1
- package/docs/blobs2b64s.mjs.html +1 -1
- package/docs/blobs2u8arrs.mjs.html +1 -1
- package/docs/bodyLog.mjs.html +1 -1
- package/docs/browserView.mjs.html +1 -1
- package/docs/browserViewFromBlob.mjs.html +1 -1
- package/docs/browserViewFromText.mjs.html +1 -1
- package/docs/browserViewFromU8arr.mjs.html +1 -1
- package/docs/bs2u8arr.mjs.html +1 -1
- package/docs/bufRead.mjs.html +1 -1
- package/docs/bufReadDbl.mjs.html +1 -1
- package/docs/bufWrite.mjs.html +1 -1
- package/docs/bufWriteDbl.mjs.html +1 -1
- package/docs/cache.mjs.html +1 -1
- package/docs/cacheBd.mjs.html +1 -1
- package/docs/cacheSt.mjs.html +1 -1
- package/docs/cbol.mjs.html +1 -1
- package/docs/cdbl.mjs.html +1 -1
- package/docs/ceil.mjs.html +1 -1
- package/docs/cfilesize.mjs.html +1 -1
- package/docs/cfinancial.mjs.html +1 -1
- package/docs/cint.mjs.html +1 -1
- package/docs/clearXSS.mjs.html +1 -1
- package/docs/clearXSSDyn.mjs.html +1 -1
- package/docs/color.mjs.html +1 -1
- package/docs/composeToTree.mjs.html +1 -1
- package/docs/convertToTree.mjs.html +1 -1
- package/docs/copyStrToClipboard.mjs.html +1 -1
- package/docs/cosd.mjs.html +1 -1
- package/docs/cotd.mjs.html +1 -1
- package/docs/createExcelWorkbook.mjs.html +1 -1
- package/docs/cscd.mjs.html +1 -1
- package/docs/cstr.mjs.html +1 -1
- package/docs/cvOrmFind.mjs.html +161 -23
- package/docs/day2cht.mjs.html +1 -1
- package/docs/debounce.mjs.html +1 -1
- package/docs/delay.mjs.html +1 -1
- package/docs/detectXSS.mjs.html +1 -1
- package/docs/detectXSSDyn.mjs.html +1 -1
- package/docs/dig.mjs.html +1 -1
- package/docs/digExp.mjs.html +1 -1
- package/docs/domAlert.mjs.html +1 -1
- package/docs/domAppend.mjs.html +1 -1
- package/docs/domCancelEvent.mjs.html +1 -1
- package/docs/domCompareText.mjs.html +1 -1
- package/docs/domConvertToPic.mjs.html +1 -1
- package/docs/domConvertToPicDyn.mjs.html +1 -1
- package/docs/domDetect.mjs.html +1 -1
- package/docs/domDrag.mjs.html +1 -1
- package/docs/domDragBarAndScroll.mjs.html +1 -1
- package/docs/domDragPointer.mjs.html +1 -1
- package/docs/domDragPreview.mjs.html +1 -1
- package/docs/domDropFiles.mjs.html +1 -1
- package/docs/domElementsFromPoint.mjs.html +1 -1
- package/docs/domFadeIn.mjs.html +1 -1
- package/docs/domFadeOut.mjs.html +1 -1
- package/docs/domFind.mjs.html +1 -1
- package/docs/domFinds.mjs.html +1 -1
- package/docs/domGetAttr.mjs.html +1 -1
- package/docs/domGetBoudRect.mjs.html +1 -1
- package/docs/domGetBoudRectRefSelf.mjs.html +1 -1
- package/docs/domGetFileAccept.mjs.html +1 -1
- package/docs/domGetFiles.mjs.html +1 -1
- package/docs/domGetParents.mjs.html +1 -1
- package/docs/domGetPointFromEvent.mjs.html +1 -1
- package/docs/domGetScrollableParent.mjs.html +1 -1
- package/docs/domGetWindowSize.mjs.html +1 -1
- package/docs/domIsClientXYIn.mjs.html +1 -1
- package/docs/domIsFocused.mjs.html +1 -1
- package/docs/domIsRendered.mjs.html +1 -1
- package/docs/domIsStable.mjs.html +1 -1
- package/docs/domIsVisible.mjs.html +1 -1
- package/docs/domPrepend.mjs.html +1 -1
- package/docs/domRemove.mjs.html +1 -1
- package/docs/domRenderMarkdownMind.mjs.html +1 -1
- package/docs/domRenderMarkdownMindDyn.mjs.html +1 -1
- package/docs/domRipple.mjs.html +1 -1
- package/docs/domScrollIntoView.mjs.html +1 -1
- package/docs/domScrollTo.mjs.html +1 -1
- package/docs/domSetAttr.mjs.html +1 -1
- package/docs/domShowImages.mjs.html +1 -1
- package/docs/domShowImagesDyn.mjs.html +1 -1
- package/docs/domShowInputAndGetFiles.mjs.html +1 -1
- package/docs/domShowInputAndGetFilesU8Arrs.mjs.html +1 -1
- package/docs/domShowInputDatatime.mjs.html +1 -1
- package/docs/domTooltip.mjs.html +1 -1
- package/docs/domTriggerEvent.mjs.html +1 -1
- package/docs/domVirtualCreate.mjs.html +1 -1
- package/docs/domVirtualCreateQueue.mjs.html +1 -1
- package/docs/downloadExcelFileFromData.mjs.html +1 -1
- package/docs/downloadExcelFileFromDataDyn.mjs.html +1 -1
- package/docs/downloadFileFromB64.mjs.html +1 -1
- package/docs/downloadFileFromBlob.mjs.html +1 -1
- package/docs/downloadFileFromText.mjs.html +1 -1
- package/docs/downloadFileFromU8Arr.mjs.html +1 -1
- package/docs/dtmapping.mjs.html +1 -1
- package/docs/dtpick.mjs.html +1 -1
- package/docs/estimateTicks.mjs.html +1 -1
- package/docs/evEmit.mjs.html +1 -1
- package/docs/evEmitDelay.mjs.html +1 -1
- package/docs/evem.mjs.html +1 -1
- package/docs/examples/ex-blob2b64.html +1 -1
- package/docs/examples/ex-clearXSS.html +1 -1
- package/docs/examples/ex-clearXSSDyn.html +1 -1
- package/docs/examples/ex-colorConverter.html +1 -1
- package/docs/examples/ex-detectXSS.html +1 -1
- package/docs/examples/ex-detectXSSDyn.html +1 -1
- package/docs/examples/ex-domCompareText.html +1 -1
- package/docs/examples/ex-domConvertToPic.html +1 -1
- package/docs/examples/ex-domDrag.html +1 -1
- package/docs/examples/ex-domDropFiles.html +1 -1
- package/docs/examples/ex-domIsVisible.html +1 -1
- package/docs/examples/ex-domRenderMarkdownMind.html +1 -1
- package/docs/examples/ex-domRenderMarkdownMindDyn.html +1 -1
- package/docs/examples/ex-domRipple.html +1 -1
- package/docs/examples/ex-domScrollIntoView.html +1 -1
- package/docs/examples/ex-domScrollTo.html +1 -1
- package/docs/examples/ex-domShowImages.html +1 -1
- package/docs/examples/ex-domShowImagesDyn.html +1 -1
- package/docs/examples/ex-domShowInputAndGetFiles.html +1 -1
- package/docs/examples/ex-domTooltip.html +1 -1
- package/docs/examples/ex-getFileHash.html +1 -1
- package/docs/examples/ex-getUserAgent.html +1 -1
- package/docs/examples/ex-getUserAgentDyn.html +1 -1
- package/docs/examples/ex-html2str.html +1 -1
- package/docs/examples/ex-obj2u8arr-u8arr2obj.html +1 -1
- package/docs/examples/ex-openLink.html +1 -1
- package/docs/examples/ex-str2aes-aes2str.html +1 -1
- package/docs/examples/ex-str2b64-b642str.html +1 -1
- package/docs/examples/ex-strFindFuzz.html +1 -1
- package/docs/examples/ex-timeTZ2expire-timeTZ2past.html +1 -1
- package/docs/examples/ex-xlsx.html +1 -1
- package/docs/execCli.mjs.html +1 -1
- package/docs/execCliCore.mjs.html +1 -1
- package/docs/execCliJsonRpc.mjs.html +1 -1
- package/docs/execCliSession.mjs.html +1 -1
- package/docs/execJsCode.mjs.html +1 -1
- package/docs/execProcess.mjs.html +1 -1
- package/docs/execProcessKillPid.mjs.html +1 -1
- package/docs/filepathToTree.mjs.html +1 -1
- package/docs/files2data.mjs.html +1 -1
- package/docs/flattenToConn.mjs.html +1 -1
- package/docs/flattenTree.mjs.html +1 -1
- package/docs/floor.mjs.html +1 -1
- package/docs/fsBuildReadStreamText.mjs.html +1 -1
- package/docs/fsBuildWriteStreamText.mjs.html +1 -1
- package/docs/fsCleanFolder.mjs.html +1 -1
- package/docs/fsCleanFolderCore.mjs.html +1 -1
- package/docs/fsCopyFile.mjs.html +1 -1
- package/docs/fsCopyFileCore.mjs.html +1 -1
- package/docs/fsCopyFolder.mjs.html +1 -1
- package/docs/fsCopyFolderCore.mjs.html +1 -1
- package/docs/fsCreateFile.mjs.html +1 -1
- package/docs/fsCreateFileCore.mjs.html +1 -1
- package/docs/fsCreateFolder.mjs.html +1 -1
- package/docs/fsCreateFolderCore.mjs.html +1 -1
- package/docs/fsDeleteFile.mjs.html +1 -1
- package/docs/fsDeleteFileCore.mjs.html +1 -1
- package/docs/fsDeleteFileSafe.mjs.html +1 -1
- package/docs/fsDeleteFileSafeCore.mjs.html +1 -1
- package/docs/fsDeleteFolder.mjs.html +1 -1
- package/docs/fsDeleteFolderCore.mjs.html +1 -1
- package/docs/fsDeleteFolderSafe.mjs.html +1 -1
- package/docs/fsDeleteFolderSafeCore.mjs.html +1 -1
- package/docs/fsDownloadFile.mjs.html +1 -1
- package/docs/fsDownloadFileCore.mjs.html +1 -1
- package/docs/fsEvem.mjs.html +1 -1
- package/docs/fsExists.mjs.html +1 -1
- package/docs/fsExistsCore.mjs.html +1 -1
- package/docs/fsGetFileBasicHash.mjs.html +1 -1
- package/docs/fsGetFileBasicHashCore.mjs.html +1 -1
- package/docs/fsGetFileHash.mjs.html +1 -1
- package/docs/fsGetFileHashCore.mjs.html +1 -1
- package/docs/fsGetFileXxHash.mjs.html +1 -1
- package/docs/fsGetFileXxHashCore.mjs.html +1 -1
- package/docs/fsGetFilesInFolder.mjs.html +1 -1
- package/docs/fsGetFilesInFolderCore.mjs.html +1 -1
- package/docs/fsGetFilesWithHashInFolder.mjs.html +1 -1
- package/docs/fsGetFilesWithHashInFolderCore.mjs.html +1 -1
- package/docs/fsGetFolderBasicHash.mjs.html +1 -1
- package/docs/fsGetFolderBasicHashCore.mjs.html +1 -1
- package/docs/fsGetFoldersInFolder.mjs.html +1 -1
- package/docs/fsGetFoldersInFolderCore.mjs.html +1 -1
- package/docs/fsIsFile.mjs.html +1 -1
- package/docs/fsIsFileCore.mjs.html +1 -1
- package/docs/fsIsFolder.mjs.html +1 -1
- package/docs/fsIsFolderCore.mjs.html +1 -1
- package/docs/fsMergeFiles.mjs.html +1 -1
- package/docs/fsMergeFilesCore.mjs.html +1 -1
- package/docs/fsReadJson.mjs.html +1 -1
- package/docs/fsReadText.mjs.html +1 -1
- package/docs/fsReadTextCore.mjs.html +1 -1
- package/docs/fsRenameFile.mjs.html +1 -1
- package/docs/fsRenameFileCore.mjs.html +1 -1
- package/docs/fsRenameFolder.mjs.html +1 -1
- package/docs/fsRenameFolderCore.mjs.html +1 -1
- package/docs/fsSrlog.mjs.html +1 -1
- package/docs/fsSyncFolder.mjs.html +1 -1
- package/docs/fsSyncFolderCore.mjs.html +1 -1
- package/docs/fsTask.mjs.html +1 -1
- package/docs/fsTaskCp.mjs.html +1 -1
- package/docs/fsTreeFolder.mjs.html +1 -1
- package/docs/fsTreeFolderCore.mjs.html +1 -1
- package/docs/fsTreeFolderWithHash.mjs.html +1 -1
- package/docs/fsTreeFolderWithHashCore.mjs.html +1 -1
- package/docs/fsWatchFile.mjs.html +1 -1
- package/docs/fsWatchFolder.mjs.html +1 -1
- package/docs/fsWriteJson.mjs.html +1 -1
- package/docs/fsWriteText.mjs.html +1 -1
- package/docs/fsWriteTextCore.mjs.html +1 -1
- package/docs/genGradientColor.mjs.html +1 -1
- package/docs/genID.mjs.html +1 -1
- package/docs/genIDSeq.mjs.html +1 -1
- package/docs/genPm.mjs.html +1 -1
- package/docs/getBufferSize.mjs.html +1 -1
- package/docs/getClearPathName.mjs.html +1 -1
- package/docs/getCsvStrFromData.mjs.html +1 -1
- package/docs/getDataFromExcelFileU8Arr.mjs.html +1 -1
- package/docs/getDataFromExcelFileU8ArrDyn.mjs.html +1 -1
- package/docs/getEnv.mjs.html +1 -1
- package/docs/getErrorMessage.mjs.html +1 -1
- package/docs/getExcelU8ArrFromData.mjs.html +1 -1
- package/docs/getExcelU8ArrFromWorkbook.mjs.html +1 -1
- package/docs/getExcelWorkbookFromData.mjs.html +1 -1
- package/docs/getExcelWorkbookFromWorksheet.mjs.html +1 -1
- package/docs/getExcelWorksheetFromData.mjs.html +1 -1
- package/docs/getFileAccept.mjs.html +1 -1
- package/docs/getFileBasicHash.mjs.html +1 -1
- package/docs/getFileHash.mjs.html +1 -1
- package/docs/getFileName.mjs.html +1 -1
- package/docs/getFileNameExt.mjs.html +1 -1
- package/docs/getFileTrueName.mjs.html +1 -1
- package/docs/getFileType.mjs.html +1 -1
- package/docs/getFileXxHash.mjs.html +1 -1
- package/docs/getGlobal.mjs.html +1 -1
- package/docs/getObjSize.mjs.html +1 -1
- package/docs/getPathParent.mjs.html +1 -1
- package/docs/getTimeBetween.mjs.html +1 -1
- package/docs/getTimeFromUnit.mjs.html +1 -1
- package/docs/getTimeHp.mjs.html +1 -1
- package/docs/getTimeObject.mjs.html +1 -1
- package/docs/getTimeRange.mjs.html +1 -1
- package/docs/getUserAgent.mjs.html +1 -1
- package/docs/getUserAgentDyn.mjs.html +1 -1
- package/docs/getltdtkeys.mjs.html +1 -1
- package/docs/global.html +1 -1
- package/docs/haskey.mjs.html +1 -1
- package/docs/html2str.mjs.html +1 -1
- package/docs/htmlDecode.mjs.html +1 -1
- package/docs/htmlEncode.mjs.html +1 -1
- package/docs/importResources.mjs.html +1 -1
- package/docs/index.html +1 -1
- package/docs/interp1.mjs.html +1 -1
- package/docs/isDate.mjs.html +1 -1
- package/docs/isDev.mjs.html +1 -1
- package/docs/isEle.mjs.html +1 -1
- package/docs/isEleExistByID.mjs.html +1 -1
- package/docs/isEmail.mjs.html +1 -1
- package/docs/isErr.mjs.html +1 -1
- package/docs/isIE.mjs.html +1 -1
- package/docs/isNarrow.mjs.html +1 -1
- package/docs/isStrHasCapital.mjs.html +1 -1
- package/docs/isStrHasLetter.mjs.html +1 -1
- package/docs/isStrHasLowerCase.mjs.html +1 -1
- package/docs/isStrHasNumber.mjs.html +1 -1
- package/docs/isStrHasSpace.mjs.html +1 -1
- package/docs/isStrHasSymbol.mjs.html +1 -1
- package/docs/isUserIdentify.mjs.html +1 -1
- package/docs/isUserName.mjs.html +1 -1
- package/docs/isUserPw.mjs.html +1 -1
- package/docs/isWindow.mjs.html +1 -1
- package/docs/isab.mjs.html +1 -1
- package/docs/isarr.mjs.html +1 -1
- package/docs/isarr0.mjs.html +1 -1
- package/docs/isarr1.mjs.html +1 -1
- package/docs/isbigint.mjs.html +1 -1
- package/docs/isblob.mjs.html +1 -1
- package/docs/isbol.mjs.html +1 -1
- package/docs/isday.mjs.html +1 -1
- package/docs/isearr.mjs.html +1 -1
- package/docs/iseobj.mjs.html +1 -1
- package/docs/iser.mjs.html +1 -1
- package/docs/isernot.mjs.html +1 -1
- package/docs/isestr.mjs.html +1 -1
- package/docs/isfile.mjs.html +1 -1
- package/docs/isfun.mjs.html +1 -1
- package/docs/isint.mjs.html +1 -1
- package/docs/ismonth.mjs.html +1 -1
- package/docs/isn0int.mjs.html +1 -1
- package/docs/isn0num.mjs.html +1 -1
- package/docs/isnan.mjs.html +1 -1
- package/docs/isnbr.mjs.html +1 -1
- package/docs/isnint.mjs.html +1 -1
- package/docs/isnnum.mjs.html +1 -1
- package/docs/isnull.mjs.html +1 -1
- package/docs/isnum.mjs.html +1 -1
- package/docs/isobj.mjs.html +1 -1
- package/docs/isobj0.mjs.html +1 -1
- package/docs/isp0int.mjs.html +1 -1
- package/docs/isp0num.mjs.html +1 -1
- package/docs/ispint.mjs.html +1 -1
- package/docs/ispm.mjs.html +1 -1
- package/docs/ispnum.mjs.html +1 -1
- package/docs/isstr.mjs.html +1 -1
- package/docs/isstr0.mjs.html +1 -1
- package/docs/istime.mjs.html +1 -1
- package/docs/istimeTZ.mjs.html +1 -1
- package/docs/istimems.mjs.html +1 -1
- package/docs/istimemsTZ.mjs.html +1 -1
- package/docs/isu16arr.mjs.html +1 -1
- package/docs/isu8arr.mjs.html +1 -1
- package/docs/isundefined.mjs.html +1 -1
- package/docs/j2o.mjs.html +1 -1
- package/docs/judge.mjs.html +1 -1
- package/docs/keysmat2ltdt.mjs.html +1 -1
- package/docs/ltdt2vrtsable.mjs.html +1 -1
- package/docs/ltdtDiff.mjs.html +1 -1
- package/docs/ltdtDiffByKey.mjs.html +1 -1
- package/docs/ltdtkeys2mat.mjs.html +1 -1
- package/docs/ltdtkeysheads2mat.mjs.html +1 -1
- package/docs/ltdtmapping.mjs.html +1 -1
- package/docs/ltdtmerge.mjs.html +1 -1
- package/docs/ltdtpick.mjs.html +1 -1
- package/docs/ltdtpull.mjs.html +1 -1
- package/docs/mat2ltdt.mjs.html +1 -1
- package/docs/matConcat.mjs.html +1 -1
- package/docs/matDiff.mjs.html +1 -1
- package/docs/matat.mjs.html +1 -1
- package/docs/now2str.mjs.html +1 -1
- package/docs/now2strp.mjs.html +1 -1
- package/docs/nowDay2str.mjs.html +1 -1
- package/docs/nowms2str.mjs.html +1 -1
- package/docs/nowms2strp.mjs.html +1 -1
- package/docs/o2j.mjs.html +1 -1
- package/docs/obj2b64.mjs.html +1 -1
- package/docs/obj2pb64.mjs.html +1 -1
- package/docs/obj2str.mjs.html +1 -1
- package/docs/obj2stru8arr.mjs.html +1 -1
- package/docs/obj2u8arr.mjs.html +1 -1
- package/docs/objSortBy.mjs.html +1 -1
- package/docs/objSortByKeys.mjs.html +1 -1
- package/docs/oo.mjs.html +1 -1
- package/docs/openLink.mjs.html +1 -1
- package/docs/pb642obj.mjs.html +1 -1
- package/docs/pmChain.mjs.html +1 -1
- package/docs/pmConvertResolve.mjs.html +1 -1
- package/docs/pmDebounce.mjs.html +1 -1
- package/docs/pmHook.mjs.html +1 -1
- package/docs/pmHookReject.mjs.html +1 -1
- package/docs/pmIni.mjs.html +1 -1
- package/docs/pmInvResolve.mjs.html +1 -1
- package/docs/pmKeyMutex.mjs.html +1 -1
- package/docs/pmMap.mjs.html +1 -1
- package/docs/pmQueue.mjs.html +1 -1
- package/docs/pmSeries.mjs.html +1 -1
- package/docs/pmThrottle.mjs.html +1 -1
- package/docs/pmTimeout.mjs.html +1 -1
- package/docs/preciseNum.mjs.html +1 -1
- package/docs/pseudoRandom.mjs.html +1 -1
- package/docs/pseudoRandomIntRange.mjs.html +1 -1
- package/docs/pseudoRandomIntsNdpRange.mjs.html +1 -1
- package/docs/pseudoRandomIntsRange.mjs.html +1 -1
- package/docs/pseudoRandomRange.mjs.html +1 -1
- package/docs/pseudoRandomsRange.mjs.html +1 -1
- package/docs/queue.mjs.html +1 -1
- package/docs/random.mjs.html +1 -1
- package/docs/randomIntRange.mjs.html +1 -1
- package/docs/randomIntsNdpRange.mjs.html +1 -1
- package/docs/randomIntsRange.mjs.html +1 -1
- package/docs/randomRange.mjs.html +1 -1
- package/docs/randomsRange.mjs.html +1 -1
- package/docs/rang.mjs.html +1 -1
- package/docs/rep.mjs.html +1 -1
- package/docs/repObj.mjs.html +1 -1
- package/docs/replace.mjs.html +1 -1
- package/docs/replaceObj.mjs.html +1 -1
- package/docs/replacePlus.mjs.html +1 -1
- package/docs/round.mjs.html +1 -1
- package/docs/secd.mjs.html +1 -1
- package/docs/sep.mjs.html +1 -1
- package/docs/sepInt.mjs.html +1 -1
- package/docs/setIntervalHp.mjs.html +1 -1
- package/docs/setTimeoutHp.mjs.html +1 -1
- package/docs/sind.mjs.html +1 -1
- package/docs/split.mjs.html +1 -1
- package/docs/str2aes.mjs.html +1 -1
- package/docs/str2b64.mjs.html +1 -1
- package/docs/str2hint.mjs.html +1 -1
- package/docs/str2md5.mjs.html +1 -1
- package/docs/str2obj.mjs.html +1 -1
- package/docs/str2sha.mjs.html +1 -1
- package/docs/str2sha512.mjs.html +1 -1
- package/docs/str2u8arr.mjs.html +1 -1
- package/docs/strCompare.mjs.html +1 -1
- package/docs/strCompareForVersion.mjs.html +1 -1
- package/docs/strDiff.mjs.html +1 -1
- package/docs/strDiffToHtml.mjs.html +1 -1
- package/docs/strFindFuzz.mjs.html +1 -1
- package/docs/strFindSimilar.mjs.html +1 -1
- package/docs/strTruncate.mjs.html +1 -1
- package/docs/strdelleft.mjs.html +1 -1
- package/docs/strdelright.mjs.html +1 -1
- package/docs/strleft.mjs.html +1 -1
- package/docs/strmid.mjs.html +1 -1
- package/docs/strright.mjs.html +1 -1
- package/docs/stru8arr2obj.mjs.html +1 -1
- package/docs/tand.mjs.html +1 -1
- package/docs/time2day.mjs.html +1 -1
- package/docs/time2hour.mjs.html +1 -1
- package/docs/time2min.mjs.html +1 -1
- package/docs/timeTZ2day.mjs.html +1 -1
- package/docs/timeTZ2expire.mjs.html +1 -1
- package/docs/timeTZ2hour.mjs.html +1 -1
- package/docs/timeTZ2min.mjs.html +1 -1
- package/docs/timeTZ2past.mjs.html +1 -1
- package/docs/timems2day.mjs.html +1 -1
- package/docs/timems2hour.mjs.html +1 -1
- package/docs/timems2min.mjs.html +1 -1
- package/docs/timems2time.mjs.html +1 -1
- package/docs/timemsTZ2day.mjs.html +1 -1
- package/docs/timemsTZ2expire.mjs.html +1 -1
- package/docs/timemsTZ2hour.mjs.html +1 -1
- package/docs/timemsTZ2min.mjs.html +1 -1
- package/docs/timemsTZ2past.mjs.html +1 -1
- package/docs/timemsTZ2time.mjs.html +1 -1
- package/docs/treeObj.mjs.html +1 -1
- package/docs/treeToFilepath.mjs.html +1 -1
- package/docs/trim.mjs.html +1 -1
- package/docs/u16arr2b64.mjs.html +1 -1
- package/docs/u16arr2u8arr.mjs.html +1 -1
- package/docs/u8arr2ab.mjs.html +1 -1
- package/docs/u8arr2b64.mjs.html +1 -1
- package/docs/u8arr2blob.mjs.html +1 -1
- package/docs/u8arr2bs.mjs.html +1 -1
- package/docs/u8arr2obj.mjs.html +1 -1
- package/docs/u8arr2str.mjs.html +1 -1
- package/docs/u8arr2u16arr.mjs.html +1 -1
- package/docs/urlParse.mjs.html +1 -1
- package/docs/verifyValue.mjs.html +1 -1
- package/docs/waitFun.mjs.html +1 -1
- package/docs/wsemi.html +5 -5
- package/package.json +2 -2
- package/src/_cvOrmFindCases.mjs +16 -0
- package/src/cvOrmFind.mjs +160 -22
- package/test/cvOrmFind.test.mjs +666 -17
- package/test/tools/cvOrmFindRunner.mjs +7 -1
- package/toolfp/dist/wsemip.umd.js +1 -1
- package/toolparfor/dist/wpf.umd.js +1 -1
- package/toolparfor/dist/wpf_pmSeries.umd.js +1 -1
package/docs/wsemi.html
CHANGED
|
@@ -18396,7 +18396,7 @@ console.log(wb)
|
|
|
18396
18396
|
<p>白名單:</p>
|
|
18397
18397
|
<ol>
|
|
18398
18398
|
<li>
|
|
18399
|
-
<p>頂層與每層條件物件須為一般物件(原型為Object.prototype或null),null、陣列、字串、數值、布林、函數、Date、RegExp、Map、Set、類別實例等一律reject,不得視同{};原型被改為null或Object.prototype之Map、Set、Promise、ArrayBuffer、DataView、TypedArray
|
|
18399
|
+
<p>頂層與每層條件物件須為一般物件(原型為Object.prototype或null),null、陣列、字串、數值、布林、函數、Date、RegExp、Map、Set、類別實例等一律reject,不得視同{};原型被改為null或Object.prototype之Map、Set、WeakMap、WeakSet、Promise、ArrayBuffer、DataView、TypedArray、Symbol與BigInt包裝、WeakRef、FinalizationRegistry等內建品牌物件,於任何位置(頂層、欄位運算子物件、$and/$or元素,空或帶自有鍵)亦reject;頂層空物件(代表全部)須可證明為真實空物件,Proxy與不可複製之宿主物件不視為全部</p>
|
|
18400
18400
|
</li>
|
|
18401
18401
|
<li>
|
|
18402
18402
|
<p>欄位等值{欄: 純量},多欄隱含AND;純量為字串、有限數字(含-0)、布林、有效Date,字串不得含NUL與孤立代理字元;null僅可用於欄位等值、$eq、$ne</p>
|
|
@@ -18420,8 +18420,8 @@ console.log(wb)
|
|
|
18420
18420
|
<p>上限(opt只可下調,不可放寬):邏輯巢狀深度32、$and/$or長度1000、$in/$nin長度10000、節點總數100000(條件物件、運算子物件、純量各計1)、欄名128</p>
|
|
18421
18421
|
</li>
|
|
18422
18422
|
</ol>
|
|
18423
|
-
<p>錯誤一律為同步拋出之Error('invalid find: 原因 at [路徑]'),不回顯值(鍵名為路徑之一部分,限30字元並以?取代控制字元、格式字元與方括號);走訪中任何例外(含呼叫端之getter、Proxy陷阱、Symbol.toStringTag getter)
|
|
18424
|
-
<p>已知限制:判定內部標籤須讀Symbol.toStringTag,可能執行呼叫端之Proxy陷阱或getter(例外一律轉為invalid find)
|
|
18423
|
+
<p>錯誤一律為同步拋出之Error('invalid find: 原因 at [路徑]'),不回顯值(鍵名為路徑之一部分,限30字元並以?取代控制字元、格式字元與方括號);走訪中任何例外(含呼叫端之getter、Proxy陷阱、Symbol.toStringTag getter)一律轉為此格式,不轉述呼叫端之錯誤訊息,描述子陷阱拋錯、存取器與不可列舉屬性之路徑含該屬性鍵或元素索引;可重入。opt須為物件、null或未給,僅可含下列五個鍵(自有資料屬性),設定錯誤另拋Error('invalid opt: 原因')。</p>
|
|
18424
|
+
<p>已知限制:判定內部標籤須讀Symbol.toStringTag,可能執行呼叫端之Proxy陷阱或getter(例外一律轉為invalid find);Proxy無法穿透,非空位置之Proxy包住原型被改之品牌物件視同其經陷阱暴露之條件物件;無法觀察品牌者(含私有欄位之類別實例與AbortController等宿主物件改原型為null、自有鍵為純量constructor之Promise)不被辨出;品牌檢查先以一次結構化複製(structuredClone)證明被記錄之條件物件皆非品牌物件,環境無可用之該全域、字串總長逾400萬碼元或樹內含Proxy時改逐物件探針(每物件約50微秒,含Proxy之近節點上限輸入可達數秒),且無可用之該全域時無法辨出空Proxy;被判為品牌物件而reject者,其內部資料(Map/Set之項目、ArrayBuffer之位元組)可能被複製讀取一次,成本不受節點預算約束;Proxy之ownKeys結果於引擎內先被完整具現化,其成本不受節點預算約束;共享參照(同一物件出現於多處)每出現一次即各讀各檢各複製,節點數亦逐次計入</p>
|
|
18425
18425
|
<p>後端專屬之檢核(欄位型別、欄是否存在、主鍵正規化、DATE範圍、NULL三值語意)不在此,由各後端於本函數之後自行處理;契約案例表見wsemi/src/_cvOrmFindCases.mjs。</p>
|
|
18426
18426
|
<p>Unit Test: <a href="https://github.com/yuda-lyu/wsemi/blob/master/test/cvOrmFind.test.mjs">Github</a></p></li></ul></dd>
|
|
18427
18427
|
|
|
@@ -18429,7 +18429,7 @@ console.log(wb)
|
|
|
18429
18429
|
|
|
18430
18430
|
<dt class="tag-source">Source:</dt>
|
|
18431
18431
|
<dd class="tag-source"><ul class="dummy"><li>
|
|
18432
|
-
<a href="cvOrmFind.mjs.html">cvOrmFind.mjs</a>, <a href="cvOrmFind.mjs.html#
|
|
18432
|
+
<a href="cvOrmFind.mjs.html">cvOrmFind.mjs</a>, <a href="cvOrmFind.mjs.html#line762">line 762</a>
|
|
18433
18433
|
</li></ul></dd>
|
|
18434
18434
|
|
|
18435
18435
|
|
|
@@ -111455,7 +111455,7 @@ console.log(u8arr2u16arr('abc', { returnWithStateAndMsg: true }))
|
|
|
111455
111455
|
<br class="clear">
|
|
111456
111456
|
|
|
111457
111457
|
<footer>
|
|
111458
|
-
Documentation generated by <a href="https://github.com/jsdoc3/jsdoc">JSDoc 4.0.5</a> on
|
|
111458
|
+
Documentation generated by <a href="https://github.com/jsdoc3/jsdoc">JSDoc 4.0.5</a> on Mon Oct 19 2026 23:54:10 GMT+0800 (台北標準時間) using the <a href="https://github.com/clenemt/docdash">docdash</a> theme.
|
|
111459
111459
|
</footer>
|
|
111460
111460
|
|
|
111461
111461
|
<script>prettyPrint();</script>
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "wsemi",
|
|
3
|
-
"version": "1.9.
|
|
3
|
+
"version": "1.9.21",
|
|
4
4
|
"main": "dist/wsemi.umd.js",
|
|
5
5
|
"dependencies": {
|
|
6
6
|
"@zumer/snapdom": "^3.3.0",
|
|
@@ -27,7 +27,7 @@
|
|
|
27
27
|
"xxhash-wasm": "^1.1.0"
|
|
28
28
|
},
|
|
29
29
|
"devDependencies": {
|
|
30
|
-
"w-package-tools": "^1.1.
|
|
30
|
+
"w-package-tools": "^1.1.21"
|
|
31
31
|
},
|
|
32
32
|
"scripts": {
|
|
33
33
|
"test": "mocha --parallel \"test/*.test.mjs\" --timeout 180000",
|
package/src/_cvOrmFindCases.mjs
CHANGED
|
@@ -26,6 +26,7 @@
|
|
|
26
26
|
//
|
|
27
27
|
//各後端對OK案之共同斷言: select(find)命中集合 = 依族別之ids; delAll(find)刪除之集合 = select(find)命中之集合(delAll前以seed()重建);
|
|
28
28
|
//對REJ案之共同斷言: select與delAll皆reject且訊息以'invalid find: '開頭, 資料表不變.
|
|
29
|
+
//例外: T38與T39(Proxy包空物件)以環境有可用之structuredClone為前提(Node 17以上、主流瀏覽器皆有); 無者cvOrmFind視為全部(帳本R-FIND-01已知限制9).
|
|
29
30
|
|
|
30
31
|
|
|
31
32
|
let columns = {
|
|
@@ -80,6 +81,7 @@ let W = {
|
|
|
80
81
|
hole: 'sparse array hole',
|
|
81
82
|
extra: 'array carries extra properties',
|
|
82
83
|
exc: 'an exception was thrown',
|
|
84
|
+
emptyodd: 'an empty find must be an ordinary object',
|
|
83
85
|
}
|
|
84
86
|
|
|
85
87
|
let A6 = ['a1', 'a2', 'a3', 'a4', 'a5', 'a6']
|
|
@@ -154,6 +156,14 @@ S('T28', 'WL-H5', '已撤銷之Proxy', () => {
|
|
|
154
156
|
S('T29', 'WL-02', '原型改為null之Map(標籤被誤判為一般物件, 無自有鍵會成為「全部」)', () => Object.setPrototypeOf(new Map([['id', 'a1']]), null), 'REJ', { why: W.plain })
|
|
155
157
|
S('T30', 'WL-02', '原型改為Object.prototype之Set', () => Object.setPrototypeOf(new Set(['a1']), Object.prototype), 'REJ', { why: W.plain })
|
|
156
158
|
S('T31', 'WL-02', '原型改為null之Uint8Array(4)', () => Object.setPrototypeOf(new Uint8Array(4), null), 'REJ', { why: W.plain })
|
|
159
|
+
S('T32', 'WL-02', '原型改為null之Map且帶自有鍵g(曾被當成條件{g:\'A\'})', () => Object.assign(Object.setPrototypeOf(new Map(), null), { g: 'A' }), 'REJ', { why: W.plain })
|
|
160
|
+
S('T33', 'WL-02', '原型改為Object.prototype之Set且帶自有鍵g', () => Object.assign(Object.setPrototypeOf(new Set(), Object.prototype), { g: 'A' }), 'REJ', { why: W.plain })
|
|
161
|
+
S('T34', 'WL-02', '原型改為null之Promise且帶自有鍵g', () => Object.assign(Object.setPrototypeOf(Promise.resolve(1), null), { g: 'A' }), 'REJ', { why: W.plain })
|
|
162
|
+
S('T35', 'WL-02', '原型改為null之ArrayBuffer且帶自有鍵g', () => Object.assign(Object.setPrototypeOf(new ArrayBuffer(4), null), { g: 'A' }), 'REJ', { why: W.plain })
|
|
163
|
+
S('T36', 'WL-02', '原型改為null之Uint8Array(2)且帶自有鍵g', () => Object.assign(Object.setPrototypeOf(new Uint8Array(2), null), { g: 'A' }), 'REJ', { why: W.plain })
|
|
164
|
+
S('T37', 'WL-02', '原型改為null之WeakMap且帶自有鍵g', () => Object.assign(Object.setPrototypeOf(new WeakMap(), null), { g: 'A' }), 'REJ', { why: W.plain })
|
|
165
|
+
S('T38', 'WL-02', 'Proxy包原型改為null之Map(無自有鍵, 曾被當成空條件而使delAll刪光全表; 前提: 環境有可用之structuredClone, 無者視為全部)', () => new Proxy(Object.setPrototypeOf(new Map(), null), {}), 'REJ', { why: W.emptyodd })
|
|
166
|
+
S('T39', 'WL-01', 'Proxy包空物件(空即全部, 須為可證明之真實空物件, Proxy不視為全部; 前提: 環境有可用之structuredClone, 無者視為全部)', () => new Proxy({}, {}), 'REJ', { why: W.emptyodd })
|
|
157
167
|
|
|
158
168
|
//E 等值與純量型別(WL-03、WL-S1、WL-S2)
|
|
159
169
|
S('E01', 'WL-03', '{id:\'a1\'}', () => ({ id: 'a1' }), 'OK', { ids: I(['a1']) })
|
|
@@ -453,6 +463,12 @@ S('H27', 'WL-H5', '欄值之Symbol.toStringTag getter拋錯', () => ({
|
|
|
453
463
|
}
|
|
454
464
|
}), 'REJ', { why: W.exc })
|
|
455
465
|
S('H28', 'WL-L3', '$in含10000元素(上限內; 首元素\'Mary\', 其餘填充; 後端上限低於10000者應reject)', () => ({ name: { $in: ['Mary', ...fills(9999)] } }), 'OK', { ids: I(['a3']), need: { maxIn: 10000 } })
|
|
466
|
+
S('H29', 'WL-02', '$or元素為原型改為null之Map且帶自有鍵g', () => ({ $or: [Object.assign(Object.setPrototypeOf(new Map(), null), { g: 'A' })] }), 'REJ', { why: W.plain })
|
|
467
|
+
S('H30', 'WL-02', '$and元素為原型改為Object.prototype之Set且帶自有鍵g', () => ({ $and: [{ age: { $gt: 0 } }, Object.assign(Object.setPrototypeOf(new Set(), Object.prototype), { g: 'A' })] }), 'REJ', { why: W.plain })
|
|
468
|
+
S('H31', 'WL-02', '欄位運算子物件為原型改為null之Map且帶自有鍵$gt', () => ({ age: Object.assign(Object.setPrototypeOf(new Map(), null), { $gt: 20 }) }), 'REJ', { why: W.type })
|
|
469
|
+
S('H32', 'WL-02', '巢狀$or/$and內之原型改為null之Promise且帶自有鍵g', () => ({ $or: [{ g: 'B' }, { $and: [Object.assign(Object.setPrototypeOf(Promise.resolve(1), null), { g: 'A' })] }] }), 'REJ', { why: W.plain })
|
|
470
|
+
S('H33', 'WL-02', '$or元素為Proxy包原型改為null之Map(空; 非頂層之空物件本即reject)', () => ({ $or: [new Proxy(Object.setPrototypeOf(new Map(), null), {})] }), 'REJ', { why: W.emptydoc })
|
|
471
|
+
S('H34', 'WL-02', '欄位值為Proxy包原型改為null之Map(空運算子物件)', () => ({ age: new Proxy(Object.setPrototypeOf(new Map(), null), {}) }), 'REJ', { why: W.emptyop })
|
|
456
472
|
|
|
457
473
|
|
|
458
474
|
let cases = list
|
package/src/cvOrmFind.mjs
CHANGED
|
@@ -14,12 +14,17 @@
|
|
|
14
14
|
//預設上限, opt只可下調
|
|
15
15
|
let DEF = { maxDepth: 32, maxList: 1000, maxIn: 10000, maxNodes: 100000, maxKey: 128 }
|
|
16
16
|
|
|
17
|
+
//結構化複製對重複出現之字串每次皆寫出並讀回, 記憶體與(字串總長 x 出現次數)成正比(同一字串被引用一萬次即放大一萬倍),
|
|
18
|
+
//走訪時累計字串碼元總長(含重複), 逾此門檻不複製而改走探針(探針成本與物件數成正比、與字串長度無關)
|
|
19
|
+
let CLONE_MAX_CHARS = 4000000
|
|
20
|
+
|
|
17
21
|
//內建函數(模組載入時取得, 不受其後之全域汙染影響)
|
|
18
22
|
let ownKeys = Reflect.ownKeys
|
|
19
23
|
let getDesc = Object.getOwnPropertyDescriptor
|
|
20
24
|
let getProto = Object.getPrototypeOf
|
|
21
25
|
let defProp = Object.defineProperty
|
|
22
26
|
let create = Object.create
|
|
27
|
+
let setProto = Object.setPrototypeOf
|
|
23
28
|
let isArray = Array.isArray
|
|
24
29
|
let isInt = Number.isInteger
|
|
25
30
|
let isFin = Number.isFinite
|
|
@@ -43,7 +48,7 @@ let toStr = String
|
|
|
43
48
|
//內部槽之品牌檢查: Map、Set、Promise等之標籤取自其原型之Symbol.toStringTag, 原型被改為null或Object.prototype後
|
|
44
49
|
//Object.prototype.toString回[object Object]而判為一般物件. TypedArray之標籤getter對非TypedArray回傳undefined(不拋錯),
|
|
45
50
|
//可於每個物件檢查(其自有索引鍵之數量與元素數成正比, 須在列舉自有鍵之前擋下); 其餘以品牌方法對非該型別拋錯判定,
|
|
46
|
-
|
|
51
|
+
//每次拋錯約3us, 逐物件探測於常見輸入慢約29倍至100倍, 故走訪完畢後先以一次結構化複製證明無品牌物件, 證明不成立才逐物件探針(規則16)
|
|
47
52
|
let taTag = call.bind(getDesc(getProto(Uint8Array.prototype), Symbol.toStringTag).get)
|
|
48
53
|
let probeKey = {}
|
|
49
54
|
let noop = () => {}
|
|
@@ -51,7 +56,7 @@ let mapHas = call.bind(Map.prototype.has)
|
|
|
51
56
|
let setHas = call.bind(Set.prototype.has)
|
|
52
57
|
let weakMapHas = call.bind(WeakMap.prototype.has)
|
|
53
58
|
let abLength = call.bind(getDesc(ArrayBuffer.prototype, 'byteLength').get)
|
|
54
|
-
let
|
|
59
|
+
let dvBuffer = call.bind(getDesc(DataView.prototype, 'buffer').get) //不用byteLength: detached或越界之DataView其byteLength getter亦拋錯而被誤判為非DataView, buffer getter不受影響
|
|
55
60
|
let symValueOf = call.bind(Symbol.prototype.valueOf)
|
|
56
61
|
let promiseThen = call.bind(Promise.prototype.then)
|
|
57
62
|
let probes = [
|
|
@@ -60,7 +65,7 @@ let probes = [
|
|
|
60
65
|
(v) => weakMapHas(v, probeKey),
|
|
61
66
|
(v) => oursHas(v, probeKey),
|
|
62
67
|
(v) => abLength(v),
|
|
63
|
-
(v) =>
|
|
68
|
+
(v) => dvBuffer(v),
|
|
64
69
|
(v) => symValueOf(v),
|
|
65
70
|
(v) => promiseThen(v, noop, noop), //兩個處理器皆給, 使真Promise衍生之Promise不致產生未處理之rejection
|
|
66
71
|
]
|
|
@@ -72,11 +77,71 @@ if (typeof WeakRef === 'function') {
|
|
|
72
77
|
let deref = call.bind(WeakRef.prototype.deref)
|
|
73
78
|
probes[probes.length] = (v) => deref(v)
|
|
74
79
|
}
|
|
80
|
+
if (typeof FinalizationRegistry === 'function') {
|
|
81
|
+
let frUnregister = call.bind(FinalizationRegistry.prototype.unregister)
|
|
82
|
+
probes[probes.length] = (v) => frUnregister(v, probeKey) //token為物件故不拋錯(回false), 非FinalizationRegistry則拋錯
|
|
83
|
+
}
|
|
75
84
|
if (typeof BigInt === 'function') {
|
|
76
85
|
let bigValueOf = call.bind(BigInt.prototype.valueOf)
|
|
77
86
|
probes[probes.length] = (v) => bigValueOf(v)
|
|
78
87
|
}
|
|
79
88
|
|
|
89
|
+
//sClone, 結構化複製(Web標準全域, 非Node API; 規則16): 用於證明條件物件中無品牌物件, 不可用時為null(改走精確探針).
|
|
90
|
+
//載入時自檢: 對Proxy須拋錯(Proxy無內部槽, 不拋錯者表示會經陷阱讀取, 不可用)、Map複製後仍為Map、{}複製後為標籤[object Object]且原型為
|
|
91
|
+
//有效之Object.prototype(自身無原型、含hasOwnProperty); 原型取複製函數所屬領域者(cloneProto), 使jest等以vm分領域、
|
|
92
|
+
//全域函數來自外層領域之環境仍可用(複本之原型為外層領域之Object.prototype), 而複本原型為null或他物者視為不可用
|
|
93
|
+
let sClone = null
|
|
94
|
+
let cloneProto = null
|
|
95
|
+
if (typeof structuredClone === 'function') {
|
|
96
|
+
try {
|
|
97
|
+
let f = structuredClone
|
|
98
|
+
let throwsOnProxy = false
|
|
99
|
+
try {
|
|
100
|
+
f(new Proxy({}, {}))
|
|
101
|
+
}
|
|
102
|
+
catch (err) {
|
|
103
|
+
throwsOnProxy = true
|
|
104
|
+
}
|
|
105
|
+
let e = f({})
|
|
106
|
+
let p = getProto(e)
|
|
107
|
+
if (throwsOnProxy && toTag(f(new Map())) === '[object Map]' && toTag(e) === '[object Object]' && ownKeys(e).length === 0 && p !== null && getProto(p) === null && hasOwn(p, 'hasOwnProperty') && getProto(f({ a: 1 })) === p) {
|
|
108
|
+
//品牌樣本(原型改為null): 複製須拋錯或複本不再是一般物件(原型不為p); 否則此實作不能用來證明無品牌物件
|
|
109
|
+
let good = true
|
|
110
|
+
let samples = [() => new Map(), () => new Set(), () => new WeakMap(), () => new WeakSet(), () => Promise.resolve(0), () => new ArrayBuffer(1), () => new DataView(new ArrayBuffer(1)), () => Object(Symbol('s'))]
|
|
111
|
+
if (typeof SharedArrayBuffer === 'function') {
|
|
112
|
+
samples[samples.length] = () => new SharedArrayBuffer(1)
|
|
113
|
+
}
|
|
114
|
+
if (typeof WeakRef === 'function') {
|
|
115
|
+
samples[samples.length] = () => new WeakRef(probeKey)
|
|
116
|
+
}
|
|
117
|
+
if (typeof FinalizationRegistry === 'function') {
|
|
118
|
+
samples[samples.length] = () => new FinalizationRegistry(noop)
|
|
119
|
+
}
|
|
120
|
+
if (typeof BigInt === 'function') {
|
|
121
|
+
samples[samples.length] = () => Object(BigInt(1))
|
|
122
|
+
}
|
|
123
|
+
for (let i = 0; i < samples.length && good; i++) {
|
|
124
|
+
let o = setProto(samples[i](), null)
|
|
125
|
+
try {
|
|
126
|
+
if (getProto(f(o)) === p) {
|
|
127
|
+
good = false
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
catch (err) {
|
|
131
|
+
//拋錯: 符合
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
if (good) {
|
|
135
|
+
sClone = f
|
|
136
|
+
cloneProto = p
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
catch (err) {
|
|
141
|
+
//不可用, 走精確探針
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
|
|
80
145
|
//原因詞彙(單一出處; 案例表src/_cvOrmFindCases.mjs之why為其子字串)
|
|
81
146
|
let R = {
|
|
82
147
|
plain: 'condition must be a plain object',
|
|
@@ -102,6 +167,7 @@ let R = {
|
|
|
102
167
|
deep: 'nesting is too deep',
|
|
103
168
|
big: 'condition is too large',
|
|
104
169
|
exc: 'an exception was thrown while reading the condition',
|
|
170
|
+
emptyOdd: 'an empty find must be an ordinary object',
|
|
105
171
|
}
|
|
106
172
|
|
|
107
173
|
//欄名文法: 字母或底線開頭, 其後字母/組合附加符號/數字/底線
|
|
@@ -227,11 +293,74 @@ let hasSlot = (v) => {
|
|
|
227
293
|
return false
|
|
228
294
|
}
|
|
229
295
|
|
|
230
|
-
//
|
|
231
|
-
|
|
296
|
+
//cloneIsPlain, 對走訪時記錄之條件物件(c.ob: 實際讀過並接受之物件本身, 不是走訪後才可能被呼叫端陷阱改動之find可達樹)做一次結構化複製
|
|
297
|
+
//(規則16): 成功且每個複本之原型皆為複製函數所屬領域之Object.prototype(只看原型身分, 不看標籤: 複本由引擎產生, 標籤可被全域汙染改變),
|
|
298
|
+
//即證明這些物件皆非品牌物件(Map、Set、ArrayBuffer、DataView、BigInt包裝等複製後仍為原品牌, 原型為其內建原型; 其下層條件物件皆各自在記錄內, 故只需逐筆淺檢).
|
|
299
|
+
//不可複製之物件(Proxy、WeakMap、Promise、WeakRef、Symbol包裝、FinalizationRegistry等)使其拋錯而回false, 改走精確探針
|
|
300
|
+
let cloneIsPlain = (ob, n) => {
|
|
301
|
+
if (sClone === null) {
|
|
302
|
+
return false
|
|
303
|
+
}
|
|
304
|
+
try {
|
|
305
|
+
let cl = sClone(ob)
|
|
306
|
+
for (let i = 0; i < n; i++) {
|
|
307
|
+
if (getProto(cl[i]) !== cloneProto) {
|
|
308
|
+
return false
|
|
309
|
+
}
|
|
310
|
+
}
|
|
311
|
+
return true
|
|
312
|
+
}
|
|
313
|
+
catch (err) {
|
|
314
|
+
return false
|
|
315
|
+
}
|
|
316
|
+
}
|
|
317
|
+
|
|
318
|
+
//emptyCloneOk, 頂層空物件(語意為「全部」)是否可證明為真實空物件: 結構化複製成功且複本為一般空物件
|
|
319
|
+
//(複本可為空物件者仍可能是含私有欄位之類別實例或宿主物件改原型為null之結果, 純JS無法辨別, 見已知限制⑤)
|
|
320
|
+
let emptyCloneOk = (v) => {
|
|
321
|
+
if (sClone === null) {
|
|
322
|
+
return false
|
|
323
|
+
}
|
|
324
|
+
try {
|
|
325
|
+
let cl = sClone(v)
|
|
326
|
+
return getProto(cl) === cloneProto && ownKeys(cl).length === 0
|
|
327
|
+
}
|
|
328
|
+
catch (err) {
|
|
329
|
+
return false
|
|
330
|
+
}
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
//track, 記錄通過一般物件判定之非空條件物件、其路徑與是否為欄位運算子物件, 供走訪完畢後之品牌檢查使用;
|
|
334
|
+
//記錄陣列為null原型(直接指派不查找Array.prototype之索引setter, 不受汙染; 比defineProperty快約45倍)
|
|
335
|
+
let track = (c, obj, ops) => {
|
|
336
|
+
let n = c.nt
|
|
337
|
+
c.ob[n] = obj
|
|
338
|
+
c.pa[n] = c.path
|
|
339
|
+
c.op[n] = ops
|
|
340
|
+
c.nt = n + 1
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
//chkSlots, 走訪完畢後檢查所有被記錄之條件物件皆非內建品牌物件: 先以一次結構化複製證明, 證明不成立才依走訪順序逐物件探針, 命中者以其路徑reject
|
|
344
|
+
let chkSlots = (c) => {
|
|
345
|
+
let n = c.nt
|
|
346
|
+
if (n === 0 || (c.chars <= CLONE_MAX_CHARS && cloneIsPlain(c.ob, n))) {
|
|
347
|
+
return
|
|
348
|
+
}
|
|
349
|
+
for (let i = 0; i < n; i++) {
|
|
350
|
+
if (hasSlot(c.ob[i])) {
|
|
351
|
+
c.path = c.pa[i]
|
|
352
|
+
fail(c.op[i] ? `${R.type} [object]` : `${R.plain}, got [object]`)
|
|
353
|
+
}
|
|
354
|
+
}
|
|
355
|
+
}
|
|
356
|
+
|
|
357
|
+
//readProp, 讀物件之自有屬性值(僅讀一次, 以屬性描述子): 拒絕Symbol鍵(無法安全顯示, 報所屬物件之路徑)、不可列舉、存取器;
|
|
358
|
+
//路徑先推進至該屬性鍵, 描述子陷阱拋錯與存取器等失敗皆報至該鍵(由呼叫端於處理完該屬性後退回)
|
|
359
|
+
let readProp = (c, obj, k) => {
|
|
232
360
|
if (typeof k !== 'string') {
|
|
233
361
|
fail(R.sym)
|
|
234
362
|
}
|
|
363
|
+
c.path = { up: c.path, k }
|
|
235
364
|
let d = getDesc(obj, k)
|
|
236
365
|
if (d === undefined || !d.enumerable) {
|
|
237
366
|
fail(R.nonEnumProp)
|
|
@@ -251,18 +380,19 @@ let readLen = (arr) => {
|
|
|
251
380
|
return n
|
|
252
381
|
}
|
|
253
382
|
|
|
254
|
-
//readElem, 讀陣列元素(僅讀一次, 以屬性描述子):
|
|
383
|
+
//readElem, 讀陣列元素(僅讀一次, 以屬性描述子): 路徑先推進至該元素(由呼叫端於處理完該元素後退回),
|
|
384
|
+
//描述子陷阱拋錯、不可列舉與存取器皆報至元素索引; 洞無元素可指, 退回而於陣列路徑報告
|
|
255
385
|
let readElem = (c, arr, i) => {
|
|
386
|
+
c.path = { up: c.path, k: i }
|
|
256
387
|
let d = getDesc(arr, i)
|
|
257
388
|
if (d === undefined) {
|
|
389
|
+
c.path = c.path.up
|
|
258
390
|
fail(`sparse array hole at index ${i}`)
|
|
259
391
|
}
|
|
260
392
|
if (!d.enumerable) {
|
|
261
|
-
c.path = { up: c.path, k: i }
|
|
262
393
|
fail(R.nonEnumEl)
|
|
263
394
|
}
|
|
264
395
|
if (!hasOwn(d, 'value')) {
|
|
265
|
-
c.path = { up: c.path, k: i }
|
|
266
396
|
fail(R.accEl)
|
|
267
397
|
}
|
|
268
398
|
return d.value
|
|
@@ -321,6 +451,7 @@ let scalar = (c, v, allowNull) => {
|
|
|
321
451
|
switch (typeof v) {
|
|
322
452
|
case 'string':
|
|
323
453
|
chkStr(v)
|
|
454
|
+
c.chars += v.length
|
|
324
455
|
return v
|
|
325
456
|
case 'number':
|
|
326
457
|
if (!isFin(v)) {
|
|
@@ -371,7 +502,6 @@ let chkSet = (c, op, arr) => {
|
|
|
371
502
|
let out = []
|
|
372
503
|
for (let i = 0; i < n; i++) {
|
|
373
504
|
let v = readElem(c, arr, i)
|
|
374
|
-
c.path = { up: c.path, k: i }
|
|
375
505
|
put(out, i, scalar(c, v, false))
|
|
376
506
|
c.path = c.path.up
|
|
377
507
|
}
|
|
@@ -390,11 +520,11 @@ let chkOps = (c, obj) => {
|
|
|
390
520
|
if (n === 0) {
|
|
391
521
|
fail(R.emptyOp)
|
|
392
522
|
}
|
|
523
|
+
track(c, obj, true)
|
|
393
524
|
let out = create(null)
|
|
394
525
|
for (let i = 0; i < n; i++) {
|
|
395
526
|
let k = keys[i]
|
|
396
|
-
let v = readProp(obj, k)
|
|
397
|
-
c.path = { up: c.path, k }
|
|
527
|
+
let v = readProp(c, obj, k)
|
|
398
528
|
switch (k) {
|
|
399
529
|
case '$eq':
|
|
400
530
|
case '$ne':
|
|
@@ -456,7 +586,6 @@ let chkList = (c, op, arr, depth) => {
|
|
|
456
586
|
let out = []
|
|
457
587
|
for (let i = 0; i < n; i++) {
|
|
458
588
|
let v = readElem(c, arr, i)
|
|
459
|
-
c.path = { up: c.path, k: i }
|
|
460
589
|
put(out, i, chkDoc(c, v, depth, false))
|
|
461
590
|
c.path = c.path.up
|
|
462
591
|
}
|
|
@@ -477,19 +606,25 @@ let chkDoc = (c, obj, depth, top) => {
|
|
|
477
606
|
let n = keys.length
|
|
478
607
|
if (n === 0) {
|
|
479
608
|
if (top) {
|
|
480
|
-
//頂層空物件代表「全部」,
|
|
481
|
-
|
|
482
|
-
|
|
609
|
+
//頂層空物件代表「全部」, 誤判代價最大: 須可證明為真實空物件(規則16), 排除原型被改為null或Object.prototype之Map、Set等
|
|
610
|
+
//(其標籤被誤判為一般物件)與Proxy、不可複製之宿主物件; 無可用結構化複製之環境只能以探針辨品牌物件
|
|
611
|
+
if (!emptyCloneOk(obj)) {
|
|
612
|
+
if (hasSlot(obj)) {
|
|
613
|
+
fail(`${R.plain}, got [object]`)
|
|
614
|
+
}
|
|
615
|
+
if (sClone !== null) {
|
|
616
|
+
fail(R.emptyOdd)
|
|
617
|
+
}
|
|
483
618
|
}
|
|
484
619
|
return create(null)
|
|
485
620
|
}
|
|
486
621
|
fail(R.emptyDoc)
|
|
487
622
|
}
|
|
623
|
+
track(c, obj, false)
|
|
488
624
|
let out = create(null)
|
|
489
625
|
for (let i = 0; i < n; i++) {
|
|
490
626
|
let k = keys[i]
|
|
491
|
-
let v = readProp(obj, k)
|
|
492
|
-
c.path = { up: c.path, k }
|
|
627
|
+
let v = readProp(c, obj, k)
|
|
493
628
|
if (k === '$and' || k === '$or') {
|
|
494
629
|
put(out, k, chkList(c, k, v, depth + 1))
|
|
495
630
|
}
|
|
@@ -562,7 +697,7 @@ let getLimits = (opt) => {
|
|
|
562
697
|
*
|
|
563
698
|
* 白名單:
|
|
564
699
|
*
|
|
565
|
-
* 1. 頂層與每層條件物件須為一般物件(原型為Object.prototype或null),null、陣列、字串、數值、布林、函數、Date、RegExp、Map、Set、類別實例等一律reject,不得視同{};原型被改為null或Object.prototype之Map、Set、Promise、ArrayBuffer、DataView、TypedArray
|
|
700
|
+
* 1. 頂層與每層條件物件須為一般物件(原型為Object.prototype或null),null、陣列、字串、數值、布林、函數、Date、RegExp、Map、Set、類別實例等一律reject,不得視同{};原型被改為null或Object.prototype之Map、Set、WeakMap、WeakSet、Promise、ArrayBuffer、DataView、TypedArray、Symbol與BigInt包裝、WeakRef、FinalizationRegistry等內建品牌物件,於任何位置(頂層、欄位運算子物件、$and/$or元素,空或帶自有鍵)亦reject;頂層空物件(代表全部)須可證明為真實空物件,Proxy與不可複製之宿主物件不視為全部
|
|
566
701
|
*
|
|
567
702
|
* 2. 欄位等值{欄: 純量},多欄隱含AND;純量為字串、有限數字(含-0)、布林、有效Date,字串不得含NUL與孤立代理字元;null僅可用於欄位等值、$eq、$ne
|
|
568
703
|
*
|
|
@@ -578,9 +713,9 @@ let getLimits = (opt) => {
|
|
|
578
713
|
*
|
|
579
714
|
* 8. 上限(opt只可下調,不可放寬):邏輯巢狀深度32、$and/$or長度1000、$in/$nin長度10000、節點總數100000(條件物件、運算子物件、純量各計1)、欄名128
|
|
580
715
|
*
|
|
581
|
-
* 錯誤一律為同步拋出之Error('invalid find: 原因 at [路徑]'),不回顯值(鍵名為路徑之一部分,限30字元並以?取代控制字元、格式字元與方括號);走訪中任何例外(含呼叫端之getter、Proxy陷阱、Symbol.toStringTag getter)
|
|
716
|
+
* 錯誤一律為同步拋出之Error('invalid find: 原因 at [路徑]'),不回顯值(鍵名為路徑之一部分,限30字元並以?取代控制字元、格式字元與方括號);走訪中任何例外(含呼叫端之getter、Proxy陷阱、Symbol.toStringTag getter)一律轉為此格式,不轉述呼叫端之錯誤訊息,描述子陷阱拋錯、存取器與不可列舉屬性之路徑含該屬性鍵或元素索引;可重入。opt須為物件、null或未給,僅可含下列五個鍵(自有資料屬性),設定錯誤另拋Error('invalid opt: 原因')。
|
|
582
717
|
*
|
|
583
|
-
* 已知限制:判定內部標籤須讀Symbol.toStringTag,可能執行呼叫端之Proxy陷阱或getter(例外一律轉為invalid find)
|
|
718
|
+
* 已知限制:判定內部標籤須讀Symbol.toStringTag,可能執行呼叫端之Proxy陷阱或getter(例外一律轉為invalid find);Proxy無法穿透,非空位置之Proxy包住原型被改之品牌物件視同其經陷阱暴露之條件物件;無法觀察品牌者(含私有欄位之類別實例與AbortController等宿主物件改原型為null、自有鍵為純量constructor之Promise)不被辨出;品牌檢查先以一次結構化複製(structuredClone)證明被記錄之條件物件皆非品牌物件,環境無可用之該全域、字串總長逾400萬碼元或樹內含Proxy時改逐物件探針(每物件約50微秒,含Proxy之近節點上限輸入可達數秒),且無可用之該全域時無法辨出空Proxy;被判為品牌物件而reject者,其內部資料(Map/Set之項目、ArrayBuffer之位元組)可能被複製讀取一次,成本不受節點預算約束;Proxy之ownKeys結果於引擎內先被完整具現化,其成本不受節點預算約束;共享參照(同一物件出現於多處)每出現一次即各讀各檢各複製,節點數亦逐次計入
|
|
584
719
|
*
|
|
585
720
|
* 後端專屬之檢核(欄位型別、欄是否存在、主鍵正規化、DATE範圍、NULL三值語意)不在此,由各後端於本函數之後自行處理;契約案例表見wsemi/src/_cvOrmFindCases.mjs。
|
|
586
721
|
*
|
|
@@ -630,13 +765,16 @@ function cvOrmFind(find, opt) {
|
|
|
630
765
|
let lim = getLimits(opt)
|
|
631
766
|
|
|
632
767
|
//c, 單次呼叫之狀態(無模組層可變狀態)
|
|
633
|
-
|
|
768
|
+
//ob/pa/op/nt為走訪中記錄之條件物件、其路徑、是否運算子物件與筆數, 供走訪完畢後之品牌檢查使用
|
|
769
|
+
let c = { nodes: 0, path: null, maxDepth: lim.maxDepth, maxList: lim.maxList, maxIn: lim.maxIn, maxNodes: lim.maxNodes, maxKey: lim.maxKey, chars: 0, ob: setProto([], null), pa: setProto([], null), op: setProto([], null), nt: 0 }
|
|
634
770
|
|
|
635
771
|
try {
|
|
636
772
|
if (find === undefined) {
|
|
637
773
|
return create(null)
|
|
638
774
|
}
|
|
639
|
-
|
|
775
|
+
let out = chkDoc(c, find, 0, true)
|
|
776
|
+
chkSlots(c)
|
|
777
|
+
return out
|
|
640
778
|
}
|
|
641
779
|
catch (err) {
|
|
642
780
|
//本模組之失敗取其原因詞彙, 其餘例外(呼叫端之getter、Proxy陷阱等)一律為固定原因, 不轉述其訊息
|