Skip to content

Commit 00fd975

Browse files
User is able to select the personal access token page via a new user menu (#488)
* Replace button bar with datamanagermenu class * remove duplicate logout handler logic * Extend userdetails to provide fullname for Avatar abbreviation within user menu * Adjust layout extension so navbars are configured correctly * Address code smell * Adjust method name for readability Co-authored-by: Sven F. <[email protected]> * adjust method call as well --------- Co-authored-by: Sven F. <[email protected]>
1 parent be0a7b0 commit 00fd975

File tree

13 files changed

+166
-255
lines changed

13 files changed

+166
-255
lines changed

project-management/src/main/java/life/qbic/projectmanagement/application/authorization/QbicUserDetails.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,10 @@ public String getUsername() {
5757
return user.id();
5858
}
5959

60+
public String fullName() {
61+
return user.fullName();
62+
}
63+
6064
@Override
6165
public boolean isAccountNonExpired() {
6266
return true;

user-interface/frontend/themes/datamanager/components/navbar.css

Lines changed: 40 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,48 +1,68 @@
1-
.project-navbar {
2-
width: 100%;
1+
.data-manager-layout::part(navbar) {
32
display: inline-flex;
4-
align-items: start;
53
justify-content: space-between;
64
}
75

8-
.project-navbar-buttonbar {
6+
.data-manager-layout .data-manager-title {
7+
font-size: var(--lumo-font-size-l);
8+
margin: var(--lumo-space-m);
9+
color: var(--lumo-header-text-color);
10+
font-weight: 600;
11+
line-height: var(--lumo-line-height-xs);
12+
margin-block: 0;
13+
padding-inline: var(--lumo-space-m);
14+
}
15+
16+
.data-manager-menu {
917
display: inline-flex;
10-
gap: var(--lumo-space-m);
11-
align-items: center;
18+
justify-content: space-between;
19+
column-gap: var(--lumo-space-s);
1220
}
1321

14-
.project-navbar-drawer-bar {
22+
/*Increase gap between menu items*/
23+
.data-manager-menu .menubar::part(container) {
1524
display: inline-flex;
16-
align-items: center;
25+
column-gap: var(--lumo-space-s);
1726
}
1827

19-
.project-navbar-title {
20-
font-weight: bold;
21-
font-size: var(--lumo-font-size-l);
28+
.data-manager-menu .user-avatar {
29+
cursor: pointer;
2230
}
2331

24-
.experiment-app-navbar {
25-
width: 100%;
32+
/*Increase gap between menu items*/
33+
.experiment-main-layout::part(navbar) {
2634
display: flex;
27-
align-items: start;
28-
justify-content: space-between;
29-
background-image: linear-gradient(var(--lumo-shade-5pct), var(--lumo-shade-5pct));
30-
padding: var(--lumo-space-s);
35+
flex-direction: column;
36+
/*Ensure proper padding even if secondary experiment tab based navigation is present*/
37+
padding-top: var(--lumo-space-s);
3138
}
3239

33-
.experiment-navbar {
40+
/*Increase gap between menu items*/
41+
.experiment-main-layout .experiment-app-navbar {
42+
display: inline-flex;
43+
justify-content: space-between;
3444
width: 100%;
3545
}
3646

37-
.experiment-navbar-buttonbar {
47+
.project-main-layout::part(navbar) {
48+
display: inline-flex;
49+
justify-content: space-between;
50+
}
51+
52+
.drawer-title-bar {
3853
display: inline-flex;
39-
gap: var(--lumo-space-m);
4054
align-items: center;
4155
}
4256

57+
.project-navbar-title {
58+
font-weight: bold;
59+
font-size: var(--lumo-font-size-l);
60+
}
61+
4362
.experiment-navbar-drawer-bar {
4463
display: inline-flex;
4564
align-items: center;
65+
justify-content: space-between;
4666
}
4767

4868
.experiment-navbar-title {
Lines changed: 9 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -1,47 +1,22 @@
11
package life.qbic.datamanager.views;
22

33
import com.vaadin.flow.component.applayout.AppLayout;
4-
import com.vaadin.flow.component.html.H1;
5-
import com.vaadin.flow.component.orderedlayout.FlexComponent;
6-
import com.vaadin.flow.component.orderedlayout.HorizontalLayout;
4+
import com.vaadin.flow.component.html.Span;
5+
import com.vaadin.flow.router.PageTitle;
76

87
/**
9-
* <b>Main layout of the app</b>
8+
* <b>Data Manager Layout</b>
109
*
11-
* <p>Defines the look of the header and the project title
10+
* <p>Defines the basic look of the application before a user has logged in
1211
*
13-
* @since 1.0.0
1412
*/
13+
@PageTitle("Data Manager")
1514
public abstract class DataManagerLayout extends AppLayout {
1615

17-
private HorizontalLayout headerLayout;
18-
1916
protected DataManagerLayout() {
20-
createHeaderContent();
21-
}
22-
23-
private void createHeaderContent() {
24-
createHeaderLayout();
25-
26-
addToNavbar(headerLayout);
27-
}
28-
29-
private void createHeaderLayout() {
30-
H1 appName = styleHeaderTitle();
31-
headerLayout = new HorizontalLayout(appName);
32-
33-
styleHeaderLayout();
34-
}
35-
36-
private void styleHeaderLayout() {
37-
headerLayout.setDefaultVerticalComponentAlignment(FlexComponent.Alignment.CENTER);
38-
headerLayout.setWidth("100%");
39-
headerLayout.addClassNames("py-0", "px-m");
40-
}
41-
42-
private H1 styleHeaderTitle() {
43-
H1 appName = new H1("Data Manager");
44-
appName.addClassNames("text-l", "m-m");
45-
return appName;
17+
addClassName("data-manager-layout");
18+
Span drawerTitle = new Span("Data Manager");
19+
drawerTitle.addClassName("data-manager-title");
20+
addToNavbar(drawerTitle);
4621
}
4722
}

user-interface/src/main/java/life/qbic/datamanager/views/MainHandler.java

Lines changed: 0 additions & 39 deletions
This file was deleted.

user-interface/src/main/java/life/qbic/datamanager/views/MainHandlerInterface.java

Lines changed: 0 additions & 17 deletions
This file was deleted.

user-interface/src/main/java/life/qbic/datamanager/views/MainLayout.java

Lines changed: 0 additions & 53 deletions
This file was deleted.

user-interface/src/main/java/life/qbic/datamanager/views/MainPage.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
*
1818
* @since 1.0.0
1919
*/
20-
@Route(value = "", layout = MainLayout.class)
20+
@Route(value = "", layout = UserMainLayout.class)
2121
@PermitAll
2222
public class MainPage extends Div implements BeforeEnterObserver {
2323

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
package life.qbic.datamanager.views;
2+
3+
import com.vaadin.flow.router.PageTitle;
4+
import java.util.Objects;
5+
import life.qbic.datamanager.security.LogoutService;
6+
import life.qbic.datamanager.views.account.PersonalAccessTokenMain;
7+
import life.qbic.datamanager.views.general.DataManagerMenu;
8+
import life.qbic.datamanager.views.projects.overview.ProjectOverviewMain;
9+
import org.springframework.beans.factory.annotation.Autowired;
10+
11+
/**
12+
* <b> The user main layout is the layout holding all views outside of an individual project view,
13+
* such as the personal-access-token-management {@link PersonalAccessTokenMain} and listing the all
14+
* projects for a user {@link ProjectOverviewMain}</b>
15+
*
16+
* @since 1.0.0
17+
*/
18+
@PageTitle("Data Manager")
19+
public class UserMainLayout extends DataManagerLayout {
20+
21+
private final DataManagerMenu dataManagerMenu;
22+
23+
public UserMainLayout(@Autowired LogoutService logoutService) {
24+
Objects.requireNonNull(logoutService);
25+
dataManagerMenu = new DataManagerMenu(logoutService);
26+
addToNavbar(dataManagerMenu);
27+
}
28+
}

user-interface/src/main/java/life/qbic/datamanager/views/account/PersonalAccessTokenMain.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
import java.util.Collection;
1414
import java.util.List;
1515
import java.util.Objects;
16-
import life.qbic.datamanager.views.MainLayout;
16+
import life.qbic.datamanager.views.UserMainLayout;
1717
import life.qbic.datamanager.views.account.PersonalAccessTokenComponent.AddTokenEvent;
1818
import life.qbic.datamanager.views.account.PersonalAccessTokenComponent.DeleteTokenEvent;
1919
import life.qbic.datamanager.views.account.PersonalAccessTokenComponent.PersonalAccessTokenDTO;
@@ -36,7 +36,7 @@
3636
* create and delete {@link PersonalAccessToken} via the provided UI elements
3737
*/
3838

39-
@Route(value = "personal-access-token", layout = MainLayout.class)
39+
@Route(value = "personal-access-token", layout = UserMainLayout.class)
4040
@SpringComponent
4141
@UIScope
4242
@PermitAll
Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
package life.qbic.datamanager.views.general;
2+
3+
import com.vaadin.flow.component.Component;
4+
import com.vaadin.flow.component.avatar.Avatar;
5+
import com.vaadin.flow.component.button.Button;
6+
import com.vaadin.flow.component.contextmenu.MenuItem;
7+
import com.vaadin.flow.component.contextmenu.SubMenu;
8+
import com.vaadin.flow.component.html.Div;
9+
import com.vaadin.flow.component.menubar.MenuBar;
10+
import com.vaadin.flow.component.menubar.MenuBarVariant;
11+
import life.qbic.datamanager.security.LogoutService;
12+
import life.qbic.datamanager.views.account.PersonalAccessTokenMain;
13+
import life.qbic.datamanager.views.projects.overview.ProjectOverviewMain;
14+
import life.qbic.projectmanagement.application.authorization.QbicUserDetails;
15+
import org.springframework.beans.factory.annotation.Autowired;
16+
import org.springframework.security.core.Authentication;
17+
import org.springframework.security.core.context.SecurityContextHolder;
18+
19+
/**
20+
* Data Manager Menu
21+
* <p>
22+
* Menubar within the data manager application with which the user can route to the
23+
* {@link ProjectOverviewMain}, logout and access his personal access tokens in the
24+
* {@link PersonalAccessTokenMain}
25+
*/
26+
public class DataManagerMenu extends Div {
27+
28+
MenuBar projectMenu = new MenuBar();
29+
Avatar userAvatar = new Avatar();
30+
private final LogoutService logoutService;
31+
32+
public DataManagerMenu(@Autowired LogoutService logoutService) {
33+
this.logoutService = logoutService;
34+
initializeHomeMenuItem();
35+
initializeUserSubMenuItems();
36+
add(projectMenu);
37+
projectMenu.addClassName("menubar");
38+
addClassName("data-manager-menu");
39+
projectMenu.addThemeVariants(MenuBarVariant.LUMO_TERTIARY_INLINE);
40+
}
41+
42+
private void initializeHomeMenuItem() {
43+
projectMenu.addItem(new Button("Home"), event -> routeTo(ProjectOverviewMain.class));
44+
}
45+
46+
private void initializeUserSubMenuItems() {
47+
initializeAvatar();
48+
MenuItem userMenuItem = projectMenu.addItem(userAvatar);
49+
SubMenu userSubMenu = userMenuItem.getSubMenu();
50+
userSubMenu.addItem("Personal Access Tokens (PAT)", event -> routeTo(
51+
PersonalAccessTokenMain.class));
52+
userSubMenu.addItem("Log Out", event -> logoutService.logout());
53+
}
54+
55+
private void initializeAvatar() {
56+
Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
57+
QbicUserDetails details = (QbicUserDetails) authentication.getPrincipal();
58+
userAvatar.setName(details.fullName());
59+
userAvatar.addClassName("user-avatar");
60+
61+
}
62+
63+
private <T extends Component> void routeTo(Class<T> mainComponent) {
64+
getUI().orElseThrow().navigate(mainComponent);
65+
}
66+
}

0 commit comments

Comments
 (0)