├── .all-contributorsrc ├── .github └── workflows │ └── prettier.yaml ├── .gitignore ├── .husky └── pre-commit ├── .prettierrc ├── LICENSE ├── PrivacyPolicy.md ├── README.md ├── _locales ├── en │ └── messages.json └── zh_CN │ └── messages.json ├── css ├── filter.css └── style.css ├── data ├── ccfAbbrFull.js ├── ccfFullUrl.js ├── ccfRankAbbr.js ├── ccfRankDb.js ├── ccfRankFull.js ├── ccfRankUrl.js └── dataGen.js ├── icon ├── 128x128.png ├── 16x16.png ├── 24x24.png ├── 32x32.png └── 64x64.png ├── img ├── connectedpapers.png ├── dblp.png ├── load_unpacked.png ├── scholar.png ├── semanticscholar.png └── wos.png ├── js ├── apiCache.js ├── ccf.js ├── connectedpapers.js ├── dblp.js ├── fetchRank.js ├── filter.js ├── scholar.js ├── semanticscholar.js └── wos.js ├── lib └── jquery-3.5.1.min.js ├── manifest.json ├── package-lock.json ├── package.json └── script.js /.all-contributorsrc: -------------------------------------------------------------------------------- 1 | { 2 | "files": ["README.md"], 3 | "imageSize": 100, 4 | "commit": false, 5 | "contributors": [ 6 | { 7 | "login": "WenyanLiu", 8 | "name": "wyliu", 9 | "avatar_url": "https://avatars.githubusercontent.com/u/16554557?v=4", 10 | "profile": "https://scholar.google.com/citations?user=a8sqKFkAAAAJ", 11 | "contributions": ["ideas", "code", "data", "doc", "maintenance"] 12 | }, 13 | { 14 | "login": "kevyn-zhang", 15 | "name": "kevyn-zhang", 16 | "avatar_url": "https://avatars1.githubusercontent.com/u/73885971?v=4", 17 | "profile": "https://github.com/kevyn-zhang", 18 | "contributions": ["bug", "ideas"] 19 | }, 20 | { 21 | "login": "realstolz", 22 | "name": "Rong Chen", 23 | "avatar_url": "https://avatars2.githubusercontent.com/u/1779861?v=4", 24 | "profile": "http://ipads.se.sjtu.edu.cn/rong_chen", 25 | "contributions": ["bug"] 26 | }, 27 | { 28 | "login": "junwei-wang", 29 | "name": "Junwei Wang", 30 | "avatar_url": "https://avatars1.githubusercontent.com/u/866329?v=4", 31 | "profile": "http://jwa.ng", 32 | "contributions": ["platform"] 33 | }, 34 | { 35 | "login": "ifzh", 36 | "name": "iFzh", 37 | "avatar_url": "https://avatars0.githubusercontent.com/u/11475849?v=4", 38 | "profile": "https://github.com/ifzh", 39 | "contributions": ["bug", "ideas"] 40 | }, 41 | { 42 | "login": "linwhitehat", 43 | "name": "lin", 44 | "avatar_url": "https://avatars3.githubusercontent.com/u/20349381?v=4", 45 | "profile": "https://linwhitehat.github.io/", 46 | "contributions": ["ideas", "bug"] 47 | }, 48 | { 49 | "login": "zhuye88", 50 | "name": "YE ZHU", 51 | "avatar_url": "https://avatars.githubusercontent.com/u/19607512?v=4", 52 | "profile": "http://www.yezhu.com.au/", 53 | "contributions": ["bug"] 54 | }, 55 | { 56 | "login": "zshhans", 57 | "name": "zshhans", 58 | "avatar_url": "https://avatars.githubusercontent.com/u/25279261?v=4", 59 | "profile": "https://github.com/zshhans", 60 | "contributions": ["bug", "code"] 61 | }, 62 | { 63 | "login": "Fanchao-Qi", 64 | "name": "Fanchao Qi", 65 | "avatar_url": "https://avatars.githubusercontent.com/u/12222818?v=4", 66 | "profile": "https://github.com/Fanchao-Qi", 67 | "contributions": ["bug"] 68 | }, 69 | { 70 | "login": "purplewall1206", 71 | "name": "ppw", 72 | "avatar_url": "https://avatars.githubusercontent.com/u/10174153?v=4", 73 | "profile": "http://www.zi-c.wang", 74 | "contributions": ["code", "platform", "bug"] 75 | }, 76 | { 77 | "login": "neardws", 78 | "name": "Near", 79 | "avatar_url": "https://avatars.githubusercontent.com/u/23012163?v=4", 80 | "profile": "https://www.neardws.com", 81 | "contributions": ["platform"] 82 | }, 83 | { 84 | "login": "bo233", 85 | "name": "bo233", 86 | "avatar_url": "https://avatars.githubusercontent.com/u/31071399?v=4", 87 | "profile": "http://bo233.github.io", 88 | "contributions": ["platform"] 89 | }, 90 | { 91 | "login": "FunClip", 92 | "name": "Kai Chen", 93 | "avatar_url": "https://avatars.githubusercontent.com/u/23724147?v=4", 94 | "profile": "https://github.com/FunClip", 95 | "contributions": ["code", "maintenance", "bug"] 96 | }, 97 | { 98 | "login": "996787373", 99 | "name": "Time machine", 100 | "avatar_url": "https://avatars.githubusercontent.com/u/25929774?v=4", 101 | "profile": "https://github.com/996787373", 102 | "contributions": ["maintenance", "review"] 103 | }, 104 | { 105 | "login": "FlyingFog", 106 | "name": "FlyingFog", 107 | "avatar_url": "https://avatars.githubusercontent.com/u/39846119?v=4", 108 | "profile": "https://github.com/FlyingFog", 109 | "contributions": ["code", "bug", "data"] 110 | }, 111 | { 112 | "login": "ViTsing", 113 | "name": "ViTsing", 114 | "avatar_url": "https://avatars.githubusercontent.com/u/39085334?v=4", 115 | "profile": "https://github.com/ViTsing", 116 | "contributions": ["data"] 117 | }, 118 | { 119 | "login": "sdtsztom", 120 | "name": "Tang", 121 | "avatar_url": "https://avatars.githubusercontent.com/u/26901541?v=4", 122 | "profile": "https://github.com/sdtsztom", 123 | "contributions": ["data"] 124 | }, 125 | { 126 | "login": "ch3n9w", 127 | "name": "ch3n", 128 | "avatar_url": "https://avatars.githubusercontent.com/u/40637063?v=4", 129 | "profile": "https://github.com/ch3n9w", 130 | "contributions": ["platform"] 131 | }, 132 | { 133 | "login": "mra42", 134 | "name": "Marcel R. Ackermann", 135 | "avatar_url": "https://avatars.githubusercontent.com/u/29752535?v=4", 136 | "profile": "https://dagstuhl.de/ackermann", 137 | "contributions": ["code", "bug"] 138 | }, 139 | { 140 | "login": "dozed", 141 | "name": "Stefan Ollinger", 142 | "avatar_url": "https://avatars.githubusercontent.com/u/239058?v=4", 143 | "profile": "https://github.com/dozed", 144 | "contributions": ["code", "bug"] 145 | }, 146 | { 147 | "login": "KezhengLiu", 148 | "name": "KezhengLiu", 149 | "avatar_url": "https://avatars.githubusercontent.com/u/43874813?v=4", 150 | "profile": "https://github.com/KezhengLiu", 151 | "contributions": ["bug"] 152 | }, 153 | { 154 | "login": "Sumsky21", 155 | "name": "Sumsky21", 156 | "avatar_url": "https://avatars.githubusercontent.com/u/58537872?v=4", 157 | "profile": "https://sumsky.top/", 158 | "contributions": ["bug"] 159 | }, 160 | { 161 | "login": "lovelxc", 162 | "name": "lovelxc", 163 | "avatar_url": "https://avatars.githubusercontent.com/u/48879827?v=4", 164 | "profile": "https://github.com/lovelxc", 165 | "contributions": ["data"] 166 | }, 167 | { 168 | "login": "liushunyu", 169 | "name": "Shunyu Liu", 170 | "avatar_url": "https://avatars.githubusercontent.com/u/30792664?v=4", 171 | "profile": "https://liushunyu.github.io/", 172 | "contributions": ["code", "data"] 173 | }, 174 | { 175 | "login": "ravenxrz", 176 | "name": "Raven", 177 | "avatar_url": "https://avatars.githubusercontent.com/u/44746032?v=4", 178 | "profile": "https://ravenxrz.github.io", 179 | "contributions": ["ideas"] 180 | }, 181 | { 182 | "login": "chenyangyc", 183 | "name": "Chen Yang", 184 | "avatar_url": "https://avatars.githubusercontent.com/u/43921095?v=4", 185 | "profile": "https://chenyangyc.github.io", 186 | "contributions": ["code", "bug"] 187 | }, 188 | { 189 | "login": "MarkLee131", 190 | "name": "Kaixuan Li", 191 | "avatar_url": "https://avatars.githubusercontent.com/u/38575222?v=4", 192 | "profile": "https://kaixuanli-ecnu.github.io/", 193 | "contributions": ["data", "code"] 194 | }, 195 | { 196 | "login": "SeddonShen", 197 | "name": "Seddon", 198 | "avatar_url": "https://avatars.githubusercontent.com/u/64512212?v=4", 199 | "profile": "http://seddon.lol", 200 | "contributions": ["bug"] 201 | } 202 | ], 203 | "contributorsPerLine": 7, 204 | "projectName": "CCFrank4dblp", 205 | "projectOwner": "WenyanLiu", 206 | "repoType": "github", 207 | "repoHost": "https://github.com", 208 | "skipCi": true, 209 | "commitConvention": "angular", 210 | "commitType": "docs" 211 | } 212 | -------------------------------------------------------------------------------- /.github/workflows/prettier.yaml: -------------------------------------------------------------------------------- 1 | name: Continuous Integration 2 | 3 | on: 4 | pull_request: 5 | push: 6 | branches: 7 | - main 8 | 9 | jobs: 10 | prettier: 11 | runs-on: ubuntu-latest 12 | 13 | steps: 14 | - name: Checkout 15 | uses: actions/checkout@v3 16 | with: 17 | # Make sure the actual branch is checked out when running on pull requests 18 | ref: ${{ github.head_ref }} 19 | 20 | - name: Prettify code 21 | uses: creyD/prettier_action@v4.3 22 | with: 23 | prettier_version: 3.3.3 24 | prettier_options: --write 25 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # mac 2 | .DS_Store 3 | **/.DS_Store 4 | .DS_Store? 5 | 6 | # PyCharm 7 | .idea/ 8 | *.iml 9 | 10 | # Node.js 11 | node_modules/ 12 | -------------------------------------------------------------------------------- /.husky/pre-commit: -------------------------------------------------------------------------------- 1 | npx lint-staged 2 | -------------------------------------------------------------------------------- /.prettierrc: -------------------------------------------------------------------------------- 1 | {} 2 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019-2023 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp) 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /PrivacyPolicy.md: -------------------------------------------------------------------------------- 1 | # CCFrank 隐私权政策 2 | 3 | # CCFrank Privacy Policy 4 | 5 | 您使用 CCFrank 服务,即表示您信赖我们对您的信息的处理方式。我们深知这项责任事关重大,因此一直致力于保护您的信息,并让您拥有控制权。 6 | 7 | When you use our services, you’re trusting us with your information. We understand that this is a big responsibility and we work hard to protect your information and put you in control. 8 | 9 | 本隐私权政策旨在协助您了解我们会收集哪些信息、为什么收集这些信息,以及您如何更新、管理、导出和删除自己的信息。 10 | 11 | This Privacy Policy is meant to help you understand what information we collect, why we collect it and how you can update, manage, export and delete your information. 12 | 13 | --- 14 | 15 | How CCFrank collects, uses and shares user data? 16 | 17 | CCFrank reads the search results from dblp, Google Scholar, Connected Papers and WoS. 18 | 19 | CCFrank tags the papers with CCF ranks locally. 20 | 21 | CCFrank only requests the paper source from dblp search API. 22 | 23 | --- 24 | 25 | All parties the user data will be shared with: 26 | 27 | dblp search API. 28 | 29 | --- 30 | 31 | References 32 | 33 | 1. https://policies.google.com/privacy?hl=zh-CN 34 | 2. https://policies.google.com/privacy 35 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
wyliu 🤔 💻 🔣 📖 🚧 |
360 | kevyn-zhang 🐛 🤔 |
361 | Rong Chen 🐛 |
362 | Junwei Wang 📦 |
363 | iFzh 🐛 🤔 |
364 | lin 🤔 🐛 |
365 | YE ZHU 🐛 |
366 |
zshhans 🐛 💻 |
369 | Fanchao Qi 🐛 |
370 | ppw 💻 📦 🐛 |
371 | Near 📦 |
372 | bo233 📦 |
373 | Kai Chen 💻 🚧 🐛 |
374 | Time machine 🚧 👀 |
375 |
FlyingFog 💻 🐛 🔣 |
378 | ViTsing 🔣 |
379 | Tang 🔣 |
380 | ch3n 📦 |
381 | Marcel R. Ackermann 💻 🐛 |
382 | Stefan Ollinger 💻 🐛 |
383 | KezhengLiu 🐛 |
384 |
Sumsky21 🐛 |
387 | lovelxc 🔣 |
388 | Shunyu Liu 💻 🔣 |
389 | Raven 🤔 |
390 | Chen Yang 💻 🐛 |
391 | Kaixuan Li 🔣 💻 |
392 | Seddon 🐛 |
393 |
").addClass("ccf-tooltiptext").text(rankInfo.info)); 92 | } 93 | return span; 94 | }; 95 | -------------------------------------------------------------------------------- /js/connectedpapers.js: -------------------------------------------------------------------------------- 1 | /** 2 | * MIT License 3 | * 4 | * Copyright (c) 2019-2023 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp), purplewall1206 (https://github.com/purplewall1206), mra42 (https://github.com/mra42) 5 | */ 6 | 7 | const connectedpapers = {}; 8 | 9 | connectedpapers.rankSpanList = []; 10 | 11 | connectedpapers.run = function () { 12 | let url = window.location.pathname; 13 | window.onload = function () { 14 | setTimeout(function () { 15 | if (url.indexOf("/main") != -1) { 16 | connectedpapers.appendRank(); 17 | connectedpapers.appendRanks(); 18 | } 19 | }, 3000); 20 | }; 21 | }; 22 | 23 | connectedpapers.appendRank = function () { 24 | let element = $(".list-group-item-mod.minilist-main-paper.main"); 25 | let nodes = element.find(".horizontal-flexbox"); 26 | let titlenode = nodes[1]; 27 | let datanode = $(nodes[2]).find("div"); 28 | 29 | let title = titlenode.innerText; 30 | let author = datanode[0].innerText.split(/[\s.,]+/)[1]; 31 | let year = datanode[1].innerText; 32 | fetchRank($(titlenode).find("h5"), title, author, year, connectedpapers); 33 | }; 34 | 35 | connectedpapers.appendRanks = function () { 36 | let elements = $(".list-group-item-mod.minilist-list-entry"); 37 | elements.each(function (index) { 38 | let nodes = $(this).find(".horizontal-flexbox"); 39 | let titlenode = nodes[0]; 40 | let datanode = $(nodes[1]).find("div"); 41 | 42 | let title = titlenode.innerText; 43 | let author = datanode[0].innerText.split(/[\s.,]+/)[1]; 44 | let year = datanode[1].innerText; 45 | setTimeout(function () { 46 | fetchRank($(titlenode).find("h5"), title, author, year, connectedpapers); 47 | }, 100 * index); 48 | }); 49 | }; 50 | -------------------------------------------------------------------------------- /js/dblp.js: -------------------------------------------------------------------------------- 1 | /** 2 | * MIT License 3 | * 4 | * Copyright (c) 2019-2023 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp), FlyingFog (https://github.com/FlyingFog) 5 | */ 6 | 7 | const dblp = {}; 8 | 9 | dblp.rankSpanList = []; 10 | 11 | dblp.run = function () { 12 | let url = window.location.pathname; 13 | if (url.includes("/pid/")) { 14 | dblp.appendRanks(); 15 | } else if (url.includes("/db/")) { 16 | if (url.includes("/index.html")) { 17 | dblp.appendRank("h1"); 18 | } else { 19 | dblp.appendRank("#breadcrumbs > ul > li > span:nth-child(3) > a > span"); 20 | } 21 | } else { 22 | setInterval(function () { 23 | let message = $("#completesearch-publs > div > p.waiting"); 24 | if (message.css("display") == "none") { 25 | $(window).bind("popstate", function () { 26 | dblp.appendRanks(); 27 | }); 28 | dblp.appendRanks(); 29 | } 30 | }, 700); 31 | } 32 | }; 33 | 34 | dblp.appendRanks = function () { 35 | let elements = $("cite > a"); 36 | elements.each(function () { 37 | let element = $(this); 38 | let source = element.attr("href"); 39 | if (source.length != 0 && !element.next().hasClass("ccf-rank")) { 40 | for (let getRankSpan of dblp.rankSpanList) { 41 | let issueName = element.find("span[itemprop=issueNumber]").text(); 42 | if (issueName.length != 0 && isNaN(issueName)) { 43 | var abbrName = ccf.abbrFull[issueName]; 44 | if (typeof abbrName != "undefined") { 45 | element.after(getRankSpan(issueName, "abbr")); 46 | continue; 47 | } 48 | } 49 | 50 | let urls = source.substring( 51 | source.indexOf("/db/") + 3, 52 | source.lastIndexOf(".html"), 53 | ); 54 | var pattern = /[0-9]{1,4}(-[0-9]{1,4})?$/; 55 | if (pattern.test(urls)) { 56 | urls = urls.replace(pattern, ""); 57 | } else { 58 | urls = ""; 59 | } 60 | element.after(getRankSpan(urls, "url")); 61 | } 62 | } 63 | }); 64 | }; 65 | 66 | dblp.appendRank = function (selector) { 67 | let element = $(selector); 68 | let headline = window.location.pathname; 69 | if (headline.length != 0) { 70 | for (let getRankSpan of dblp.rankSpanList) { 71 | let urls = headline.substring( 72 | headline.indexOf("/db/") + 3, 73 | headline.lastIndexOf("/"), 74 | ); 75 | url = ccf.rankDb[urls]; 76 | element.after(getRankSpan(url, "url")); 77 | } 78 | } 79 | }; 80 | -------------------------------------------------------------------------------- /js/fetchRank.js: -------------------------------------------------------------------------------- 1 | /** 2 | * MIT License 3 | * 4 | * Copyright (c) 2019-2023 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp), FlyingFog (https://github.com/FlyingFog), mra42 (https://github.com/mra42), dozed (https://github.com/dozed) 5 | */ 6 | 7 | function fetchRank(node, title, authorA, year, site) { 8 | const manifest = chrome.runtime.getManifest(); 9 | const version = manifest.version; 10 | 11 | let query_url = 12 | "https://dblp.org/search/publ/api?q=" + 13 | encodeURIComponent(title + " author:" + authorA) + 14 | "&format=json&app=CCFrank4dblp_" + 15 | version; 16 | 17 | let cached = apiCache.getItem(query_url); 18 | // console.log("cached: ", cached); 19 | if (cached) fetchFromCache(cached, node, title, authorA, year, site); 20 | else fetchFromDblpApi(query_url, node, title, authorA, year, site); 21 | } 22 | 23 | function fetchFromCache(cached, node, title, authorA, year, site) { 24 | console.debug('fetch from cache: %s (%s) "%s"', authorA, year, title); 25 | 26 | let dblp_url = cached.dblp_url; 27 | let resp = cached.resp; 28 | let resp_flag = cached.flag; 29 | // console.log("dblp_url: ", dblp_url); 30 | 31 | //Find a new vul: rankDB lacks of `tacas` etc., but it does occur in file `dataGen`. 32 | if (typeof dblp_url == "undefined" && resp_flag != false) { 33 | dblp_abbr = resp.hit[0].info.number; 34 | if (typeof dblp_abbr != "undefined" && isNaN(dblp_abbr)) { 35 | // console.log("dblp_abbr: ", dblp_abbr); 36 | } else { 37 | dblp_abbr = resp.hit[0].info.venue; 38 | } 39 | 40 | for (let getRankSpan of site.rankSpanList) { 41 | // console.log("with abbr"); 42 | $(node).after(getRankSpan(dblp_abbr, "abbr")); 43 | } 44 | } else if (dblp_url == "/journals/pacmpl/pacmpl") { 45 | // @kaixuan: Here, we need to process the four PL confs (oopsla, popl, pldi, and icfp) in two branches. 46 | // Details can be accessed at the same location in the `fetchFromDblpApi` function. 47 | let number_raw = resp.hit[0]?.info?.number; // may miss the number info in some cases, e.g., recently publised papers 48 | let number = number_raw ? number_raw.toString().toLowerCase() : ""; 49 | 50 | // a hacky way to handle the missing number issue 51 | // travese the resp.hit array to find a element with number info 52 | if (number == "") { 53 | for (let i = 0; i < resp["@sent"]; i++) { 54 | let number_raw = resp.hit[i]?.info?.number; 55 | if (number_raw) { 56 | number = number_raw.toString().toLowerCase(); 57 | break; 58 | } 59 | } 60 | } else { 61 | // console.log("number is not empty"); 62 | } 63 | 64 | if (number == "oopsla1" || number == "oopsla2" || number == "oopsla") { 65 | // previously, the number is "oopsla", now it is "oopsla1" or "oopsla2" due to the two cycles of oopsla 66 | dblp_url = "/conf/oopsla/oopsla"; 67 | } else if (number == "popl") { 68 | dblp_url = "/conf/popl/popl"; 69 | } else if (number == "pldi") { 70 | dblp_url = "/conf/pldi/pldi"; 71 | } else if (number == "icfp") { 72 | dblp_url = "/conf/icfp/icfp"; 73 | // console.log("already enter this branch"); 74 | } else { 75 | // console.log("number is not in the list"); 76 | } 77 | 78 | for (let getRankSpan of site.rankSpanList) { 79 | // console.log("with url"); 80 | $(node).after(getRankSpan(dblp_url, "url")); 81 | } 82 | } else { 83 | // console.log("dblp_url is not empty"); 84 | for (let getRankSpan of site.rankSpanList) { 85 | // console.log("with url"); 86 | $(node).after(getRankSpan(dblp_url, "url")); 87 | } 88 | } 89 | } 90 | 91 | function fetchFromDblpApi(query_url, node, title, authorA, year, site) { 92 | console.debug('fetch from API: %s (%s) "%s"', authorA, year, title); 93 | console.debug("query url: %s", query_url); 94 | 95 | var xhr = new XMLHttpRequest(); 96 | xhr.open("GET", query_url, true); 97 | var resp_flag = true; 98 | xhr.onreadystatechange = function () { 99 | if (xhr.readyState == 4) { 100 | var dblp_url = ""; 101 | var resp = JSON.parse(xhr.responseText).result.hits; 102 | if (resp["@total"] == 0) { 103 | dblp_url == ""; 104 | resp_flag = false; 105 | } else if (resp["@total"] == 1) { 106 | url = resp.hit[0].info.url; 107 | dblp_url = url.substring( 108 | url.indexOf("/rec/") + 4, 109 | url.lastIndexOf("/"), 110 | ); 111 | } else { 112 | for (var h = 0; h < resp["@sent"]; h++) { 113 | info = resp.hit[h].info; 114 | 115 | var cur_venue = info.type; 116 | if (cur_venue == "Informal Publications") continue; 117 | 118 | if (Array.isArray(info.authors.author)) { 119 | author_1st = info.authors.author[0].text; 120 | } else { 121 | author_1st = info.authors.author.text; 122 | } 123 | year_fuzzy = info.year; 124 | year_last_check = 0; 125 | if ( 126 | Math.abs(Number(year) - year_fuzzy) <= 1 && 127 | // && author_1st.toLowerCase().split(" ").indexOf(authorA.toLowerCase()) != -1 128 | author_1st.toLowerCase().split(" ") && 129 | year_fuzzy != year_last_check 130 | ) { 131 | year_last_check = year_fuzzy; 132 | url = resp.hit[h].info.url; 133 | dblp_url_last_check = url.substring( 134 | url.indexOf("/rec/") + 4, 135 | url.lastIndexOf("/"), 136 | ); 137 | if (year_fuzzy == year + 1) { 138 | dblp_url = dblp_url_last_check; 139 | } else if (year_fuzzy == year) { 140 | dblp_url = dblp_url_last_check; 141 | break; 142 | } else { 143 | if (dblp_url == "") { 144 | dblp_url = dblp_url_last_check; 145 | } 146 | } 147 | } 148 | } 149 | } 150 | dblp_url = ccf.rankDb[dblp_url]; 151 | apiCache.setItem(query_url, { 152 | dblp_url: dblp_url, 153 | resp: resp, 154 | flag: resp_flag, 155 | }); 156 | 157 | //Find a new vul: rankDB lacks of `tacas` etc., but it does occur in file `dataGen`. 158 | if (typeof dblp_url == "undefined" && resp_flag != false) { 159 | dblp_abbr = resp.hit[0].info.number; 160 | if (typeof dblp_abbr != "undefined" && isNaN(dblp_abbr)) { 161 | } else { 162 | dblp_abbr = resp.hit[0].info.venue; 163 | } 164 | for (let getRankSpan of site.rankSpanList) { 165 | // console.log("with abbr"); 166 | $(node).after(getRankSpan(dblp_abbr, "abbr")); 167 | } 168 | } 169 | // @kaixuan: Here, we need to process the four PL confs (oopsla, popl, pldi, and icfp) in two branches. 170 | // They are wrongly recognized as journals in the dblp api since they are published in PACMPL. 171 | // So, we need to parse the number info from the response and determine the dblp_url accordingly. 172 | // The same logic is applied to func `fetchFromCache`. 173 | else if (dblp_url == "/journals/pacmpl/pacmpl") { 174 | // we need to process the confs including oopsla, popl, and pldi in the same way 175 | let number_raw = resp.hit[0]?.info?.number; // may miss the number info in some cases, e.g., recently publised papers 176 | let number = number_raw ? number_raw.toString().toLowerCase() : ""; 177 | 178 | // a hacky way to handle the missing number issue 179 | // travese the resp.hit array to find a element with number info 180 | if (number == "") { 181 | for (let i = 0; i < resp["@sent"]; i++) { 182 | let number_raw = resp.hit[i]?.info?.number; 183 | if (number_raw) { 184 | number = number_raw.toString().toLowerCase(); 185 | break; 186 | } 187 | } 188 | } 189 | 190 | if (number == "oopsla1" || number == "oopsla2") { 191 | dblp_url = "/conf/oopsla/oopsla"; 192 | } else if (number == "popl") { 193 | dblp_url = "/conf/popl/popl"; 194 | } else if (number == "pldi") { 195 | dblp_url = "/conf/pldi/pldi"; 196 | } else if (number == "icfp") { 197 | dblp_url = "/conf/icfp/icfp"; 198 | } else { 199 | // console.log("number is not in the list"); 200 | } 201 | 202 | for (let getRankSpan of site.rankSpanList) { 203 | // console.log("with url"); 204 | $(node).after(getRankSpan(dblp_url, "url")); 205 | } 206 | } else { 207 | for (let getRankSpan of site.rankSpanList) { 208 | // console.log("with url"); 209 | $(node).after(getRankSpan(dblp_url, "url")); 210 | } 211 | } 212 | } 213 | // for (let getRankSpan of site.rankSpanList) { 214 | // // console.log("with abbr"); 215 | // $(node).after(getRankSpan(dblp_abbr, "abbr")); 216 | // } 217 | else { 218 | for (let getRankSpan of site.rankSpanList) { 219 | // console.log("with abbr"); 220 | $(node).after(getRankSpan(dblp_abbr, "abbr")); // I am not sure the difference between "abbr" and "url" 221 | } 222 | } 223 | }; 224 | xhr.send(); 225 | } 226 | -------------------------------------------------------------------------------- /js/filter.js: -------------------------------------------------------------------------------- 1 | /** 2 | * MIT License 3 | * 4 | * Copyright (c) 2019-2024 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp) 5 | */ 6 | 7 | const filter = { 8 | currentFilter: "ALL", 9 | processedEntries: new Set(), 10 | 11 | init() { 12 | if (!window.location.hostname.startsWith("dblp")) { 13 | return; 14 | } 15 | 16 | this.createFilterButtons(); 17 | this.bindEvents(); 18 | this.setupInfiniteScrollHandler(); 19 | }, 20 | 21 | createFilterButtons() { 22 | const filterDiv = document.createElement("div"); 23 | filterDiv.className = "ccf-filter"; 24 | filterDiv.innerHTML = ` 25 | 26 | 27 | 28 | 29 | `; 30 | document.body.appendChild(filterDiv); 31 | }, 32 | 33 | setupInfiniteScrollHandler() { 34 | const observer = new IntersectionObserver((entries) => { 35 | entries.forEach((entry) => { 36 | if (entry.isIntersecting) { 37 | this.applyFilter(true); 38 | } 39 | }); 40 | }); 41 | 42 | const trigger = document.querySelector("#completesearch-publs"); 43 | if (trigger) { 44 | observer.observe(trigger); 45 | } 46 | 47 | window.addEventListener( 48 | "scroll", 49 | this.debounce(() => { 50 | this.applyFilter(true); 51 | }, 200), 52 | ); 53 | }, 54 | 55 | applyFilter(preserveExisting = false) { 56 | const entries = document.querySelectorAll( 57 | "#completesearch-publs > div > ul > li", 58 | ); 59 | entries.forEach((entry) => { 60 | const entryId = entry.querySelector("a")?.href || entry.innerHTML; 61 | if (this.processedEntries.has(entryId) && preserveExisting) { 62 | return; 63 | } 64 | 65 | this.processedEntries.add(entryId); 66 | 67 | const hasCCFC = entry.textContent.includes("CCF C"); 68 | const hasCCFB = entry.textContent.includes("CCF B"); 69 | const hasCCFA = entry.textContent.includes("CCF A"); 70 | 71 | let shouldShow = false; 72 | 73 | if (this.currentFilter === "ALL") { 74 | shouldShow = true; 75 | } else if (this.currentFilter === "C" && hasCCFC) { 76 | shouldShow = true; 77 | } else if (this.currentFilter === "B" && hasCCFB) { 78 | shouldShow = true; 79 | } else if (this.currentFilter === "A" && hasCCFA) { 80 | shouldShow = true; 81 | } 82 | 83 | const currentlyVisible = entry.style.display !== "none"; 84 | if (currentlyVisible !== shouldShow || !preserveExisting) { 85 | entry.style.display = shouldShow ? "" : "none"; 86 | } 87 | }); 88 | }, 89 | 90 | debounce(func, wait) { 91 | let timeout; 92 | return function executedFunction(...args) { 93 | const later = () => { 94 | clearTimeout(timeout); 95 | func(...args); 96 | }; 97 | clearTimeout(timeout); 98 | timeout = setTimeout(later, wait); 99 | }; 100 | }, 101 | 102 | bindEvents() { 103 | document.querySelector(".ccf-filter").addEventListener("click", (e) => { 104 | if (e.target.tagName === "BUTTON") { 105 | document.querySelectorAll(".ccf-filter button").forEach((btn) => { 106 | btn.classList.remove("active"); 107 | }); 108 | e.target.classList.add("active"); 109 | 110 | this.currentFilter = e.target.dataset.rank; 111 | this.applyFilter(false); 112 | } 113 | }); 114 | }, 115 | }; 116 | -------------------------------------------------------------------------------- /js/scholar.js: -------------------------------------------------------------------------------- 1 | /** 2 | * MIT License 3 | * 4 | * Copyright (c) 2019-2023 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp), mra42 (https://github.com/mra42) 5 | */ 6 | 7 | const scholar = {}; 8 | 9 | scholar.rankSpanList = []; 10 | 11 | scholar.run = function () { 12 | let url = window.location.pathname; 13 | if (url == "/scholar") { 14 | scholar.appendRank(); 15 | } else if (url == "/citations") { 16 | scholar.appendRanks(); // 页面加载时先处理一次作者主页上的条目 17 | scholar.observeCitations(); // 然后设置观察者以处理动态加载的条目 18 | } 19 | }; 20 | 21 | scholar.appendRank = function () { 22 | let elements = $("#gs_res_ccl_mid > div > div.gs_ri"); 23 | elements.each(function (index) { 24 | let node = $(this).find("h3 > a"); 25 | if (!node.next().hasClass("ccf-rank")) { 26 | let title = node.text(); 27 | let data = $(this) 28 | .find("div.gs_a") 29 | .text() 30 | .replace(/[\,\-\…]/g, "") 31 | .split(" "); 32 | let author = data[1]; 33 | let year = data.slice(-3)[0]; 34 | setTimeout(function () { 35 | fetchRank(node, title, author, year, scholar); 36 | }, 100 * index); 37 | } 38 | }); 39 | }; 40 | 41 | scholar.observeCitations = function () { 42 | console.debug("Start citations ..."); 43 | const observer = new MutationObserver((mutationsList, observer) => { 44 | for (const mutation of mutationsList) { 45 | if (mutation.type === "childList" && mutation.addedNodes.length > 0) { 46 | // 检查是否有新的文献项被添加到列表 47 | scholar.appendRanks(); 48 | } 49 | } 50 | }); 51 | 52 | // 开始观察文献列表的变化 53 | const targetNode = document.getElementById("gsc_a_b"); 54 | if (targetNode) { 55 | observer.observe(targetNode, { childList: true, subtree: true }); 56 | } 57 | }; 58 | 59 | scholar.appendRanks = function () { 60 | let elements = $("tr.gsc_a_tr"); 61 | elements.each(function (index) { 62 | let node = $(this).find("td.gsc_a_t > a").first(); 63 | if (!node.next().hasClass("ccf-rank") && !$(this).hasClass("ccf-ranked")) { 64 | let title = node.text(); 65 | let author = $(this) 66 | .find("div.gs_gray")[0] 67 | .innerText.replace(/[\,\…]/g, "") 68 | .split(" ")[1]; 69 | let year = $(this).find("td.gsc_a_y").text(); 70 | $(this).addClass("ccf-ranked"); 71 | setTimeout(function () { 72 | fetchRank(node, title, author, year, scholar); 73 | }, 100 * index); 74 | } 75 | }); 76 | }; 77 | -------------------------------------------------------------------------------- /js/semanticscholar.js: -------------------------------------------------------------------------------- 1 | /** 2 | * MIT License 3 | * 4 | * Copyright (c) 2019-2023 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp) 5 | */ 6 | 7 | const semanticscholar = {}; 8 | 9 | semanticscholar.rankSpanList = []; 10 | 11 | semanticscholar.run = function () { 12 | let url = window.location.pathname; 13 | setInterval(function () { 14 | $(window).bind("popstate", function () { 15 | semanticscholar.appendRanks(); 16 | }); 17 | semanticscholar.appendRanks(); 18 | }, 700); 19 | }; 20 | 21 | semanticscholar.appendRanks = function () { 22 | let elements = $(".cl-paper-venue"); 23 | elements.each(function () { 24 | let element = $(this); 25 | let source = element[0].innerText; 26 | if (source.length != 0 && !element.next().hasClass("ccf-rank")) { 27 | for (let getRankSpan of semanticscholar.rankSpanList) { 28 | if (source.includes("(")) { 29 | source = source.substring( 30 | source.indexOf("(") + 1, 31 | source.indexOf(")"), 32 | ); 33 | } 34 | if (source.includes("'")) { 35 | source = source.substring(0, source.indexOf("'")).trim(); 36 | } 37 | element.after(getRankSpan(source, "abbr")); 38 | } 39 | } 40 | }); 41 | }; 42 | 43 | semanticscholar.appendRank = function (selector) { 44 | let element = $(selector); 45 | let headline = window.location.pathname; 46 | if (headline.length != 0) { 47 | for (let getRankSpan of dblp.rankSpanList) { 48 | let urls = headline.substring( 49 | headline.indexOf("/db/") + 3, 50 | headline.lastIndexOf("/"), 51 | ); 52 | url = ccf.rankDb[urls]; 53 | element.after(getRankSpan(url, "url")); 54 | } 55 | } 56 | }; 57 | -------------------------------------------------------------------------------- /js/wos.js: -------------------------------------------------------------------------------- 1 | /** 2 | * MIT License 3 | * 4 | * Copyright (c) 2019-2023 WenyanLiu (https://github.com/WenyanLiu/CCFrank4dblp), Kai Chen (https://github.com/FunClip) 5 | */ 6 | 7 | const wos = {}; 8 | 9 | wos.rankSpanList = []; 10 | 11 | wos.run = function () { 12 | setInterval(function () { 13 | $(window).bind("popstate", function () { 14 | wos.appendRanks(); 15 | }); 16 | wos.appendRanks(); 17 | }, 700); 18 | }; 19 | 20 | wos.appendRanks = function () { 21 | $(".summary-source-title-link[lang='en']").each(function () { 22 | let node = $(this); 23 | if (!node.next().hasClass("ccf-rank")) { 24 | for (let getRankSpan of wos.rankSpanList) { 25 | let publication = node.text(); 26 | node.after(getRankSpan(publication, "publication")); 27 | } 28 | } 29 | }); 30 | $(".summary-source-title[lang='en']").each(function () { 31 | let node = $(this); 32 | if (!node.next().hasClass("ccf-rank")) { 33 | for (let getRankSpan of wos.rankSpanList) { 34 | let publication = node.text(); 35 | node.after(getRankSpan(publication, "publication")); 36 | } 37 | } 38 | }); 39 | $("[name='conf_title']").each(function () { 40 | let node = $(this); 41 | if (!node.next().hasClass("ccf-rank")) { 42 | for (let getRankSpan of wos.rankSpanList) { 43 | let meeting = ""; 44 | let options = node.text().match(/\((.+?)\)/g); 45 | let items = []; 46 | if (options) { 47 | for (let m of options) { 48 | let short_name = m.substring(1, m.length - 1).split(/\s+/); 49 | let tmp_name = []; 50 | for (let name of short_name) { 51 | if (name.match(/^[0-9]*$/)) { 52 | continue; 53 | } else { 54 | tmp_name.push(name); 55 | } 56 | } 57 | meeting = tmp_name.join(" "); 58 | items.push(getRankSpan(meeting, "meeting")); 59 | } 60 | } 61 | 62 | if (meeting == "") { 63 | items.push(getRankSpan(meeting, "meeting")); 64 | } 65 | node.after(items); 66 | } 67 | } 68 | }); 69 | }; 70 | -------------------------------------------------------------------------------- /manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "__MSG_extName__", 3 | "version": "4.5.2", 4 | "description": "__MSG_extDesc__", 5 | "manifest_version": 3, 6 | "default_locale": "en", 7 | "icons": { 8 | "16": "icon/16x16.png", 9 | "24": "icon/24x24.png", 10 | "32": "icon/32x32.png", 11 | "64": "icon/64x64.png", 12 | "128": "icon/128x128.png" 13 | }, 14 | "action": { 15 | "default_icon": { 16 | "16": "icon/16x16.png", 17 | "24": "icon/24x24.png", 18 | "32": "icon/32x32.png" 19 | } 20 | }, 21 | "content_scripts": [ 22 | { 23 | "matches": [ 24 | "https://dblp.org/*", 25 | "https://dblp.uni-trier.de/*", 26 | "https://dblp2.uni-trier.de/*", 27 | "https://dblp.dagstuhl.de/*", 28 | "https://scholar.google.ae/*", 29 | "https://scholar.google.at/*", 30 | "https://scholar.google.be/*", 31 | "https://scholar.google.bg/*", 32 | "https://scholar.google.ca/*", 33 | "https://scholar.google.cat/*", 34 | "https://scholar.google.ch/*", 35 | "https://scholar.google.cl/*", 36 | "https://scholar.google.co.cr/*", 37 | "https://scholar.google.co.hu/*", 38 | "https://scholar.google.co.id/*", 39 | "https://scholar.google.co.il/*", 40 | "https://scholar.google.co.in/*", 41 | "https://scholar.google.co.jp/*", 42 | "https://scholar.google.co.kr/*", 43 | "https://scholar.google.co.nz/*", 44 | "https://scholar.google.co.th/*", 45 | "https://scholar.google.co.uk/*", 46 | "https://scholar.google.co.ve/*", 47 | "https://scholar.google.co.za/*", 48 | "https://scholar.google.com/*", 49 | "https://scholar.google.com.ar/*", 50 | "https://scholar.google.com.au/*", 51 | "https://scholar.google.com.bo/*", 52 | "https://scholar.google.com.br/*", 53 | "https://scholar.google.com.co/*", 54 | "https://scholar.google.com.cu/*", 55 | "https://scholar.google.com.do/*", 56 | "https://scholar.google.com.ec/*", 57 | "https://scholar.google.com.eg/*", 58 | "https://scholar.google.com.gr/*", 59 | "https://scholar.google.com.gt/*", 60 | "https://scholar.google.com.hk/*", 61 | "https://scholar.google.com.ly/*", 62 | "https://scholar.google.com.mx/*", 63 | "https://scholar.google.com.my/*", 64 | "https://scholar.google.com.ni/*", 65 | "https://scholar.google.com.pa/*", 66 | "https://scholar.google.com.pe/*", 67 | "https://scholar.google.com.ph/*", 68 | "https://scholar.google.com.pk/*", 69 | "https://scholar.google.com.pl/*", 70 | "https://scholar.google.com.pr/*", 71 | "https://scholar.google.com.py/*", 72 | "https://scholar.google.com.ru/*", 73 | "https://scholar.google.com.sg/*", 74 | "https://scholar.google.com.sv/*", 75 | "https://scholar.google.com.tr/*", 76 | "https://scholar.google.com.tw/*", 77 | "https://scholar.google.com.ua/*", 78 | "https://scholar.google.com.uy/*", 79 | "https://scholar.google.com.vn/*", 80 | "https://scholar.google.cz/*", 81 | "https://scholar.google.de/*", 82 | "https://scholar.google.dk/*", 83 | "https://scholar.google.es/*", 84 | "https://scholar.google.fi/*", 85 | "https://scholar.google.fr/*", 86 | "https://scholar.google.gr/*", 87 | "https://scholar.google.hk/*", 88 | "https://scholar.google.hn/*", 89 | "https://scholar.google.hr/*", 90 | "https://scholar.google.hu/*", 91 | "https://scholar.google.is/*", 92 | "https://scholar.google.it/*", 93 | "https://scholar.google.li/*", 94 | "https://scholar.google.lt/*", 95 | "https://scholar.google.lu/*", 96 | "https://scholar.google.lv/*", 97 | "https://scholar.google.nl/*", 98 | "https://scholar.google.no/*", 99 | "https://scholar.google.pl/*", 100 | "https://scholar.google.pt/*", 101 | "https://scholar.google.ro/*", 102 | "https://scholar.google.ru/*", 103 | "https://scholar.google.se/*", 104 | "https://scholar.google.si/*", 105 | "https://scholar.google.sk/*", 106 | "https://www.connectedpapers.com/main/*", 107 | "https://www.webofscience.com/*", 108 | "https://www.semanticscholar.org/*" 109 | ], 110 | "css": ["css/style.css", "css/filter.css"], 111 | "js": [ 112 | "lib/jquery-3.5.1.min.js", 113 | "js/dblp.js", 114 | "js/connectedpapers.js", 115 | "js/scholar.js", 116 | "js/semanticscholar.js", 117 | "js/wos.js", 118 | "js/apiCache.js", 119 | "js/ccf.js", 120 | "js/fetchRank.js", 121 | "js/filter.js", 122 | "data/ccfRankAbbr.js", 123 | "data/ccfRankFull.js", 124 | "data/ccfRankDb.js", 125 | "data/ccfRankUrl.js", 126 | "data/ccfFullUrl.js", 127 | "data/ccfAbbrFull.js", 128 | "script.js" 129 | ] 130 | } 131 | ], 132 | "host_permissions": ["*://dblp.org/*"], 133 | "browser_specific_settings": { 134 | "gecko": { 135 | "id": "{cc79b7c3-7c57-4051-a3cc-9e9fccf5855b}", 136 | "strict_min_version": "58.0" 137 | } 138 | } 139 | } 140 | -------------------------------------------------------------------------------- /package-lock.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "CCFrank4dblp", 3 | "lockfileVersion": 3, 4 | "requires": true, 5 | "packages": { 6 | "": { 7 | "devDependencies": { 8 | "git-format-staged": "^3.1.1", 9 | "husky": "^9.1.6", 10 | "lint-staged": "^15.2.10", 11 | "prettier": "3.3.3" 12 | } 13 | }, 14 | "node_modules/ansi-escapes": { 15 | "version": "7.0.0", 16 | "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-7.0.0.tgz", 17 | "integrity": "sha512-GdYO7a61mR0fOlAsvC9/rIHf7L96sBc6dEWzeOu+KAea5bZyQRPIpojrVoI4AXGJS/ycu/fBTdLrUkA4ODrvjw==", 18 | "dev": true, 19 | "license": "MIT", 20 | "dependencies": { 21 | "environment": "^1.0.0" 22 | }, 23 | "engines": { 24 | "node": ">=18" 25 | }, 26 | "funding": { 27 | "url": "https://github.com/sponsors/sindresorhus" 28 | } 29 | }, 30 | "node_modules/ansi-regex": { 31 | "version": "6.1.0", 32 | "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.1.0.tgz", 33 | "integrity": "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA==", 34 | "dev": true, 35 | "license": "MIT", 36 | "engines": { 37 | "node": ">=12" 38 | }, 39 | "funding": { 40 | "url": "https://github.com/chalk/ansi-regex?sponsor=1" 41 | } 42 | }, 43 | "node_modules/ansi-styles": { 44 | "version": "6.2.1", 45 | "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-6.2.1.tgz", 46 | "integrity": "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==", 47 | "dev": true, 48 | "license": "MIT", 49 | "engines": { 50 | "node": ">=12" 51 | }, 52 | "funding": { 53 | "url": "https://github.com/chalk/ansi-styles?sponsor=1" 54 | } 55 | }, 56 | "node_modules/braces": { 57 | "version": "3.0.3", 58 | "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.3.tgz", 59 | "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", 60 | "dev": true, 61 | "license": "MIT", 62 | "dependencies": { 63 | "fill-range": "^7.1.1" 64 | }, 65 | "engines": { 66 | "node": ">=8" 67 | } 68 | }, 69 | "node_modules/chalk": { 70 | "version": "5.3.0", 71 | "resolved": "https://registry.npmjs.org/chalk/-/chalk-5.3.0.tgz", 72 | "integrity": "sha512-dLitG79d+GV1Nb/VYcCDFivJeK1hiukt9QjRNVOsUtTy1rR1YJsmpGGTZ3qJos+uw7WmWF4wUwBd9jxjocFC2w==", 73 | "dev": true, 74 | "license": "MIT", 75 | "engines": { 76 | "node": "^12.17.0 || ^14.13 || >=16.0.0" 77 | }, 78 | "funding": { 79 | "url": "https://github.com/chalk/chalk?sponsor=1" 80 | } 81 | }, 82 | "node_modules/cli-cursor": { 83 | "version": "5.0.0", 84 | "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-5.0.0.tgz", 85 | "integrity": "sha512-aCj4O5wKyszjMmDT4tZj93kxyydN/K5zPWSCe6/0AV/AA1pqe5ZBIw0a2ZfPQV7lL5/yb5HsUreJ6UFAF1tEQw==", 86 | "dev": true, 87 | "license": "MIT", 88 | "dependencies": { 89 | "restore-cursor": "^5.0.0" 90 | }, 91 | "engines": { 92 | "node": ">=18" 93 | }, 94 | "funding": { 95 | "url": "https://github.com/sponsors/sindresorhus" 96 | } 97 | }, 98 | "node_modules/cli-truncate": { 99 | "version": "4.0.0", 100 | "resolved": "https://registry.npmjs.org/cli-truncate/-/cli-truncate-4.0.0.tgz", 101 | "integrity": "sha512-nPdaFdQ0h/GEigbPClz11D0v/ZJEwxmeVZGeMo3Z5StPtUTkA9o1lD6QwoirYiSDzbcwn2XcjwmCp68W1IS4TA==", 102 | "dev": true, 103 | "license": "MIT", 104 | "dependencies": { 105 | "slice-ansi": "^5.0.0", 106 | "string-width": "^7.0.0" 107 | }, 108 | "engines": { 109 | "node": ">=18" 110 | }, 111 | "funding": { 112 | "url": "https://github.com/sponsors/sindresorhus" 113 | } 114 | }, 115 | "node_modules/colorette": { 116 | "version": "2.0.20", 117 | "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.20.tgz", 118 | "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", 119 | "dev": true, 120 | "license": "MIT" 121 | }, 122 | "node_modules/commander": { 123 | "version": "12.1.0", 124 | "resolved": "https://registry.npmjs.org/commander/-/commander-12.1.0.tgz", 125 | "integrity": "sha512-Vw8qHK3bZM9y/P10u3Vib8o/DdkvA2OtPtZvD871QKjy74Wj1WSKFILMPRPSdUSx5RFK1arlJzEtA4PkFgnbuA==", 126 | "dev": true, 127 | "license": "MIT", 128 | "engines": { 129 | "node": ">=18" 130 | } 131 | }, 132 | "node_modules/cross-spawn": { 133 | "version": "7.0.5", 134 | "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.5.tgz", 135 | "integrity": "sha512-ZVJrKKYunU38/76t0RMOulHOnUcbU9GbpWKAOZ0mhjr7CX6FVrH+4FrAapSOekrgFQ3f/8gwMEuIft0aKq6Hug==", 136 | "dev": true, 137 | "license": "MIT", 138 | "dependencies": { 139 | "path-key": "^3.1.0", 140 | "shebang-command": "^2.0.0", 141 | "which": "^2.0.1" 142 | }, 143 | "engines": { 144 | "node": ">= 8" 145 | } 146 | }, 147 | "node_modules/debug": { 148 | "version": "4.3.7", 149 | "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.7.tgz", 150 | "integrity": "sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ==", 151 | "dev": true, 152 | "license": "MIT", 153 | "dependencies": { 154 | "ms": "^2.1.3" 155 | }, 156 | "engines": { 157 | "node": ">=6.0" 158 | }, 159 | "peerDependenciesMeta": { 160 | "supports-color": { 161 | "optional": true 162 | } 163 | } 164 | }, 165 | "node_modules/emoji-regex": { 166 | "version": "10.4.0", 167 | "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-10.4.0.tgz", 168 | "integrity": "sha512-EC+0oUMY1Rqm4O6LLrgjtYDvcVYTy7chDnM4Q7030tP4Kwj3u/pR6gP9ygnp2CJMK5Gq+9Q2oqmrFJAz01DXjw==", 169 | "dev": true, 170 | "license": "MIT" 171 | }, 172 | "node_modules/environment": { 173 | "version": "1.1.0", 174 | "resolved": "https://registry.npmjs.org/environment/-/environment-1.1.0.tgz", 175 | "integrity": "sha512-xUtoPkMggbz0MPyPiIWr1Kp4aeWJjDZ6SMvURhimjdZgsRuDplF5/s9hcgGhyXMhs+6vpnuoiZ2kFiu3FMnS8Q==", 176 | "dev": true, 177 | "license": "MIT", 178 | "engines": { 179 | "node": ">=18" 180 | }, 181 | "funding": { 182 | "url": "https://github.com/sponsors/sindresorhus" 183 | } 184 | }, 185 | "node_modules/eventemitter3": { 186 | "version": "5.0.1", 187 | "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.1.tgz", 188 | "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==", 189 | "dev": true, 190 | "license": "MIT" 191 | }, 192 | "node_modules/execa": { 193 | "version": "8.0.1", 194 | "resolved": "https://registry.npmjs.org/execa/-/execa-8.0.1.tgz", 195 | "integrity": "sha512-VyhnebXciFV2DESc+p6B+y0LjSm0krU4OgJN44qFAhBY0TJ+1V61tYD2+wHusZ6F9n5K+vl8k0sTy7PEfV4qpg==", 196 | "dev": true, 197 | "license": "MIT", 198 | "dependencies": { 199 | "cross-spawn": "^7.0.3", 200 | "get-stream": "^8.0.1", 201 | "human-signals": "^5.0.0", 202 | "is-stream": "^3.0.0", 203 | "merge-stream": "^2.0.0", 204 | "npm-run-path": "^5.1.0", 205 | "onetime": "^6.0.0", 206 | "signal-exit": "^4.1.0", 207 | "strip-final-newline": "^3.0.0" 208 | }, 209 | "engines": { 210 | "node": ">=16.17" 211 | }, 212 | "funding": { 213 | "url": "https://github.com/sindresorhus/execa?sponsor=1" 214 | } 215 | }, 216 | "node_modules/fill-range": { 217 | "version": "7.1.1", 218 | "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.1.1.tgz", 219 | "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", 220 | "dev": true, 221 | "license": "MIT", 222 | "dependencies": { 223 | "to-regex-range": "^5.0.1" 224 | }, 225 | "engines": { 226 | "node": ">=8" 227 | } 228 | }, 229 | "node_modules/get-east-asian-width": { 230 | "version": "1.3.0", 231 | "resolved": "https://registry.npmjs.org/get-east-asian-width/-/get-east-asian-width-1.3.0.tgz", 232 | "integrity": "sha512-vpeMIQKxczTD/0s2CdEWHcb0eeJe6TFjxb+J5xgX7hScxqrGuyjmv4c1D4A/gelKfyox0gJJwIHF+fLjeaM8kQ==", 233 | "dev": true, 234 | "license": "MIT", 235 | "engines": { 236 | "node": ">=18" 237 | }, 238 | "funding": { 239 | "url": "https://github.com/sponsors/sindresorhus" 240 | } 241 | }, 242 | "node_modules/get-stream": { 243 | "version": "8.0.1", 244 | "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-8.0.1.tgz", 245 | "integrity": "sha512-VaUJspBffn/LMCJVoMvSAdmscJyS1auj5Zulnn5UoYcY531UWmdwhRWkcGKnGU93m5HSXP9LP2usOryrBtQowA==", 246 | "dev": true, 247 | "license": "MIT", 248 | "engines": { 249 | "node": ">=16" 250 | }, 251 | "funding": { 252 | "url": "https://github.com/sponsors/sindresorhus" 253 | } 254 | }, 255 | "node_modules/git-format-staged": { 256 | "version": "3.1.1", 257 | "resolved": "https://registry.npmjs.org/git-format-staged/-/git-format-staged-3.1.1.tgz", 258 | "integrity": "sha512-P749fkktaiAchFZKR7bgdvruzhvbcIDr1uRBrS9/Wdimb7wH1Twchz9gOixj8tUaHVMuXY/ckDojfOwV6AxgPA==", 259 | "dev": true, 260 | "license": "MIT", 261 | "bin": { 262 | "git-format-staged": "git-format-staged" 263 | } 264 | }, 265 | "node_modules/human-signals": { 266 | "version": "5.0.0", 267 | "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-5.0.0.tgz", 268 | "integrity": "sha512-AXcZb6vzzrFAUE61HnN4mpLqd/cSIwNQjtNWR0euPm6y0iqx3G4gOXaIDdtdDwZmhwe82LA6+zinmW4UBWVePQ==", 269 | "dev": true, 270 | "license": "Apache-2.0", 271 | "engines": { 272 | "node": ">=16.17.0" 273 | } 274 | }, 275 | "node_modules/husky": { 276 | "version": "9.1.6", 277 | "resolved": "https://registry.npmjs.org/husky/-/husky-9.1.6.tgz", 278 | "integrity": "sha512-sqbjZKK7kf44hfdE94EoX8MZNk0n7HeW37O4YrVGCF4wzgQjp+akPAkfUK5LZ6KuR/6sqeAVuXHji+RzQgOn5A==", 279 | "dev": true, 280 | "license": "MIT", 281 | "bin": { 282 | "husky": "bin.js" 283 | }, 284 | "engines": { 285 | "node": ">=18" 286 | }, 287 | "funding": { 288 | "url": "https://github.com/sponsors/typicode" 289 | } 290 | }, 291 | "node_modules/is-fullwidth-code-point": { 292 | "version": "4.0.0", 293 | "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-4.0.0.tgz", 294 | "integrity": "sha512-O4L094N2/dZ7xqVdrXhh9r1KODPJpFms8B5sGdJLPy664AgvXsreZUyCQQNItZRDlYug4xStLjNp/sz3HvBowQ==", 295 | "dev": true, 296 | "license": "MIT", 297 | "engines": { 298 | "node": ">=12" 299 | }, 300 | "funding": { 301 | "url": "https://github.com/sponsors/sindresorhus" 302 | } 303 | }, 304 | "node_modules/is-number": { 305 | "version": "7.0.0", 306 | "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", 307 | "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", 308 | "dev": true, 309 | "license": "MIT", 310 | "engines": { 311 | "node": ">=0.12.0" 312 | } 313 | }, 314 | "node_modules/is-stream": { 315 | "version": "3.0.0", 316 | "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-3.0.0.tgz", 317 | "integrity": "sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA==", 318 | "dev": true, 319 | "license": "MIT", 320 | "engines": { 321 | "node": "^12.20.0 || ^14.13.1 || >=16.0.0" 322 | }, 323 | "funding": { 324 | "url": "https://github.com/sponsors/sindresorhus" 325 | } 326 | }, 327 | "node_modules/isexe": { 328 | "version": "2.0.0", 329 | "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", 330 | "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", 331 | "dev": true, 332 | "license": "ISC" 333 | }, 334 | "node_modules/lilconfig": { 335 | "version": "3.1.2", 336 | "resolved": "https://registry.npmjs.org/lilconfig/-/lilconfig-3.1.2.tgz", 337 | "integrity": "sha512-eop+wDAvpItUys0FWkHIKeC9ybYrTGbU41U5K7+bttZZeohvnY7M9dZ5kB21GNWiFT2q1OoPTvncPCgSOVO5ow==", 338 | "dev": true, 339 | "license": "MIT", 340 | "engines": { 341 | "node": ">=14" 342 | }, 343 | "funding": { 344 | "url": "https://github.com/sponsors/antonk52" 345 | } 346 | }, 347 | "node_modules/lint-staged": { 348 | "version": "15.2.10", 349 | "resolved": "https://registry.npmjs.org/lint-staged/-/lint-staged-15.2.10.tgz", 350 | "integrity": "sha512-5dY5t743e1byO19P9I4b3x8HJwalIznL5E1FWYnU6OWw33KxNBSLAc6Cy7F2PsFEO8FKnLwjwm5hx7aMF0jzZg==", 351 | "dev": true, 352 | "license": "MIT", 353 | "dependencies": { 354 | "chalk": "~5.3.0", 355 | "commander": "~12.1.0", 356 | "debug": "~4.3.6", 357 | "execa": "~8.0.1", 358 | "lilconfig": "~3.1.2", 359 | "listr2": "~8.2.4", 360 | "micromatch": "~4.0.8", 361 | "pidtree": "~0.6.0", 362 | "string-argv": "~0.3.2", 363 | "yaml": "~2.5.0" 364 | }, 365 | "bin": { 366 | "lint-staged": "bin/lint-staged.js" 367 | }, 368 | "engines": { 369 | "node": ">=18.12.0" 370 | }, 371 | "funding": { 372 | "url": "https://opencollective.com/lint-staged" 373 | } 374 | }, 375 | "node_modules/listr2": { 376 | "version": "8.2.5", 377 | "resolved": "https://registry.npmjs.org/listr2/-/listr2-8.2.5.tgz", 378 | "integrity": "sha512-iyAZCeyD+c1gPyE9qpFu8af0Y+MRtmKOncdGoA2S5EY8iFq99dmmvkNnHiWo+pj0s7yH7l3KPIgee77tKpXPWQ==", 379 | "dev": true, 380 | "license": "MIT", 381 | "dependencies": { 382 | "cli-truncate": "^4.0.0", 383 | "colorette": "^2.0.20", 384 | "eventemitter3": "^5.0.1", 385 | "log-update": "^6.1.0", 386 | "rfdc": "^1.4.1", 387 | "wrap-ansi": "^9.0.0" 388 | }, 389 | "engines": { 390 | "node": ">=18.0.0" 391 | } 392 | }, 393 | "node_modules/log-update": { 394 | "version": "6.1.0", 395 | "resolved": "https://registry.npmjs.org/log-update/-/log-update-6.1.0.tgz", 396 | "integrity": "sha512-9ie8ItPR6tjY5uYJh8K/Zrv/RMZ5VOlOWvtZdEHYSTFKZfIBPQa9tOAEeAWhd+AnIneLJ22w5fjOYtoutpWq5w==", 397 | "dev": true, 398 | "license": "MIT", 399 | "dependencies": { 400 | "ansi-escapes": "^7.0.0", 401 | "cli-cursor": "^5.0.0", 402 | "slice-ansi": "^7.1.0", 403 | "strip-ansi": "^7.1.0", 404 | "wrap-ansi": "^9.0.0" 405 | }, 406 | "engines": { 407 | "node": ">=18" 408 | }, 409 | "funding": { 410 | "url": "https://github.com/sponsors/sindresorhus" 411 | } 412 | }, 413 | "node_modules/log-update/node_modules/is-fullwidth-code-point": { 414 | "version": "5.0.0", 415 | "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-5.0.0.tgz", 416 | "integrity": "sha512-OVa3u9kkBbw7b8Xw5F9P+D/T9X+Z4+JruYVNapTjPYZYUznQ5YfWeFkOj606XYYW8yugTfC8Pj0hYqvi4ryAhA==", 417 | "dev": true, 418 | "license": "MIT", 419 | "dependencies": { 420 | "get-east-asian-width": "^1.0.0" 421 | }, 422 | "engines": { 423 | "node": ">=18" 424 | }, 425 | "funding": { 426 | "url": "https://github.com/sponsors/sindresorhus" 427 | } 428 | }, 429 | "node_modules/log-update/node_modules/slice-ansi": { 430 | "version": "7.1.0", 431 | "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-7.1.0.tgz", 432 | "integrity": "sha512-bSiSngZ/jWeX93BqeIAbImyTbEihizcwNjFoRUIY/T1wWQsfsm2Vw1agPKylXvQTU7iASGdHhyqRlqQzfz+Htg==", 433 | "dev": true, 434 | "license": "MIT", 435 | "dependencies": { 436 | "ansi-styles": "^6.2.1", 437 | "is-fullwidth-code-point": "^5.0.0" 438 | }, 439 | "engines": { 440 | "node": ">=18" 441 | }, 442 | "funding": { 443 | "url": "https://github.com/chalk/slice-ansi?sponsor=1" 444 | } 445 | }, 446 | "node_modules/merge-stream": { 447 | "version": "2.0.0", 448 | "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", 449 | "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", 450 | "dev": true, 451 | "license": "MIT" 452 | }, 453 | "node_modules/micromatch": { 454 | "version": "4.0.8", 455 | "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.8.tgz", 456 | "integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==", 457 | "dev": true, 458 | "license": "MIT", 459 | "dependencies": { 460 | "braces": "^3.0.3", 461 | "picomatch": "^2.3.1" 462 | }, 463 | "engines": { 464 | "node": ">=8.6" 465 | } 466 | }, 467 | "node_modules/mimic-fn": { 468 | "version": "4.0.0", 469 | "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz", 470 | "integrity": "sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw==", 471 | "dev": true, 472 | "license": "MIT", 473 | "engines": { 474 | "node": ">=12" 475 | }, 476 | "funding": { 477 | "url": "https://github.com/sponsors/sindresorhus" 478 | } 479 | }, 480 | "node_modules/mimic-function": { 481 | "version": "5.0.1", 482 | "resolved": "https://registry.npmjs.org/mimic-function/-/mimic-function-5.0.1.tgz", 483 | "integrity": "sha512-VP79XUPxV2CigYP3jWwAUFSku2aKqBH7uTAapFWCBqutsbmDo96KY5o8uh6U+/YSIn5OxJnXp73beVkpqMIGhA==", 484 | "dev": true, 485 | "license": "MIT", 486 | "engines": { 487 | "node": ">=18" 488 | }, 489 | "funding": { 490 | "url": "https://github.com/sponsors/sindresorhus" 491 | } 492 | }, 493 | "node_modules/ms": { 494 | "version": "2.1.3", 495 | "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", 496 | "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", 497 | "dev": true, 498 | "license": "MIT" 499 | }, 500 | "node_modules/npm-run-path": { 501 | "version": "5.3.0", 502 | "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-5.3.0.tgz", 503 | "integrity": "sha512-ppwTtiJZq0O/ai0z7yfudtBpWIoxM8yE6nHi1X47eFR2EWORqfbu6CnPlNsjeN683eT0qG6H/Pyf9fCcvjnnnQ==", 504 | "dev": true, 505 | "license": "MIT", 506 | "dependencies": { 507 | "path-key": "^4.0.0" 508 | }, 509 | "engines": { 510 | "node": "^12.20.0 || ^14.13.1 || >=16.0.0" 511 | }, 512 | "funding": { 513 | "url": "https://github.com/sponsors/sindresorhus" 514 | } 515 | }, 516 | "node_modules/npm-run-path/node_modules/path-key": { 517 | "version": "4.0.0", 518 | "resolved": "https://registry.npmjs.org/path-key/-/path-key-4.0.0.tgz", 519 | "integrity": "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ==", 520 | "dev": true, 521 | "license": "MIT", 522 | "engines": { 523 | "node": ">=12" 524 | }, 525 | "funding": { 526 | "url": "https://github.com/sponsors/sindresorhus" 527 | } 528 | }, 529 | "node_modules/onetime": { 530 | "version": "6.0.0", 531 | "resolved": "https://registry.npmjs.org/onetime/-/onetime-6.0.0.tgz", 532 | "integrity": "sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ==", 533 | "dev": true, 534 | "license": "MIT", 535 | "dependencies": { 536 | "mimic-fn": "^4.0.0" 537 | }, 538 | "engines": { 539 | "node": ">=12" 540 | }, 541 | "funding": { 542 | "url": "https://github.com/sponsors/sindresorhus" 543 | } 544 | }, 545 | "node_modules/path-key": { 546 | "version": "3.1.1", 547 | "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", 548 | "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", 549 | "dev": true, 550 | "license": "MIT", 551 | "engines": { 552 | "node": ">=8" 553 | } 554 | }, 555 | "node_modules/picomatch": { 556 | "version": "2.3.1", 557 | "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", 558 | "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", 559 | "dev": true, 560 | "license": "MIT", 561 | "engines": { 562 | "node": ">=8.6" 563 | }, 564 | "funding": { 565 | "url": "https://github.com/sponsors/jonschlinkert" 566 | } 567 | }, 568 | "node_modules/pidtree": { 569 | "version": "0.6.0", 570 | "resolved": "https://registry.npmjs.org/pidtree/-/pidtree-0.6.0.tgz", 571 | "integrity": "sha512-eG2dWTVw5bzqGRztnHExczNxt5VGsE6OwTeCG3fdUf9KBsZzO3R5OIIIzWR+iZA0NtZ+RDVdaoE2dK1cn6jH4g==", 572 | "dev": true, 573 | "license": "MIT", 574 | "bin": { 575 | "pidtree": "bin/pidtree.js" 576 | }, 577 | "engines": { 578 | "node": ">=0.10" 579 | } 580 | }, 581 | "node_modules/prettier": { 582 | "version": "3.3.3", 583 | "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.3.3.tgz", 584 | "integrity": "sha512-i2tDNA0O5IrMO757lfrdQZCc2jPNDVntV0m/+4whiDfWaTKfMNgR7Qz0NAeGz/nRqF4m5/6CLzbP4/liHt12Ew==", 585 | "dev": true, 586 | "license": "MIT", 587 | "bin": { 588 | "prettier": "bin/prettier.cjs" 589 | }, 590 | "engines": { 591 | "node": ">=14" 592 | }, 593 | "funding": { 594 | "url": "https://github.com/prettier/prettier?sponsor=1" 595 | } 596 | }, 597 | "node_modules/restore-cursor": { 598 | "version": "5.1.0", 599 | "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-5.1.0.tgz", 600 | "integrity": "sha512-oMA2dcrw6u0YfxJQXm342bFKX/E4sG9rbTzO9ptUcR/e8A33cHuvStiYOwH7fszkZlZ1z/ta9AAoPk2F4qIOHA==", 601 | "dev": true, 602 | "license": "MIT", 603 | "dependencies": { 604 | "onetime": "^7.0.0", 605 | "signal-exit": "^4.1.0" 606 | }, 607 | "engines": { 608 | "node": ">=18" 609 | }, 610 | "funding": { 611 | "url": "https://github.com/sponsors/sindresorhus" 612 | } 613 | }, 614 | "node_modules/restore-cursor/node_modules/onetime": { 615 | "version": "7.0.0", 616 | "resolved": "https://registry.npmjs.org/onetime/-/onetime-7.0.0.tgz", 617 | "integrity": "sha512-VXJjc87FScF88uafS3JllDgvAm+c/Slfz06lorj2uAY34rlUu0Nt+v8wreiImcrgAjjIHp1rXpTDlLOGw29WwQ==", 618 | "dev": true, 619 | "license": "MIT", 620 | "dependencies": { 621 | "mimic-function": "^5.0.0" 622 | }, 623 | "engines": { 624 | "node": ">=18" 625 | }, 626 | "funding": { 627 | "url": "https://github.com/sponsors/sindresorhus" 628 | } 629 | }, 630 | "node_modules/rfdc": { 631 | "version": "1.4.1", 632 | "resolved": "https://registry.npmjs.org/rfdc/-/rfdc-1.4.1.tgz", 633 | "integrity": "sha512-q1b3N5QkRUWUl7iyylaaj3kOpIT0N2i9MqIEQXP73GVsN9cw3fdx8X63cEmWhJGi2PPCF23Ijp7ktmd39rawIA==", 634 | "dev": true, 635 | "license": "MIT" 636 | }, 637 | "node_modules/shebang-command": { 638 | "version": "2.0.0", 639 | "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", 640 | "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", 641 | "dev": true, 642 | "license": "MIT", 643 | "dependencies": { 644 | "shebang-regex": "^3.0.0" 645 | }, 646 | "engines": { 647 | "node": ">=8" 648 | } 649 | }, 650 | "node_modules/shebang-regex": { 651 | "version": "3.0.0", 652 | "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", 653 | "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", 654 | "dev": true, 655 | "license": "MIT", 656 | "engines": { 657 | "node": ">=8" 658 | } 659 | }, 660 | "node_modules/signal-exit": { 661 | "version": "4.1.0", 662 | "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-4.1.0.tgz", 663 | "integrity": "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==", 664 | "dev": true, 665 | "license": "ISC", 666 | "engines": { 667 | "node": ">=14" 668 | }, 669 | "funding": { 670 | "url": "https://github.com/sponsors/isaacs" 671 | } 672 | }, 673 | "node_modules/slice-ansi": { 674 | "version": "5.0.0", 675 | "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-5.0.0.tgz", 676 | "integrity": "sha512-FC+lgizVPfie0kkhqUScwRu1O/lF6NOgJmlCgK+/LYxDCTk8sGelYaHDhFcDN+Sn3Cv+3VSa4Byeo+IMCzpMgQ==", 677 | "dev": true, 678 | "license": "MIT", 679 | "dependencies": { 680 | "ansi-styles": "^6.0.0", 681 | "is-fullwidth-code-point": "^4.0.0" 682 | }, 683 | "engines": { 684 | "node": ">=12" 685 | }, 686 | "funding": { 687 | "url": "https://github.com/chalk/slice-ansi?sponsor=1" 688 | } 689 | }, 690 | "node_modules/string-argv": { 691 | "version": "0.3.2", 692 | "resolved": "https://registry.npmjs.org/string-argv/-/string-argv-0.3.2.tgz", 693 | "integrity": "sha512-aqD2Q0144Z+/RqG52NeHEkZauTAUWJO8c6yTftGJKO3Tja5tUgIfmIl6kExvhtxSDP7fXB6DvzkfMpCd/F3G+Q==", 694 | "dev": true, 695 | "license": "MIT", 696 | "engines": { 697 | "node": ">=0.6.19" 698 | } 699 | }, 700 | "node_modules/string-width": { 701 | "version": "7.2.0", 702 | "resolved": "https://registry.npmjs.org/string-width/-/string-width-7.2.0.tgz", 703 | "integrity": "sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ==", 704 | "dev": true, 705 | "license": "MIT", 706 | "dependencies": { 707 | "emoji-regex": "^10.3.0", 708 | "get-east-asian-width": "^1.0.0", 709 | "strip-ansi": "^7.1.0" 710 | }, 711 | "engines": { 712 | "node": ">=18" 713 | }, 714 | "funding": { 715 | "url": "https://github.com/sponsors/sindresorhus" 716 | } 717 | }, 718 | "node_modules/strip-ansi": { 719 | "version": "7.1.0", 720 | "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-7.1.0.tgz", 721 | "integrity": "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==", 722 | "dev": true, 723 | "license": "MIT", 724 | "dependencies": { 725 | "ansi-regex": "^6.0.1" 726 | }, 727 | "engines": { 728 | "node": ">=12" 729 | }, 730 | "funding": { 731 | "url": "https://github.com/chalk/strip-ansi?sponsor=1" 732 | } 733 | }, 734 | "node_modules/strip-final-newline": { 735 | "version": "3.0.0", 736 | "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-3.0.0.tgz", 737 | "integrity": "sha512-dOESqjYr96iWYylGObzd39EuNTa5VJxyvVAEm5Jnh7KGo75V43Hk1odPQkNDyXNmUR6k+gEiDVXnjB8HJ3crXw==", 738 | "dev": true, 739 | "license": "MIT", 740 | "engines": { 741 | "node": ">=12" 742 | }, 743 | "funding": { 744 | "url": "https://github.com/sponsors/sindresorhus" 745 | } 746 | }, 747 | "node_modules/to-regex-range": { 748 | "version": "5.0.1", 749 | "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", 750 | "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", 751 | "dev": true, 752 | "license": "MIT", 753 | "dependencies": { 754 | "is-number": "^7.0.0" 755 | }, 756 | "engines": { 757 | "node": ">=8.0" 758 | } 759 | }, 760 | "node_modules/which": { 761 | "version": "2.0.2", 762 | "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", 763 | "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", 764 | "dev": true, 765 | "license": "ISC", 766 | "dependencies": { 767 | "isexe": "^2.0.0" 768 | }, 769 | "bin": { 770 | "node-which": "bin/node-which" 771 | }, 772 | "engines": { 773 | "node": ">= 8" 774 | } 775 | }, 776 | "node_modules/wrap-ansi": { 777 | "version": "9.0.0", 778 | "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-9.0.0.tgz", 779 | "integrity": "sha512-G8ura3S+3Z2G+mkgNRq8dqaFZAuxfsxpBB8OCTGRTCtp+l/v9nbFNmCUP1BZMts3G1142MsZfn6eeUKrr4PD1Q==", 780 | "dev": true, 781 | "license": "MIT", 782 | "dependencies": { 783 | "ansi-styles": "^6.2.1", 784 | "string-width": "^7.0.0", 785 | "strip-ansi": "^7.1.0" 786 | }, 787 | "engines": { 788 | "node": ">=18" 789 | }, 790 | "funding": { 791 | "url": "https://github.com/chalk/wrap-ansi?sponsor=1" 792 | } 793 | }, 794 | "node_modules/yaml": { 795 | "version": "2.5.1", 796 | "resolved": "https://registry.npmjs.org/yaml/-/yaml-2.5.1.tgz", 797 | "integrity": "sha512-bLQOjaX/ADgQ20isPJRvF0iRUHIxVhYvr53Of7wGcWlO2jvtUlH5m87DsmulFVxRpNLOnI4tB6p/oh8D7kpn9Q==", 798 | "dev": true, 799 | "license": "ISC", 800 | "bin": { 801 | "yaml": "bin.mjs" 802 | }, 803 | "engines": { 804 | "node": ">= 14" 805 | } 806 | } 807 | } 808 | } 809 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "devDependencies": { 3 | "git-format-staged": "^3.1.1", 4 | "husky": "^9.1.6", 5 | "lint-staged": "^15.2.10", 6 | "prettier": "3.3.3" 7 | }, 8 | "scripts": { 9 | "prepare": "husky" 10 | }, 11 | "lint-staged": { 12 | "**/*": "prettier --write --ignore-unknown" 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /script.js: -------------------------------------------------------------------------------- 1 | dblp.rankSpanList.push(ccf.getRankSpan); 2 | scholar.rankSpanList.push(ccf.getRankSpan); 3 | connectedpapers.rankSpanList.push(ccf.getRankSpan); 4 | semanticscholar.rankSpanList.push(ccf.getRankSpan); 5 | wos.rankSpanList.push(ccf.getRankSpan); 6 | 7 | if (window.location.hostname.startsWith("dblp")) { 8 | dblp.run(); 9 | } else if (window.location.hostname.startsWith("scholar.google")) { 10 | scholar.run(); 11 | } else if (window.location.hostname.includes("connectedpaper")) { 12 | connectedpapers.run(); 13 | } else if (window.location.hostname.includes("semanticscholar")) { 14 | semanticscholar.run(); 15 | } else if (window.location.hostname.includes("webofscience")) { 16 | wos.run(); 17 | } 18 | 19 | filter.init(); 20 | --------------------------------------------------------------------------------