From 777173d9f43d5e6e20f40835c24a03b162e7afac Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Mon, 29 Jul 2013 15:15:49 -0400 Subject: [PATCH] adding admin panel integration to plugins (issue #143) --- public/css/admin.less | 6 +++ public/src/forum/admin/plugins.js | 22 +++++++++ public/templates/admin/header.tpl | 1 + public/templates/admin/plugins.tpl | 14 ++++++ public/templates/config.json | 1 + src/plugins.js | 76 ++++++++++++++++++++++++------ src/routes/admin.js | 20 ++++++-- src/websockets.js | 11 ++++- 8 files changed, 133 insertions(+), 18 deletions(-) create mode 100644 public/src/forum/admin/plugins.js create mode 100644 public/templates/admin/plugins.tpl diff --git a/public/css/admin.less b/public/css/admin.less index 61ed7755e1..52f7752a64 100644 --- a/public/css/admin.less +++ b/public/css/admin.less @@ -141,4 +141,10 @@ } } } + + .plugins { + li { + list-style-type: none; + } + } } \ No newline at end of file diff --git a/public/src/forum/admin/plugins.js b/public/src/forum/admin/plugins.js new file mode 100644 index 0000000000..e1b49c8a9c --- /dev/null +++ b/public/src/forum/admin/plugins.js @@ -0,0 +1,22 @@ +var nodebb_admin = nodebb_admin || {}; + +(function() { + var plugins = { + init: function() { + // socket.on('api:admin.plugins.getInstalled', function(pluginsArr) { + // var pluginsFrag = document.createDocumentFragment(), + // liEl = document.createElement('li'); + // for(var x=0,numPlugins=pluginsArr.length;x Users
  • Topics
  • Themes
  • +
  • Plugins
  • Settings
  • Redis
  • MOTD
  • diff --git a/public/templates/admin/plugins.tpl b/public/templates/admin/plugins.tpl new file mode 100644 index 0000000000..c058d841c3 --- /dev/null +++ b/public/templates/admin/plugins.tpl @@ -0,0 +1,14 @@ +

    Plugins

    + + + + \ No newline at end of file diff --git a/public/templates/config.json b/public/templates/config.json index 5f00752c23..eb4a43b89a 100644 --- a/public/templates/config.json +++ b/public/templates/config.json @@ -7,6 +7,7 @@ "admin/redis[^]*": "admin/redis", "admin/index[^]*": "admin/index", "admin/themes[^]*": "admin/themes", + "admin/plugins[^]*": "admin/plugins", "admin/settings[^]*": "admin/settings", "admin/twitter[^]*": "admin/twitter", "admin/facebook[^]*": "admin/facebook", diff --git a/src/plugins.js b/src/plugins.js index 3340e69f97..f512c6a270 100644 --- a/src/plugins.js +++ b/src/plugins.js @@ -119,9 +119,33 @@ var fs = require('fs'), } } }, - showInstalled: function() { + isActive: function(id, callback) { + RDB.sismember('plugins:active', id, callback); + }, + toggleActive: function(id, callback) { + this.isActive(id, function(err, active) { + if (err) { + if (global.env === 'development') console.log('Info: [plugins] Could not toggle active state on plugin \'' + id + '\''); + return; + } + + RDB[(active ? 'srem' : 'sadd')]('plugins:active', id, function(err, success) { + if (err) { + if (global.env === 'development') console.log('Info: [plugins] Could not toggle active state on plugin \'' + id + '\''); + return; + } + + callback({ + id: id, + active: !active + }); + }); + }); + }, + showInstalled: function(callback) { // TODO: Also check /node_modules - var moduleBasePath = path.join(__dirname, '../plugins'); + var _self = this; + moduleBasePath = path.join(__dirname, '../plugins'); async.waterfall([ function(next) { @@ -134,26 +158,50 @@ var fs = require('fs'), var modulePath = path.join(moduleBasePath, file), configPath; - fs.stat(path.join(moduleBasePath, file), function(err, stats) { - if (err || !stats.isDirectory()) return next(); //Silently fail - - // Load the config file - fs.readFile(path.join(modulePath, 'plugin.json'), function(err, configJSON) { - if (err) return next(); // Silently fail if config can't be read + async.waterfall([ + function(next) { + fs.stat(path.join(moduleBasePath, file), next); + }, + function(stats, next) { + if (stats.isDirectory()) fs.readFile(path.join(modulePath, 'plugin.json'), next); + else next(new Error('not-a-directory')); + }, + function(configJSON, next) { var config = JSON.parse(configJSON); - delete config.library; - delete config.hooks; + _self.isActive(config.id, function(err, active) { + if (err) next(new Error('no-active-state')); - plugins.push(config); - next(); - }); + delete config.library; + delete config.hooks; + config.active = active; + next(null, config); + }); + } + ], function(err, config) { + if (err) next(); // Silently fail + + plugins.push(config); }); + // fs.stat(path.join(moduleBasePath, file), function(err, stats) { + // if (err || !stats.isDirectory()) return next(); // Silently fail + + // // Load the config file + // fs.readFile(path.join(modulePath, 'plugin.json'), function(err, configJSON) { + // if (err) return next(); // Silently fail if config can't be read + // var config = JSON.parse(configJSON); + // delete config.library; + // delete config.hooks; + + // plugins.push(config); + // next(); + // }); + // }); }, function(err) { next(null, plugins); }); } ], function(err, plugins) { - console.log('plugins:', plugins); + callback(err, plugins); }); } } diff --git a/src/routes/admin.js b/src/routes/admin.js index cfc18ebd2c..0ff665087d 100644 --- a/src/routes/admin.js +++ b/src/routes/admin.js @@ -3,7 +3,8 @@ var user = require('./../user.js'), topics = require('./../topics.js'), RDB = require('./../redis.js'), pkg = require('./../../package.json'), - categories = require('./../categories.js'); + categories = require('./../categories.js'), + plugins = require('../plugins'); (function(Admin) { Admin.isAdmin = function(req, res, next) { @@ -23,8 +24,12 @@ var user = require('./../user.js'), Admin.create_routes = function(app) { (function() { - var routes = ['categories', 'users', 'topics', 'settings', 'themes', 'twitter', 'facebook', 'gplus', 'redis', 'motd', - 'users/latest', 'users/sort-posts', 'users/sort-reputation', 'users/search']; + var routes = [ + 'categories', 'users', 'topics', 'settings', 'themes', + 'twitter', 'facebook', 'gplus', 'redis', 'motd', + 'users/latest', 'users/sort-posts', 'users/sort-reputation', + 'users/search', 'plugins' + ]; for (var i=0, ii=routes.length; i