### Instantiate and Start BasRemoteClient Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Client) Instantiate BasRemoteClient with a script name and start the client. This is a prerequisite for running functions. ```javascript const client = new BasRemoteClient({scriptName: 'TestRemoteControl'}); await client.start(); ``` -------------------------------- ### client.start([timeout]) Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Initializes and connects the client by downloading, starting the BAS engine, and establishing a WebSocket connection. It waits for a handshake and accepts an optional timeout. ```APIDOC ## `client.start([timeout])` — Initialize and connect the client Downloads (if necessary) and starts the BAS engine subprocess, then opens a WebSocket connection and waits for the `thread_start` handshake. The optional `timeout` (default `60000` ms) controls how long to wait before rejecting. Must be called once before any other method. Subsequent calls are no-ops if the client is already started. ```js const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { try { // Engine download + extract only happens on first run or version change. // Subsequent starts typically complete in under 5 seconds. await client.start(90000); // 90-second timeout console.log('Client ready'); } catch (err) { console.error('Failed to start:', err.message); // Common errors: // 'Script with selected name not exist' // 'Script engine not supported (Required 22.4.2 or newer)' // 'Timeout during client initialize' process.exit(1); } } main(); ``` ``` -------------------------------- ### Quick Start: Automate Google Search with bas-remote-node Source: https://github.com/bablosoft/bas-remote-node/blob/master/README.md This example demonstrates how to connect to a BAS script, run a function named 'GoogleSearch' with a 'cats' query, and log the resulting URLs. Ensure you have a BAS script named 'TestRemoteControl' with a function 'GoogleSearch' configured for remote execution. ```javascript const BasRemoteClient = require('bas-remote-node'); async function main() { //Set script name, and optionally auth details (login, password) const options = { scriptName: 'TestRemoteControl' /* or 'YourScriptName' */, }; //Create client const scriptClient = new BasRemoteClient(options); //Start application, this may take some time await scriptClient.start(); //Set parameters for function const scriptParams = { Query: 'cats', }; //Run function and wait for result //Following function will return list of strings const result = await scriptClient.runFunction('GoogleSearch' /* or 'YourFunctionName' */, scriptParams); //Iterate and output results result.forEach(link => { console.log(link); }); await scriptClient.close(); } main(); ``` -------------------------------- ### Install bas-remote-node Source: https://github.com/bablosoft/bas-remote-node/blob/master/README.md Install the bas-remote-node library using npm. This is the first step to integrate browser automation into your NodeJS projects. ```bash npm install --save bas-remote-node ``` -------------------------------- ### Initialize and Connect BasRemoteClient Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Start the BAS engine and establish a WebSocket connection. This must be called before other methods. Handles engine download and extraction on first run. Subsequent calls are no-ops. ```javascript const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { try { // Engine download + extract only happens on first run or version change. // Subsequent starts typically complete in under 5 seconds. await client.start(90000); // 90-second timeout console.log('Client ready'); } catch (err) { console.error('Failed to start:', err.message); // Common errors: // 'Script with selected name not exist' // 'Script engine not supported (Required 22.4.2 or newer)' // 'Timeout during client initialize' process.exit(1); } } main(); ``` -------------------------------- ### Initialize and Close Bas-Remote-Node Client Source: https://github.com/bablosoft/bas-remote-node/wiki/Quick-start Initialize the client with a script name and ensure the connection is closed after use. The start() method initializes the script, and close() terminates the connection. ```javascript const BasRemoteClient = require('bas-remote-node'); async function main() { const client = new BasRemoteClient({scriptName: 'TestRemoteControl'}); // Initialize script (Required) await client.start(); // Permorm any actions here // Close client connection await client.close(); } main(); ``` -------------------------------- ### Send Message and Wait for Result with Async/Await Source: https://github.com/bablosoft/bas-remote-node/wiki/Messages Utilize sendAsync() with the await keyword for cleaner asynchronous code. This example sets a global variable and then retrieves its value. ```javascript // Set global variable with name 'TEST_VARIABLE' and value 'Hello'. await client.sendAsync('set_global_variable', { name: 'TEST_VARIABLE', value: JSON.stringify('Hello') }); // Retrieve actual variable value. const variable = await client.sendAsync('get_global_variable', { name: 'TEST_VARIABLE' }); // Print the value. console.log(variable); ``` -------------------------------- ### Send Message and Perform Action with Promises Source: https://github.com/bablosoft/bas-remote-node/wiki/Messages Use sendAsync() with .then() to chain operations and handle results asynchronously. This example sets a global variable and then retrieves its value. ```javascript // Set global variable with name 'TEST_VARIABLE' and value 'Hello'. client.sendAsync('set_global_variable', { name: 'TEST_VARIABLE', value: JSON.stringify('Hello') }) .then(() => { // Retrieve actual variable value. return client.sendAsync('get_global_variable', { name: 'TEST_VARIABLE' }); }) .then((result) => { // Print the value. console.log(result); }); ``` -------------------------------- ### Subscribe to Log and Thread Events Source: https://github.com/bablosoft/bas-remote-node/wiki/Events Use `client.on()` to subscribe to 'messageReceived' events. Filter by 'type' to process specific events like 'log', 'thread_start', or 'thread_end'. Ensure the client is started with `await client.start()` before performing actions. ```javascript const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({scriptName: 'TestRemoteControl'}); // Add event handler for log messages. client.on('messageReceived', ({ type, data }) => { // Process only log event. if (type === 'log') { // Retrieve log text. const { text } = data; // Output text to the console console.log(`[Log] - ${text}`); } }); // Add event handler for threads. client.on('messageReceived', ({ type, data }) => { if (type === 'thread_start') { console.log('[Thread] - started'); } if (type === 'thread_end') { console.log('[Thread] - ended'); } }); await client.start(); // Perform any actions here. ``` -------------------------------- ### client.setWorkingFolder Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Change the engine working directory used for caching the BAS engine binary and per-script run folders. This must be called before `start()` to affect engine placement. ```APIDOC ## `client.setWorkingFolder(workingDir)` — Change the engine working directory Updates the local directory used for caching the BAS engine binary and per-script run folders. Must be called before `start()` to have any effect on engine placement. Accepts either an absolute or relative path (resolved to absolute internally). ### Parameters #### Path Parameters - **workingDir** (string) - Required - The absolute or relative path to the new working directory. ### Example ```javascript const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); // Override working folder before starting client.setWorkingFolder('/opt/bas-cache'); await client.start(); // Engine stored at: /opt/bas-cache/engine// // Script run dirs: /opt/bas-cache/run/TestRemoteControl// await client.close(); ``` ``` -------------------------------- ### Send Message Without Waiting for Result Source: https://github.com/bablosoft/bas-remote-node/wiki/Messages Use the send() method for fire-and-forget messages when no immediate result is needed. This example shows the database manager window. ```javascript client.send('show_database_manager'); ``` -------------------------------- ### Create and Manage Reusable BAS Threads Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Use `client.createThread()` to get a `BasThread` instance for persistent state across multiple `runFunction` calls. Configure thread-specific settings like proxies and explicitly manage thread lifetime with `stop()`. ```javascript const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { await client.start(); const thread = client.createThread(); // Configure proxy on this thread await thread.runFunction('SetProxy', { Proxy: '192.168.1.100:8080', IsSocks5: 'false', }); // Verify the proxy IP on the same thread const ip = await thread.runFunction('CheckIp'); console.log('Thread IP:', ip); // e.g. '192.168.1.100' // Check busy state before dispatching more work if (!thread.isRunning) { const result = await thread.runFunction('GoogleSearch', { Query: 'nodejs' }); console.log('Results:', result); } // Manually stop and release the thread thread.stop(); await client.close(); } main(); ``` -------------------------------- ### new BasRemoteClient(options) Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Constructs a new BasRemoteClient instance. Requires `scriptName` and optionally accepts `login`, `password`, `workingDir`, and `args` for configuration. ```APIDOC ## `new BasRemoteClient(options)` — Create a remote client instance Constructs a new `BasRemoteClient`. The `scriptName` option is required and must match the name of a BAS script available in the cloud. `login` and `password` are only needed for private scripts. `workingDir` controls where the engine binary and script files are cached (defaults to `./data` relative to the process working directory). Additional engine CLI arguments can be passed via `args`. ```js const BasRemoteClient = require('bas-remote-node'); // Public script — no credentials needed const client = new BasRemoteClient({ scriptName: 'TestRemoteControl', }); // Private script with authentication and custom working directory const privateClient = new BasRemoteClient({ scriptName: 'MyPrivateScript', login: 'myuser@example.com', password: 'secret', workingDir: '/var/app/bas-data', args: ['--some-engine-flag'], }); ``` ``` -------------------------------- ### Create BasRemoteClient Instance Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Instantiate BasRemoteClient with script name. Provide login/password for private scripts and specify a working directory if needed. Additional engine arguments can be passed. ```javascript const BasRemoteClient = require('bas-remote-node'); // Public script — no credentials needed const client = new BasRemoteClient({ scriptName: 'TestRemoteControl', }); // Private script with authentication and custom working directory const privateClient = new BasRemoteClient({ scriptName: 'MyPrivateScript', login: 'myuser@example.com', password: 'secret', workingDir: '/var/app/bas-data', args: ['--some-engine-flag'], }); ``` -------------------------------- ### Create and Manage a Remote Thread Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Threads) Use `client.createThread()` to instantiate a new thread. You can then use the thread object to run functions, set configurations like proxies, and stop the thread when done. Ensure proxy details are correctly formatted. ```javascript const thread = client.createThread(); // Set up proxy. await thread.runFunction('SetProxy', { Proxy: '127.0.0.1:11185', IsSocks5: 'true', }); // Check the ip of this proxy. const proxyIp = await thread.runFunction('CheckIp'); // Stop the thread. thread.stop(); ``` -------------------------------- ### Run Multiple Functions in Parallel Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Client) Execute multiple functions concurrently using Promise.all. This is efficient for independent tasks. ```javascript // Start functions. const promise1 = client.runFunction('GoogleSearch', {Query: 'cats'}); const promise2 = client.runFunction('GoogleSearch', {Query: 'dogs'}); // Wait for both functions to finish. const results = await Promise.all([promise1, promise2]) // Output results. results.forEach(result => console.log(result)) ``` -------------------------------- ### Run Single Function with Async/Await Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Client) Execute a single function and retrieve its result using async/await. Pass function name and parameters. ```javascript // Run function and get result using 'await'. const result = await client.runFunction('GoogleSearch', { Query: 'cats' }); console.log(result); ``` -------------------------------- ### client.runFunction(functionName, params) Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Calls a specified BAS function by name with given parameters, managing thread creation and teardown automatically. Returns a Promise that resolves with the function's return value. ```APIDOC ## `client.runFunction(functionName, params)` — Call a BAS function via the client Calls a BAS function by name, automatically creating and tearing down a dedicated thread. Returns a decorated Promise that resolves with the function's return value (already parsed from JSON). The decorated Promise also exposes `.stop()` to interrupt execution and `.threadId` to inspect which thread was allocated. Throws if the client has not been started. ```js const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { await client.start(); // Single call with await const links = await client.runFunction('GoogleSearch', { Query: 'open source nodejs' }); links.forEach((url) => console.log(url)); // Parallel calls — each gets its own thread automatically const [catsLinks, dogsLinks] = await Promise.all([ client.runFunction('GoogleSearch', { Query: 'cats' }), client.runFunction('GoogleSearch', { Query: 'dogs' }), ]); console.log('Cats results:', catsLinks.length); console.log('Dogs results:', dogsLinks.length); // Error handling — BAS errors surface as rejected Promises try { await client.runFunction('NotExistingFunction'); } catch (err) { console.error('BAS error:', err.message); } // Interrupt a long-running function after a timeout const resultPromise = client.runFunction('LongRunningFunction').catch((err) => { console.warn('Stopped:', err.message); // 'Task stopped manually' }); setTimeout(() => resultPromise.stop(), 10000); await resultPromise; await client.close(); } main(); ``` ``` -------------------------------- ### client.createThread() Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Creates a reusable BAS thread instance bound to the client. Threads persist across multiple `runFunction` calls, allowing for state configuration and reuse. Use this when explicit control over thread lifetime is needed. ```APIDOC ## `client.createThread()` — Create a reusable BAS thread Returns a `BasThread` instance bound to this client. Threads persist across multiple `runFunction` calls, allowing you to set up state (e.g., proxy configuration) and reuse it for subsequent calls on the same thread. Use when you need explicit control over thread lifetime. ```js const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { await client.start(); const thread = client.createThread(); // Configure proxy on this thread await thread.runFunction('SetProxy', { Proxy: '192.168.1.100:8080', IsSocks5: 'false', }); // Verify the proxy IP on the same thread const ip = await thread.runFunction('CheckIp'); console.log('Thread IP:', ip); // e.g. '192.168.1.100' // Check busy state before dispatching more work if (!thread.isRunning) { const result = await thread.runFunction('GoogleSearch', { Query: 'nodejs' }); console.log('Results:', result); } // Manually stop and release the thread thread.stop(); await client.close(); } main(); ``` ``` -------------------------------- ### Change Engine Working Directory with setWorkingFolder Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Update the local directory for caching the BAS engine binary and per-script run folders. This must be called before client.start() to affect engine placement. Accepts absolute or relative paths. ```javascript const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); // Override working folder before starting client.setWorkingFolder('/opt/bas-cache'); await client.start(); // Engine stored at: /opt/bas-cache/engine// // Script run dirs: /opt/bas-cache/run/TestRemoteControl// await client.close(); ``` -------------------------------- ### Run Single Function with then/catch Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Client) Execute a single function and handle its result using the Promise.then() method. Ensure the promise is awaited or handled to avoid race conditions. ```javascript // Run function and get result using 'then'. const promise = client.runFunction('GoogleSearch', { Query: 'cats' }) .then((links) => console.log(links)); await promise; ``` -------------------------------- ### client.on / client.once / client.off Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Subscribe to WebSocket events to react to incoming messages, track thread lifecycle, and manage outgoing messages. `messageReceived` provides details about incoming BAS messages, while `messageSent` mirrors outgoing messages. ```APIDOC ## `client.on(event, listener)` / `client.once(event, listener)` / `client.off(event, listener)` — Subscribe to WebSocket events Attaches persistent or one-time listeners to the underlying socket event emitter. The `messageReceived` event fires for every incoming BAS message with `{ type, data, async, id }`. The `messageSent` event mirrors outgoing messages. Use these to react to log output, thread lifecycle notifications, and any other events emitted by the BAS script. ### Parameters #### Path Parameters - **event** (string) - Required - The name of the event to listen for (e.g., 'messageReceived', 'messageSent'). - **listener** (function) - Required - The callback function to execute when the event is fired. ### Example ```javascript // Stream BAS log output to console client.on('messageReceived', ({ type, data }) => { if (type === 'log') { console.log('[BAS Log]', data.text); } }); // One-time listener — fires only for the first sent message client.once('messageSent', (message) => { console.log('First outgoing message type:', message.type); }); // Detach a listener when no longer needed const logListener = ({ type, data }) => { if (type === 'log') console.log(data.text); }; client.on('messageReceived', logListener); // ... later ... client.off('messageReceived', logListener); ``` ``` -------------------------------- ### Call BAS Function with BasRemoteClient Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Execute a BAS function by name, automatically managing threads. Returns a Promise that resolves with the function's result. Use `.stop()` to interrupt and `.threadId` to inspect the thread. Handles BAS errors as rejected Promises. ```javascript const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { await client.start(); // Single call with await const links = await client.runFunction('GoogleSearch', { Query: 'open source nodejs' }); links.forEach((url) => console.log(url)); // Parallel calls — each gets its own thread automatically const [catsLinks, dogsLinks] = await Promise.all([ client.runFunction('GoogleSearch', { Query: 'cats' }), client.runFunction('GoogleSearch', { Query: 'dogs' }), ]); console.log('Cats results:', catsLinks.length); console.log('Dogs results:', dogsLinks.length); // Error handling — BAS errors surface as rejected Promises try { await client.runFunction('NotExistingFunction'); } catch (err) { console.error('BAS error:', err.message); } // Interrupt a long-running function after a timeout const resultPromise = client.runFunction('LongRunningFunction').catch((err) => { console.warn('Stopped:', err.message); // 'Task stopped manually' }); setTimeout(() => resultPromise.stop(), 10000); await resultPromise; await client.close(); } main(); ``` -------------------------------- ### client.sendAsync(type, data) Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Sends a typed protocol message asynchronously to the running BAS script. It returns a Promise that resolves with the script's response. This method is useful for reading and writing BAS global variables, triggering UI actions, or any other message type supported by the BAS remote-control protocol. ```APIDOC ## `client.sendAsync(type, data)` — Send an async message to the BAS script Sends a typed protocol message to the running BAS script and returns a Promise that resolves with the script's response. Useful for reading and writing BAS global variables, triggering UI actions, or any other message type supported by the BAS remote-control protocol. ```js await client.start(); // Write a global variable in BAS await client.sendAsync('set_global_variable', { name: 'API_KEY', value: JSON.stringify('abc-123'), }); // Read it back const apiKey = await client.sendAsync('get_global_variable', { name: 'API_KEY' }); console.log('API_KEY =', apiKey); // 'abc-123' // Chain with .then() client.sendAsync('set_global_variable', { name: 'COUNTER', value: JSON.stringify(0) }) .then(() => client.sendAsync('get_global_variable', { name: 'COUNTER' })) .then((val) => console.log('Counter:', val)); // 0 ``` ``` -------------------------------- ### Shut Down BasRemoteClient with client.close() Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Gracefully terminate the BAS engine subprocess and close the WebSocket connection. This resets 'isStarted' to false. Always call 'close()' in a 'finally' block to prevent orphaned BAS processes. ```javascript const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { await client.start(); try { const result = await client.runFunction('Add', { X: 10, Y: 20 }); console.log('Result:', result); // 30 } finally { // Always close, even if runFunction throws await client.close(); console.log('Client closed'); } } main(); ``` -------------------------------- ### client.close Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Shut down the client by gracefully terminating the BAS engine subprocess and closing the WebSocket connection. This should always be called to prevent orphaned BAS processes. ```APIDOC ## `client.close()` — Shut down the client Gracefully terminates the BAS engine subprocess and closes the WebSocket connection. Sets `isStarted` back to `false`. Should always be called in a `finally` block to prevent orphaned BAS processes. ### Example ```javascript const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); async function main() { await client.start(); try { const result = await client.runFunction('Add', { X: 10, Y: 20 }); console.log('Result:', result); // 30 } finally { // Always close, even if runFunction throws await client.close(); console.log('Client closed'); } } main(); ``` ``` -------------------------------- ### Run Sequential Operations on a BAS Thread Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Utilize `thread.runFunction()` to execute sequential operations on the same BAS thread. The thread ID is allocated lazily and reused. Check `thread.isRunning` before dispatching new work to avoid rejections. ```javascript // Run sequential operations on the same thread const thread = client.createThread(); // Step 1 — set up proxy await thread.runFunction('SetProxy', { Proxy: '10.0.0.1:3128', IsSocks5: 'false' }); // Step 2 — verify identity const ip = await thread.runFunction('CheckIp'); console.log('Proxied IP:', ip); // Step 3 — use thread only when free if (!thread.isRunning) { const sum = await thread.runFunction('Add', { X: 3, Y: 7 }); console.log('3 + 7 =', sum); // 10 } // Inspect thread state console.log('Thread ID:', thread.threadId); // e.g. 482910 console.log('Is running:', thread.isRunning); // false thread.stop(); // releases the thread ID ``` -------------------------------- ### Send Async Messages to BAS Script Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Employ `client.sendAsync()` to send typed protocol messages to the BAS script, resolving with the script's response. This is useful for interacting with BAS global variables, UI actions, or other protocol-defined messages. ```javascript await client.start(); // Write a global variable in BAS await client.sendAsync('set_global_variable', { name: 'API_KEY', value: JSON.stringify('abc-123'), }); // Read it back const apiKey = await client.sendAsync('get_global_variable', { name: 'API_KEY' }); console.log('API_KEY =', apiKey); // 'abc-123' // Chain with .then() client.sendAsync('set_global_variable', { name: 'COUNTER', value: JSON.stringify(0) }) .then(() => client.sendAsync('get_global_variable', { name: 'COUNTER' })) .then((val) => console.log('Counter:', val)); // 0 ``` -------------------------------- ### BasThread.runFunction(functionName, params) Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Calls a BAS function on a specific thread using its persistent BAS thread ID. Rejects immediately if the thread is already running a function. The thread ID is allocated lazily on the first call and reused until `stop()` is called. Resolves or rejects identically to the client-level `runFunction`. ```APIDOC ## `BasThread.runFunction(functionName, params)` — Call a BAS function on a specific thread Calls a BAS function on the thread's persistent BAS thread ID. Rejects immediately if the thread is already running a function (`thread.isRunning === true`). The thread ID is allocated lazily on the first call and reused for all subsequent calls until `stop()` is called. Resolves or rejects identically to the client-level `runFunction`. ```js // Run sequential operations on the same thread const thread = client.createThread(); // Step 1 — set up proxy await thread.runFunction('SetProxy', { Proxy: '10.0.0.1:3128', IsSocks5: 'false' }); // Step 2 — verify identity const ip = await thread.runFunction('CheckIp'); console.log('Proxied IP:', ip); // Step 3 — use thread only when free if (!thread.isRunning) { const sum = await thread.runFunction('Add', { X: 3, Y: 7 }); console.log('3 + 7 =', sum); // 10 } // Inspect thread state console.log('Thread ID:', thread.threadId); // e.g. 482910 console.log('Is running:', thread.isRunning); // false thread.stop(); // releases the thread ID ``` ``` -------------------------------- ### Subscribe to WebSocket Events with BasRemoteClient Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Attach persistent or one-time listeners to WebSocket events like 'messageReceived' and 'messageSent'. Use these to react to BAS script output, thread lifecycle changes, and other emitted events. Detach listeners using 'off' when no longer needed. ```javascript const BasRemoteClient = require('bas-remote-node'); const client = new BasRemoteClient({ scriptName: 'TestRemoteControl' }); // Stream BAS log output to console client.on('messageReceived', ({ type, data }) => { if (type === 'log') { console.log('[BAS Log]', data.text); } }); // Track thread lifecycle client.on('messageReceived', ({ type }) => { if (type === 'thread_start') console.log('[Thread] started'); if (type === 'thread_end') console.log('[Thread] ended'); }); // One-time listener — fires only for the first sent message client.once('messageSent', (message) => { console.log('First outgoing message type:', message.type); }); // Detach a listener when no longer needed const logListener = ({ type, data }) => { if (type === 'log') console.log(data.text); }; client.on('messageReceived', logListener); // ... later ... client.off('messageReceived', logListener); await client.start(); await client.runFunction('GoogleSearch', { Query: 'bas remote node' }); await client.close(); ``` -------------------------------- ### Send Fire-and-Forget Messages to BAS Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Use `client.send()` for fire-and-forget messages to BAS without waiting for a response. It returns the message ID and is suitable for one-way commands or notifications where no result is expected. ```javascript await client.start(); // Open the BAS database manager window client.send('show_database_manager'); // Send with async flag and manually track response via messageReceived const msgId = client.send('some_custom_type', { key: 'value' }, true); console.log('Sent message ID:', msgId); ``` -------------------------------- ### client.send(type, data, isAsync) Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Sends a protocol message to BAS without waiting for a response. It returns the numeric message ID assigned to the outgoing frame. This method is suitable for one-way UI commands or notifications where no result is expected. ```APIDOC ## `client.send(type, data, isAsync)` — Send a fire-and-forget message Sends a protocol message to BAS without waiting for a response. Returns the numeric message ID assigned to the outgoing frame. Suitable for one-way UI commands or notifications where no result is expected. ```js await client.start(); // Open the BAS database manager window client.send('show_database_manager'); // Send with async flag and manually track response via messageReceived const msgId = client.send('some_custom_type', { key: 'value' }, true); console.log('Sent message ID:', msgId); ``` ``` -------------------------------- ### Conditional Function Execution in a Thread Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Threads) Check the `isRunning` property before calling `runFunction` to ensure the thread is not already busy. This prevents race conditions and ensures functions are executed only when the thread is available. ```javascript // Run function only if thread is free. if (!thread.isRunning) { await thread.runFunction('SomeFunction'); } // Run another function only if thread is free. if (!thread.isRunning) { await thread.runFunction('SomeAnotherFunction'); } ``` -------------------------------- ### Handle Function Execution Errors Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Client) Catch errors during function execution using a try/catch block. Errors from the remote function will be thrown. ```javascript try { await client.runFunction('NotExistingFunction'); } catch(err) { console.log(err.message); } ``` -------------------------------- ### Stop and Release a BAS Thread Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Use `thread.stop()` to immediately signal BAS to stop the thread's current execution, resetting its state. The thread object can then be reused, with the next `runFunction` call allocating a new thread ID. ```javascript const thread = client.createThread(); // Start a long task without awaiting const promise = thread.runFunction('LongRunningFunction').catch((err) => { console.log(err.message); // 'Task stopped manually' }); // Stop it after 5 seconds setTimeout(() => { thread.stop(); }, 5000); await promise; console.log('Thread is free again. threadId:', thread.threadId); // 0 ``` -------------------------------- ### BasThread.stop() Source: https://context7.com/bablosoft/bas-remote-node/llms.txt Stops a thread and releases its ID. It immediately signals BAS to stop the thread's current execution and resets `isRunning` to `false` and `threadId` to `0`. The thread object can be reused after calling `stop()`; the next `runFunction` call will allocate a fresh thread ID. ```APIDOC ## `BasThread.stop()` — Stop a thread and release its ID Immediately signals BAS to stop the thread's current execution and resets `isRunning` to `false` and `threadId` to `0`. After `stop()`, the thread object can be reused — the next `runFunction` call will allocate a fresh thread ID. ```js const thread = client.createThread(); // Start a long task without awaiting const promise = thread.runFunction('LongRunningFunction').catch((err) => { console.log(err.message); // 'Task stopped manually' }); // Stop it after 5 seconds setTimeout(() => { thread.stop(); }, 5000); await promise; console.log('Thread is free again. threadId:', thread.threadId); // 0 ``` ``` -------------------------------- ### Interrupt Function Execution Source: https://github.com/bablosoft/bas-remote-node/wiki/Functions-(Client) Stop a running function using the stop() method on the returned promise. This is useful for implementing timeouts or canceling long-running tasks. ```javascript const resultPromise = client.runFunction('LongRunningFunction') .catch((err) => { // Handle 'Task stopped manually' error. console.log(err.message); }); // Stop function execution after ten seconds. setTimeout(() => { resultPromise.stop(); }, 10000); ``` === COMPLETE CONTENT === This response contains all available snippets from this library. No additional content exists. Do not make further requests.