Skip to content

Commit 745ba45

Browse files
committed
feat: finalize v1.0.0 template (ESLint/Prettier ready, TS configs split)
- Prettier added (with Tailwind plugin) + badge - ESLint flat config fixed; per-project parsing (renderer/electron) - Project updated to pass strict rules; devtools typed; root rendering cleaned - TypeScript configs overhauled: split into renderer/electron, ESNext targets/libs
1 parent c3114a2 commit 745ba45

29 files changed

+953
-859
lines changed

README.md

Lines changed: 0 additions & 430 deletions
This file was deleted.

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
markdown/README.md

electron-builder.json5

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@
1616
win: {
1717
target: [{ target: 'nsis', arch: ['x64'] }],
1818
artifactName: '${productName}-Windows-${version}-Setup.${ext}',
19-
signAndEditExecutable: false,
2019
},
2120
nsis: {
2221
oneClick: false,

electron/backend/ctx.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,13 @@
33
*
44
* Add fields later if you need per-call data (e.g., windowId, user, db, logger).
55
*/
6+
// eslint-disable-next-line @typescript-eslint/no-empty-object-type
67
export type CallerContext = {};
78

89
/**
910
* Build the context for each IPC → tRPC call.
1011
* Extend to include request-scoped info when needed.
1112
*/
12-
export async function createCallerContext(): Promise<CallerContext> {
13+
export function createCallerContext(): CallerContext {
1314
return {};
1415
}

electron/backend/functions/os/osStats.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ export type OsStats = {
1111
uptime: number;
1212
};
1313

14-
export async function getOsStats(): Promise<OsStats> {
14+
export function getOsStats(): OsStats {
1515
return {
1616
platform: os.platform(),
1717
arch: os.arch(),

electron/backend/ipcTrpc.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
import { BrowserWindow } from 'electron';
22
import { createIPCHandler } from 'electron-trpc-experimental/main';
3-
import { appRouter } from '@app/backend/router';
3+
44
import { createCallerContext } from '@app/backend/ctx';
5+
import { appRouter } from '@app/backend/router';
56

67
export function registerTrpcHandler(win: BrowserWindow): void {
78
createIPCHandler({

electron/backend/router.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
import { initTRPC } from '@trpc/server';
2-
import type { CallerContext } from '@app/backend/ctx';
2+
33
import { osRouter } from '@app/backend/routers/os';
44

5+
import type { CallerContext } from '@app/backend/ctx';
6+
57
const t = initTRPC.context<CallerContext>().create();
68

79
export const appRouter = t.router({

electron/backend/routers/os.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
import { initTRPC } from '@trpc/server';
2-
import type { CallerContext } from '@app/backend/ctx';
2+
33
import { getOsStats } from '@app/backend/functions/os/osStats';
44

5+
import type { CallerContext } from '@app/backend/ctx';
6+
57
const t = initTRPC.context<CallerContext>().create();
68

79
export const osRouter = t.router({

electron/main.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import { app, BrowserWindow, Menu } from 'electron';
22
import path from 'node:path';
33
import { fileURLToPath } from 'node:url';
4+
45
import { registerTrpcHandler } from '@app/backend/ipcTrpc';
56

67
const __filename = fileURLToPath(import.meta.url);
@@ -48,7 +49,7 @@ function createMainWindow(): void {
4849
}
4950

5051
// This is the entry point for the main process
51-
app.whenReady().then(() => {
52+
void app.whenReady().then(() => {
5253
// Remove default application menu (File/Edit/View...)
5354
Menu.setApplicationMenu(null);
5455

eslint.config.js

Lines changed: 62 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -7,55 +7,50 @@ import tseslint from 'typescript-eslint';
77
import { globalIgnores } from 'eslint/config';
88
import jsxA11y from 'eslint-plugin-jsx-a11y';
99
import importPlugin from 'eslint-plugin-import';
10-
import unicorn from 'eslint-plugin-unicorn';
11-
import sonarjs from 'eslint-plugin-sonarjs';
12-
import electronPlugin from 'eslint-plugin-electron';
13-
import security from 'eslint-plugin-security';
14-
import noSecrets from 'eslint-plugin-no-secrets';
10+
import prettierPlugin from 'eslint-plugin-prettier';
11+
import prettierConfig from 'eslint-config-prettier';
12+
// Avoid legacy shareable presets to keep flat config compatibility stable
1513

1614
export default tseslint.config([
17-
globalIgnores(['dist', 'dist-electron', 'release']),
15+
globalIgnores([
16+
'dist',
17+
'dist-electron',
18+
'release',
19+
'eslint.config.js',
20+
'prettier.config.js',
21+
'electron-builder.json5',
22+
]),
1823
{
19-
files: ['**/*.{js,jsx,ts,tsx}'],
24+
files: ['src/**/*.{js,jsx,ts,tsx}'],
2025
plugins: {
2126
react,
2227
'react-hooks': reactHooks,
2328
'react-refresh': reactRefresh,
2429
'jsx-a11y': jsxA11y,
2530
import: importPlugin,
26-
unicorn,
27-
sonarjs,
28-
electron: electronPlugin,
29-
security,
30-
'no-secrets': noSecrets,
31+
prettier: prettierPlugin,
3132
},
3233
extends: [
3334
js.configs.recommended,
3435
// Type-aware + strict rules for TypeScript
3536
tseslint.configs.recommendedTypeChecked,
3637
tseslint.configs.strictTypeChecked,
37-
// React core + JSX runtime + Hooks and Vite Fast Refresh
38-
react.configs.recommended,
39-
react.configs['jsx-runtime'],
40-
reactHooks.configs['recommended-latest'],
41-
reactRefresh.configs.vite,
42-
// SonarJS recommended (code smells & complexity)
43-
sonarjs.configs.recommended,
38+
// Disable stylistic rules that conflict with Prettier formatting
39+
prettierConfig,
4440
],
4541
languageOptions: {
46-
ecmaVersion: 2025,
42+
ecmaVersion: 2023,
4743
sourceType: 'module',
4844
globals: globals.browser,
4945
parserOptions: {
50-
// Enable type-aware linting without listing every tsconfig
51-
projectService: true,
46+
project: ['./tsconfig.renderer.json'],
5247
tsconfigRootDir: import.meta.dirname,
5348
},
5449
},
5550
settings: {
5651
react: { version: 'detect' },
5752
'import/resolver': {
58-
typescript: { project: true },
53+
typescript: { project: ['tsconfig.renderer.json'] },
5954
node: true,
6055
},
6156
},
@@ -64,6 +59,7 @@ export default tseslint.config([
6459
'react/jsx-no-useless-fragment': 'warn',
6560
'react/jsx-key': ['error', { checkFragmentShorthand: true }],
6661
'react/no-unstable-nested-components': 'warn',
62+
'react-refresh/only-export-components': 'warn',
6763

6864
// Imports
6965
'import/order': [
@@ -77,32 +73,54 @@ export default tseslint.config([
7773
'import/newline-after-import': 'warn',
7874
'import/no-unresolved': 'off',
7975

80-
// Unicorn (curated subset)
81-
'unicorn/prefer-node-protocol': 'warn',
82-
'unicorn/prefer-top-level-await': 'warn',
83-
'unicorn/prevent-abbreviations': 'off',
84-
85-
// Security & secrets
86-
'security/detect-unsafe-regex': 'warn',
87-
'security/detect-object-injection': 'off',
88-
'no-secrets/no-secrets': ['warn', { tolerance: 4.2, ignoreContent: true }],
76+
// removed unicorn/security/secrets rules per request
77+
// Run Prettier as an ESLint rule (optional; can be run separately)
78+
'prettier/prettier': 'warn',
8979
},
9080
},
9181
{
92-
files: ['src/**/*.{jsx,tsx}'],
93-
extends: [jsxA11y.configs.recommended],
94-
},
95-
{
96-
files: ['electron/**/*.{js,ts,tsx}', 'vite.config.ts', 'electron-builder.json5'],
97-
languageOptions: { globals: globals.node },
98-
rules: {
99-
'electron/no-unfiltered-navigate': 'error',
82+
files: ['electron/**/*.{js,ts,tsx}', 'vite.config.ts'],
83+
plugins: {
84+
react,
85+
'react-hooks': reactHooks,
86+
'react-refresh': reactRefresh,
87+
'jsx-a11y': jsxA11y,
88+
import: importPlugin,
89+
prettier: prettierPlugin,
90+
},
91+
extends: [
92+
js.configs.recommended,
93+
tseslint.configs.recommendedTypeChecked,
94+
tseslint.configs.strictTypeChecked,
95+
prettierConfig,
96+
],
97+
languageOptions: {
98+
ecmaVersion: 2023,
99+
sourceType: 'module',
100+
globals: globals.node,
101+
parserOptions: {
102+
project: ['./tsconfig.electron.json'],
103+
tsconfigRootDir: import.meta.dirname,
104+
},
105+
},
106+
settings: {
107+
'import/resolver': {
108+
typescript: { project: ['tsconfig.electron.json'] },
109+
node: true,
110+
},
100111
},
101-
},
102-
{
103-
files: ['src/**/*.{js,ts,tsx}'],
104112
rules: {
105-
'electron/no-node-in-renderer': 'error',
113+
'import/order': [
114+
'warn',
115+
{
116+
groups: [['builtin', 'external'], ['internal', 'parent', 'sibling', 'index'], ['type']],
117+
'newlines-between': 'always',
118+
alphabetize: { order: 'asc', caseInsensitive: true },
119+
},
120+
],
121+
'import/newline-after-import': 'warn',
122+
'import/no-unresolved': 'off',
123+
'prettier/prettier': 'warn',
106124
},
107125
},
108126
]);

0 commit comments

Comments
 (0)