Embedding NodeRed & Creating nodes

Hi folks,
thanks for furter reading. I'm tryng to integrate nodered with my already existing typescript@node.js app. I already use express as ws, so, by follow embedding guide (https://nodered.org/docs/user-guide/runtime/embedding) I'm able to start an embedded fully operational version of NodeRed. Ok, so good :slight_smile:
Then I would like to have some nodes that interact with my app mechanichs, such as websocket or graphQL interface. I tryed to create a basic nodeType with RED.nodes.registerType function from inside my app lifecycle right after RED initialization promise resolution (in it's then). On NodeRed log output I can't see anything relevant but the node won't appear on editor.

So my questions are: what is the right way to achieve this kind of integration? Where I put html file and how can bring it to embed node-red?
Unfortunately the documentation about embedding doesn't explain well this part. Also @types I found on npm isn't corrected forcing me to use a lot of "any", losing precious intellisense aid :slight_smile:

I'm struggling into this since a couple of days and the only achieve I got is a tera-headache :smiley:
Any halp is greatly appreciated, thank you again :slight_smile:
Manuel

That's a good question. And I don't know the answer. Trying to find some time to do some investigation.

In the meantime, I would try running your app with embedded Node-RED using the node.js --inspect option or via vscode or some other way to be able to dig into the innards.

Put a debugger break statement into your custom node so that the debugger pauses there and you should be able to see exactly what you have access to.

Hi Julian, thanks for response :slight_smile:
I passed last 3 days literally inside nodered code and maybe I found a way to achieve that bypassing some input checks. I'm working right now to clean up the code and refactor it in a less messy way.
If the solution will satisfy me I will post some snippets to you

There is no way to inject nodes into the runtime - it has to discover them for itself on startup by scanning the node_modules directories in the node-red user directory (~/.node-red by default)

Create user-defined NR nodes and store them in the node_modules subfolder of the folder defined by userDir in settings.js ... (of course respect package.json requirements). Create your NR nodes so they communicate with ports you've opened in your app using the protocol you choose ...

Hi François, yep this was what my app did in past versions. It used to communicate with a standalone nodered with unix socket. It's a nice solution but with some drawbacks. Atm I'm able to import and interact with pieces of my app direcly inside my custom node as follow:

[...]
import { AppState } from '../../appstate.module'
[...]

export class CommMqttInputTEST extends BaseCustomNode {

    constructor(config: NodeRed.NodeProperties) {
        const RED: any = NodeRed
        super(config, RED)

        AppState.app.mqttBroker.inboundMessages.subscribe((m: Message) => { this.send(m) })
    }

    protected onInput(data: any): void {
        this.logger.debug(data)
        this.status({ fill: "green", shape: "dot", text: "Status test" })
    }
}

and my abstract base class:

[...]
export interface BaseCustomNode {
    on(event: string, handler: (msg: any) => void): void
    status(statusObject: StatusObject): void
    send(messages: any[]): void
}

export abstract class BaseCustomNode {
    constructor(config: any, RED: any) {
        RED.nodes.createNode(this, config);
        this.on('input', (msg: any) => { this.onInput(msg) })
        // this.on('close', () => { this.onClose() })
    }

    protected abstract onInput(msg: any): void
    // protected abstract onClose(): void
   [...]
}

The interface bring type support to mixin applied from RED.nodes.createNode: on, status and send are NR's methods.
It's all messy yet. I'm refactoring it in a more elegant way

This topic was automatically closed 60 days after the last reply. New replies are no longer allowed.