mirror of
				https://github.com/node-red/node-red.git
				synced 2025-03-01 10:36:34 +00:00 
			
		
		
		
	Separate library api and runtime components
This commit is contained in:
		| @@ -86,10 +86,12 @@ module.exports = { | |||||||
|  |  | ||||||
|             // Library |             // Library | ||||||
|             var library = require("./library"); |             var library = require("./library"); | ||||||
|             library.init(editorApp,runtime); |             library.init(editorApp,runtimeAPI); | ||||||
|             editorApp.post(new RegExp("/library/flows\/(.*)"),needsPermission("library.write"),library.post,apiUtil.errorHandler); |  | ||||||
|             editorApp.get("/library/flows",needsPermission("library.read"),library.getAll,apiUtil.errorHandler); |             editorApp.get("/library/flows",needsPermission("library.read"),library.getAll,apiUtil.errorHandler); | ||||||
|             editorApp.get(new RegExp("/library/flows\/(.*)"),needsPermission("library.read"),library.get,apiUtil.errorHandler); |             editorApp.get(/library\/([^\/]+)(?:$|\/(.*))/,needsPermission("library.read"),library.getEntry); | ||||||
|  |             editorApp.post(/library\/([^\/]+)\/(.*)/,needsPermission("library.write"),library.saveEntry); | ||||||
|  |  | ||||||
|  |  | ||||||
|             // Credentials |             // Credentials | ||||||
|             var credentials = require("./credentials"); |             var credentials = require("./credentials"); | ||||||
|   | |||||||
| @@ -13,149 +13,71 @@ | |||||||
|  * See the License for the specific language governing permissions and |  * See the License for the specific language governing permissions and | ||||||
|  * limitations under the License. |  * limitations under the License. | ||||||
|  **/ |  **/ | ||||||
|  |  | ||||||
|  | var apiUtils = require("../util"); | ||||||
| var fs = require('fs'); | var fs = require('fs'); | ||||||
| var fspath = require('path'); | var fspath = require('path'); | ||||||
| var when = require('when'); | var when = require('when'); | ||||||
|  |  | ||||||
| var redApp = null; | var runtimeAPI; | ||||||
| var storage; |  | ||||||
| var log; |  | ||||||
| var redNodes; |  | ||||||
| var needsPermission = require("../auth").needsPermission; |  | ||||||
|  |  | ||||||
| function createLibrary(type) { | module.exports = { | ||||||
|     if (redApp) { |     init: function(app,_runtimeAPI) { | ||||||
|         redApp.get(new RegExp("/library/"+type+"($|\/(.*))"),needsPermission("library.read"),function(req,res) { |         runtimeAPI = _runtimeAPI; | ||||||
|             var path = req.params[1]||""; |     }, | ||||||
|             storage.getLibraryEntry(type,path).then(function(result) { |  | ||||||
|                 log.audit({event: "library.get",type:type},req); |     getAll: function(req,res) { | ||||||
|  |         var opts = { | ||||||
|  |             user: req.user, | ||||||
|  |             type: 'flows' | ||||||
|  |         } | ||||||
|  |         runtimeAPI.library.getEntries(opts).then(function(result) { | ||||||
|  |             res.json(result); | ||||||
|  |         }).catch(function(err) { | ||||||
|  |             apiUtils.rejectHandler(req,res,err); | ||||||
|  |         }); | ||||||
|  |     }, | ||||||
|  |     getEntry: function(req,res) { | ||||||
|  |         var opts = { | ||||||
|  |             user: req.user, | ||||||
|  |             type: req.params[0], | ||||||
|  |             path: req.params[1]||"" | ||||||
|  |         } | ||||||
|  |         runtimeAPI.library.getEntry(opts).then(function(result) { | ||||||
|             if (typeof result === "string") { |             if (typeof result === "string") { | ||||||
|  |                 if (opts.type === 'flows') { | ||||||
|  |                     res.writeHead(200, {'Content-Type': 'application/json'}); | ||||||
|  |                 } else { | ||||||
|                     res.writeHead(200, {'Content-Type': 'text/plain'}); |                     res.writeHead(200, {'Content-Type': 'text/plain'}); | ||||||
|  |                 } | ||||||
|                 res.write(result); |                 res.write(result); | ||||||
|                 res.end(); |                 res.end(); | ||||||
|             } else { |             } else { | ||||||
|                 res.json(result); |                 res.json(result); | ||||||
|             } |             } | ||||||
|         }).catch(function(err) { |         }).catch(function(err) { | ||||||
|                 if (err) { |             apiUtils.rejectHandler(req,res,err); | ||||||
|                     log.warn(log._("api.library.error-load-entry",{path:path,message:err.toString()})); |  | ||||||
|                     if (err.code === 'forbidden') { |  | ||||||
|                         log.audit({event: "library.get",type:type,error:"forbidden"},req); |  | ||||||
|                         res.status(403).end(); |  | ||||||
|                         return; |  | ||||||
|                     } |  | ||||||
|                 } |  | ||||||
|                 log.audit({event: "library.get",type:type,error:"not_found"},req); |  | ||||||
|                 res.status(404).end(); |  | ||||||
|             }); |  | ||||||
|         }); |  | ||||||
|  |  | ||||||
|         redApp.post(new RegExp("/library/"+type+"\/(.*)"),needsPermission("library.write"),function(req,res) { |  | ||||||
|             var path = req.params[0]; |  | ||||||
|             var meta = req.body; |  | ||||||
|             var text = meta.text; |  | ||||||
|             delete meta.text; |  | ||||||
|  |  | ||||||
|             storage.saveLibraryEntry(type,path,meta,text).then(function() { |  | ||||||
|                 log.audit({event: "library.set",type:type},req); |  | ||||||
|                 res.status(204).end(); |  | ||||||
|             }).catch(function(err) { |  | ||||||
|                 log.warn(log._("api.library.error-save-entry",{path:path,message:err.toString()})); |  | ||||||
|                     if (err.code === 'forbidden') { |  | ||||||
|                     log.audit({event: "library.set",type:type,error:"forbidden"},req); |  | ||||||
|                     res.status(403).end(); |  | ||||||
|                     return; |  | ||||||
|                 } |  | ||||||
|                 log.audit({event: "library.set",type:type,error:"unexpected_error",message:err.toString()},req); |  | ||||||
|                 res.status(500).json({error:"unexpected_error", message:err.toString()}); |  | ||||||
|             }); |  | ||||||
|         }); |  | ||||||
|     } |  | ||||||
| } |  | ||||||
|  |  | ||||||
| module.exports = { |  | ||||||
|     init: function(app,runtime) { |  | ||||||
|         redApp = app; |  | ||||||
|         log = runtime.log; |  | ||||||
|         storage = runtime.storage; |  | ||||||
|         redNodes = runtime.nodes; |  | ||||||
|     }, |  | ||||||
|     register: createLibrary, |  | ||||||
|  |  | ||||||
|     getAll: function(req,res) { |  | ||||||
|         storage.getAllFlows().then(function(flows) { |  | ||||||
|             log.audit({event: "library.get.all",type:"flow"},req); |  | ||||||
|             var examples = redNodes.getNodeExampleFlows(); |  | ||||||
|             if (examples) { |  | ||||||
|                 flows.d = flows.d||{}; |  | ||||||
|                 flows.d._examples_ = redNodes.getNodeExampleFlows(); |  | ||||||
|             } |  | ||||||
|             res.json(flows); |  | ||||||
|         }); |         }); | ||||||
|     }, |     }, | ||||||
|     get: function(req,res) { |     saveEntry: function(req,res) { | ||||||
|         if (req.params[0].indexOf("_examples_/") === 0) { |         var opts = { | ||||||
|             var m = /^_examples_\/(@.*?\/[^\/]+|[^\/]+)\/(.*)$/.exec(req.params[0]); |             user: req.user, | ||||||
|             if (m) { |             type: req.params[0], | ||||||
|                 var module = m[1]; |             path: req.params[1]||"" | ||||||
|                 var path = m[2]; |  | ||||||
|                 var fullPath = redNodes.getNodeExampleFlowPath(module,path); |  | ||||||
|                 if (fullPath) { |  | ||||||
|                     try { |  | ||||||
|                         fs.statSync(fullPath); |  | ||||||
|                         log.audit({event: "library.get",type:"flow",path:req.params[0]},req); |  | ||||||
|                         return res.sendFile(fullPath,{ |  | ||||||
|                             headers:{ |  | ||||||
|                                 'Content-Type': 'application/json' |  | ||||||
|         } |         } | ||||||
|                         }) |         // TODO: horrible inconsistencies between flows and all other types | ||||||
|                     } catch(err) { |         if (opts.type === "flows") { | ||||||
|                         console.log(err); |             opts.meta = {}; | ||||||
|                     } |             opts.body = JSON.stringify(req.body); | ||||||
|                 } |  | ||||||
|             } |  | ||||||
|             // IF we get here, we didn't find the file |  | ||||||
|             log.audit({event: "library.get",type:"flow",path:req.params[0],error:"not_found"},req); |  | ||||||
|             return res.status(404).end(); |  | ||||||
|         } else { |         } else { | ||||||
|             storage.getFlow(req.params[0]).then(function(data) { |             opts.meta = req.body; | ||||||
|                 // data is already a JSON string |             opts.body = opts.meta.text; | ||||||
|                 log.audit({event: "library.get",type:"flow",path:req.params[0]},req); |             delete opts.meta.text; | ||||||
|                 res.set('Content-Type', 'application/json'); |  | ||||||
|                 res.send(data); |  | ||||||
|             }).catch(function(err) { |  | ||||||
|                 if (err) { |  | ||||||
|                     log.warn(log._("api.library.error-load-flow",{path:req.params[0],message:err.toString()})); |  | ||||||
|                     if (err.code === 'forbidden') { |  | ||||||
|                         log.audit({event: "library.get",type:"flow",path:req.params[0],error:"forbidden"},req); |  | ||||||
|                         res.status(403).end(); |  | ||||||
|                         return; |  | ||||||
|         } |         } | ||||||
|                 } |         runtimeAPI.library.saveEntry(opts).then(function(result) { | ||||||
|                 log.audit({event: "library.get",type:"flow",path:req.params[0],error:"not_found"},req); |  | ||||||
|                 res.status(404).end(); |  | ||||||
|             }); |  | ||||||
|         } |  | ||||||
|     }, |  | ||||||
|     post: function(req,res) { |  | ||||||
|         // if (req.params[0].indexOf("_examples_/") === 0) { |  | ||||||
|         //     log.warn(log._("api.library.error-save-flow",{path:req.params[0],message:"forbidden"})); |  | ||||||
|         //     log.audit({event: "library.set",type:"flow",path:req.params[0],error:"forbidden"},req); |  | ||||||
|         //     return res.status(403).send({error:"unexpected_error", message:"forbidden"}); |  | ||||||
|         // } |  | ||||||
|         var flow = JSON.stringify(req.body); |  | ||||||
|         storage.saveFlow(req.params[0],flow).then(function() { |  | ||||||
|             log.audit({event: "library.set",type:"flow",path:req.params[0]},req); |  | ||||||
|             res.status(204).end(); |             res.status(204).end(); | ||||||
|         }).catch(function(err) { |         }).catch(function(err) { | ||||||
|             log.warn(log._("api.library.error-save-flow",{path:req.params[0],message:err.toString()})); |             apiUtils.rejectHandler(req,res,err); | ||||||
|             if (err.code === 'forbidden') { |  | ||||||
|                 log.audit({event: "library.set",type:"flow",path:req.params[0],error:"forbidden"},req); |  | ||||||
|                 res.status(403).end(); |  | ||||||
|                 return; |  | ||||||
|             } |  | ||||||
|             log.audit({event: "library.set",type:"flow",path:req.params[0],error:"unexpected_error",message:err.toString()},req); |  | ||||||
|             res.status(500).send({error:"unexpected_error", message:err.toString()}); |  | ||||||
|         }); |         }); | ||||||
|     } |     } | ||||||
| } | } | ||||||
|   | |||||||
| @@ -223,7 +223,7 @@ var api = module.exports = { | |||||||
|     */ |     */ | ||||||
|     getNodeCredentials: function(opts) { |     getNodeCredentials: function(opts) { | ||||||
|         return new Promise(function(resolve,reject) { |         return new Promise(function(resolve,reject) { | ||||||
|             log.audit({event: "credentials.get",type:opts.type,id:opts.id}); |             runtime.log.audit({event: "credentials.get",type:opts.type,id:opts.id}); | ||||||
|             var credentials = runtime.nodes.getCredentials(opts.id); |             var credentials = runtime.nodes.getCredentials(opts.id); | ||||||
|             if (!credentials) { |             if (!credentials) { | ||||||
|                 return resolve({}); |                 return resolve({}); | ||||||
|   | |||||||
| @@ -30,6 +30,7 @@ var api = module.exports = { | |||||||
|         api.flows.init(runtime); |         api.flows.init(runtime); | ||||||
|         api.nodes.init(runtime); |         api.nodes.init(runtime); | ||||||
|         api.settings.init(runtime); |         api.settings.init(runtime); | ||||||
|  |         api.library.init(runtime); | ||||||
|     }, |     }, | ||||||
|  |  | ||||||
|     /** |     /** | ||||||
|   | |||||||
| @@ -15,21 +15,107 @@ | |||||||
|  **/ |  **/ | ||||||
|  |  | ||||||
| /** | /** | ||||||
|  * @module red/library |  * @namespace RED.library | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| module.exports = { | var runtime; | ||||||
|  |  | ||||||
|  | var api = module.exports = { | ||||||
|  |     init: function(_runtime) { | ||||||
|  |         runtime = _runtime; | ||||||
|  |     }, | ||||||
|  |  | ||||||
|     /** |     /** | ||||||
|     * Does something |     * Gets an entry from the library. | ||||||
|  |     * @param {Object} opts | ||||||
|  |     * @param {User} opts.user - the user calling the api | ||||||
|  |     * @param {String} opts.type - the type of entry | ||||||
|  |     * @param {String} opts.path - the path of the entry | ||||||
|  |     * @return {Promise<String|Object>} - resolves when complete | ||||||
|  |     * @memberof RED.library | ||||||
|     */ |     */ | ||||||
|     setEnty: function() {}, |     getEntry: function(opts) { | ||||||
|  |         return new Promise(function(resolve,reject) { | ||||||
|  |             runtime.library.getEntry(opts.type,opts.path).then(function(result) { | ||||||
|  |                 runtime.log.audit({event: "library.get",type:opts.type,path:opts.path}); | ||||||
|  |                 return resolve(result); | ||||||
|  |             }).catch(function(err) { | ||||||
|  |                 if (err) { | ||||||
|  |                     runtime.log.warn(runtime.log._("api.library.error-load-entry",{path:opts.path,message:err.toString()})); | ||||||
|  |                     if (err.code === 'forbidden') { | ||||||
|  |                         err.status = 403; | ||||||
|  |                         return reject(err); | ||||||
|  |                     } else if (err.code === "not_found") { | ||||||
|  |                         err.status = 404; | ||||||
|  |                     } else { | ||||||
|  |                         err.status = 400; | ||||||
|  |                     } | ||||||
|  |                     runtime.log.audit({event: "library.get",type:opts.type,path:opts.path,error:err.code}); | ||||||
|  |                     return reject(err); | ||||||
|  |                 } | ||||||
|  |                 runtime.log.audit({event: "library.get",type:type,error:"not_found"}); | ||||||
|  |                 var error = new Error(); | ||||||
|  |                 error.code = "not_found"; | ||||||
|  |                 error.status = 404; | ||||||
|  |                 return reject(error); | ||||||
|  |             }); | ||||||
|  |         }) | ||||||
|  |     }, | ||||||
|  |  | ||||||
|     /** |     /** | ||||||
|     * Does something |     * Saves an entry to the library | ||||||
|  |     * @param {Object} opts | ||||||
|  |     * @param {User} opts.user - the user calling the api | ||||||
|  |     * @param {String} opts.type - the type of entry | ||||||
|  |     * @param {String} opts.path - the path of the entry | ||||||
|  |     * @param {Object} opts.meta - any meta data associated with the entry | ||||||
|  |     * @param {String} opts.body - the body of the entry | ||||||
|  |     * @return {Promise} - resolves when complete | ||||||
|  |     * @memberof RED.library | ||||||
|     */ |     */ | ||||||
|     getEntry: function() {}, |     saveEntry: function(opts) { | ||||||
|  |         return new Promise(function(resolve,reject) { | ||||||
|  |             runtime.library.saveEntry(opts.type,opts.path,opts.meta,opts.body).then(function() { | ||||||
|  |                 runtime.log.audit({event: "library.set",type:opts.type,path:opts.path}); | ||||||
|  |                 return resolve(); | ||||||
|  |             }).catch(function(err) { | ||||||
|  |                 runtime.log.warn(runtime.log._("api.library.error-save-entry",{path:opts.path,message:err.toString()})); | ||||||
|  |                     if (err.code === 'forbidden') { | ||||||
|  |                     runtime.log.audit({event: "library.set",type:opts.type,path:opts.path,error:"forbidden"}); | ||||||
|  |                     err.status = 403; | ||||||
|  |                     return reject(err); | ||||||
|  |                 } | ||||||
|  |                 runtime.log.audit({event: "library.set",type:opts.type,path:opts.path,error:"unexpected_error",message:err.toString()}); | ||||||
|  |                 var error = new Error(); | ||||||
|  |                 error.code = "not_found"; | ||||||
|  |                 error.status = 400; | ||||||
|  |                 return reject(error); | ||||||
|  |             }); | ||||||
|  |         }) | ||||||
|  |     }, | ||||||
|     /** |     /** | ||||||
|     * Does something |     * Returns a complete listing of all entries of a given type in the library. | ||||||
|  |     * @param {Object} opts | ||||||
|  |     * @param {User} opts.user - the user calling the api | ||||||
|  |     * @param {String} opts.type - the type of entry | ||||||
|  |     * @return {Promise<Object>} - the entry listing | ||||||
|  |     * @memberof RED.library | ||||||
|     */ |     */ | ||||||
|     getEntries: function() {} |     getEntries: function(opts) { | ||||||
|  |         return new Promise(function(resolve,reject) { | ||||||
|  |             if (opts.type !== 'flows') { | ||||||
|  |                 return reject(new Error("API only supports flows")); | ||||||
|  |  | ||||||
|  |             } | ||||||
|  |             runtime.storage.getAllFlows().then(function(flows) { | ||||||
|  |                 runtime.log.audit({event: "library.get.all",type:"flow"}); | ||||||
|  |                 var examples = runtime.nodes.getNodeExampleFlows(); | ||||||
|  |                 if (examples) { | ||||||
|  |                     flows.d = flows.d||{}; | ||||||
|  |                     flows.d._examples_ = examples; | ||||||
|  |                 } | ||||||
|  |                 return resolve(flows); | ||||||
|  |             }); | ||||||
|  |         }) | ||||||
|  |     } | ||||||
| } | } | ||||||
|   | |||||||
| @@ -14,27 +14,12 @@ | |||||||
|  * limitations under the License. |  * limitations under the License. | ||||||
|  **/ |  **/ | ||||||
| "use strict" | "use strict" | ||||||
|  /** | /** | ||||||
|  * @namespace RED.nodes |  * @namespace RED.nodes | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| var runtime; | var runtime; | ||||||
|  |  | ||||||
| function putNode(node, enabled) { |  | ||||||
|     var promise; |  | ||||||
|     if (!node.err && node.enabled === enabled) { |  | ||||||
|         promise = Promise.resolve(node); |  | ||||||
|     } else { |  | ||||||
|         if (enabled) { |  | ||||||
|             promise = runtime.nodes.enableNode(node.id); |  | ||||||
|         } else { |  | ||||||
|             promise = runtime.nodes.disableNode(node.id); |  | ||||||
|         } |  | ||||||
|     } |  | ||||||
|     return promise; |  | ||||||
| } |  | ||||||
|  |  | ||||||
|  |  | ||||||
| var api = module.exports = { | var api = module.exports = { | ||||||
|     init: function(_runtime) { |     init: function(_runtime) { | ||||||
|         runtime = _runtime; |         runtime = _runtime; | ||||||
|   | |||||||
| @@ -18,6 +18,7 @@ var when = require('when'); | |||||||
|  |  | ||||||
| var redNodes = require("./nodes"); | var redNodes = require("./nodes"); | ||||||
| var storage = require("./storage"); | var storage = require("./storage"); | ||||||
|  | var library = require("./library"); | ||||||
| var log = require("./log"); | var log = require("./log"); | ||||||
| var i18n = require("./i18n"); | var i18n = require("./i18n"); | ||||||
| var events = require("./events"); | var events = require("./events"); | ||||||
| @@ -65,6 +66,7 @@ function init(userSettings,_adminApi) { | |||||||
|         adminApi = _adminApi; |         adminApi = _adminApi; | ||||||
|     } |     } | ||||||
|     redNodes.init(runtime); |     redNodes.init(runtime); | ||||||
|  |     library.init(runtime); | ||||||
| } | } | ||||||
|  |  | ||||||
| var version; | var version; | ||||||
| @@ -245,6 +247,7 @@ var runtime = module.exports = { | |||||||
|     storage: storage, |     storage: storage, | ||||||
|     events: events, |     events: events, | ||||||
|     nodes: redNodes, |     nodes: redNodes, | ||||||
|  |     library: library, | ||||||
|     util: require("./util"), |     util: require("./util"), | ||||||
|     get adminApi() { return adminApi }, |     get adminApi() { return adminApi }, | ||||||
|     get nodeApp() { return nodeApp }, |     get nodeApp() { return nodeApp }, | ||||||
|   | |||||||
							
								
								
									
										100
									
								
								red/runtime/library/index.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										100
									
								
								red/runtime/library/index.js
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,100 @@ | |||||||
|  | /** | ||||||
|  |  * Copyright JS Foundation and other contributors, http://js.foundation | ||||||
|  |  * | ||||||
|  |  * Licensed under the Apache License, Version 2.0 (the "License"); | ||||||
|  |  * you may not use this file except in compliance with the License. | ||||||
|  |  * You may obtain a copy of the License at | ||||||
|  |  * | ||||||
|  |  * http://www.apache.org/licenses/LICENSE-2.0 | ||||||
|  |  * | ||||||
|  |  * Unless required by applicable law or agreed to in writing, software | ||||||
|  |  * distributed under the License is distributed on an "AS IS" BASIS, | ||||||
|  |  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||||||
|  |  * See the License for the specific language governing permissions and | ||||||
|  |  * limitations under the License. | ||||||
|  |  **/ | ||||||
|  |  | ||||||
|  | var fs = require('fs'); | ||||||
|  | var fspath = require('path'); | ||||||
|  |  | ||||||
|  | var runtime; | ||||||
|  | var knownTypes = {}; | ||||||
|  |  | ||||||
|  | var storage; | ||||||
|  |  | ||||||
|  | function init(_runtime) { | ||||||
|  |     runtime = _runtime; | ||||||
|  |     storage = runtime.storage; | ||||||
|  |     knownTypes = {}; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | function registerType(id,type) { | ||||||
|  |     if (knownTypes.hasOwnProperty(type)) { | ||||||
|  |         throw new Error(`Library type '${type}' already registerd by ${id}'`) | ||||||
|  |     } | ||||||
|  |     knownTypes[type] = id; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | function getAllEntries(type) { | ||||||
|  |     if (!knownTypes.hasOwnProperty(type)) { | ||||||
|  |         throw new Error(`Unknown library type '${type}'`); | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | function getEntry(type,path) { | ||||||
|  |     if (type !== 'flows') { | ||||||
|  |         if (!knownTypes.hasOwnProperty(type)) { | ||||||
|  |             throw new Error(`Unknown library type '${type}'`); | ||||||
|  |         } | ||||||
|  |         return storage.getLibraryEntry(type,path); | ||||||
|  |     } else { | ||||||
|  |         return new Promise(function(resolve,reject) { | ||||||
|  |             if (path.indexOf("_examples_/") === 0) { | ||||||
|  |                 var m = /^_examples_\/(@.*?\/[^\/]+|[^\/]+)\/(.*)$/.exec(path); | ||||||
|  |                 if (m) { | ||||||
|  |                     var module = m[1]; | ||||||
|  |                     var entryPath = m[2]; | ||||||
|  |                     var fullPath = runtime.nodes.getNodeExampleFlowPath(module,entryPath); | ||||||
|  |                     if (fullPath) { | ||||||
|  |                         try { | ||||||
|  |                             fs.readFile(fullPath,'utf8',function(err, data) { | ||||||
|  |                                 runtime.log.audit({event: "library.get",type:"flow",path:path}); | ||||||
|  |                                 if (err) { | ||||||
|  |                                     return reject(err); | ||||||
|  |                                 } | ||||||
|  |                                 return resolve(data); | ||||||
|  |                             }) | ||||||
|  |                         } catch(err) { | ||||||
|  |                             return reject(err); | ||||||
|  |                         } | ||||||
|  |                     } | ||||||
|  |                 } else { | ||||||
|  |                     // IF we get here, we didn't find the file | ||||||
|  |                     var error = new Error("not_found"); | ||||||
|  |                     error.code = "not_found"; | ||||||
|  |                     return reject(error); | ||||||
|  |                 } | ||||||
|  |             } else { | ||||||
|  |                 resolve(storage.getFlow(path)); | ||||||
|  |             } | ||||||
|  |         }); | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | function saveEntry(type,path,meta,body) { | ||||||
|  |     if (type !== 'flows') { | ||||||
|  |         if (!knownTypes.hasOwnProperty(type)) { | ||||||
|  |             throw new Error(`Unknown library type '${type}'`); | ||||||
|  |         } | ||||||
|  |         return storage.saveLibraryEntry(type,path,meta,body); | ||||||
|  |     } else { | ||||||
|  |         return storage.saveFlow(path,body); | ||||||
|  |     } | ||||||
|  | } | ||||||
|  |  | ||||||
|  | module.exports = { | ||||||
|  |     init: init, | ||||||
|  |     registerType: registerType, | ||||||
|  |     getAllEntries: getAllEntries, | ||||||
|  |     getEntry: getEntry, | ||||||
|  |     saveEntry: saveEntry | ||||||
|  |  | ||||||
|  | } | ||||||
| @@ -80,7 +80,11 @@ function createNodeApi(node) { | |||||||
|     copyObjectProperties(runtime.settings,red.settings,null,["init","load","reset"]); |     copyObjectProperties(runtime.settings,red.settings,null,["init","load","reset"]); | ||||||
|     if (runtime.adminApi) { |     if (runtime.adminApi) { | ||||||
|         red.comms = runtime.adminApi.comms; |         red.comms = runtime.adminApi.comms; | ||||||
|         red.library = runtime.adminApi.library; |         red.library = { | ||||||
|  |             register: function(type) { | ||||||
|  |                 return runtime.library.registerType(node.id,type); | ||||||
|  |             } | ||||||
|  |         }; | ||||||
|         red.auth = runtime.adminApi.auth; |         red.auth = runtime.adminApi.auth; | ||||||
|         red.httpAdmin = runtime.adminApi.adminApp; |         red.httpAdmin = runtime.adminApi.adminApp; | ||||||
|         red.httpNode = runtime.nodeApp; |         red.httpNode = runtime.nodeApp; | ||||||
| @@ -377,7 +381,7 @@ function addModule(module) { | |||||||
|  |  | ||||||
| function loadNodeHelp(node,lang) { | function loadNodeHelp(node,lang) { | ||||||
|     var base = path.basename(node.template); |     var base = path.basename(node.template); | ||||||
|     var localePath = undefined; |     var localePath; | ||||||
|     if (node.module === 'node-red') { |     if (node.module === 'node-red') { | ||||||
|         var cat_dir = path.dirname(node.template); |         var cat_dir = path.dirname(node.template); | ||||||
|         var cat = path.basename(cat_dir); |         var cat = path.basename(cat_dir); | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user