You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@allura.apache.org by tv...@apache.org on 2014/02/12 16:49:04 UTC
git commit: [#7154] Introduce SiteAdminExtension
Updated Branches:
refs/heads/tv/7154 [created] ee19d509d
[#7154] Introduce SiteAdminExtension
Move neighborhood stats to an extension.
Signed-off-by: Tim Van Steenburgh <tv...@gmail.com>
Project: http://git-wip-us.apache.org/repos/asf/incubator-allura/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-allura/commit/ee19d509
Tree: http://git-wip-us.apache.org/repos/asf/incubator-allura/tree/ee19d509
Diff: http://git-wip-us.apache.org/repos/asf/incubator-allura/diff/ee19d509
Branch: refs/heads/tv/7154
Commit: ee19d509dff10e0a3a2a3577c3e1298d664344f5
Parents: 84c2b7c
Author: Tim Van Steenburgh <tv...@gmail.com>
Authored: Tue Feb 11 20:47:17 2014 +0000
Committer: Tim Van Steenburgh <tv...@gmail.com>
Committed: Wed Feb 12 15:47:08 2014 +0000
----------------------------------------------------------------------
Allura/allura/controllers/root.py | 2 +-
Allura/allura/controllers/site_admin.py | 61 +++++++++++++++++---
Allura/allura/lib/app_globals.py | 1 +
Allura/allura/lib/plugin.py | 30 ++++++++++
Allura/allura/templates/site_admin.html | 15 ++---
Allura/allura/templates/site_admin_index.html | 12 +---
Allura/allura/templates/site_admin_stats.html | 30 ++--------
.../allura/tests/functional/test_site_admin.py | 5 ++
Allura/docs/extending.rst | 1 +
Allura/setup.py | 3 +
10 files changed, 106 insertions(+), 54 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/controllers/root.py
----------------------------------------------------------------------
diff --git a/Allura/allura/controllers/root.py b/Allura/allura/controllers/root.py
index 198493c..d43afa4 100644
--- a/Allura/allura/controllers/root.py
+++ b/Allura/allura/controllers/root.py
@@ -68,7 +68,6 @@ class RootController(WsgiDispatchController):
auth = AuthController()
error = ErrorController()
nf = NewForgeController()
- nf.admin = SiteAdminController()
search = SearchController()
rest = RestController()
if config.get('trovecategories.enableediting', 'false') == 'true':
@@ -80,6 +79,7 @@ class RootController(WsgiDispatchController):
if n and not n.url_prefix.startswith('//'):
n.bind_controller(self)
self.browse = ProjectBrowseController()
+ self.nf.admin = SiteAdminController()
super(RootController, self).__init__()
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/controllers/site_admin.py
----------------------------------------------------------------------
diff --git a/Allura/allura/controllers/site_admin.py b/Allura/allura/controllers/site_admin.py
index e2680dd..352d35f 100644
--- a/Allura/allura/controllers/site_admin.py
+++ b/Allura/allura/controllers/site_admin.py
@@ -25,14 +25,17 @@ from ming.orm import session
import pymongo
import bson
import tg
+from pylons import app_globals as g
from pylons import tmpl_context as c
from pylons import request
from formencode import validators, Invalid
from webob.exc import HTTPNotFound
+from allura.app import SitemapEntry
from allura.lib import helpers as h
from allura.lib import validators as v
from allura.lib.decorators import require_post
+from allura.lib.plugin import SiteAdminExtension
from allura.lib.security import require_access
from allura.lib.widgets import form_fields as ffw
from allura import model as M
@@ -54,24 +57,40 @@ class SiteAdminController(object):
def __init__(self):
self.task_manager = TaskManagerController()
+ c.site_admin_sidebar_menu = self.sidebar_menu()
def _check_security(self):
with h.push_context(config.get('site_admin_project', 'allura'),
neighborhood=config.get('site_admin_project_nbhd', 'Projects')):
require_access(c.project, 'admin')
+ @expose()
+ def _lookup(self, name, *remainder):
+ for ep_name in sorted(g.entry_points['site_admin'].keys()):
+ admin_extension = g.entry_points['site_admin'][ep_name]
+ controller = admin_extension().controllers.get(name)
+ if controller:
+ return controller(), remainder
+ raise HTTPNotFound, name
+
+ def sidebar_menu(self):
+ base_url = '/nf/admin/'
+ links = [
+ SitemapEntry('Home', base_url, ui_icon=g.icons['admin']),
+ SitemapEntry('API Tickets', base_url + 'api_tickets', ui_icon=g.icons['admin']),
+ SitemapEntry('Add Subscribers', base_url + 'add_subscribers', ui_icon=g.icons['admin']),
+ SitemapEntry('New Projects', base_url + 'new_projects', ui_icon=g.icons['admin']),
+ SitemapEntry('Reclone Repo', base_url + 'reclone_repo', ui_icon=g.icons['admin']),
+ SitemapEntry('Task Manager', base_url + 'task_manager?state=busy', ui_icon=g.icons['stats']),
+ ]
+ for ep_name in sorted(g.entry_points['site_admin']):
+ g.entry_points['site_admin'][ep_name]().update_sidebar_menu(links)
+ return links
+
@expose('jinja:allura:templates/site_admin_index.html')
@with_trailing_slash
def index(self):
- neighborhoods = []
- for n in M.Neighborhood.query.find():
- project_count = M.Project.query.find(
- dict(neighborhood_id=n._id)).count()
- configured_count = M.Project.query.find(
- dict(neighborhood_id=n._id, database_configured=True)).count()
- neighborhoods.append((n.name, project_count, configured_count))
- neighborhoods.sort(key=lambda n: n[0])
- return dict(neighborhoods=neighborhoods)
+ return {}
@expose('jinja:allura:templates/site_admin_api_tickets.html')
@without_trailing_slash
@@ -380,3 +399,27 @@ class TaskManagerController(object):
except Invalid as e:
error = str(e)
return dict(doc=doc, error=error)
+
+
+class StatsController(object):
+ """Show neighborhood stats."""
+ @expose('jinja:allura:templates/site_admin_stats.html')
+ @with_trailing_slash
+ def index(self):
+ neighborhoods = []
+ for n in M.Neighborhood.query.find():
+ project_count = M.Project.query.find(
+ dict(neighborhood_id=n._id)).count()
+ configured_count = M.Project.query.find(
+ dict(neighborhood_id=n._id, database_configured=True)).count()
+ neighborhoods.append((n.name, project_count, configured_count))
+ neighborhoods.sort(key=lambda n: n[0])
+ return dict(neighborhoods=neighborhoods)
+
+
+class StatsSiteAdminExtension(SiteAdminExtension):
+ controllers = {'stats': StatsController}
+
+ def update_sidebar_menu(self, links):
+ links.append(SitemapEntry('Stats', '/nf/admin/stats',
+ ui_icon=g.icons['stats']))
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/lib/app_globals.py
----------------------------------------------------------------------
diff --git a/Allura/allura/lib/app_globals.py b/Allura/allura/lib/app_globals.py
index d4f1b06..3ac8499 100644
--- a/Allura/allura/lib/app_globals.py
+++ b/Allura/allura/lib/app_globals.py
@@ -254,6 +254,7 @@ class Globals(object):
stats=_cache_eps('allura.stats'),
site_stats=_cache_eps('allura.site_stats'),
admin=_cache_eps('allura.admin'),
+ site_admin=_cache_eps('allura.site_admin'),
# macro eps are used solely for ensuring that external macros are
# imported (after load, the ep itself is not used)
macros=_cache_eps('allura.macros'),
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/lib/plugin.py
----------------------------------------------------------------------
diff --git a/Allura/allura/lib/plugin.py b/Allura/allura/lib/plugin.py
index 4617303..cd0ed23 100644
--- a/Allura/allura/lib/plugin.py
+++ b/Allura/allura/lib/plugin.py
@@ -1038,6 +1038,36 @@ class AdminExtension(object):
pass
+class SiteAdminExtension(object):
+ """
+ A base class for extending the site admin area in Allura.
+
+ After extending this, expose the extension by adding an entry point in your
+ setup.py::
+
+ [allura.site_admin]
+ myext = foo.bar.baz:MySiteAdminExtension
+
+ :ivar dict controllers: Mapping of str (url component) to
+ Controllers. Can be implemented as a ``@property`` function. The str
+ url components will be mounted at /nf/admin/STR/ and will
+ invoke the Controller.
+ """
+
+ controllers = {}
+
+ def update_sidebar_menu(self, sidebar_links):
+ """
+ Change the site admin sidebar by modifying ``sidebar_links``.
+
+ :param sidebar_links: site admin side bar links
+ :type sidebar_links: list of :class:`allura.app.SitemapEntry`
+
+ :rtype: ``None``
+ """
+ pass
+
+
class ImportIdConverter(object):
'''
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/templates/site_admin.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/site_admin.html b/Allura/allura/templates/site_admin.html
index 8e82374..d83f06e 100644
--- a/Allura/allura/templates/site_admin.html
+++ b/Allura/allura/templates/site_admin.html
@@ -16,6 +16,9 @@
specific language governing permissions and limitations
under the License.
-#}
+
+{% from 'allura:templates/jinja_master/sidebar_menu.html' import sidebar_item with context %}
+
{% set hide_left_bar=False %}
{% if page == 'new_projects' %}
{% set hide_left_bar=True %}
@@ -32,15 +35,9 @@
{% block sidebar_menu %}
<div id="sidebar">
<div> </div>
- <ul>
- <li class="{{page=='index' and 'active' or ''}}"><a href="{{sidebar_rel}}."><b data-icon="{{g.icons['admin'].char}}" class="ico {{g.icons['admin'].css}}"></b>Home</a></li>
- <li class="{{page=='api_tickets' and 'active' or ''}}"><a href="{{sidebar_rel}}api_tickets"><b data-icon="{{g.icons['admin'].char}}" class="ico {{g.icons['admin'].css}}"></b>API Tickets</a></li>
- <li class="{{page=='add_subscribers' and 'active' or ''}}"><a href="{{sidebar_rel}}add_subscribers"><b data-icon="{{g.icons['admin'].char}}" class="ico {{g.icons['admin'].css}}"></b>Add Subscribers</a></li>
- <li class="{{page=='new_projects' and 'active' or ''}}"><a href="{{sidebar_rel}}new_projects"><b data-icon="{{g.icons['admin'].char}}" class="ico {{g.icons['admin'].css}}"></b>New Projects</a></li>
- <li class="{{page=='reclone_repo' and 'active' or ''}}"><a href="{{sidebar_rel}}reclone_repo"><b data-icon="{{g.icons['admin'].char}}" class="ico {{g.icons['admin'].css}}"></b>Reclone Repo</a></li>
- <li class="{{page=='task_manager' and 'active' or ''}}"><a href="{{sidebar_rel}}task_manager?state=busy"><b data-icon="{{g.icons['stats'].char}}" class="ico {{g.icons['stats'].css}}"></b>Task Manager</a></li>
-
- </ul>
+ {% for s in c.site_admin_sidebar_menu %}
+ {{sidebar_item(s)}}
+ {% endfor %}
</div>
{% endblock %}
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/templates/site_admin_index.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/site_admin_index.html b/Allura/allura/templates/site_admin_index.html
index a03bed1..4fea844 100644
--- a/Allura/allura/templates/site_admin_index.html
+++ b/Allura/allura/templates/site_admin_index.html
@@ -18,14 +18,8 @@
-#}
{% set page="index" %}
{% extends 'allura:templates/site_admin.html' %}
+
{% block content %}
-<h2>Neighborhood Stats</h2>
-<table>
- <thead>
- <tr><th>Name</th><th>Projects</th><th>Configured</th></tr>
- </thead>
- {% for name, count, count_configured in neighborhoods %}
- <tr><td>{{name}}</td><td>{{count}}</td><td>{{count_configured}}</td></tr>
- {% endfor %}
-</table>
+<h2>Site Admin Home</h2>
+<p>Choose an action from the menu on the left.</p>
{% endblock %}
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/templates/site_admin_stats.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/site_admin_stats.html b/Allura/allura/templates/site_admin_stats.html
index 86262d5..6bdcf3b 100644
--- a/Allura/allura/templates/site_admin_stats.html
+++ b/Allura/allura/templates/site_admin_stats.html
@@ -20,35 +20,13 @@
{% extends 'allura:templates/site_admin.html' %}
{% block content %}
+<h2>Neighborhood Stats</h2>
<table>
<thead>
- <tr>
- <th>Url</th>
- <th>Ming</th>
- <th>Mongo</th>
- <th>Render</th>
- <th>Template</th>
- <th>Total Time</th>
- </tr>
- <tr>
- <th>Mean</th>
- <td>{{agg_timings.ming}}</td>
- <td>{{agg_timings.mongo}}</td>
- <td>{{agg_timings.render}}</td>
- <td>{{agg_timings.template}}</td>
- <td>{{agg_timings.total}}</td>
- </tr>
+ <tr><th>Name</th><th>Projects</th><th>Configured</th></tr>
</thead>
- {% for url,timers in stats %}
- <tr>
- <td>{{url}}</td>
- <td>{{timers.get('ming')}}</td>
- <td>{{timers.get('mongo')}}</td>
- <td>{{timers.get('render')}}</td>
- <td>{{timers.get('template')}}</td>
- <td>{{timers.get('total')}}</td>
- </tr>
+ {% for name, count, count_configured in neighborhoods %}
+ <tr><td>{{name}}</td><td>{{count}}</td><td>{{count_configured}}</td></tr>
{% endfor %}
</table>
-
{% endblock %}
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/allura/tests/functional/test_site_admin.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tests/functional/test_site_admin.py b/Allura/allura/tests/functional/test_site_admin.py
index 0bbff58..79ca43b 100644
--- a/Allura/allura/tests/functional/test_site_admin.py
+++ b/Allura/allura/tests/functional/test_site_admin.py
@@ -39,6 +39,11 @@ class TestSiteAdmin(TestController):
def test_home(self):
r = self.app.get('/nf/admin/', extra_environ=dict(
username='root'))
+ assert 'Site Admin Home' in r
+
+ def test_stats(self):
+ r = self.app.get('/nf/admin/stats/', extra_environ=dict(
+ username='root'))
assert 'Forge Site Admin' in r.html.find(
'h2', {'class': 'dark title'}).contents[0]
stats_table = r.html.find('table')
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/docs/extending.rst
----------------------------------------------------------------------
diff --git a/Allura/docs/extending.rst b/Allura/docs/extending.rst
index 9758f55..1e7cef7 100644
--- a/Allura/docs/extending.rst
+++ b/Allura/docs/extending.rst
@@ -31,6 +31,7 @@ The available extension points for Allura are:
* :class:`allura.lib.plugin.AuthenticationProvider`
* :class:`allura.lib.plugin.UserPreferencesProvider`
* :class:`allura.lib.plugin.AdminExtension`
+* :class:`allura.lib.plugin.SiteAdminExtension`
* :class:`allura.lib.spam.SpamFilter`
* ``site_stats`` in the root API data. Docs in :class:`allura.controllers.rest.RestController`
* :mod:`allura.lib.package_path_loader` (for overriding templates)
http://git-wip-us.apache.org/repos/asf/incubator-allura/blob/ee19d509/Allura/setup.py
----------------------------------------------------------------------
diff --git a/Allura/setup.py b/Allura/setup.py
index f4ea03a..cfb4649 100644
--- a/Allura/setup.py
+++ b/Allura/setup.py
@@ -124,6 +124,9 @@ setup(
akismet = allura.lib.spam.akismetfilter:AkismetSpamFilter
mollom = allura.lib.spam.mollomfilter:MollomSpamFilter
+ [allura.site_admin]
+ stats = allura.controllers.site_admin:StatsSiteAdminExtension
+
[paste.paster_command]
taskd = allura.command.taskd:TaskdCommand
taskd_cleanup = allura.command.taskd_cleanup:TaskdCleanupCommand