├── ace-builds ├── index.html └── src-min-noconflict │ ├── index.html │ ├── theme-xcode.js │ ├── mode-json.js │ └── worker-json.js ├── sweetalert2 └── index.html ├── INSTALL.md ├── CHANGELOG.md ├── api └── cve │ ├── CVE-9999-0000 │ └── CVE-9999-9999 ├── README.md ├── RISKS.md ├── LICENSE ├── encrypt-storage.js ├── cveClientlib.js ├── autoCompleter.js ├── cveInterface.css ├── language-codes.json ├── cwe-common.json ├── certicon.ico ├── schemaToForm.js ├── index.html └── cveIterface.js /ace-builds/index.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /sweetalert2/index.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /ace-builds/src-min-noconflict/index.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /INSTALL.md: -------------------------------------------------------------------------------- 1 | ### Installing cveClient on your webserver (apache2, IIS, nginx, tinyhttp) 2 | 3 | All the files in this repository are client utilities expected to served from a webserver to run inside a web browser. Directly accessing the index.html file inside a browser will NOT work as most browsers will not allow network activity from static files on your local or network attached drive/storage. 4 | 5 | Clone this repository to a web accessible folder in your webserver says into a folder called `cveClient` using git command `git clone https://github.com/CERTCC/cveClient`. Once you have cloned this folder, you can visit your webserver's relative URL at `/cveClient/` to the folder where the repository was cloned. Ensure your webserver's default index file is `index.html` 6 | 7 | If you use Content-Security-Policy (CSP) headers on your webserver or on your web reverse proxy, make sure the appropriate domain URLs are allowed for the folder that was cloned (`cveClient`). Below is the sample Content-Security-Policy header recommended for this folder: 8 | 9 | `default-src 'self' blob: http://127.0.0.1:* http://localhost:*; connect-src 'self' http://127.0.0.1:* http://localhost:* *.mitre.org; script-src 'self' https://stackpath.bootstrapcdn.com https://code.jquery.com https://cdnjs.cloudflare.com https://unpkg.com https://apis.google.com blob:; style-src 'self' https://stackpath.bootstrapcdn.com 'unsafe-inline' https://unpkg.com; img-src 'self' data: blob:;object-src 'self'` 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | # cveClient Changelog 2 | 3 | Version 1.0.22 2025-06-26 4 | * Resolved a bug as filled in #31 multiple versions under affected tree 5 | * Moved from jquery .data() to .attr(data- to avoid unexpected behaviors. 6 | * ProblemTypes can be array of array with only one dictionary object - fixed issue where m*n array can be consisten in JSON view and Friendly (Minimal) view. 7 | 8 | Version 1.0.21 2025-06-24 9 | * Added a new version of CVE Chatbot 10 | * Ask chatGPT button 11 | * Fixed bugs on multi-row elements 12 | 13 | 14 | Version 1.0.20 2023-08-21 15 | 16 | * Add schemaToJson.js generic library to support conversion of CVE schema 17 | * Added updates to support viewing of full schema as presented by CVE5.0 schema 18 | 19 | 20 | Version 1.0.19 2023-08-21 21 | 22 | * Fixed some bugs on cveInterface.js related to apply_diff 23 | * Added the ability to download CVE JSON from repositories for edit/duplicate 24 | * Moved display capabilities using CSS. 25 | 26 | 27 | Version 1.0.18 2023-08-09 28 | 29 | * Fixed some bugs on cveInterface.js related to from_json and to_json routines 30 | * The cveclientLib on 1.0.14 now support ADP capability 31 | * The User Management interface bug fixes on duplicate ID or duplicate name field fixed. 32 | * ADP client interface is available only via JSON editor at this time. 33 | * Require at least One product to have STatus "affected" or "unknown". 34 | 35 | Version 1.0.17 2023-08-09 36 | * Allow entry of CVE data without being logged in just to create mock records 37 | * Implemented offload download button for CVE records 38 | * Fixed XSS issue due to changes to CVE Services RSUS interface 39 | * Pagination issues resolved 40 | -------------------------------------------------------------------------------- /ace-builds/src-min-noconflict/theme-xcode.js: -------------------------------------------------------------------------------- 1 | ace.define("ace/theme/xcode",["require","exports","module","ace/lib/dom"],function(e,t,n){t.isDark=!1,t.cssClass="ace-xcode",t.cssText=".ace-xcode .ace_gutter {background: #e8e8e8;color: #333}.ace-xcode .ace_print-margin {width: 1px;background: #e8e8e8}.ace-xcode {background-color: #FFFFFF;color: #000000}.ace-xcode .ace_cursor {color: #000000}.ace-xcode .ace_marker-layer .ace_selection {background: #B5D5FF}.ace-xcode.ace_multiselect .ace_selection.ace_start {box-shadow: 0 0 3px 0px #FFFFFF;}.ace-xcode .ace_marker-layer .ace_step {background: rgb(198, 219, 174)}.ace-xcode .ace_marker-layer .ace_bracket {margin: -1px 0 0 -1px;border: 1px solid #BFBFBF}.ace-xcode .ace_marker-layer .ace_active-line {background: rgba(0, 0, 0, 0.071)}.ace-xcode .ace_gutter-active-line {background-color: rgba(0, 0, 0, 0.071)}.ace-xcode .ace_marker-layer .ace_selected-word {border: 1px solid #B5D5FF}.ace-xcode .ace_constant.ace_language,.ace-xcode .ace_keyword,.ace-xcode .ace_meta,.ace-xcode .ace_variable.ace_language {color: #C800A4}.ace-xcode .ace_invisible {color: #BFBFBF}.ace-xcode .ace_constant.ace_character,.ace-xcode .ace_constant.ace_other {color: #275A5E}.ace-xcode .ace_constant.ace_numeric {color: #3A00DC}.ace-xcode .ace_entity.ace_other.ace_attribute-name,.ace-xcode .ace_support.ace_constant,.ace-xcode .ace_support.ace_function {color: #450084}.ace-xcode .ace_fold {background-color: #C800A4;border-color: #000000}.ace-xcode .ace_entity.ace_name.ace_tag,.ace-xcode .ace_support.ace_class,.ace-xcode .ace_support.ace_type {color: #790EAD}.ace-xcode .ace_storage {color: #C900A4}.ace-xcode .ace_string {color: #DF0002}.ace-xcode .ace_comment {color: #008E00}.ace-xcode .ace_indent-guide {background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbYnAAAAE0lEQVQImWP4////f4bLly//BwAmVgd1/w11/gAAAABJRU5ErkJggg==) right repeat-y}";var r=e("../lib/dom");r.importCssString(t.cssText,t.cssClass)}); (function() { 2 | ace.require(["ace/theme/xcode"], function(m) { 3 | if (typeof module == "object" && typeof exports == "object" && module) { 4 | module.exports = m; 5 | } 6 | }); 7 | })(); 8 | -------------------------------------------------------------------------------- /api/cve/CVE-9999-0000: -------------------------------------------------------------------------------- 1 | { 2 | "containers": { 3 | "cna": { 4 | "title": "Test CVE Record 0000", 5 | "descriptions": [ 6 | { 7 | "lang": "en", 8 | "value": "The CVE-9999-0000 is a Test CVE Record for cveClient Program" 9 | } 10 | ], 11 | "source": { 12 | "discovery": "external" 13 | }, 14 | "credits": [ 15 | { 16 | "lang": "en", 17 | "type": "finder", 18 | "value": "John Smith" 19 | } 20 | ], 21 | "affected": [ 22 | { 23 | "vendor": "ACME Productions", 24 | "product": "Dun Lori", 25 | "versions": [ 26 | { 27 | "status": "affected", 28 | "version": "1.9.1" 29 | } 30 | ] 31 | }, 32 | { 33 | "vendor": "ACME Productions", 34 | "product": "Virginia Square", 35 | "versions": [ 36 | { 37 | "status": "affected", 38 | "version": "1.12.1" 39 | } 40 | ] 41 | }, 42 | { 43 | "vendor": "ACME Productions", 44 | "product": "Metro Central", 45 | "versions": [ 46 | { 47 | "status": "unaffected", 48 | "version": "2.1.1" 49 | } 50 | ] 51 | } 52 | ], 53 | "problemTypes": [ 54 | { 55 | "descriptions": [ 56 | { 57 | "lang": "en", 58 | "description": "CWE-125 Out-of-bounds Read" 59 | } 60 | ] 61 | } 62 | ], 63 | "references": [ 64 | { 65 | "name": "CERT/CC Advisory", 66 | "url": "https://kb.cert.org/vuls/" 67 | } 68 | ], 69 | "x_generator": { 70 | "engine": "cveClient 1.0.19" 71 | } 72 | } 73 | } 74 | } 75 | 76 | -------------------------------------------------------------------------------- /api/cve/CVE-9999-9999: -------------------------------------------------------------------------------- 1 | { 2 | "containers": { 3 | "cna": { 4 | "title": "Test CVE Record 9999", 5 | "descriptions": [ 6 | { 7 | "lang": "en", 8 | "value": "The CVE-9999-9999 is a Test CVE Record for cveClient Program" 9 | } 10 | ], 11 | "source": { 12 | "discovery": "external" 13 | }, 14 | "credits": [ 15 | { 16 | "lang": "en", 17 | "type": "finder", 18 | "value": "John Smith" 19 | } 20 | ], 21 | "affected": [ 22 | { 23 | "vendor": "ACME Productions", 24 | "product": "Dun Lori", 25 | "versions": [ 26 | { 27 | "status": "affected", 28 | "version": "1.9.1" 29 | } 30 | ] 31 | }, 32 | { 33 | "vendor": "ACME Productions", 34 | "product": "Virginia Square", 35 | "versions": [ 36 | { 37 | "status": "affected", 38 | "version": "1.12.1" 39 | } 40 | ] 41 | }, 42 | { 43 | "vendor": "ACME Productions", 44 | "product": "Metro Central", 45 | "versions": [ 46 | { 47 | "status": "unaffected", 48 | "version": "2.1.1" 49 | } 50 | ] 51 | } 52 | ], 53 | "problemTypes": [ 54 | { 55 | "descriptions": [ 56 | { 57 | "lang": "en", 58 | "description": "CWE-125 Out-of-bounds Read" 59 | } 60 | ] 61 | } 62 | ], 63 | "references": [ 64 | { 65 | "name": "CERT/CC Advisory", 66 | "url": "https://kb.cert.org/vuls/" 67 | } 68 | ], 69 | "x_generator": { 70 | "engine": "cveClient 1.0.19" 71 | } 72 | } 73 | } 74 | } 75 | 76 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # cveClient 2 | A web-based client interface and a client library to cve-services 2.x to provide CVE JSON (5.x) vulnerability management for CVE Numbering Authorities (CNAs) and Roots. 3 | 4 | 5 | # Introduction 6 | A JavaScript library and simple HTML interface for CVE services that is like RedHat's [cvelib](https://github.com/RedHatProductSecurity/cvelib) and [Vulnogram](https://github.com/Vulnogram/Vulnogram). Provides capabilities to interface with [cve-services](https://github.com/CVEProject/cve-services) with a JavaScript client and simple HTML UI. You can just serve the index.html file from any static content area of your webserver (Apache2, NGINX, thttpd, lighttpd, Caddy). 7 | 8 | A JavaScript encryption toolkit is also served from [encrypt-storage.js](./encrypt-storage.js) file. This is a simple asymmetric encryption to protect your API Key while in `localStorage` (if *Keep me logged in* checkbox is enabled) or `sessionStorage` with PKI stored in native `indexedDB`. This provides some limited protection of your API keys. Currently cve-services expects API key for every transaction, there is no middleware providing session capability or related CSRF protection. 9 | 10 | Demo of the UI and client library can be accessed at [https://certcc.github.io/cveClient/](https://certcc.github.io/cveClient/) or CERT's [demo site](https://democert.org/cveClient). Currently the allowed servers (cve-services servers) are limited with Content Security Policy headers to cve-services 2.x production site, testing site and a localhost instance. 11 | 12 | Dependency libraries for HTML UI only. 13 | * [jQuery - 3.5.1](https://jquery.com/) 14 | * [Bootstrap - 4.3.1](https://getbootstrap.com/) 15 | * [Popper - 1.14.7](https://popper.js.org/) 16 | * [SweetAlert2 - 2.11](https://sweetalert2.github.io/) 17 | * [Bootstrap-Table - 1.19.1](https://bootstrap-table.com/) 18 | * [Ace Editor - 1.2.4](https://ace.c9.io/) 19 | 20 | Except for Ace Editor and SweetAlert2 library all the dependencies are served from CDN sources with sha-284 [Subsource Integrity](https://developer.mozilla.org/en-US/docs/Web/Security/Subresource_Integrity) checks. There is some issue with the nightly builds, so these two libraries are served from local. Please ensure you understand their license agreements as well. 21 | 22 | # Roll out your own using cveClientlib 23 | If you plan to rollour your own UI, this JavaScript library is helpful. Also note that there is another client library with similar capabilities built with ECMAScrip6 requirement at [https://github.com/xdrr/cve.js](https://github.com/xdrr/cve.js). 24 | 25 | You can use the [cveClientlib.js](./cveClientlib.js) to do all the tasks being performed by the current UI. The file is called cveClientlib.js as Safari browsers have trouble with filename and a Class name being the same. 26 | 27 | # Risks of using API keys in browser for CVE-Services 28 | 29 | See the [RISKS.md](./RISKS.md) that captures some of the inherent risks of using API keys to access an API service. If you decide to use these web base clients to access `cve-services`, please be aware of these risks. 30 | 31 | 32 | # Installation on your own webserver 33 | 34 | See the [INSTALL.md](./INSTALL.md), if you would like to run a private version of the cveClient in your own webserver. -------------------------------------------------------------------------------- /RISKS.md: -------------------------------------------------------------------------------- 1 | # Risk of using API keys in browser for CVE-Services 2 | 3 | 4 | The [cve-services](https://github.com/CVEProject/cve-services)' API interface is protected by an API key to perform CNA functions to manage CVE records. An API-key assigned to a user with Admin role (administrator) is also able manage users under their organization. 5 | 6 | Any browser-based client to cve-services requires unencrypted access to the API key to perform each transaction with the cve-services endpoints. The browser-based clients such as Vulnogram and cveClient depend on the browser to protect these API keys. API key, unlike passwords, are rarely changed and could be stolen from the browser where the API key was entered. This is a known risk in using browser-based clients when accessing CVE program capabilities as a CNA. Although there are several technologies such as [ServiceWorkers](https://developer.mozilla.org/en-US/docs/Web/API/Service_Worker_API/Using_Service_Workers) and [Storage APIs](https://cheatsheetseries.owasp.org/cheatsheets/HTML5_Security_Cheat_Sheet.html#storage-apis), the browser needs to repeatedly retrieve and use the API keys making this data available in its raw form to support CAN activities. 7 | 8 | If a CNA decides to use these clients, they should be aware of the risks that the API key could be stolen from the browser. The CNA should take necessary precautions as appropriate for their organization to protect the API keys. 9 | 10 | If a CNA chooses to use this or other web based interfaces to access the cve-services, here are some precautionary measures the CNA may adapt to reduce risk of abuse of their cve-services credentials. 11 | * Secure the browser. 12 | Ensure the organization’s computer and browser software are well-managed and kept up to date with security updates. Limit the browser plugins to ensure secure and audited plugins are installed on the browser. Use automatic updates and timely restart of the browser to reduce long-running unpatched software. 13 | * Audit and manage users. 14 | Organization audits and verifies the users who belong to their organization and timely disables the users who have left the organization or have no longer need the role to manage CVE records for the organization. 15 | * Regenerate your API keys periodically. 16 | The cve-program allows for regeneration of the API keys for users in an organization. This is recommended to match the organization password and API credentials lifecycle management policy. This can also allow for timely auditing and detection of rogue users and stray accounts that are part of your organization 17 | * Protect web server, if you run your own. 18 | The software Vulnogram can be accessed at [https://vulnogram.github.io](https://vulnogram.github.io) for a client only solution from GitHub site. Similarly cveClient is also accessible from [https://certcc.github.io/cveClient/](https://certcc.github.io/cveClient/). These are static websites hosted at GitHub and do not collect any information from your browser but only serve static web content. However, if you wish to run a cloned or forked version of Vulnogram or cveClient software from GitHub, ensure your publishing web server is protected from Cross-Site Scripting (XSS) attacks using something like [Content-Security-Policy headers](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy). 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The following license applies to software contained in this repository. 2 | 3 | ---- 4 | MIT License 5 | 6 | Copyright (c) 2020 Carnegie Mellon University 7 | 8 | Permission is hereby granted, free of charge, to any person obtaining a copy 9 | of this software and associated documentation files (the "Software"), to deal 10 | in the Software without restriction, including without limitation the rights 11 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 12 | copies of the Software, and to permit persons to whom the Software is 13 | furnished to do so, subject to the following conditions: 14 | 15 | The above copyright notice and this permission notice shall be included in all 16 | copies or substantial portions of the Software. 17 | 18 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 19 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 20 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 21 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 22 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 23 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 24 | SOFTWARE. 25 | 26 | ---- 27 | The following statement applies to documents contained in this repository, and can also be found in each 28 | individual document. 29 | 30 | This material is based upon work funded and supported by the Department of Defense 31 | under Contract No. FA8702-15-D-0002 with Carnegie Mellon University for the operation 32 | of the Software Engineering Institute, a federally funded research and development center. 33 | 34 | The view, opinions, and/or findings contained in this material are those of the author(s) 35 | and should not be construed as an official Government position, policy, or decision, unless 36 | designated by other documentation. 37 | 38 | References herein to any specific commercial product, process, or service by trade name, 39 | trade mark, manufacturer, or otherwise, does not necessarily constitute or imply its 40 | endorsement, recommendation, or favoring by Carnegie Mellon University or its 41 | Software Engineering Institute. 42 | 43 | NO WARRANTY. THIS CARNEGIE MELLON UNIVERSITY AND SOFTWARE ENGINEERING INSTITUTE MATERIAL 44 | IS FURNISHED ON AN "AS-IS" BASIS. CARNEGIE MELLON UNIVERSITY MAKES NO WARRANTIES OF ANY KIND, 45 | EITHER EXPRESSED OR IMPLIED, AS TO ANY MATTER INCLUDING, BUT NOT LIMITED TO, WARRANTY OF 46 | FITNESS FOR PURPOSE OR MERCHANTABILITY, EXCLUSIVITY, OR RESULTS OBTAINED FROM USE OF THE 47 | MATERIAL. CARNEGIE MELLON UNIVERSITY DOES NOT MAKE ANY WARRANTY OF ANY KIND WITH RESPECT 48 | TO FREEDOM FROM PATENT, TRADEMARK, OR COPYRIGHT INFRINGEMENT. 49 | 50 | [DISTRIBUTION STATEMENT A] This material has been approved for public release and unlimited distribution. 51 | Please see Copyright notice for non-US Government use and distribution. 52 | 53 | Internal use: 54 | * Permission to reproduce this material and to prepare derivative works from this material for internal 55 | use is granted, provided the copyright and “No Warranty” statements are included with all reproductions 56 | and derivative works. 57 | 58 | External use: 59 | * This material may be reproduced in its entirety, without modification, and freely distributed in 60 | written or electronic form without requesting formal permission. Permission is required for any 61 | other external and/or commercial use. Requests for permission should be directed to the 62 | Software Engineering Institute at permission@sei.cmu.edu. 63 | 64 | * These restrictions do not apply to U.S. government entities. 65 | 66 | Carnegie Mellon®, CERT Coordination Center® and OCTAVE® are registered in the U.S. Patent and 67 | Trademark Office by Carnegie Mellon University. 68 | DM18-1203, DM19-1222 69 | -------------------------------------------------------------------------------- /encrypt-storage.js: -------------------------------------------------------------------------------- 1 | /* Encryption API using JavaScript native crypto.js and indexeDB for storing private keys */ 2 | const encrypt_storage_version = "1.1.14"; 3 | async function encryptMessage(message,publicKey) { 4 | let encoded = new TextEncoder().encode(message); 5 | let ciphertext = await window.crypto.subtle.encrypt( 6 | { 7 | name: "RSA-OAEP" 8 | }, 9 | publicKey, 10 | encoded 11 | ); 12 | return ciphertext; 13 | } 14 | async function decryptMessage(ciphertext,privateKey) { 15 | let decrypted = await window.crypto.subtle.decrypt( 16 | { 17 | name: "RSA-OAEP" 18 | }, 19 | privateKey, 20 | ciphertext 21 | ); 22 | 23 | let dec = new TextDecoder(); 24 | return dec.decode(decrypted); 25 | } 26 | async function arrayBuffertoURI(arrayBuffer) { 27 | let blob = new Blob([arrayBuffer]); 28 | return new Promise((resolve) => { 29 | let reader = new FileReader() 30 | reader.onloadend = function() { 31 | resolve(reader.result); 32 | }; 33 | reader.readAsDataURL(blob); 34 | }); 35 | } 36 | function URItoarrayBuffer(URI) { 37 | var byteString = atob(URI.split(',')[1]); 38 | var arrayBuffer = new ArrayBuffer(byteString.length); 39 | var _ia = new Uint8Array(arrayBuffer); 40 | for (var i = 0; i < byteString.length; i++) { 41 | _ia[i] = byteString.charCodeAt(i); 42 | } 43 | return arrayBuffer; 44 | } 45 | 46 | 47 | async function sha256sum(msg) { 48 | let enc = new TextEncoder().encode(msg); 49 | const buff = await crypto.subtle.digest('SHA-256', enc); 50 | const barray = Array.from(new Uint8Array(buff)); 51 | let hex = barray.map(function(b) { 52 | return b.toString(16).padStart(2, '0'); 53 | }).join(''); 54 | return hex; 55 | }; 56 | function dbManager(user,key,sum) { 57 | return new Promise(function(resolve, reject) { 58 | var indexedDB = window.indexedDB || window.mozIndexedDB 59 | || window.webkitIndexedDB || window.msIndexedDB 60 | || window.shimIndexedDB; 61 | var open = indexedDB.open("cve-services.apikeyStore", 1); 62 | open.onupgradeneeded = function() { 63 | var db = open.result; 64 | if (!db.objectStoreNames.contains("keyStore")) { 65 | var store = db.createObjectStore("keyStore", 66 | {keyPath: "user"}); 67 | var index = store.createIndex("sigIndex", ["sum.sha256"]); 68 | } 69 | }; 70 | open.onsuccess = function() { 71 | var db = open.result; 72 | var tx = db.transaction("keyStore", "readwrite"); 73 | var store = tx.objectStore("keyStore"); 74 | if(key) { 75 | store.put({user: user, key: key, sum: sum}); 76 | } else { 77 | if(user) { 78 | var getUser = store.get(user); 79 | getUser.onsuccess = function(q) { 80 | resolve(q); 81 | }; 82 | } else if(sum.sha256) { 83 | var index = store.index("sigIndex"); 84 | var getSum = index.get([sum.sha256]); 85 | getSum.onsuccess = function(q) { 86 | resolve(q); 87 | }; 88 | } else { 89 | reject("A user or a checksum is required"); 90 | } 91 | }; 92 | tx.oncomplete = function() { 93 | db.close(); 94 | }; 95 | } 96 | }); 97 | } 98 | async function save_key(user,key) { 99 | let fpb = await window.crypto.subtle.exportKey("jwk", key.publicKey); 100 | let fpr = await window.crypto.subtle.exportKey("jwk", key.privateKey); 101 | let exportKey = {epr: fpr, epb: fpb}; 102 | let sum = {sha256: await sha256sum(fpb.n)}; 103 | dbManager(user,exportKey,sum); 104 | return exportKey; 105 | } 106 | async function import_key({epr,epb}) { 107 | let prkey = await window.crypto.subtle.importKey("jwk",epr,{name:"RSA-OAEP", hash: {name: "SHA-256"}},false,['decrypt']); 108 | let pbkey = await window.crypto.subtle.importKey("jwk",epb,{name:"RSA-OAEP", hash: {name: "SHA-256"}},false,['encrypt']); 109 | return { privateKey: prkey, publicKey: pbkey }; 110 | } 111 | 112 | async function check_create_key(user) { 113 | let dbKey = await dbManager(user); 114 | if(('target' in dbKey) && (dbKey.target.result) && 115 | (dbKey.target.result.user == user)) { 116 | return import_key(dbKey.target.result.key); 117 | } 118 | return window.crypto.subtle.generateKey( 119 | { 120 | name: "RSA-OAEP", 121 | modulusLength: 4096, 122 | publicExponent: new Uint8Array([1, 0, 1]), 123 | hash: "SHA-256", 124 | }, 125 | true, 126 | ["encrypt", "decrypt"] 127 | ).then(function(key) { 128 | save_key(user,key); 129 | return key; 130 | }); 131 | } 132 | -------------------------------------------------------------------------------- /cveClientlib.js: -------------------------------------------------------------------------------- 1 | class cveClient { 2 | constructor(org,user,key,url) { 3 | this.org = org; 4 | this.user = user; 5 | this.key = key; 6 | this.url = url; 7 | this.user_path = "/org/" + this.org + "/user/" + this.user; 8 | this._version = "1.0.15"; 9 | } 10 | publishadp(cve,adp) { 11 | let path = "/cve/" + cve + "/adp"; 12 | let opts = {method: "PUT"}; 13 | return this.putjson(path,opts,null,adp); 14 | } 15 | publishcve(cve,cnajson,update,rejected) { 16 | /* Create or Update a CVE */ 17 | let opts = null; 18 | if(update) 19 | opts = {method: "PUT"}; 20 | let path = "/cve/" + cve + "/cna"; 21 | if(rejected) 22 | path = "/cve/" + cve + "/reject"; 23 | return this.putjson(path,opts,null,{cnaContainer:cnajson}); 24 | } 25 | reservecve(amount,cve_year,batch_type) { 26 | let path = "/cve-id/"; 27 | let opts = {method: 'POST'}; 28 | let valid_batch_types = {"nonsequential":1,"sequential":1}; 29 | let qvars = {amount: amount ? amount: 1, 30 | short_name:this.org, 31 | cve_year: cve_year ? cve_year : new Date().getFullYear()}; 32 | if(amount > 1) { 33 | if(batch_type && batch_type in valid_batch_types) { 34 | qvars['batch_type'] = batch_type; 35 | } else { 36 | qvars['batch_type'] = "sequential"; 37 | } 38 | }; 39 | return this.putjson(path,opts,qvars); 40 | } 41 | getcvedetail(cve) { 42 | return this.getjson("/cve/" + cve); 43 | } 44 | getcve(cve) { 45 | return this.getjson("/cve-id/" + cve); 46 | } 47 | getcvefilter(year,state,reserved_before,reserved_after, 48 | modified_before,modified_after) { 49 | let qvars = {}; 50 | let path = "/cve-id/"; 51 | let arg_map = ["cve_id_year","state","time_reserved.lt", 52 | "time_reserved.gt","time_modified.lt", 53 | "time_modified.gt"]; 54 | let largs = arguments; 55 | arg_map.forEach(function(f,i) { 56 | if(largs[i]) 57 | qvars[f] = largs[i]; 58 | }); 59 | return this.getjson(path,null,qvars); 60 | } 61 | getquota() { 62 | return this.getjson("/org/" + this.org + "/id_quota"); 63 | } 64 | 65 | getcveids(cve,opts,qvars) { 66 | let path = "/cve-id/"; 67 | if(cve) 68 | path = path + cve; 69 | return this.getjson(path,opts,qvars); 70 | } 71 | getuser(username) { 72 | let path = this.user_path; 73 | if(username) 74 | path = "/org/"+ this.org + "/user/" + username; 75 | return this.rfetch(path); 76 | } 77 | resetuser(username) { 78 | let path = this.user_path+"/reset_secret"; 79 | if(username) 80 | path = "/org/" + this.org + "/user/" + username + "/reset_secret"; 81 | return this.putjson(path,{method:'PUT'}); 82 | } 83 | createuser(userdata) { 84 | let path = "/org/" + this.org + "/user"; 85 | return this.putjson(path,null,null,userdata); 86 | } 87 | updateuser(username,userdata) { 88 | if(!username) 89 | username = this.user; 90 | let path = "/org/" + this.org + "/user/" + username; 91 | return this.putjson(path,{method:'PUT'},userdata,null); 92 | } 93 | listusers(path,opts,qvars) { 94 | /* Overwrite the path variable */ 95 | path = "/org/" + this.org + "/users"; 96 | return this.getjson(path,opts,qvars); 97 | } 98 | getorg(worg) { 99 | if(!worg) 100 | worg = this.org; 101 | let path = "/org/" + worg; 102 | return this.getjson(path); 103 | } 104 | gethealth() { 105 | return this.rfetch("/health-check"); 106 | } 107 | getjson(path,opts,qvars) { 108 | return this.rfetch(path,opts,qvars).then(function(j) { 109 | if(j && j.ok) 110 | return j.json(); 111 | }); 112 | } 113 | putjson(path,opts,qvars,pvars) { 114 | if(!opts) 115 | opts = {method: 'POST'}; 116 | if(!('headers' in opts)) 117 | opts.headers = {}; 118 | opts.headers["Content-Type"] = 'application/json'; 119 | if(pvars) 120 | opts.body = JSON.stringify(pvars); 121 | return this.rfetch(path,opts,qvars).then(function(j) { 122 | return j.json(); 123 | }); 124 | } 125 | rfetch(path,opts,qvars) { 126 | let url; 127 | try { 128 | url = new URL(this.url); 129 | delete this.error; 130 | } catch(err) { 131 | this.error = err; 132 | return; 133 | } 134 | url.pathname = url.pathname + path; 135 | if(!opts) { 136 | opts = {method:'GET'}; 137 | } 138 | if(qvars) { 139 | var qstr = new URLSearchParams(); 140 | Object.keys(qvars).forEach(function(x) { 141 | /* Remove empty values in query_string 142 | strange issue #11 when changing user's information 143 | see https://github.com/CERTCC/cveClient/issues/11 144 | */ 145 | if(qvars[x] != "") 146 | qstr.append(x,qvars[x]); 147 | }); 148 | url.search = qstr.toString(); 149 | } 150 | if(!('headers' in opts)) 151 | opts.headers = {}; 152 | opts.headers = Object.assign({},opts.headers, 153 | {'CVE-API-KEY': this.key, 154 | 'CVE-API-ORG': this.org, 155 | 'CVE-API-USER': this.user }); 156 | let client = this; 157 | return fetch(url.toString(),opts).then(function(r) { 158 | client.response = r; 159 | if(r.ok) { 160 | delete client.error; 161 | return r; 162 | } 163 | client.error = "Error see client.response for full error"; 164 | }).catch(function(err) { 165 | delete client.response; 166 | client.error = err; 167 | }); 168 | } 169 | } 170 | -------------------------------------------------------------------------------- /ace-builds/src-min-noconflict/mode-json.js: -------------------------------------------------------------------------------- 1 | ace.define("ace/mode/json_highlight_rules",["require","exports","module","ace/lib/oop","ace/mode/text_highlight_rules"],function(e,t,n){"use strict";var r=e("../lib/oop"),i=e("./text_highlight_rules").TextHighlightRules,s=function(){this.$rules={start:[{token:"variable",regex:'["](?:(?:\\\\.)|(?:[^"\\\\]))*?["]\\s*(?=:)'},{token:"string",regex:'"',next:"string"},{token:"constant.numeric",regex:"0[xX][0-9a-fA-F]+\\b"},{token:"constant.numeric",regex:"[+-]?\\d+(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b"},{token:"constant.language.boolean",regex:"(?:true|false)\\b"},{token:"text",regex:"['](?:(?:\\\\.)|(?:[^'\\\\]))*?[']"},{token:"comment",regex:"\\/\\/.*$"},{token:"comment.start",regex:"\\/\\*",next:"comment"},{token:"paren.lparen",regex:"[[({]"},{token:"paren.rparen",regex:"[\\])}]"},{token:"text",regex:"\\s+"}],string:[{token:"constant.language.escape",regex:/\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|["\\\/bfnrt])/},{token:"string",regex:'"|$',next:"start"},{defaultToken:"string"}],comment:[{token:"comment.end",regex:"\\*\\/",next:"start"},{defaultToken:"comment"}]}};r.inherits(s,i),t.JsonHighlightRules=s}),ace.define("ace/mode/matching_brace_outdent",["require","exports","module","ace/range"],function(e,t,n){"use strict";var r=e("../range").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\s+$/.test(e)?/^\s*\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\s*\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),ace.define("ace/mode/folding/cstyle",["require","exports","module","ace/lib/oop","ace/range","ace/mode/folding/fold_mode"],function(e,t,n){"use strict";var r=e("../../lib/oop"),i=e("../../range").Range,s=e("./fold_mode").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\|[^|]*?$/,"|"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\|[^|]*?$/,"|"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/([\{\[\(])[^\}\]\)]*$|^\s*(\/\*)/,this.foldingStopMarker=/^[^\[\{\(]*([\}\]\)])|^[\s\*]*(\*\/)/,this.singleLineBlockCommentRe=/^\s*(\/\*).*\*\/\s*$/,this.tripleStarBlockCommentRe=/^\s*(\/\*\*\*).*\*\/\s*$/,this.startRegionRe=/^\s*(\/\*|\/\/)#?region\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return"";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?"start":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!="all"&&(u=null)),u}if(t==="markbegin")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++tf)break;var l=this.getFoldWidgetRange(e,"all",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\s*$/),s=e.getLength(),o=n,u=/^\s*(?:\/\*|\/\/|--)#?(end)?region\b/,a=1;while(++no)return new i(o,r,l,t.length)}}.call(o.prototype)}),ace.define("ace/mode/json",["require","exports","module","ace/lib/oop","ace/mode/text","ace/mode/json_highlight_rules","ace/mode/matching_brace_outdent","ace/mode/behaviour/cstyle","ace/mode/folding/cstyle","ace/worker/worker_client"],function(e,t,n){"use strict";var r=e("../lib/oop"),i=e("./text").Mode,s=e("./json_highlight_rules").JsonHighlightRules,o=e("./matching_brace_outdent").MatchingBraceOutdent,u=e("./behaviour/cstyle").CstyleBehaviour,a=e("./folding/cstyle").FoldMode,f=e("../worker/worker_client").WorkerClient,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new u,this.foldingRules=new a};r.inherits(l,i),function(){this.lineCommentStart="//",this.blockComment={start:"/*",end:"*/"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t);if(e=="start"){var i=t.match(/^.*[\{\(\[]\s*$/);i&&(r+=n)}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new f(["ace"],"ace/mode/json_worker","JsonWorker");return t.attachToDocument(e.getDocument()),t.on("annotate",function(t){e.setAnnotations(t.data)}),t.on("terminate",function(){e.clearAnnotations()}),t},this.$id="ace/mode/json"}.call(l.prototype),t.Mode=l}); (function() { 2 | ace.require(["ace/mode/json"], function(m) { 3 | if (typeof module == "object" && typeof exports == "object" && module) { 4 | module.exports = m; 5 | } 6 | }); 7 | })(); 8 | -------------------------------------------------------------------------------- /autoCompleter.js: -------------------------------------------------------------------------------- 1 | function autoCompleter(inputElement, suggestionsArray, suggestionUrl, selector, search) { 2 | /* 3 | let autoComplete = autocompleter(document.getElementById("searchInput"),null,"https://democert.org/cveClient/cwe-common.json","cwe-common","templet"); 4 | autoComplete.hoverColor = "#333"; 5 | autoComplete.bgColor = "#000"; // for dark mode 6 | */ 7 | "use strict"; 8 | if( !(this instanceof autoCompleter) ){ 9 | return new autoCompleter(...arguments); 10 | } 11 | this.hoverColor = "#eee"; 12 | this.bgColor = "#f9f9f9"; 13 | this._version = "1.0.12"; 14 | let main = this; 15 | if(!inputElement || (!(inputElement.parentElement))) { 16 | console.error("Error no inputelement found to work with"); 17 | return; 18 | } 19 | async function fetch_data(suggestionUrl, searchString) { 20 | const url = new URL(suggestionUrl); 21 | if(search) { 22 | url.searchParams.delete(search); 23 | url.searchParams.append(search, searchString) 24 | } 25 | suggestionUrl = url.href; 26 | const fobj = await fetch(suggestionUrl); 27 | const data = await fobj.json(); 28 | if(selector && data[selector]) 29 | return data[selector]; 30 | return data; 31 | } 32 | inputElement.parentElement.style.display = "inline-block"; 33 | inputElement.parentElement.style.position = "relative"; 34 | inputElement.addEventListener("click", function(e) { 35 | closeAllLists(e.target); 36 | }); 37 | function cleanHTML(content) { 38 | const div = document.createElement("div"); 39 | div.textContent = content; 40 | return div.innerHTML; 41 | } 42 | let currentFocus; 43 | inputElement.addEventListener("input", async function() { 44 | let suggestionBox, suggestionItem, val = this.value; 45 | /* Dynamicly update the suggestions array or fetch it once for all*/ 46 | if(suggestionUrl) { 47 | if(search) { 48 | suggestionsArray = await fetch_data(suggestionUrl, val); 49 | } else if (!("once" in main)) { 50 | suggestionsArray = await fetch_data(suggestionUrl, ""); 51 | main.once = true; 52 | } 53 | } 54 | if((!Array.isArray(suggestionsArray))) { 55 | console.error("Suggestion Array cannot be empty or not array"); 56 | return; 57 | } 58 | if(suggestionsArray.length < 1) { 59 | console.error("Input array cannot be empty with no suggestions"); 60 | return; 61 | } 62 | closeAllLists(); 63 | if (!val) return false; 64 | currentFocus = -1; 65 | 66 | suggestionBox = document.createElement("DIV"); 67 | const boxCSS = {"position": "absolute", 68 | "border": "1px solid #ddd", 69 | "border-bottom": "none","border-top": "none", 70 | "z-index": "99","top": "100%","left": "0", 71 | "right": "0", "background-color": main.bgColor}; 72 | for(const k in boxCSS) { 73 | suggestionBox.style.setProperty(k,boxCSS[k]) 74 | } 75 | this.parentNode.appendChild(suggestionBox); 76 | 77 | suggestionsArray.forEach(function(suggestion) { 78 | if (suggestion.toLowerCase().indexOf(val.toLowerCase()) > -1) { 79 | suggestionItem = document.createElement("DIV"); 80 | const itemCSS = {"padding": "10px", 81 | "cursor": "pointer", 82 | "border-bottom": "1px solid #ddd"}; 83 | for(const k in itemCSS) { 84 | suggestionItem.style.setProperty(k,itemCSS[k]) 85 | } 86 | suggestionItem.onmouseover = function() { 87 | this.style.backgroundColor = main.hoverColor; 88 | } 89 | suggestionItem.onmouseleave = function () { 90 | this.style.backgroundColor = ""; 91 | } 92 | const r = new RegExp(cleanHTML(val),"dgi"); 93 | let suggestionHTML = cleanHTML(suggestion); 94 | new Set(suggestionHTML.match(r)).forEach(function(m) { 95 | suggestionHTML = suggestionHTML.replaceAll(m,"" + m + ""); 96 | }); 97 | suggestionItem.innerHTML = suggestionHTML; 98 | let input = document.createElement("input"); 99 | input.value = suggestion; 100 | input.type = "hidden"; 101 | suggestionItem.appendChild(input); 102 | suggestionItem.addEventListener("click", function() { 103 | inputElement.value = this.getElementsByTagName("input")[0].value; 104 | closeAllLists(); 105 | }); 106 | suggestionBox.appendChild(suggestionItem); 107 | } 108 | }); 109 | }); 110 | 111 | inputElement.addEventListener("keydown", function(e) { 112 | const keyCodes = {arrowDown: 40, arrowUp: 38, Enter: 13} 113 | let items = inputElement.parentElement.querySelectorAll("div > div"); 114 | if (items) items = Array.from(items); 115 | if (e.keyCode == keyCodes.arrowDown) { 116 | currentFocus++; 117 | if(currentFocus > 0 ) 118 | addActive(items); 119 | } else if (e.keyCode == keyCodes.arrowUp) { 120 | currentFocus--; 121 | if(currentFocus > 0 ) 122 | addActive(items); 123 | } else if (e.keyCode == keyCodes.Enter) { 124 | e.preventDefault(); 125 | if (currentFocus > -1 && items) { 126 | items[currentFocus].click(); 127 | } 128 | } 129 | }); 130 | 131 | function addActive(items) { 132 | if (!items) return false; 133 | removeActive(items); 134 | if (currentFocus >= items.length) currentFocus = 0; 135 | if (currentFocus < 0) currentFocus = items.length - 1; 136 | if(currentFocus > 0) 137 | items[currentFocus].style.backgroundColor = main.hoverColor; 138 | } 139 | 140 | function removeActive(items) { 141 | items.forEach(function(item) { item.style.backgroundColor= ""}); 142 | } 143 | 144 | function closeAllLists(elmnt) { 145 | let items = inputElement.parentElement.querySelectorAll(":scope > div"); 146 | items.forEach(function(item) { 147 | if (elmnt != item && elmnt != inputElement) { 148 | item.parentNode.removeChild(item); 149 | } 150 | }); 151 | } 152 | return main; 153 | } 154 | 155 | 156 | -------------------------------------------------------------------------------- /cveInterface.css: -------------------------------------------------------------------------------- 1 | /* version 1.0.12 */ 2 | li.optional { 3 | list-style-type: none; 4 | } 5 | #chatbox { 6 | border: 1px solid #ccc; 7 | padding: 1rem; 8 | max-width: 600px; 9 | overflow-y: auto; 10 | background: #f9f9f9; 11 | border-radius: 5px; 12 | clear: both; 13 | } 14 | .cvechat input.form-control { 15 | display: inline-block; 16 | min-width: 40ch; 17 | } 18 | .cvechat .bot, 19 | .cvechat .user { 20 | margin: 0.5rem 0; 21 | padding: 0.5rem; 22 | border-radius: 5px; 23 | } 24 | .cvechat .bot { 25 | background: #e6f2ff; 26 | } 27 | .cvechat .user { 28 | background: #dfffd6; 29 | text-align: right; 30 | } 31 | .cvechat button { 32 | padding: 0.5rem 1rem; 33 | } 34 | .cvechat pre { 35 | background: #333; 36 | color: #fff; 37 | padding: 1rem; 38 | overflow-x: auto; 39 | } 40 | 41 | head { 42 | --version: 1.0.10; 43 | } 44 | .childarray { 45 | margin: 0px 0px 0px 16px; 46 | border-left: 2px dotted #999; 47 | position:relative; 48 | padding-left: 4px; 49 | } 50 | button.arrowdown { 51 | transform: rotate(90deg); 52 | color: #999; 53 | } 54 | .editorwrap.show { 55 | display: inline-block; 56 | } 57 | .editorwrap { 58 | width: 100%; 59 | min-height: 600px; 60 | position: relative; 61 | } 62 | .jsoneditor { 63 | position: absolute; 64 | top: 0; 65 | right: 0; 66 | bottom: 0; 67 | left: 0; 68 | } 69 | .lang { 70 | width: 30ch; 71 | display: inline-block; 72 | } 73 | .erow { 74 | text-align: left; 75 | padding: 4px 1px 4px 1px; 76 | border-bottom: 1px dotted #aaa; 77 | } 78 | /* consider some other color for values other than placeholder 79 | .erow input.form-control, 80 | .erow textarea.form-control 81 | { 82 | color: blue; 83 | } 84 | */ 85 | .frow { 86 | border-bottom: 1px solid #999; 87 | position:relative; 88 | padding: 0px 0px 0px 4px; 89 | } 90 | ol.frow, 91 | ol.childarray { 92 | counter-reset: listCounter; 93 | } 94 | li.erow { 95 | counter-increment: listCounter; 96 | } 97 | ol.frow li.erow::marker { 98 | font-size: 0.6em; 99 | content: "(" counter(listCounter) ")"; 100 | } 101 | ol.frow li.erow:nth-of-type(1)::marker { 102 | list-style-type: none; 103 | content: ""; 104 | } 105 | .erow:nth-of-type(1) > .enoncerequired { 106 | pointer-events: none; 107 | background: #eee; 108 | } 109 | .erow:last-of-type:not(:first-of-type) > .deleterow { 110 | display: block; 111 | } 112 | .deleterow { 113 | display: none; 114 | } 115 | .erow:nth-of-type(n+2) > input:nth-of-type(1) { 116 | width: 90%; 117 | } 118 | .duplicator { 119 | color: #333; 120 | background: transparent; 121 | border: none; 122 | font-size: 20px; 123 | top: 2px; 124 | right:2px; 125 | position: absolute; 126 | z-Index: 10; 127 | } 128 | .mauto { 129 | width: auto; 130 | display:inline-block; 131 | } 132 | #cveUpdateModal label{ 133 | display:block; 134 | font-weight: bold; 135 | text-align: left; 136 | } 137 | .ousername { 138 | display: none; 139 | } 140 | .ustatus { 141 | display:inline-block; 142 | padding-top: 4px; 143 | } 144 | .tswitch { 145 | position: absolute; 146 | display: inline-block; 147 | width: 60px; 148 | height: 34px; 149 | } 150 | 151 | .tswitch input { 152 | opacity: 0; 153 | width: 0; 154 | height: 0; 155 | } 156 | 157 | .tslider { 158 | position: absolute; 159 | cursor: pointer; 160 | top: 0; 161 | left: 0; 162 | right: 0; 163 | bottom: 0; 164 | background-color: #ccc; 165 | -webkit-transition: .4s; 166 | transition: .4s; 167 | } 168 | 169 | .tslider:before { 170 | position: absolute; 171 | content: ""; 172 | height: 26px; 173 | width: 26px; 174 | left: 4px; 175 | bottom: 4px; 176 | background-color: white; 177 | -webkit-transition: .4s; 178 | transition: .4s; 179 | } 180 | 181 | 182 | input:focus + .tslider { 183 | box-shadow: 0 0 1px #2196F3; 184 | } 185 | 186 | input.enabled + .tslider { 187 | background-color: #2196F3; 188 | } 189 | 190 | input.enabled + .tslider:before { 191 | -webkit-transform: translateX(26px); 192 | -ms-transform: translateX(26px); 193 | transform: translateX(26px); 194 | } 195 | 196 | /* Rounded tsliders */ 197 | .tslider.round { 198 | border-radius: 34px; 199 | } 200 | 201 | .tslider.round:before { 202 | border-radius: 50%; 203 | } 204 | .hwarn, 205 | tr.hwarn { 206 | background-color: #fff3cd !important; 207 | } 208 | tr.hnew { 209 | background-color: lightgreen !important; 210 | } 211 | tr.hdanger { 212 | background-color: #f8d7da !important; 213 | } 214 | div.bootstrap-table button.btn { 215 | background-color: transparent; 216 | color: black; 217 | } 218 | /*↻ "↺" ↺ */ 219 | .fa-sync::before { 220 | content: "\021BB"; 221 | } 222 | .fa-sync { 223 | color: black; 224 | } 225 | .blackbody .fa-sync, 226 | .blackbody div.bootstrap-table button.btn { 227 | color: white; 228 | } 229 | .blackbody { 230 | background-color: #333; 231 | color: white; 232 | } 233 | .logout { 234 | border: 1px solid black; 235 | border-right: transparent; 236 | padding: 2px 4px 2px 6px; 237 | } 238 | #topalert { 239 | display: none; 240 | /* Just 1 above bootstrap modal */ 241 | z-index: 1051; 242 | } 243 | #deepDive .table td { 244 | text-align: left; 245 | } 246 | .addUser .updateuser { 247 | display:none; 248 | } 249 | .updateUser .adduser { 250 | display:none; 251 | } 252 | .loading { 253 | border: 4px solid #ddd; 254 | border-radius: 50%; 255 | border-top: 4px solid #222; 256 | width: 20px; 257 | height: 20px; 258 | -webkit-animation: spin 2s linear infinite; /* Safari */ 259 | animation: spin 2s linear infinite; 260 | } 261 | @-webkit-keyframes spin { 262 | 0% { -webkit-transform: rotate(0deg); } 263 | 100% { -webkit-transform: rotate(360deg); } 264 | } 265 | 266 | @keyframes spin { 267 | 0% { transform: rotate(0deg); } 268 | 100% { transform: rotate(360deg); } 269 | } 270 | #cveUpdateModal .btn { 271 | color: white; 272 | } 273 | #allFields { all: initial; } 274 | #allFields:not(.active) { display: none; } 275 | #allFields fieldset { all:revert;} 276 | #allFields label { all:revert;} 277 | #allFields * { all:revert;} 278 | .nologin { padding: 2px;} 279 | .nologin label * { margin: 2px !important;} 280 | li.nonumber { list-style-type: none;} 281 | label#cvenumber { display: inline-block;} 282 | label.optional { color: #999; } 283 | .lowbottom { margin-bottom: 0px; border: none; } 284 | .mrpad { margin-right: 28px;} 285 | -------------------------------------------------------------------------------- /language-codes.json: -------------------------------------------------------------------------------- 1 | {"source": "https://datahub.io/core/language-codes/r/language-codes.json", 2 | "langs": [{"English": "Afar", "alpha2": "aa"},{"English": "Abkhazian", "alpha2": "ab"},{"English": "Avestan", "alpha2": "ae"},{"English": "Afrikaans", "alpha2": "af"},{"English": "Akan", "alpha2": "ak"},{"English": "Amharic", "alpha2": "am"},{"English": "Aragonese", "alpha2": "an"},{"English": "Arabic", "alpha2": "ar"},{"English": "Assamese", "alpha2": "as"},{"English": "Avaric", "alpha2": "av"},{"English": "Aymara", "alpha2": "ay"},{"English": "Azerbaijani", "alpha2": "az"},{"English": "Bashkir", "alpha2": "ba"},{"English": "Belarusian", "alpha2": "be"},{"English": "Bulgarian", "alpha2": "bg"},{"English": "Bihari languages", "alpha2": "bh"},{"English": "Bislama", "alpha2": "bi"},{"English": "Bambara", "alpha2": "bm"},{"English": "Bengali", "alpha2": "bn"},{"English": "Tibetan", "alpha2": "bo"},{"English": "Breton", "alpha2": "br"},{"English": "Bosnian", "alpha2": "bs"},{"English": "Catalan; Valencian", "alpha2": "ca"},{"English": "Chechen", "alpha2": "ce"},{"English": "Chamorro", "alpha2": "ch"},{"English": "Corsican", "alpha2": "co"},{"English": "Cree", "alpha2": "cr"},{"English": "Czech", "alpha2": "cs"},{"English": "Church Slavic; Old Slavonic; Church Slavonic; Old Bulgarian; Old Church Slavonic", "alpha2": "cu"},{"English": "Chuvash", "alpha2": "cv"},{"English": "Welsh", "alpha2": "cy"},{"English": "Danish", "alpha2": "da"},{"English": "German", "alpha2": "de"},{"English": "Divehi; Dhivehi; Maldivian", "alpha2": "dv"},{"English": "Dzongkha", "alpha2": "dz"},{"English": "Ewe", "alpha2": "ee"},{"English": "Greek, Modern (1453-)", "alpha2": "el"},{"English": "English", "alpha2": "en"},{"English": "Esperanto", "alpha2": "eo"},{"English": "Spanish; Castilian", "alpha2": "es"},{"English": "Estonian", "alpha2": "et"},{"English": "Basque", "alpha2": "eu"},{"English": "Persian", "alpha2": "fa"},{"English": "Fulah", "alpha2": "ff"},{"English": "Finnish", "alpha2": "fi"},{"English": "Fijian", "alpha2": "fj"},{"English": "Faroese", "alpha2": "fo"},{"English": "French", "alpha2": "fr"},{"English": "Western Frisian", "alpha2": "fy"},{"English": "Irish", "alpha2": "ga"},{"English": "Gaelic; Scottish Gaelic", "alpha2": "gd"},{"English": "Galician", "alpha2": "gl"},{"English": "Guarani", "alpha2": "gn"},{"English": "Gujarati", "alpha2": "gu"},{"English": "Manx", "alpha2": "gv"},{"English": "Hausa", "alpha2": "ha"},{"English": "Hebrew", "alpha2": "he"},{"English": "Hindi", "alpha2": "hi"},{"English": "Hiri Motu", "alpha2": "ho"},{"English": "Croatian", "alpha2": "hr"},{"English": "Haitian; Haitian Creole", "alpha2": "ht"},{"English": "Hungarian", "alpha2": "hu"},{"English": "Armenian", "alpha2": "hy"},{"English": "Herero", "alpha2": "hz"},{"English": "Interlingua (International Auxiliary Language Association)", "alpha2": "ia"},{"English": "Indonesian", "alpha2": "id"},{"English": "Interlingue; Occidental", "alpha2": "ie"},{"English": "Igbo", "alpha2": "ig"},{"English": "Sichuan Yi; Nuosu", "alpha2": "ii"},{"English": "Inupiaq", "alpha2": "ik"},{"English": "Ido", "alpha2": "io"},{"English": "Icelandic", "alpha2": "is"},{"English": "Italian", "alpha2": "it"},{"English": "Inuktitut", "alpha2": "iu"},{"English": "Japanese", "alpha2": "ja"},{"English": "Javanese", "alpha2": "jv"},{"English": "Georgian", "alpha2": "ka"},{"English": "Kongo", "alpha2": "kg"},{"English": "Kikuyu; Gikuyu", "alpha2": "ki"},{"English": "Kuanyama; Kwanyama", "alpha2": "kj"},{"English": "Kazakh", "alpha2": "kk"},{"English": "Kalaallisut; Greenlandic", "alpha2": "kl"},{"English": "Central Khmer", "alpha2": "km"},{"English": "Kannada", "alpha2": "kn"},{"English": "Korean", "alpha2": "ko"},{"English": "Kanuri", "alpha2": "kr"},{"English": "Kashmiri", "alpha2": "ks"},{"English": "Kurdish", "alpha2": "ku"},{"English": "Komi", "alpha2": "kv"},{"English": "Cornish", "alpha2": "kw"},{"English": "Kirghiz; Kyrgyz", "alpha2": "ky"},{"English": "Latin", "alpha2": "la"},{"English": "Luxembourgish; Letzeburgesch", "alpha2": "lb"},{"English": "Ganda", "alpha2": "lg"},{"English": "Limburgan; Limburger; Limburgish", "alpha2": "li"},{"English": "Lingala", "alpha2": "ln"},{"English": "Lao", "alpha2": "lo"},{"English": "Lithuanian", "alpha2": "lt"},{"English": "Luba-Katanga", "alpha2": "lu"},{"English": "Latvian", "alpha2": "lv"},{"English": "Malagasy", "alpha2": "mg"},{"English": "Marshallese", "alpha2": "mh"},{"English": "Maori", "alpha2": "mi"},{"English": "Macedonian", "alpha2": "mk"},{"English": "Malayalam", "alpha2": "ml"},{"English": "Mongolian", "alpha2": "mn"},{"English": "Marathi", "alpha2": "mr"},{"English": "Malay", "alpha2": "ms"},{"English": "Maltese", "alpha2": "mt"},{"English": "Burmese", "alpha2": "my"},{"English": "Nauru", "alpha2": "na"},{"English": "Bokm\u00e5l, Norwegian; Norwegian Bokm\u00e5l", "alpha2": "nb"},{"English": "Ndebele, North; North Ndebele", "alpha2": "nd"},{"English": "Nepali", "alpha2": "ne"},{"English": "Ndonga", "alpha2": "ng"},{"English": "Dutch; Flemish", "alpha2": "nl"},{"English": "Norwegian Nynorsk; Nynorsk, Norwegian", "alpha2": "nn"},{"English": "Norwegian", "alpha2": "no"},{"English": "Ndebele, South; South Ndebele", "alpha2": "nr"},{"English": "Navajo; Navaho", "alpha2": "nv"},{"English": "Chichewa; Chewa; Nyanja", "alpha2": "ny"},{"English": "Occitan (post 1500)", "alpha2": "oc"},{"English": "Ojibwa", "alpha2": "oj"},{"English": "Oromo", "alpha2": "om"},{"English": "Oriya", "alpha2": "or"},{"English": "Ossetian; Ossetic", "alpha2": "os"},{"English": "Panjabi; Punjabi", "alpha2": "pa"},{"English": "Pali", "alpha2": "pi"},{"English": "Polish", "alpha2": "pl"},{"English": "Pushto; Pashto", "alpha2": "ps"},{"English": "Portuguese", "alpha2": "pt"},{"English": "Quechua", "alpha2": "qu"},{"English": "Romansh", "alpha2": "rm"},{"English": "Rundi", "alpha2": "rn"},{"English": "Romanian; Moldavian; Moldovan", "alpha2": "ro"},{"English": "Russian", "alpha2": "ru"},{"English": "Kinyarwanda", "alpha2": "rw"},{"English": "Sanskrit", "alpha2": "sa"},{"English": "Sardinian", "alpha2": "sc"},{"English": "Sindhi", "alpha2": "sd"},{"English": "Northern Sami", "alpha2": "se"},{"English": "Sango", "alpha2": "sg"},{"English": "Sinhala; Sinhalese", "alpha2": "si"},{"English": "Slovak", "alpha2": "sk"},{"English": "Slovenian", "alpha2": "sl"},{"English": "Samoan", "alpha2": "sm"},{"English": "Shona", "alpha2": "sn"},{"English": "Somali", "alpha2": "so"},{"English": "Albanian", "alpha2": "sq"},{"English": "Serbian", "alpha2": "sr"},{"English": "Swati", "alpha2": "ss"},{"English": "Sotho, Southern", "alpha2": "st"},{"English": "Sundanese", "alpha2": "su"},{"English": "Swedish", "alpha2": "sv"},{"English": "Swahili", "alpha2": "sw"},{"English": "Tamil", "alpha2": "ta"},{"English": "Telugu", "alpha2": "te"},{"English": "Tajik", "alpha2": "tg"},{"English": "Thai", "alpha2": "th"},{"English": "Tigrinya", "alpha2": "ti"},{"English": "Turkmen", "alpha2": "tk"},{"English": "Tagalog", "alpha2": "tl"},{"English": "Tswana", "alpha2": "tn"},{"English": "Tonga (Tonga Islands)", "alpha2": "to"},{"English": "Turkish", "alpha2": "tr"},{"English": "Tsonga", "alpha2": "ts"},{"English": "Tatar", "alpha2": "tt"},{"English": "Twi", "alpha2": "tw"},{"English": "Tahitian", "alpha2": "ty"},{"English": "Uighur; Uyghur", "alpha2": "ug"},{"English": "Ukrainian", "alpha2": "uk"},{"English": "Urdu", "alpha2": "ur"},{"English": "Uzbek", "alpha2": "uz"},{"English": "Venda", "alpha2": "ve"},{"English": "Vietnamese", "alpha2": "vi"},{"English": "Volap\u00fck", "alpha2": "vo"},{"English": "Walloon", "alpha2": "wa"},{"English": "Wolof", "alpha2": "wo"},{"English": "Xhosa", "alpha2": "xh"},{"English": "Yiddish", "alpha2": "yi"},{"English": "Yoruba", "alpha2": "yo"},{"English": "Zhuang; Chuang", "alpha2": "za"},{"English": "Chinese", "alpha2": "zh"},{"English": "Zulu", "alpha2": "zu"}] 3 | } 4 | -------------------------------------------------------------------------------- /cwe-common.json: -------------------------------------------------------------------------------- 1 | { 2 | "cwe-common": [ 3 | "CWE-20 Improper Input Validation", 4 | "CWE-129 Improper Validation of Array Index", 5 | "CWE-74 Improper Neutralization of Special Elements in Output Used by a Downstream Component ('Injection')", 6 | "CWE-1236 Improper Neutralization of Formula Elements in a CSV File", 7 | "CWE-77 Improper Neutralization of Special Elements used in a Command ('Command Injection')", 8 | "CWE-78 Improper Neutralization of Special Elements used in an OS Command ('OS Command Injection')", 9 | "CWE-79 Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting')", 10 | "CWE-88 Improper Neutralization of Argument Delimiters in a Command ('Argument Injection')", 11 | "CWE-89 Improper Neutralization of Special Elements used in an SQL Command ('SQL Injection')", 12 | "CWE-91 XML Injection (aka Blind XPath Injection)", 13 | "CWE-917 Improper Neutralization of Special Elements used in an Expression Language Statement ('Expression Language Injection')", 14 | "CWE-94 Improper Control of Generation of Code ('Code Injection')", 15 | "CWE-116 Improper Encoding or Escaping of Output", 16 | "CWE-838 Inappropriate Encoding for Output Context", 17 | "CWE-119 Improper Restriction of Operations within the Bounds of a Memory Buffer", 18 | "CWE-120 Buffer Copy without Checking Size of Input ('Classic Buffer Overflow')", 19 | "CWE-125 Out-of-bounds Read", 20 | "CWE-787 Out-of-bounds Write", 21 | "CWE-824 Access of Uninitialized Pointer", 22 | "CWE-200 Exposure of Sensitive Information to an Unauthorized Actor", 23 | "CWE-203 Observable Discrepancy", 24 | "CWE-209 Generation of Error Message Containing Sensitive Information", 25 | "CWE-532 Insertion of Sensitive Information into Log File", 26 | "CWE-269 Improper Privilege Management", 27 | "CWE-287 Improper Authentication", 28 | "CWE-290 Authentication Bypass by Spoofing", 29 | "CWE-294 Authentication Bypass by Capture-replay", 30 | "CWE-295 Improper Certificate Validation", 31 | "CWE-306 Missing Authentication for Critical Function", 32 | "CWE-307 Improper Restriction of Excessive Authentication Attempts", 33 | "CWE-521 Weak Password Requirements", 34 | "CWE-522 Insufficiently Protected Credentials", 35 | "CWE-640 Weak Password Recovery Mechanism for Forgotten Password", 36 | "CWE-798 Use of Hard-coded Credentials", 37 | "CWE-311 Missing Encryption of Sensitive Data", 38 | "CWE-312 Cleartext Storage of Sensitive Information", 39 | "CWE-319 Cleartext Transmission of Sensitive Information", 40 | "CWE-326 Inadequate Encryption Strength", 41 | "CWE-327 Use of a Broken or Risky Cryptographic Algorithm", 42 | "CWE-916 Use of Password Hash With Insufficient Computational Effort", 43 | "CWE-330 Use of Insufficiently Random Values", 44 | "CWE-331 Insufficient Entropy", 45 | "CWE-335 Incorrect Usage of Seeds in Pseudo-Random Number Generator (PRNG)", 46 | "CWE-338 Use of Cryptographically Weak Pseudo-Random Number Generator (PRNG)", 47 | "CWE-345 Insufficient Verification of Data Authenticity", 48 | "CWE-346 Origin Validation Error", 49 | "CWE-347 Improper Verification of Cryptographic Signature", 50 | "CWE-352 Cross-Site Request Forgery (CSRF)", 51 | "CWE-354 Improper Validation of Integrity Check Value", 52 | "CWE-924 Improper Enforcement of Message Integrity During Transmission in a Communication Channel", 53 | "CWE-362 Concurrent Execution using Shared Resource with Improper Synchronization ('Race Condition')", 54 | "CWE-367 Time-of-check Time-of-use (TOCTOU) Race Condition", 55 | "CWE-400 Uncontrolled Resource Consumption", 56 | "CWE-770 Allocation of Resources Without Limits or Throttling", 57 | "CWE-920 Improper Restriction of Power Consumption", 58 | "CWE-404 Improper Resource Shutdown or Release", 59 | "CWE-401 Missing Release of Memory after Effective Lifetime", 60 | "CWE-459 Incomplete Cleanup", 61 | "CWE-763 Release of Invalid Pointer or Reference", 62 | "CWE-772 Missing Release of Resource after Effective Lifetime", 63 | "CWE-436 Interpretation Conflict", 64 | "CWE-444 Inconsistent Interpretation of HTTP Requests ('HTTP Request Smuggling')", 65 | "CWE-610 Externally Controlled Reference to a Resource in Another Sphere", 66 | "CWE-1021 Improper Restriction of Rendered UI Layers or Frames", 67 | "CWE-384 Session Fixation", 68 | "CWE-601 URL Redirection to Untrusted Site ('Open Redirect')", 69 | "CWE-611 Improper Restriction of XML External Entity Reference", 70 | "CWE-918 Server-Side Request Forgery (SSRF)", 71 | "CWE-662 Improper Synchronization", 72 | "CWE-667 Improper Locking", 73 | "CWE-665 Improper Initialization", 74 | "CWE-1188 Insecure Default Initialization of Resource", 75 | "CWE-908 Use of Uninitialized Resource", 76 | "CWE-909 Missing Initialization of Resource", 77 | "CWE-668 Exposure of Resource to Wrong Sphere", 78 | "CWE-134 Use of Externally-Controlled Format String", 79 | "CWE-426 Untrusted Search Path", 80 | "CWE-427 Uncontrolled Search Path Element", 81 | "CWE-428 Unquoted Search Path or Element", 82 | "CWE-552 Files or Directories Accessible to External Parties", 83 | "CWE-669 Incorrect Resource Transfer Between Spheres", 84 | "CWE-212 Improper Removal of Sensitive Information Before Storage or Transfer", 85 | "CWE-434 Unrestricted Upload of File with Dangerous Type", 86 | "CWE-494 Download of Code Without Integrity Check", 87 | "CWE-565 Reliance on Cookies without Validation and Integrity Checking", 88 | "CWE-829 Inclusion of Functionality from Untrusted Control Sphere", 89 | "CWE-670 Always-Incorrect Control Flow Implementation", 90 | "CWE-617 Reachable Assertion", 91 | "CWE-672 Operation on a Resource after Expiration or Release", 92 | "CWE-415 Double Free", 93 | "CWE-416 Use After Free", 94 | "CWE-613 Insufficient Session Expiration", 95 | "CWE-674 Uncontrolled Recursion", 96 | "CWE-776 Improper Restriction of Recursive Entity References in DTDs ('XML Entity Expansion')", 97 | "CWE-682 Incorrect Calculation", 98 | "CWE-131 Incorrect Calculation of Buffer Size", 99 | "CWE-190 Integer Overflow or Wraparound", 100 | "CWE-191 Integer Underflow (Wrap or Wraparound)", 101 | "CWE-193 Off-by-one Error", 102 | "CWE-369 Divide By Zero", 103 | "CWE-697 Incorrect Comparison", 104 | "CWE-704 Incorrect Type Conversion or Cast", 105 | "CWE-681 Incorrect Conversion between Numeric Types", 106 | "CWE-843 Access of Resource Using Incompatible Type ('Type Confusion')", 107 | "CWE-706 Use of Incorrectly-Resolved Name or Reference", 108 | "CWE-178 Improper Handling of Case Sensitivity", 109 | "CWE-22 Improper Limitation of a Pathname to a Restricted Directory ('Path Traversal')", 110 | "CWE-59 Improper Link Resolution Before File Access ('Link Following')", 111 | "CWE-732 Incorrect Permission Assignment for Critical Resource", 112 | "CWE-276 Incorrect Default Permissions", 113 | "CWE-281 Improper Preservation of Permissions", 114 | "CWE-754 Improper Check for Unusual or Exceptional Conditions", 115 | "CWE-252 Unchecked Return Value", 116 | "CWE-273 Improper Check for Dropped Privileges", 117 | "CWE-476 NULL Pointer Dereference", 118 | "CWE-755 Improper Handling of Exceptional Conditions", 119 | "CWE-834 Excessive Iteration", 120 | "CWE-835 Loop with Unreachable Exit Condition ('Infinite Loop')", 121 | "CWE-862 Missing Authorization", 122 | "CWE-425 Direct Request ('Forced Browsing')", 123 | "CWE-863 Incorrect Authorization", 124 | "CWE-639 Authorization Bypass Through User-Controlled Key", 125 | "CWE-913 Improper Control of Dynamically-Managed Code Resources", 126 | "CWE-470 Use of Externally-Controlled Input to Select Classes or Code ('Unsafe Reflection')", 127 | "CWE-502 Deserialization of Untrusted Data", 128 | "CWE-915 Improperly Controlled Modification of Dynamically-Determined Object Attributes", 129 | "CWE-922 Insecure Storage of Sensitive Information" 130 | ] 131 | } 132 | -------------------------------------------------------------------------------- /certicon.ico: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Internet Security by Zscaler 9 | 10 | 11 | 343 | 344 | 345 | 346 |
347 |
348 |
349 | 350 | 351 | 352 | 354 |
355 | 356 | 357 | 383 |
358 |
D16
359 | 360 | 361 | 365 | 366 | 369 | 372 | 373 | 376 | 380 |
362 | 363 | Sorry, company policy prohibits this action. 364 |

367 | Website blocked 368 |
370 | HTTPS is Blocked by Firewall rule Prohibit Internal Relay (Proxy) 371 |

374 | Need help? Contact our support team at 412.268.5015, ithelpdesk@sei.cmu.edu 375 |
377 | 378 | Your organization has selected Zscaler to protect you from internet threats. 379 |
381 | 382 |
384 |
385 |
386 | 387 | -------------------------------------------------------------------------------- /schemaToForm.js: -------------------------------------------------------------------------------- 1 | function schemaToForm(schemaUrl, elementId) { 2 | "use strict"; 3 | if( !(this instanceof schemaToForm) ){ 4 | return new schemaToForm(...arguments); 5 | } 6 | this._version = "1.0.9"; 7 | let main = this; 8 | async function fetchObj(url) { 9 | try { 10 | const response = await fetch(url); 11 | return await response.json(); 12 | } catch (error) { 13 | console.error('Error fetching schema:', error); 14 | return null; 15 | } 16 | } 17 | function populate(obj, base) { 18 | Object.keys(obj).forEach(function(field) { 19 | let bfield = field; 20 | if(base) 21 | bfield = base + "." + field; 22 | let el = document.querySelector("[data-path='" + bfield + "']"); 23 | if(el) { 24 | if(el.querySelector("div") && 25 | (!el.querySelector("div").checkVisibility())) { 26 | displayOnly(el.querySelector("legend")); 27 | } 28 | } 29 | if(typeof(obj[field]) == "object") { 30 | if(field.match(/^\d+$/)) { 31 | let count = parseInt(field) + 1; 32 | let sfield = bfield.replace(/\.\d+$/,'.0'); 33 | let rcount = document.querySelectorAll("[data-path='" + sfield + "']").length; 34 | 35 | /* If the fields do not exist create them*/ 36 | if(rcount > 0 && rcount < count) { 37 | const tel = document.querySelector("[data-path='" + sfield + "']").querySelector("legend > a"); 38 | if(tel && tel.parentElement) 39 | cloner(tel.parentElement); 40 | } 41 | } 42 | return populate(obj[field], bfield); 43 | } 44 | if(el) { 45 | el.value = obj[field]; 46 | if(el.style && el.style.border && el.style.border.indexOf("red") > -1) { 47 | el.style.border = "1px solid green"; 48 | if(el.validity && el.validity.valid) { 49 | const sp = document.createElement('span'); 50 | sp.innerHTML = " ✓ "; 51 | sp.style.color = "green"; 52 | sp.setAttribute("data-valid",el.getAttribute("data-path")); 53 | el.after(sp); 54 | } 55 | } 56 | } else { 57 | console.error(obj, base, field); 58 | } 59 | }); 60 | } 61 | function resolveRef(ref, prop, schema) { 62 | const path = ref.replace(/^#\/definitions\//, '').split('/'); 63 | let resolved = schema.definitions; 64 | path.forEach(p => { 65 | if(p in resolved) 66 | resolved = resolved[p]; 67 | else 68 | resolved = {}; 69 | }); 70 | let copyFields = ["examples","minItems","maxItems","allOf","anyOf"]; 71 | copyFields.forEach(field => { if(prop && field in prop) 72 | resolved[prop] = field[prop] }); 73 | if(resolved.$ref) 74 | return resolveRef(resolved.$ref, prop, schema); 75 | return resolved; 76 | } 77 | function elToField(el) { 78 | let elx; 79 | let eltype = "string"; 80 | let elkey; 81 | let oldtype = "string"; 82 | let tree = []; 83 | elx = el.parentElement; 84 | let cid = 0; 85 | while(elx) { 86 | if(elx.tagName == "FIELDSET" && elx.hasAttribute("data-cid")) { 87 | cid = parseInt(elx.getAttribute("data-cid")); 88 | } 89 | if(elx.tagName == "DIV" && elx.hasAttribute("data-type")) { 90 | eltype = elx.getAttribute("data-type"); 91 | elkey = elx.getAttribute("data-key"); 92 | if(eltype == "array") { 93 | if(oldtype == "object") 94 | tree.pop(); 95 | tree.push(cid); 96 | tree.push(elkey); 97 | } 98 | if((eltype == "object") || ((eltype == "string" || eltype == "number" || eltype == "boolean" ) && elkey != '[]')) 99 | tree.push(elkey); 100 | 101 | oldtype = eltype; 102 | } 103 | elx = elx.parentElement; 104 | } 105 | /* Remove the last element if the path value is empty like a.b.c.d.0 is a string/enum/int 106 | and NOT an object or another array */ 107 | if(tree[0] == "" && el.tagName != "FIELDSET") 108 | tree.shift(); 109 | el.setAttribute("data-path", tree.reverse().join(".")); 110 | } 111 | main.elToField = elToField; 112 | function removeRequired(el) { 113 | el.removeAttribute("required"); 114 | el.removeAttribute("data-required"); 115 | el.removeAttribute("style"); 116 | } 117 | function makeRequired(el) { 118 | const allowed = ["INPUT","TEXTAREA","SELECT"]; 119 | if(allowed.includes(el.tagName)) 120 | el.setAttribute("required", true); 121 | el.setAttribute("data-required",true); 122 | el.style.border = "1px solid red"; 123 | } 124 | function hideDecloners(el) { 125 | let els = el.querySelectorAll(":scope > fieldset > legend > a[data-decloner]"); 126 | if(els.length == 1) { 127 | els[0].style.display = ""; 128 | } else { 129 | for(let i=0; i < els.length - 1; i++) 130 | els[i].style.display = "none"; 131 | els[els.length - 1].style.display = ""; 132 | } 133 | } 134 | 135 | function decloner(el) { 136 | let es = el.parentElement.parentElement.querySelector(el.tagName).parentElement; 137 | if(el.querySelector("[data-hidder]") && (es.getAttribute("data-counter") == "0")) { 138 | el.parentElement.querySelector("div").style.display = "none"; 139 | el.innerHTML = el.innerHTML.replace('[0]','[]'); 140 | if(el.querySelector("[data-hidder]")) 141 | el.querySelector("[data-hidder]").remove(); 142 | return; 143 | } 144 | if(es && es.hasAttribute("data-counter")) { 145 | let delid = es.getAttribute("data-counter"); 146 | let er = el.parentElement.parentElement.querySelector("[data-cid='" + delid + "']"); 147 | if(er) { 148 | let et = er.parentElement; 149 | er.remove(); 150 | hideDecloners(et); 151 | es.setAttribute("data-counter", String(parseInt(delid) - 1)); 152 | } 153 | } 154 | } 155 | function deleterButton(deleter) { 156 | if(!deleter) { 157 | /* Identify a new deleter button with a data-hidder attribute*/ 158 | deleter = document.createElement('a'); 159 | deleter.setAttribute('data-hidder', "1"); 160 | } 161 | deleter.innerHTML = " ⊖ "; 162 | deleter.style.color = "#dc3545"; 163 | deleter.style.cursor = "pointer"; 164 | deleter.setAttribute("title","Delete/Remove this entry"); 165 | deleter.addEventListener("click", function () { 166 | decloner(this.parentElement); 167 | }); 168 | deleter.setAttribute('data-decloner', "1"); 169 | return deleter; 170 | } 171 | function displayOnly(el) { 172 | el.parentElement.querySelectorAll("div").forEach(function(eldiv) { 173 | eldiv.style.display = "block"; 174 | }) 175 | el.innerHTML = el.innerHTML.replaceAll('[]','[0]'); 176 | if(!el.querySelector("[data-hidder]")){ 177 | el.appendChild(deleterButton()); 178 | } 179 | } 180 | function cloner(el) { 181 | /* If the first div is invisible, this is a 182 | NOT required fieldset just display it and return */ 183 | if((!el.hasAttribute("data-required")) && el.parentElement.querySelector("div").style.display == "none") { 184 | return displayOnly(el); 185 | } 186 | let cloned = el.parentElement.cloneNode(true); 187 | if(cloned.querySelector("[data-hidder]")) 188 | cloned.querySelector("[data-hidder]").remove(); 189 | let i = parseInt(el.parentElement.getAttribute("data-counter") || "0"); 190 | let elx = cloned.querySelector(el.tagName); 191 | if(elx) { 192 | elx.innerHTML = elx.innerHTML.replace(/\[(\d+)\]/, function() { 193 | return "[" + String(i + 1) + "]"; 194 | }); 195 | elx.parentElement.setAttribute("data-cid", String(i + 1)); 196 | elx.parentElement.removeAttribute("data-counter"); 197 | let ela = elx.querySelector('a'); 198 | if(ela) { 199 | ela = deleterButton(ela); 200 | } 201 | 202 | } 203 | el.parentElement.setAttribute("data-counter", String(i + 1)); 204 | el.parentElement.parentElement.appendChild(cloned); 205 | cloned.querySelectorAll('input,select:not([data-exclude])').forEach(elToField); 206 | hideDecloners(el.parentElement.parentElement); 207 | } 208 | 209 | function regexUpgrade(regex) { 210 | /*Upgrade regex that is invalid for v-mode to a compatible mode */ 211 | try { 212 | const _ = new RegExp(regex,"v"); 213 | return regex; 214 | } catch(err) { 215 | let nregex = regex; 216 | /* dash only in character classes otherwise but it in brackets escaped */ 217 | const vInvalid = /([^a-zA-Z0-9\\])\-([^a-zA-Z0-9])/g; 218 | 219 | Array.from(new Set(regex.match(vInvalid))).forEach(function(bok) { 220 | nregex = nregex.replaceAll(bok,bok.replaceAll('-','[\\-]')); 221 | }); 222 | try { 223 | new RegExp(nregex,"v"); 224 | console.log("Replacing " + regex + " due to Error " + err + 225 | "Now upgraded to " + nregex); 226 | return nregex; 227 | } catch (err) { 228 | console.error("Cannot upgrade this " + regex + " due to Error " + err + 229 | "Now upgraded to " + nregex); 230 | return ""; 231 | } 232 | } 233 | } 234 | 235 | 236 | 237 | function createInputFromProperty(key, property, required, schema) { 238 | const wrapper = document.createElement('div'); 239 | if (property.$ref) { 240 | property = resolveRef(property.$ref, property, schema); 241 | } 242 | wrapper.setAttribute("data-key", key); 243 | wrapper.setAttribute("data-type", property.type); 244 | const label = document.createElement('label'); 245 | label.setAttribute('for', key); 246 | label.textContent = property.title || key; 247 | wrapper.appendChild(label); 248 | wrapper.appendChild (document.createTextNode (" ")); 249 | /* If anyof or allof is setup some form of this field(set) is required*/ 250 | if(property.items) 251 | ["anyOf", "allOf", "oneOf"].forEach(yOf => { 252 | if(yOf in property.items) { 253 | required = true; 254 | if(!(yOf in property)) 255 | property["validator"] = {} 256 | property["validator"][yOf] = property.items[yOf]; 257 | } 258 | }); 259 | let input; 260 | if (property.type === 'string') { 261 | input = document.createElement('input'); 262 | input.setAttribute('type', property.format === 'email' ? 'email' : 'text'); 263 | } else if (property.type === 'integer' || property.type === 'number') { 264 | input = document.createElement('input'); 265 | input.setAttribute('type', 'number'); 266 | } else if (property.type === 'boolean') { 267 | input = document.createElement('input'); 268 | input.setAttribute('type', 'checkbox'); 269 | } else if ((property.type === 'array') && (property.items)) { 270 | if (property.items.enum) { 271 | input = document.createElement('select'); 272 | input.setAttribute('multiple', true); 273 | property.items.enum.forEach(value => input.appendChild(new Option(value,value))); 274 | } else { 275 | label.style.display = "none"; 276 | const fieldset = document.createElement('fieldset'); 277 | const legend = document.createElement('legend'); 278 | if(required) 279 | legend.innerHTML = (property.title || key) + ' [0]' ; 280 | else 281 | legend.innerHTML = (property.title || key) + ' []' ; 282 | const adder = document.createElement('a'); 283 | adder.style.color = "#007bff"; 284 | adder.style.cursor = "pointer"; 285 | adder.setAttribute("title","Add new entry for " + (property.title || key)); 286 | adder.addEventListener("click", function () { 287 | cloner(this.parentElement); 288 | }); 289 | adder.setAttribute('data-cloner', "1"); 290 | adder.innerHTML = ' ⊕ '; 291 | fieldset.setAttribute("data-property", key); 292 | fieldset.setAttribute("data-counter", "0"); 293 | fieldset.setAttribute("data-cid", "0"); 294 | legend.appendChild(adder); 295 | fieldset.appendChild(legend); 296 | if(property.items.oneOf) { 297 | const selectEl = document.createElement('select'); 298 | selectEl.setAttribute("data-exclude","oneOf"); 299 | const classBase = label.textContent + "oneOf"; 300 | selectEl.setAttribute("data-classBase", classBase); 301 | const created = {}; 302 | property.items.oneOf.forEach((item,i) => { 303 | const className = classBase + String(i); 304 | if(item.required) { 305 | selectEl.appendChild(new Option("Valid Formats: " + String(i), className)); 306 | item.required.forEach(subKey => { 307 | if(subKey in property.items.properties) { 308 | if (!(subKey in created)) { 309 | let subItem = property.items.properties[subKey]; 310 | /* First set of inputs will be default required i == 0 */ 311 | const subInput = createInputFromProperty(subKey, subItem, i < 1, schema); 312 | created[subKey] = subInput; 313 | } 314 | } 315 | created[subKey].querySelectorAll('input') 316 | .forEach(x => x.classList.add(classBase,className)); 317 | }); 318 | selectEl.addEventListener( 319 | 'change', 320 | function() { 321 | let classBase = this.getAttribute("data-classBase"); 322 | document.querySelectorAll("." + classBase).forEach(removeRequired); 323 | let className = this.options[this.selectedIndex].value; 324 | document.querySelectorAll("." + className).forEach(makeRequired); 325 | }, 326 | false 327 | ); 328 | } else { 329 | selectEl.appendChild(new Option("Schema Formats: " + String(i), className)); 330 | if(item.$ref) 331 | item = resolveRef(item.$ref, item, schema); 332 | let subKey = key + String(i); 333 | /* item if it got resolved form $ref may have "required" fields*/ 334 | const subRequired = item.required && item.required.includes(subKey); 335 | created[subKey] = createInputFromProperty("", item, false, schema); 336 | created[subKey].classList.add(classBase,className); 337 | if(i > 0) 338 | created[subKey].style.display = "none"; 339 | selectEl.addEventListener( 340 | 'change', 341 | function() { 342 | let classBase = this.getAttribute("data-classBase"); 343 | document.querySelectorAll("." + classBase) 344 | .forEach( x => x.style.display = "none"); 345 | let className = this.options[this.selectedIndex].value; 346 | document.querySelectorAll("." + className) 347 | .forEach(x => x.style.display = "block"); 348 | }, 349 | false 350 | ); 351 | 352 | } 353 | }); 354 | /* Now add all the inputs */ 355 | Object.entries(created).forEach(function([_,x]) { fieldset.appendChild(x) }); 356 | fieldset.prepend(selectEl); 357 | } else { 358 | let subItem; 359 | if(property.items.$ref) { 360 | const subProperty = resolveRef(property.items.$ref, property.items, schema); 361 | let subKey = property.items.$ref.split('/').pop(); 362 | const subRequired = property.minItems && property.minItems > 0; 363 | subItem = createInputFromProperty(subKey, subProperty, subRequired, schema); 364 | } else { 365 | subItem = createInputFromProperty('[]',property.items, property.items.minItems && property.items.minItems > 0, schema); 366 | } 367 | fieldset.appendChild(subItem); 368 | } 369 | if (required) 370 | makeRequired(fieldset); 371 | wrapper.appendChild(fieldset); 372 | return wrapper; // return early because object fields are handled recursively 373 | } 374 | } else if (property.type === 'object') { 375 | label.style.display = "none"; 376 | // Recursively create form elements for nested objects 377 | const fieldset = document.createElement('fieldset'); 378 | const legend = document.createElement('legend'); 379 | legend.textContent = property.title || key; 380 | fieldset.appendChild(legend); 381 | if(property.properties) { 382 | Object.keys(property.properties).forEach(function(subKey) { 383 | let subProperty = property.properties[subKey]; 384 | if(subProperty.$ref) { 385 | subProperty = resolveRef(subProperty.$ref, subProperty, schema); 386 | } 387 | const subRequired = property.required && property.required.includes(subKey); 388 | const subInput = createInputFromProperty(subKey, subProperty, subRequired, schema); 389 | fieldset.appendChild(subInput); 390 | }); 391 | if (required) { 392 | makeRequired(fieldset); 393 | } 394 | wrapper.appendChild(fieldset); 395 | } 396 | return wrapper; // return early because object fields are handled recursively 397 | } else { 398 | input = document.createElement('input'); 399 | input.setAttribute('type', 'text'); // Fallback for unsupported types 400 | } 401 | input.setAttribute('name', key); 402 | if (property.enum) { 403 | if(property.enum.length > 1) { 404 | input = document.createElement('select'); 405 | input.appendChild(new Option("Select..","")); 406 | property.enum.forEach(value => input.appendChild(new Option(value,value))); 407 | } else { 408 | input.setAttribute('readonly',true); 409 | input.value = property.enum[0]; 410 | input.style.border = "1px solid #333"; 411 | input.style.background = "#eee"; 412 | } 413 | } 414 | if (required) 415 | makeRequired(input); 416 | if(property.pattern && regexUpgrade(property.pattern)) 417 | input.setAttribute("pattern", regexUpgrade(property.pattern)); 418 | if(property.description) 419 | input.setAttribute("title", property.description); 420 | wrapper.appendChild(input); 421 | if(property.examples) { 422 | let example = document.createElement('select'); 423 | example.setAttribute("data-exclude","example"); 424 | example.appendChild(new Option("Example entries:","")); 425 | property.examples.forEach(ex => example.appendChild(new Option(ex,ex))); 426 | example.style.marginLeft = "0.2em"; 427 | example.setAttribute("onchange","exampleFill(this)"); 428 | wrapper.appendChild(example); 429 | } 430 | return wrapper; 431 | } 432 | function exampleFill(el) { 433 | if(el.value) 434 | el.previousElementSibling.value = el.value; 435 | } 436 | function createFormFromSchema(schema, parentElement) { 437 | const form = document.createElement('div'); 438 | form.setAttribute('id', schema.title ? schema.title.toLowerCase().replace(/\s+/g, '-') + '-form' : 'dynamic-form'); 439 | if(schema.oneOf) { 440 | const selectEl = document.createElement('select'); 441 | selectEl.setAttribute("data-exclude","oneOf"); 442 | selectEl.addEventListener( 443 | 'change', 444 | function() { 445 | let show = document.getElementById(this.options[this.selectedIndex].value); 446 | if(show) { 447 | parentElement.querySelectorAll(".selectEl") 448 | .forEach( x => x.style.display = "none"); 449 | show.style.display = "block"; 450 | } 451 | }, 452 | false 453 | ); 454 | const definitions = schema.definitions; 455 | schema.oneOf.forEach((schema,i) => { 456 | /* If definitions exists copy them over to schema subschema*/ 457 | if(definitions) 458 | schema.definitions = definitions; 459 | const oneElement = document.createElement('div'); 460 | oneElement.id = schema.title || ('selectEl' + String(i)); 461 | if(i > 0) 462 | oneElement.style.display = "none"; 463 | oneElement.className = "selectEl"; 464 | parentElement.appendChild(oneElement); 465 | createFormFromSchema(schema, oneElement); 466 | selectEl.appendChild(new Option(oneElement.id, oneElement.id)); 467 | }); 468 | parentElement.prepend(selectEl); 469 | return; 470 | } 471 | if(schema.properties) { 472 | Object.keys(schema.properties).forEach(key => { 473 | let property = schema.properties[key]; 474 | 475 | // Resolve $ref if it exists 476 | if (property.$ref) { 477 | property = resolveRef(property.$ref, property, schema); 478 | } 479 | 480 | const required = schema.required && schema.required.includes(key); 481 | const inputElement = createInputFromProperty(key, property, required, schema); 482 | form.appendChild(inputElement); 483 | }); 484 | } 485 | parentElement.appendChild(form); 486 | /* Add field designation in Object-Oriented form */ 487 | parentElement.querySelectorAll('input,select:not([data-exclude])').forEach(elToField); 488 | /* Add field desgination i OO form to fieldset that are arrays */ 489 | parentElement.querySelectorAll("[data-counter='0']").forEach(elToField); 490 | /* Ensure not required fieldset are added only as needed*/ 491 | parentElement.querySelectorAll('fieldset:not([data-required])') 492 | .forEach(el => el.querySelector('div').style.display = "none"); 493 | 494 | } 495 | async function initializeForm(schemaUrl, elementId) { 496 | const schema = await fetchObj(schemaUrl); 497 | const dElement = document.getElementById(elementId); 498 | if (schema && dElement) { 499 | main.dElement = dElement; 500 | createFormFromSchema(schema, dElement); 501 | } else { 502 | document.getElementById(elementId).textContent = 'Failed to load schema.'; 503 | } 504 | } 505 | function toData() { 506 | let fobj = {}; 507 | main.dElement.querySelectorAll('input,select[data-path]:not([data-exclude])').forEach( function(el) { 508 | if(!el.checkVisibility()) 509 | return; 510 | let val = el.value; 511 | if(el.type == "checkbox") { 512 | if(el.checked) 513 | val = true; 514 | else 515 | val = false; 516 | } 517 | /* If val is empty or set to be False for a not required element */ 518 | if(!val) 519 | if(!el.hasAttribute("data-required")) 520 | return; 521 | let x = fobj; 522 | let prop = el.getAttribute("data-path"); 523 | console.log(x); 524 | if(!prop) 525 | return; 526 | let props = prop.split("."); 527 | if(!props.length) 528 | return; 529 | let fprop = props.pop(); 530 | for(var i=0; i x.style.display = "none"); 562 | } 563 | initializeForm(schemaUrl, elementId); 564 | main.populate = populate; 565 | main.toData = toData; 566 | return main; 567 | } 568 | -------------------------------------------------------------------------------- /ace-builds/src-min-noconflict/worker-json.js: -------------------------------------------------------------------------------- 1 | "no use strict";!function(e){function t(e,t){var n=e,r="";while(n){var i=t[n];if(typeof i=="string")return i+r;if(i)return i.location.replace(/\/*$/,"/")+(r||i.main||i.name);if(i===!1)return"";var s=n.lastIndexOf("/");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!="undefined"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:"log",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:"error",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf("!")!==-1){var r=n.split("!");return e.normalizeModule(t,r[0])+"!"+e.normalizeModule(t,r[1])}if(n.charAt(0)=="."){var i=t.split("/").slice(0,-1).join("/");n=(i?i+"/":"")+n;while(n.indexOf(".")!==-1&&s!=n){var s=n;n=n.replace(/^\.\//,"").replace(/\/\.\//,"/").replace(/[^\/]+\/\.\.\//,"")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error("worker.js require() accepts only (parentId, id) as arguments");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log("unable to load "+i);var o=t(i,e.require.tlns);return o.slice(-3)!=".js"&&(o+=".js"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!="string"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!="function"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=["require","exports","module"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.slice(0,r.length).map(function(t){switch(t){case"require":return i;case"exports":return e.exports;case"module":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require("ace/lib/event_emitter").EventEmitter,r=e.require("ace/lib/oop"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:"call",id:t,data:e})},this.emit=function(e,t){postMessage({type:"event",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error("Unknown command:"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}}(this),ace.define("ace/lib/oop",[],function(e,t,n){"use strict";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),ace.define("ace/range",[],function(e,t,n){"use strict";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return"Range: ["+this.start.row+"/"+this.start.column+"] -> ["+this.end.row+"/"+this.end.column+"]"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e=="object"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e=="object"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?tthis.end.column?1:0:ethis.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.rowt)var r={row:t+1,column:0};else if(this.start.row=0&&t.row=0&&t.column<=e[t.row].length}function s(e,t){t.action!="insert"&&t.action!="remove"&&r(t,"delta.action must be 'insert' or 'remove'"),t.lines instanceof Array||r(t,"delta.lines must be an Array"),(!t.start||!t.end)&&r(t,"delta.start/end must be an present");var n=t.start;i(e,t.start)||r(t,"delta.start must be contained in document");var s=t.end;t.action=="remove"&&!i(e,s)&&r(t,"delta.end must contained in document for 'remove' actions");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,"delta.range must match delta lines")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||"";switch(t.action){case"insert":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case"remove":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),ace.define("ace/lib/event_emitter",[],function(e,t,n){"use strict";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!="object"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;othis.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal("change",{old:i,value:r})},this.detach=function(){this.document.off("change",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on("change",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),ace.define("ace/document",[],function(e,t,n){"use strict";var r=e("./lib/oop"),i=e("./apply_delta").applyDelta,s=e("./lib/event_emitter").EventEmitter,o=e("./range").Range,u=e("./anchor").Anchor,a=function(e){this.$lines=[""],e.length===0?this.$lines=[""]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},"aaa".split(/a/).length===0?this.$split=function(e){return e.replace(/\r\n|\r/g,"\n").split("\n")}:this.$split=function(e){return e.split(/\r\n|\r|\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\r\n|\r|\n)/m);this.$autoNewLine=t?t[1]:"\n",this._signal("changeNewLineMode")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case"windows":return"\r\n";case"unix":return"\n";default:return this.$autoNewLine||"\n"}},this.$autoNewLine="",this.$newLineMode="auto",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal("changeNewLineMode")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e=="\r\n"||e=="\r"||e=="\n"},this.getLine=function(e){return this.$lines[e]||""},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||"").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn("Use of document.insertLines is deprecated. Use the insertFullLines method instead."),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn("Use of document.removeLines is deprecated. Use the removeFullLines method instead."),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn("Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead."),this.insertMergedLines(e,["",""])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:"insert",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e0,r=t=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:"remove",lines:["",""]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action=="insert";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4?this.$splitAndapplyLargeDelta(e,2e4):(i(this.$lines,e,t),this._signal("change",e))},this.$safeApplyDelta=function(e){var t=this.$lines.length;(e.action=="remove"&&e.start.row0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\s\s*/,i=/\s\s*$/;t.stringTrimLeft=function(e){return e.replace(r,"")},t.stringTrimRight=function(e){return e.replace(i,"")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n="0"&&i<="9")t+=i,a();if(i==="."){t+=".";while(a()&&i>="0"&&i<="9")t+=i}if(i==="e"||i==="E"){t+=i,a();if(i==="-"||i==="+")t+=i,a();while(i>="0"&&i<="9")t+=i,a()}e=+t;if(!isNaN(e))return e;u("Bad number")},l=function(){var e,t,n="",r;if(i==='"')while(a()){if(i==='"')return a(),n;if(i==="\\"){a();if(i==="u"){r=0;for(t=0;t<4;t+=1){e=parseInt(a(),16);if(!isFinite(e))break;r=r*16+e}n+=String.fromCharCode(r)}else{if(typeof s[i]!="string")break;n+=s[i]}}else{if(i=="\n"||i=="\r")break;n+=i}}u("Bad string")},c=function(){while(i&&i<=" ")a()},h=function(){switch(i){case"t":return a("t"),a("r"),a("u"),a("e"),!0;case"f":return a("f"),a("a"),a("l"),a("s"),a("e"),!1;case"n":return a("n"),a("u"),a("l"),a("l"),null}u("Unexpected '"+i+"'")},p,d=function(){var e=[];if(i==="["){a("["),c();if(i==="]")return a("]"),e;while(i){e.push(p()),c();if(i==="]")return a("]"),e;a(","),c()}}u("Bad array")},v=function(){var e,t={};if(i==="{"){a("{"),c();if(i==="}")return a("}"),t;while(i){e=l(),c(),a(":"),Object.hasOwnProperty.call(t,e)&&u('Duplicate key "'+e+'"'),t[e]=p(),c();if(i==="}")return a("}"),t;a(","),c()}}u("Bad object")};return p=function(){c();switch(i){case"{":return v();case"[":return d();case'"':return l();case"-":return f();default:return i>="0"&&i<="9"?f():h()}},function(e,t){var n;return o=e,r=0,i=" ",n=p(),c(),i&&u("Syntax error"),typeof t=="function"?function s(e,n){var r,i,o=e[n];if(o&&typeof o=="object")for(r in o)Object.hasOwnProperty.call(o,r)&&(i=s(o,r),i!==undefined?o[r]=i:delete o[r]);return t.call(e,n,o)}({"":n},""):n}}),ace.define("ace/mode/json_worker",[],function(e,t,n){"use strict";var r=e("../lib/oop"),i=e("../worker/mirror").Mirror,s=e("./json/json_parse"),o=t.JsonWorker=function(e){i.call(this,e),this.setTimeout(200)};r.inherits(o,i),function(){this.onUpdate=function(){var e=this.doc.getValue(),t=[];try{e&&s(e)}catch(n){var r=this.doc.indexToPosition(n.at-1);t.push({row:r.row,column:r.column,text:n.message,type:"error"})}this.sender.emit("annotate",t)}}.call(o.prototype)}) -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | CVE Services Client Interface 8 | 9 | 13 | 17 | 20 | 23 | 24 | 25 | 26 | 27 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 40 | 84 | 166 | 528 | 585 | 632 | 694 |
695 |
696 |
697 |
Demo of CVE 5.0 service client
698 | 754 |
755 |
757 |
758 | Year: 763 |
764 | 765 | 766 | 767 |
[No Records Found] --
768 |
769 | 770 |
771 | 772 | 773 |
Loading
774 |
775 |
776 |
777 |
778 |
779 |
780 |

781 | 782 | This website does NOT store any data or track usage. The code is freely available 783 | at GitHub 784 | 785 |

786 | 787 |
788 |
789 | 790 | 791 | 792 | 793 | -------------------------------------------------------------------------------- /cveIterface.js: -------------------------------------------------------------------------------- 1 | /* Clientlib, UI html, css and UI js all are version controlled */ 2 | const _version = "1.0.15"; 3 | const _tool = "CVE Services Client Interface "+_version; 4 | const _cna_template = { "descriptions": [ { "lang": "${descriptions.0.lang}", "value": "${descriptions.0.value}"} ] , "affected": [ { "versions": [{"version": "${affected.0.versions.0.version}"}], "product": "${affected.0.product}", "vendor": "${affected.0.vendor|client.orgobj.name}" } ],"references": [ { "name": "${references.0.name}", "url": "${references.0.url}" }], "providerMetadata": { "orgId": "${client.userobj.org_UUID}", "shortName": "${client.org}" } } 5 | const valid_states = {PUBLISHED: 1,RESERVED: 1, REJECTED: 1}; 6 | let store; 7 | let store_tag = "cveClient/"; 8 | /* User var to access client as window.client global var */ 9 | var client; 10 | function add_option(w,v,f,s) { 11 | $(w).append($('