Node-RED dashboard performance across tablets & mobiles


I have a question about performance of Node-RED on different devices.
I am running Node-RED on a perfectly adequate desktop PC, but plan to migrate to a 4GB Pi4 shortly.

The question is related to this previous post:

On my 2016 iPad pro the dashboards I have created load up reasonably quickly – a few seconds max. Admittedly, these are fairly big dashboards. They go off screen requiring the user to scroll down to get to the bottom.

On my much older Sony Z2 they take 15+ seconds (sometimes I give up trying to load them after 30_ seconds) and the dashboards never really work e.g. buttons don’t work when pressed, scrolling up/down locks up the screen requiring a reload etc. If I open up a very small dashboard, it loads reasonably quickly and is responsive.

When I load the dashboards from my Google Pixel 3A the performance is not too dissimilar to the Sony. This surprises me as the 3A isn’t that old. I know it’s a relatively low spec phone, but it works fine in 99% of the applications I use it, including loading lots of web pages. Even just opening the side menu and trying to click on a dashboard take lock up the phone all together. Again, if I can get to a small dashboard, which is a big if, it seems to work ok.

Now, I am going to show my ignorance as to how Node-RED works. I thought that the tablets were only getting a very light webpage to load, so I expected the pages to load lightning to very fast on any device that can load web pages reasonably well.

Other info

I have accessed the dashboards via Chrome on the Sony and both Chrome and Mozilla on the Pixel 3A. Chrome works faster on the Pixel 3A vs Mozilla, but Chrome also has a weird rendering issue where sometimes half the screen is covered with a white box. I have to wait for a long time and it eventually disappears which renders performance to be not to dissimilar to the Sony on Chrome when the white box issue happens.

I do not want to view the dashboards via my Pixel as they are generally way too large; however I was just using it for testing purposes to understand what might be happening.

My Questions:

Can someone please explain to me how performance really works and/or why I might be experiencing what I am across the 3x devices I have described?

Would running Node-Red on a Pi4 with 4GB RAM help with performance on my devices?

Is there something, other than redesigning my dashboards (or buying better hardware/tablets) which I can do to improve performance?

First question, what version of node-red-dashboard are you running? Look in the Manage Palette menu to see, and to see if there is a later version. Also what version of node-red are you running?

Secondly, are you using charts on the dashboard? If so what rate are you adding data at, how many lines (in total across all charts) and what time range are they displaying? Work out how many samples you are adding across the time range, if that is much more that the width of the chart in pixels then slow the rate down. The browser has to be passed all those points on initial loading, it has to store them, and move them down the chart every time a new sample appears. That can add up to a lot of work.

Switching to a Pi 4 is not likely to make any measurable difference to the load time.

1 Like

Hi Colin,

Thank you for the prompt reply.

I am running v1.1.0 of Node-Red and v2.23.0 of node-red-dashboard.
I believe these are the latest versions.

I have only 1 chart across all my dashbaords, but the dashboards are densely packed with nodes....

For example one has:

  • 30 buttons
  • 60 ui_level nodes
  • 120 text nodes

And the details of that chart? The statistics mentioned on the previous post.
How often are you updating the level and text nodes? Though I don't know whether that would affect the initial load.

Apologies, I wrote my reply and then edited it.

Let me go back to my original reply... I have no charts.

The closest thing i have to a chart is a single gauge.
The only other unusual nodes I have is 2x templates that have been designed to look like nest thermostats.

That said, these are all on one dashboard. The performance issues happen on other large dashboards that do not have the gauges and nest-like templates.

How do I IM you?

There is only one dashboard, with multiple groups/tabs. So what do mean when you say that one of the dashboards has all those nodes? That makes me wonder whether I understand exactly what it is that is slow, is it the initial load (which I had been assuming you meant) or do you mean switching tabs, or what?

You didn't answer the question about how often the ui_level and gauge nodes are being updated.

[Edit] I meant to add that node-red is on 1.1.2 now, there were some issues with 1.1.0, but I don't think that will make any difference to this issue.

the reality is that the node-red-dashboard is built on top of Angular 1 - with Material design libraries, a whole bunch of fonts, and a load of built in widgets... so the default download for even a simple page is quite large - and a) can take a while to transfer and b) take a while to render on any slightly old/slow/constrained device.

If you need something more lightweight then you probably need to consider building something more custom maybe using the node-red-contrib-uibuilder which lets you use whatever library you are comfortable with or node-red-contrib-component-dashboard, which is sort of halfway between.


Ok, so here goes...

There are 3x developed dashboards plus a couple of in-development dashboards.

The 3x developed dashboards are fairly large by my, a few weeks into living with node-red, standards.

I'm trying to listen to your questions to understand the angle you are coming from. It sounds like the number of times you refresh a node can heavily impact performance, especially graphical nodes. I say this like I don’t understand it. I had serious issues with performance when I inadvertently started doing mass API dumps from my HA controller, so learnt quickly to design my dashboards to be event driven.

I did some testing that I probably should have done before I posted the original question. I deleted 2 of the 3 dashboards, leaving an efficient (yet large) dashboard that does inject a refresh of data every 1 second, but only using local calculations and local global variables. The live data coming from my HA controller only comes through based on events, so this dashboard is pretty much as efficient as I know how to write it based on what I want it to do. Also, and there is the clincher, in deleting the other 2x dashboards I deleted the node that communicates with the HA controller, so in reality there is little processing going on with the remaining “large” dashboard.

The result: On the Sony Z2 it is still lagging... so I am guessing this is an out and out hardware issue.

"Big" dashboards with lots of nodes = heavy on performance.

Now, to answer your question, the gauge updates every 15 minutes. It just reports the temp and the 2x “nest-like” templates update when you click and then to make a change, so none of these node are update very often.

I have testing all these dashboards on my PC, iPad Pro, Sony Z2 and Pixel 3A and from what I’m hearing, it’s just down to raw power, however you want to define the concept of raw power.

  • The PC works relatively quickly
  • The iPad Pro, despite being 4 years old, not to bad, but could be better
  • The Sony Z2 – not at all
  • Google Pixel 3A (a surprise to me) – not at all

Thanks for sharing... so, these concepts are completely new to me. I will look at the uibuilder and node-red-contrib-component-dashboard, but I am loathe to rebuild my dashboards yet again....

It would be nice to have an idea of how much better they would perform if rebuilt, but I guess that's like answering how long a piece of string is....

One thing you can do to get a feel for things is to load your Dashboard on a PC/Mac browser and look at the stats in the developer tools of the browser. You will see that the Libraries that Dashboard loads are fairly monstrous in size. Also, Angular v1 was never all that mobile friendly I don't believe.

Also remember that Dashboard is a Single Page App (SPA). So all tabs are loaded into browser memory when you open any of them. If you had 20 tabs each with a large chart, that is a heck of a lot of memory.

Mobile browsers, at least on older devices are typically both memory and CPU constrained. They also often don't support the latest standards and this was a real problem at least when UI (the predecessor to Dashboard) came out.

With something like uibuilder, you only need to load exactly what you want so if you only wanted to use jQuery, you could do so. By default, it loads VueJS and bootstrap-vue and I think that even then, those combined are still quite a lot lighter in weight and more performant than Angular v1. But you could do without a library at all if you didn't want to use one.

uibuilder also lets you have multiple pages if you like so it is possible to split things up so that your browser doesn't have to hold everything in memory at once (though I think most people will still find it easier and more convenient to keep everything in a single page).

So if you want to optimise your pages, uibuilder is the tool for the job. The downside is that you have to build the page yourself without the help that Dashboard provides. With VueJS and bootstrap-vue, this is actually pretty easy but it does generally require a bit more code.

1 Like

Ok, so I've never look at the developer stats of a web page before. When I hit ctrl+shift+c and do a recording, it comes back with so much info I'm not sure what I'm looking for.

During the recording I clicked on a few buttons and then did a refresh of the dashboard to re-load it completely.

"So if you want to optimise your pages, uibuilder is the tool for the job. The downside is that you have to build the page yourself without the help that Dashboard provides.

I am going to look at uibuilder at some point soon. Can you explain what you mean by build the pages yourself? What do I lose exactly vs the dashboard?
Are you talking about the positioning of each node on the web page or is it more than that?
If there is a worked example you could point me in the direction of that would be great.

1 Like

The "heap" shows you that it quickly climbs from 8MB to over 40MB - that is a measure of the amount of memory being used.

Also note the "scripting" part showing 22 seconds. This is the amount of time that has been taken by running scripts. Though that probably includes the results of your interactions rather than an indication of the initial load.

If you look on the network tab, you will get a better feel for how long it takes to do the main page load. I have a Dashboard with 2 tabs, one of which is reasonably complex (a weather display). It takes just short of 3 secs to do the main part of the load.

If I look at the memory tab (by the way, I'm using the new Chromium-based Edge browser), I can see that the Dashboard is using 16MB:

By contrast. My much more complex uibuilder dashboard takes around 2 secs to load the page framework and then spreads out the data load (it isn't optimised and requests a large dump of data after it loads. Memory is around 12MB.

1 Like

Interesting topic and it helps me understand what is impacting the performance of the dashboard.

UIbuilder has been mentioned a couple of times and coming from the electronics side of the house the learning curve seems to be pretty steep.

Just wondering and maybe asking a stupid question (yes they exist and feel free to acknowledge :grin:): is there an option to leverage all the work I have put into the various NodeRED dashboards by importing/converting them into a UIbuilder type dashboard?

Further to @fvhemert's question, is it possible to build a dashboard part in uibuilder and part using the dashboard node?

This way I can convert my dashboards across in stages.....

Ok, Google is our friend. The answer to my question is NO.

With uibuilder you are building from the ground up.

Weeeel, yes, if you have no web knowledge at all, it may be. I've tried to make it as simple as possible and you could simplify further by using jQuery instead of Vue. Wouldn't be as pretty out of the box though. jQuery is more procedural and therefore more likely to be easily comprehended. Vue is worth learning though if you want to be able to write general purpose web-based UI's simply.

No such thing as a stupid question :wink:

Sadly not, sorry. They are fundamentally too different.

However, many of the concepts translate fairly readily. Such as the card-style interface. But the layouts will naturally be somewhat different. Things like inputs and outputs translate very easily though since Vue and bootstrap-vue provide a lot of easy to use components.

Well, kind-of. You could embed one inside the other. Probably easiest to embed the uibuilder app into the Dashboard - you would need to use the ui_template node and include the uibuilder page as an iframe. Not tried it though so can't comment on how good it would be.

However, they are both web-pages so you can easily link between the 2 and I do that regularly. You can open them on separate browser tabs or windows and some browsers (Vivaldi? can't remember) will let you have >1 tab in a single view. Side-by-side for example.

Weeeel, again partly. But not entirely. Because you can use Vue/bootstrap, you can have a really nice dashboard with minimal code. I've build a few where the number of lines of HTML is no more than a couple of dozen (much of which is loading the libraries, CSS, etc) with a similar number of lines of JavaScript. Check out the "simple" example for instance to see what you can do with very little code.

So, yes, you need to understand the basics of how a web page is constructed. So that you know how to nest things to get the effect you want. But with Vue/bootstrap, you don't need to do anything with CSS to get something that looks pretty good. And the JS is mainly to get the data from NR into the structure of your page (generally just a few lines of code) and to get data back to NR if you need to do that (even less lines typically).

Incidentally, while Dashboard is great for getting things going really quickly with no hand-written code. Many people hit a wall with in and when you do, you will find your code very quickly being at least as complex as writing uibuilder/vue/bootstrap code. This is one of the main drivers for me writing uibuilder in the first place. That and the overheads of Angular v1 meant that for a long time it wasn't feasible to access the Dashboard (except for the very simplest of cases) on a mobile device.

1 Like

There is also that is a possible halfway house, and uses web components technology to build pages. But again there is no simple transition.

Thanks for your support so far!

Let me start by saying that I am blown away by Node-RED. I absolutely love it and it has filled a gap that I have had for years with my home automation system.

I want to look into uibuilder as I am just starting to see some lags in performance, however only on loading pages. Once loaded, the pages seem to work fine. I say this in the context that they load fine on newer fairly beefy hardware, which is not a huge compromise at the end of the day i.e. only run beefier hardware in my solution vs delve into uibuilder from scratch.

I know NOTHING about constructing a web page, so for me when I started to look into uibuilder yesterday, it was daunting, however a few weeks ago I didn't know anything about Node-RED, since then I've built some dashboards.

That process felt like a very steep hill to climb, however Google is my friend and more importantly I had help from a real-life friend (who built the node that integrates my Home Automation system) in pushing me in the right direction.

So far I've mainly built a whole house Heating Panel which is working, but could do with a bit of finessing and I am also working on a whole house lighting panel which is still very much in development.

My solutions are frankenstein-ian. I am leveraging my home automation systems pre-existing code to build interactive dashboards. In the future I am looking to build as much as possible in Node-RED, but for now leveraging what I have already built in my HA system was the quickest way to get results.

If I built the heating panel again, I am sure it would be designed better and after sleeping on it for some time, I think I can move it to 100% event driven, like the lighting panel which means it will not kill my home automation system by pulling vast volumes of data every second and hopefully lighten the load on Node-RED at the same time.

I am now at a huge fork in the road. Do I continue down the path of the dashboard node or do I start learning all over again, and more importantly, re-building my dashboards with uibuilder?

The easier option is to overspec all the hardware I am using and continue with the dashboard node and pray that when I'm done the performance is acceptable.

I want to take this a little further and am hoping, rather than spending countless hours searching Google, which I'm sure I will have to do at some point anyway, that someone can provide some guidance / share their knowledge on what's involved in migrating to uibuilder.

Following is the heating panel I have built. It is interactive i.e. you can press any button and click and hold on the 2x nest-like wheels (which I most definitely did not build myself) to change the setpoint temp and time.

To give you an idea of how daunting a complete rebuild is, following is what it looks like in the Node-RED:

So to break-down a migration, at a minimum I need to know how to build the following with uibuilder:

  • buttons + text and colour formatting
  • text boxes + text formatting
  • ui_level node
  • ui_template equivalent for the 2x nest like scroll wheels, or else I just go back to using buttons again e.g. +0.5C -0.5C, which I guess is where the compromises might start to creep in.

Then there's all the code in the back end... I think/trust that I can just leverage all my existing code for things like:

  • reading from my HA system
  • writing back to my HA system with user updates
  • all the code I have written in functions
  • all the other nodes that I have used e.g. switch, change, json converted, delays

EDIT: I have had a bit of time to think about it and I now understand a little bit more.... the answer to, can i use all my existing components appears to be a big fat YES. From what I can see, the uibuilder needs you to write all of your code for the exposed parts of your webpage i.e. the bits that people see and interact with in a single node, however I can see that the uibuilder node does still have an input and 2x outputs. I however still have a lot to wrap my head around with how to implement uibuilder for my dashboard has distinct components that interact with each other, it's relatively easy to see the interaction when using dashboard nodes, but not so easy to visualise how it would work with all the processing happening in one node... I guess it's time for a step change in my understanding of how to develop using uibuilder

Ok, so I get I'm asking a VERY big question with absolutely no idea how to implement it, yet.

Maybe the first question is more about getting some guidance... is it really worth migrating across?

Then the next question is, where can I get examples of the code for the buttons, text boxes etc + how to implement ui_level with uibuilder.... is it even possible or do you need to do it all yourself from scratch?

EDIT: The last question is one of design, how to design such a beast to work with one node only.

Where is this example?

EDIT: OK, I guess you mean the examples built into the index.js for if the uibuilder node.

1 Like

@dceejay, thanks for sharing this. I had seen it before, but don't really understand it anymore than uibuilder.

With anything I embark on, the challenge is figuring out the cost vs benefit, and now to the probably impossible questions to answer.... Given the screenshot I pasted above of my heating panel - designed only for tablet use BTW:

  • How much quicker would component-dashboard load than dashboard?
  • How much quicker would uibuilder load than dashboard?
  • How much quicker would uibuilder load than component-dashboard?

EDIT: Ok, so through some more research I have answered part of my question here... I am going to guess that component-dashboard is no faster than dashboard, however it's just a lot more flexible in its layout.
Now this is something that may just come in handy for me in the future... I have some ideas that the angular layout just doesn't support.

@dceejay, great piece of work there, well done!

We all started there :slight_smile: And certainly Dashboard is the quickest and easiest way to quickly knock up a UI and of course, I still use it as such.

This is always an issue when using any kind of framework, even Node-RED itself. All I can give is advice based on my own experience. That is to say that I generally eventually regret choosing a locked-down framework whether that is Dashboard, Angular (on which Dashboard is built, that turned out to be far too complex for anything I'll ever build). Or even something like EasyESP on an ESP8266 where I generally end up hand-cranking my own C++ so that I can do exactly what I want. Of course, this may well be just the way my brain works!

Node-RED itself has turned out to be rather an exception to that. It is mostly flexible enough for many tasks and has enough freedom to use it as a base framework and delve into node.js if needed. That isn't to say that it is right for every job. I do wish that it (and node,js in general) were better at analytical work since I regularly have to wrangle large interlocking spreadsheets/tabular data for work (mainly identity data, sometimes performance data). But in truth, node.js generally sucks at those tasks compared to Excel, PowerShell or Python. Not Node-RED's fault.

You would almost certainly find that a uibuilder version would be simpler since you feed data into and out-of a single uibuilder node. Of course, you slightly pay for that with more JavaScript code in the front-end. But as you build it up a piece at a time and because uibuilder and VueJS do all the heavy lifting, as long as you take it slowly and logically, it isn't as hard as you probably think.

Creating buttons is trivial and the default template contains a simple example button. Colour formatting is easy in Vue since it is fully data-driven. Changing colour is as simple as having a variable that contains 1 or more CSS class names or alternatively some CSS Style definitions.

So here are some examples of buttons using bootstrap-vue's button which gives you good control. The first is direct from the default template, the second drives the overal look from a variable and the 3rd gives you detailed control via CSS classes. The final example is a button that triggers a function called increment when it is pressed & is also a more rounded format. You can, of course, use ordinary HTML button tags instead but then you get less help from the framework.

<b-button type="submit" variant="primary">Login</b-button>
<b-button type="submit" :variant="btncolourvariable">Login</b-button>
<b-button type="submit" :class="btncolourclassvariable">Login</b-button>

<b-button pill variant="primary" v-on:click="increment">Increment</b-button>

So using the last of the above buttons, the following code returns a bunch of data from an on-page form back to Node-RED:

    methods: {
        increment: function() {
            // Increment the count by one
            this.counterBtn = this.counterBtn + 1
            var topic = this.msgRecvd.topic || 'uibuilder/vue'
            uibuilder.send( {
                'topic': topic,
                'payload': {
                    'type': 'counterBtn',
                    'btnCount': this.counterBtn,
                    'message': this.inputText,
                    'inputChkBox': this.inputChkBox
            } )
        }, // --- End of increment --- //

Any variable that starts with this. are ones that are defined in the data section of your JavaScript code and are understood by VueJS so that any use of them in your html is dynamic, if they change, the UI changes - no code required. In this example, you can also see that there are 2 ways that you could differentiate the data you are sending back to Node-RED. The msg.topic and the msg.payload.type could both be used in switch nodes attached to the output of the uibuilder node to trigger different flows. A similar approach is taken to incoming msg's from Node-RED to the front-end. The uibuilder.onchange('msg', ....) function is triggered whenever a new msg is received from Node-RED and you can use if or switch JavaScript statements to take specific actions dependent on the incoming data.

You can either leave them where they are and send any output into the uibuilder node or move them into your front-end code if it makes more sense to run the code in the users browser instead.

You may also want to start thinking about caching of data. Do you want data to be ready to deliver when a new user loads the uibuilder page? (or reloads the page) Dashboard does some basic caching, in uibuilder you can build a caching function node just before data is input to the uibuilder node. uibuilder has a control channel that includes outputs that let you control a cache in a standard way and there are some examples of how to do that (one day I'll get time to finish a proper node but there are so many edge-cases to caching, it isn't a trivial thing to create, using a function node gives you maximum flexibility).


Yes. A single input as described above. For the outputs, the top one is data output from uibuilder.send() in the front-end. The 2nd is for control msg's such as the cache control and for when a new browser tab loads or unloads the page.

Yes, here is a big difference. In Dashboard, most of the data goes to and comes from the Dashboard (front-end) into Node-RED and is processed there. This is perhaps easier to conceive visually but isn't terribly efficient since in some cases that data isn't really needed in Node-RED itself, only in the front-end. uibuilder gives you the chance to do the processing in the front-end if you want to. However, you can still pass it back to Node-RED if you like & process it there if it makes sense.

One of the other projects I want to do is to create a set of standard (VueJS) components with standard data interfaces. I've already done 1 example which mirrors the excellent SVG Dashboard node. Other examples would be components for charting for example to make that simpler. Sadly I have to still work for a living and have a family who demand time :slightly_frowning_face:

Ah, well, that is indeed the big question. No easy answer there. Though the fact that you are already asking the question tells me you aren't certain that Dashboard is going to be suitable for you in the longer term.

What I will say is that you don't need to take an either/or decision immediately. If Dashboard does what you want then fine, stick with it but maybe start to learn about HTML, CSS and VueJS so that if/when you do grow out of Dashboard, you are ready to start moving over.

Also, having a 2nd actual page (rather than the virtual pages in Dashboard) is easy enough to integrate to Dashboard so you don't have to migrate everything at once. A uibuilder page can appear to an end user as just another link from the Dashboard.

The node is just a gateway. Send data in and it goes to the front-end. Send data from the front-end and it comes out the back of the node. In Node-RED, you can use link nodes to help keeping your flows neat. Personally, I find the single node a lot easier to work with & I think your screenshot shows that Dashboard flows can get rather horrendous.

Just think about your data flows and things will become clear. And that is a key difference. When using uibuilder, it is easier to take a data-centric view which often leads to a more robust solution.

Yup! If you can't find one there, you will generally find something in the WIKI on GitHub.


Awesome response! It's much clearer now.

I think I'll keep what I have built using the dashboard node and have a go at using your uibuilder node for my next web page .... looking forward to it... as with you, family and work permitting :slight_smile: