@getpara/paramedic 2.7.0

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 (74) hide show
  1. package/README.md +131 -0
  2. package/dist/checks/chain-dependencies.check.d.ts +2 -0
  3. package/dist/checks/chain-dependencies.check.d.ts.map +1 -0
  4. package/dist/checks/chain-dependencies.check.js +129 -0
  5. package/dist/checks/css-import.check.d.ts +2 -0
  6. package/dist/checks/css-import.check.d.ts.map +1 -0
  7. package/dist/checks/css-import.check.js +57 -0
  8. package/dist/checks/deprecated-packages.check.d.ts +2 -0
  9. package/dist/checks/deprecated-packages.check.d.ts.map +1 -0
  10. package/dist/checks/deprecated-packages.check.js +52 -0
  11. package/dist/checks/env-api-key.check.d.ts +2 -0
  12. package/dist/checks/env-api-key.check.d.ts.map +1 -0
  13. package/dist/checks/env-api-key.check.js +75 -0
  14. package/dist/checks/env-var-prefix.check.d.ts +2 -0
  15. package/dist/checks/env-var-prefix.check.d.ts.map +1 -0
  16. package/dist/checks/env-var-prefix.check.js +52 -0
  17. package/dist/checks/index.d.ts +12 -0
  18. package/dist/checks/index.d.ts.map +1 -0
  19. package/dist/checks/index.js +33 -0
  20. package/dist/checks/para-provider.check.d.ts +2 -0
  21. package/dist/checks/para-provider.check.d.ts.map +1 -0
  22. package/dist/checks/para-provider.check.js +42 -0
  23. package/dist/checks/query-client.check.d.ts +2 -0
  24. package/dist/checks/query-client.check.d.ts.map +1 -0
  25. package/dist/checks/query-client.check.js +58 -0
  26. package/dist/checks/use-client-directive.check.d.ts +2 -0
  27. package/dist/checks/use-client-directive.check.d.ts.map +1 -0
  28. package/dist/checks/use-client-directive.check.js +82 -0
  29. package/dist/checks/version-consistency.check.d.ts +2 -0
  30. package/dist/checks/version-consistency.check.d.ts.map +1 -0
  31. package/dist/checks/version-consistency.check.js +93 -0
  32. package/dist/cli.d.ts +2 -0
  33. package/dist/cli.d.ts.map +1 -0
  34. package/dist/cli.js +96 -0
  35. package/dist/core/check.d.ts +21 -0
  36. package/dist/core/check.d.ts.map +1 -0
  37. package/dist/core/check.js +10 -0
  38. package/dist/core/context.d.ts +3 -0
  39. package/dist/core/context.d.ts.map +1 -0
  40. package/dist/core/context.js +56 -0
  41. package/dist/core/registry.d.ts +18 -0
  42. package/dist/core/registry.d.ts.map +1 -0
  43. package/dist/core/registry.js +38 -0
  44. package/dist/core/reporter.d.ts +5 -0
  45. package/dist/core/reporter.d.ts.map +1 -0
  46. package/dist/core/reporter.js +82 -0
  47. package/dist/core/runner.d.ts +3 -0
  48. package/dist/core/runner.d.ts.map +1 -0
  49. package/dist/core/runner.js +38 -0
  50. package/dist/detectors/framework.d.ts +5 -0
  51. package/dist/detectors/framework.d.ts.map +1 -0
  52. package/dist/detectors/framework.js +67 -0
  53. package/dist/detectors/package-manager.d.ts +3 -0
  54. package/dist/detectors/package-manager.d.ts.map +1 -0
  55. package/dist/detectors/package-manager.js +17 -0
  56. package/dist/detectors/sdk.d.ts +7 -0
  57. package/dist/detectors/sdk.d.ts.map +1 -0
  58. package/dist/detectors/sdk.js +42 -0
  59. package/dist/index.d.ts +2 -0
  60. package/dist/index.d.ts.map +1 -0
  61. package/dist/index.js +6 -0
  62. package/dist/types.d.ts +51 -0
  63. package/dist/types.d.ts.map +1 -0
  64. package/dist/types.js +6 -0
  65. package/dist/utils/ast-parser.d.ts +10 -0
  66. package/dist/utils/ast-parser.d.ts.map +1 -0
  67. package/dist/utils/ast-parser.js +98 -0
  68. package/dist/utils/file-system.d.ts +9 -0
  69. package/dist/utils/file-system.d.ts.map +1 -0
  70. package/dist/utils/file-system.js +81 -0
  71. package/dist/utils/package-json.d.ts +10 -0
  72. package/dist/utils/package-json.d.ts.map +1 -0
  73. package/dist/utils/package-json.js +39 -0
  74. package/package.json +52 -0
@@ -0,0 +1,67 @@
1
+ import path from "node:path";
2
+ import { pathExists } from "../utils/file-system.js";
3
+ async function detectFramework(projectRoot, packageJson) {
4
+ if (!packageJson) {
5
+ return "unknown";
6
+ }
7
+ const deps = {
8
+ ...packageJson.dependencies,
9
+ ...packageJson.devDependencies
10
+ };
11
+ if (deps["next"]) {
12
+ return "nextjs";
13
+ }
14
+ if (deps["@tanstack/start"]) {
15
+ return "tanstack-start";
16
+ }
17
+ if (deps["vue"]) {
18
+ return "vue";
19
+ }
20
+ if (deps["svelte"] || deps["@sveltejs/kit"]) {
21
+ return "svelte";
22
+ }
23
+ if (deps["react-scripts"]) {
24
+ return "create-react-app";
25
+ }
26
+ if (deps["vite"]) {
27
+ const hasViteConfig = await pathExists(path.join(projectRoot, "vite.config.ts")) || await pathExists(path.join(projectRoot, "vite.config.js")) || await pathExists(path.join(projectRoot, "vite.config.mjs"));
28
+ if (hasViteConfig) {
29
+ return "vite";
30
+ }
31
+ }
32
+ return "unknown";
33
+ }
34
+ function getEnvVarPrefix(framework) {
35
+ switch (framework) {
36
+ case "nextjs":
37
+ return "NEXT_PUBLIC_";
38
+ case "create-react-app":
39
+ return "REACT_APP_";
40
+ case "vite":
41
+ case "vue":
42
+ case "svelte":
43
+ case "tanstack-start":
44
+ return "VITE_";
45
+ default:
46
+ return "";
47
+ }
48
+ }
49
+ function getEnvAccessPattern(framework) {
50
+ switch (framework) {
51
+ case "nextjs":
52
+ case "create-react-app":
53
+ return "process.env";
54
+ case "vite":
55
+ case "vue":
56
+ case "svelte":
57
+ case "tanstack-start":
58
+ return "import.meta.env";
59
+ default:
60
+ return "process.env";
61
+ }
62
+ }
63
+ export {
64
+ detectFramework,
65
+ getEnvAccessPattern,
66
+ getEnvVarPrefix
67
+ };
@@ -0,0 +1,3 @@
1
+ import type { PackageManager } from '../types.js';
2
+ export declare function detectPackageManager(projectRoot: string): Promise<PackageManager>;
3
+ //# sourceMappingURL=package-manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"package-manager.d.ts","sourceRoot":"","sources":["../../src/detectors/package-manager.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAElD,wBAAsB,oBAAoB,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,CAAC,CAcvF"}
@@ -0,0 +1,17 @@
1
+ import path from "node:path";
2
+ import { pathExists } from "../utils/file-system.js";
3
+ async function detectPackageManager(projectRoot) {
4
+ if (await pathExists(path.join(projectRoot, "pnpm-lock.yaml"))) {
5
+ return "pnpm";
6
+ }
7
+ if (await pathExists(path.join(projectRoot, "yarn.lock"))) {
8
+ return "yarn";
9
+ }
10
+ if (await pathExists(path.join(projectRoot, "package-lock.json"))) {
11
+ return "npm";
12
+ }
13
+ return "unknown";
14
+ }
15
+ export {
16
+ detectPackageManager
17
+ };
@@ -0,0 +1,7 @@
1
+ import type { SDKType, PackageJsonData } from '../types.js';
2
+ export declare function detectSDKType(packageJson: PackageJsonData | null): {
3
+ sdkType: SDKType;
4
+ sdkVersion?: string;
5
+ };
6
+ export declare function getCSSImportPath(sdkType: SDKType): string | null;
7
+ //# sourceMappingURL=sdk.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sdk.d.ts","sourceRoot":"","sources":["../../src/detectors/sdk.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAE5D,wBAAgB,aAAa,CAAC,WAAW,EAAE,eAAe,GAAG,IAAI,GAAG;IAClE,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB,CAgCA;AAED,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,OAAO,GAAG,MAAM,GAAG,IAAI,CAShE"}
@@ -0,0 +1,42 @@
1
+ function detectSDKType(packageJson) {
2
+ if (!packageJson) {
3
+ return { sdkType: "none" };
4
+ }
5
+ const deps = {
6
+ ...packageJson.dependencies,
7
+ ...packageJson.devDependencies
8
+ };
9
+ if (deps["@getpara/react-sdk"]) {
10
+ return {
11
+ sdkType: "@getpara/react-sdk",
12
+ sdkVersion: deps["@getpara/react-sdk"]
13
+ };
14
+ }
15
+ if (deps["@getpara/react-sdk-lite"]) {
16
+ return {
17
+ sdkType: "@getpara/react-sdk-lite",
18
+ sdkVersion: deps["@getpara/react-sdk-lite"]
19
+ };
20
+ }
21
+ if (deps["@getpara/web-sdk"]) {
22
+ return {
23
+ sdkType: "@getpara/web-sdk",
24
+ sdkVersion: deps["@getpara/web-sdk"]
25
+ };
26
+ }
27
+ return { sdkType: "none" };
28
+ }
29
+ function getCSSImportPath(sdkType) {
30
+ switch (sdkType) {
31
+ case "@getpara/react-sdk":
32
+ return "@getpara/react-sdk/styles.css";
33
+ case "@getpara/react-sdk-lite":
34
+ return "@getpara/react-sdk-lite/styles.css";
35
+ default:
36
+ return null;
37
+ }
38
+ }
39
+ export {
40
+ detectSDKType,
41
+ getCSSImportPath
42
+ };
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":""}
package/dist/index.js ADDED
@@ -0,0 +1,6 @@
1
+ #!/usr/bin/env node
2
+ import { cli } from "./cli.js";
3
+ cli().catch((error) => {
4
+ console.error("Fatal error:", error);
5
+ process.exit(1);
6
+ });
@@ -0,0 +1,51 @@
1
+ export type CheckSeverity = 'error' | 'warning' | 'info';
2
+ export type CheckCategory = 'configuration' | 'dependencies' | 'setup' | 'best-practices';
3
+ export type Framework = 'nextjs' | 'vite' | 'create-react-app' | 'tanstack-start' | 'vue' | 'svelte' | 'unknown';
4
+ export type SDKType = '@getpara/react-sdk' | '@getpara/react-sdk-lite' | '@getpara/web-sdk' | 'none';
5
+ export declare function isReactSDK(sdkType: SDKType): boolean;
6
+ export type PackageManager = 'yarn' | 'npm' | 'pnpm' | 'unknown';
7
+ export interface FileLocation {
8
+ file: string;
9
+ line?: number;
10
+ column?: number;
11
+ }
12
+ export interface CheckResult {
13
+ checkId: string;
14
+ passed: boolean;
15
+ severity: CheckSeverity;
16
+ message: string;
17
+ details?: string;
18
+ recommendation?: string;
19
+ location?: FileLocation;
20
+ }
21
+ export interface PackageJsonData {
22
+ name?: string;
23
+ version?: string;
24
+ dependencies?: Record<string, string>;
25
+ devDependencies?: Record<string, string>;
26
+ peerDependencies?: Record<string, string>;
27
+ scripts?: Record<string, string>;
28
+ }
29
+ export interface DiagnosticContext {
30
+ projectRoot: string;
31
+ packageManager: PackageManager;
32
+ framework: Framework;
33
+ sdkType: SDKType;
34
+ sdkVersion?: string;
35
+ files: string[];
36
+ packageJson: PackageJsonData | null;
37
+ shouldIgnoreFile: (file: string) => boolean;
38
+ cache: Map<string, unknown>;
39
+ }
40
+ export interface RunResult {
41
+ results: CheckResult[];
42
+ passed: number;
43
+ failed: number;
44
+ warnings: number;
45
+ total: number;
46
+ }
47
+ export interface CheckOptions {
48
+ categories?: CheckCategory[];
49
+ severity?: CheckSeverity[];
50
+ }
51
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,aAAa,GAAG,OAAO,GAAG,SAAS,GAAG,MAAM,CAAC;AAEzD,MAAM,MAAM,aAAa,GAAG,eAAe,GAAG,cAAc,GAAG,OAAO,GAAG,gBAAgB,CAAC;AAE1F,MAAM,MAAM,SAAS,GAAG,QAAQ,GAAG,MAAM,GAAG,kBAAkB,GAAG,gBAAgB,GAAG,KAAK,GAAG,QAAQ,GAAG,SAAS,CAAC;AAEjH,MAAM,MAAM,OAAO,GAAG,oBAAoB,GAAG,yBAAyB,GAAG,kBAAkB,GAAG,MAAM,CAAC;AAErG,wBAAgB,UAAU,CAAC,OAAO,EAAE,OAAO,GAAG,OAAO,CAEpD;AAED,MAAM,MAAM,cAAc,GAAG,MAAM,GAAG,KAAK,GAAG,MAAM,GAAG,SAAS,CAAC;AAEjE,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,WAAW;IAC1B,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,OAAO,CAAC;IAChB,QAAQ,EAAE,aAAa,CAAC;IACxB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,EAAE,YAAY,CAAC;CACzB;AAED,MAAM,WAAW,eAAe;IAC9B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,YAAY,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACtC,eAAe,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACzC,gBAAgB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC1C,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAClC;AAED,MAAM,WAAW,iBAAiB;IAChC,WAAW,EAAE,MAAM,CAAC;IACpB,cAAc,EAAE,cAAc,CAAC;IAC/B,SAAS,EAAE,SAAS,CAAC;IACrB,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB,WAAW,EAAE,eAAe,GAAG,IAAI,CAAC;IACpC,gBAAgB,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC;IAC5C,KAAK,EAAE,GAAG,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAC7B;AAED,MAAM,WAAW,SAAS;IACxB,OAAO,EAAE,WAAW,EAAE,CAAC;IACvB,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,YAAY;IAC3B,UAAU,CAAC,EAAE,aAAa,EAAE,CAAC;IAC7B,QAAQ,CAAC,EAAE,aAAa,EAAE,CAAC;CAC5B"}
package/dist/types.js ADDED
@@ -0,0 +1,6 @@
1
+ function isReactSDK(sdkType) {
2
+ return sdkType === "@getpara/react-sdk" || sdkType === "@getpara/react-sdk-lite";
3
+ }
4
+ export {
5
+ isReactSDK
6
+ };
@@ -0,0 +1,10 @@
1
+ import type { FileLocation } from '../types.js';
2
+ export declare function findImportInFiles(files: string[], importPath: string, shouldIgnore: (file: string) => boolean): Promise<FileLocation | null>;
3
+ export declare function findPatternInFiles(files: string[], pattern: RegExp, shouldIgnore: (file: string) => boolean): Promise<FileLocation[]>;
4
+ export declare function fileContainsPattern(filePath: string, pattern: RegExp): Promise<{
5
+ found: boolean;
6
+ line?: number;
7
+ }>;
8
+ export declare function fileStartsWithDirective(filePath: string, directive: string): Promise<boolean>;
9
+ export declare function findFilesWithPattern(files: string[], pattern: RegExp, shouldIgnore: (file: string) => boolean): Promise<string[]>;
10
+ //# sourceMappingURL=ast-parser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ast-parser.d.ts","sourceRoot":"","sources":["../../src/utils/ast-parser.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAoBhD,wBAAsB,iBAAiB,CACrC,KAAK,EAAE,MAAM,EAAE,EACf,UAAU,EAAE,MAAM,EAClB,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,GACtC,OAAO,CAAC,YAAY,GAAG,IAAI,CAAC,CAsB9B;AAED,wBAAsB,kBAAkB,CACtC,KAAK,EAAE,MAAM,EAAE,EACf,OAAO,EAAE,MAAM,EACf,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,GACtC,OAAO,CAAC,YAAY,EAAE,CAAC,CAoBzB;AAED,wBAAsB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC;IAAE,KAAK,EAAE,OAAO,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAYvH;AAED,wBAAsB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CA6BnG;AAED,wBAAsB,oBAAoB,CACxC,KAAK,EAAE,MAAM,EAAE,EACf,OAAO,EAAE,MAAM,EACf,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,GACtC,OAAO,CAAC,MAAM,EAAE,CAAC,CAcnB"}
@@ -0,0 +1,98 @@
1
+ import { readFile } from "./file-system.js";
2
+ const CODE_EXTENSIONS = [".ts", ".tsx", ".js", ".jsx", ".mjs", ".mts", ".cjs", ".cts", ".vue", ".svelte"];
3
+ function isCodeFile(file) {
4
+ return CODE_EXTENSIONS.some((ext) => file.endsWith(ext));
5
+ }
6
+ function getCodeFiles(files, shouldIgnore) {
7
+ return files.filter((f) => !shouldIgnore(f) && isCodeFile(f));
8
+ }
9
+ function getLineNumber(content, index) {
10
+ return content.substring(0, index).split("\n").length;
11
+ }
12
+ function escapeRegex(str) {
13
+ return str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
14
+ }
15
+ async function findImportInFiles(files, importPath, shouldIgnore) {
16
+ const relevantFiles = getCodeFiles(files, shouldIgnore);
17
+ for (const file of relevantFiles) {
18
+ const content = await readFile(file);
19
+ if (!content) continue;
20
+ const patterns = [
21
+ new RegExp(`import\\s+[^;]*['"]${escapeRegex(importPath)}['"]`, "g"),
22
+ new RegExp(`import\\s*['"]${escapeRegex(importPath)}['"]`, "g"),
23
+ new RegExp(`require\\s*\\(\\s*['"]${escapeRegex(importPath)}['"]\\s*\\)`, "g")
24
+ ];
25
+ for (const pattern of patterns) {
26
+ const match = pattern.exec(content);
27
+ if (match) {
28
+ return { file, line: getLineNumber(content, match.index) };
29
+ }
30
+ }
31
+ }
32
+ return null;
33
+ }
34
+ async function findPatternInFiles(files, pattern, shouldIgnore) {
35
+ const locations = [];
36
+ const relevantFiles = getCodeFiles(files, shouldIgnore);
37
+ for (const file of relevantFiles) {
38
+ const content = await readFile(file);
39
+ if (!content) continue;
40
+ const flags = pattern.flags.includes("g") ? pattern.flags : pattern.flags + "g";
41
+ const globalPattern = new RegExp(pattern.source, flags);
42
+ const matches = Array.from(content.matchAll(globalPattern));
43
+ for (const match of matches) {
44
+ if (match.index !== void 0) {
45
+ locations.push({ file, line: getLineNumber(content, match.index) });
46
+ }
47
+ }
48
+ }
49
+ return locations;
50
+ }
51
+ async function fileContainsPattern(filePath, pattern) {
52
+ const content = await readFile(filePath);
53
+ if (!content) {
54
+ return { found: false };
55
+ }
56
+ const match = pattern.exec(content);
57
+ if (match && match.index !== void 0) {
58
+ return { found: true, line: getLineNumber(content, match.index) };
59
+ }
60
+ return { found: false };
61
+ }
62
+ async function fileStartsWithDirective(filePath, directive) {
63
+ const content = await readFile(filePath);
64
+ if (!content) {
65
+ return false;
66
+ }
67
+ const lines = content.split("\n");
68
+ let nonEmptyCount = 0;
69
+ for (const line of lines) {
70
+ const trimmed = line.trim();
71
+ if (!trimmed) continue;
72
+ nonEmptyCount++;
73
+ if (nonEmptyCount > 5) break;
74
+ if (trimmed === `"${directive}";` || trimmed === `'${directive}';` || trimmed === `"${directive}"` || trimmed === `'${directive}'`) {
75
+ return true;
76
+ }
77
+ }
78
+ return false;
79
+ }
80
+ async function findFilesWithPattern(files, pattern, shouldIgnore) {
81
+ const matchingFiles = [];
82
+ const relevantFiles = getCodeFiles(files, shouldIgnore);
83
+ for (const file of relevantFiles) {
84
+ const content = await readFile(file);
85
+ if (!content) continue;
86
+ if (pattern.test(content)) {
87
+ matchingFiles.push(file);
88
+ }
89
+ }
90
+ return matchingFiles;
91
+ }
92
+ export {
93
+ fileContainsPattern,
94
+ fileStartsWithDirective,
95
+ findFilesWithPattern,
96
+ findImportInFiles,
97
+ findPatternInFiles
98
+ };
@@ -0,0 +1,9 @@
1
+ export declare function pathExists(filePath: string): Promise<boolean>;
2
+ export declare function readFile(filePath: string): Promise<string | null>;
3
+ export declare function writeFile(filePath: string, content: string): Promise<void>;
4
+ export declare function copyFile(src: string, dest: string): Promise<void>;
5
+ export declare function readGitignore(projectRoot: string): Promise<string | null>;
6
+ export declare function findProjectFiles(projectRoot: string, shouldIgnore: (file: string) => boolean): Promise<string[]>;
7
+ export declare function findEnvFiles(projectRoot: string): Promise<string[]>;
8
+ export declare function findFilesWithExtension(projectRoot: string, extensions: string[], shouldIgnore: (file: string) => boolean): Promise<string[]>;
9
+ //# sourceMappingURL=file-system.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file-system.d.ts","sourceRoot":"","sources":["../../src/utils/file-system.ts"],"names":[],"mappings":"AAIA,wBAAsB,UAAU,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAOnE;AAED,wBAAsB,QAAQ,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAMvE;AAED,wBAAsB,SAAS,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAGhF;AAED,wBAAsB,QAAQ,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAEvE;AAED,wBAAsB,aAAa,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAE/E;AAED,wBAAsB,gBAAgB,CAAC,WAAW,EAAE,MAAM,EAAE,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAiBtH;AAED,wBAAsB,YAAY,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAqBzE;AAED,wBAAsB,sBAAsB,CAC1C,WAAW,EAAE,MAAM,EACnB,UAAU,EAAE,MAAM,EAAE,EACpB,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,GACtC,OAAO,CAAC,MAAM,EAAE,CAAC,CAUnB"}
@@ -0,0 +1,81 @@
1
+ import fs from "node:fs/promises";
2
+ import path from "node:path";
3
+ import { glob } from "glob";
4
+ async function pathExists(filePath) {
5
+ try {
6
+ await fs.access(filePath);
7
+ return true;
8
+ } catch {
9
+ return false;
10
+ }
11
+ }
12
+ async function readFile(filePath) {
13
+ try {
14
+ return await fs.readFile(filePath, "utf-8");
15
+ } catch {
16
+ return null;
17
+ }
18
+ }
19
+ async function writeFile(filePath, content) {
20
+ await fs.mkdir(path.dirname(filePath), { recursive: true });
21
+ await fs.writeFile(filePath, content, "utf-8");
22
+ }
23
+ async function copyFile(src, dest) {
24
+ await fs.copyFile(src, dest);
25
+ }
26
+ async function readGitignore(projectRoot) {
27
+ return readFile(path.join(projectRoot, ".gitignore"));
28
+ }
29
+ async function findProjectFiles(projectRoot, shouldIgnore) {
30
+ const patterns = ["**/*.{ts,tsx,js,jsx,vue,svelte}", "**/.env*", "**/package.json"];
31
+ const allFiles = [];
32
+ for (const pattern of patterns) {
33
+ const files = await glob(pattern, {
34
+ cwd: projectRoot,
35
+ absolute: true,
36
+ ignore: ["**/node_modules/**", "**/.git/**"],
37
+ dot: true
38
+ });
39
+ allFiles.push(...files);
40
+ }
41
+ const uniqueFiles = [...new Set(allFiles)];
42
+ return uniqueFiles.filter((f) => !shouldIgnore(f));
43
+ }
44
+ async function findEnvFiles(projectRoot) {
45
+ const envFileNames = [
46
+ ".env",
47
+ ".env.local",
48
+ ".env.development",
49
+ ".env.development.local",
50
+ ".env.production",
51
+ ".env.production.local",
52
+ ".env.example"
53
+ ];
54
+ const existingFiles = [];
55
+ for (const fileName of envFileNames) {
56
+ const filePath = path.join(projectRoot, fileName);
57
+ if (await pathExists(filePath)) {
58
+ existingFiles.push(filePath);
59
+ }
60
+ }
61
+ return existingFiles;
62
+ }
63
+ async function findFilesWithExtension(projectRoot, extensions, shouldIgnore) {
64
+ const pattern = `**/*.{${extensions.join(",")}}`;
65
+ const files = await glob(pattern, {
66
+ cwd: projectRoot,
67
+ absolute: true,
68
+ ignore: ["**/node_modules/**", "**/.git/**", "**/dist/**", "**/build/**"]
69
+ });
70
+ return files.filter((f) => !shouldIgnore(f));
71
+ }
72
+ export {
73
+ copyFile,
74
+ findEnvFiles,
75
+ findFilesWithExtension,
76
+ findProjectFiles,
77
+ pathExists,
78
+ readFile,
79
+ readGitignore,
80
+ writeFile
81
+ };
@@ -0,0 +1,10 @@
1
+ import type { PackageJsonData } from '../types.js';
2
+ export declare function readPackageJson(projectRoot: string): Promise<PackageJsonData | null>;
3
+ export declare function getAllDependencies(packageJson: PackageJsonData): Record<string, string>;
4
+ export declare function getParaPackages(packageJson: PackageJsonData): Array<{
5
+ name: string;
6
+ version: string;
7
+ }>;
8
+ export declare function hasDependency(packageJson: PackageJsonData, depName: string): boolean;
9
+ export declare function getDependencyVersion(packageJson: PackageJsonData, depName: string): string | null;
10
+ //# sourceMappingURL=package-json.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"package-json.d.ts","sourceRoot":"","sources":["../../src/utils/package-json.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAEnD,wBAAsB,eAAe,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,eAAe,GAAG,IAAI,CAAC,CAa1F;AAED,wBAAgB,kBAAkB,CAAC,WAAW,EAAE,eAAe,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAKvF;AAED,wBAAgB,eAAe,CAAC,WAAW,EAAE,eAAe,GAAG,KAAK,CAAC;IACnE,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;CACjB,CAAC,CAMD;AAED,wBAAgB,aAAa,CAAC,WAAW,EAAE,eAAe,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAGpF;AAED,wBAAgB,oBAAoB,CAAC,WAAW,EAAE,eAAe,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAGjG"}
@@ -0,0 +1,39 @@
1
+ import path from "node:path";
2
+ import { readFile } from "./file-system.js";
3
+ async function readPackageJson(projectRoot) {
4
+ const pkgPath = path.join(projectRoot, "package.json");
5
+ const content = await readFile(pkgPath);
6
+ if (!content) {
7
+ return null;
8
+ }
9
+ try {
10
+ return JSON.parse(content);
11
+ } catch {
12
+ return null;
13
+ }
14
+ }
15
+ function getAllDependencies(packageJson) {
16
+ return {
17
+ ...packageJson.dependencies,
18
+ ...packageJson.devDependencies
19
+ };
20
+ }
21
+ function getParaPackages(packageJson) {
22
+ const deps = getAllDependencies(packageJson);
23
+ return Object.entries(deps).filter(([name]) => name.startsWith("@getpara/")).map(([name, version]) => ({ name, version }));
24
+ }
25
+ function hasDependency(packageJson, depName) {
26
+ const deps = getAllDependencies(packageJson);
27
+ return depName in deps;
28
+ }
29
+ function getDependencyVersion(packageJson, depName) {
30
+ const deps = getAllDependencies(packageJson);
31
+ return deps[depName] ?? null;
32
+ }
33
+ export {
34
+ getAllDependencies,
35
+ getDependencyVersion,
36
+ getParaPackages,
37
+ hasDependency,
38
+ readPackageJson
39
+ };
package/package.json ADDED
@@ -0,0 +1,52 @@
1
+ {
2
+ "name": "@getpara/paramedic",
3
+ "version": "2.7.0",
4
+ "description": "Para SDK diagnostic and troubleshooting CLI tool",
5
+ "type": "module",
6
+ "bin": {
7
+ "paramedic": "./dist/index.js"
8
+ },
9
+ "main": "./dist/index.js",
10
+ "files": [
11
+ "dist"
12
+ ],
13
+ "scripts": {
14
+ "build": "rm -rf dist && node ./scripts/build.mjs && yarn typegen",
15
+ "typegen": "tsc --emitDeclarationOnly",
16
+ "dev": "tsc --watch",
17
+ "typecheck": "tsc --noEmit",
18
+ "prepublishOnly": "yarn build"
19
+ },
20
+ "dependencies": {
21
+ "@clack/prompts": "^0.9.1",
22
+ "glob": "^11.0.1",
23
+ "ignore": "^6.0.2",
24
+ "picocolors": "^1.1.1"
25
+ },
26
+ "devDependencies": {
27
+ "@types/node": "^22.13.10",
28
+ "esbuild": "0.24.0",
29
+ "typescript": "^5.8.3"
30
+ },
31
+ "engines": {
32
+ "node": ">=18.0.0"
33
+ },
34
+ "keywords": [
35
+ "para",
36
+ "diagnostic",
37
+ "troubleshooting",
38
+ "cli",
39
+ "web3",
40
+ "wallet"
41
+ ],
42
+ "repository": {
43
+ "type": "git",
44
+ "url": "https://github.com/getpara/web-sdk.git",
45
+ "directory": "packages/paramedic"
46
+ },
47
+ "publishConfig": {
48
+ "access": "public"
49
+ },
50
+ "license": "MIT",
51
+ "gitHead": "5a87af838d739b904a124c423b868aaafe7398d9"
52
+ }