@aminnairi/react-router 2.0.0 → 2.0.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.
package/.eslintrc.cjs ADDED
@@ -0,0 +1,13 @@
1
+ module.exports = {
2
+ root: true,
3
+ env: { browser: true, es2020: true },
4
+ extends: [
5
+ 'eslint:recommended',
6
+ 'plugin:@typescript-eslint/recommended',
7
+ 'plugin:react-hooks/recommended',
8
+ ],
9
+ ignorePatterns: ['dist', '.eslintrc.cjs', 'index.js'],
10
+ parser: '@typescript-eslint/parser',
11
+ plugins: [],
12
+ rules: {},
13
+ }
package/README.md CHANGED
@@ -17,6 +17,7 @@ cd project
17
17
  ```
18
18
 
19
19
  ### Dependencies installation
20
+
20
21
  ```bash
21
22
  npm install
22
23
  ```
@@ -41,10 +42,8 @@ import { createPage } from "@aminnairi/react-router";
41
42
  export const home = createPage({
42
43
  path: "/",
43
44
  element: function Home() {
44
- return (
45
- <h1>Home page</h1>
46
- );
47
- }
45
+ return <h1>Home page</h1>;
46
+ },
48
47
  });
49
48
  ```
50
49
 
@@ -59,12 +58,8 @@ import { home } from "./pages/home";
59
58
  export const Fallback = () => {
60
59
  const navigateToHomePage = useNavigateToPage(home);
61
60
 
62
- return (
63
- <button onClick={() => navigateToHomePage({})}>
64
- Go back home
65
- </button>
66
- );
67
- }
61
+ return <button onClick={() => navigateToHomePage({})}>Go back home</button>;
62
+ };
68
63
  ```
69
64
 
70
65
  ```bash
@@ -82,12 +77,10 @@ export const Issue = () => {
82
77
  return (
83
78
  <Fragment>
84
79
  <h1>An issue occurred</h1>
85
- <button onClick={() => navigateToHomePage({})}>
86
- Go back home
87
- </button>
80
+ <button onClick={() => navigateToHomePage({})}>Go back home</button>
88
81
  </Fragment>
89
82
  );
90
- }
83
+ };
91
84
  ```
92
85
 
93
86
  ```bash
@@ -103,9 +96,7 @@ import { home } from "./pages/home";
103
96
  export const router = createRouter({
104
97
  fallback: Fallback,
105
98
  issue: Issue,
106
- pages: [
107
- home
108
- ]
99
+ pages: [home],
109
100
  });
110
101
  ```
111
102
 
@@ -117,9 +108,7 @@ touch src/App.tsx
117
108
  import { router } from "./router";
118
109
 
119
110
  export default function App() {
120
- return (
121
- <router.View />
122
- );
111
+ return <router.View />;
123
112
  }
124
113
  ```
125
114
 
@@ -144,7 +133,7 @@ createRoot(rootElement).render(
144
133
  <router.Provider>
145
134
  <App />
146
135
  </router.Provider>
147
- </StrictMode>
136
+ </StrictMode>,
148
137
  );
149
138
  ```
150
139
 
@@ -166,10 +155,8 @@ import { createPage } from "@aminnairi/react-router";
166
155
  createPage({
167
156
  path: "/",
168
157
  element: function Home() {
169
- return (
170
- <h1>Home</h1>
171
- );
172
- }
158
+ return <h1>Home</h1>;
159
+ },
173
160
  });
174
161
  ```
175
162
 
@@ -181,24 +168,14 @@ import { createPage, createRouter } from "@aminnairi/react-router";
181
168
  const home = createPage({
182
169
  path: "/",
183
170
  element: function Home() {
184
- return (
185
- <h1>Home</h1>
186
- );
187
- }
171
+ return <h1>Home</h1>;
172
+ },
188
173
  });
189
174
 
190
175
  createRouter({
191
- fallback: () => (
192
- <h1>
193
- Not found
194
- </h1>
195
- ),
196
- issue: () => (
197
- <h1>
198
- An error occurred
199
- </h1>
200
- ),
201
- pages: [home]
176
+ fallback: () => <h1>Not found</h1>,
177
+ issue: () => <h1>An error occurred</h1>,
178
+ pages: [home],
202
179
  });
203
180
  ```
204
181
 
@@ -209,11 +186,9 @@ import { createPage } from "@aminnairi/react-router";
209
186
 
210
187
  createPage({
211
188
  path: "/users/:user",
212
- element: function User({ parameters: { user }}) {
213
- return (
214
- <h1>User#{user}</h1>
215
- );
216
- }
189
+ element: function User({ parameters: { user } }) {
190
+ return <h1>User#{user}</h1>;
191
+ },
217
192
  });
218
193
  ```
219
194
 
@@ -224,11 +199,13 @@ import { createPage } from "@aminnairi/react-router";
224
199
 
225
200
  createPage({
226
201
  path: "/users/:user/articles/:article",
227
- element: function UserArticle({ parameters: { user, article }}) {
202
+ element: function UserArticle({ parameters: { user, article } }) {
228
203
  return (
229
- <h1>Article#{article } of user#{user}</h1>
204
+ <h1>
205
+ Article#{article} of user#{user}
206
+ </h1>
230
207
  );
231
- }
208
+ },
232
209
  });
233
210
  ```
234
211
 
@@ -243,10 +220,8 @@ import { createPage, useNavigateToPage } from "@aminnairi/react-router";
243
220
  const login = createPage({
244
221
  path: "/login",
245
222
  element: function Login() {
246
- return (
247
- <h1>Login</h1>
248
- );
249
- }
223
+ return <h1>Login</h1>;
224
+ },
250
225
  });
251
226
 
252
227
  const about = createPage({
@@ -256,15 +231,11 @@ const about = createPage({
256
231
 
257
232
  return (
258
233
  <Fragment>
259
- <h1>
260
- About Us
261
- </h1>
262
- <button onClick={() => navigateToLoginPage({})}>
263
- Login
264
- </button>
234
+ <h1>About Us</h1>
235
+ <button onClick={() => navigateToLoginPage({})}>Login</button>
265
236
  </Fragment>
266
237
  );
267
- }
238
+ },
268
239
  });
269
240
 
270
241
  createPage({
@@ -274,15 +245,11 @@ createPage({
274
245
 
275
246
  return (
276
247
  <Fragment>
277
- <h1>
278
- Home
279
- </h1>
280
- <button onClick={() => navigateToAboutPage({})}>
281
- About Us
282
- </button>
248
+ <h1>Home</h1>
249
+ <button onClick={() => navigateToAboutPage({})}>About Us</button>
283
250
  </Fragment>
284
251
  );
285
- }
252
+ },
286
253
  });
287
254
  ```
288
255
 
@@ -294,11 +261,9 @@ import { createPage, useNavigateToPage } from "@aminnairi/react-router";
294
261
 
295
262
  const user = createPage({
296
263
  path: "/users/:user",
297
- element: function User({ parameters: { user }}) {
298
- return (
299
- <h1>User#{user}</h1>
300
- );
301
- }
264
+ element: function User({ parameters: { user } }) {
265
+ return <h1>User#{user}</h1>;
266
+ },
302
267
  });
303
268
 
304
269
  createPage({
@@ -308,15 +273,13 @@ createPage({
308
273
 
309
274
  return (
310
275
  <Fragment>
311
- <h1>
312
- Home
313
- </h1>
276
+ <h1>Home</h1>
314
277
  <button onClick={() => navigateToUserPage({ user: "123" })}>
315
278
  User#123
316
279
  </button>
317
280
  </Fragment>
318
281
  );
319
- }
282
+ },
320
283
  });
321
284
  ```
322
285
 
@@ -332,22 +295,14 @@ import { createRouter, createPage } from "@aminnairi/react-router";
332
295
  const home = createPage({
333
296
  path: "/",
334
297
  element: function Home() {
335
- return (
336
- <h1>Home</h1>
337
- );
338
- }
298
+ return <h1>Home</h1>;
299
+ },
339
300
  });
340
301
 
341
302
  const router = createRouter({
342
- fallback: () => (
343
- <h1>Not found</h1>
344
- ),
345
- issue: () => (
346
- <h1>An error occurred</h1>
347
- ),
348
- pages: [
349
- home
350
- ]
303
+ fallback: () => <h1>Not found</h1>,
304
+ issue: () => <h1>An error occurred</h1>,
305
+ pages: [home],
351
306
  });
352
307
 
353
308
  const rootElement = document.getElementById("root");
@@ -367,19 +322,17 @@ const App = () => {
367
322
  <main>
368
323
  <router.View />
369
324
  </main>
370
- <footer>
371
- Credit © Yourself 2025
372
- </footer>
325
+ <footer>Credit © Yourself 2025</footer>
373
326
  </Fragment>
374
327
  );
375
- }
328
+ };
376
329
 
377
330
  root.render(
378
331
  <StrictMode>
379
332
  <router.Provider>
380
333
  <App />
381
334
  </router.Provider>
382
- </StrictMode>
335
+ </StrictMode>,
383
336
  );
384
337
  ```
385
338
 
@@ -392,28 +345,24 @@ This library also exports a `slideFadeTransition` that you can use out-of-the-bo
392
345
  ```tsx
393
346
  import { Fragment, StrictMode } from "react";
394
347
  import { createRoot } from "react-dom/client";
395
- import { createRouter, createPage, slideFadeTransition } from "@aminnairi/react-router";
348
+ import {
349
+ createRouter,
350
+ createPage,
351
+ slideFadeTransition,
352
+ } from "@aminnairi/react-router";
396
353
 
397
354
  const home = createPage({
398
355
  path: "/",
399
356
  element: function Page() {
400
- return (
401
- <h1>Home</h1>
402
- );
403
- }
357
+ return <h1>Home</h1>;
358
+ },
404
359
  });
405
360
 
406
361
  const router = createRouter({
407
362
  transition: slideFadeTransition,
408
- fallback: () => (
409
- <h1>Not found</h1>
410
- ),
411
- issue: () => (
412
- <h1>An error occurred</h1>
413
- ),
414
- pages: [
415
- home
416
- ]
363
+ fallback: () => <h1>Not found</h1>,
364
+ issue: () => <h1>An error occurred</h1>,
365
+ pages: [home],
417
366
  });
418
367
 
419
368
  const rootElement = document.getElementById("root");
@@ -433,19 +382,17 @@ const App = () => {
433
382
  <main>
434
383
  <router.View />
435
384
  </main>
436
- <footer>
437
- Credit © Yourself 2025
438
- </footer>
385
+ <footer>Credit © Yourself 2025</footer>
439
386
  </Fragment>
440
387
  );
441
- }
388
+ };
442
389
 
443
390
  root.render(
444
391
  <StrictMode>
445
392
  <router.Provider>
446
393
  <App />
447
394
  </router.Provider>
448
- </StrictMode>
395
+ </StrictMode>,
449
396
  );
450
397
  ```
451
398
 
@@ -459,16 +406,12 @@ import { createRouter, createPage } from "@aminnairi/react-router";
459
406
  const home = createPage({
460
407
  path: "/",
461
408
  element: function Home() {
462
- return (
463
- <h1>Home</h1>
464
- );
465
- }
409
+ return <h1>Home</h1>;
410
+ },
466
411
  });
467
412
 
468
413
  const router = createRouter({
469
- fallback: () => (
470
- <h1>Not found</h1>
471
- ),
414
+ fallback: () => <h1>Not found</h1>,
472
415
  issue: ({ error, reset }) => (
473
416
  <Fragment>
474
417
  <h1>Error</h1>
@@ -476,9 +419,7 @@ const router = createRouter({
476
419
  <button onClick={reset}>Reset</button>
477
420
  </Fragment>
478
421
  ),
479
- pages: [
480
- home
481
- ]
422
+ pages: [home],
482
423
  });
483
424
 
484
425
  const rootElement = document.getElementById("root");
@@ -498,19 +439,17 @@ const App = () => {
498
439
  <main>
499
440
  <router.View />
500
441
  </main>
501
- <footer>
502
- Credit © Yourself 2025
503
- </footer>
442
+ <footer>Credit © Yourself 2025</footer>
504
443
  </Fragment>
505
444
  );
506
- }
445
+ };
507
446
 
508
447
  root.render(
509
448
  <StrictMode>
510
449
  <router.Provider>
511
450
  <App />
512
451
  </router.Provider>
513
- </StrictMode>
452
+ </StrictMode>,
514
453
  );
515
454
  ```
516
455
 
@@ -524,17 +463,13 @@ import { createRouter, createPage, createIssue } from "@aminnairi/react-router";
524
463
  const home = createPage({
525
464
  path: "/",
526
465
  element: function Home() {
527
- return (
528
- <h1>Home</h1>
529
- );
530
- }
466
+ return <h1>Home</h1>;
467
+ },
531
468
  });
532
469
 
533
470
  const Fallback = () => {
534
- return (
535
- <h1>Not found</h1>
536
- );
537
- }
471
+ return <h1>Not found</h1>;
472
+ };
538
473
 
539
474
  const Issue = createIssue(({ error, reset }) => (
540
475
  <Fragment>
@@ -547,9 +482,7 @@ const Issue = createIssue(({ error, reset }) => (
547
482
  const router = createRouter({
548
483
  fallback: Fallback,
549
484
  issue: Issue,
550
- pages: [
551
- home
552
- ]
485
+ pages: [home],
553
486
  });
554
487
 
555
488
  const rootElement = document.getElementById("root");
@@ -569,19 +502,17 @@ const App = () => {
569
502
  <main>
570
503
  <router.View />
571
504
  </main>
572
- <footer>
573
- Credit © Yourself 2025
574
- </footer>
505
+ <footer>Credit © Yourself 2025</footer>
575
506
  </Fragment>
576
507
  );
577
- }
508
+ };
578
509
 
579
510
  root.render(
580
511
  <StrictMode>
581
512
  <router.Provider>
582
513
  <App />
583
514
  </router.Provider>
584
- </StrictMode>
515
+ </StrictMode>,
585
516
  );
586
517
  ```
587
518
 
@@ -592,15 +523,18 @@ You don't have to manually append this prefix when creating pages, its automatic
592
523
  ```tsx
593
524
  import { Fragment, StrictMode } from "react";
594
525
  import { createRoot } from "react-dom/client";
595
- import { createRouter, createPage, createIssue, useNavigateToPage } from "@aminnairi/react-router";
526
+ import {
527
+ createRouter,
528
+ createPage,
529
+ createIssue,
530
+ useNavigateToPage,
531
+ } from "@aminnairi/react-router";
596
532
 
597
533
  const home = createPage({
598
534
  path: "/",
599
535
  element: function Home() {
600
- return (
601
- <h1>Home</h1>
602
- );
603
- }
536
+ return <h1>Home</h1>;
537
+ },
604
538
  });
605
539
 
606
540
  const Fallback = () => {
@@ -609,12 +543,10 @@ const Fallback = () => {
609
543
  return (
610
544
  <Fragment>
611
545
  <h1>Not found</h1>
612
- <button onClick={() => navigateToHomePage({})}>
613
- Go Back Home
614
- </button>
546
+ <button onClick={() => navigateToHomePage({})}>Go Back Home</button>
615
547
  </Fragment>
616
548
  );
617
- }
549
+ };
618
550
 
619
551
  const Issue = createIssue(({ error, reset }) => (
620
552
  <Fragment>
@@ -628,9 +560,7 @@ const router = createRouter({
628
560
  prefix: "/portfolio",
629
561
  fallback: Fallback,
630
562
  issue: Issue,
631
- pages: [
632
- home
633
- ]
563
+ pages: [home],
634
564
  });
635
565
 
636
566
  const rootElement = document.getElementById("root");
@@ -650,19 +580,17 @@ const App = () => {
650
580
  <main>
651
581
  <router.View />
652
582
  </main>
653
- <footer>
654
- Credit © Yourself 2025
655
- </footer>
583
+ <footer>Credit © Yourself 2025</footer>
656
584
  </Fragment>
657
585
  );
658
- }
586
+ };
659
587
 
660
588
  root.render(
661
589
  <StrictMode>
662
590
  <router.Provider>
663
591
  <App />
664
592
  </router.Provider>
665
- </StrictMode>
593
+ </StrictMode>,
666
594
  );
667
595
  ```
668
596
 
@@ -679,10 +607,8 @@ import { createPage, useNavigateToPage } from "@aminnairi/react-router";
679
607
  const home = createPage({
680
608
  path: "/",
681
609
  element: function Home() {
682
- return (
683
- <h1>Home</h1>
684
- );
685
- }
610
+ return <h1>Home</h1>;
611
+ },
686
612
  });
687
613
 
688
614
  createPage({
@@ -696,7 +622,7 @@ createPage({
696
622
  <button onClick={() => navigateToHomePage({})}>Home</button>
697
623
  </Fragment>
698
624
  );
699
- }
625
+ },
700
626
  });
701
627
  ```
702
628
 
@@ -710,11 +636,9 @@ import { createPage, useNavigateToPage } from "@aminnairi/react-router";
710
636
 
711
637
  const user = createPage({
712
638
  path: "/users/:user",
713
- element: function User({ parameters: { user }}) {
714
- return (
715
- <h1>User#{user}</h1>
716
- );
717
- }
639
+ element: function User({ parameters: { user } }) {
640
+ return <h1>User#{user}</h1>;
641
+ },
718
642
  });
719
643
 
720
644
  createPage({
@@ -725,10 +649,12 @@ createPage({
725
649
  return (
726
650
  <Fragment>
727
651
  <h1>About</h1>
728
- <button onClick={() => navigateToUserPage({ user: "123" })}>Home</button>
652
+ <button onClick={() => navigateToUserPage({ user: "123" })}>
653
+ Home
654
+ </button>
729
655
  </Fragment>
730
656
  );
731
- }
657
+ },
732
658
  });
733
659
  ```
734
660
 
@@ -744,11 +670,9 @@ import { createPage, useLink } from "@aminnairi/react-router";
744
670
 
745
671
  const user = createPage({
746
672
  path: "/users/:user",
747
- element: function User({ parameters: { user }}) {
748
- return (
749
- <h1>User#{user}</h1>
750
- );
751
- }
673
+ element: function User({ parameters: { user } }) {
674
+ return <h1>User#{user}</h1>;
675
+ },
752
676
  });
753
677
 
754
678
  createPage({
@@ -762,7 +686,7 @@ createPage({
762
686
  <Link parameters={{ user: "123" }}>User#123</Link>
763
687
  </Fragment>
764
688
  );
765
- }
689
+ },
766
690
  });
767
691
  ```
768
692
 
@@ -804,10 +728,8 @@ createPage({
804
728
  element: function OauthCallback() {
805
729
  const token = useHash();
806
730
 
807
- return (
808
- <h1>You token is {token}</h1>
809
- );
810
- }
731
+ return <h1>You token is {token}</h1>;
732
+ },
811
733
  });
812
734
  ```
813
735
 
@@ -927,6 +849,7 @@ See [`LICENSE`](./LICENSE).
927
849
 
928
850
  ### Versions
929
851
 
852
+ - [`2.0.1`](#201)
930
853
  - [`2.0.0`](#200)
931
854
  - [`1.1.0`](#110)
932
855
  - [`1.0.1`](#101)
@@ -934,6 +857,20 @@ See [`LICENSE`](./LICENSE).
934
857
  - [`0.1.1`](#011)
935
858
  - [`0.1.0`](#010)
936
859
 
860
+ ### 2.0.1
861
+
862
+ #### Major changes
863
+
864
+ None.
865
+
866
+ #### Minor changes
867
+
868
+ - Now running a linter with eslint and TypeScript and a stricter configuration to prevent type errors
869
+
870
+ #### Bug & security fixes
871
+
872
+ - Fixed an error while the error boundary was not using an override when using a stricter typescript configuration
873
+
937
874
  ### 2.0.0
938
875
 
939
876
  #### Major changes
package/index.tsx CHANGED
@@ -1,3 +1,4 @@
1
+ /* eslint-disable */
1
2
  import { useEffect, useState, FunctionComponent, useMemo, Component, PropsWithChildren, createContext, SetStateAction, Dispatch, ReactNode, useContext, useCallback, memo, MouseEvent } from "react";
2
3
 
3
4
  export type AbsolutePath<Path extends string> =
@@ -115,13 +116,13 @@ export class ErrorBoundary extends Component<PropsWithChildren<ErrorBoundaryProp
115
116
  this.state = { error: null };
116
117
  }
117
118
 
118
- static getDerivedStateFromError(error: unknown) {
119
+ public static getDerivedStateFromError(error: unknown) {
119
120
  const normalizedError = error instanceof Error ? error : new Error(String(error));
120
121
 
121
122
  return { error: normalizedError };
122
123
  }
123
124
 
124
- render() {
125
+ public override render() {
125
126
  const viewTransitionSupported = typeof document.startViewTransition === "function";
126
127
 
127
128
  if (this.state.error) {
@@ -201,7 +202,7 @@ export const useNavigateToPage = <Path extends string>(page: Page<Path>) => {
201
202
  }
202
203
 
203
204
  window.dispatchEvent(new CustomEvent(NavigationDirection.Forward));
204
- }, [page]);
205
+ }, [page, prefix]);
205
206
  };
206
207
 
207
208
  export const useNavigateBack = () => {
@@ -236,12 +237,12 @@ export const useLink = <Path extends string>(page: Page<Path>) => {
236
237
  return Object.entries(parameters).reduce((previousPath, [parameterName, parameterValue]) => {
237
238
  return previousPath.replace(`:${parameterName}`, parameterValue);
238
239
  }, sanitizePath(`${prefix ?? ""}/${page.path}`));
239
- }, []);
240
+ }, [prefix, page, parameters]);
240
241
 
241
242
  const navigate = useCallback((event: MouseEvent) => {
242
243
  event.preventDefault();
243
244
  navigateToPage(parameters);
244
- }, []);
245
+ }, [navigateToPage, parameters]);
245
246
 
246
247
  return (
247
248
  <a
package/package.json CHANGED
@@ -2,7 +2,7 @@
2
2
  "type": "module",
3
3
  "name": "@aminnairi/react-router",
4
4
  "description": "Type-safe router for the React library",
5
- "version": "2.0.0",
5
+ "version": "2.0.1",
6
6
  "homepage": "https://github.com/aminnairi/react-router#readme",
7
7
  "license": "MIT",
8
8
  "bugs": {
@@ -26,5 +26,14 @@
26
26
  ],
27
27
  "peerDependencies": {
28
28
  "react": ">=18.0.0"
29
+ },
30
+ "scripts": {
31
+ "lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0"
32
+ },
33
+ "devDependencies": {
34
+ "@typescript-eslint/eslint-plugin": "^7.2.0",
35
+ "@typescript-eslint/parser": "^7.2.0",
36
+ "eslint": "^8.57.0",
37
+ "eslint-plugin-react-hooks": "^4.6.0"
29
38
  }
30
39
  }
package/tsconfig.json ADDED
@@ -0,0 +1,16 @@
1
+ {
2
+ "compilerOptions": {
3
+ "jsx": "react-jsx",
4
+ "target": "esnext",
5
+ "module": "esnext",
6
+ "moduleResolution": "node",
7
+ "strict": true,
8
+ "forceConsistentCasingInFileNames": true,
9
+ "noFallthroughCasesInSwitch": true,
10
+ "noUncheckedIndexedAccess": true,
11
+ "noImplicitOverride": true,
12
+ "exactOptionalPropertyTypes": true,
13
+ "esModuleInterop": true,
14
+ "isolatedModules": true
15
+ }
16
+ }