2 * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
9 package org.opendaylight.controller.web;
11 import java.net.InetAddress;
12 import java.net.UnknownHostException;
13 import java.util.ArrayList;
14 import java.util.List;
17 import javax.servlet.http.HttpServletRequest;
19 import org.opendaylight.controller.clustering.services.IClusterGlobalServices;
20 import org.opendaylight.controller.connectionmanager.IConnectionManager;
21 import org.opendaylight.controller.sal.authorization.UserLevel;
22 import org.opendaylight.controller.sal.core.Description;
23 import org.opendaylight.controller.sal.core.Node;
24 import org.opendaylight.controller.sal.utils.GlobalConstants;
25 import org.opendaylight.controller.sal.utils.ServiceHelper;
26 import org.opendaylight.controller.sal.utils.Status;
27 import org.opendaylight.controller.sal.utils.StatusCode;
28 import org.opendaylight.controller.switchmanager.ISwitchManager;
29 import org.opendaylight.controller.usermanager.IUserManager;
30 import org.opendaylight.controller.usermanager.UserConfig;
31 import org.springframework.stereotype.Controller;
32 import org.springframework.web.bind.annotation.PathVariable;
33 import org.springframework.web.bind.annotation.RequestMapping;
34 import org.springframework.web.bind.annotation.RequestMethod;
35 import org.springframework.web.bind.annotation.RequestParam;
36 import org.springframework.web.bind.annotation.ResponseBody;
38 import com.google.gson.Gson;
41 @RequestMapping("/admin")
42 public class DaylightWebAdmin {
43 Gson gson = new Gson();
46 * Returns list of clustered controllers. Highlights "this" controller and
47 * if controller is coordinator
48 * @return List<ClusterBean>
50 @RequestMapping("/cluster")
52 public String getClusteredControllers() {
53 IClusterGlobalServices clusterServices = (IClusterGlobalServices) ServiceHelper.getGlobalInstance(
54 IClusterGlobalServices.class, this);
55 if (clusterServices == null) {
58 IConnectionManager connectionManager = (IConnectionManager) ServiceHelper.getGlobalInstance(
59 IConnectionManager.class, this);
60 if (connectionManager == null) {
64 List<ClusterNodeBean> clusterNodes = new ArrayList<ClusterNodeBean>();
66 List<InetAddress> controllers = clusterServices.getClusteredControllers();
67 for (InetAddress controller : controllers) {
68 ClusterNodeBean.Builder clusterBeanBuilder = new ClusterNodeBean.Builder(controller);
70 //get number of connected nodes
71 Set<Node> connectedNodes = connectionManager.getNodes(controller);
72 int numNodes = connectedNodes == null ? 0 : connectedNodes.size();
73 clusterBeanBuilder.nodesConnected(numNodes);
75 //determine if this is the executing controller
76 if (controller.equals(clusterServices.getMyAddress())) {
77 clusterBeanBuilder.highlightMe();
80 //determine whether this is coordinator
81 if (clusterServices.getCoordinatorAddress().equals(controller)) {
82 clusterBeanBuilder.iAmCoordinator();
84 clusterNodes.add(clusterBeanBuilder.build());
87 return gson.toJson(clusterNodes);
91 * Return nodes connected to controller {controller}
93 * - byte[] of the address of the controller
94 * @return List<NodeBean>
96 @RequestMapping("/cluster/controller/{controller}")
98 public String getNodesConnectedToController(@PathVariable("controller") String controller) {
99 IClusterGlobalServices clusterServices = (IClusterGlobalServices) ServiceHelper.getGlobalInstance(
100 IClusterGlobalServices.class, this);
101 if (clusterServices == null) {
104 IConnectionManager connectionManager = (IConnectionManager) ServiceHelper.getGlobalInstance(
105 IConnectionManager.class, this);
106 if (connectionManager == null) {
109 ISwitchManager switchManager = (ISwitchManager) ServiceHelper.getInstance(ISwitchManager.class,
110 GlobalConstants.DEFAULT.toString(), this);
111 if (switchManager == null) {
115 byte[] address = gson.fromJson(controller, byte[].class);
116 InetAddress controllerAddress = null;
118 controllerAddress = InetAddress.getByAddress(address);
119 } catch (UnknownHostException e) {
123 List<NodeBean> result = new ArrayList<NodeBean>();
125 Set<Node> nodes = connectionManager.getNodes(controllerAddress);
127 return gson.toJson(result);
129 for (Node node : nodes) {
130 Description description = (Description) switchManager.getNodeProp(node, Description.propertyName);
132 if (description == null || description.getValue().equals("None")) {
133 nodeBean = new NodeBean(node);
135 nodeBean = new NodeBean(node, description.getValue());
137 result.add(nodeBean);
140 return gson.toJson(result);
143 @RequestMapping("/users")
145 public List<UserConfig> getUsers() {
146 IUserManager userManager = (IUserManager) ServiceHelper.getGlobalInstance(IUserManager.class, this);
147 if (userManager == null) {
151 List<UserConfig> userConfList = userManager.getLocalUserList();
157 * Password in clear text, moving to HTTP/SSL soon
159 @RequestMapping(value = "/users", method = RequestMethod.POST)
161 public String saveLocalUserConfig(@RequestParam(required = true) String json,
162 @RequestParam(required = true) String action, HttpServletRequest request) {
164 IUserManager userManager = (IUserManager) ServiceHelper.getGlobalInstance(IUserManager.class, this);
165 if (userManager == null) {
166 return "Internal Error";
169 if (!authorize(userManager, UserLevel.NETWORKADMIN, request)) {
170 return "Operation not permitted";
173 Gson gson = new Gson();
174 UserConfig plainConfig = gson.fromJson(json, UserConfig.class);
175 // Recreate using the proper constructor which will hash the password
176 UserConfig config = new UserConfig(plainConfig.getUser(), plainConfig.getPassword(), plainConfig.getRoles());
178 Status result = (action.equals("add")) ? userManager.addLocalUser(config) : userManager.removeLocalUser(config);
179 if (result.isSuccess()) {
180 String userAction = (action.equals("add")) ? "added" : "removed";
181 DaylightWebUtil.auditlog("User", request.getUserPrincipal().getName(), userAction, config.getUser());
184 return result.getDescription();
187 @RequestMapping(value = "/users/{username}", method = RequestMethod.POST)
189 public String removeLocalUser(@PathVariable("username") String userName, HttpServletRequest request) {
191 String username = request.getUserPrincipal().getName();
192 if (username.equals(userName)) {
193 return "Invalid Request: User cannot delete itself";
196 IUserManager userManager = (IUserManager) ServiceHelper.getGlobalInstance(IUserManager.class, this);
197 if (userManager == null) {
198 return "Internal Error";
201 if (!authorize(userManager, UserLevel.NETWORKADMIN, request)) {
202 return "Operation not permitted";
205 Status result = userManager.removeLocalUser(userName);
206 if (result.isSuccess()) {
207 DaylightWebUtil.auditlog("User", request.getUserPrincipal().getName(), "removed", userName);
210 return result.getDescription();
213 @RequestMapping(value = "/users/password/{username}", method = RequestMethod.POST)
215 public Status changePassword(@PathVariable("username") String username, HttpServletRequest request,
216 @RequestParam("currentPassword") String currentPassword, @RequestParam("newPassword") String newPassword) {
217 IUserManager userManager = (IUserManager) ServiceHelper.getGlobalInstance(IUserManager.class, this);
218 if (userManager == null) {
219 return new Status(StatusCode.GONE, "User Manager not found");
222 if (!authorize(userManager, UserLevel.NETWORKADMIN, request)) {
223 return new Status(StatusCode.FORBIDDEN, "Operation not permitted");
226 if (newPassword.isEmpty()) {
227 return new Status(StatusCode.BADREQUEST, "Empty passwords not allowed");
230 Status status = userManager.changeLocalUserPassword(username, currentPassword, newPassword);
231 if (status.isSuccess()) {
232 DaylightWebUtil.auditlog("User", request.getUserPrincipal().getName(), "changed password for", username);
238 * Is the operation permitted for the given level
241 private boolean authorize(IUserManager userManager, UserLevel level, HttpServletRequest request) {
242 String username = request.getUserPrincipal().getName();
243 UserLevel userLevel = userManager.getUserLevel(username);
244 return userLevel.toNumber() <= level.toNumber();