Skip to content

Commit 18c5e4c

Browse files
committed
Embed Spaces/Datasets/Collections viewer into user profile page
1 parent b41a2a1 commit 18c5e4c

File tree

8 files changed

+174
-104
lines changed

8 files changed

+174
-104
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
1010
[CATS-1044](https://opensource.ncsa.illinois.edu/jira/browse/CATS-1044)
1111
- API add tags endpoint now returns the added tags.
1212
[CATS-1053](https://opensource.ncsa.illinois.edu/jira/browse/CATS-1053)
13+
- List Spaces/Datasets/Collections created by each user on their User Profile.
14+
[CATS-1056](https://opensource.ncsa.illinois.edu/jira/browse/CATS-1056)
1315

1416
### Fixed
1517
- Ability to delete tags on file page.

app/controllers/Profile.scala

Lines changed: 23 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -53,17 +53,31 @@ class Profile @Inject() (users: UserService, files: FileService, datasets: Datas
5353
val viewerUser = request.user
5454
val muser = users.findById(uuid)
5555

56-
muser match {
57-
case Some(existingUser) => {
58-
val (ownProfile, keys) = viewerUser match {
59-
case Some(loggedInUser) if loggedInUser.id == existingUser.id => {
60-
(true, users.getUserKeys(loggedInUser.identityId))
61-
}
62-
case _ => (false, List.empty[UserApiKey])
63-
}
56+
viewerUser match {
57+
case Some(viewer) => {
58+
muser match {
59+
case Some(existingUser) => {
60+
val (ownProfile, keys) = viewerUser match {
61+
case Some(loggedInUser) if loggedInUser.id == existingUser.id => {
62+
(true, users.getUserKeys(loggedInUser.identityId))
63+
}
64+
case _ => (false, List.empty[UserApiKey])
65+
}
6466

65-
Ok(views.html.profile(existingUser, keys, ownProfile))
67+
val showAll = false
68+
val limit = 12
69+
val spacesList = spaces.listUser(limit, muser, showAll, viewer)
70+
val datasetsList = datasets.listUser(limit, muser, showAll, viewer)
71+
val collectionsList = collections.listUser(limit, muser, showAll, viewer)
6672

73+
Ok(views.html.profile(existingUser, keys, spacesList, datasetsList, collectionsList, ownProfile))
74+
75+
}
76+
case None => {
77+
Logger.error("no user model exists for " + uuid.stringify)
78+
BadRequest(views.html.notFound("User does not exist in this " + AppConfiguration.getDisplayName + " instance."))
79+
}
80+
}
6781
}
6882
case None => {
6983
Logger.error("no user model exists for " + uuid.stringify)
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
2+
@(profile: User, collectionsList: List[Collection], deletePermission: Boolean,
3+
ownProfile: Option[Boolean], userSelections: List[String])(implicit user: Option[models.User])
4+
5+
6+
<div class="row top-padding">
7+
<div class="col-xs-12">
8+
<p>@Messages("collection.list.message", Messages("collections.title").toLowerCase, Messages("datasets.title").toLowerCase )</p>
9+
</div>
10+
<div class="col-xs-6">
11+
</div>
12+
<div class="col-xs-6">
13+
<span class="pull-right">
14+
<a href="@routes.Collections.list("","",12, None, "", Some(profile.id.stringify))">See More</a>
15+
</span>
16+
</div>
17+
</div>
18+
<div class="row" id ="masonry-collections">
19+
@collectionsList.map { collection =>
20+
@collections.tile(collection, routes.Application.index(), None, "col-xs-3", false)
21+
}
22+
</div>
23+
@if(collectionsList.size < 1) {
24+
<div class="text-center">
25+
<div>@Messages("home.empty.message", Messages("collections.title").toLowerCase) </div>
26+
27+
<div> <a class="btn-link" href="@routes.Collections.newCollection(None)" title="Create a new @Messages("collection.title")">@Messages("create.title", Messages("collection.title"))</a></div>
28+
</div>
29+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
2+
@(profile: User, datasetsList: List[Dataset], deletePermission: Boolean,
3+
ownProfile: Option[Boolean], userSelections: List[String])(implicit user: Option[models.User])
4+
5+
6+
<div class="row top-padding">
7+
<div class="col-xs-12">
8+
<p>@Messages("dataset.list.message", Messages("datasets.title").toLowerCase, Messages("dataset.title").toLowerCase) </p>
9+
</div>
10+
<div class="col-xs-6">
11+
</div>
12+
<div class="col-xs-6">
13+
<span class="pull-right"><a href="@routes.Datasets.list("","",12, None, None, "", Some(profile.id.stringify))">See More</a></span>
14+
</div>
15+
</div>
16+
<div class="row" id="masonry-datasets">
17+
@datasetsList.map { dataset =>
18+
@if(userSelections.indexOf(dataset.id.toString()) != -1) {
19+
@datasets.tile(dataset, None, "col-xs-3", false, false, routes.Application.index(), true)
20+
} else {
21+
@datasets.tile(dataset, None, "col-xs-3", false, false, routes.Application.index(), false)
22+
}
23+
24+
}
25+
</div>
26+
@if(datasetsList.size < 1) {
27+
<div class="text-center">
28+
<div>@Messages("home.empty.message", Messages("datasets.title").toLowerCase) </div>
29+
<div> <a class="btn-link" href="@routes.Datasets.newDataset(None, None)" title="Create a new @Messages("dataset.title")">@Messages("create.title", Messages("dataset.title"))</a></div>
30+
</div>
31+
}
32+

app/views/home.scala.html

Lines changed: 3 additions & 74 deletions
Original file line numberDiff line numberDiff line change
@@ -56,86 +56,15 @@ <h2>@profile.fullName</h2>
5656
</div>
5757
<div role="tabpanel" class="tab-pane" id="spaces">
5858
@* spaces *@
59-
<div class="row top-padding">
60-
<div class="col-xs-12">
61-
<p>@Messages("space.list.message", Messages("spaces.title"))</p>
62-
</div>
63-
<div class="col-xs-6">
64-
</div>
65-
<div class="col-xs-6">
66-
<span class="pull-right">
67-
<a href="@routes.Spaces.list("","",12, "", Some(profile.id.stringify))">See More</a>
68-
</span>
69-
</div>
70-
</div>
71-
<div class="row" id="masonry-spaces">
72-
@spacesList.map { space =>
73-
@spaces.tile(space, "col-xs-3", routes.Application.index(), false)
74-
}
75-
</div>
76-
@if(spacesList.size < 1) {
77-
<div class="text-center">
78-
<div>@Messages("home.empty.message", Messages("spaces.title")) </div>
79-
80-
<div> <a class="btn-link" href="@routes.Spaces.newSpace()" title="Create a new @Messages("space.title")">@Messages("create.title", Messages("space.title"))</a></div>
81-
</div>
82-
}
59+
@views.html.spaces.miniList(profile, spacesList, deletePermission, ownProfile, userSelections)
8360
</div>
8461
<div role="tabpanel" class="tab-pane" id="datasets">
8562
@* datasets *@
86-
<div class="row top-padding">
87-
<div class="col-xs-12">
88-
<p>@Messages("dataset.list.message", Messages("datasets.title").toLowerCase, Messages("dataset.title").toLowerCase) </p>
89-
</div>
90-
<div class="col-xs-6">
91-
</div>
92-
<div class="col-xs-6">
93-
<span class="pull-right"><a href="@routes.Datasets.list("","",12, None, None, "", Some(profile.id.stringify))">See More</a></span>
94-
</div>
95-
</div>
96-
<div class="row" id="masonry-datasets">
97-
@datasetsList.map { dataset =>
98-
@if(userSelections.indexOf(dataset.id.toString()) != -1) {
99-
@datasets.tile(dataset, None, "col-xs-3", false, false, routes.Application.index(), true)
100-
} else {
101-
@datasets.tile(dataset, None, "col-xs-3", false, false, routes.Application.index(), false)
102-
}
103-
104-
}
105-
</div>
106-
@if(datasetsList.size < 1) {
107-
<div class="text-center">
108-
<div>@Messages("home.empty.message", Messages("datasets.title").toLowerCase) </div>
109-
<div> <a class="btn-link" href="@routes.Datasets.newDataset(None, None)" title="Create a new @Messages("dataset.title")">@Messages("create.title", Messages("dataset.title"))</a></div>
110-
</div>
111-
}
63+
@views.html.datasets.miniList(profile, datasetsList, deletePermission, ownProfile, userSelections)
11264
</div>
11365
<div role="tabpanel" class="tab-pane" id="collections">
11466
@* collections *@
115-
<div class="row top-padding">
116-
<div class="col-xs-12">
117-
<p>@Messages("collection.list.message", Messages("collections.title").toLowerCase, Messages("datasets.title").toLowerCase )</p>
118-
</div>
119-
<div class="col-xs-6">
120-
</div>
121-
<div class="col-xs-6">
122-
<span class="pull-right">
123-
<a href="@routes.Collections.list("","",12, None, "", Some(profile.id.stringify))">See More</a>
124-
</span>
125-
</div>
126-
</div>
127-
<div class="row" id ="masonry-collections">
128-
@collectionsList.map { collection =>
129-
@collections.tile(collection, routes.Application.index(), None, "col-xs-3", false)
130-
}
131-
</div>
132-
@if(collectionsList.size < 1) {
133-
<div class="text-center">
134-
<div>@Messages("home.empty.message", Messages("collections.title").toLowerCase) </div>
135-
136-
<div> <a class="btn-link" href="@routes.Collections.newCollection(None)" title="Create a new @Messages("collection.title")">@Messages("create.title", Messages("collection.title"))</a></div>
137-
</div>
138-
}
67+
@views.html.collections.miniList(profile, collectionsList, deletePermission, ownProfile, userSelections)
13968
</div>
14069
<div role="tabpanel" class="tab-pane" id="followers">
14170
<div class="row top-padding">

app/views/profile.scala.html

Lines changed: 56 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1-
@(profile: User, keys: List[UserApiKey], ownProfile: Boolean)(implicit user: Option[models.User] = None)
1+
@(profile: User, keys: List[UserApiKey], spacesList: List[models.ProjectSpace],
2+
datasetsList: List[models.Dataset], collectionsList: List[models.Collection],
3+
ownProfile: Boolean)(implicit user: Option[models.User] = None)
24
@main("Profile") {
35
<script src="@routes.Application.javascriptRoutes" type="text/javascript"></script>
46
<script src="@routes.Assets.at("javascripts/recommendation.js")" type="text/javascript"></script>
@@ -143,36 +145,70 @@ <h4>Past Projects</h4>
143145
@if(ownProfile && play.api.Play.current.plugin[services.StagingAreaPlugin].isDefined) {
144146
<div class="profile-disclaimer small">@play.api.i18n.Messages("profile.disclaimer")</div>
145147
}
146-
@if(ownProfile) {
147-
<h4 id="userkeys">User API Keys</h4>
148-
<span>Create your personal API keys by providing a name for the key and clicking the Add button. Key names have to be unique per user.</span>
149-
<div class="row wrapped" id="key-">
150-
<div class="col-md-1"></div>
151-
<div class="col-md-2">Name</div>
152-
<div class="col-md-9">Key</div>
148+
</div>
149+
150+
<div class="col-md-9 col-lg-9 col-sm-7">
151+
<!-- Nav tabs -->
152+
<ul class="nav nav-tabs" role="tablist">
153+
<li role="presentation" class="active"><a href="#spaces" aria-controls="spaces" role="tab" data-toggle="tab"><b>Spaces</b></a></li>
154+
<li role="presentation"><a href="#datasets" aria-controls="datasets" role="tab" data-toggle="tab"><b>Datasets</b></a></li>
155+
<li role="presentation"><a href="#collections" aria-controls="collections" role="tab" data-toggle="tab"><b>Collections</b></a></li>
156+
157+
@if(ownProfile) {
158+
<li role="presentation"><a href="#apikeys" aria-controls="apikeys" role="tab" data-toggle="tab"><b>
159+
API Keys</b></a></li>
160+
}
161+
</ul>
162+
163+
<!-- Tab panes -->
164+
<div class="tab-content">
165+
<!-- Spaces tab -->
166+
<div role="tabpanel" class="tab-pane active" id="spaces">
167+
@views.html.spaces.miniList(profile, spacesList, false, Some(ownProfile), List.empty)
168+
</div>
169+
170+
<!-- Datasets tab -->
171+
<div role="tabpanel" class="tab-pane" id="datasets">
172+
@views.html.datasets.miniList(profile, datasetsList, false, Some(ownProfile), List.empty)
173+
</div>
174+
175+
<!-- Collections tab -->
176+
<div role="tabpanel" class="tab-pane" id="collections">
177+
@views.html.collections.miniList(profile, collectionsList, false, Some(ownProfile), List.empty)
153178
</div>
154-
@keys.map{key =>
155-
<div class="row wrapped" id="[email protected]">
156-
<div class="col-md-1">
179+
180+
<!-- API Keys tab -->
181+
<div role="tabpanel" class="tab-pane" id="apikeys">
182+
<h4 id="userkeys">User API Keys</h4>
183+
<span>Create your personal API keys by providing a name for the key and clicking the Add button. Key names have to be unique per user.</span>
184+
<div class="row wrapped" id="key-">
185+
<div class="col-md-1"></div>
186+
<div class="col-md-2">Name</div>
187+
<div class="col-md-9">Key</div>
188+
</div>
189+
190+
@keys.map{key =>
191+
<div class="row wrapped" id="[email protected]">
192+
<div class="col-md-1">
157193
@if(key.name.startsWith("_")) {
158194
<span class="glyphicon glyphicon-trash"
159-
title="System API keys start with and underscore and connot be deleted from the user interface"></span>
195+
title="System API keys start with and underscore and connot be deleted from the user interface"></span>
160196
} else {
161197
<a href='javascript:deleteUserKey("@key.name");' title="Delete this user API key">
162198
<span class="glyphicon glyphicon-trash"></span></a>
163199
}
200+
</div>
201+
<div class="col-md-2">@key.name</div>
202+
<div class="col-md-9">@key.key</div>
164203
</div>
165-
<div class="col-md-2">@key.name</div>
166-
<div class="col-md-9">@key.key</div>
204+
}
205+
<div class="row wrapped">
206+
<div class="col-md-1"><a href='javascript:addUserKey();'><span class="glyphicon glyphicon-plus"></span> Add</a></div>
207+
<div class="col-md-2"><input type="text" id="userkeyname" class="form-control"></div>
167208
</div>
168-
}
169-
<div class="row wrapped">
170-
<div class="col-md-1"><a href='javascript:addUserKey();'><span class="glyphicon glyphicon-plus"></span> Add</a></div>
171-
<div class="col-md-2"><input type="text" id="userkeyname" class="form-control"></div>
172209
</div>
173-
}
210+
</div>
174211
</div>
175-
176212
</div>
177213

178214
<script language="javascript">
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
2+
@(profile: User, spacesList: List[ProjectSpace], deletePermission: Boolean,
3+
ownProfile: Option[Boolean], userSelections: List[String])(implicit user: Option[models.User])
4+
5+
<div class="row top-padding">
6+
<div class="col-xs-12">
7+
<p>@Messages("space.list.message", Messages("spaces.title"))</p>
8+
</div>
9+
<div class="col-xs-6">
10+
</div>
11+
<div class="col-xs-6">
12+
<span class="pull-right">
13+
<a href="@routes.Spaces.list("","",12, "", Some(profile.id.stringify))">See More</a>
14+
</span>
15+
</div>
16+
</div>
17+
<div class="row" id="masonry-spaces">
18+
@spacesList.map { space =>
19+
@spaces.tile(space, "col-xs-3", routes.Application.index(), false)
20+
}
21+
</div>
22+
@if(spacesList.size < 1) {
23+
<div class="text-center">
24+
<div>@Messages("home.empty.message", Messages("spaces.title")) </div>
25+
26+
<div> <a class="btn-link" href="@routes.Spaces.newSpace()" title="Create a new @Messages("space.title")">@Messages("create.title", Messages("space.title"))</a></div>
27+
</div>
28+
}

app/views/spaces/tile.scala.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ <h4 class="no-overflow oneline"><a href="@routes.Spaces.getSpace(space.id)">@spa
3737

3838
<!-- If user can view, the search button is enabled, otherwise the button is present but disabled to provide consistent UE. -->
3939
@if(Permission.checkPermission(Permission.ViewSpace, ResourceRef(ResourceRef.space, space.id)) || user.get.identityId.userId.equals(space.creator)){
40-
<a href="@routes.Metadata.search()[email protected]" class="btn btn-link pull-right" title="Search metadata within the @Messages("space.title")">
40+
<a href="@routes.Metadata.search()[email protected]" class="btn btn-link pull-right" style="display:contents" title="Search metadata within the @Messages("space.title")">
4141
<span class="glyphicon glyphicon-search"></span>
4242
</a>
4343
} else {

0 commit comments

Comments
 (0)