@kitschpatrol/create-project 1.0.4 → 1.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (75) hide show
  1. package/dist/index.js +15 -10
  2. package/package.json +9 -7
  3. package/readme.md +6 -0
  4. package/templates/cli/.npmrc +3 -0
  5. package/templates/cli/.vscode/settings.json +2 -2
  6. package/templates/cli/mdat.config.ts +6 -1
  7. package/templates/cli/package.json +8 -6
  8. package/templates/cli/pnpm-lock.yaml +1512 -0
  9. package/templates/cli/src/index.ts +8 -0
  10. package/templates/cli+library/.npmrc +3 -0
  11. package/templates/cli+library/.vscode/settings.json +2 -2
  12. package/templates/cli+library/mdat.config.ts +6 -1
  13. package/templates/cli+library/package.json +10 -8
  14. package/templates/cli+library/src/bin/cli.ts +11 -3
  15. package/templates/cli+library/src/lib/index.ts +6 -0
  16. package/templates/cli+library/src/lib/log.ts +16 -0
  17. package/templates/cli+library/tsconfig.build.json +0 -3
  18. package/templates/electron/.github/workflows/github-release.yml +81 -0
  19. package/templates/electron/.github/workflows/set-github-metadata.yml +21 -0
  20. package/templates/{cli+library/node_modules/.pnpm/@kitschpatrol+repo-config@5.7.4_@types+node@20.19.21_typescript@5.9.3/node_modules/@kitschpatrol/repo-config/init → electron}/.gitignore +2 -0
  21. package/templates/{web/node_modules/.pnpm/@kitschpatrol+repo-config@5.7.4_@types+node@20.19.21_typescript@5.9.3/node_modules/@kitschpatrol/repo-config/init → electron}/.npmrc +3 -0
  22. package/templates/electron/.prettierignore +8 -0
  23. package/templates/electron/.remarkrc.js +8 -0
  24. package/templates/electron/.vscode/extensions.json +9 -0
  25. package/templates/electron/.vscode/settings.json +68 -0
  26. package/templates/electron/cspell.config.js +5 -0
  27. package/templates/electron/electron/electron-env.d.ts +29 -0
  28. package/templates/electron/electron/main.ts +50 -0
  29. package/templates/electron/electron/preload.ts +130 -0
  30. package/templates/electron/electron/resources/icons/mac/icon.icns +0 -0
  31. package/templates/electron/electron/resources/icons/png/1024x1024.png +0 -0
  32. package/templates/electron/electron/resources/icons/win/icon.ico +0 -0
  33. package/templates/electron/electron/resources/mac/entitlements.mac.plist +11 -0
  34. package/templates/electron/electron-builder.ts +40 -0
  35. package/templates/electron/eslint.config.ts +22 -0
  36. package/templates/electron/index.html +13 -0
  37. package/templates/electron/knip.config.ts +3 -0
  38. package/templates/electron/license.txt +21 -0
  39. package/templates/electron/mdat.config.ts +3 -0
  40. package/templates/electron/package.json +61 -0
  41. package/templates/electron/pnpm-workspace.yaml +3 -0
  42. package/templates/electron/prettier.config.js +3 -0
  43. package/templates/electron/public/vite.svg +35 -0
  44. package/templates/electron/readme.md +29 -0
  45. package/templates/electron/src/counter.ts +15 -0
  46. package/templates/electron/src/main.ts +27 -0
  47. package/templates/electron/src/style.css +102 -0
  48. package/templates/electron/src/typescript.svg +14 -0
  49. package/templates/electron/stylelint.config.js +3 -0
  50. package/templates/electron/tsconfig.json +9 -0
  51. package/templates/electron/vite.config.ts +15 -0
  52. package/templates/library/.npmrc +3 -0
  53. package/templates/library/.vscode/settings.json +2 -2
  54. package/templates/library/package.json +10 -9
  55. package/templates/library/pnpm-workspace.yaml +0 -1
  56. package/templates/library/src/index.ts +6 -0
  57. package/templates/library/src/log.ts +16 -0
  58. package/templates/library/tsconfig.build.json +0 -3
  59. package/templates/minimal/.npmrc +3 -0
  60. package/templates/minimal/.vscode/settings.json +2 -2
  61. package/templates/minimal/package.json +3 -3
  62. package/templates/minimal/pnpm-workspace.yaml +0 -1
  63. package/templates/minimal/tsconfig.build.json +0 -3
  64. package/templates/web/.npmrc +3 -0
  65. package/templates/web/.vscode/settings.json +2 -2
  66. package/templates/web/package.json +4 -4
  67. package/templates/web/pnpm-workspace.yaml +0 -1
  68. package/templates/cli+library/node_modules/.pnpm/@kitschpatrol+repo-config@5.7.4_@types+node@20.19.21_typescript@5.9.3/node_modules/@kitschpatrol/repo-config/init/.npmrc +0 -13
  69. package/templates/cli+library/node_modules/.pnpm/@kitschpatrol+shared-config@5.7.4_@types+estree@1.0.8_@types+node@20.19.21_@typescript-_2447bd682c28a4894c15b76c356f369c/node_modules/@kitschpatrol/repo-config/init/.npmrc +0 -13
  70. package/templates/cli+library/node_modules/@kitschpatrol/repo-config/init/.npmrc +0 -13
  71. package/templates/cli+library/pnpm-lock.yaml +0 -10094
  72. package/templates/web/node_modules/.pnpm/@kitschpatrol+repo-config@5.7.4_@types+node@20.19.21_typescript@5.9.3/node_modules/@kitschpatrol/repo-config/init/.gitignore +0 -22
  73. package/templates/web/node_modules/.pnpm/@kitschpatrol+shared-config@5.7.4_@types+estree@1.0.8_@types+node@20.19.21_@typescript-_2447bd682c28a4894c15b76c356f369c/node_modules/@kitschpatrol/repo-config/init/.npmrc +0 -13
  74. package/templates/web/node_modules/@kitschpatrol/repo-config/init/.npmrc +0 -13
  75. package/templates/web/pnpm-lock.yaml +0 -10213
@@ -1,5 +1,6 @@
1
1
  #!/usr/bin/env node
2
2
 
3
+ import { log, setDefaultLogOptions } from 'lognow'
3
4
  import yargs from 'yargs'
4
5
  import { hideBin } from 'yargs/helpers'
5
6
  import { bin, version } from '../package.json'
@@ -12,9 +13,14 @@ await yargsInstance
12
13
  .scriptName(cliCommandName)
13
14
  .usage('$0 [command]', `Run a ${cliCommandName} command.`)
14
15
  .option('verbose', {
16
+ default: false,
15
17
  description: 'Run with verbose logging',
16
18
  type: 'boolean',
17
19
  })
20
+ .middleware((argv) => {
21
+ // Set log level globally based on verbose flag
22
+ setDefaultLogOptions({ verbose: argv.verbose })
23
+ })
18
24
  .command(
19
25
  ['$0', 'do-something'],
20
26
  'Run the do-something command.',
@@ -22,6 +28,7 @@ await yargsInstance
22
28
  // Options go here
23
29
  },
24
30
  () => {
31
+ log.debug('Running command...')
25
32
  process.stdout.write('Did something!\n')
26
33
  },
27
34
  )
@@ -32,6 +39,7 @@ await yargsInstance
32
39
  // Options go here
33
40
  },
34
41
  () => {
42
+ log.debug('Running command...')
35
43
  process.stdout.write('Did something else!\n')
36
44
  },
37
45
  )
@@ -11,3 +11,6 @@ public-hoist-pattern[]=*mdat*
11
11
  public-hoist-pattern[]=*prettier*
12
12
  public-hoist-pattern[]=*remark*
13
13
  public-hoist-pattern[]=*stylelint*
14
+
15
+ # Required for automated local publishing
16
+ //registry.npmjs.org/:_authToken=${NPM_AUTH_TOKEN}
@@ -2,8 +2,8 @@
2
2
  "explorer.fileNesting.enabled": true,
3
3
  "explorer.fileNesting.expand": false,
4
4
  "explorer.fileNesting.patterns": {
5
- "*.js": "*.ts.map, *.js.map, *.d.ts, *.d.ts.map, *.d.js.map",
6
- "*.ts": "*.ts.map, *.d.ts, *.d.ts.map",
5
+ "*.js": "${basename}.ts.map, ${basename}.js.map, ${basename}.d.ts, ${basename}.d.ts.map, ${basename}.d.js.map",
6
+ "*.ts": "${basename}.ts.map, ${basename}.d.ts, ${basename}.d.ts.map",
7
7
  ".env": ".env.*",
8
8
  "package.json": ".*ignore, .*rc, .*.js, .*.mjs, .*.cjs, .*.ts, .*.mts, .*.cts, .*.json, .*.jsonc, .*.json5, .*.yml, .*.yaml, *config.js, *config.mjs, *config.cjs, *config.ts, *config.mts, *config.cts, *config.json, *config.jsonc, *config.json5, *config.yml, *config.yaml, pnpm*, workspace*, yarn*, lerna.json, netlify.toml, package-lock.json, turbo.json, vercel.json, wrangler.toml, yarn.lock",
9
9
  "readme.md": "authors*, backers*, changelog*, citation*, code_of_conduct*, contributing*, contributors*, copying*, credits*, governance*, history*, license*, maintainers*, release_notes*, security*, sponsors*"
@@ -1,3 +1,8 @@
1
1
  import { mdatConfig } from '@kitschpatrol/mdat-config'
2
+ import cliHelpPlugin from 'mdat-plugin-cli-help'
2
3
 
3
- export default mdatConfig()
4
+ export default mdatConfig({
5
+ rules: {
6
+ ...cliHelpPlugin,
7
+ },
8
+ })
@@ -21,8 +21,8 @@
21
21
  "type": "module",
22
22
  "exports": {
23
23
  ".": {
24
- "import": "./dist/lib/index.js",
25
- "types": "./dist/lib/index.d.ts"
24
+ "types": "./dist/lib/index.d.ts",
25
+ "import": "./dist/lib/index.js"
26
26
  }
27
27
  },
28
28
  "main": "./dist/lib/index.js",
@@ -38,21 +38,23 @@
38
38
  "clean": "git rm -f pnpm-lock.yaml ; git clean -fdX",
39
39
  "fix": "ksc fix",
40
40
  "lint": "ksc lint",
41
- "release": "bumpp --commit 'Release: %s' && pnpm run build && pnpm publish --otp $({{npm-otp-command}})",
41
+ "release": "bumpp --commit 'Release: %s' && pnpm run build && NPM_AUTH_TOKEN=$({{npm-auth-command}}) && pnpm publish",
42
42
  "test": "echo \"Error: no test specified\" && exit 1"
43
43
  },
44
44
  "dependencies": {
45
- "@types/node": "^20.19.21",
46
- "@types/yargs": "^17.0.33",
45
+ "@types/node": "^20.19.24",
46
+ "@types/yargs": "^17.0.34",
47
+ "lognow": "^0.2.1",
47
48
  "yargs": "^17.7.2"
48
49
  },
49
50
  "devDependencies": {
50
- "@kitschpatrol/shared-config": "^5.7.4",
51
+ "@kitschpatrol/shared-config": "^5.8.0",
51
52
  "bumpp": "^10.3.1",
52
- "tsdown": "^0.15.7",
53
+ "mdat-plugin-cli-help": "^1.0.1",
54
+ "tsdown": "^0.15.12",
53
55
  "typescript": "~5.9.3"
54
56
  },
55
- "packageManager": "pnpm@10.18.3",
57
+ "packageManager": "pnpm@10.20.0",
56
58
  "engines": {
57
59
  "node": ">=20.19.0"
58
60
  },
@@ -3,8 +3,10 @@
3
3
  import yargs from 'yargs'
4
4
  import { hideBin } from 'yargs/helpers'
5
5
  import { version, bin } from '../../package.json'
6
+ import { log, setDefaultLogOptions } from 'lognow'
7
+ import { doSomething, doSomethingElse, setLogger } from '../lib'
6
8
 
7
- import { doSomething, doSomethingElse } from '../lib'
9
+ setLogger(log)
8
10
 
9
11
  const cliCommandName = Object.keys(bin).at(0)!
10
12
  const yargsInstance = yargs(hideBin(process.argv))
@@ -17,6 +19,10 @@ await yargsInstance
17
19
  description: 'Run with verbose logging',
18
20
  type: 'boolean',
19
21
  })
22
+ .middleware((argv) => {
23
+ // Set log level globally based on verbose flag
24
+ setDefaultLogOptions({ verbose: argv.verbose })
25
+ })
20
26
  .command(
21
27
  ['$0', 'do-something'],
22
28
  'Run the do-something command.',
@@ -24,7 +30,8 @@ await yargsInstance
24
30
  // Options go here
25
31
  },
26
32
  () => {
27
- process.stdout.write(doSomething())
33
+ log.debug('Running command...')
34
+ process.stdout.write(doSomething() + '\n')
28
35
  },
29
36
  )
30
37
  .command(
@@ -34,7 +41,8 @@ await yargsInstance
34
41
  // Options go here
35
42
  },
36
43
  () => {
37
- process.stdout.write(doSomethingElse())
44
+ log.debug('Running command...')
45
+ process.stdout.write(doSomethingElse() + '\n')
38
46
  },
39
47
  )
40
48
  .alias('h', 'help')
@@ -1,7 +1,10 @@
1
+ import { log } from './log'
2
+
1
3
  /**
2
4
  * Do something.
3
5
  */
4
6
  export function doSomething(): string {
7
+ log.info('Doing something...')
5
8
  return 'Something happened'
6
9
  }
7
10
 
@@ -9,5 +12,8 @@ export function doSomething(): string {
9
12
  * Do something else.
10
13
  */
11
14
  export function doSomethingElse(): string {
15
+ log.info('Doing something else...')
12
16
  return 'Something else happened'
13
17
  }
18
+
19
+ export { setLogger } from './log'
@@ -0,0 +1,16 @@
1
+ import type { ILogBasic, ILogLayer } from 'lognow'
2
+ import { createLogger, injectionHelper } from 'lognow'
3
+
4
+ /**
5
+ * The default logger instance for the library.
6
+ */
7
+ export let log = createLogger()
8
+
9
+ /**
10
+ * Set the logger instance for the module.
11
+ * Export this for library consumers to inject their own logger.
12
+ * @param logger - Accepts either a LogLayer instance or a Console- or Stream-like log target
13
+ */
14
+ export function setLogger(logger?: ILogBasic | ILogLayer) {
15
+ log = injectionHelper(logger)
16
+ }
@@ -1,8 +1,5 @@
1
1
  {
2
2
  "extends": "./tsconfig.json",
3
- "compilerOptions": {
4
- "declarationMap": true
5
- },
6
3
  "include": ["**/*", "**/**.*"],
7
4
  "exclude": ["**/dist/", "**/bin/"]
8
5
  }
@@ -0,0 +1,81 @@
1
+ name: Create GitHub Release
2
+
3
+ on:
4
+ push:
5
+ tags:
6
+ - 'v[0-9]*'
7
+
8
+ jobs:
9
+ build:
10
+ name: Create Release
11
+ runs-on: ubuntu-latest
12
+ env:
13
+ ACCESS_TOKEN: ${{ secrets.PERSONAL_ACCESS_TOKEN || secrets.GITHUB_TOKEN }}
14
+ IS_VALID_COMMIT: false
15
+ TAG_NAME: ''
16
+
17
+ steps:
18
+ - name: Checkout
19
+ uses: actions/checkout@v4
20
+ with:
21
+ fetch-depth: 0
22
+
23
+ - name: Log Token Type
24
+ run: |
25
+ if [ ${{ env.ACCESS_TOKEN }} == ${{ secrets.GITHUB_TOKEN }} ]; then
26
+ echo "🗝️ Authenticated with GitHub Token"
27
+ else
28
+ echo "🔑 Authenticated with Personal Access token"
29
+ fi
30
+
31
+ - name: Validate Tag and Branch
32
+ id: validation
33
+ run: |
34
+ TAG=$(git tag --contains HEAD | grep '^v[0-9]' | head -n 1)
35
+ echo "🏷️ Tag for commit is: $TAG"
36
+ BRANCH=$(git branch -r --contains tags/${GITHUB_REF_NAME} | grep 'origin/main' | xargs)
37
+ if [[ -z "$BRANCH" ]]; then
38
+ echo "🚨 Tag is not on main branch"
39
+ else
40
+ echo "🕊️ Current branch is: $BRANCH"
41
+ fi
42
+ if [[ -z "$TAG" || -z "$BRANCH" ]]; then
43
+ echo "IS_VALID_COMMIT=false" >> "$GITHUB_ENV"
44
+ echo "TAG_NAME=''" >> "$GITHUB_ENV"
45
+ else
46
+ echo "IS_VALID_COMMIT=true" >> "$GITHUB_ENV"
47
+ echo "TAG_NAME=$TAG" >> "$GITHUB_ENV"
48
+ fi
49
+
50
+ - name: Release Notes
51
+ if: env.IS_VALID_COMMIT == 'true'
52
+ id: release-notes
53
+ uses: kitschpatrol/github-action-release-changelog@v2
54
+
55
+ - name: Release
56
+ if: env.IS_VALID_COMMIT == 'true'
57
+ id: release
58
+ uses: kitschpatrol/github-action-release@v2
59
+ with:
60
+ token: ${{ env.ACCESS_TOKEN }}
61
+ draft: false
62
+ prerelease: false
63
+ name: ${{ env.TAG_NAME }}
64
+ tag_name: ${{ env.TAG_NAME }}
65
+ body: |
66
+ ${{ steps.release-notes.outputs.changelog }}
67
+ files: |
68
+ readme.md
69
+ README.md
70
+ LICENSE
71
+ license.txt
72
+ CHANGELOG
73
+ CHANGELOG.md
74
+ changelog.md
75
+
76
+ - name: Log Release Details
77
+ if: env.IS_VALID_COMMIT == 'true'
78
+ run: |
79
+ echo "📦 Successfully released: ${{ env.TAG_NAME }}"
80
+ echo "🔗 Release URL: ${{ steps.release.outputs.url }}"
81
+ echo "🪪 Release ID: ${{ steps.release.outputs.id }}"
@@ -0,0 +1,21 @@
1
+ name: Set GitHub Metadata
2
+ on:
3
+ push:
4
+ branches: [main]
5
+ workflow_dispatch: {}
6
+
7
+ jobs:
8
+ build:
9
+ name: Set GitHub Metadata
10
+ runs-on: ubuntu-latest
11
+
12
+ steps:
13
+ - name: Checkout
14
+ uses: actions/checkout@v4
15
+ with:
16
+ fetch-depth: 0
17
+
18
+ - name: Sync Package info to GitHub
19
+ uses: kitschpatrol/github-action-repo-sync@v3
20
+ with:
21
+ TOKEN: ${{ secrets.PERSONAL_ACCESS_TOKEN }}
@@ -11,3 +11,6 @@ public-hoist-pattern[]=*mdat*
11
11
  public-hoist-pattern[]=*prettier*
12
12
  public-hoist-pattern[]=*remark*
13
13
  public-hoist-pattern[]=*stylelint*
14
+
15
+ # Required for automated local publishing
16
+ //registry.npmjs.org/:_authToken=${NPM_AUTH_TOKEN}
@@ -0,0 +1,8 @@
1
+ # Prettier Ignore
2
+ # Also respects .gitignore
3
+
4
+ # @kitschpatrol/prettier-config boilerplate
5
+ pnpm-lock.yaml
6
+ package-lock.json
7
+
8
+ # Customizations
@@ -0,0 +1,8 @@
1
+ import { remarkConfig } from '@kitschpatrol/remark-config'
2
+
3
+ export default remarkConfig({
4
+ rules: [
5
+ // Useful if the repository is not yet pushed to a remote.
6
+ ['remarkValidateLinks', { repository: false }],
7
+ ],
8
+ })
@@ -0,0 +1,9 @@
1
+ {
2
+ "recommendations": [
3
+ "dbaeumer.vscode-eslint",
4
+ "esbenp.prettier-vscode",
5
+ "streetsidesoftware.code-spell-checker",
6
+ "stylelint.vscode-stylelint",
7
+ "unifiedjs.vscode-mdx"
8
+ ]
9
+ }
@@ -0,0 +1,68 @@
1
+ {
2
+ "explorer.fileNesting.enabled": true,
3
+ "explorer.fileNesting.expand": false,
4
+ "explorer.fileNesting.patterns": {
5
+ "*.js": "${basename}.ts.map, ${basename}.js.map, ${basename}.d.ts, ${basename}.d.ts.map, ${basename}.d.js.map",
6
+ "*.ts": "${basename}.ts.map, ${basename}.d.ts, ${basename}.d.ts.map",
7
+ ".env": ".env.*",
8
+ "package.json": ".*ignore, .*rc, .*.js, .*.mjs, .*.cjs, .*.ts, .*.mts, .*.cts, .*.json, .*.jsonc, .*.json5, .*.yml, .*.yaml, *config.js, *config.mjs, *config.cjs, *config.ts, *config.mts, *config.cts, *config.json, *config.jsonc, *config.json5, *config.yml, *config.yaml, pnpm*, workspace*, yarn*, lerna.json, netlify.toml, package-lock.json, turbo.json, vercel.json, wrangler.toml, yarn.lock",
9
+ "readme.md": "authors*, backers*, changelog*, citation*, code_of_conduct*, contributing*, contributors*, copying*, credits*, governance*, history*, license*, maintainers*, release_notes*, security*, sponsors*"
10
+ },
11
+ "typescript.enablePromptUseWorkspaceTsdk": true,
12
+ "typescript.tsdk": "node_modules/typescript/lib",
13
+ "editor.codeActionsOnSave": {
14
+ "source.fixAll": "explicit",
15
+ "source.organizeImports": "never"
16
+ },
17
+ "eslint.enable": true,
18
+ "eslint.runtime": "node",
19
+ "eslint.validate": [
20
+ "astro",
21
+ "html",
22
+ "javascript",
23
+ "javascriptreact",
24
+ "json",
25
+ "json5",
26
+ "jsonc",
27
+ "markdown",
28
+ "mdx",
29
+ "svelte",
30
+ "toml",
31
+ "typescript",
32
+ "typescriptreact",
33
+ "xml",
34
+ "yaml"
35
+ ],
36
+ "eslint.useFlatConfig": true,
37
+ "cSpell.enabled": true,
38
+ "cSpell.workspaceRootPath": ".",
39
+ "[astro]": {
40
+ "editor.defaultFormatter": "esbenp.prettier-vscode"
41
+ },
42
+ "[gitignore]": {
43
+ "editor.defaultFormatter": "esbenp.prettier-vscode"
44
+ },
45
+ "[ruby]": {
46
+ "editor.defaultFormatter": "esbenp.prettier-vscode"
47
+ },
48
+ "[shellscript]": {
49
+ "editor.defaultFormatter": "esbenp.prettier-vscode"
50
+ },
51
+ "[svelte]": {
52
+ "editor.defaultFormatter": "esbenp.prettier-vscode"
53
+ },
54
+ "editor.defaultFormatter": "esbenp.prettier-vscode",
55
+ "editor.formatOnSave": true,
56
+ "prettier.documentSelectors": [
57
+ "**/.eslintignore",
58
+ "**/.node-version",
59
+ "**/.npmrc",
60
+ "**/.prettierignore",
61
+ "**/*.astro",
62
+ "**/*.rb",
63
+ "**/*.svelte"
64
+ ],
65
+ "prettier.enable": true,
66
+ "stylelint.enable": true,
67
+ "stylelint.validate": ["css", "html", "svelte", "astro"]
68
+ }
@@ -0,0 +1,5 @@
1
+ import { cspellConfig } from '@kitschpatrol/cspell-config'
2
+
3
+ export default cspellConfig({
4
+ words: ['asar', 'nsis'],
5
+ })
@@ -0,0 +1,29 @@
1
+ /* eslint-disable ts/consistent-type-definitions */
2
+ /* eslint-disable ts/naming-convention */
3
+
4
+ declare namespace NodeJS {
5
+ interface ProcessEnv {
6
+ /**
7
+ * The built directory structure
8
+ *
9
+ * ```tree
10
+ * ├─┬ dist
11
+ * │ ├─┬ electron
12
+ * │ │ ├── main.js
13
+ * │ │ └── preload.js
14
+ * │ ├── index.html
15
+ * │ ├── ...other-static-files-from-public
16
+ * │
17
+ * ```
18
+ */
19
+ DIST: string
20
+ /** /dist/ or /public/ */
21
+ VITE_PUBLIC: string
22
+ }
23
+ }
24
+
25
+ // Used in Renderer process, expose in `preload.ts`
26
+ interface Window {
27
+ // eslint-disable-next-line ts/consistent-type-imports
28
+ ipcRenderer: import('electron').IpcRenderer
29
+ }
@@ -0,0 +1,50 @@
1
+ import { app, BrowserWindow } from 'electron'
2
+ import { log } from 'lognow/electron'
3
+ import path from 'node:path'
4
+
5
+ process.env.ELECTRON_DISABLE_SECURITY_WARNINGS = 'true'
6
+ process.env.DIST = path.join(import.meta.dirname, '../dist')
7
+ process.env.VITE_PUBLIC = app.isPackaged
8
+ ? process.env.DIST
9
+ : path.join(process.env.DIST, '../public')
10
+
11
+ if (!app.requestSingleInstanceLock()) {
12
+ app.quit()
13
+ process.exit(0)
14
+ }
15
+
16
+ let win: BrowserWindow | undefined
17
+
18
+ async function createWindow() {
19
+ win = new BrowserWindow({
20
+ icon: path.join(process.env.VITE_PUBLIC, 'logo.svg'),
21
+ webPreferences: {
22
+ preload: path.join(import.meta.dirname, './preload.mjs'),
23
+ },
24
+ })
25
+
26
+ // Test active push message to Renderer-process.
27
+ win.webContents.on('did-finish-load', () => {
28
+ win?.webContents.send('main-process-message', new Date().toLocaleString())
29
+ })
30
+
31
+ if (process.env.VITE_DEV_SERVER_URL) {
32
+ await win.loadURL(process.env.VITE_DEV_SERVER_URL)
33
+ win.webContents.openDevTools()
34
+ } else {
35
+ //
36
+ // win.loadFile('dist/index.html')
37
+ await win.loadFile(path.join(process.env.DIST, 'index.html'))
38
+ }
39
+
40
+ log.info('Hello from Main!')
41
+ }
42
+
43
+ app.on('window-all-closed', () => {
44
+ app.quit()
45
+ win = undefined
46
+ })
47
+
48
+ app.on('ready', () => {
49
+ void createWindow()
50
+ })
@@ -0,0 +1,130 @@
1
+ /* eslint-disable ts/unbound-method */
2
+ /* eslint-disable unicorn/prefer-dom-node-remove */
3
+ /* eslint-disable unicorn/prefer-dom-node-append */
4
+ import { contextBridge, ipcRenderer } from 'electron'
5
+ import 'lognow/electron/preload'
6
+
7
+ // --------- Expose some API to the Renderer process ---------
8
+ contextBridge.exposeInMainWorld('ipcRenderer', {
9
+ async invoke(...args: Parameters<typeof ipcRenderer.invoke>) {
10
+ const [channel, ...omit] = args
11
+ // eslint-disable-next-line ts/no-unsafe-return, ts/no-unsafe-argument
12
+ return ipcRenderer.invoke(channel, ...omit)
13
+ },
14
+ off(...args: Parameters<typeof ipcRenderer.off>) {
15
+ const [channel, ...omit] = args
16
+ return ipcRenderer.off(channel, ...omit)
17
+ },
18
+ on(...args: Parameters<typeof ipcRenderer.on>) {
19
+ const [channel, listener] = args
20
+ return ipcRenderer.on(channel, (event, ...args) => {
21
+ // eslint-disable-next-line ts/no-unsafe-argument
22
+ listener(event, ...args)
23
+ })
24
+ },
25
+ send(...args: Parameters<typeof ipcRenderer.send>) {
26
+ const [channel, ...omit] = args
27
+ // eslint-disable-next-line ts/no-unsafe-argument
28
+ ipcRenderer.send(channel, ...omit)
29
+ },
30
+
31
+ // You can expose other APTs you need here.
32
+ // ...
33
+ })
34
+
35
+ // --------- Preload scripts loading ---------
36
+ async function domReady(condition: DocumentReadyState[] = ['complete', 'interactive']) {
37
+ return new Promise((resolve) => {
38
+ if (condition.includes(document.readyState)) {
39
+ resolve(true)
40
+ } else {
41
+ document.addEventListener('readystatechange', () => {
42
+ if (condition.includes(document.readyState)) {
43
+ resolve(true)
44
+ }
45
+ })
46
+ }
47
+ })
48
+ }
49
+
50
+ const safeDOM = {
51
+ append(parent: HTMLElement, child: HTMLElement) {
52
+ if (![...parent.children].includes(child)) {
53
+ return parent.appendChild(child)
54
+ }
55
+ },
56
+ remove(parent: HTMLElement, child: HTMLElement) {
57
+ if ([...parent.children].includes(child)) {
58
+ return parent.removeChild(child)
59
+ }
60
+ },
61
+ }
62
+
63
+ /**
64
+ * https://tobiasahlin.com/spinkit
65
+ * https://connoratherton.com/loaders
66
+ * https://projects.lukehaas.me/css-loaders
67
+ * https://matejkustec.github.io/SpinThatShit
68
+ */
69
+ function useLoading() {
70
+ const className = `loaders-css__square-spin`
71
+ const styleContent = `
72
+ @keyframes square-spin {
73
+ 25% { transform: perspective(100px) rotateX(180deg) rotateY(0); }
74
+ 50% { transform: perspective(100px) rotateX(180deg) rotateY(180deg); }
75
+ 75% { transform: perspective(100px) rotateX(0) rotateY(180deg); }
76
+ 100% { transform: perspective(100px) rotateX(0) rotateY(0); }
77
+ }
78
+ .${className} > div {
79
+ animation-fill-mode: both;
80
+ width: 50px;
81
+ height: 50px;
82
+ background: #fff;
83
+ animation: square-spin 3s 0s cubic-bezier(0.09, 0.57, 0.49, 0.9) infinite;
84
+ }
85
+ .app-loading-wrap {
86
+ position: fixed;
87
+ top: 0;
88
+ left: 0;
89
+ width: 100vw;
90
+ height: 100vh;
91
+ display: flex;
92
+ align-items: center;
93
+ justify-content: center;
94
+ background: #282c34;
95
+ z-index: 9;
96
+ }
97
+ `
98
+ const oStyle = document.createElement('style')
99
+ const oDiv = document.createElement('div')
100
+
101
+ oStyle.id = 'app-loading-style'
102
+ oStyle.innerHTML = styleContent
103
+ oDiv.className = 'app-loading-wrap'
104
+ oDiv.innerHTML = `<div class="${className}"><div></div></div>`
105
+
106
+ return {
107
+ appendLoading() {
108
+ safeDOM.append(document.head, oStyle)
109
+ safeDOM.append(document.body, oDiv)
110
+ },
111
+ removeLoading() {
112
+ safeDOM.remove(document.head, oStyle)
113
+ safeDOM.remove(document.body, oDiv)
114
+ },
115
+ }
116
+ }
117
+
118
+ // ----------------------------------------------------------------------
119
+
120
+ const { appendLoading, removeLoading } = useLoading()
121
+ // eslint-disable-next-line ts/no-floating-promises, unicorn/prefer-top-level-await
122
+ domReady().then(appendLoading)
123
+
124
+ // eslint-disable-next-line unicorn/prefer-add-event-listener
125
+ window.onmessage = (event) => {
126
+ // eslint-disable-next-line ts/no-unused-expressions, ts/no-unsafe-member-access
127
+ event.data.payload === 'removeLoading' && removeLoading()
128
+ }
129
+
130
+ setTimeout(removeLoading, 4999)
@@ -0,0 +1,11 @@
1
+ <?xml version="1.0" encoding="UTF-8" ?>
2
+ <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN"
3
+ "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
4
+ <plist version="1.0">
5
+ <dict>
6
+ <key>com.apple.security.cs.allow-jit</key>
7
+ <true/>
8
+ <key>com.apple.security.files.user-selected.read-only</key>
9
+ <true/>
10
+ </dict>
11
+ </plist>