diff --git a/internal/web3ext/web3ext.go b/internal/web3ext/web3ext.go
index 190fd57d25d90d6604f92d821e8b9f74336b4ba8..e76e15177d336f3cfb698c2ff5eed2f1f2e3e8df 100644
--- a/internal/web3ext/web3ext.go
+++ b/internal/web3ext/web3ext.go
@@ -39,6 +39,11 @@ web3._extend({
 			call: 'admin_addPeer',
 			params: 1
 		}),
+		new web3._extend.Method({
+			name: 'removePeer',
+			call: 'admin_removePeer',
+			params: 1
+		}),
 		new web3._extend.Method({
 			name: 'exportChain',
 			call: 'admin_exportChain',
diff --git a/node/api.go b/node/api.go
index 9b2be9c2e4ae5c48b92a0063d37efa9ce733476b..3523874ab8d8c4086fc3b15d77ee50bda91f9c11 100644
--- a/node/api.go
+++ b/node/api.go
@@ -58,6 +58,22 @@ func (api *PrivateAdminAPI) AddPeer(url string) (bool, error) {
 	return true, nil
 }
 
+// RemovePeer disconnects from a a remote node if the connection exists
+func (api *PrivateAdminAPI) RemovePeer(url string) (bool, error) {
+	// Make sure the server is running, fail otherwise
+	server := api.node.Server()
+	if server == nil {
+		return false, ErrNodeStopped
+	}
+	// Try to remove the url as a static peer and return
+	node, err := discover.ParseNode(url)
+	if err != nil {
+		return false, fmt.Errorf("invalid enode: %v", err)
+	}
+	server.RemovePeer(node)
+	return true, nil
+}
+
 // StartRPC starts the HTTP RPC API server.
 func (api *PrivateAdminAPI) StartRPC(host *string, port *rpc.HexNumber, cors *string, apis *string) (bool, error) {
 	api.node.lock.Lock()
diff --git a/p2p/dial.go b/p2p/dial.go
index c0e703d7d094d29d801e51be445efd2f2a3a5843..691b8539e351610408e96c7e514ca352d37f7aac 100644
--- a/p2p/dial.go
+++ b/p2p/dial.go
@@ -121,6 +121,11 @@ func (s *dialstate) addStatic(n *discover.Node) {
 	s.static[n.ID] = &dialTask{flags: staticDialedConn, dest: n}
 }
 
+func (s *dialstate) removeStatic(n *discover.Node) {
+	// This removes a task so future attempts to connect will not be made.
+	delete(s.static, n.ID)
+}
+
 func (s *dialstate) newTasks(nRunning int, peers map[discover.NodeID]*Peer, now time.Time) []task {
 	var newtasks []task
 	isDialing := func(id discover.NodeID) bool {
diff --git a/p2p/server.go b/p2p/server.go
index 880aa7cf1fb1ca66ad51e0664fda5165d669d644..8e3cd93f99b79c0906a6a8fbe2953aad0533a142 100644
--- a/p2p/server.go
+++ b/p2p/server.go
@@ -142,6 +142,7 @@ type Server struct {
 
 	quit          chan struct{}
 	addstatic     chan *discover.Node
+	removestatic  chan *discover.Node
 	posthandshake chan *conn
 	addpeer       chan *conn
 	delpeer       chan *Peer
@@ -257,6 +258,14 @@ func (srv *Server) AddPeer(node *discover.Node) {
 	}
 }
 
+// RemovePeer disconnects from the given node
+func (srv *Server) RemovePeer(node *discover.Node) {
+	select {
+	case srv.removestatic <- node:
+	case <-srv.quit:
+	}
+}
+
 // Self returns the local node's endpoint information.
 func (srv *Server) Self() *discover.Node {
 	srv.lock.Lock()
@@ -327,6 +336,7 @@ func (srv *Server) Start() (err error) {
 	srv.delpeer = make(chan *Peer)
 	srv.posthandshake = make(chan *conn)
 	srv.addstatic = make(chan *discover.Node)
+	srv.removestatic = make(chan *discover.Node)
 	srv.peerOp = make(chan peerOpFunc)
 	srv.peerOpDone = make(chan struct{})
 
@@ -395,6 +405,7 @@ type dialer interface {
 	newTasks(running int, peers map[discover.NodeID]*Peer, now time.Time) []task
 	taskDone(task, time.Time)
 	addStatic(*discover.Node)
+	removeStatic(*discover.Node)
 }
 
 func (srv *Server) run(dialstate dialer) {
@@ -458,6 +469,15 @@ running:
 			// it will keep the node connected.
 			glog.V(logger.Detail).Infoln("<-addstatic:", n)
 			dialstate.addStatic(n)
+		case n := <-srv.removestatic:
+			// This channel is used by RemovePeer to send a
+			// disconnect request to a peer and begin the
+			// stop keeping the node connected
+			glog.V(logger.Detail).Infoln("<-removestatic:", n)
+			dialstate.removeStatic(n)
+			if p, ok := peers[n.ID]; ok {
+				p.Disconnect(DiscRequested)
+			}
 		case op := <-srv.peerOp:
 			// This channel is used by Peers and PeerCount.
 			op(peers)
diff --git a/p2p/server_test.go b/p2p/server_test.go
index deb34f5bb18411fa44d3d3b98e63af2d33cd21b2..313d086ec4af8864efbdd1569bd635d1e941525c 100644
--- a/p2p/server_test.go
+++ b/p2p/server_test.go
@@ -301,6 +301,8 @@ func (tg taskgen) taskDone(t task, now time.Time) {
 }
 func (tg taskgen) addStatic(*discover.Node) {
 }
+func (tg taskgen) removeStatic(*discover.Node) {
+}
 
 type testTask struct {
 	index  int