commit | author | age
|
1e1b85
|
1 |
/*
|
JM |
2 |
* Copyright 2012 gitblit.com.
|
|
3 |
*
|
|
4 |
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
5 |
* you may not use this file except in compliance with the License.
|
|
6 |
* You may obtain a copy of the License at
|
|
7 |
*
|
|
8 |
* http://www.apache.org/licenses/LICENSE-2.0
|
|
9 |
*
|
|
10 |
* Unless required by applicable law or agreed to in writing, software
|
|
11 |
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
12 |
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13 |
* See the License for the specific language governing permissions and
|
|
14 |
* limitations under the License.
|
|
15 |
*/
|
|
16 |
package com.gitblit.wicket.pages;
|
|
17 |
|
c9921b
|
18 |
import java.io.Serializable;
|
1e1b85
|
19 |
import java.util.ArrayList;
|
c9921b
|
20 |
import java.util.Arrays;
|
1e1b85
|
21 |
import java.util.Collections;
|
JM |
22 |
import java.util.Comparator;
|
|
23 |
import java.util.List;
|
c9921b
|
24 |
import java.util.Locale;
|
1e1b85
|
25 |
|
JM |
26 |
import org.apache.wicket.PageParameters;
|
c9921b
|
27 |
import org.apache.wicket.ajax.AjaxRequestTarget;
|
JM |
28 |
import org.apache.wicket.ajax.markup.html.form.AjaxButton;
|
1e1b85
|
29 |
import org.apache.wicket.markup.html.basic.Label;
|
c9921b
|
30 |
import org.apache.wicket.markup.html.form.Form;
|
JM |
31 |
import org.apache.wicket.markup.html.panel.Fragment;
|
1e1b85
|
32 |
import org.apache.wicket.markup.repeater.Item;
|
JM |
33 |
import org.apache.wicket.markup.repeater.data.DataView;
|
|
34 |
import org.apache.wicket.markup.repeater.data.ListDataProvider;
|
c9921b
|
35 |
import org.apache.wicket.model.IModel;
|
JM |
36 |
import org.apache.wicket.model.Model;
|
1e1b85
|
37 |
|
1b04d7
|
38 |
import com.gitblit.Constants.Transport;
|
c9921b
|
39 |
import com.gitblit.GitBlitException;
|
1e1b85
|
40 |
import com.gitblit.Keys;
|
856f3f
|
41 |
import com.gitblit.models.Menu.ParameterMenuItem;
|
7a401a
|
42 |
import com.gitblit.models.NavLink;
|
0047fb
|
43 |
import com.gitblit.models.NavLink.DropDownPageMenuNavLink;
|
1e1b85
|
44 |
import com.gitblit.models.ProjectModel;
|
JM |
45 |
import com.gitblit.models.RepositoryModel;
|
|
46 |
import com.gitblit.models.UserModel;
|
|
47 |
import com.gitblit.utils.StringUtils;
|
|
48 |
import com.gitblit.wicket.GitBlitWebApp;
|
|
49 |
import com.gitblit.wicket.GitBlitWebSession;
|
9bdf88
|
50 |
import com.gitblit.wicket.GitblitRedirectException;
|
1e1b85
|
51 |
import com.gitblit.wicket.WicketUtils;
|
afbaeb
|
52 |
import com.gitblit.wicket.panels.BooleanOption;
|
c9921b
|
53 |
import com.gitblit.wicket.panels.ChoiceOption;
|
1e1b85
|
54 |
import com.gitblit.wicket.panels.ProjectRepositoryPanel;
|
05f229
|
55 |
import com.gitblit.wicket.panels.SshKeysPanel;
|
c9921b
|
56 |
import com.gitblit.wicket.panels.TextOption;
|
JM |
57 |
import com.gitblit.wicket.panels.UserTitlePanel;
|
1e1b85
|
58 |
|
JM |
59 |
public class UserPage extends RootPage {
|
699e71
|
60 |
|
1e1b85
|
61 |
List<ProjectModel> projectModels = new ArrayList<ProjectModel>();
|
JM |
62 |
|
|
63 |
public UserPage() {
|
|
64 |
super();
|
9bdf88
|
65 |
throw new GitblitRedirectException(GitBlitWebApp.get().getHomePage());
|
1e1b85
|
66 |
}
|
JM |
67 |
|
|
68 |
public UserPage(PageParameters params) {
|
|
69 |
super(params);
|
|
70 |
setup(params);
|
|
71 |
}
|
|
72 |
|
|
73 |
@Override
|
|
74 |
protected boolean reusePageParameters() {
|
|
75 |
return true;
|
|
76 |
}
|
|
77 |
|
|
78 |
private void setup(PageParameters params) {
|
|
79 |
setupPage("", "");
|
|
80 |
// check to see if we should display a login message
|
99d0d4
|
81 |
boolean authenticateView = app().settings().getBoolean(Keys.web.authenticateViewPages, true);
|
1e1b85
|
82 |
if (authenticateView && !GitBlitWebSession.get().isLoggedIn()) {
|
JM |
83 |
authenticationError("Please login");
|
|
84 |
return;
|
|
85 |
}
|
|
86 |
|
|
87 |
String userName = WicketUtils.getUsername(params);
|
|
88 |
if (StringUtils.isEmpty(userName)) {
|
9bdf88
|
89 |
throw new GitblitRedirectException(GitBlitWebApp.get().getHomePage());
|
1e1b85
|
90 |
}
|
JM |
91 |
|
99d0d4
|
92 |
UserModel user = app().users().getUserModel(userName);
|
1e1b85
|
93 |
if (user == null) {
|
JM |
94 |
// construct a temporary user model
|
|
95 |
user = new UserModel(userName);
|
|
96 |
}
|
699e71
|
97 |
|
JM |
98 |
|
c9921b
|
99 |
add(new UserTitlePanel("userTitlePanel", user, user.username));
|
699e71
|
100 |
|
6662e3
|
101 |
UserModel sessionUser = GitBlitWebSession.get().getUser();
|
c9921b
|
102 |
boolean isMyProfile = sessionUser != null && sessionUser.equals(user);
|
JM |
103 |
|
|
104 |
if (isMyProfile) {
|
|
105 |
addPreferences(user);
|
05f229
|
106 |
|
7d3a31
|
107 |
if (app().services().isServingSSH()) {
|
05f229
|
108 |
// show the SSH key management tab
|
JM |
109 |
addSshKeys(user);
|
|
110 |
} else {
|
|
111 |
// SSH daemon is disabled, hide keys tab
|
|
112 |
add(new Label("sshKeysLink").setVisible(false));
|
|
113 |
add(new Label("sshKeysTab").setVisible(false));
|
|
114 |
}
|
6662e3
|
115 |
} else {
|
c9921b
|
116 |
// visiting user
|
JM |
117 |
add(new Label("preferencesLink").setVisible(false));
|
|
118 |
add(new Label("preferencesTab").setVisible(false));
|
05f229
|
119 |
|
JM |
120 |
add(new Label("sshKeysLink").setVisible(false));
|
|
121 |
add(new Label("sshKeysTab").setVisible(false));
|
6662e3
|
122 |
}
|
699e71
|
123 |
|
1e1b85
|
124 |
List<RepositoryModel> repositories = getRepositories(params);
|
699e71
|
125 |
|
1e1b85
|
126 |
Collections.sort(repositories, new Comparator<RepositoryModel>() {
|
JM |
127 |
@Override
|
|
128 |
public int compare(RepositoryModel o1, RepositoryModel o2) {
|
|
129 |
// reverse-chronological sort
|
|
130 |
return o2.lastChange.compareTo(o1.lastChange);
|
|
131 |
}
|
|
132 |
});
|
|
133 |
|
|
134 |
final ListDataProvider<RepositoryModel> dp = new ListDataProvider<RepositoryModel>(repositories);
|
|
135 |
DataView<RepositoryModel> dataView = new DataView<RepositoryModel>("repositoryList", dp) {
|
|
136 |
private static final long serialVersionUID = 1L;
|
|
137 |
|
699e71
|
138 |
@Override
|
1e1b85
|
139 |
public void populateItem(final Item<RepositoryModel> item) {
|
JM |
140 |
final RepositoryModel entry = item.getModelObject();
|
699e71
|
141 |
|
JM |
142 |
ProjectRepositoryPanel row = new ProjectRepositoryPanel("repository",
|
1e1b85
|
143 |
getLocalizer(), this, showAdmin, entry, getAccessRestrictions());
|
JM |
144 |
item.add(row);
|
|
145 |
}
|
|
146 |
};
|
|
147 |
add(dataView);
|
|
148 |
}
|
|
149 |
|
|
150 |
@Override
|
7a401a
|
151 |
protected void addDropDownMenus(List<NavLink> navLinks) {
|
1e1b85
|
152 |
PageParameters params = getPageParameters();
|
JM |
153 |
|
7a401a
|
154 |
DropDownPageMenuNavLink menu = new DropDownPageMenuNavLink("gb.filters",
|
1e1b85
|
155 |
UserPage.class);
|
JM |
156 |
// preserve time filter option on repository choices
|
|
157 |
menu.menuItems.addAll(getRepositoryFilterItems(params));
|
|
158 |
|
|
159 |
// preserve repository filter option on time choices
|
|
160 |
menu.menuItems.addAll(getTimeFilterItems(params));
|
|
161 |
|
|
162 |
if (menu.menuItems.size() > 0) {
|
|
163 |
// Reset Filter
|
856f3f
|
164 |
menu.menuItems.add(new ParameterMenuItem(getString("gb.reset")));
|
1e1b85
|
165 |
}
|
JM |
166 |
|
7a401a
|
167 |
navLinks.add(menu);
|
1e1b85
|
168 |
}
|
c9921b
|
169 |
|
JM |
170 |
private void addPreferences(UserModel user) {
|
|
171 |
// add preferences
|
|
172 |
Form<Void> prefs = new Form<Void>("prefsForm");
|
|
173 |
|
|
174 |
List<Language> languages = Arrays.asList(
|
13dd75
|
175 |
new Language("Deutsch","de"),
|
c9921b
|
176 |
new Language("English","en"),
|
JM |
177 |
new Language("Español", "es"),
|
|
178 |
new Language("Français", "fr"),
|
5881c4
|
179 |
new Language("Italiano", "it"),
|
c9921b
|
180 |
new Language("日本語", "ja"),
|
JM |
181 |
new Language("한국말", "ko"),
|
|
182 |
new Language("Nederlands", "nl"),
|
|
183 |
new Language("Norsk", "no"),
|
|
184 |
new Language("Język Polski", "pl"),
|
|
185 |
new Language("Português", "pt_BR"),
|
25e1a6
|
186 |
new Language("簡體中文", "zh_CN"),
|
JM |
187 |
new Language("正體中文", "zh_TW"));
|
c9921b
|
188 |
|
6537de
|
189 |
Locale locale = user.getPreferences().getLocale();
|
JM |
190 |
if (locale == null) {
|
c9921b
|
191 |
// user has not specified language preference
|
JM |
192 |
// try server default preference
|
6537de
|
193 |
String lc = app().settings().getString(Keys.web.forceDefaultLocale, null);
|
c9921b
|
194 |
if (StringUtils.isEmpty(lc)) {
|
JM |
195 |
// server default language is not configured
|
|
196 |
// try browser preference
|
|
197 |
Locale sessionLocale = GitBlitWebSession.get().getLocale();
|
|
198 |
if (sessionLocale != null) {
|
6537de
|
199 |
locale = sessionLocale;
|
c9921b
|
200 |
}
|
6537de
|
201 |
} else {
|
JM |
202 |
|
c9921b
|
203 |
}
|
JM |
204 |
}
|
6537de
|
205 |
|
c9921b
|
206 |
Language preferredLanguage = null;
|
6537de
|
207 |
if (locale != null) {
|
JM |
208 |
String localeCode = locale.getLanguage();
|
|
209 |
if (!StringUtils.isEmpty(locale.getCountry())) {
|
|
210 |
localeCode += "_" + locale.getCountry();
|
|
211 |
}
|
|
212 |
|
c9921b
|
213 |
for (Language language : languages) {
|
6537de
|
214 |
if (language.code.equals(localeCode)) {
|
c9921b
|
215 |
// language_COUNTRY match
|
JM |
216 |
preferredLanguage = language;
|
6537de
|
217 |
} else if (preferredLanguage != null && language.code.startsWith(locale.getLanguage())) {
|
JM |
218 |
// language match
|
c9921b
|
219 |
preferredLanguage = language;
|
JM |
220 |
}
|
|
221 |
}
|
|
222 |
}
|
|
223 |
|
|
224 |
final IModel<String> displayName = Model.of(user.getDisplayName());
|
|
225 |
final IModel<String> emailAddress = Model.of(user.emailAddress == null ? "" : user.emailAddress);
|
|
226 |
final IModel<Language> language = Model.of(preferredLanguage);
|
afbaeb
|
227 |
final IModel<Boolean> emailMeOnMyTicketChanges = Model.of(user.getPreferences().isEmailMeOnMyTicketChanges());
|
1b04d7
|
228 |
final IModel<Transport> transport = Model.of(user.getPreferences().getTransport());
|
c9921b
|
229 |
|
JM |
230 |
prefs.add(new TextOption("displayName",
|
|
231 |
getString("gb.displayName"),
|
|
232 |
getString("gb.displayNameDescription"),
|
|
233 |
displayName).setVisible(app().authentication().supportsDisplayNameChanges(user)));
|
|
234 |
|
|
235 |
prefs.add(new TextOption("emailAddress",
|
|
236 |
getString("gb.emailAddress"),
|
|
237 |
getString("gb.emailAddressDescription"),
|
|
238 |
emailAddress).setVisible(app().authentication().supportsEmailAddressChanges(user)));
|
|
239 |
|
|
240 |
prefs.add(new ChoiceOption<Language>("language",
|
|
241 |
getString("gb.languagePreference"),
|
|
242 |
getString("gb.languagePreferenceDescription"),
|
|
243 |
language,
|
|
244 |
languages));
|
|
245 |
|
afbaeb
|
246 |
prefs.add(new BooleanOption("emailMeOnMyTicketChanges",
|
JM |
247 |
getString("gb.emailMeOnMyTicketChanges"),
|
|
248 |
getString("gb.emailMeOnMyTicketChangesDescription"),
|
|
249 |
emailMeOnMyTicketChanges).setVisible(app().notifier().isSendingMail()));
|
|
250 |
|
1b04d7
|
251 |
List<Transport> availableTransports = new ArrayList<>();
|
7d3a31
|
252 |
if (app().services().isServingSSH()) {
|
1b04d7
|
253 |
availableTransports.add(Transport.SSH);
|
JM |
254 |
}
|
7d3a31
|
255 |
if (app().services().isServingHTTP()) {
|
1b04d7
|
256 |
availableTransports.add(Transport.HTTP);
|
JM |
257 |
}
|
67ba8f
|
258 |
if (app().services().isServingHTTPS()) {
|
JM |
259 |
availableTransports.add(Transport.HTTPS);
|
|
260 |
}
|
7d3a31
|
261 |
if (app().services().isServingGIT()) {
|
1b04d7
|
262 |
availableTransports.add(Transport.GIT);
|
JM |
263 |
}
|
|
264 |
|
|
265 |
prefs.add(new ChoiceOption<Transport>("transport",
|
|
266 |
getString("gb.transportPreference"),
|
|
267 |
getString("gb.transportPreferenceDescription"),
|
|
268 |
transport,
|
|
269 |
availableTransports));
|
|
270 |
|
c9921b
|
271 |
prefs.add(new AjaxButton("save") {
|
JM |
272 |
|
|
273 |
private static final long serialVersionUID = 1L;
|
|
274 |
|
|
275 |
@Override
|
|
276 |
protected void onSubmit(AjaxRequestTarget target, Form<?> form) {
|
|
277 |
|
|
278 |
UserModel user = GitBlitWebSession.get().getUser();
|
|
279 |
|
|
280 |
user.displayName = displayName.getObject();
|
|
281 |
user.emailAddress = emailAddress.getObject();
|
|
282 |
|
|
283 |
Language lang = language.getObject();
|
|
284 |
if (lang != null) {
|
6537de
|
285 |
user.getPreferences().setLocale(lang.code);
|
c9921b
|
286 |
}
|
JM |
287 |
|
afbaeb
|
288 |
user.getPreferences().setEmailMeOnMyTicketChanges(emailMeOnMyTicketChanges.getObject());
|
1b04d7
|
289 |
user.getPreferences().setTransport(transport.getObject());
|
afbaeb
|
290 |
|
c9921b
|
291 |
try {
|
JM |
292 |
app().gitblit().reviseUser(user.username, user);
|
|
293 |
|
|
294 |
setRedirect(true);
|
|
295 |
setResponsePage(UserPage.class, WicketUtils.newUsernameParameter(user.username));
|
|
296 |
} catch (GitBlitException e) {
|
|
297 |
// logger.error("Failed to update user " + user.username, e);
|
|
298 |
// error(getString("gb.failedToUpdateUser"), false);
|
|
299 |
}
|
|
300 |
}
|
|
301 |
});
|
|
302 |
|
|
303 |
// add the preferences tab
|
|
304 |
add(new Fragment("preferencesLink", "preferencesLinkFragment", this).setRenderBodyOnly(true));
|
|
305 |
Fragment fragment = new Fragment("preferencesTab", "preferencesTabFragment", this);
|
|
306 |
fragment.add(prefs);
|
|
307 |
add(fragment.setRenderBodyOnly(true));
|
|
308 |
}
|
|
309 |
|
05f229
|
310 |
private void addSshKeys(final UserModel user) {
|
JM |
311 |
Fragment keysTab = new Fragment("sshKeysTab", "sshKeysTabFragment", this);
|
b0658e
|
312 |
keysTab.add(new SshKeysPanel("sshKeysPanel", user));
|
05f229
|
313 |
|
JM |
314 |
// add the SSH keys tab
|
|
315 |
add(new Fragment("sshKeysLink", "sshKeysLinkFragment", this).setRenderBodyOnly(true));
|
|
316 |
add(keysTab.setRenderBodyOnly(true));
|
|
317 |
}
|
|
318 |
|
c9921b
|
319 |
private class Language implements Serializable {
|
JM |
320 |
|
|
321 |
private static final long serialVersionUID = 1L;
|
|
322 |
|
|
323 |
final String name;
|
|
324 |
final String code;
|
|
325 |
|
|
326 |
public Language(String name, String code) {
|
|
327 |
this.name = name;
|
|
328 |
this.code = code;
|
|
329 |
}
|
|
330 |
|
|
331 |
@Override
|
|
332 |
public String toString() {
|
|
333 |
return name + " (" + code +")";
|
|
334 |
}
|
|
335 |
}
|
1e1b85
|
336 |
}
|