diff --git a/CHANGELOG.md b/CHANGELOG.md index 6bb34189..7e917257 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,33 +4,82 @@ typora-root-url: docs/images # Changelog -Please see the documentation for archived changelogs - a new archive is produced for each major version. +Please see the documentation for archived changelogs - a new archive is produced for each major version. Check the [roadmap](./docs/roadmap.md) for future developments. -## To do/In-progress +------------ -Check the [roadmap](./docs/roadmap.md) for future developments. +## [Unreleased](https://github.com/TotallyInformation/node-red-contrib-uibuilder/compare/v6.7.0...main) -* Outdated examples - some of the included example flows such as the "remote-commands" example are now out of date. What is there will still work but they are no longer comprehensive. Will try to catch them up as soon as I can. -* Add URL case sensitivity flag - currently ExpressJS and Socket.IO handle URL case sensitivity differently. In rare cases, this can cause an error. Will make both case sensitive in line with W3C recommendations (will be optional until next major release). +Nothing currently. - Add case sensitivity flag to uibuilder node and allow setting of ExpressJS flags on routers. [ref 1](https://stackoverflow.com/questions/21216523/nodejs-express-case-sensitive-urls), [Ref 2](http://expressjs.com/en/api.html). Also document in uibuilder settings. [Ref 3](https://discourse.nodered.org/t/uibuilder-and-url-case-sensitivity/81019/6). +## [v6.7.0](https://github.com/TotallyInformation/node-red-contrib-uibuilder/compare/v6.6.0...v6.7.0) -### TO FIX +### Highlights -* Loading template - if it fails due to a missing dependency, the template isn't loaded but the Template shows the new one. Need to revert the name if loading fails. -* uibRoot package.json - add check if dependencies blank but `node_modules` is not empty, if so, repopulate? Need to decide when to check - on commit at least. -* uib-tag - Attribs Source - should be "None" as default -* Editor (all nodes) - Use jQueryUI tooltips instead of uib custom (see `uib-element`) -* Templates - add eslint dev dependencies to package.json - * .eslintrc.js: Configuration for rule "sonarjs/no-duplicate-string" is invalid: Value 6 should be object. +* The new front-end routing library is available. Easy to use, robust and reasonably comprehensive. It is not dependent on uibuilder but offered with it to enable Single-Page Apps (SPA's) to be easily created with uibuilder. +* The `uib-html` node now allows an HTML string wrapper. This defaults to uibuilder's default "Blank" template HTML or can be overridden using `msg.template`. This lets you create a fully working page from no-code and low-code configurations that can be fed direct to `uib-save` or used in Dashboard or with http-in/-out nodes. Or indeed with external web server tools. +### New client library - uibrouter - front-end routing library +A complete, standalone library for doing front-end routing with both internal and external templates. Lightweight and simple to use. See the [documentation](docs/client-docs/fe-router.md) for details. + +### `uib-html` improvements + +* The `uib-html` node now accepts a `msg.template` property which, if provided, MUST contain a valid HTML page template. + + This allows you to grab an existing page using the `htmlSend` command, add new elements/updates and save it back to a uibuilder instance either as the default page or another page, for example, using the `uib-save` node. Overwriting a page is a way of ensuring that new accesses get a known page with structure and potentially data. + + You can, of course, use this node to produce HTML for use outside of UIBUILDER. For example, use uib-element/uib-update, add a template and use this node to create a complete web page for use with http-in/-out, a static website or some other web service. + + You probably don't need/want the template if outputting for the Node-RED Dashboard `ui_template` node. + +### `uib-save` improvements + +* The reload client flag now actually works. +* The new "Use pageName" flag allows you to save to the uibuilder node's live folder using the page name returned from the front-end or manually set in `msg._ui.pageName` or `msg.uib.pageName`. This makes it easier to save an updated page via the `htmlSend` command (either from Node-RED or from front-end code). See the example flow to see how this works. It means that you don't need to know the folder or the pageName at all. +* The filename can include folders (use `/` as separator) and missing folders will be created automatically if the "Create Folder" flag is set. Note that you cannot have any `..` in the filename, this is to prevent escaping from the instance root folder and causing mayhem elsewhere. By default, new folders cannot be created (this is a safety feature), select the "Create Folder?" flag to allow creation. +* The Editor js has been moved out of the html file and put into `resources/uib-save.js`. It is loaded by the html file in a link. This makes development a lot easier. The code also references `resources/ti-common.js` to ensure consistency. + +### `uib-tag` improvements + +* **FIXED** - Tag name input would only accept string. Now correctly processes other types. + +### Client library improvements + +* **FIXED** Client `htmlSend`, when called as a Node-RED command, was returning 2 messages. Now returns the HTML string and sends it to Node-RED directly only if the new 2nd argument is TRUE (the default so that direct calls will still work without changes). +* **FIXED** `eventSend` when attached to a change event returns the `value` property that all `input` tags have - except when they don't! When input is used as a checkbox, it has a `checked` property instead. Function changed to return the checked value if it exists (`true` or `false`), the value property otherwise. +* **NEW function and command** `watchUrlHash` - Toggle (or manually set on/off) sending URL Hash changes back to Node-RED in a standard msg. +* **NEW watched variable** `urlHash` Set on load and updated as it changes. URL Hashes are used by front-end routing for Single-Page-Apps (SPA's). They do not reload the page. +* **New utility function** `truthy` Takes a truthy/falsy input (e.g. text, number, boolean) and returns true or false (boolean). If input is neither truthy or falsy, can take a 2nd parameter which is the default return. +* Function added to watch for url hash changes. + +### `uibuilder` node improvements + +* `uibuilder` - Reduce code complexity by moving more fs actions out into `libs/fs.js`. +* Some common Node-RED Editor code and styles moved to common libraries (`resources/ti-common.js` & `resources/ti-common.css`) loaded as resources. Making the editor code smaller and more consistent. + +#### Editor panel improvements + +* Major rework of tracking node instances. Custom events are now fired: 'uibuilder:node-added', 'uibuilder:node-changed', 'uibuilder:node-deleted'. With the node in question passed as data in the event. For added nodes, an extra property `addType` is added to the node object and set to either "load" (fired when the Editor is loaded which adds all nodes), "new" (when a brand new instance is added, eg from the palette), or "paste/import". The tracking code is also now only ever instanciated once when the Editor is loaded. +* Better and more consistent removal of URL setting when pasting or importing existing uibuilder nodes. +* The Editor js has been moved out of the html file and put into `resources/uibuilder.js`. It is loaded by the html file in a link. This makes development a lot easier. The code also references `resources/ti-common.js` to ensure consistency. +* Improved debug information. Debug output to Editor page console is automatic if environment variable NODE_ENV is set to 'dev' or 'development' (it used to be if running on localhost). Otherwise can be turned on by manually issueing `uibuilder.debug = true` on the browser console on the Editor page. + +### Examples + +* `uib-save` and `uib-html` example flows added. +* `uib-var-web-component` example flow added. Contains several examples of showing uibuilder managed variables dynamically in your HTML code. Including several no-code examples. +* `uib-tag` example flow added. + +### Other improvements + +* **NEW node Library** `libs/lowcode.js` - The beginnings of moving the zero- to low-code element translations (e.g. uib-element, uib-update and uib-tag) to their own library. With the possibility of eventually making that library available as a stand-alone front-end library as well. Not yet in use. +* `libs/fs.js` - More replacements towards removing dependency on fs-extra. More move of filing system actions out of other nodes and libraries. +* **NEW utility function** `getSource(propName, node, msg, RED, src, srcType)` in `libs/uiblib.js` - this is an ASYNC function that returns a promise. It is a standardised way of getting the current value from a Node-RED Typed Input field. +* Enhanced tooltips not applied to the Monaco/Ace edit panel. ------------- -## [Unreleased](https://github.com/TotallyInformation/node-red-contrib-uibuilder/compare/v6.6.0...main) -Nothing currently. ## [v6.6.0](https://github.com/TotallyInformation/node-red-contrib-uibuilder/compare/v6.5.0...v6.6.0) diff --git a/README.md b/README.md index 9b0bfbba..c655fb88 100644 --- a/README.md +++ b/README.md @@ -131,31 +131,33 @@ The purpose of UIBUILDER is to: The core features of UIBUILDER: -* Provides nodes to enable zero-code translation of input data to usable and accessible web elements. -* Provides capability for low-code, configuration-driven (data-driven) UI's. Creating a framework for describing a UI and translating to actual code without having to write code. -* Provides a 2-way communications channel between the Node-RED server (back-end) and front-end UI. -* Provides a Node-RED node to act as the focus for communications with other nodes for additional ease of use. -* Provides a front-end library to: do the complex parts of the communications in the client browser; make manipulation of the UI easier and more consistent; make it easy to get data back to Node-RED as needed (both automatically and manually). -* Provides easy to use templates and examples for front-end code to enable people to get a quick start on creating web apps. -* Provides management and serving of npm packages that provide front-end libraries consumable easily by front-end code. -* Allows editing of front-end code from the Node-RED Editor (designed for small changes, use web development tools generally). -* Enables the use of external authentication and authorisation methods and services to control multi-user access to web apps. -* Provides various server middleware and API options for additional custom capabilities. -* Allows as many `uibuilder` node instances as you like. Each instance allows the creation of many web pages and sub-folders for easy management. +* As far as possible, uses only vanilla, native HTML, CSS and JavaScript. Other than the Socket.IO client for communications (which is baked into the front-end library), no other front-end libraries are needed. UIBUILDER stays as close as possible to native HTML to avoid future compatibility issues. However, it does aim to make interaction with native HTML easier. +* Nodes to enable zero-code translation of input data to usable and accessible web elements. +* Capability for low-code, configuration-driven (data-driven) UI's. Creating a framework for describing a UI and translating to actual code without having to write code. +* 2-way communications channel between the Node-RED server (back-end) and front-end UI. +* A Node-RED node to act as the focus for communications with other nodes for additional ease of use. +* Front-end library to: do the complex parts of the communications in the client browser; make manipulation of the UI easier and more consistent; make it easy to get data back to Node-RED as needed (both automatically and manually). +* Easy to use templates and examples for front-end code to enable people to get a quick start on creating web apps. +* Management and serving of npm packages that provide front-end libraries consumable easily by front-end code. +* Editing of front-end code from the Node-RED Editor (designed for small changes, use web development tools generally). +* Various server middleware and API options for additional custom capabilities. +* A caching capability allowing newly joining clients to receive the latest data and configurations. Joining/leaving clients create notifications in Node-RED. +* A front-end lightweight router for creating Single-Page Apps. +* Have as many `uibuilder` node instances as you like. Each instance allows the creation of many web pages and sub-folders for easy management. * Each `uibuilder` node instance provides a private 2-way communications channel between the Node-RED server (back-end) and browser (front-end) UI code. * Supports the use of standard web development workflows. * Allows the creation of a dedicated web service to facilitate independent security. -* Provides a caching capability allowing newly joining clients to receive the latest data and configurations. Joining/leaving clients create notifications in Node-RED. -
No-code UI's -UIBUILDER is still growing towards offering more no-code capabilities like Node-RED's Dashboard extension does. However, it is starting to offer these features via the "new" client available since v5. V6.1 introduced the new `uib-element` and `uib-update` nodes that offer the first usable no-code features. +UIBUILDER continues to expand its no-code capabilities. THe `uib-element`, `uib-tag`, and `uib-update` nodes offer no-code methods for creating and updating data-driven web UI's. `uib-element` takes in simple data and outputs configuration data. This can then be sent to the front-end via the `uibuilder` node. Alternatively, it can be saved and the result used in an initial load. Several simple options such as tables and lists are available in UIBUILDER v6.1, additional elements and structures will be made available in future versions. The UIBUILDER front-end client takes the configuration information and dynamically builds HTML elements and inserts them to the web page (or removes/updates as needed). While this is not the most efficient processing approach (since updates are mostly replacing the whole element which could be quite large for things like big tables), it is very efficient from an authoring perspective. So the `uib-update` node provides a more targetted approach to updating and changing specific attributes and "slot" content for elements. +The `uib-tag` node then lets you create ANY single HTML element and so covers all the many things that `uib-element` might not (yet) cover. This even works with web components which are vanilla HTML/JavaScript native enhancements to HTML. + It is important to note that no front-end, 3rd-party frameworks such as VueJS or REACT are needed for this approach! Everything uses vanilla HTML, JavaScript and CSS under the skin and so is **compatible with current and future web standards**.
@@ -164,20 +166,27 @@ It is important to note that no front-end, 3rd-party frameworks such as VueJS or The data that `uib-element` outputs is a format that you can use in your own flows in Node-RED and even in front-end code if desired. It describes a set of HTML UI elements but does not need you to actually write HTML code. The configuration schema is very flexible and even allows you to load configuration data, HTML, scripts, and new ECMA Modules/Components from external files. The schema and the UI creator functions built into the front-end client are specifically designed to work with current and future HTML standards in order to avoid the kinds of issues commonly encountered when using 3rd-party front-end frameworks (e.g. major version changes forcing rewrites of all of your tooling). So ES Modules, ECMA Components, and future ECMA versions should all be supported. + +The `ui.js` library is now also available for anyone to use in their own projects and works fully stand-alone without UIBUILDER. It is also baked into the `uib-html` node which turns low-code configurations into HTML from within Node-RED.
Future direction -The general direction of UIBUILDER (or associated modules) is likely to include: +UIBUILDER will continue to be independent of front-end frameworks though it will also continue to be as compatible as possible so that any desired framework can be used with it. + +* It will continue to gain more zero-code pre-built elements. +* It will gain improved control over the instance root folder structure and the ability to execute `npm run` scripts defined in the `package.json`. +* More videos! + +### Longer term focus + +There remains a desire to build a page-builder feature so that people with no coding skills can build great data-driven web apps. + +* The documentation quality will continue to improve. +* The number of 3rd-party module dependencies will be reduced. Starting with the eventual removal of `fs-extra` in favour of the native promisified fs library. Followed most likely by `arun`. +* Once Node.js v18 or 20 is the base, the code is likely to be refactored into multiple sub-packages in a mono-repo. -* Provide more no-code and low-code UI creation and update capabilities. As of v6.1, these are now starting to be delivered, v6.2 will extend these. -* The ability to save updated HTML from the front-end via Node-RED so that UI building can be done once and loaded as efficient, static HTML. -* The ability to use the zero-code features to produce HTML for other tools to use. -* The ability within Node-RED to, for each `uibuilder` node, run npm scripts such as build processes and to manage instance-level npm packages. -* Be able to install/update/remove instance-level npm packages as can already be done for UIBUILDER-level packages. -* Provide a "development server" capability that auto-reloads connected clients when code changes are made. -* A UI designer allowing users without HTML/CSS/JS skills to create reasonable web apps without code.
Feature details and benefits @@ -201,18 +210,7 @@ The general direction of UIBUILDER (or associated modules) is likely to include: * Uses Node-RED's own ExpressJS webservers by default. Switch to a custom ExpressJS server if desired. When using a custom server, pages can also include EJB server-side templating. * Has middleware for ExpressJS (for web services) and Socket.IO (for communications, both at initial connection and per-message) so that you can add your own custom features including security. * Can create custom API's for each UIBUILDER instance. -
- -
Current limitations - -* You may need to write some of your own HTML. -* You have to know the front-end library locations for installed 3rd-party packages and edit your HTML accordingly. The `uibindex` admin API (accessible from any node's admin ui) shows you all of the root folders and what the package authors report as the main entry point for all active packages. There is now also a simplified information page for the currently viewed `uibuilder` node instance, this is access from a button in the configuration panel. - - Note that this is a limitation of `npm` and module authors, not of UIBUILDER. Unless module authors correctly identify the browser entrypoint for their libraries, UIBUILDER can only guess. - -* You cannot yet compile/compress your custom front-end code (HMTL, JS, SCSS, etc.) for efficiency. *This will be added soon.* - - This will use a local package.json file that contains a "build" script. If it exists, UIBUILDER will expose a build button that will run the script. +* Use the `ui.js` library in your own projects!
## Contributing @@ -250,6 +248,7 @@ You can also support the development of UIBUILDER by sponsoring the development. - [dczysz](https://github.com/dczysz) - Thanks for reporting [Issue #186](https://github.com/TotallyInformation/node-red-contrib-uibuilder/issues/186) and helping work through the complex async bug. - [Colin J (mudwalkercj)](https://github.com/mudwalkercj) - Thanks for helping with the documentation. - [Marcus Davies](https://discourse.nodered.org/u/marcus-j-davies) - Many thanks for the encouragement and for the 3d logo. +- [Fabio Marzocca (fmarzocca)](https://discourse.nodered.org/u/fmarzocca)) - Many thanks for help with the design and testing of the uibrouter front-end router library. Many other people have contributed ideas and suggestions, thanks to everyone who does, they are most welcome. diff --git a/docs/-sidebar.md b/docs/-sidebar.md index ca5a156c..39acc38b 100644 --- a/docs/-sidebar.md +++ b/docs/-sidebar.md @@ -10,12 +10,14 @@ * [Zero-code UI creation](using/zero-code-ui.md "Dynamically creating web UI's") * [Why uibuilder?](using/why-uibuilder.md "Why would I want to use UIBUILDER?") * [The nodes](nodes/README.md) - * [`uibuilder`](nodes/uibuilder.md) - * [`uib-cache`](nodes/uib-cache.md) - * [`uib-element`](nodes/uib-element.md) - * [`uib-tag`](nodes/uib-tag.md) - * [`uib-update`](nodes/uib-update.md) - * [`uib-sender`](nodes/uib-sender.md) + * [`uib-cache`](nodes/uib-cache.md "Cache data so that (re)loaded pages get the latest") + * [`uib-element`](nodes/uib-element.md "no-code creation of page elements") + * [`uib-html`](nodes/uib-html.md "Hydrate low-code JSON UI descriptions into HTML in Node-RED rather than the browser") + * [`uib-save`](nodes/uib-save.md "Save files to the served folder of a given uibuilder node") + * [`uib-sender`](nodes/uib-sender.md "Tunnel messages direct to a uibuilder node - with optional return. Use lightly if at all") + * [`uib-tag`](nodes/uib-tag.md "no-code creation of ANY HTML tag") + * [`uib-update`](nodes/uib-update.md "no-code update of any existing HTML page element") + * [`uibuilder`](nodes/uibuilder.md "The main node") * The front-end client * [Introduction](client-docs/readme.md) * [Features](client-docs/features.md) @@ -24,6 +26,7 @@ * [Functions](client-docs/functions.md) * [Variables](client-docs/variables.md) * [Custom Components](client-docs/custom-components.md "The built-in uib-var component, using external components") + * [Routing Library](client-docs/fe-router.md "A full-featured front-end router for Single Page Apps and other use") * [Custom Events](client-docs/custom-events.md) * [uib-brand Style Sheet](client-docs/uib-brand-css.md "How to use the UIBUILDER standard style sheet uib-brand.css") * [Troubleshooting](client-docs/troubleshooting.md) @@ -50,6 +53,7 @@ * [Change the root folder (uibRoot)](how-to/changing-uibroot.md) * [Create instance-specific API's](how-to/instance-apis.md) * [How & why to use the sender node](how-to/sender-node.md) + * [How to use low-code in the browser](how-to/use-low-code-in-fe.md "Define and update elements in the browser using low-code") * [Other How-To's](how-to/README.md) * Security * [Securing uib web apps](security/security.md "Overview of general web app security with some specifics for Node-RED and UIBUILDER") diff --git a/docs/client-docs/control-from-node-red.md b/docs/client-docs/control-from-node-red.md index dd357280..d6612f51 100644 --- a/docs/client-docs/control-from-node-red.md +++ b/docs/client-docs/control-from-node-red.md @@ -31,6 +31,7 @@ Possible `msg._uib.command` values. * `showStatus` - Turn on/off the display of the uibuilder client library settings. * `uiGet` - get detailed information about an HTML DOM element. * `uiWatch` - watch for changes to the HTML DOM, return messages about changes. +* `watchUrlHash` - watch for URL Hash changes. Used for front-end routing. > [!NOTE] @@ -51,7 +52,26 @@ A message containing a `msg._ui` property will be processed internally by the li Please see the [Dynamic, data-driven HTML content](config-driven-ui.md) content for details. -## Navigation control +## Navigation & routing + +### `watchUrlHash` Watch for URL Hash changes + +Typically from front-end routers and Single-Page App (SPA) style pages. URL Hash changes do not cause the browser to reload the page. + +Set `msg._ui` to: + +```jsonc +// Toggle watcher on/off +{"command": "watchUrlHash"} +``` + +```jsonc +// Force watch ON +{"command": "watchUrlHash", "prop": "true"} +``` + + +### Navigation control Currently, only a page reload control is available. Set `msg._ui` to `{"method": "reload"}`. diff --git a/docs/client-docs/fe-router.md b/docs/client-docs/fe-router.md new file mode 100644 index 00000000..cc9143c6 --- /dev/null +++ b/docs/client-docs/fe-router.md @@ -0,0 +1,277 @@ +--- +title: UIBUILDER Front-End Router Library +description: > + Details on the configuration and use of UIBUILDER's front-end router. +created: 2022-02-01 11:15:27 +lastUpdated: 2023-11-19 17:21:15 +--- + +The `uibrouter` front-end library defines a `UibRouter` class. This allows both internal and external content to be dynamically shown, allowing the creation of "Single-Page Apps" (SPA's) or simply keeping parts of the UI hidden from the users until they need them. + +Internal route content is defined in `