feat: upgrade to svelte 4 (#372)

This commit is contained in:
Nolan Lawson 2023-11-11 08:12:20 -08:00 committed by GitHub
parent 6ce65d7648
commit e5fde551fe
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
18 changed files with 194 additions and 853 deletions

View File

@ -837,7 +837,7 @@ import Picker from 'emoji-picker-element/svelte';
`svelte.js` is the same as `picker.js`, except it `import`s Svelte rather than bundling it.
While this option can reduce your bundle size, note that it only works if your Svelte version is compatible with `emoji-picker-element`'s Svelte version (v3 currently).
While this option can reduce your bundle size, note that it only works with compatible Svelte versions. Currently Svelte v3 and v4 are supported.
## Data and offline

View File

@ -11,7 +11,7 @@ async function main () {
await mkdirp(targetDir)
await writeFile(
path.join(targetDir, 'styles.js'),
`const styles = ${JSON.stringify(styles)}; module.exports = styles;`,
`export default ${JSON.stringify(styles)};`,
'utf8'
)
}

View File

@ -1,15 +0,0 @@
const babelJest = require('babel-jest').default
module.exports = babelJest.createTransformer({
presets: [
[
'@babel/preset-env',
{
targets: {
node: 'current'
}
}
]
],
plugins: []
})

View File

@ -1,46 +1,49 @@
import '@testing-library/jest-dom/jest-globals'
import { jest } from '@jest/globals'
import * as FakeIndexedDB from 'fake-indexeddb'
import { Crypto } from '@peculiar/webcrypto'
import { ResizeObserver } from 'd2l-resize-aware/resize-observer-module.js'
import { deleteDatabase } from '../src/database/databaseLifecycle'
import styles from '../node_modules/.cache/emoji-picker-element/styles.js'
import * as fetchMockJest from 'fetch-mock-jest'
const { IDBFactory, IDBKeyRange } = FakeIndexedDB
// See https://github.com/jsdom/jsdom/issues/3455#issuecomment-1333567714
global.crypto.subtle = new Crypto().subtle
globalThis.crypto.subtle = new Crypto().subtle
if (!global.performance) {
global.performance = {}
if (!globalThis.performance) {
globalThis.performance = {}
}
if (!global.performance.mark) {
global.performance.mark = () => {}
if (!globalThis.performance.mark) {
globalThis.performance.mark = () => {}
}
if (!global.performance.measure) {
global.performance.measure = () => {}
if (!globalThis.performance.measure) {
globalThis.performance.measure = () => {}
}
jest.mock('node-fetch', () => require('fetch-mock-jest').sandbox())
jest.setTimeout(60000)
global.fetch = require('node-fetch')
global.Response = fetch.Response
global.ResizeObserver = ResizeObserver
globalThis.ResizeObserver = ResizeObserver
process.env.NODE_ENV = 'test'
process.env.STYLES = styles
global.IDBKeyRange = IDBKeyRange
global.indexedDB = new IDBFactory()
globalThis.IDBKeyRange = IDBKeyRange
globalThis.indexedDB = new IDBFactory()
beforeAll(() => {
jest.spyOn(global.console, 'log').mockImplementation()
jest.spyOn(global.console, 'warn').mockImplementation()
jest.spyOn(globalThis.console, 'log').mockImplementation()
jest.spyOn(globalThis.console, 'warn').mockImplementation()
const fetch = fetchMockJest.default.sandbox()
globalThis.fetch = fetch
globalThis.Response = fetch.Response
})
afterEach(async () => {
// fresh indexedDB for every test
const dbs = await global.indexedDB.databases()
const dbs = await globalThis.indexedDB.databases()
await Promise.all(dbs.map(({ name }) => deleteDatabase(name)))
})

View File

@ -1,5 +0,0 @@
const preprocess = require('svelte-preprocess')
module.exports = {
preprocess: preprocess()
}

5
config/svelte.config.js Normal file
View File

@ -0,0 +1,5 @@
import preprocess from 'svelte-preprocess'
export default {
preprocess: preprocess()
}

View File

@ -4,19 +4,16 @@ module.exports = {
'<rootDir>/test/spec/**/*.{spec,test}.{js,jsx,ts,tsx}'
],
transform: {
'^.+\\.js$': './config/babelJestTransform.cjs',
'^.+\\.svelte$': ['svelte-jester', {
preprocess: './config/svelte.config.cjs',
preprocess: './config/svelte.config.js',
compilerOptions: {
dev: false
}
}]
},
moduleFileExtensions: ['js', 'svelte'],
extensionsToTreatAsEsm: ['.svelte'],
testPathIgnorePatterns: ['node_modules'],
transformIgnorePatterns: [
'<rootDir>/node_modules/(?!lodash-es|if-emoji|d2l-resize-aware|fake-indexeddb)'
],
bail: true,
verbose: true,
silent: false,

View File

@ -46,9 +46,9 @@
"dev:server": "node ./test/adhoc/server.js",
"lint": "standard && stylelint '**/*.scss'",
"lint:fix": "standard --fix && stylelint --fix '**/*.scss'",
"test": "node ./bin/buildStylesForJest.js && jest --runInBand",
"test": "node ./bin/buildStylesForJest.js && NODE_OPTIONS=--experimental-vm-modules jest --runInBand",
"test:adhoc": "node ./test/adhoc/server.js",
"cover": "node ./bin/buildStylesForJest.js && jest --runInBand --coverage",
"cover": "node ./bin/buildStylesForJest.js && NODE_OPTIONS=--experimental-vm-modules jest --runInBand --coverage",
"docs": "node bin/processCustomEmoji.js",
"changelog": "conventional-changelog -p angular -i CHANGELOG.md -s",
"version": "run-s changelog docs && git add CHANGELOG.md docs"
@ -74,16 +74,15 @@
},
"homepage": "https://github.com/nolanlawson/emoji-picker-element#readme",
"devDependencies": {
"@babel/preset-env": "^7.22.20",
"@peculiar/webcrypto": "^1.4.3",
"@rollup/plugin-commonjs": "^25.0.5",
"@rollup/plugin-inject": "^5.0.5",
"@rollup/plugin-node-resolve": "^15.2.2",
"@rollup/plugin-replace": "^5.0.3",
"@rollup/plugin-strip": "^3.0.3",
"@testing-library/dom": "^9.3.3",
"@testing-library/jest-dom": "^6.1.3",
"@testing-library/user-event": "^14.5.1",
"babel-jest": "^29.7.0",
"blob-util": "^2.0.2",
"compression": "^1.7.4",
"conventional-changelog-cli": "^2.2.2",
@ -105,7 +104,6 @@
"lodash-es": "^4.17.15",
"markdown-table": "^3.0.2",
"markdown-toc": "^1.2.0",
"node-fetch": "^2.6.7",
"npm-run-all": "^4.1.5",
"playwright": "^1.38.1",
"pretty-bytes": "^6.1.1",
@ -122,8 +120,8 @@
"stylelint": "^15.10.3",
"stylelint-config-recommended-scss": "^13.0.0",
"stylelint-scss": "^5.2.1",
"svelte": "^3.59.1",
"svelte-jester": "^2.3.2",
"svelte": "^4.2.1",
"svelte-jester": "^3.0.0",
"svelte-preprocess": "^5.0.4",
"svgo": "^3.0.2",
"tachometer": "^0.7.0",
@ -165,7 +163,6 @@
"requestIdleCallback",
"test",
"expect",
"jest",
"beforeAll",
"afterAll",
"beforeEach",

View File

@ -1,3 +1,4 @@
import inject from '@rollup/plugin-inject'
import cjs from '@rollup/plugin-commonjs'
import resolve from '@rollup/plugin-node-resolve'
import replace from '@rollup/plugin-replace'
@ -43,7 +44,8 @@ const baseConfig = {
}),
svelte({
compilerOptions: {
dev
dev,
discloseVersion: false
},
preprocess: preprocessConfig
}),
@ -93,21 +95,43 @@ const entryPoints = [
{
input: './src/picker/PickerElement.js',
output: './svelte.js',
external: ['svelte', 'svelte/internal']
external: ['svelte', 'svelte/internal'],
// TODO: drop Svelte v3 support
// ensure_array_like was added in Svelte v4 - we shim it to avoid breaking Svelte v3 users
plugins: [
{
name: 'svelte-v3-compat',
transform (source) {
return source
.replaceAll('ensure_array_like(', 'ensure_array_like_shim(')
}
},
inject({
ensure_array_like_shim: [
'../../../../shims/svelte-v3-shim.js',
'ensure_array_like_shim'
]
})
],
onwarn (warning) {
if (!warning.message.includes('ensure_array_like')) { // intentionally ignore warning for unused import
console.warn(warning.message)
}
}
}
]
export default entryPoints.map(({ input, output, format = 'es', external = [] }) => {
const res = {
...baseConfig,
export default entryPoints.map(({ input, output, format = 'es', external = [], plugins = [], onwarn }) => {
return {
input,
output: {
format,
file: output,
sourcemap: dev,
exports: 'auto'
}
},
external: [...baseConfig.external, ...external],
plugins: [...baseConfig.plugins, ...plugins],
onwarn
}
res.external = [...res.external, ...external]
return res
})

9
shims/svelte-v3-shim.js Normal file
View File

@ -0,0 +1,9 @@
// TODO: drop Svelte v3 support
// ensure_array_like was added in Svelte v4 - we shim it to avoid breaking Svelte v3 users
// this code is copied from svelte v4
/* eslint-disable camelcase */
export function ensure_array_like_shim (array_like_or_iterator) {
return array_like_or_iterator?.length !== undefined
? array_like_or_iterator
: Array.from(array_like_or_iterator)
}

View File

@ -1,4 +1,4 @@
<svelte:options tag={null} /><section
<svelte:options customElement={null} /><section
class="picker"
aria-label={i18n.regionLabel}
style={pickerStyle}

View File

@ -7,7 +7,6 @@
/* global addPicker removePicker */
import puppeteer from 'puppeteer'
import fetch from 'node-fetch'
const ITERATIONS = 10

View File

@ -1,7 +1,6 @@
import puppeteer from 'puppeteer'
import prettyBytes from 'pretty-bytes'
import { markdownTable as table } from 'markdown-table'
import fetch from 'node-fetch'
const scenarios = [
'blank',

View File

@ -8,7 +8,7 @@ describe('basic fetch tests', () => {
expect(fetch).toHaveBeenCalledTimes(0)
const resp = await fetch(ALL_EMOJI)
expect(resp.headers.get('etag')).toBe('W/xxx')
expect(await (resp).json()).toStrictEqual(truncatedEmoji)
expect(await (resp).json()).toEqual(truncatedEmoji)
expect(fetch).toHaveBeenCalledTimes(1)
expect(fetch).toHaveBeenLastCalledWith(ALL_EMOJI, undefined)
})
@ -17,7 +17,7 @@ describe('basic fetch tests', () => {
expect(fetch).toHaveBeenCalledTimes(0)
const resp = await fetch(ALL_EMOJI_NO_ETAG)
expect(resp.headers.get('etag')).toBeFalsy()
expect(await (resp).json()).toStrictEqual(truncatedEmoji)
expect(await (resp).json()).toEqual(truncatedEmoji)
expect(fetch).toHaveBeenCalledTimes(1)
expect(fetch).toHaveBeenLastCalledWith(ALL_EMOJI_NO_ETAG, undefined)
})

View File

@ -1,3 +1,4 @@
import { jest } from '@jest/globals'
import { ALL_EMOJI, basicAfterEach, basicBeforeEach } from '../shared'
import Database from '../../../src/database/Database'

View File

@ -1,3 +1,4 @@
import { jest } from '@jest/globals'
import Picker from '../../../src/picker/PickerElement'
import { ALL_EMOJI, basicAfterEach, basicBeforeEach, tick, truncatedEmoji } from '../shared'
import Database from '../../../src/database/Database'

View File

@ -1,3 +1,4 @@
import { jest } from '@jest/globals'
import { basicAfterEach, basicBeforeEach, tick } from '../shared'
import Picker from '../../../src/picker/PickerElement'
import { getByRole, waitFor } from '@testing-library/dom'

903
yarn.lock

File diff suppressed because it is too large Load Diff