@effectstream/npm-midnight-indexer 0.3.99 → 0.100.9

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/binary.js CHANGED
@@ -4,7 +4,8 @@ const axios = require("axios");
4
4
  const extract = require("extract-zip");
5
5
  const path = require("path");
6
6
 
7
- const CURRENT_BINARY_VERSION = "v2.1.4";
7
+ const CURRENT_BINARY_VERSION = "v4.0.0";
8
+ const FINAL_BINARY_NAME = "indexer-standalone";
8
9
 
9
10
  /*
10
11
  @returns {string} The platform and architecture of the current machine. Example: "linux-amd64"
@@ -39,9 +40,12 @@ function getBinaryUrl() {
39
40
  if (!supportedPlatforms.includes(platform)) {
40
41
  throw new Error(`Unsupported platform: ${platform}`);
41
42
  }
42
- return `https://paima-midnight.nyc3.cdn.digitaloceanspaces.com/binaries/indexer-standalone-${platform}-${CURRENT_BINARY_VERSION}.zip`;
43
+
44
+ return `https://github.com/effectstream/binaries/releases/download/0.3.120/indexer-standalone-${platform}-${CURRENT_BINARY_VERSION}.zip`;
43
45
  }
44
46
 
47
+ const ZIP_FILE_PATH = path.join(__dirname, "indexer-standalone.zip");
48
+
45
49
  /*
46
50
  @returns {Promise<void>} Downloads and saves the binary for the current platform.
47
51
  */
@@ -50,9 +54,7 @@ async function downloadAndSaveBinary() {
50
54
  try {
51
55
  console.error(`Downloading... ${url}`);
52
56
  const response = await axios.get(url, { responseType: "stream" });
53
- const writer = fs.createWriteStream(
54
- path.join(__dirname, "indexer-standalone.zip"),
55
- );
57
+ const writer = fs.createWriteStream(ZIP_FILE_PATH);
56
58
 
57
59
  response.data.pipe(writer);
58
60
 
@@ -74,21 +76,73 @@ async function unzipBinary() {
74
76
  if (!fs.existsSync(dir)) {
75
77
  fs.mkdirSync(dir, { recursive: true });
76
78
  }
77
- await extract(path.join(__dirname, "indexer-standalone.zip"), { dir });
78
- fs.unlinkSync(path.join(__dirname, "indexer-standalone.zip"));
79
+ await extract(ZIP_FILE_PATH, { dir });
80
+ const dataDir = path.join(dir, "data");
81
+ if (!fs.existsSync(dataDir)) {
82
+ fs.mkdirSync(dataDir, { recursive: true });
83
+ }
79
84
 
80
85
  const platform = getPlatform();
81
- const parts = platform.split("-");
82
- if (parts[0] === "linux") {
83
- fs.chmodSync(
84
- path.join(
85
- __dirname,
86
- "indexer-standalone",
87
- `indexer-standalone-${platform}`,
88
- ),
89
- 0o755,
90
- );
86
+ const possibleBinaryNames = [
87
+ `indexer-standalone-${platform}-${CURRENT_BINARY_VERSION}`,
88
+ `indexer-standalone`,
89
+ `indexer-standalone-${platform}`
90
+ ];
91
+
92
+ let extractedBinaryPath = null;
93
+ for (const name of possibleBinaryNames) {
94
+ const p = path.join(dir, name);
95
+ if (fs.existsSync(p) && fs.statSync(p).isFile()) {
96
+ extractedBinaryPath = p;
97
+ break;
98
+ }
99
+ }
100
+
101
+ const finalBinaryPath = path.join(dir, FINAL_BINARY_NAME);
102
+
103
+ // Rename the extracted file to indexer-standalone
104
+ if (extractedBinaryPath) {
105
+ if (extractedBinaryPath !== finalBinaryPath) {
106
+ if (fs.existsSync(finalBinaryPath)) {
107
+ fs.unlinkSync(finalBinaryPath);
108
+ }
109
+ fs.renameSync(extractedBinaryPath, finalBinaryPath);
110
+ }
111
+ } else {
112
+ throw new Error(`Extracted binary not found in: ${dir}. Expected one of: ${possibleBinaryNames.join(", ")}`);
113
+ }
114
+
115
+ // Clean up any other extracted files (e.g., readme.md)
116
+ const files = fs.readdirSync(dir);
117
+ for (const file of files) {
118
+ const filePath = path.join(dir, file);
119
+ // Explicitly protect config.yaml and other potential config files
120
+ const isConfigFile =
121
+ file === "config.yaml" ||
122
+ file === "config.yml" ||
123
+ file.endsWith(".yaml") ||
124
+ file.endsWith(".yml") ||
125
+ file.endsWith(".toml") ||
126
+ file.endsWith(".json");
127
+
128
+ if (
129
+ filePath !== finalBinaryPath &&
130
+ file !== "data" &&
131
+ !isConfigFile &&
132
+ fs.existsSync(filePath) &&
133
+ fs.statSync(filePath).isFile()
134
+ ) {
135
+ console.log(`Cleaning up extracted file: ${file}`);
136
+ fs.unlinkSync(filePath);
137
+ }
138
+ }
139
+
140
+ if (!fs.existsSync(finalBinaryPath)) {
141
+ throw new Error(`Expected binary not found: ${finalBinaryPath}`);
91
142
  }
143
+
144
+ fs.chmodSync(finalBinaryPath, 0o755);
145
+ fs.unlinkSync(ZIP_FILE_PATH);
92
146
  }
93
147
 
94
148
  async function binary() {
@@ -96,7 +150,68 @@ async function binary() {
96
150
  await unzipBinary();
97
151
  }
98
152
 
153
+ async function cleanBinaries() {
154
+ const binaryDir = path.join(__dirname, "indexer-standalone");
155
+ const binaryPath = path.join(binaryDir, FINAL_BINARY_NAME);
156
+ const zipPath = path.join(__dirname, "indexer-standalone.zip");
157
+
158
+ let deletedFiles = [];
159
+
160
+ // Delete the binary executable if it exists
161
+ if (fs.existsSync(binaryPath)) {
162
+ try {
163
+ fs.unlinkSync(binaryPath);
164
+ deletedFiles.push(binaryPath);
165
+ } catch (error) {
166
+ console.error(`Error removing binary ${binaryPath}:`, error.message);
167
+ }
168
+ }
169
+
170
+ // Delete the zip file if it exists
171
+ if (fs.existsSync(zipPath)) {
172
+ try {
173
+ fs.unlinkSync(zipPath);
174
+ deletedFiles.push(zipPath);
175
+ } catch (error) {
176
+ console.error(`Error removing file ${zipPath}:`, error.message);
177
+ }
178
+ }
179
+
180
+ // Delete any other binary-related files from the directory, preserving config files
181
+ if (fs.existsSync(binaryDir)) {
182
+ const files = fs.readdirSync(binaryDir);
183
+ for (const file of files) {
184
+ const filePath = path.join(binaryDir, file);
185
+ const stat = fs.statSync(filePath);
186
+
187
+ // Preserve config files and readme
188
+ const isConfigFile =
189
+ file === "config.yaml" ||
190
+ file === "config.yml" ||
191
+ file.endsWith(".yaml") ||
192
+ file.endsWith(".yml") ||
193
+ file.endsWith(".toml") ||
194
+ file.endsWith(".json") ||
195
+ file.toLowerCase().startsWith("readme") ||
196
+ file.toLowerCase().startsWith("license") ||
197
+ file.toLowerCase().startsWith("changelog");
198
+
199
+ if (!isConfigFile && stat.isFile() && fs.existsSync(filePath)) {
200
+ try {
201
+ fs.unlinkSync(filePath);
202
+ deletedFiles.push(filePath);
203
+ } catch (error) {
204
+ console.error(`Error removing file ${filePath}:`, error.message);
205
+ }
206
+ }
207
+ }
208
+ }
209
+
210
+ return deletedFiles;
211
+ }
212
+
99
213
  module.exports = {
100
214
  binary,
101
215
  getPlatform,
216
+ cleanBinaries,
102
217
  };
package/index.js CHANGED
@@ -1,4 +1,4 @@
1
- const { binary, getPlatform } = require("./binary");
1
+ const { binary, getPlatform, cleanBinaries } = require("./binary");
2
2
  const { runMidnightIndexer } = require("./run_midnight_indexer");
3
3
  const { checkIfDockerExists, pullDockerImage, runDockerContainer } = require(
4
4
  "./docker",
@@ -8,12 +8,11 @@ const path = require("path");
8
8
  const readline = require("readline");
9
9
  const os = require("os");
10
10
 
11
+ const FINAL_BINARY_NAME = "indexer-standalone";
12
+
11
13
  function checkIfBinaryExists() {
12
- const platform = getPlatform();
13
- const parts = platform.split("-");
14
- const binaryName = `indexer-standalone-${platform}`;
15
14
  return fs.existsSync(
16
- path.join(__dirname, "indexer-standalone", binaryName),
15
+ path.join(__dirname, "indexer-standalone", FINAL_BINARY_NAME),
17
16
  );
18
17
  }
19
18
 
@@ -22,21 +21,9 @@ function checkIfBinaryExists() {
22
21
  * @returns {boolean} True if binary execution is supported
23
22
  */
24
23
  function isBinarySupported() {
25
- const platform = os.platform();
26
- const arch = os.arch();
27
-
28
- // Check if the current platform-arch combination is supported
24
+ const platformString = getPlatform();
29
25
  const supportedPlatforms = require("./package.json").supportedPlatforms;
30
26
 
31
- let platformString;
32
- if (platform === "darwin") {
33
- platformString = arch === "x64" ? "macos-amd64" : `macos-${arch}`;
34
- } else {
35
- platformString = arch === "x64"
36
- ? `${platform}-amd64`
37
- : `${platform}-${arch}`;
38
- }
39
-
40
27
  return supportedPlatforms.includes(platformString);
41
28
  }
42
29
 
@@ -69,9 +56,12 @@ function showUsage() {
69
56
  Usage: node index.js [options] [args...]
70
57
 
71
58
  Options:
72
- --docker Force use of Docker container
73
- --binary Force use of binary execution (supports Linux and macOS arm64)
74
- --help Show this help message
59
+ --docker Force use of Docker container
60
+ --binary Force use of binary execution (supports Linux and macOS arm64)
61
+ --clean-binaries Delete downloaded binaries and download them again
62
+ --only-clean Only delete downloaded binaries without downloading them again
63
+ --clean Clean the SQLite database (existing flag)
64
+ --help Show this help message
75
65
 
76
66
  Environment Variables:
77
67
  APP__INFRA__SECRET Required: Secret key for the application
@@ -87,10 +77,12 @@ Environment Variables:
87
77
  Note: macOS Intel users will automatically use Docker. macOS arm64 supports both binary and Docker execution.
88
78
 
89
79
  Examples:
90
- APP__INFRA__SECRET=mysecret node index.js --docker # Use Docker
91
- APP__INFRA__SECRET=mysecret node index.js --binary # Use binary (if supported)
92
- APP__INFRA__SECRET=mysecret node index.js # Interactive mode (or auto-Docker on unsupported platforms)
93
- node index.js --help # Show this help
80
+ APP__INFRA__SECRET=mysecret node index.js --docker # Use Docker
81
+ APP__INFRA__SECRET=mysecret node index.js --binary # Use binary (if supported)
82
+ APP__INFRA__SECRET=mysecret node index.js --clean-binaries # Delete and redownload binaries
83
+ node index.js --only-clean # Only delete downloaded binaries
84
+ APP__INFRA__SECRET=mysecret node index.js --clean # Clean SQLite database
85
+ node index.js --help # Show this help
94
86
  `);
95
87
  }
96
88
 
@@ -103,6 +95,8 @@ function parseFlags(args) {
103
95
  const flags = {
104
96
  useDocker: false,
105
97
  useBinary: false,
98
+ cleanBinaries: false,
99
+ onlyClean: false,
106
100
  showHelp: false,
107
101
  remainingArgs: [],
108
102
  };
@@ -112,6 +106,10 @@ function parseFlags(args) {
112
106
  flags.useDocker = true;
113
107
  } else if (args[i] === "--binary") {
114
108
  flags.useBinary = true;
109
+ } else if (args[i] === "--clean-binaries") {
110
+ flags.cleanBinaries = true;
111
+ } else if (args[i] === "--only-clean") {
112
+ flags.onlyClean = true;
115
113
  } else if (args[i] === "--help" || args[i] === "-h") {
116
114
  flags.showHelp = true;
117
115
  } else {
@@ -166,7 +164,7 @@ function setBinaryDefaults(env) {
166
164
  return binaryEnv;
167
165
  }
168
166
 
169
- async function runWithBinary(env, args) {
167
+ async function runWithBinary(env, args, forceClean = false) {
170
168
  console.log("Using binary to run midnight indexer...");
171
169
 
172
170
  // Check for required environment variable
@@ -176,8 +174,12 @@ async function runWithBinary(env, args) {
176
174
  process.exit(1);
177
175
  }
178
176
 
179
- if (!checkIfBinaryExists()) {
180
- console.log("Binary not found, downloading...");
177
+ if (forceClean || !checkIfBinaryExists()) {
178
+ if (forceClean) {
179
+ console.log("Cleaning downloaded binaries...");
180
+ await cleanBinaries();
181
+ }
182
+ console.log("Downloading binary...");
181
183
  await binary();
182
184
  }
183
185
 
@@ -197,6 +199,18 @@ async function main(args) {
197
199
  process.exit(0);
198
200
  }
199
201
 
202
+ // Handle --only-clean flag
203
+ if (flags.onlyClean) {
204
+ console.log("Cleaning downloaded binaries...");
205
+ const deletedFiles = await cleanBinaries();
206
+ if (deletedFiles.length > 0) {
207
+ console.log("Deleted:", deletedFiles.join(", "));
208
+ } else {
209
+ console.log("No downloaded binaries found to delete.");
210
+ }
211
+ process.exit(0);
212
+ }
213
+
200
214
  // If both flags are provided, show error
201
215
  if (flags.useDocker && flags.useBinary) {
202
216
  console.error(
@@ -205,6 +219,14 @@ async function main(args) {
205
219
  process.exit(1);
206
220
  }
207
221
 
222
+ // Validate clean flag usage
223
+ if (flags.cleanBinaries && flags.useDocker) {
224
+ console.error(
225
+ "Error: --clean-binaries flag cannot be used with --docker flag",
226
+ );
227
+ process.exit(1);
228
+ }
229
+
208
230
  // If --docker flag is explicitly provided
209
231
  if (flags.useDocker) {
210
232
  const dockerAvailable = await checkIfDockerExists();
@@ -242,7 +264,7 @@ async function main(args) {
242
264
  );
243
265
  process.exit(1);
244
266
  }
245
- return runWithBinary(env, flags.remainingArgs);
267
+ return runWithBinary(env, flags.remainingArgs, flags.cleanBinaries);
246
268
  }
247
269
 
248
270
  // No explicit flag provided - determine best execution method
@@ -298,7 +320,7 @@ async function main(args) {
298
320
  }
299
321
 
300
322
  // Default to binary execution (only on supported platforms)
301
- return runWithBinary(env, flags.remainingArgs);
323
+ return runWithBinary(env, flags.remainingArgs, flags.clean);
302
324
  }
303
325
 
304
326
  // Handle unhandled promise rejections
@@ -313,4 +335,8 @@ process.on("SIGINT", () => {
313
335
  process.exit(0);
314
336
  });
315
337
 
338
+ module.exports = {
339
+ cleanBinaries,
340
+ };
341
+
316
342
  main(process.argv.slice(2));
@@ -1,37 +1,57 @@
1
- run_migrations: true
2
- network_id: &network_id "Undeployed"
3
-
4
- chain_indexer_application:
5
- network_id: *network_id
6
- blocks_buffer: 60
7
- save_zswap_state_after: 1000
8
- caught_up_max_distance: 60
9
- caught_up_leeway: 30
1
+ thread_stack_size: "24MiB"
10
2
 
11
- wallet_indexer_application:
12
- network_id: *network_id
13
- active_wallets_repeat_delay: "100ms"
3
+ application:
4
+ network_id: "undeployed"
5
+ blocks_buffer: 10
6
+ save_ledger_state_after: 1000
7
+ caught_up_max_distance: 10
8
+ caught_up_leeway: 5
9
+ active_wallets_query_delay: "500ms"
14
10
  active_wallets_ttl: "30m"
15
- transaction_batch_size: 10
16
- # Number of cores by default.
17
- # parallelism:
11
+ transaction_batch_size: 50
12
+ # 1 by default
13
+ # concurrency_limit:
14
+
15
+ # CHECK: linux binary requires this flag in the root.
16
+ run_migrations: true
18
17
 
19
18
  infra:
19
+ run_migrations: true
20
+ storage:
21
+ cnn_url: "data/indexer.sqlite"
22
+
23
+ ledger_db:
24
+ cache_size: "1kiB"
25
+ cnn_url: "data/ledger-db.sqlite"
26
+
20
27
  node:
21
28
  url: "ws://localhost:9944"
22
29
  reconnect_max_delay: "10s" # 10ms, 100ms, 1s, 10s
23
30
  reconnect_max_attempts: 30 # Roughly 5m
24
-
25
- storage:
26
- cnn_url: "./data/indexer.sqlite"
31
+ subscription_recovery_timeout: "30s" # Re-subscribe if no block received within this time
27
32
 
28
33
  api:
29
- address: "127.0.0.1"
34
+ address: "0.0.0.0"
30
35
  port: 8088
31
36
  request_body_limit: "1MiB"
32
37
  max_complexity: 200
33
38
  max_depth: 15
34
- network_id: *network_id
39
+ subscription:
40
+ blocks:
41
+ batch_size: 20
42
+ contract_actions:
43
+ batch_size: 20
44
+ dust_ledger_events:
45
+ batch_size: 20
46
+ shielded_transactions:
47
+ batch_size: 20
48
+ progress_update_interval: "30s"
49
+ keep_wallet_alive_interval: "1m"
50
+ unshielded_transactions:
51
+ batch_size: 20
52
+ progress_update_interval: "30s"
53
+ zswap_ledger_events:
54
+ batch_size: 20
35
55
 
36
56
  telemetry:
37
57
  tracing:
package/package.json CHANGED
@@ -1,16 +1,27 @@
1
1
  {
2
2
  "name": "@effectstream/npm-midnight-indexer",
3
- "version": "0.3.99",
3
+ "version": "0.100.9",
4
4
  "description": "Downloads and runs the Midnight Indexer. It needs a running Midnight Node",
5
5
  "main": "index.js",
6
6
  "scripts": {
7
- "test": "echo \"Error: no test specified\" && exit 1"
7
+ "test": "echo \"Error: no test specified\" && exit 1",
8
+ "clean": "node index.js --clean-binaries",
9
+ "clean-only": "node index.js --only-clean"
8
10
  },
9
11
  "bin": {
10
12
  "npm-midnight-indexer": "index.js"
11
13
  },
12
14
  "author": "Paima Studios",
13
15
  "license": "ISC",
16
+ "homepage": "https://effectstream.github.io/docs/",
17
+ "repository": {
18
+ "type": "git",
19
+ "url": "https://github.com/PaimaStudios/paima-engine",
20
+ "directory": "packages/binaries/midnight-indexer"
21
+ },
22
+ "bugs": {
23
+ "url": "https://github.com/PaimaStudios/paima-engine/issues"
24
+ },
14
25
  "supportedPlatforms": [
15
26
  "linux-arm64",
16
27
  "linux-amd64",
@@ -22,4 +33,4 @@
22
33
  "extract-zip": "^2.0.1",
23
34
  "js-yaml": "^4.1.0"
24
35
  }
25
- }
36
+ }
@@ -2,7 +2,93 @@ const { spawn } = require("child_process");
2
2
  const path = require("path");
3
3
  const fs = require("fs");
4
4
  const yaml = require("js-yaml");
5
- const { getPlatform } = require("./binary");
5
+
6
+ const BINARY_NAME = "indexer-standalone";
7
+
8
+ /**
9
+ * Resolves the configuration file path
10
+ * @param {Object} env - Environment variables
11
+ * @param {string} workingDir - The working directory where the indexer runs
12
+ * @returns {string} The resolved configuration file path
13
+ */
14
+ function resolveConfigPath(env, workingDir) {
15
+ if (env.CONFIG_FILE) {
16
+ return path.isAbsolute(env.CONFIG_FILE)
17
+ ? env.CONFIG_FILE
18
+ : path.resolve(workingDir, env.CONFIG_FILE);
19
+ }
20
+ // Fall back to config.yaml in the current working directory
21
+ return path.join(workingDir, "config.yaml");
22
+ }
23
+
24
+ /**
25
+ * Ensures that a configuration file exists at the given path
26
+ * @param {string} configPath - The path to the configuration file
27
+ * @param {Object} env - Environment variables
28
+ */
29
+ function ensureConfigExists(configPath, env) {
30
+ if (fs.existsSync(configPath)) {
31
+ return;
32
+ }
33
+
34
+ console.log(
35
+ `Config file not found. Generating default config at: ${configPath}`,
36
+ );
37
+
38
+ const networkId = env.LEDGER_NETWORK_ID || "Undeployed";
39
+ const nodeUrl = env.SUBSTRATE_NODE_WS_URL ||
40
+ env.APP__INFRA__NODE__URL ||
41
+ "ws://localhost:9944";
42
+ const cnnUrl = env.APP__INFRA__STORAGE__CNN_URL || "./data/indexer.sqlite";
43
+ const apiPort = env.APP__INFRA__API__PORT || 8088;
44
+
45
+ const defaultConfig = `
46
+ run_migrations: true
47
+ network_id: &network_id "${networkId}"
48
+
49
+ chain_indexer_application:
50
+ network_id: *network_id
51
+ blocks_buffer: 60
52
+ save_zswap_state_after: 1000
53
+ caught_up_max_distance: 60
54
+ caught_up_leeway: 30
55
+
56
+ wallet_indexer_application:
57
+ network_id: *network_id
58
+ active_wallets_repeat_delay: "100ms"
59
+ active_wallets_ttl: "30m"
60
+ transaction_batch_size: 10
61
+
62
+ infra:
63
+ node:
64
+ url: "${nodeUrl}"
65
+ reconnect_max_delay: "10s"
66
+ reconnect_max_attempts: 30
67
+
68
+ storage:
69
+ cnn_url: "${cnnUrl}"
70
+
71
+ api:
72
+ address: "0.0.0.0"
73
+ port: ${apiPort}
74
+ request_body_limit: "1MiB"
75
+ max_complexity: 200
76
+ max_depth: 15
77
+ network_id: *network_id
78
+
79
+ telemetry:
80
+ tracing:
81
+ enabled: false
82
+ service_name: "indexer"
83
+ metrics:
84
+ enabled: false
85
+ address: "0.0.0.0"
86
+ port: 9000
87
+ `;
88
+
89
+ fs.writeFileSync(configPath, defaultConfig.trim());
90
+ }
91
+
6
92
  /**
7
93
  * Resolves the SQLite database path using the midnight-indexer configuration rules
8
94
  * @param {Object} env - Environment variables
@@ -17,17 +103,7 @@ function resolveSqlitePath(env, workingDir) {
17
103
  return envCnnUrl;
18
104
  }
19
105
 
20
- // Determine config file path using the configuration resolution rules
21
- let configPath;
22
- if (env.CONFIG_FILE) {
23
- configPath = path.isAbsolute(env.CONFIG_FILE)
24
- ? env.CONFIG_FILE
25
- : path.resolve(workingDir, env.CONFIG_FILE);
26
- } else {
27
- // Fall back to config.yaml in the current working directory
28
- configPath = path.join(workingDir, "config.yaml");
29
- }
30
-
106
+ const configPath = resolveConfigPath(env, workingDir);
31
107
  console.log(`Looking for config file at: ${configPath}`);
32
108
 
33
109
  // Check if config file exists
@@ -64,6 +140,24 @@ function resolveSqlitePath(env, workingDir) {
64
140
  }
65
141
  }
66
142
 
143
+ /**
144
+ * Resolves the SQLite database path with a fallback to the default location
145
+ * @param {Object} env - Environment variables
146
+ * @param {string} workingDir - The working directory where the indexer runs
147
+ * @returns {string} The resolved SQLite database path
148
+ */
149
+ function resolveSqlitePathWithFallback(env, workingDir) {
150
+ const sqlitePath = resolveSqlitePath(env, workingDir);
151
+ if (sqlitePath) {
152
+ return sqlitePath;
153
+ }
154
+
155
+ // Fallback to default indexer location: data/indexer.sqlite
156
+ const defaultPath = path.join(workingDir, "data", "indexer.sqlite");
157
+ console.log(`Using default SQLite path: ${defaultPath}`);
158
+ return defaultPath;
159
+ }
160
+
67
161
  /**
68
162
  * Handles the --clean flag by deleting the SQLite database file
69
163
  * @param {Object} env - Environment variables
@@ -72,12 +166,7 @@ function resolveSqlitePath(env, workingDir) {
72
166
  function handleCleanFlag(env, workingDir) {
73
167
  console.log("Processing --clean flag...");
74
168
 
75
- const sqlitePath = resolveSqlitePath(env, workingDir);
76
-
77
- if (!sqlitePath) {
78
- console.warn("Could not resolve SQLite database path. Skipping cleanup.");
79
- return;
80
- }
169
+ const sqlitePath = resolveSqlitePathWithFallback(env, workingDir);
81
170
 
82
171
  // Handle sqlite:// URLs and extract the file path
83
172
  let filePath = sqlitePath;
@@ -110,16 +199,16 @@ function handleCleanFlag(env, workingDir) {
110
199
  * @returns {ChildProcess} The spawned child process
111
200
  */
112
201
  function runMidnightIndexer(env = process.env, args = []) {
113
- const platform = getPlatform();
114
- const parts = platform.split("-");
115
- const binaryName = `indexer-standalone-${platform}`;
116
202
  const binaryPath = path.join(
117
203
  __dirname,
118
204
  "indexer-standalone",
119
- binaryName,
205
+ BINARY_NAME,
120
206
  );
121
207
  const workingDir = path.join(__dirname, "indexer-standalone");
122
208
 
209
+ const configPath = resolveConfigPath(env, workingDir);
210
+ ensureConfigExists(configPath, env);
211
+
123
212
  // Check for --clean flag and handle it
124
213
  const cleanFlagIndex = args.indexOf("--clean");
125
214
  if (cleanFlagIndex !== -1) {
@@ -130,6 +219,11 @@ function runMidnightIndexer(env = process.env, args = []) {
130
219
 
131
220
  console.log(`Starting midnight-indexer binary at: ${binaryPath}`);
132
221
 
222
+ const dataDir = path.join(workingDir, "data");
223
+ if (!fs.existsSync(dataDir)) {
224
+ fs.mkdirSync(dataDir, { recursive: true });
225
+ }
226
+
133
227
  const childProcess = spawn(binaryPath, args, {
134
228
  env: env,
135
229
  stdio: "inherit", // Inherit stdin, stdout, stderr from parent process