From dfb88962fdbd29f59abe92178bb042738d57c3e1 Mon Sep 17 00:00:00 2001 From: James Moger <james.moger@gitblit.com> Date: Wed, 11 May 2011 22:07:18 -0400 Subject: [PATCH] Add user. Implemented repository view and git access restrictions. --- src/com/gitblit/JettyLoginService.java | 180 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 files changed, 172 insertions(+), 8 deletions(-) diff --git a/src/com/gitblit/JettyLoginService.java b/src/com/gitblit/JettyLoginService.java index 5173d21..ddd3722 100644 --- a/src/com/gitblit/JettyLoginService.java +++ b/src/com/gitblit/JettyLoginService.java @@ -1,14 +1,33 @@ package com.gitblit; -import org.eclipse.jetty.security.HashLoginService; +import java.io.File; +import java.io.FileReader; +import java.io.FileWriter; +import java.io.IOException; +import java.security.Principal; +import java.util.ArrayList; +import java.util.Map; +import java.util.Properties; + +import javax.security.auth.Subject; + +import org.eclipse.jetty.http.security.Credential; +import org.eclipse.jetty.security.IdentityService; +import org.eclipse.jetty.security.MappedLoginService; import org.eclipse.jetty.server.UserIdentity; +import org.eclipse.jetty.util.log.Log; -import com.gitblit.wicket.User; +import com.gitblit.utils.StringUtils; +import com.gitblit.wicket.models.User; -public class JettyLoginService extends HashLoginService implements ILoginService { +public class JettyLoginService extends MappedLoginService implements ILoginService { - public JettyLoginService(String realmFile) { - super(Constants.NAME, realmFile); + private final File realmFile; + + public JettyLoginService(File realmFile) { + super(); + setName(Constants.NAME); + this.realmFile = realmFile; } @Override @@ -17,10 +36,19 @@ if (identity == null || identity.equals(UserIdentity.UNAUTHENTICATED_IDENTITY)) { return null; } - User user = new User(username, password); + User user = new User(username); + user.setCookie(StringUtils.getSHA1((Constants.NAME + username + new String(password)))); user.canAdmin(identity.isUserInRole(Constants.ADMIN_ROLE, null)); - user.canClone(identity.isUserInRole(Constants.PULL_ROLE, null)); - user.canPush(identity.isUserInRole(Constants.PUSH_ROLE, null)); + + // Add repositories + for (Principal principal : identity.getSubject().getPrincipals()) { + if (principal instanceof RolePrincipal) { + RolePrincipal role = (RolePrincipal) principal; + if (role.getName().charAt(0) != '#') { + user.addRepository(role.getName().substring(1)); + } + } + } return user; } @@ -29,4 +57,140 @@ // TODO cookie login return null; } + + @Override + public User getUserModel(String username) { + User model = new User(username); + UserIdentity identity = _users.get(username); + Subject subject = identity.getSubject(); + for (Principal principal : subject.getPrincipals()) { + if (principal instanceof RolePrincipal) { + RolePrincipal role = (RolePrincipal) principal; + String name = role.getName(); + switch (name.charAt(0)) { + case '#': + // Permissions + if (name.equalsIgnoreCase(Constants.ADMIN_ROLE)) { + model.canAdmin(true); + } + break; + default: + model.addRepository(name.substring(1)); + } + } + } + return model; + } + + @Override + public boolean updateUserModel(User model) { + try { + Properties properties = new Properties(); + FileReader reader = new FileReader(realmFile); + properties.load(reader); + reader.close(); + + ArrayList<String> roles = new ArrayList<String>(); + + // Repositories + roles.addAll(model.getRepositories()); + + // Permissions + if (model.canAdmin()) { + roles.add(Constants.ADMIN_ROLE); + } + + StringBuilder sb = new StringBuilder(); + sb.append(model.getPassword()); + sb.append(','); + for (String role : roles) { + sb.append(role); + sb.append(','); + } + // trim trailing comma + sb.setLength(sb.length() - 1); + + // Update realm file + File realmFileCopy = new File(realmFile.getAbsolutePath() + ".tmp"); + FileWriter writer = new FileWriter(realmFileCopy); + properties.put(model.getUsername(), sb.toString()); + properties.store(writer, null); + writer.close(); + realmFile.delete(); + realmFileCopy.renameTo(realmFile); + + // Update login service + putUser(model.getUsername(), Credential.getCredential(model.getPassword()), roles.toArray(new String[0])); + return true; + } catch (Throwable t) { + t.printStackTrace(); + } + return false; + } + + @Override + public boolean deleteUserModel(User model) { + try { + // Read realm file + Properties properties = new Properties(); + FileReader reader = new FileReader(realmFile); + properties.load(reader); + reader.close(); + properties.remove(model.getUsername()); + + // Update realm file + File realmFileCopy = new File(realmFile.getAbsolutePath() + ".tmp"); + FileWriter writer = new FileWriter(realmFileCopy); + properties.store(writer, null); + writer.close(); + realmFile.delete(); + realmFileCopy.renameTo(realmFile); + + // Drop user from map + _users.remove(model.getUsername()); + return true; + } catch (Throwable t) { + t.printStackTrace(); + } + return false; + } + + /* ------------------------------------------------------------ */ + @Override + public void loadUsers() throws IOException { + if (realmFile == null) + return; + + if (Log.isDebugEnabled()) + Log.debug("Load " + this + " from " + realmFile); + Properties properties = new Properties(); + FileReader reader = new FileReader(realmFile); + properties.load(reader); + reader.close(); + + // Map Users + for (Map.Entry<Object, Object> entry : properties.entrySet()) { + String username = ((String) entry.getKey()).trim(); + String credentials = ((String) entry.getValue()).trim(); + String roles = null; + int c = credentials.indexOf(','); + if (c > 0) { + roles = credentials.substring(c + 1).trim(); + credentials = credentials.substring(0, c).trim(); + } + + if (username != null && username.length() > 0 && credentials != null && credentials.length() > 0) { + String[] roleArray = IdentityService.NO_ROLES; + if (roles != null && roles.length() > 0) { + roleArray = roles.split(","); + } + putUser(username, Credential.getCredential(credentials), roleArray); + } + } + } + + @Override + protected UserIdentity loadUser(String username) { + return null; + } } -- Gitblit v1.9.1