├── .gitignore
├── .prettierrc
├── LICENSE
├── README.md
├── assets
├── icons
│ ├── icon_128.png
│ ├── icon_16.png
│ ├── icon_256.png
│ └── icon_48.png
└── promo
│ ├── Large promo tile.jpg
│ ├── Marquee promo tile.jpg
│ ├── Small promo tile.jpg
│ └── screenshot_1.jpg
├── bundle.ts
├── example.png
├── package.json
├── src
└── index.ts
├── tsconfig.json
└── yarn.lock
/.gitignore:
--------------------------------------------------------------------------------
1 | *.zip
2 |
3 | dist/
4 | node_modules/
5 |
--------------------------------------------------------------------------------
/.prettierrc:
--------------------------------------------------------------------------------
1 | {
2 | "singleQuote": true,
3 | "semi": false
4 | }
5 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) Lasse Norfeldt
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 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Archive Notice ⚠️
2 |
3 | > This project is no longer actively maintained and has been archived. Feel free to fork it and build upon it. Thank you for your interest and support!
4 |
5 |
6 | # Issue Reactions Chrome & Firefox Extension
7 | List reaction links on a Github issue or discussion page
8 |
9 |
10 |
11 | See it in action
12 |
13 | [](http://www.youtube.com/watch?v=K4wc818iNDc "Video Title")
14 |
15 | ## Chrome
16 |
17 | Grab it from the chrome extensions: [Github Issue Reactions](https://chrome.google.com/webstore/detail/github-issue-reactions/enekincdenmmbpgkbhflknhaphpajnfd)
18 |
19 | ## Firefox
20 |
21 | Grab it from the firefox add-ons: [Github Issue Reactions](https://addons.mozilla.org/addon/github-issue-reactions/)
22 |
23 | ## Manual Setup
24 |
25 | 1. Clone this repo
26 | 2. `yarn install`
27 | 3. `yarn bundle`
28 | 4. Chrome:
29 | 1. Open Chrome Extensions
30 | 2. Enable Developer mode
31 | 3. Pick Load unpacked
32 | 5. Firefox:
33 | 1. Settings/Extension & Themes
34 | 2. Click the gear icon and select "Debug add-ons"
35 | 3. Load Temporary Add-on..
36 | 6. Navigate to the relevant `/dist` directory
37 | 7. Enjoy! 👍
38 |
39 | ## Not Working Any More?
40 |
41 | Try to do a git pull to see if it has been fixed
42 |
43 | (**DO NOT FORGET go into your extensions and reload the lasted version**).
44 |
--------------------------------------------------------------------------------
/assets/icons/icon_128.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/icons/icon_128.png
--------------------------------------------------------------------------------
/assets/icons/icon_16.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/icons/icon_16.png
--------------------------------------------------------------------------------
/assets/icons/icon_256.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/icons/icon_256.png
--------------------------------------------------------------------------------
/assets/icons/icon_48.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/icons/icon_48.png
--------------------------------------------------------------------------------
/assets/promo/Large promo tile.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/promo/Large promo tile.jpg
--------------------------------------------------------------------------------
/assets/promo/Marquee promo tile.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/promo/Marquee promo tile.jpg
--------------------------------------------------------------------------------
/assets/promo/Small promo tile.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/promo/Small promo tile.jpg
--------------------------------------------------------------------------------
/assets/promo/screenshot_1.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/assets/promo/screenshot_1.jpg
--------------------------------------------------------------------------------
/bundle.ts:
--------------------------------------------------------------------------------
1 | import * as fs from 'fs'
2 | import * as path from 'path'
3 | import * as child_process from 'child_process'
4 | import * as archiver from 'archiver'
5 |
6 | import { version } from './package.json'
7 |
8 | console.log('Bundling started')
9 |
10 | type Browser = 'chrome' | 'firefox'
11 |
12 | function writeToDist(browser: Browser, fileName: string, content: any) {
13 | const dir = path.join(__dirname, 'dist', browser)
14 | if (!fs.existsSync(dir)) {
15 | fs.mkdirSync(dir, { recursive: true })
16 | }
17 | fs.writeFileSync(path.join(dir, fileName), content)
18 | }
19 |
20 | // MANIFESTS
21 | const commonManifest = {
22 | name: 'Github Issue Reactions',
23 | version,
24 | description:
25 | 'List a link of reactions on a github issue and pull request page',
26 | content_scripts: [
27 | {
28 | matches: ['*://*.github.com/*'],
29 | js: ['index.js'],
30 | run_at: 'document_end',
31 | },
32 | ],
33 | permissions: ['storage'],
34 | icons: {
35 | '16': 'icon_16.png',
36 | '48': 'icon_48.png',
37 | '128': 'icon_128.png',
38 | '256': 'icon_256.png',
39 | },
40 | host_permissions: ['https://www.github.com/', 'http://www.github.com/'],
41 | }
42 |
43 | // CHROME
44 | const chromeManifest = {
45 | manifest_version: 3,
46 | ...commonManifest,
47 | }
48 | writeToDist('chrome', 'manifest.json', JSON.stringify(chromeManifest, null, 2))
49 |
50 | // FIREFOX
51 | const { host_permissions, ...firefoxManifest } = {
52 | manifest_version: 2,
53 | ...commonManifest,
54 | permissions: [
55 | ...commonManifest.host_permissions,
56 | ...commonManifest.permissions,
57 | ],
58 | browser_specific_settings: {
59 | gecko: {
60 | id: '{f6ec3962-fd1d-4a7b-8dab-d211fbf91389}',
61 | strict_min_version: '57.0a1',
62 | },
63 | },
64 | }
65 | writeToDist(
66 | 'firefox',
67 | 'manifest.json',
68 | JSON.stringify(firefoxManifest, null, 2)
69 | )
70 |
71 | // ICONS
72 | const iconFiles = fs.readdirSync(path.join(__dirname, 'assets', 'icons'))
73 | for (const iconFile of iconFiles) {
74 | const iconData = fs.readFileSync(
75 | path.join(__dirname, 'assets', 'icons', iconFile)
76 | )
77 | writeToDist('chrome', iconFile, iconData)
78 | writeToDist('firefox', iconFile, iconData)
79 | }
80 |
81 | // CONTENT SCRIPT
82 | const tscCommand = (browser: Browser) => {
83 | const command = `yarn tsc src/index.ts --outDir dist/${browser}`
84 | console.log(command)
85 |
86 | return command
87 | }
88 | child_process.exec(tscCommand('chrome'), () => callBack('chrome'))
89 | child_process.exec(tscCommand('firefox'), () => callBack('firefox'))
90 |
91 | // If it should z(h)ip it when done
92 | function callBack(browser: Browser) {
93 | if (process.argv.includes('zip')) {
94 | const archive = archiver('zip', {
95 | zlib: { level: 9 },
96 | })
97 | const output = fs.createWriteStream(
98 | path.join(__dirname, `${browser}_${version}.zip`)
99 | )
100 | archive.pipe(output)
101 | archive.directory(path.join(__dirname, 'dist', `${browser}`), false)
102 | archive.finalize()
103 | }
104 | }
105 |
106 | setTimeout(() => {
107 | const timeStampWithoutMs = new Date()
108 | .toISOString()
109 | .split('.')[0]
110 | .replace('T', ' ')
111 | console.log('Bundling finished', timeStampWithoutMs)
112 | }, 5000)
113 |
--------------------------------------------------------------------------------
/example.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/Norfeldt/github-issue-reactions-browser-extension/0c853a2032b5d03edd34f52408bc64caac4e2164/example.png
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "github-issue-reactions-browser-extension",
3 | "version": "2.4.5",
4 | "repository": "git@github.com:Norfeldt/github-issue-reactions-browser-extension.git",
5 | "author": "Lasse Nørfeldt ",
6 | "license": "MIT",
7 | "scripts": {
8 | "dev": "watch 'yarn bundle' src",
9 | "bundle": "ts-node bundle.ts",
10 | "zip": "ts-node bundle.ts --args zip"
11 | },
12 | "devDependencies": {
13 | "@types/archiver": "^5.3.1",
14 | "@types/chrome": "^0.0.209",
15 | "@types/firefox-webext-browser": "^109.0.0",
16 | "@types/node": "^18.11.17",
17 | "archiver": "^5.3.1",
18 | "ts-node": "^10.9.1",
19 | "typescript": "^5.0.0-beta",
20 | "watch": "^1.0.2"
21 | },
22 | "volta": {
23 | "node": "18.16.0",
24 | "yarn": "1.22.19"
25 | }
26 | }
27 |
--------------------------------------------------------------------------------
/src/index.ts:
--------------------------------------------------------------------------------
1 | const primaryColor = 'var(--color-fg-default)'
2 | const backgroundColor = 'var(--color-social-reaction-bg-hover)'
3 | const DISPLAY = 'DISPLAY'
4 |
5 | const getBrowser = () => {
6 | if (navigator.userAgent.match(/Chrome/)) return chrome
7 |
8 | return browser
9 | }
10 |
11 | const [sideBarId, wrapperId] = [
12 | '#partial-discussion-sidebar',
13 | '#reactions-wrapper',
14 | ]
15 |
16 | // INITIAL LOADING INDICATOR
17 | injectWrapper({ withLoadingSpinner: true })
18 |
19 | // Create a sticking wrapper to place all reactions
20 | function injectWrapper({ withLoadingSpinner } = { withLoadingSpinner: false }) {
21 | if (document.querySelector('header')?.innerText.includes('Sign in')) {
22 | const header = document.querySelector(sideBarId) as HTMLDivElement
23 | if (header) {
24 | const notSignedInClass = 'not-signed-in'
25 | Array.from(document.querySelectorAll(`.${notSignedInClass}`)).forEach(
26 | (element) => element?.remove()
27 | )
28 | const textHeader = document.createElement('div')
29 | textHeader.className = notSignedInClass
30 | textHeader.style.margin = '1.25rem 0 0.2rem 0'
31 | textHeader.style.fontWeight = 'bold'
32 | textHeader.appendChild(
33 | document.createTextNode('Sign in to list reactions')
34 | )
35 | // add the text below "Github source code is different for signed out users and it is currently too much work to support both"
36 | const textReason = document.createElement('div')
37 | textReason.className = notSignedInClass
38 | textReason.style.margin = '1.25rem 0 0.5rem 0'
39 | textReason.style.fontStyle = 'italic'
40 | textReason.appendChild(
41 | document.createTextNode(
42 | 'Github source code is different for signed out users and it is currently too much work to support both - sorry! 🙈'
43 | )
44 | )
45 | textReason.appendChild(
46 | document.createTextNode(
47 | 'You are welcome to contribute to the project on Github 🙌'
48 | )
49 | )
50 | header.appendChild(textHeader)
51 | header.appendChild(textReason)
52 |
53 | Array.from(document.querySelectorAll(`.credits`)).forEach((element) =>
54 | element?.remove()
55 | )
56 | header.appendChild(Credits())
57 | }
58 | return
59 | }
60 |
61 | const header = document.querySelector(sideBarId) as HTMLDivElement
62 | if (!header) return
63 |
64 | header.style.position = 'relative'
65 | header.style.height = '100%'
66 |
67 | const wrapper = document.createElement('div')
68 | wrapper.setAttribute('id', wrapperId.replace('#', ''))
69 | const top =
70 | document.querySelectorAll('.gh-header-sticky').length > 0 ? 70 : 10
71 | wrapper.style.position = 'sticky'
72 | wrapper.style.setProperty('position', '-webkit-sticky', 'important')
73 | wrapper.style.top = top + 'px'
74 | wrapper.innerHTML = ''
75 |
76 | wrapper.appendChild(Title('Reactions', true))
77 | if (withLoadingSpinner) {
78 | wrapper.appendChild(LoadingSpinner())
79 | }
80 | header.appendChild(wrapper)
81 | }
82 |
83 | function LoadingSpinner() {
84 | const loadingSpinner = document.createElement('div')
85 | const side = '25px'
86 | loadingSpinner.style.width = side
87 | loadingSpinner.style.height = side
88 | loadingSpinner.style.border = `2px solid ${backgroundColor}`
89 | loadingSpinner.style.borderTop = `2px solid ${primaryColor}`
90 | loadingSpinner.style.borderRadius = '50%'
91 | loadingSpinner.style.animation = 'spin 1s linear infinite'
92 | const style = document.createElement('style')
93 | document.head.appendChild(style)
94 | const keyframes = `
95 | @keyframes spin {
96 | 0% { transform: rotate(0deg); }
97 | 100% { transform: rotate(360deg); }
98 | }`
99 | style.sheet?.insertRule(keyframes)
100 |
101 | return loadingSpinner
102 | }
103 |
104 | // OBSERVE FOR PAGE MUTATIONS
105 | function hasAncestorWithId(element: Element | null, id: string) {
106 | while (element) {
107 | if (element.id === id) {
108 | return true
109 | }
110 | element = element.parentElement
111 | }
112 | return false
113 | }
114 |
115 | const observer = new MutationObserver((mutations: MutationRecord[]) => {
116 | for (const mutation of mutations) {
117 | if (
118 | hasAncestorWithId(
119 | mutation.target as Element | null,
120 | sideBarId.replace('#', '')
121 | ) ||
122 | hasAncestorWithId(
123 | mutation.target as Element | null,
124 | wrapperId.replace('#', '')
125 | )
126 | ) {
127 | continue
128 | }
129 |
130 | // Check if the URL contains /discussions/ or /issues/
131 | if (/\/(discussions|issues|pull)\//.test(window.location.pathname)) {
132 | addReactionNav()
133 | }
134 | }
135 | })
136 |
137 | // Start observing mutations on the whole document
138 | observer.observe(document, {
139 | childList: true,
140 | subtree: true,
141 | })
142 |
143 | // Scan the site for reactions and stick it into the wrapper
144 | function addReactionNav() {
145 | document.querySelector(wrapperId)?.remove()
146 | injectWrapper()
147 | const wrapper = document.querySelector(wrapperId)
148 | if (!wrapper) {
149 | return
150 | }
151 |
152 | wrapper.appendChild(Reactions())
153 | if (window.location.pathname.match(/\/discussions\//)) {
154 | wrapper.appendChild(Title('Discussion Votes'))
155 | wrapper.appendChild(DiscussionVotes())
156 | }
157 | wrapper.appendChild(Credits())
158 | }
159 |
160 | function Title(title: string, withSwitch = false) {
161 | const element = document.createElement('div') satisfies HTMLDivElement
162 | element.style.display = 'flex'
163 | element.style.justifyContent = 'space-between'
164 | element.style.alignItems = 'center'
165 | element.style.fontWeight = 'bold'
166 | element.style.margin = '1.25rem 0 0.5rem 0'
167 |
168 | element.appendChild(document.createTextNode(title))
169 |
170 | if (withSwitch) {
171 | const switchDiv = document.createElement('div')
172 | switchDiv.appendChild(SvgBlockIcon())
173 | switchDiv.appendChild(Switch())
174 | switchDiv.appendChild(SvgInlineBlockIcon())
175 | element.appendChild(switchDiv)
176 | }
177 |
178 | return element
179 | }
180 |
181 | const reactionClass = 'reaction-sidebar-link'
182 |
183 | function Reactions() {
184 | const all = document.createElement('div')
185 |
186 | const issueUrl =
187 | window.location.origin + window.location.pathname + window.location.search
188 |
189 | // Grabbing all reactions Reactions 👍 🚀 🎉 😄 ❤️ 😕 👎 👀
190 | const reactions = [
191 | { emoji: '👍', name: '+1' },
192 | { emoji: '🚀', name: 'rocket' },
193 | { emoji: '🎉', name: 'tada' },
194 | { emoji: '😄', name: 'smile' },
195 | { emoji: '❤️', name: 'heart' },
196 | { emoji: '😕', name: 'thinking_face' },
197 | { emoji: '👎', name: '-1' },
198 | { emoji: '👀', name: 'eyes' },
199 | ]
200 |
201 | const findReaction = (node: Element) => (reaction: typeof reactions[number]) =>
202 | node.textContent?.includes(reaction.emoji) ||
203 | node.querySelector(`g-emoji[alias="${reaction.name}"]`)
204 |
205 | Array.from(document.querySelectorAll('.js-comment-reactions-options'))
206 | .filter((node) => reactions.some(findReaction(node)))
207 | .forEach((reactionSection) => {
208 | const combinedReactions = Array.from(
209 | reactionSection.querySelectorAll('button[class*="reaction"]')
210 | )
211 | .map((btn) => ({
212 | emoji: reactions.find(findReaction(btn))?.emoji,
213 | count: btn.textContent?.match(/\d+/)?.join(''),
214 | }))
215 | .filter((reaction) => reaction.emoji && reaction.count)
216 | .reduce((acc, { emoji, count }) => `${acc} ${emoji} ${count}`, '')
217 |
218 | const linkContainer = document.createElement('div')
219 | linkContainer.classList.add(reactionClass)
220 |
221 | const a = document.createElement('a')
222 | const linkText = document.createTextNode(' ' + combinedReactions)
223 | linkContainer.appendChild(a)
224 | a.appendChild(linkText)
225 | a.title = combinedReactions
226 |
227 | let id = null
228 | while (id == null) {
229 | if (reactionSection.tagName === 'A' && reactionSection.name) {
230 | id = reactionSection.name
231 | break
232 | }
233 | if (reactionSection.id) {
234 | id = reactionSection.id
235 | break
236 | }
237 | // @ts-expect-error
238 | reactionSection = reactionSection.parentNode
239 | }
240 |
241 | linkContainer.style.margin = '0.5rem 0'
242 | a.href = issueUrl + '#' + id
243 | a.style.border = '1px solid var(--borderColor-default, #d2dff0)'
244 | a.style.borderRadius = '100px'
245 | a.style.padding = '2px 7px'
246 | a.style.color = 'var(--color-fg-muted)'
247 |
248 | all.appendChild(linkContainer)
249 | })
250 |
251 | getBrowser()
252 | .storage.sync.get([DISPLAY])
253 | .then((result: { [x: string]: string }) => {
254 | const display = (result[DISPLAY] as Display) ?? 'block'
255 | const elements = Array.from(
256 | document.getElementsByClassName(reactionClass)
257 | ) as HTMLDivElement[]
258 | for (let element of elements) {
259 | element.style.display = display
260 | }
261 | })
262 |
263 | if (all.childElementCount === 0) {
264 | const noReactions = document.createElement('div')
265 | noReactions.innerText = '🤷♂️ no reactions found'
266 | all.appendChild(noReactions)
267 | }
268 |
269 | return all
270 | }
271 |
272 | function DiscussionVotes() {
273 | const all = document.createElement('div')
274 | document.querySelectorAll('[data-url]').forEach((discussionComment) => {
275 | const defaultVote = discussionComment.querySelector(
276 | '.js-default-vote-count'
277 | )
278 | const upvotedVote = discussionComment.querySelector(
279 | '.js-upvoted-vote-count'
280 | )
281 | const isUpvote = !!discussionComment.querySelector('[data-upvoted="true"]')
282 | const vote = isUpvote ? upvotedVote : defaultVote
283 | let url = discussionComment.dataset?.url?.replace(
284 | '/comments/',
285 | '#discussioncomment-'
286 | )
287 | if (!url) return
288 |
289 | if (url.match(/body$/)) {
290 | url = `${
291 | window.location.origin +
292 | window.location.pathname +
293 | window.location.search
294 | }#${discussionComment.children[0].id}`
295 | }
296 |
297 | if (!vote || url.match(/votes$/)) return
298 | const votes = vote.textContent
299 | const a = document.createElement('a')
300 | const linkText = document.createTextNode(
301 | `\n⬆️ ${votes}${isUpvote ? ' 🫵' : ''}`
302 | )
303 | a.appendChild(linkText)
304 | a.title = url
305 | a.href = url
306 | a.style.border = '1px solid var(--borderColor-default, #d2dff0)'
307 | a.style.borderRadius = '100px'
308 | a.style.padding = '2px 7px'
309 | a.style.margin = '0.5rem 0'
310 | const linkContainer = document.createElement('div')
311 | linkContainer.appendChild(a)
312 | linkContainer.classList.add(reactionClass)
313 | all.appendChild(linkContainer)
314 | })
315 |
316 | return all
317 | }
318 |
319 | function Credits() {
320 | const credits = document.createElement('div')
321 | credits.classList.add('credits')
322 | credits.style.display = 'flex'
323 | credits.style.gap = '0.5rem'
324 | credits.style.alignItems = 'center'
325 | credits.style.margin = '1rem 0'
326 | credits.style.fontSize = '0.8rem'
327 | credits.style.color = '#777'
328 |
329 | const laptopEmojiSpan = document.createElement('span')
330 | laptopEmojiSpan.appendChild(document.createTextNode('💻'))
331 |
332 | const extensionLink = document.createElement('a')
333 | extensionLink.href =
334 | 'https://github.com/Norfeldt/github-issue-reactions-browser-extension'
335 | extensionLink.appendChild(document.createTextNode('Reactions Extension'))
336 |
337 | const madeBySpan = document.createElement('span')
338 | madeBySpan.appendChild(document.createTextNode(' by '))
339 |
340 | const authorLink = document.createElement('a')
341 | authorLink.href = 'https://github.com/Norfeldt'
342 | authorLink.appendChild(document.createTextNode('Norfeldt'))
343 |
344 | credits.appendChild(laptopEmojiSpan)
345 | credits.appendChild(extensionLink)
346 | credits.appendChild(madeBySpan)
347 | credits.appendChild(authorLink)
348 |
349 | return credits
350 | }
351 |
352 | // Create the switch container, label, input, and handle elements
353 | function Switch() {
354 | const switchContainer = document.createElement('span')
355 | const switchLabel = document.createElement('label')
356 | const switchInput = document.createElement('span')
357 | switchLabel.appendChild(switchInput)
358 | const switchHandle = document.createElement('span')
359 | switchHandle.setAttribute('class', 'switch-handle-reactions-layout')
360 | switchLabel.appendChild(switchHandle)
361 | switchContainer.appendChild(switchLabel)
362 |
363 | // Add CSS styles to the switch container
364 | switchContainer.style.display = 'inline-block'
365 | switchContainer.style.position = 'relative'
366 | switchContainer.style.backgroundColor = backgroundColor
367 | switchContainer.style.borderRadius = '14px'
368 | switchContainer.style.width = '30px'
369 | switchContainer.style.height = '17px'
370 |
371 | // Add CSS styles to the switch label
372 | switchLabel.style.display = 'block'
373 | switchLabel.style.position = 'relative'
374 | switchLabel.style.width = '100%'
375 | switchLabel.style.height = '100%'
376 | switchLabel.style.cursor = 'pointer'
377 |
378 | // Add CSS styles to the switch input
379 | switchInput.style.display = 'none'
380 |
381 | // Add CSS styles to the switch handle
382 | switchHandle.style.display = 'block'
383 | switchHandle.style.position = 'absolute'
384 | switchHandle.style.top = '1px'
385 | switchHandle.style.width = '14px'
386 | switchHandle.style.height = '14px'
387 | switchHandle.style.borderRadius = '14px'
388 | switchHandle.style.backgroundColor = primaryColor
389 | switchHandle.style.boxShadow = '0 2px 4px 0 rgba(0, 0, 0, 0.1)'
390 | switchHandle.style.transition = 'left 0.2s ease-in-out'
391 |
392 | const toggle = (value: boolean) => {
393 | switchHandle.style.left = value ? '12px' : '2px'
394 | }
395 |
396 | getBrowser()
397 | .storage.sync?.get([DISPLAY])
398 | ?.then((result) => {
399 | if (!result[DISPLAY]) return
400 | toggle(result[DISPLAY] === 'inline-block')
401 | })
402 |
403 | // Add an event listener to the switch
404 | switchContainer.addEventListener('click', async function changeSwitch() {
405 | // Get Layout from storage and change it to the opposite (either block or inline-block)
406 | const settings = await getBrowser().storage.sync.get([DISPLAY])
407 | const display: Display =
408 | settings[DISPLAY] === 'inline-block' ? 'block' : 'inline-block'
409 | getBrowser().storage.sync.set({ [DISPLAY]: display })
410 | })
411 |
412 | getBrowser().storage.onChanged.addListener(function (changes, _namespace) {
413 | for (const key in changes) {
414 | const storageChange = changes[key]
415 | if (key === DISPLAY) {
416 | toggle(storageChange.newValue === 'inline-block')
417 | }
418 | }
419 | })
420 |
421 | return switchContainer
422 | }
423 |
424 | getBrowser().storage.onChanged.addListener(function (changes) {
425 | for (let key in changes) {
426 | if (key === DISPLAY) {
427 | const display =
428 | changes[key].newValue === 'block' ? 'block' : 'inline-block'
429 | const elements = Array.from(
430 | document.getElementsByClassName(reactionClass)
431 | ) as HTMLDivElement[]
432 | for (let element of elements) {
433 | element.style.display = display
434 | }
435 | }
436 | }
437 | })
438 |
439 | function SvgBlockIcon() {
440 | const svg = `
441 |
450 | `
451 | const span = document.createElement('span')
452 | span.innerHTML = svg
453 |
454 | return span
455 | }
456 |
457 | function SvgInlineBlockIcon() {
458 | const svg = `
459 |
468 | `
469 | const span = document.createElement('span')
470 | span.innerHTML = svg
471 |
472 | return span
473 | }
474 |
475 | declare interface Element {
476 | dataset: DOMStringMap
477 | name: string
478 | }
479 |
480 | type Display = 'block' | 'inline-block'
481 |
482 | type Settings = {
483 | [DISPLAY]: Display
484 | }
485 |
--------------------------------------------------------------------------------
/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compilerOptions": {
3 | "target": "es6",
4 | "module": "CommonJS",
5 | "strict": true,
6 | "resolveJsonModule": true,
7 | "types": ["chrome", "firefox-webext-browser"]
8 | },
9 | "include": ["src", "scripts", "bundle.ts"],
10 | "exclude": ["node_modules", "dist", "scripts"]
11 | }
12 |
--------------------------------------------------------------------------------
/yarn.lock:
--------------------------------------------------------------------------------
1 | # THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
2 | # yarn lockfile v1
3 |
4 |
5 | "@cspotcode/source-map-support@^0.8.0":
6 | version "0.8.1"
7 | resolved "https://registry.yarnpkg.com/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz#00629c35a688e05a88b1cda684fb9d5e73f000a1"
8 | integrity sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==
9 | dependencies:
10 | "@jridgewell/trace-mapping" "0.3.9"
11 |
12 | "@jridgewell/resolve-uri@^3.0.3":
13 | version "3.1.0"
14 | resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.1.0.tgz#2203b118c157721addfe69d47b70465463066d78"
15 | integrity sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==
16 |
17 | "@jridgewell/sourcemap-codec@^1.4.10":
18 | version "1.4.14"
19 | resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz#add4c98d341472a289190b424efbdb096991bb24"
20 | integrity sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==
21 |
22 | "@jridgewell/trace-mapping@0.3.9":
23 | version "0.3.9"
24 | resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz#6534fd5933a53ba7cbf3a17615e273a0d1273ff9"
25 | integrity sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==
26 | dependencies:
27 | "@jridgewell/resolve-uri" "^3.0.3"
28 | "@jridgewell/sourcemap-codec" "^1.4.10"
29 |
30 | "@tsconfig/node10@^1.0.7":
31 | version "1.0.9"
32 | resolved "https://registry.yarnpkg.com/@tsconfig/node10/-/node10-1.0.9.tgz#df4907fc07a886922637b15e02d4cebc4c0021b2"
33 | integrity sha512-jNsYVVxU8v5g43Erja32laIDHXeoNvFEpX33OK4d6hljo3jDhCBDhx5dhCCTMWUojscpAagGiRkBKxpdl9fxqA==
34 |
35 | "@tsconfig/node12@^1.0.7":
36 | version "1.0.11"
37 | resolved "https://registry.yarnpkg.com/@tsconfig/node12/-/node12-1.0.11.tgz#ee3def1f27d9ed66dac6e46a295cffb0152e058d"
38 | integrity sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==
39 |
40 | "@tsconfig/node14@^1.0.0":
41 | version "1.0.3"
42 | resolved "https://registry.yarnpkg.com/@tsconfig/node14/-/node14-1.0.3.tgz#e4386316284f00b98435bf40f72f75a09dabf6c1"
43 | integrity sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==
44 |
45 | "@tsconfig/node16@^1.0.2":
46 | version "1.0.3"
47 | resolved "https://registry.yarnpkg.com/@tsconfig/node16/-/node16-1.0.3.tgz#472eaab5f15c1ffdd7f8628bd4c4f753995ec79e"
48 | integrity sha512-yOlFc+7UtL/89t2ZhjPvvB/DeAr3r+Dq58IgzsFkOAvVC6NMJXmCGjbptdXdR9qsX7pKcTL+s87FtYREi2dEEQ==
49 |
50 | "@types/archiver@^5.3.1":
51 | version "5.3.1"
52 | resolved "https://registry.yarnpkg.com/@types/archiver/-/archiver-5.3.1.tgz#02991e940a03dd1a32678fead4b4ca03d0e387ca"
53 | integrity sha512-wKYZaSXaDvTZuInAWjCeGG7BEAgTWG2zZW0/f7IYFcoHB2X2d9lkVFnrOlXl3W6NrvO6Ml3FLLu8Uksyymcpnw==
54 | dependencies:
55 | "@types/glob" "*"
56 |
57 | "@types/chrome@^0.0.209":
58 | version "0.0.209"
59 | resolved "https://registry.yarnpkg.com/@types/chrome/-/chrome-0.0.209.tgz#3c023bb9b4e51d317167b4459e2f58bbd1fbc49e"
60 | integrity sha512-YL3gz9cAKKym/b+u26p8BQuKAc3USsPRcOYZ1OWQmOw0kfYBXkxrh9ASvSRgwA8ywA4sIahio0z0chzmmLq2og==
61 | dependencies:
62 | "@types/filesystem" "*"
63 | "@types/har-format" "*"
64 |
65 | "@types/filesystem@*":
66 | version "0.0.32"
67 | resolved "https://registry.yarnpkg.com/@types/filesystem/-/filesystem-0.0.32.tgz#307df7cc084a2293c3c1a31151b178063e0a8edf"
68 | integrity sha512-Yuf4jR5YYMR2DVgwuCiP11s0xuVRyPKmz8vo6HBY3CGdeMj8af93CFZX+T82+VD1+UqHOxTq31lO7MI7lepBtQ==
69 | dependencies:
70 | "@types/filewriter" "*"
71 |
72 | "@types/filewriter@*":
73 | version "0.0.29"
74 | resolved "https://registry.yarnpkg.com/@types/filewriter/-/filewriter-0.0.29.tgz#a48795ecadf957f6c0d10e0c34af86c098fa5bee"
75 | integrity sha512-BsPXH/irW0ht0Ji6iw/jJaK8Lj3FJemon2gvEqHKpCdDCeemHa+rI3WBGq5z7cDMZgoLjY40oninGxqk+8NzNQ==
76 |
77 | "@types/firefox-webext-browser@^109.0.0":
78 | version "109.0.0"
79 | resolved "https://registry.yarnpkg.com/@types/firefox-webext-browser/-/firefox-webext-browser-109.0.0.tgz#17120057a46985ec7659dfd33589655860419929"
80 | integrity sha512-tkEjBP/zZxaS5bv8MH/0kUs3WeUm8KU3Ew1B9BtQQdq5PwtG23SXvAbjxjMSQpoIzbxyWG4Yu4mi1uB2S8W7ng==
81 |
82 | "@types/glob@*":
83 | version "8.0.0"
84 | resolved "https://registry.yarnpkg.com/@types/glob/-/glob-8.0.0.tgz#321607e9cbaec54f687a0792b2d1d370739455d2"
85 | integrity sha512-l6NQsDDyQUVeoTynNpC9uRvCUint/gSUXQA2euwmTuWGvPY5LSDUu6tkCtJB2SvGQlJQzLaKqcGZP4//7EDveA==
86 | dependencies:
87 | "@types/minimatch" "*"
88 | "@types/node" "*"
89 |
90 | "@types/har-format@*":
91 | version "1.2.10"
92 | resolved "https://registry.yarnpkg.com/@types/har-format/-/har-format-1.2.10.tgz#7b4e1e0ada4d17684ac3b05d601a4871cfab11fc"
93 | integrity sha512-o0J30wqycjF5miWDKYKKzzOU1ZTLuA42HZ4HE7/zqTOc/jTLdQ5NhYWvsRQo45Nfi1KHoRdNhteSI4BAxTF1Pg==
94 |
95 | "@types/minimatch@*":
96 | version "5.1.2"
97 | resolved "https://registry.yarnpkg.com/@types/minimatch/-/minimatch-5.1.2.tgz#07508b45797cb81ec3f273011b054cd0755eddca"
98 | integrity sha512-K0VQKziLUWkVKiRVrx4a40iPaxTUefQmjtkQofBkYRcoaaL/8rhwDWww9qWbrgicNOgnpIsMxyNIUM4+n6dUIA==
99 |
100 | "@types/node@*", "@types/node@^18.11.17":
101 | version "18.11.18"
102 | resolved "https://registry.yarnpkg.com/@types/node/-/node-18.11.18.tgz#8dfb97f0da23c2293e554c5a50d61ef134d7697f"
103 | integrity sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==
104 |
105 | acorn-walk@^8.1.1:
106 | version "8.2.0"
107 | resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-8.2.0.tgz#741210f2e2426454508853a2f44d0ab83b7f69c1"
108 | integrity sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA==
109 |
110 | acorn@^8.4.1:
111 | version "8.8.1"
112 | resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.8.1.tgz#0a3f9cbecc4ec3bea6f0a80b66ae8dd2da250b73"
113 | integrity sha512-7zFpHzhnqYKrkYdUjF1HI1bzd0VygEGX8lFk4k5zVMqHEoES+P+7TKI+EvLO9WVMJ8eekdO0aDEK044xTXwPPA==
114 |
115 | archiver-utils@^2.1.0:
116 | version "2.1.0"
117 | resolved "https://registry.yarnpkg.com/archiver-utils/-/archiver-utils-2.1.0.tgz#e8a460e94b693c3e3da182a098ca6285ba9249e2"
118 | integrity sha512-bEL/yUb/fNNiNTuUz979Z0Yg5L+LzLxGJz8x79lYmR54fmTIb6ob/hNQgkQnIUDWIFjZVQwl9Xs356I6BAMHfw==
119 | dependencies:
120 | glob "^7.1.4"
121 | graceful-fs "^4.2.0"
122 | lazystream "^1.0.0"
123 | lodash.defaults "^4.2.0"
124 | lodash.difference "^4.5.0"
125 | lodash.flatten "^4.4.0"
126 | lodash.isplainobject "^4.0.6"
127 | lodash.union "^4.6.0"
128 | normalize-path "^3.0.0"
129 | readable-stream "^2.0.0"
130 |
131 | archiver@^5.3.1:
132 | version "5.3.1"
133 | resolved "https://registry.yarnpkg.com/archiver/-/archiver-5.3.1.tgz#21e92811d6f09ecfce649fbefefe8c79e57cbbb6"
134 | integrity sha512-8KyabkmbYrH+9ibcTScQ1xCJC/CGcugdVIwB+53f5sZziXgwUh3iXlAlANMxcZyDEfTHMe6+Z5FofV8nopXP7w==
135 | dependencies:
136 | archiver-utils "^2.1.0"
137 | async "^3.2.3"
138 | buffer-crc32 "^0.2.1"
139 | readable-stream "^3.6.0"
140 | readdir-glob "^1.0.0"
141 | tar-stream "^2.2.0"
142 | zip-stream "^4.1.0"
143 |
144 | arg@^4.1.0:
145 | version "4.1.3"
146 | resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089"
147 | integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==
148 |
149 | async@^3.2.3:
150 | version "3.2.4"
151 | resolved "https://registry.yarnpkg.com/async/-/async-3.2.4.tgz#2d22e00f8cddeb5fde5dd33522b56d1cf569a81c"
152 | integrity sha512-iAB+JbDEGXhyIUavoDl9WP/Jj106Kz9DEn1DPgYw5ruDn0e3Wgi3sKFm55sASdGBNOQB8F59d9qQ7deqrHA8wQ==
153 |
154 | balanced-match@^1.0.0:
155 | version "1.0.2"
156 | resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee"
157 | integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==
158 |
159 | base64-js@^1.3.1:
160 | version "1.5.1"
161 | resolved "https://registry.yarnpkg.com/base64-js/-/base64-js-1.5.1.tgz#1b1b440160a5bf7ad40b650f095963481903930a"
162 | integrity sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==
163 |
164 | bl@^4.0.3:
165 | version "4.1.0"
166 | resolved "https://registry.yarnpkg.com/bl/-/bl-4.1.0.tgz#451535264182bec2fbbc83a62ab98cf11d9f7b3a"
167 | integrity sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==
168 | dependencies:
169 | buffer "^5.5.0"
170 | inherits "^2.0.4"
171 | readable-stream "^3.4.0"
172 |
173 | brace-expansion@^1.1.7:
174 | version "1.1.11"
175 | resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd"
176 | integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==
177 | dependencies:
178 | balanced-match "^1.0.0"
179 | concat-map "0.0.1"
180 |
181 | brace-expansion@^2.0.1:
182 | version "2.0.1"
183 | resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.1.tgz#1edc459e0f0c548486ecf9fc99f2221364b9a0ae"
184 | integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA==
185 | dependencies:
186 | balanced-match "^1.0.0"
187 |
188 | buffer-crc32@^0.2.1, buffer-crc32@^0.2.13:
189 | version "0.2.13"
190 | resolved "https://registry.yarnpkg.com/buffer-crc32/-/buffer-crc32-0.2.13.tgz#0d333e3f00eac50aa1454abd30ef8c2a5d9a7242"
191 | integrity sha512-VO9Ht/+p3SN7SKWqcrgEzjGbRSJYTx+Q1pTQC0wrWqHx0vpJraQ6GtHx8tvcg1rlK1byhU5gccxgOgj7B0TDkQ==
192 |
193 | buffer@^5.5.0:
194 | version "5.7.1"
195 | resolved "https://registry.yarnpkg.com/buffer/-/buffer-5.7.1.tgz#ba62e7c13133053582197160851a8f648e99eed0"
196 | integrity sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==
197 | dependencies:
198 | base64-js "^1.3.1"
199 | ieee754 "^1.1.13"
200 |
201 | compress-commons@^4.1.0:
202 | version "4.1.1"
203 | resolved "https://registry.yarnpkg.com/compress-commons/-/compress-commons-4.1.1.tgz#df2a09a7ed17447642bad10a85cc9a19e5c42a7d"
204 | integrity sha512-QLdDLCKNV2dtoTorqgxngQCMA+gWXkM/Nwu7FpeBhk/RdkzimqC3jueb/FDmaZeXh+uby1jkBqE3xArsLBE5wQ==
205 | dependencies:
206 | buffer-crc32 "^0.2.13"
207 | crc32-stream "^4.0.2"
208 | normalize-path "^3.0.0"
209 | readable-stream "^3.6.0"
210 |
211 | concat-map@0.0.1:
212 | version "0.0.1"
213 | resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b"
214 | integrity sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==
215 |
216 | core-util-is@~1.0.0:
217 | version "1.0.3"
218 | resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.3.tgz#a6042d3634c2b27e9328f837b965fac83808db85"
219 | integrity sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==
220 |
221 | crc-32@^1.2.0:
222 | version "1.2.2"
223 | resolved "https://registry.yarnpkg.com/crc-32/-/crc-32-1.2.2.tgz#3cad35a934b8bf71f25ca524b6da51fb7eace2ff"
224 | integrity sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ==
225 |
226 | crc32-stream@^4.0.2:
227 | version "4.0.2"
228 | resolved "https://registry.yarnpkg.com/crc32-stream/-/crc32-stream-4.0.2.tgz#c922ad22b38395abe9d3870f02fa8134ed709007"
229 | integrity sha512-DxFZ/Hk473b/muq1VJ///PMNLj0ZMnzye9thBpmjpJKCc5eMgB95aK8zCGrGfQ90cWo561Te6HK9D+j4KPdM6w==
230 | dependencies:
231 | crc-32 "^1.2.0"
232 | readable-stream "^3.4.0"
233 |
234 | create-require@^1.1.0:
235 | version "1.1.1"
236 | resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333"
237 | integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==
238 |
239 | diff@^4.0.1:
240 | version "4.0.2"
241 | resolved "https://registry.yarnpkg.com/diff/-/diff-4.0.2.tgz#60f3aecb89d5fae520c11aa19efc2bb982aade7d"
242 | integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==
243 |
244 | end-of-stream@^1.4.1:
245 | version "1.4.4"
246 | resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.4.tgz#5ae64a5f45057baf3626ec14da0ca5e4b2431eb0"
247 | integrity sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==
248 | dependencies:
249 | once "^1.4.0"
250 |
251 | exec-sh@^0.2.0:
252 | version "0.2.2"
253 | resolved "https://registry.yarnpkg.com/exec-sh/-/exec-sh-0.2.2.tgz#2a5e7ffcbd7d0ba2755bdecb16e5a427dfbdec36"
254 | integrity sha512-FIUCJz1RbuS0FKTdaAafAByGS0CPvU3R0MeHxgtl+djzCc//F8HakL8GzmVNZanasTbTAY/3DRFA0KpVqj/eAw==
255 | dependencies:
256 | merge "^1.2.0"
257 |
258 | fs-constants@^1.0.0:
259 | version "1.0.0"
260 | resolved "https://registry.yarnpkg.com/fs-constants/-/fs-constants-1.0.0.tgz#6be0de9be998ce16af8afc24497b9ee9b7ccd9ad"
261 | integrity sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==
262 |
263 | fs.realpath@^1.0.0:
264 | version "1.0.0"
265 | resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f"
266 | integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==
267 |
268 | glob@^7.1.4:
269 | version "7.2.3"
270 | resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.3.tgz#b8df0fb802bbfa8e89bd1d938b4e16578ed44f2b"
271 | integrity sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==
272 | dependencies:
273 | fs.realpath "^1.0.0"
274 | inflight "^1.0.4"
275 | inherits "2"
276 | minimatch "^3.1.1"
277 | once "^1.3.0"
278 | path-is-absolute "^1.0.0"
279 |
280 | graceful-fs@^4.2.0:
281 | version "4.2.10"
282 | resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.10.tgz#147d3a006da4ca3ce14728c7aefc287c367d7a6c"
283 | integrity sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==
284 |
285 | ieee754@^1.1.13:
286 | version "1.2.1"
287 | resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.2.1.tgz#8eb7a10a63fff25d15a57b001586d177d1b0d352"
288 | integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==
289 |
290 | inflight@^1.0.4:
291 | version "1.0.6"
292 | resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9"
293 | integrity sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==
294 | dependencies:
295 | once "^1.3.0"
296 | wrappy "1"
297 |
298 | inherits@2, inherits@^2.0.3, inherits@^2.0.4, inherits@~2.0.3:
299 | version "2.0.4"
300 | resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c"
301 | integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==
302 |
303 | isarray@~1.0.0:
304 | version "1.0.0"
305 | resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11"
306 | integrity sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==
307 |
308 | lazystream@^1.0.0:
309 | version "1.0.1"
310 | resolved "https://registry.yarnpkg.com/lazystream/-/lazystream-1.0.1.tgz#494c831062f1f9408251ec44db1cba29242a2638"
311 | integrity sha512-b94GiNHQNy6JNTrt5w6zNyffMrNkXZb3KTkCZJb2V1xaEGCk093vkZ2jk3tpaeP33/OiXC+WvK9AxUebnf5nbw==
312 | dependencies:
313 | readable-stream "^2.0.5"
314 |
315 | lodash.defaults@^4.2.0:
316 | version "4.2.0"
317 | resolved "https://registry.yarnpkg.com/lodash.defaults/-/lodash.defaults-4.2.0.tgz#d09178716ffea4dde9e5fb7b37f6f0802274580c"
318 | integrity sha512-qjxPLHd3r5DnsdGacqOMU6pb/avJzdh9tFX2ymgoZE27BmjXrNy/y4LoaiTeAb+O3gL8AfpJGtqfX/ae2leYYQ==
319 |
320 | lodash.difference@^4.5.0:
321 | version "4.5.0"
322 | resolved "https://registry.yarnpkg.com/lodash.difference/-/lodash.difference-4.5.0.tgz#9ccb4e505d486b91651345772885a2df27fd017c"
323 | integrity sha512-dS2j+W26TQ7taQBGN8Lbbq04ssV3emRw4NY58WErlTO29pIqS0HmoT5aJ9+TUQ1N3G+JOZSji4eugsWwGp9yPA==
324 |
325 | lodash.flatten@^4.4.0:
326 | version "4.4.0"
327 | resolved "https://registry.yarnpkg.com/lodash.flatten/-/lodash.flatten-4.4.0.tgz#f31c22225a9632d2bbf8e4addbef240aa765a61f"
328 | integrity sha512-C5N2Z3DgnnKr0LOpv/hKCgKdb7ZZwafIrsesve6lmzvZIRZRGaZ/l6Q8+2W7NaT+ZwO3fFlSCzCzrDCFdJfZ4g==
329 |
330 | lodash.isplainobject@^4.0.6:
331 | version "4.0.6"
332 | resolved "https://registry.yarnpkg.com/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz#7c526a52d89b45c45cc690b88163be0497f550cb"
333 | integrity sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==
334 |
335 | lodash.union@^4.6.0:
336 | version "4.6.0"
337 | resolved "https://registry.yarnpkg.com/lodash.union/-/lodash.union-4.6.0.tgz#48bb5088409f16f1821666641c44dd1aaae3cd88"
338 | integrity sha512-c4pB2CdGrGdjMKYLA+XiRDO7Y0PRQbm/Gzg8qMj+QH+pFVAoTp5sBpO0odL3FjoPCGjK96p6qsP+yQoiLoOBcw==
339 |
340 | make-error@^1.1.1:
341 | version "1.3.6"
342 | resolved "https://registry.yarnpkg.com/make-error/-/make-error-1.3.6.tgz#2eb2e37ea9b67c4891f684a1394799af484cf7a2"
343 | integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==
344 |
345 | merge@^1.2.0:
346 | version "1.2.1"
347 | resolved "https://registry.yarnpkg.com/merge/-/merge-1.2.1.tgz#38bebf80c3220a8a487b6fcfb3941bb11720c145"
348 | integrity sha512-VjFo4P5Whtj4vsLzsYBu5ayHhoHJ0UqNm7ibvShmbmoz7tGi0vXaoJbGdB+GmDMLUdg8DpQXEIeVDAe8MaABvQ==
349 |
350 | minimatch@^3.1.1:
351 | version "3.1.2"
352 | resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b"
353 | integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==
354 | dependencies:
355 | brace-expansion "^1.1.7"
356 |
357 | minimatch@^5.1.0:
358 | version "5.1.2"
359 | resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.1.2.tgz#0939d7d6f0898acbd1508abe534d1929368a8fff"
360 | integrity sha512-bNH9mmM9qsJ2X4r2Nat1B//1dJVcn3+iBLa3IgqJ7EbGaDNepL9QSHOxN4ng33s52VMMhhIfgCYDk3C4ZmlDAg==
361 | dependencies:
362 | brace-expansion "^2.0.1"
363 |
364 | minimist@^1.2.0:
365 | version "1.2.7"
366 | resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.7.tgz#daa1c4d91f507390437c6a8bc01078e7000c4d18"
367 | integrity sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==
368 |
369 | normalize-path@^3.0.0:
370 | version "3.0.0"
371 | resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-3.0.0.tgz#0dcd69ff23a1c9b11fd0978316644a0388216a65"
372 | integrity sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==
373 |
374 | once@^1.3.0, once@^1.4.0:
375 | version "1.4.0"
376 | resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1"
377 | integrity sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==
378 | dependencies:
379 | wrappy "1"
380 |
381 | path-is-absolute@^1.0.0:
382 | version "1.0.1"
383 | resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f"
384 | integrity sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==
385 |
386 | process-nextick-args@~2.0.0:
387 | version "2.0.1"
388 | resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-2.0.1.tgz#7820d9b16120cc55ca9ae7792680ae7dba6d7fe2"
389 | integrity sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==
390 |
391 | readable-stream@^2.0.0, readable-stream@^2.0.5:
392 | version "2.3.7"
393 | resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.7.tgz#1eca1cf711aef814c04f62252a36a62f6cb23b57"
394 | integrity sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==
395 | dependencies:
396 | core-util-is "~1.0.0"
397 | inherits "~2.0.3"
398 | isarray "~1.0.0"
399 | process-nextick-args "~2.0.0"
400 | safe-buffer "~5.1.1"
401 | string_decoder "~1.1.1"
402 | util-deprecate "~1.0.1"
403 |
404 | readable-stream@^3.1.1, readable-stream@^3.4.0, readable-stream@^3.6.0:
405 | version "3.6.0"
406 | resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-3.6.0.tgz#337bbda3adc0706bd3e024426a286d4b4b2c9198"
407 | integrity sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==
408 | dependencies:
409 | inherits "^2.0.3"
410 | string_decoder "^1.1.1"
411 | util-deprecate "^1.0.1"
412 |
413 | readdir-glob@^1.0.0:
414 | version "1.1.2"
415 | resolved "https://registry.yarnpkg.com/readdir-glob/-/readdir-glob-1.1.2.tgz#b185789b8e6a43491635b6953295c5c5e3fd224c"
416 | integrity sha512-6RLVvwJtVwEDfPdn6X6Ille4/lxGl0ATOY4FN/B9nxQcgOazvvI0nodiD19ScKq0PvA/29VpaOQML36o5IzZWA==
417 | dependencies:
418 | minimatch "^5.1.0"
419 |
420 | safe-buffer@~5.1.0, safe-buffer@~5.1.1:
421 | version "5.1.2"
422 | resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d"
423 | integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==
424 |
425 | safe-buffer@~5.2.0:
426 | version "5.2.1"
427 | resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6"
428 | integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==
429 |
430 | string_decoder@^1.1.1:
431 | version "1.3.0"
432 | resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e"
433 | integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==
434 | dependencies:
435 | safe-buffer "~5.2.0"
436 |
437 | string_decoder@~1.1.1:
438 | version "1.1.1"
439 | resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8"
440 | integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==
441 | dependencies:
442 | safe-buffer "~5.1.0"
443 |
444 | tar-stream@^2.2.0:
445 | version "2.2.0"
446 | resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-2.2.0.tgz#acad84c284136b060dc3faa64474aa9aebd77287"
447 | integrity sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==
448 | dependencies:
449 | bl "^4.0.3"
450 | end-of-stream "^1.4.1"
451 | fs-constants "^1.0.0"
452 | inherits "^2.0.3"
453 | readable-stream "^3.1.1"
454 |
455 | ts-node@^10.9.1:
456 | version "10.9.1"
457 | resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-10.9.1.tgz#e73de9102958af9e1f0b168a6ff320e25adcff4b"
458 | integrity sha512-NtVysVPkxxrwFGUUxGYhfux8k78pQB3JqYBXlLRZgdGUqTO5wU/UyHop5p70iEbGhB7q5KmiZiU0Y3KlJrScEw==
459 | dependencies:
460 | "@cspotcode/source-map-support" "^0.8.0"
461 | "@tsconfig/node10" "^1.0.7"
462 | "@tsconfig/node12" "^1.0.7"
463 | "@tsconfig/node14" "^1.0.0"
464 | "@tsconfig/node16" "^1.0.2"
465 | acorn "^8.4.1"
466 | acorn-walk "^8.1.1"
467 | arg "^4.1.0"
468 | create-require "^1.1.0"
469 | diff "^4.0.1"
470 | make-error "^1.1.1"
471 | v8-compile-cache-lib "^3.0.1"
472 | yn "3.1.1"
473 |
474 | typescript@^5.0.0-beta:
475 | version "5.0.0-beta"
476 | resolved "https://registry.yarnpkg.com/typescript/-/typescript-5.0.0-beta.tgz#791fa95411d6ff64ee77d677ed1e6f32a2eaabaf"
477 | integrity sha512-+SSabbSXG5mtF+QGdV9uXXt9Saq1cSyI6hSG7znhaLoquleJpnmfkwSxFngK9c2fWWi1W/263TuzXQOsIcdjjA==
478 |
479 | util-deprecate@^1.0.1, util-deprecate@~1.0.1:
480 | version "1.0.2"
481 | resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf"
482 | integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==
483 |
484 | v8-compile-cache-lib@^3.0.1:
485 | version "3.0.1"
486 | resolved "https://registry.yarnpkg.com/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz#6336e8d71965cb3d35a1bbb7868445a7c05264bf"
487 | integrity sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==
488 |
489 | watch@^1.0.2:
490 | version "1.0.2"
491 | resolved "https://registry.yarnpkg.com/watch/-/watch-1.0.2.tgz#340a717bde765726fa0aa07d721e0147a551df0c"
492 | integrity sha512-1u+Z5n9Jc1E2c7qDO8SinPoZuHj7FgbgU1olSFoyaklduDvvtX7GMMtlE6OC9FTXq4KvNAOfj6Zu4vI1e9bAKA==
493 | dependencies:
494 | exec-sh "^0.2.0"
495 | minimist "^1.2.0"
496 |
497 | wrappy@1:
498 | version "1.0.2"
499 | resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f"
500 | integrity sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==
501 |
502 | yn@3.1.1:
503 | version "3.1.1"
504 | resolved "https://registry.yarnpkg.com/yn/-/yn-3.1.1.tgz#1e87401a09d767c1d5eab26a6e4c185182d2eb50"
505 | integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==
506 |
507 | zip-stream@^4.1.0:
508 | version "4.1.0"
509 | resolved "https://registry.yarnpkg.com/zip-stream/-/zip-stream-4.1.0.tgz#51dd326571544e36aa3f756430b313576dc8fc79"
510 | integrity sha512-zshzwQW7gG7hjpBlgeQP9RuyPGNxvJdzR8SUM3QhxCnLjWN2E7j3dOvpeDcQoETfHx0urRS7EtmVToql7YpU4A==
511 | dependencies:
512 | archiver-utils "^2.1.0"
513 | compress-commons "^4.1.0"
514 | readable-stream "^3.6.0"
515 |
--------------------------------------------------------------------------------