mirror of
https://github.com/galaxyproject/galaxy.git
synced 2026-09-24 16:30:27 +08:00
backbone base of TS groups
fix backbone hash problem; some more formatting and API polishing refactor group API controller; better format group detail view more formating and refactoring add column to group detail update details, add some more info to API response
This commit is contained in:
@@ -0,0 +1,134 @@
|
||||
define([
|
||||
"libs/toastr",
|
||||
"mvc/groups/group-model"
|
||||
],
|
||||
function(
|
||||
mod_toastr,
|
||||
mod_group_model
|
||||
) {
|
||||
|
||||
// toolshed group detail view
|
||||
var GroupDetailView = Backbone.View.extend({
|
||||
el: "#groups_element",
|
||||
options: {},
|
||||
app: null,
|
||||
|
||||
initialize : function( options ){
|
||||
this.options = _.extend( this.options, options );
|
||||
this.app = window.globalTS.groups;
|
||||
|
||||
if ( this.app.collection !== null ){
|
||||
this.model = this.app.collection.get( this.options.group_id );
|
||||
this.render();
|
||||
} else {
|
||||
this.fetchGroup();
|
||||
}
|
||||
|
||||
},
|
||||
|
||||
fetchGroup: function( options ){
|
||||
var that = this;
|
||||
this.options = _.extend( this.options, options );
|
||||
this.model = new mod_group_model.Group( { id: this.options.group_id } );
|
||||
this.model.fetch({
|
||||
success: function( model ){
|
||||
console.log( 'received data: ' );
|
||||
console.log( model );
|
||||
that.render();
|
||||
},
|
||||
error: function( model, response ){
|
||||
if ( typeof response.responseJSON !== "undefined" ){
|
||||
mod_toastr.error( response.responseJSON.err_msg );
|
||||
} else {
|
||||
mod_toastr.error( 'An error ocurred.' );
|
||||
}
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
render: function(){
|
||||
var template = this.templateRow();
|
||||
this.$el.html( template( { group: this.model } ) );
|
||||
$("#center [data-toggle]").tooltip();
|
||||
},
|
||||
|
||||
templateRow: function() {
|
||||
return _.template([
|
||||
'<div>',
|
||||
'<h3><%= group.get("name") %></h3>',
|
||||
'<p class="" style="color:gray;">',
|
||||
'A group of <%= group.get("members").length %> members with <%= group.get("repositories").length %> repositories and a total of <%= group.get("total_downloads") %> combined tool downloads.</p>',
|
||||
|
||||
'<h3>Members</h3>',
|
||||
'<table class="grid table table-condensed">',
|
||||
'<thead>',
|
||||
'<th>Name</th>',
|
||||
'<th>Repositories</th>',
|
||||
'<th>Registered</th>',
|
||||
'</thead>',
|
||||
'<tbody>',
|
||||
'<% _.each(group.get("members"), function(member) { %>',
|
||||
'<tr>',
|
||||
'<td>',
|
||||
'<%= member.username %>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<a data-toggle="tooltip" data-placement="top" title="Repositories of <%= member.username %>" href="/repository/browse_repositories_by_user?user_id=<%= member.id %>&use_panels=true" id="<%= member.id %>"><%= member.user_repos_count %></a>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<%= member.time_created %>',
|
||||
'</td>',
|
||||
'</tr>',
|
||||
'<% }); %>',
|
||||
'</tbody>',
|
||||
'</table>',
|
||||
|
||||
'<h3>Repositories</h3>',
|
||||
'<table class="grid table table-condensed">',
|
||||
'<thead>',
|
||||
'<th>Name</th>',
|
||||
'<th>Description</th>',
|
||||
'<th>Downloads</th>',
|
||||
'<th>Owner</th>',
|
||||
'<th>Created</th>',
|
||||
'<th>Rating</th>',
|
||||
'<th>Verified</th>',
|
||||
'</thead>',
|
||||
'<tbody>',
|
||||
'<% _.each(group.get("repositories"), function(repo) { %>',
|
||||
'<tr>',
|
||||
'<td>',
|
||||
'<a data-toggle="tooltip" data-placement="top" title="Details of <%= repo.name %>" href="/view/<%= repo.owner %>/<%= repo.name %>" id="<%= repo.id %>"><%= repo.name %></a>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<%= repo.description %>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<%= repo.times_downloaded %>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<%= repo.owner %>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<%= repo.time_created %>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<%= repo.ratings_mean %>',
|
||||
'</td>',
|
||||
'<td>',
|
||||
'<%= repo.approved %>',
|
||||
'</td>',
|
||||
'</tr>',
|
||||
'<% }); %>',
|
||||
'</tbody>',
|
||||
'</table>',
|
||||
'</div>'
|
||||
].join(''));
|
||||
}
|
||||
});
|
||||
return {
|
||||
GroupDetailView: GroupDetailView
|
||||
};
|
||||
|
||||
});
|
||||
|
||||
@@ -0,0 +1,148 @@
|
||||
define([
|
||||
"libs/toastr",
|
||||
"mvc/groups/group-model",
|
||||
"mvc/groups/group-listrow-view"
|
||||
|
||||
], function(
|
||||
mod_toastr,
|
||||
mod_group_model,
|
||||
mod_group_listrow_view
|
||||
){
|
||||
|
||||
var GroupListView = Backbone.View.extend({
|
||||
el: '#groups_element',
|
||||
defaults: {},
|
||||
|
||||
/**
|
||||
* Initialize and fetch the groups from server.
|
||||
* Async render afterwards.
|
||||
* @param {object} options an object with options
|
||||
*/
|
||||
initialize : function( options ){
|
||||
this.options = _.defaults( this.options || {}, this.defaults, options );
|
||||
var that = this;
|
||||
window.globalTS.groups.collection = new mod_group_model.Groups();
|
||||
window.globalTS.groups.collection.fetch({
|
||||
success: function( model ){
|
||||
console.log( 'received data: ' );
|
||||
console.log( model );
|
||||
that.render();
|
||||
},
|
||||
error: function( model, response ){
|
||||
if ( typeof response.responseJSON !== "undefined" ){
|
||||
mod_toastr.error( response.responseJSON.err_msg );
|
||||
} else {
|
||||
mod_toastr.error( 'An error ocurred.' );
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
},
|
||||
|
||||
fetch: function(){
|
||||
},
|
||||
|
||||
/**
|
||||
* Render the groups table from the object's own collection.
|
||||
*/
|
||||
render: function ( options ) {
|
||||
this.options = _.extend( this.options, options );
|
||||
$( ".tooltip" ).hide();
|
||||
var template = this.templateGroupsList();
|
||||
this.$el.html( template( { length: 10, order: 'asc' } ) );
|
||||
this.renderRows( window.globalTS.groups.collection.models );
|
||||
$( "#center [data-toggle]" ).tooltip();
|
||||
$( "#center" ).css( 'overflow','auto' );
|
||||
},
|
||||
|
||||
/**
|
||||
* Render all given models as rows in the groups list
|
||||
* @param {array} groups_to_render array of group models to render
|
||||
*/
|
||||
renderRows: function( groups_to_render ){
|
||||
for ( var i = 0; i < groups_to_render.length; i++ ) {
|
||||
var group = groups_to_render[i];
|
||||
this.renderOne( { group: group } )
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Create a view for the given model and add it to the groups view.
|
||||
* @param {Group} model of the view that will be rendered
|
||||
*/
|
||||
renderOne: function( options ){
|
||||
var rowView = new mod_group_listrow_view.GroupListRowView( options );
|
||||
this.$el.find( '#group_list_body' ).append( rowView.el );
|
||||
},
|
||||
|
||||
/**
|
||||
* Table heading was clicked, update sorting preferences and re-render.
|
||||
* @return {[type]} [description]
|
||||
*/
|
||||
// sort_clicked : function(){
|
||||
// if (Galaxy.libraries.preferences.get('sort_order') === 'asc'){
|
||||
// Galaxy.libraries.preferences.set({'sort_order': 'desc'});
|
||||
// } else {
|
||||
// Galaxy.libraries.preferences.set({'sort_order': 'asc'});
|
||||
// }
|
||||
// this.render();
|
||||
// },
|
||||
|
||||
/**
|
||||
* Sort the underlying collection according to the parameters received.
|
||||
* Currently supports only sorting by name.
|
||||
*/
|
||||
// sortLibraries: function(){
|
||||
// if (Galaxy.libraries.preferences.get('sort_by') === 'name'){
|
||||
// if (Galaxy.libraries.preferences.get('sort_order') === 'asc'){
|
||||
// this.collection.sortByNameAsc();
|
||||
// } else if (Galaxy.libraries.preferences.get('sort_order') === 'desc'){
|
||||
// this.collection.sortByNameDesc();
|
||||
// }
|
||||
// }
|
||||
// },
|
||||
|
||||
// redirectToHome: function(){
|
||||
// window.location = '../';
|
||||
// },
|
||||
// redirectToLogin: function(){
|
||||
// window.location = '/user/login';
|
||||
// },
|
||||
|
||||
// MMMMMMMMMMMMMMMMMM
|
||||
// === TEMPLATES ====
|
||||
// MMMMMMMMMMMMMMMMMM
|
||||
|
||||
templateGroupsList: function(){
|
||||
tmpl_array = [];
|
||||
|
||||
tmpl_array.push('<div id="groups">');
|
||||
tmpl_array.push('</div>');
|
||||
tmpl_array.push('<div class="groups_container table-responsive">');
|
||||
tmpl_array.push('<% if(length === 0) { %>');
|
||||
tmpl_array.push('<div>There are no groups yet.</div>');
|
||||
tmpl_array.push('<% } else{ %>');
|
||||
tmpl_array.push('<table class="grid table table-condensed">');
|
||||
tmpl_array.push(' <thead>');
|
||||
tmpl_array.push(' <th style="width:30%;"><a class="sort-groups-link" title="Click to reverse order" href="#">name</a> <span title="Sorted alphabetically" class="fa fa-sort-alpha-<%- order %>"></span></th>');
|
||||
tmpl_array.push(' <th style="width:22%;">description</th>');
|
||||
tmpl_array.push(' <th style="width:22%;">members</th> ');
|
||||
tmpl_array.push(' <th style="width:26%;">repositories</th>');
|
||||
tmpl_array.push(' </thead>');
|
||||
tmpl_array.push(' <tbody id="group_list_body">');
|
||||
// group item views will attach here
|
||||
tmpl_array.push(' </tbody>');
|
||||
tmpl_array.push('</table>');
|
||||
tmpl_array.push('<% }%>');
|
||||
tmpl_array.push('</div>');
|
||||
|
||||
return _.template(tmpl_array.join(''));
|
||||
},
|
||||
|
||||
});
|
||||
|
||||
return {
|
||||
GroupListView: GroupListView
|
||||
};
|
||||
|
||||
});
|
||||
@@ -0,0 +1,36 @@
|
||||
define([],
|
||||
function() {
|
||||
|
||||
// toolshed group row view
|
||||
var GroupListRowView = Backbone.View.extend({
|
||||
events: {},
|
||||
|
||||
initialize : function( options ){
|
||||
this.render( options.group );
|
||||
},
|
||||
|
||||
render: function( group ){
|
||||
var tmpl = this.templateRow();
|
||||
this.setElement(tmpl( { group:group } ));
|
||||
this.$el.show();
|
||||
return this;
|
||||
},
|
||||
|
||||
templateRow: function() {
|
||||
return _.template([
|
||||
'<tr class="" data-id="<%- group.get("id") %>">',
|
||||
'<td><a href="groups#/<%= group.get("id") %>"><%= group.get("name") %></a></td>',
|
||||
'<td>description</td>',
|
||||
'<td><%= group.get("total_members") %></td>',
|
||||
'<td><%= group.get("total_repos") %></td>',
|
||||
'</tr>'
|
||||
].join(''));
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
return {
|
||||
GroupListRowView: GroupListRowView
|
||||
};
|
||||
|
||||
});
|
||||
@@ -0,0 +1,22 @@
|
||||
define([], function() {
|
||||
|
||||
// ============================================================================
|
||||
// LIBRARY RELATED MODELS
|
||||
|
||||
var Group = Backbone.Model.extend({
|
||||
urlRoot: '/api/groups',
|
||||
});
|
||||
|
||||
var Groups = Backbone.Collection.extend({
|
||||
url: '/api/groups',
|
||||
|
||||
model: Group,
|
||||
|
||||
});
|
||||
|
||||
return {
|
||||
Group: Group,
|
||||
Groups: Groups
|
||||
};
|
||||
|
||||
});
|
||||
@@ -0,0 +1,51 @@
|
||||
// MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM
|
||||
// === MAIN TOOLSHED GROUP MODULE ====
|
||||
// MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM
|
||||
|
||||
define([
|
||||
"mvc/groups/group-list-view",
|
||||
"mvc/groups/group-detail-view",
|
||||
"mvc/groups/group-model"
|
||||
],
|
||||
function(
|
||||
mod_group_list,
|
||||
mod_group_detail,
|
||||
mod_group_model
|
||||
) {
|
||||
|
||||
// ============================================================================
|
||||
// ROUTER
|
||||
var ToolshedRouter = Backbone.Router.extend({
|
||||
routes: {
|
||||
"" : "groups",
|
||||
":group_id" : "group_page"
|
||||
}
|
||||
|
||||
});
|
||||
|
||||
var ToolshedGroups = Backbone.View.extend({
|
||||
groupListView: null,
|
||||
groupDetailView: null,
|
||||
collection: null,
|
||||
|
||||
initialize : function(){
|
||||
window.globalTS.groups = this;
|
||||
|
||||
this.ts_router = new ToolshedRouter();
|
||||
this.ts_router.on( 'route:groups', function() {
|
||||
window.globalTS.groups.groupListView = new mod_group_list.GroupListView();
|
||||
});
|
||||
|
||||
this.ts_router.on( 'route:group_page', function( group_id ) {
|
||||
window.globalTS.groups.groupDetailView = new mod_group_detail.GroupDetailView( { group_id: group_id } );
|
||||
});
|
||||
|
||||
Backbone.history.start({pushState: false});
|
||||
}
|
||||
});
|
||||
|
||||
return {
|
||||
ToolshedGroups: ToolshedGroups
|
||||
};
|
||||
|
||||
});
|
||||
@@ -818,8 +818,7 @@ class GalaxyWebTransaction( base.DefaultWebTransaction,
|
||||
template = template_lookup.get_template( filename )
|
||||
template.output_encoding = 'utf-8'
|
||||
|
||||
data = dict( caller=self, t=self, trans=self, h=helpers, util=util,
|
||||
request=self.request, response=self.response, app=self.app )
|
||||
data = dict( caller=self, t=self, trans=self, h=helpers, util=util, request=self.request, response=self.response, app=self.app )
|
||||
data.update( self.template_context )
|
||||
data.update( kwargs )
|
||||
return template.render( **data )
|
||||
|
||||
@@ -3,8 +3,10 @@ import os
|
||||
|
||||
from galaxy import util
|
||||
from galaxy import web
|
||||
from galaxy.util import pretty_print_time_interval
|
||||
from galaxy.exceptions import RequestParameterMissingException
|
||||
from galaxy.exceptions import AdminRequiredException
|
||||
from galaxy.exceptions import ObjectNotFound
|
||||
from galaxy.web import require_admin as require_admin
|
||||
from galaxy.web import _future_expose_api as expose_api
|
||||
from galaxy.web import _future_expose_api_anonymous as expose_api_anonymous
|
||||
@@ -37,29 +39,12 @@ class GroupsController( BaseAPIController ):
|
||||
|
||||
Example: GET localhost:9009/api/groups
|
||||
"""
|
||||
model = trans.app.model
|
||||
group_dicts = []
|
||||
deleted = util.asbool( deleted )
|
||||
if deleted and not trans.user_is_admin():
|
||||
raise AdminRequiredException( 'Only administrators can query deleted groups.' )
|
||||
for group in self.group_manager.list( trans ):
|
||||
group_dict = group.to_dict( view='collection', value_mapper=self.__get_value_mapper( trans ) )
|
||||
group_members = []
|
||||
for uga in group.users:
|
||||
member = ( trans.sa_session.query( model.User ).filter( model.User.table.c.id == uga.user_id ).one() )
|
||||
member_repositories = []
|
||||
for repo in trans.sa_session.query( model.Repository ) \
|
||||
.filter( model.Repository.table.c.user_id == uga.user_id ) \
|
||||
.join( model.RepositoryMetadata.table ) \
|
||||
.join( model.User.table ) \
|
||||
.outerjoin( model.RepositoryCategoryAssociation.table ) \
|
||||
.outerjoin( model.Category.table ):
|
||||
member_repositories.append( { 'name': repo.name, 'times_downloaded': repo.times_downloaded } )
|
||||
|
||||
member_dict = { 'username' : member.username, 'repositories': member_repositories }
|
||||
group_members.append( member_dict )
|
||||
group_dict[ 'members' ] = group_members
|
||||
group_dicts.append( group_dict )
|
||||
for group in self.group_manager.list( trans, deleted ):
|
||||
group_dicts.append( self._populate( trans, group ) )
|
||||
return group_dicts
|
||||
|
||||
@expose_api
|
||||
@@ -83,8 +68,7 @@ class GroupsController( BaseAPIController ):
|
||||
description = payload.get( 'description', '' )
|
||||
if not description:
|
||||
description = ''
|
||||
# TODO check existence
|
||||
# if suc.get_category_by_name( trans.app, name ):
|
||||
# TODO check group existence
|
||||
# raise exceptions.Conflict( 'A category with that name already exists.' )
|
||||
else:
|
||||
# Create the group
|
||||
@@ -98,7 +82,7 @@ class GroupsController( BaseAPIController ):
|
||||
return group_dict
|
||||
|
||||
@expose_api_anonymous_and_sessionless
|
||||
def show( self, trans, id, **kwd ):
|
||||
def show( self, trans, encoded_id, **kwd ):
|
||||
"""
|
||||
GET /api/groups/{encoded_group_id}
|
||||
Return a dictionary of information about a group.
|
||||
@@ -107,12 +91,52 @@ class GroupsController( BaseAPIController ):
|
||||
|
||||
Example: GET localhost:9009/api/groups/f9cad7b01a472135
|
||||
"""
|
||||
# TODO write get group utility function
|
||||
group = suc.get_group( trans.app, id )
|
||||
decoded_id = trans.security.decode_id( encoded_id )
|
||||
group = self.group_manager.get( trans, decoded_id )
|
||||
if group is None:
|
||||
group_dict = dict( message = 'Unable to locate group record for id %s.' % ( str( id ) ), status = 'error' )
|
||||
return group_dict
|
||||
group_dict = group.to_dict( view='element', value_mapper=self.__get_value_mapper( trans ) )
|
||||
raise ObjectNotFound( 'Unable to locate group record for id %s.' % ( str( encoded_id ) ) )
|
||||
return self._populate( trans, group )
|
||||
|
||||
def _populate( self, trans, group ):
|
||||
"""
|
||||
Turn the given group information from DB into a dict
|
||||
and add other characteristics like members and repositories.
|
||||
"""
|
||||
model = trans.app.model
|
||||
group_dict = group.to_dict( view='collection', value_mapper=self.__get_value_mapper( trans ) )
|
||||
group_members = []
|
||||
group_repos = []
|
||||
total_downloads = 0
|
||||
for uga in group.users:
|
||||
user = trans.sa_session.query( model.User ).filter( model.User.table.c.id == uga.user_id ).one()
|
||||
user_repos_count = 0
|
||||
for repo in trans.sa_session.query( model.Repository ) \
|
||||
.filter( model.Repository.table.c.user_id == uga.user_id ) \
|
||||
.join( model.RepositoryMetadata.table ) \
|
||||
.join( model.User.table ) \
|
||||
.outerjoin( model.RepositoryCategoryAssociation.table ) \
|
||||
.outerjoin( model.Category.table ):
|
||||
time_repo_created = pretty_print_time_interval( repo.create_time, True )
|
||||
approved = ''
|
||||
ratings = []
|
||||
for review in repo.reviews:
|
||||
if review.rating:
|
||||
ratings.append( review.rating )
|
||||
if review.approved == 'yes':
|
||||
approved = 'yes'
|
||||
# TODO add user ratings
|
||||
ratings_mean = str( float( sum( ratings ) ) / len( ratings ) ) if len( ratings ) > 0 else ''
|
||||
total_downloads += repo.times_downloaded
|
||||
group_repos.append( { 'name': repo.name, 'times_downloaded': repo.times_downloaded, 'owner': repo.user.username, 'time_created': time_repo_created, 'description': repo.description, 'approved': approved, 'ratings_mean': ratings_mean, 'tools': 'unknown' } )
|
||||
user_repos_count += 1
|
||||
encoded_user_id = trans.app.security.encode_id( repo.user.id )
|
||||
user_repos_url = web.url_for( controller='repository', action='browse_repositories_by_user', user_id=encoded_user_id )
|
||||
time_created = pretty_print_time_interval( user.create_time, True )
|
||||
member_dict = { 'id': encoded_user_id, 'username': user.username, 'user_repos_url': user_repos_url, 'user_repos_count': user_repos_count, 'user_tools_count': 'unknown', 'time_created': time_created }
|
||||
group_members.append( member_dict )
|
||||
group_dict[ 'members' ] = group_members
|
||||
group_dict[ 'total_members' ] = len( group_members )
|
||||
group_dict[ 'repositories' ] = group_repos
|
||||
group_dict[ 'total_repos' ] = len( group_repos )
|
||||
group_dict[ 'total_downloads' ] = total_downloads
|
||||
return group_dict
|
||||
|
||||
|
||||
|
||||
@@ -91,6 +91,11 @@ def app_factory( global_conf, **kwargs ):
|
||||
controller='groups',
|
||||
action='index',
|
||||
conditions=dict( method=[ "GET" ] ) )
|
||||
webapp.mapper.connect( 'group',
|
||||
'/api/groups/:encoded_id',
|
||||
controller='groups',
|
||||
action='show',
|
||||
conditions=dict( method=[ "GET" ] ) )
|
||||
webapp.mapper.connect( 'repo_search',
|
||||
'/api/search/',
|
||||
controller='search',
|
||||
|
||||
@@ -0,0 +1,22 @@
|
||||
import logging
|
||||
from galaxy import model, util
|
||||
from galaxy import web
|
||||
from galaxy.model.orm import and_, not_, or_
|
||||
from galaxy.web.base.controller import BaseUIController
|
||||
from galaxy.web.framework.helpers import escape, grids
|
||||
|
||||
log = logging.getLogger( __name__ )
|
||||
|
||||
|
||||
class Group( BaseUIController ):
|
||||
|
||||
@web.expose
|
||||
def index( self, trans, **kwd ):
|
||||
# define app configuration for generic mako template
|
||||
app = {
|
||||
'jscript' : "toolshed.groups"
|
||||
}
|
||||
return trans.fill_template( '/webapps/tool_shed/group/index.mako',
|
||||
config = {
|
||||
'title': 'Tool Shed Groups',
|
||||
'app': app } )
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"group-detail-view.js","sources":["../../../src/mvc/groups/group-detail-view.js"],"names":["define","mod_toastr","mod_group_model","GroupDetailView","Backbone","View","extend","el","options","app","initialize","this","_","window","globalTS","groups","collection","model","get","group_id","render","fetchGroup","that","Group","id","fetch","success","console","log","error","response","responseJSON","err_msg","template","templateRow","$el","html","group","$","tooltip","join"],"mappings":"AAAAA,QACI,cACA,0BAEJ,SACIC,EACAC,GAIJ,GAAIC,GAAkBC,SAASC,KAAKC,QAChCC,GAAI,kBACJC,WACAC,IAAK,KAELC,WAAa,SAAUF,GACnBG,KAAKH,QAAUI,EAAEN,OAAQK,KAAKH,QAASA,GACvCG,KAAKF,IAAMI,OAAOC,SAASC,OAEE,OAAxBJ,KAAKF,IAAIO,YACVL,KAAKM,MAAQN,KAAKF,IAAIO,WAAWE,IAAKP,KAAKH,QAAQW,UACnDR,KAAKS,UAELT,KAAKU,cAKbA,WAAY,SAAUb,GAClB,GAAIc,GAAOX,IACXA,MAAKH,QAAUI,EAAEN,OAAQK,KAAKH,QAASA,GACvCG,KAAKM,MAAQ,GAAIf,GAAgBqB,OAASC,GAAIb,KAAKH,QAAQW,WAC3DR,KAAKM,MAAMQ,OACTC,QAAS,SAAUT,GACjBU,QAAQC,IAAK,mBACbD,QAAQC,IAAKX,GACbK,EAAKF,UAEPS,MAAO,SAAUZ,EAAOa,GAElB7B,EAAW4B,MADyB,mBAA1BC,GAASC,aACDD,EAASC,aAAaC,QAEtB,yBAM9BZ,OAAQ,WACJ,GAAIa,GAAWtB,KAAKuB,aACpBvB,MAAKwB,IAAIC,KAAMH,GAAYI,MAAO1B,KAAKM,SACvCqB,EAAE,yBAAyBC,WAG/BL,YAAa,WACT,MAAOtB,GAAEqB,UACD,QACI,oCACA,mCACA,kMAEA,mBACA,6CACI,UACI,gBACA,wBACA,sBACJ,WACA,UACI,wDACA,OACI,OACI,yBACJ,QACA,OACI,gPACJ,QACA,OACI,6BACJ,QACJ,QACA,YACJ,WACJ,WAEA,wBACA,6CACI,UACI,gBACA,uBACA,qBACA,iBACA,mBACA,kBACA,oBACJ,WACA,UACI,2DACA,OACI,OACI,6KACJ,QACA,OACI,0BACJ,QACA,OACI,+BACJ,QACA,OACI,oBACJ,QACA,OACI,2BACJ,QACA,OACI,2BACJ,QACA,OACI,uBACJ,QACJ,QACA,YACJ,WACJ,WACJ,UACNO,KAAK,OAGf,QACIrC,gBAAiBA"}
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"group-groupdetail-view.js","sources":["../../../src/mvc/groups/group-groupdetail-view.js"],"names":["define","GroupDetailView","Backbone","View","extend","events","initialize","group","this","render","tmpl","templateRow","setElement","$el","show","_","template","join"],"mappings":"AAAAA,UACA,WAGA,GAAIC,GAAkBC,SAASC,KAAKC,QAChCC,UAGAC,WAAa,SAAUC,GACnBC,KAAKC,OAAQF,IAGjBE,OAAQ,SAAUF,GACd,GAAIG,GAAOF,KAAKG,aAGhB,OAFAH,MAAKI,WAAWF,GAAQH,MAAMA,KAC9BC,KAAKK,IAAIC,OACFN,MAGXG,YAAa,WACT,MAAOI,GAAEC,UACD,8BACNC,KAAK,OAKf,QACIhB,gBAAiBA"}
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"group-grouprow-view.js","sources":["../../../src/mvc/groups/group-grouprow-view.js"],"names":["define","GroupRowView","Backbone","View","extend","events","initialize","group","this","render","tmpl","templateRow","setElement","$el","show","_","template","join"],"mappings":"AAAAA,UACA,WAGA,GAAIC,GAAeC,SAASC,KAAKC,QAC7BC,UAGAC,WAAa,SAAUC,GACnBC,KAAKC,OAAOF,IAGhBE,OAAQ,SAAUF,GACd,GAAIG,GAAOF,KAAKG,aAIhB,OAFAH,MAAKI,WAAWF,GAAQH,MAAMA,KAC9BC,KAAKK,IAAIC,OACFN,MAaXG,YAAa,WACT,MAAOI,GAAEC,UACD,iDACA,iFACA,uBACA,6CACA,2CACA,SACNC,KAAK,OAKf,QACIhB,aAAcA"}
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"group-list-view.js","sources":["../../../src/mvc/groups/group-list-view.js"],"names":["define","mod_toastr","mod_group_model","mod_group_listrow_view","GroupListView","Backbone","View","extend","el","defaults","initialize","options","this","_","that","window","globalTS","groups","collection","Groups","fetch","success","model","console","log","render","error","response","responseJSON","err_msg","$","hide","template","templateGroupsList","$el","html","length","order","renderRows","models","tooltip","css","groups_to_render","i","group","renderOne","rowView","GroupListRowView","find","append","tmpl_array","push","join"],"mappings":"AAAAA,QACI,cACA,yBACA,iCAED,SACCC,EACAC,EACAC,GAGJ,GAAIC,GAAgBC,SAASC,KAAKC,QAC9BC,GAAI,kBACJC,YAOAC,WAAa,SAAUC,GACnBC,KAAKD,QAAUE,EAAEJ,SAAUG,KAAKD,YAAeC,KAAKH,SAAUE,EAC9D,IAAIG,GAAOF,IACXG,QAAOC,SAASC,OAAOC,WAAa,GAAIhB,GAAgBiB,OACxDJ,OAAOC,SAASC,OAAOC,WAAWE,OAChCC,QAAS,SAAUC,GACjBC,QAAQC,IAAK,mBACbD,QAAQC,IAAKF,GACbR,EAAKW,UAEPC,MAAO,SAAUJ,EAAOK,GAElB1B,EAAWyB,MADyB,mBAA1BC,GAASC,aACDD,EAASC,aAAaC,QAEtB,yBAO9BT,MAAO,aAMPK,OAAQ,SAAWd,GACfC,KAAKD,QAAUE,EAAEN,OAAQK,KAAKD,QAASA,GACvCmB,EAAG,YAAaC,MAChB,IAAIC,GAAWpB,KAAKqB,oBACpBrB,MAAKsB,IAAIC,KAAMH,GAAYI,OAAQ,GAAIC,MAAO,SAC9CzB,KAAK0B,WAAYvB,OAAOC,SAASC,OAAOC,WAAWqB,QACnDT,EAAG,yBAA0BU,UAC7BV,EAAG,WAAYW,IAAK,WAAW,SAOnCH,WAAY,SAAUI,GAClB,IAAM,GAAIC,GAAI,EAAGA,EAAID,EAAiBN,OAAQO,IAAM,CAChD,GAAIC,GAAQF,EAAiBC,EAC7B/B,MAAKiC,WAAaD,MAAOA,MAQjCC,UAAW,SAAUlC,GACjB,GAAImC,GAAU,GAAI3C,GAAuB4C,iBAAkBpC,EAC3DC,MAAKsB,IAAIc,KAAM,oBAAqBC,OAAQH,EAAQtC,KAyCxDyB,mBAAoB,WAuBhB,MAtBAiB,eAEAA,WAAWC,KAAK,qBAChBD,WAAWC,KAAK,UAChBD,WAAWC,KAAK,mDAChBD,WAAWC,KAAK,4BAChBD,WAAWC,KAAK,uCAChBD,WAAWC,KAAK,iBAChBD,WAAWC,KAAK,8CAChBD,WAAWC,KAAK,cAChBD,WAAWC,KAAK,mMAChBD,WAAWC,KAAK,gDAChBD,WAAWC,KAAK,6CAChBD,WAAWC,KAAK,iDAChBD,WAAWC,KAAK,eAChBD,WAAWC,KAAK,mCAEhBD,WAAWC,KAAK,eAChBD,WAAWC,KAAK,YAChBD,WAAWC,KAAK,UAChBD,WAAWC,KAAK,UAETtC,EAAEmB,SAASkB,WAAWE,KAAK,OAK1C,QACIhD,cAAeA"}
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"group-listrow-view.js","sources":["../../../src/mvc/groups/group-listrow-view.js"],"names":["define","GroupListRowView","Backbone","View","extend","events","initialize","options","this","render","group","tmpl","templateRow","setElement","$el","show","_","template","join"],"mappings":"AAAAA,UACA,WAGA,GAAIC,GAAmBC,SAASC,KAAKC,QACjCC,UAEAC,WAAa,SAAUC,GACnBC,KAAKC,OAAQF,EAAQG,QAGzBD,OAAQ,SAAUC,GACd,GAAIC,GAAOH,KAAKI,aAGhB,OAFAJ,MAAKK,WAAWF,GAAQD,MAAMA,KAC9BF,KAAKM,IAAIC,OACFP,MAGXI,YAAa,WACT,MAAOI,GAAEC,UACD,iDACA,iFACA,uBACA,6CACA,2CACA,SACNC,KAAK,OAKf,QACIjB,iBAAkBA"}
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"group-model.js","sources":["../../../src/mvc/groups/group-model.js"],"names":["define","Group","Backbone","Model","extend","urlRoot","Groups","Collection","url","model"],"mappings":"AAAAA,UAAW,WAKP,GAAIC,GAAQC,SAASC,MAAMC,QACzBC,QAAS,gBAGPC,EAASJ,SAASK,WAAWH,QAC/BI,IAAK,cAELC,MAAOR,GAIb,QACIA,MAAOA,EACPK,OAAQA"}
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"group.model.js","sources":["../../../src/mvc/groups/group.model.js"],"names":["define","Group","Backbone","Model","extend","urlRoot","Groups","Collection","url","model"],"mappings":"AAAAA,UAAW,WAKP,GAAIC,GAAQC,SAASC,MAAMC,QACzBC,QAAS,iBAGPC,EAASJ,SAASK,WAAWH,QAC/BI,IAAK,cAELC,MAAOR,GAIb,QACIA,MAAOA,EACPK,OAAQA"}
|
||||
@@ -0,0 +1 @@
|
||||
{"version":3,"file":"toolshed.groups.js","sources":["../src/toolshed.groups.js"],"names":["define","mod_group_list","mod_group_detail","ToolshedRouter","Backbone","Router","extend","routes",":group_id","ToolshedGroups","View","groupListView","groupDetailView","collection","initialize","window","globalTS","groups","this","ts_router","on","GroupListView","group_id","GroupDetailView","history","start","pushState"],"mappings":"AAIAA,QACQ,6BACA,+BACA,0BAEJ,SACIC,EACAC,GAMR,GAAIC,GAAiBC,SAASC,OAAOC,QACjCC,QACI,GAA4B,SAC5BC,YAA4B,gBAKhCC,EAAiBL,SAASM,KAAKJ,QAC/BK,cAAe,KACfC,gBAAiB,KACjBC,WAAY,KAEZC,WAAa,WACTC,OAAOC,SAASC,OAASC,KAEzBA,KAAKC,UAAY,GAAIhB,GACrBe,KAAKC,UAAUC,GAAI,eAAgB,WAC/BL,OAAOC,SAASC,OAAON,cAAgB,GAAIV,GAAeoB,gBAG9DH,KAAKC,UAAUC,GAAI,mBAAoB,SAAUE,GAC7CP,OAAOC,SAASC,OAAOL,gBAAkB,GAAIV,GAAiBqB,iBAAmBD,SAAUA,MAG/FlB,SAASoB,QAAQC,OAAOC,WAAW,MAI3C,QACIjB,eAAgBA"}
|
||||
@@ -0,0 +1,2 @@
|
||||
define(["libs/toastr","mvc/groups/group-model"],function(a,b){var c=Backbone.View.extend({el:"#groups_element",options:{},app:null,initialize:function(a){this.options=_.extend(this.options,a),this.app=window.globalTS.groups,null!==this.app.collection?(this.model=this.app.collection.get(this.options.group_id),this.render()):this.fetchGroup()},fetchGroup:function(c){var d=this;this.options=_.extend(this.options,c),this.model=new b.Group({id:this.options.group_id}),this.model.fetch({success:function(a){console.log("received data: "),console.log(a),d.render()},error:function(b,c){a.error("undefined"!=typeof c.responseJSON?c.responseJSON.err_msg:"An error ocurred.")}})},render:function(){var a=this.templateRow();this.$el.html(a({group:this.model})),$("#center [data-toggle]").tooltip()},templateRow:function(){return _.template(["<div>",'<h3><%= group.get("name") %></h3>','<p class="" style="color:gray;">','A group of <%= group.get("members").length %> members with <%= group.get("repositories").length %> repositories and a total of <%= group.get("total_downloads") %> combined tool downloads.</p>',"<h3>Members</h3>",'<table class="grid table table-condensed">',"<thead>","<th>Name</th>","<th>Repositories</th>","<th>Registered</th>","</thead>","<tbody>",'<% _.each(group.get("members"), function(member) { %>',"<tr>","<td>","<%= member.username %>","</td>","<td>",'<a data-toggle="tooltip" data-placement="top" title="Repositories of <%= member.username %>" href="/repository/browse_repositories_by_user?user_id=<%= member.id %>&use_panels=true" id="<%= member.id %>"><%= member.user_repos_count %></a>',"</td>","<td>","<%= member.time_created %>","</td>","</tr>","<% }); %>","</tbody>","</table>","<h3>Repositories</h3>",'<table class="grid table table-condensed">',"<thead>","<th>Name</th>","<th>Description</th>","<th>Downloads</th>","<th>Owner</th>","<th>Created</th>","<th>Rating</th>","<th>Verified</th>","</thead>","<tbody>",'<% _.each(group.get("repositories"), function(repo) { %>',"<tr>","<td>",'<a data-toggle="tooltip" data-placement="top" title="Details of <%= repo.name %>" href="/view/<%= repo.owner %>/<%= repo.name %>" id="<%= repo.id %>"><%= repo.name %></a>',"</td>","<td>","<%= repo.description %>","</td>","<td>","<%= repo.times_downloaded %>","</td>","<td>","<%= repo.owner %>","</td>","<td>","<%= repo.time_created %>","</td>","<td>","<%= repo.ratings_mean %>","</td>","<td>","<%= repo.approved %>","</td>","</tr>","<% }); %>","</tbody>","</table>","</div>"].join(""))}});return{GroupDetailView:c}});
|
||||
//# sourceMappingURL=../../../maps/mvc/groups/group-detail-view.js.map
|
||||
@@ -0,0 +1,2 @@
|
||||
define([],function(){var a=Backbone.View.extend({events:{},initialize:function(a){this.render(a)},render:function(a){var b=this.templateRow();return this.setElement(b({group:a})),this.$el.show(),this},templateRow:function(){return _.template(["<div>TEST GROUP PAGE</div>"].join(""))}});return{GroupDetailView:a}});
|
||||
//# sourceMappingURL=../../../maps/mvc/groups/group-groupdetail-view.js.map
|
||||
@@ -0,0 +1,2 @@
|
||||
define([],function(){var a=Backbone.View.extend({events:{},initialize:function(a){this.render(a)},render:function(a){var b=this.templateRow();return this.setElement(b({group:a})),this.$el.show(),this},templateRow:function(){return _.template(['<tr class="" data-id="<%- group.get("id") %>">','<td><a href="/groups/<%= group.get("id") %>"><%= group.get("name") %></a></td>',"<td>description</td>",'<td><%= group.get("total_members") %></td>','<td><%= group.get("total_repos") %></td>',"</tr>"].join(""))}});return{GroupRowView:a}});
|
||||
//# sourceMappingURL=../../../maps/mvc/groups/group-grouprow-view.js.map
|
||||
@@ -0,0 +1,2 @@
|
||||
define(["libs/toastr","mvc/groups/group-model","mvc/groups/group-listrow-view"],function(a,b,c){var d=Backbone.View.extend({el:"#groups_element",defaults:{},initialize:function(c){this.options=_.defaults(this.options||{},this.defaults,c);var d=this;window.globalTS.groups.collection=new b.Groups,window.globalTS.groups.collection.fetch({success:function(a){console.log("received data: "),console.log(a),d.render()},error:function(b,c){a.error("undefined"!=typeof c.responseJSON?c.responseJSON.err_msg:"An error ocurred.")}})},fetch:function(){},render:function(a){this.options=_.extend(this.options,a),$(".tooltip").hide();var b=this.templateGroupsList();this.$el.html(b({length:10,order:"asc"})),this.renderRows(window.globalTS.groups.collection.models),$("#center [data-toggle]").tooltip(),$("#center").css("overflow","auto")},renderRows:function(a){for(var b=0;b<a.length;b++){var c=a[b];this.renderOne({group:c})}},renderOne:function(a){var b=new c.GroupListRowView(a);this.$el.find("#group_list_body").append(b.el)},templateGroupsList:function(){return tmpl_array=[],tmpl_array.push('<div id="groups">'),tmpl_array.push("</div>"),tmpl_array.push('<div class="groups_container table-responsive">'),tmpl_array.push("<% if(length === 0) { %>"),tmpl_array.push("<div>There are no groups yet.</div>"),tmpl_array.push("<% } else{ %>"),tmpl_array.push('<table class="grid table table-condensed">'),tmpl_array.push(" <thead>"),tmpl_array.push(' <th style="width:30%;"><a class="sort-groups-link" title="Click to reverse order" href="#">name</a> <span title="Sorted alphabetically" class="fa fa-sort-alpha-<%- order %>"></span></th>'),tmpl_array.push(' <th style="width:22%;">description</th>'),tmpl_array.push(' <th style="width:22%;">members</th> '),tmpl_array.push(' <th style="width:26%;">repositories</th>'),tmpl_array.push(" </thead>"),tmpl_array.push(' <tbody id="group_list_body">'),tmpl_array.push(" </tbody>"),tmpl_array.push("</table>"),tmpl_array.push("<% }%>"),tmpl_array.push("</div>"),_.template(tmpl_array.join(""))}});return{GroupListView:d}});
|
||||
//# sourceMappingURL=../../../maps/mvc/groups/group-list-view.js.map
|
||||
@@ -0,0 +1,2 @@
|
||||
define([],function(){var a=Backbone.View.extend({events:{},initialize:function(a){this.render(a.group)},render:function(a){var b=this.templateRow();return this.setElement(b({group:a})),this.$el.show(),this},templateRow:function(){return _.template(['<tr class="" data-id="<%- group.get("id") %>">','<td><a href="groups#/<%= group.get("id") %>"><%= group.get("name") %></a></td>',"<td>description</td>",'<td><%= group.get("total_members") %></td>','<td><%= group.get("total_repos") %></td>',"</tr>"].join(""))}});return{GroupListRowView:a}});
|
||||
//# sourceMappingURL=../../../maps/mvc/groups/group-listrow-view.js.map
|
||||
@@ -0,0 +1,2 @@
|
||||
define([],function(){var a=Backbone.Model.extend({urlRoot:"/api/groups"}),b=Backbone.Collection.extend({url:"/api/groups",model:a});return{Group:a,Groups:b}});
|
||||
//# sourceMappingURL=../../../maps/mvc/groups/group-model.js.map
|
||||
@@ -0,0 +1,2 @@
|
||||
define([],function(){var a=Backbone.Model.extend({urlRoot:"/api/groups/"}),b=Backbone.Collection.extend({url:"/api/groups",model:a});return{Group:a,Groups:b}});
|
||||
//# sourceMappingURL=../../../maps/mvc/groups/group.model.js.map
|
||||
@@ -0,0 +1,2 @@
|
||||
define(["mvc/groups/group-list-view","mvc/groups/group-detail-view","mvc/groups/group-model"],function(a,b){var c=Backbone.Router.extend({routes:{"":"groups",":group_id":"group_page"}}),d=Backbone.View.extend({groupListView:null,groupDetailView:null,collection:null,initialize:function(){window.globalTS.groups=this,this.ts_router=new c,this.ts_router.on("route:groups",function(){window.globalTS.groups.groupListView=new a.GroupListView}),this.ts_router.on("route:group_page",function(a){window.globalTS.groups.groupDetailView=new b.GroupDetailView({group_id:a})}),Backbone.history.start({pushState:!1})}});return{ToolshedGroups:d}});
|
||||
//# sourceMappingURL=../maps/toolshed.groups.js.map
|
||||
@@ -6,7 +6,6 @@
|
||||
if kwargs.get( 'embedded', False ):
|
||||
# No inheritance - using only embeddable content (self.body)
|
||||
return None
|
||||
|
||||
if context.get('use_panels'):
|
||||
if context.get('webapp'):
|
||||
app_name = context.get('webapp')
|
||||
|
||||
@@ -80,6 +80,9 @@
|
||||
## Repositories tab.
|
||||
${tab( "repositories", "Repositories", h.url_for( controller='/repository', action='index' ) )}
|
||||
|
||||
## Groups tab.
|
||||
${tab( "groups", "Groups", h.url_for( controller='/groups', action='index' ) )}
|
||||
|
||||
## Admin tab.
|
||||
${tab( "admin", "Admin", h.url_for( controller='/admin', action='index' ), extra_class="admin-only", visible=( trans.user and app.config.is_admin_user( trans.user ) ) )}
|
||||
|
||||
|
||||
@@ -0,0 +1,50 @@
|
||||
<%inherit file="/webapps/tool_shed/base_panels.mako"/>
|
||||
<%namespace file="/message.mako" import="render_msg" />
|
||||
|
||||
<%def name="stylesheets()">
|
||||
## Include "base.css" for styling tool menu and forms (details)
|
||||
${h.css( "base", "autocomplete_tagging", "tool_menu" )}
|
||||
|
||||
## But make sure styles for the layout take precedence
|
||||
${parent.stylesheets()}
|
||||
|
||||
<style type="text/css">
|
||||
body { margin: 0; padding: 0; overflow: hidden; }
|
||||
#left {
|
||||
background: #C1C9E5 url(${h.url_for('/static/style/menu_bg.png')}) top repeat-x;
|
||||
}
|
||||
.unified-panel-body {
|
||||
overflow: auto;
|
||||
}
|
||||
.toolMenu {
|
||||
margin-left: 10px;
|
||||
}
|
||||
</style>
|
||||
</%def>
|
||||
|
||||
|
||||
<%def name="javascripts()">
|
||||
${parent.javascripts()}
|
||||
</%def>
|
||||
|
||||
<%def name="init()">
|
||||
%if trans.app.config.require_login and not trans.user:
|
||||
<script type="text/javascript">
|
||||
if ( window != top ) {
|
||||
top.location.href = location.href;
|
||||
}
|
||||
</script>
|
||||
%endif
|
||||
</%def>
|
||||
|
||||
<%def name="center_panel()">
|
||||
<script type="text/javascript">
|
||||
window.globalTS = new Object();
|
||||
$( function(){
|
||||
require([ '${config.get( "app" ).get( "jscript" )}' ], function( groups ){
|
||||
app = new groups.ToolshedGroups();
|
||||
});
|
||||
});
|
||||
</script>
|
||||
<div id="groups_element" style="width: 95%; margin:auto; margin-top:2em; "></div>
|
||||
</%def>
|
||||
Reference in New Issue
Block a user