From a45efb7126357aa059919b237d9e076fc2d98568 Mon Sep 17 00:00:00 2001 From: Patrick Nelson Date: Sun, 3 Dec 2023 17:43:25 -0800 Subject: [PATCH 1/5] Issue #30: Adding .d.ts files and incorporating into build/publish process --- .gitignore | 3 +++ package-lock.json | 24 ++++++++++++++++++++++-- package.json | 5 ++++- tsconfig.json | 24 ++++++++++++++++++++++++ 4 files changed, 53 insertions(+), 3 deletions(-) create mode 100644 tsconfig.json diff --git a/.gitignore b/.gitignore index ee47302..4231334 100644 --- a/.gitignore +++ b/.gitignore @@ -5,3 +5,6 @@ coverage # In case contributors use yarn (just prevent it from being committed). Standardizing on npm for broad compatibility. yarn.lock + +# Ignore autogenerated .d.ts (and associated .map) files since this are automatically generated prior to publish to NPM. +*.d.ts* diff --git a/package-lock.json b/package-lock.json index 0e5fcdf..28557db 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "svelte-retag", - "version": "1.3.8", + "version": "1.4.0", "lockfileVersion": 2, "requires": true, "packages": { "": { "name": "svelte-retag", - "version": "1.3.8", + "version": "1.4.0", "license": "MIT", "devDependencies": { "@sveltejs/adapter-auto": "^2.1.1", @@ -15,6 +15,7 @@ "eslint-plugin-svelte": "^2.35.1", "jsdom": "^22.1.0", "svelte": "^4.2.8", + "typescript": "^5.3.3", "vite": "^4.5.1", "vitest": "^0.25.8" }, @@ -2732,6 +2733,19 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/typescript": { + "version": "5.3.3", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.3.3.tgz", + "integrity": "sha512-pXWcraxM0uxAS+tN0AG/BF2TyqmHO014Z070UsJ+pFvYuRSq8KH8DmWpnbXe0pEPDHXZV3FcAbJkijJ5oNEnWw==", + "dev": true, + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=14.17" + } + }, "node_modules/undici": { "version": "5.26.5", "resolved": "https://registry.npmjs.org/undici/-/undici-5.26.5.tgz", @@ -4901,6 +4915,12 @@ "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", "dev": true }, + "typescript": { + "version": "5.3.3", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.3.3.tgz", + "integrity": "sha512-pXWcraxM0uxAS+tN0AG/BF2TyqmHO014Z070UsJ+pFvYuRSq8KH8DmWpnbXe0pEPDHXZV3FcAbJkijJ5oNEnWw==", + "dev": true + }, "undici": { "version": "5.26.5", "resolved": "https://registry.npmjs.org/undici/-/undici-5.26.5.tgz", diff --git a/package.json b/package.json index 525f0d3..beba24b 100644 --- a/package.json +++ b/package.json @@ -3,11 +3,13 @@ "version": "1.4.0", "description": "Light DOM custom element wrapper for Svelte 3 and 4 with slots, context and Vite HMR support", "main": "index.js", + "types": "./types/index.d.ts", "scripts": { "test": "npm run eslint && vitest run", "vitest": "vitest run", "eslint": "eslint index.js tests/*", - "pub": "npm run test && npm run eslint && npm publish" + "build": "tsc --emitDeclarationOnly", + "pub": "npm run test && npm run eslint && npm run build && npm publish" }, "repository": { "type": "git", @@ -23,6 +25,7 @@ "eslint-plugin-svelte": "^2.35.1", "jsdom": "^22.1.0", "svelte": "^4.2.8", + "typescript": "^5.3.3", "vite": "^4.5.1", "vitest": "^0.25.8" }, diff --git a/tsconfig.json b/tsconfig.json new file mode 100644 index 0000000..a238c93 --- /dev/null +++ b/tsconfig.json @@ -0,0 +1,24 @@ +{ + // Only needed for JS files in the project root (exclude vite config). + "include": ["*.js"], + "exclude": ["vite.config.js"], + + // See: https://www.typescriptlang.org/docs/handbook/declaration-files/dts-from-js.html + "compilerOptions": { + // Tells TypeScript to read JS files, as + // normally they are ignored as source files + "allowJs": true, + // Generate d.ts files + "declaration": true, + // This compiler run should + // only output d.ts files + "emitDeclarationOnly": true, + // Types should go into this directory. + // Removing this would place the .d.ts files + // next to the .js files + "outDir": "types", + // go to js file when using IDE functions like + // "Go to Definition" in VSCode + "declarationMap": true + } +} From 4711adae40ea41d344af5a35e54c2e6444a67766 Mon Sep 17 00:00:00 2001 From: Patrick Nelson Date: Wed, 6 Dec 2023 14:23:25 -0800 Subject: [PATCH 2/5] Issue #30: Reworking TypeScript types in JSDoc. Making Svelte component a "newable" constructor type and also fixing the optional types by defining their defaults, so the generated .d.ts properly suffixes the "?" at the end of each optional field. --- index.js | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/index.js b/index.js index e2d73df..f7743db 100644 --- a/index.js +++ b/index.js @@ -66,24 +66,29 @@ function renderElements(timestamp) { } +/** + * @typedef {new(...args: any[]) => any} Newable Type alias for a really generic class constructor + * @typedef {Newable} SvelteComponent Svelte component class constructor (basically a "newable" object) + */ + /** * Please see README.md for usage information. * * @param {object} opts Custom element options * - * @param {any} opts.component Svelte component instance to incorporate into your custom element. - * @param {string} opts.tagname Name of the custom element tag you'd like to define. - * @param {string[]|boolean|undefined} opts.attributes Optional array of attributes that should be reactively forwarded to the component when modified. Set to true to automatically watch all attributes. - * @param {boolean?} opts.shadow Indicates if we should build the component in the shadow root instead of in the regular ("light") DOM. - * @param {string?} opts.href URL to the CSS stylesheet to incorporate into the shadow DOM (if enabled). + * @param {SvelteComponent} opts.component The Svelte component *class* constructor to incorporate into your custom element (this is the imported component class, *not* an instance) + * @param {string} opts.tagname Name of the custom element tag you'd like to define. + * @param {string[]|boolean} [opts.attributes=[]] Optional array of attributes that should be reactively forwarded to the component when modified. Set to true to automatically watch all attributes. + * @param {boolean} [opts.shadow=false] Indicates if we should build the component in the shadow root instead of in the regular ("light") DOM. + * @param {string} [opts.href=""] URL to the CSS stylesheet to incorporate into the shadow DOM (if enabled). * * Experimental: - * @param {boolean?} opts.hydratable Light DOM slot hydration (specific to svelte-retag): Enables pre-rendering of the + * @param {boolean} [opts.hydratable=false] Light DOM slot hydration (specific to svelte-retag): Enables pre-rendering of the * web component (e.g. SSR) by adding extra markers (attributes & wrappers) during * rendering to enable svelte-retag to find and restore light DOM slots when * restoring interactivity. * - * @param {boolean|string?} opts.debugMode Hidden option to enable debugging for package development purposes. + * @param {boolean|string} [opts.debugMode=false] Hidden option to enable debugging for package development purposes. */ export default function svelteRetag(opts) { /** From 0cf3426364eb1706b2d70b06eac7fb5430ebba95 Mon Sep 17 00:00:00 2001 From: Patrick Nelson Date: Wed, 6 Dec 2023 14:34:25 -0800 Subject: [PATCH 3/5] Issue #30: Minor formatting (JSDoc indentation) --- index.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/index.js b/index.js index f7743db..da53dbf 100644 --- a/index.js +++ b/index.js @@ -83,10 +83,10 @@ function renderElements(timestamp) { * @param {string} [opts.href=""] URL to the CSS stylesheet to incorporate into the shadow DOM (if enabled). * * Experimental: - * @param {boolean} [opts.hydratable=false] Light DOM slot hydration (specific to svelte-retag): Enables pre-rendering of the - * web component (e.g. SSR) by adding extra markers (attributes & wrappers) during - * rendering to enable svelte-retag to find and restore light DOM slots when - * restoring interactivity. + * @param {boolean} [opts.hydratable=false] Light DOM slot hydration (specific to svelte-retag): Enables pre-rendering of the + * web component (e.g. SSR) by adding extra markers (attributes & wrappers) during + * rendering to enable svelte-retag to find and restore light DOM slots when + * restoring interactivity. * * @param {boolean|string} [opts.debugMode=false] Hidden option to enable debugging for package development purposes. */ From 1efa1387b82a57a74db1436e9e1af1592c132066 Mon Sep 17 00:00:00 2001 From: Patrick Nelson Date: Wed, 6 Dec 2023 15:44:01 -0800 Subject: [PATCH 4/5] Issue #30: Adding note in changelog. --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index 0d193c3..db4ddf9 100644 --- a/README.md +++ b/README.md @@ -153,6 +153,7 @@ Changes since forking from [`svelte-tag`](https://github.com/crisward/svelte-tag - Add step-by-step instructions and provided a simple MVP example (https://github.com/patricknelson/svelte-retag/pull/24) - Automatically forward all attributes to component (i.e. `attributes: true`) (https://github.com/patricknelson/svelte-retag/issues/34) +- Add better TypeScript support (https://github.com/patricknelson/svelte-retag/pull/33) ### v2 From ef5955fc08abe98d5204a67932871c9db86d4a21 Mon Sep 17 00:00:00 2001 From: Patrick Nelson Date: Thu, 7 Dec 2023 12:52:19 -0800 Subject: [PATCH 5/5] Issue #30: Using 'CmpConstructor' instead of 'SvelteComponent' as the custom type for 'component' to prevent any confusion with an actual Svelte type. --- index.js | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/index.js b/index.js index da53dbf..ac541b7 100644 --- a/index.js +++ b/index.js @@ -67,8 +67,8 @@ function renderElements(timestamp) { /** - * @typedef {new(...args: any[]) => any} Newable Type alias for a really generic class constructor - * @typedef {Newable} SvelteComponent Svelte component class constructor (basically a "newable" object) + * @typedef {new(...args: any[]) => any} Newable Type alias for a really generic class constructor + * @typedef {Newable} CmpConstructor Svelte component class constructor (basically a "newable" object) */ /** @@ -76,17 +76,17 @@ function renderElements(timestamp) { * * @param {object} opts Custom element options * - * @param {SvelteComponent} opts.component The Svelte component *class* constructor to incorporate into your custom element (this is the imported component class, *not* an instance) + * @param {CmpConstructor} opts.component The Svelte component *class* constructor to incorporate into your custom element (this is the imported component class, *not* an instance) * @param {string} opts.tagname Name of the custom element tag you'd like to define. * @param {string[]|boolean} [opts.attributes=[]] Optional array of attributes that should be reactively forwarded to the component when modified. Set to true to automatically watch all attributes. * @param {boolean} [opts.shadow=false] Indicates if we should build the component in the shadow root instead of in the regular ("light") DOM. * @param {string} [opts.href=""] URL to the CSS stylesheet to incorporate into the shadow DOM (if enabled). * * Experimental: - * @param {boolean} [opts.hydratable=false] Light DOM slot hydration (specific to svelte-retag): Enables pre-rendering of the - * web component (e.g. SSR) by adding extra markers (attributes & wrappers) during - * rendering to enable svelte-retag to find and restore light DOM slots when - * restoring interactivity. + * @param {boolean} [opts.hydratable=false] EXPERIMENTAL.Light DOM slot hydration (specific to svelte-retag): Enables + * pre-rendering of the web component (e.g. SSR) by adding extra markers + * (attributes & wrappers) during rendering to enable svelte-retag to find and + * restore light DOM slots when restoring interactivity. See README.md for more. * * @param {boolean|string} [opts.debugMode=false] Hidden option to enable debugging for package development purposes. */