Changeset - 62e493c7f436
[Not reviewed]
beta
0 10 0
Marcin Kuzminski - 13 years ago 2012-10-18 20:16:00
marcin@python-works.com
Added lightweight dashboard option. ref #500
10 files changed with 246 insertions and 33 deletions:
0 comments (0 inline, 0 general)
rhodecode/controllers/admin/settings.py
Show inline comments
 
@@ -185,18 +185,23 @@ class SettingsController(BaseController)
 
                sett1 = RhodeCodeSetting.get_by_name_or_create('show_public_icon')
 
                sett1.app_settings_value = \
 
                    form_result['rhodecode_show_public_icon']
 
                Session().add(sett1)
 

	
 
                sett2 = RhodeCodeSetting.get_by_name_or_create('show_private_icon')
 
                sett2.app_settings_value = \
 
                    form_result['rhodecode_show_private_icon']
 
                Session().add(sett2)
 

	
 
                sett3 = RhodeCodeSetting.get_by_name_or_create('stylify_metatags')
 
                sett3.app_settings_value = \
 
                    form_result['rhodecode_stylify_metatags']
 
                Session().add(sett3)
 

	
 
                Session().add(sett1)
 
                Session().add(sett2)
 
                Session().add(sett3)
 
                sett4 = RhodeCodeSetting.get_by_name_or_create('lightweight_dashboard')
 
                sett4.app_settings_value = \
 
                    form_result['rhodecode_lightweight_dashboard']
 
                Session().add(sett4)
 

	
 
                Session().commit()
 
                set_rhodecode_config(config)
 
                h.flash(_('Updated visualisation settings'),
rhodecode/controllers/home.py
Show inline comments
 
@@ -26,11 +26,16 @@
 
import logging
 

	
 
from pylons import tmpl_context as c, request
 
from pylons.i18n.translation import _
 
from webob.exc import HTTPBadRequest
 

	
 
import rhodecode
 
from rhodecode.lib import helpers as h
 
from rhodecode.lib.ext_json import json
 
from rhodecode.lib.auth import LoginRequired
 
from rhodecode.lib.base import BaseController, render
 
from rhodecode.model.db import Repository
 
from sqlalchemy.sql.expression import func
 

	
 
log = logging.getLogger(__name__)
 

	
 
@@ -42,9 +47,55 @@ class HomeController(BaseController):
 
        super(HomeController, self).__before__()
 

	
 
    def index(self):
 
        c.repos_list = self.scm_model.get_repos()
 
        c.groups = self.scm_model.get_repos_groups()
 
        c.group = None
 

	
 
        if c.visual.lightweight_dashboard is False:
 
            c.repos_list = self.scm_model.get_repos()
 
        ## lightweight version of dashboard
 
        else:
 
            c.repos_list = Repository.query()\
 
                            .filter(Repository.group_id == None)\
 
                            .order_by(func.lower(Repository.repo_name))\
 
                            .all()
 
            repos_data = []
 
            total_records = len(c.repos_list)
 

	
 
            _tmpl_lookup = rhodecode.CONFIG['pylons.app_globals'].mako_lookup
 
            template = _tmpl_lookup.get_template('data_table/_dt_elements.html')
 

	
 
            quick_menu = lambda repo_name: (template.get_def("quick_menu")
 
                                            .render(repo_name, _=_, h=h, c=c))
 
            repo_lnk = lambda name, rtype, private, fork_of: (
 
                template.get_def("repo_name")
 
                .render(name, rtype, private, fork_of, short_name=False,
 
                        admin=False, _=_, h=h, c=c))
 
            rss_lnk = lambda repo_name: (template.get_def("rss")
 
                                           .render(repo_name, _=_, h=h, c=c))
 
            atom_lnk = lambda repo_name: (template.get_def("atom")
 
                                           .render(repo_name, _=_, h=h, c=c))
 

	
 
            for repo in c.repos_list:
 
                repos_data.append({
 
                    "menu": quick_menu(repo.repo_name),
 
                    "raw_name": repo.repo_name.lower(),
 
                    "name": repo_lnk(repo.repo_name, repo.repo_type,
 
                                     repo.private, repo.fork),
 
                    "last_change": h.age(repo.last_db_change),
 
                    "desc": repo.description,
 
                    "owner": h.person(repo.user.username),
 
                    "rss": rss_lnk(repo.repo_name),
 
                    "atom": atom_lnk(repo.repo_name),
 
                })
 

	
 
            c.data = json.dumps({
 
                "totalRecords": total_records,
 
                "startIndex": 0,
 
                "sort": "name",
 
                "dir": "asc",
 
                "records": repos_data
 
            })
 

	
 
        return render('/index.html')
 

	
 
    def repo_switcher(self):
rhodecode/lib/base.py
Show inline comments
 
@@ -245,6 +245,7 @@ class BaseController(WSGIController):
 
        c.visual.show_public_icon = str2bool(config.get('rhodecode_show_public_icon'))
 
        c.visual.show_private_icon = str2bool(config.get('rhodecode_show_private_icon'))
 
        c.visual.stylify_metatags = str2bool(config.get('rhodecode_stylify_metatags'))
 
        c.visual.lightweight_dashboard = str2bool(config.get('rhodecode_lightweight_dashboard'))
 

	
 
        c.repo_name = get_repo_slug(request)
 
        c.backends = BACKENDS.keys()
rhodecode/lib/helpers.py
Show inline comments
 
@@ -42,7 +42,7 @@ from webhelpers.html.tags import _set_in
 
from rhodecode.lib.annotate import annotate_highlight
 
from rhodecode.lib.utils import repo_name_slug
 
from rhodecode.lib.utils2 import str2bool, safe_unicode, safe_str, \
 
    get_changeset_safe, datetime_to_time, time_to_datetime
 
    get_changeset_safe, datetime_to_time, time_to_datetime, AttributeDict
 
from rhodecode.lib.markup_renderer import MarkupRenderer
 
from rhodecode.lib.vcs.exceptions import ChangesetDoesNotExistError
 
from rhodecode.lib.vcs.backends.base import BaseChangeset
rhodecode/model/db.py
Show inline comments
 
@@ -856,6 +856,10 @@ class Repository(Base, BaseModel):
 
        Session().add(repo)
 
        Session().commit()
 

	
 
    @property
 
    def last_db_change(self):
 
        return self.updated_on
 

	
 
    #==========================================================================
 
    # SCM PROPERTIES
 
    #==========================================================================
rhodecode/model/forms.py
Show inline comments
 
@@ -254,6 +254,8 @@ def ApplicationVisualisationForm():
 
        rhodecode_show_private_icon = v.StringBoolean(if_missing=False)
 
        rhodecode_stylify_metatags = v.StringBoolean(if_missing=False)
 

	
 
        rhodecode_lightweight_dashboard = v.StringBoolean(if_missing=False)
 

	
 
    return _ApplicationVisualisationForm
 

	
 

	
rhodecode/model/scm.py
Show inline comments
 
@@ -115,6 +115,7 @@ class CachedRepoList(object):
 
            tmp_d = {}
 
            tmp_d['name'] = dbr.repo_name
 
            tmp_d['name_sort'] = tmp_d['name'].lower()
 
            tmp_d['raw_name'] = tmp_d['name'].lower()
 
            tmp_d['description'] = dbr.description
 
            tmp_d['description_sort'] = tmp_d['description'].lower()
 
            tmp_d['last_change'] = last_change
 
@@ -149,6 +150,7 @@ class SimpleCachedRepoList(CachedRepoLis
 
            tmp_d = {}
 
            tmp_d['name'] = dbr.repo_name
 
            tmp_d['name_sort'] = tmp_d['name'].lower()
 
            tmp_d['raw_name'] = tmp_d['name'].lower()
 
            tmp_d['description'] = dbr.description
 
            tmp_d['description_sort'] = tmp_d['description'].lower()
 
            tmp_d['dbrepo'] = dbr.get_dict()
rhodecode/templates/admin/settings/settings.html
Show inline comments
 
@@ -122,6 +122,17 @@
 
        <!-- fields -->
 

	
 
        <div class="fields">
 
             <div class="field">
 
                <div class="label label-checkbox">
 
                    <label>${_('General')}:</label>
 
                </div>
 
                <div class="checkboxes">
 
                    <div class="checkbox">
 
                        ${h.checkbox('rhodecode_lightweight_dashboard','True')}
 
                        <label for="rhodecode_lightweight_dashboard">${_('Use lightweight dashboard')}</label>
 
                    </div>
 
                 </div>
 
             </div>
 

	
 
             <div class="field">
 
                <div class="label label-checkbox">
rhodecode/templates/data_table/_dt_elements.html
Show inline comments
 
@@ -76,8 +76,8 @@
 
    ${h.link_to(get_name(name),h.url('summary_home',repo_name=name),class_="repo_name")}
 
   %endif
 
   %if fork_of:
 
        <a href="${h.url('summary_home',repo_name=fork_of)}">
 
        <img class="icon" alt="${_('fork')}" title="${_('Fork of')} ${fork_of}" src="${h.url('/images/icons/arrow_divide.png')}"/></a>
 
        <a href="${h.url('summary_home',repo_name=fork_of.repo_name)}">
 
        <img class="icon" alt="${_('fork')}" title="${_('Fork of')} ${fork_of.repo_name}" src="${h.url('/images/icons/arrow_divide.png')}"/></a>
 
   %endif
 
  </div>
 
</%def>
 
@@ -94,6 +94,22 @@
 
  </div>
 
</%def>
 

	
 
<%def name="rss(name)">
 
  %if c.rhodecode_user.username != 'default':
 
    <a title="${_('Subscribe to %s rss feed')% name}" class="rss_icon"  href="${h.url('rss_feed_home',repo_name=name,api_key=c.rhodecode_user.api_key)}"></a>
 
  %else:
 
    <a title="${_('Subscribe to %s rss feed')% name}" class="rss_icon"  href="${h.url('rss_feed_home',repo_name=name)}"></a>
 
  %endif
 
</%def>
 

	
 
<%def name="atom(name)">
 
  %if c.rhodecode_user.username != 'default':
 
    <a title="${_('Subscribe to %s atom feed')% name}"  class="atom_icon" href="${h.url('atom_feed_home',repo_name=name,api_key=c.rhodecode_user.api_key)}"></a>
 
  %else:
 
    <a title="${_('Subscribe to %s atom feed')% name}"  class="atom_icon" href="${h.url('atom_feed_home',repo_name=name)}"></a>
 
  %endif
 
</%def>
 

	
 
<%def name="user_gravatar(email, size=24)">
 
    <div class="gravatar"><img alt="gravatar" src="${h.gravatar_url(email, size)}"/> </div>
 
</%def>
rhodecode/templates/index_base.html
Show inline comments
 
@@ -59,10 +59,11 @@
 
            <div id="welcome" style="display:none;text-align:center">
 
                <h1><a href="${h.url('home')}">${c.rhodecode_name} ${c.rhodecode_version}</a></h1>
 
            </div>
 
             <%cnt=0%>
 
             <%namespace name="dt" file="/data_table/_dt_elements.html"/>
 
            % if c.visual.lightweight_dashboard is False:
 
              ## old full detailed version
 
            <div id='repos_list_wrap' class="yui-skin-sam">
 
            <%cnt=0%>
 
            <%namespace name="dt" file="/data_table/_dt_elements.html"/>
 

	
 
            <table id="repos_list">
 
            <thead>
 
                <tr>
 
@@ -85,7 +86,7 @@
 
                    </td>
 
                    ##REPO NAME AND ICONS
 
                    <td class="reponame">
 
                      ${dt.repo_name(repo['name'],repo['dbrepo']['repo_type'],repo['dbrepo']['private'],repo['dbrepo_fork'].get('repo_name'),pageargs.get('short_repo_names'))}
 
                      ${dt.repo_name(repo['name'],repo['dbrepo']['repo_type'],repo['dbrepo']['private'],h.AttributeDict(repo['dbrepo_fork']),pageargs.get('short_repo_names'))}
 
                    </td>
 
                    ##DESCRIPTION
 
                    <td><span class="tooltip" title="${h.tooltip(repo['description'])}">
 
@@ -106,38 +107,33 @@
 
                    ##
 
                    <td title="${repo['contact']}">${h.person(repo['contact'])}</td>
 
                    <td>
 
                      %if c.rhodecode_user.username != 'default':
 
                        <a title="${_('Subscribe to %s rss feed')%repo['name']}" class="rss_icon"  href="${h.url('rss_feed_home',repo_name=repo['name'],api_key=c.rhodecode_user.api_key)}"></a>
 
                      %else:
 
                        <a title="${_('Subscribe to %s rss feed')%repo['name']}" class="rss_icon"  href="${h.url('rss_feed_home',repo_name=repo['name'])}"></a>
 
                      %endif:
 
                      ${dt.rss(repo['name'])}
 
                    </td>
 
                    <td>
 
                      %if c.rhodecode_user.username != 'default':
 
                        <a title="${_('Subscribe to %s atom feed')%repo['name']}"  class="atom_icon" href="${h.url('atom_feed_home',repo_name=repo['name'],api_key=c.rhodecode_user.api_key)}"></a>
 
                      %else:
 
                        <a title="${_('Subscribe to %s atom feed')%repo['name']}"  class="atom_icon" href="${h.url('atom_feed_home',repo_name=repo['name'])}"></a>
 
                      %endif:
 
                      ${dt.atom(repo['name'])}
 
                    </td>
 
                </tr>
 
            %endfor
 
            </tbody>
 
            </table>
 
            </div>
 
            % else:
 
              ## lightweight version
 
                <div class="yui-skin-sam" id="repos_list_wrap"></div>
 
                <div id="user-paginator" style="padding: 0px 0px 0px 0px"></div>
 
            % endif
 
        </div>
 
    </div>
 
    % if c.visual.lightweight_dashboard is False:
 
    <script>
 
      YUD.get('repo_count').innerHTML = ${cnt+1 if cnt else 0};
 
      var func = function(node){
 
          return node.parentNode.parentNode.parentNode.parentNode;
 
      }
 

	
 
      var sort_by = "name";
 
      var sort_dir = "asc";
 

	
 
      // groups table sorting
 
      var myColumnDefs = [
 
          {key:"name",label:"${_('Group Name')}",sortable:true,
 
          {key:"name",label:"${_('Group name')}",sortable:true,
 
              sortOptions: { sortFunction: groupNameSort }},
 
          {key:"desc",label:"${_('Description')}",sortable:true},
 
      ];
 
@@ -152,13 +148,25 @@
 
          ]
 
      };
 

	
 
      var myDataTable = new YAHOO.widget.DataTable("groups_list_wrap", myColumnDefs, myDataSource,
 
              {
 
               sortedBy:{key:"name",dir:"asc"},
 
               MSG_SORTASC:"${_('Click to sort ascending')}",
 
               MSG_SORTDESC:"${_('Click to sort descending')}"
 
              }
 
      );
 
      var myDataTable = new YAHOO.widget.DataTable("groups_list_wrap", myColumnDefs, myDataSource,{
 
          sortedBy:{key:"name",dir:"asc"},
 
          paginator: new YAHOO.widget.Paginator({
 
              rowsPerPage: 5,
 
              alwaysVisible: false,
 
              template : "{PreviousPageLink} {FirstPageLink} {PageLinks} {LastPageLink} {NextPageLink}",
 
              pageLinks: 5,
 
              containerClass: 'pagination-wh',
 
              currentPageClass: 'pager_curpage',
 
              pageLinkClass: 'pager_link',
 
              nextPageLinkLabel: '&gt;',
 
              previousPageLinkLabel: '&lt;',
 
              firstPageLinkLabel: '&lt;&lt;',
 
              lastPageLinkLabel: '&gt;&gt;',
 
              containers:['user-paginator']
 
          }),          
 
          MSG_SORTASC:"${_('Click to sort ascending')}",
 
          MSG_SORTDESC:"${_('Click to sort descending')}"
 
      });
 

	
 
      // main table sorting
 
      var myColumnDefs = [
 
@@ -182,6 +190,7 @@
 
      myDataSource.responseSchema = {
 
          fields: [
 
              {key:"menu"},
 
              //{key:"raw_name"},
 
              {key:"name"},
 
              {key:"desc"},
 
              {key:"last_change"},
 
@@ -194,7 +203,7 @@
 

	
 
      var myDataTable = new YAHOO.widget.DataTable("repos_list_wrap", myColumnDefs, myDataSource,
 
              {
 
               sortedBy:{key:sort_by,dir:sort_dir},
 
    	       sortedBy:{key:"name",dir:"asc"},
 
               MSG_SORTASC:"${_('Click to sort ascending')}",
 
               MSG_SORTDESC:"${_('Click to sort descending')}",
 
               MSG_EMPTY:"${_('No records found.')}",
 
@@ -209,3 +218,115 @@
 
      });
 

	
 
    </script>
 
    % else:
 
      <script>
 
        //var url = "${h.url('formatted_users', format='json')}";
 
        var data = ${c.data|n};
 
        var myDataSource = new YAHOO.util.DataSource(data);
 
        myDataSource.responseType = YAHOO.util.DataSource.TYPE_JSON;
 
      
 
        myDataSource.responseSchema = {
 
            resultsList: "records",
 
            fields: [
 
               {key:"menu"},
 
               {key:"raw_name"},
 
               {key:"name"},
 
               {key:"desc"},
 
               //{key:"last_change"},
 
               {key:"owner"},
 
               {key:"rss"},
 
               {key:"atom"},
 
            ]
 
         };
 
        myDataSource.doBeforeCallback = function(req,raw,res,cb) {
 
            // This is the filter function
 
            var data     = res.results || [],
 
                filtered = [],
 
                i,l;
 
      
 
            if (req) {
 
                req = req.toLowerCase();
 
                for (i = 0; i<data.length; i++) {
 
                    var pos = data[i].raw_name.toLowerCase().indexOf(req)
 
                    if (pos != -1) {
 
                        filtered.push(data[i]);
 
                    }
 
                }
 
                res.results = filtered;
 
            }
 
            YUD.get('repo_count').innerHTML = res.results.length;
 
            return res;
 
        }
 
      
 
        // main table sorting
 
        var myColumnDefs = [
 
            {key:"menu",label:"",sortable:false,className:"quick_repo_menu hidden"},
 
            {key:"name",label:"${_('Name')}",sortable:true,
 
                sortOptions: { sortFunction: nameSort }},
 
            {key:"desc",label:"${_('Description')}",sortable:true},
 
            //{key:"last_change",label:"${_('Last Change')}",sortable:true,
 
            //    sortOptions: { sortFunction: ageSort }},
 
            {key:"owner",label:"${_('Owner')}",sortable:true},
 
            {key:"rss",label:"",sortable:false},
 
            {key:"atom",label:"",sortable:false},
 
        ];
 
      
 
        var myDataTable = new YAHOO.widget.DataTable("repos_list_wrap", myColumnDefs, myDataSource,{
 
          sortedBy:{key:"name",dir:"asc"},
 
          paginator: new YAHOO.widget.Paginator({
 
              rowsPerPage: 15,
 
              alwaysVisible: false,
 
              template : "{PreviousPageLink} {FirstPageLink} {PageLinks} {LastPageLink} {NextPageLink}",
 
              pageLinks: 5,
 
              containerClass: 'pagination-wh',
 
              currentPageClass: 'pager_curpage',
 
              pageLinkClass: 'pager_link',
 
              nextPageLinkLabel: '&gt;',
 
              previousPageLinkLabel: '&lt;',
 
              firstPageLinkLabel: '&lt;&lt;',
 
              lastPageLinkLabel: '&gt;&gt;',
 
              containers:['user-paginator']
 
          }),
 
      
 
          MSG_SORTASC:"${_('Click to sort ascending')}",
 
          MSG_SORTDESC:"${_('Click to sort descending')}",
 
          MSG_EMPTY:"${_('No records found.')}",
 
          MSG_ERROR:"${_('Data error.')}",
 
          MSG_LOADING:"${_('Loading...')}",
 
        }
 
        );
 
        myDataTable.subscribe('postRenderEvent',function(oArgs) {
 
            tooltip_activate();
 
            quick_repo_menu();
 
        });
 
      
 
        var filterTimeout = null;
 
      
 
        updateFilter  = function () {
 
            // Reset timeout
 
            filterTimeout = null;
 
      
 
            // Reset sort
 
            var state = myDataTable.getState();
 
                state.sortedBy = {key:'name', dir:YAHOO.widget.DataTable.CLASS_ASC};
 
      
 
            // Get filtered data
 
            myDataSource.sendRequest(YUD.get('q_filter').value,{
 
                success : myDataTable.onDataReturnInitializeTable,
 
                failure : myDataTable.onDataReturnInitializeTable,
 
                scope   : myDataTable,
 
                argument: state
 
            });
 
      
 
        };
 
        YUE.on('q_filter','click',function(){
 
            YUD.get('q_filter').value = '';
 
         });
 
      
 
        YUE.on('q_filter','keyup',function (e) {
 
            clearTimeout(filterTimeout);
 
            filterTimeout = setTimeout(updateFilter,600);
 
        });
 
      </script>
 
    % endif
 
    
 
\ No newline at end of file
0 comments (0 inline, 0 general)