func (r *fakeRouter) RemoveRoute(name, ip string) error { backendName, err := router.Retrieve(name) if err != nil { return err } if !r.HasBackend(backendName) { return ErrBackendNotFound } r.mutex.Lock() defer r.mutex.Unlock() index := -1 routes := r.backends[backendName] for i := range routes { if routes[i] == ip { index = i break } } if index < 0 { return errors.New("Route not found") } routes[index] = routes[len(routes)-1] r.backends[backendName] = routes[:len(routes)-1] return nil }
func (r hipacheRouter) AddRoute(name, address string) error { backendName, err := router.Retrieve(name) if err != nil { return err } domain, err := config.GetString("hipache:domain") if err != nil { log.Errorf("error on getting hipache domain in add route for %s - %s", backendName, address) return &routeError{"add", err} } frontend := "frontend:" + backendName + "." + domain if err := r.addRoute(frontend, address); err != nil { log.Errorf("error on add route for %s - %s", backendName, address) return &routeError{"add", err} } cname, err := r.getCName(backendName) if err != nil { log.Errorf("error on get cname in add route for %s - %s", backendName, address) return err } if cname == "" { return nil } return r.addRoute("frontend:"+cname, address) }
func (r elbRouter) AddRoute(name, address string) error { backendName, err := router.Retrieve(name) if err != nil { return err } _, err = r.elb().RegisterInstancesWithLoadBalancer([]string{address}, backendName) return err }
func (r *fakeRouter) Routes(name string) ([]string, error) { backendName, err := router.Retrieve(name) if err != nil { return nil, err } r.mutex.Lock() defer r.mutex.Unlock() routes := r.backends[backendName] return routes, nil }
func (s *S) TestSwap(c *gocheck.C) { instance1 := s.server.NewInstance() defer s.server.RemoveInstance(instance1) instance2 := s.server.NewInstance() defer s.server.RemoveInstance(instance2) backend1 := "b1" backend2 := "b2" elb := elbRouter{} err := elb.AddBackend(backend1) c.Assert(err, gocheck.IsNil) err = elb.AddRoute(backend1, instance1) c.Assert(err, gocheck.IsNil) err = elb.AddBackend(backend2) c.Assert(err, gocheck.IsNil) err = elb.AddRoute(backend2, instance2) c.Assert(err, gocheck.IsNil) retrieved1, err := router.Retrieve(backend1) c.Assert(err, gocheck.IsNil) c.Assert(retrieved1, gocheck.Equals, backend1) retrieved2, err := router.Retrieve(backend2) c.Assert(err, gocheck.IsNil) c.Assert(retrieved2, gocheck.Equals, backend2) err = elb.Swap(backend1, backend2) c.Assert(err, gocheck.IsNil) routes, err := elb.Routes(backend2) c.Assert(err, gocheck.IsNil) c.Assert(routes, gocheck.DeepEquals, []string{instance2}) routes, err = elb.Routes(backend1) c.Assert(err, gocheck.IsNil) c.Assert(routes, gocheck.DeepEquals, []string{instance1}) retrieved1, err = router.Retrieve(backend1) c.Assert(err, gocheck.IsNil) c.Assert(retrieved1, gocheck.Equals, backend2) retrieved2, err = router.Retrieve(backend2) c.Assert(err, gocheck.IsNil) c.Assert(retrieved2, gocheck.Equals, backend1) addr, err := elb.Addr(backend1) c.Assert(err, gocheck.IsNil) c.Assert(addr, gocheck.Equals, "b2-some-aws-stuff.us-east-1.elb.amazonaws.com") addr, err = elb.Addr(backend2) c.Assert(err, gocheck.IsNil) c.Assert(addr, gocheck.Equals, "b1-some-aws-stuff.us-east-1.elb.amazonaws.com") }
func (r elbRouter) Addr(name string) (string, error) { backendName, err := router.Retrieve(name) if err != nil { return "", err } resp, err := r.elb().DescribeLoadBalancers(backendName) if err != nil { return "", err } return resp.LoadBalancerDescriptions[0].DNSName, nil }
func (r elbRouter) RemoveBackend(name string) error { backendName, err := router.Retrieve(name) if err != nil { return err } _, err = r.elb().DeleteLoadBalancer(backendName) if err != nil { return err } return router.Remove(backendName) }
func (s *S) TestSwap(c *gocheck.C) { instance1 := "127.0.0.1" instance2 := "127.0.0.2" backend1 := "b1" backend2 := "b2" r := fakeRouter{backends: make(map[string][]string)} err := r.AddBackend(backend1) c.Assert(err, gocheck.IsNil) err = r.AddRoute(backend1, instance1) c.Assert(err, gocheck.IsNil) err = r.AddBackend(backend2) c.Assert(err, gocheck.IsNil) err = r.AddRoute(backend2, instance2) c.Assert(err, gocheck.IsNil) retrieved1, err := router.Retrieve(backend1) c.Assert(err, gocheck.IsNil) c.Assert(retrieved1, gocheck.Equals, backend1) retrieved2, err := router.Retrieve(backend2) c.Assert(err, gocheck.IsNil) c.Assert(retrieved2, gocheck.Equals, backend2) err = r.Swap(backend1, backend2) c.Assert(err, gocheck.IsNil) routes, err := r.Routes(backend2) c.Assert(err, gocheck.IsNil) c.Assert(routes, gocheck.DeepEquals, []string{instance2}) routes, err = r.Routes(backend1) c.Assert(err, gocheck.IsNil) c.Assert(routes, gocheck.DeepEquals, []string{instance1}) retrieved1, err = router.Retrieve(backend1) c.Assert(err, gocheck.IsNil) c.Assert(retrieved1, gocheck.Equals, backend2) retrieved2, err = router.Retrieve(backend2) c.Assert(err, gocheck.IsNil) c.Assert(retrieved2, gocheck.Equals, backend1) addr, err := r.Addr(backend1) c.Assert(err, gocheck.IsNil) c.Assert(addr, gocheck.Equals, "127.0.0.2") addr, err = r.Addr(backend2) c.Assert(err, gocheck.IsNil) c.Assert(addr, gocheck.Equals, "127.0.0.1") }
func (r *fakeRouter) RemoveBackend(name string) error { backendName, err := router.Retrieve(name) if err != nil { return err } if !r.HasBackend(backendName) { return ErrBackendNotFound } r.mutex.Lock() defer r.mutex.Unlock() delete(r.backends, backendName) return nil }
func (r *fakeRouter) SetCName(cname, name string) error { backendName, err := router.Retrieve(name) if err != nil { return err } if !r.HasBackend(backendName) { return nil } r.AddBackend(cname) r.mutex.Lock() defer r.mutex.Unlock() r.backends[cname] = append(r.backends[backendName]) return nil }
func (r *fakeRouter) AddRoute(name, ip string) error { backendName, err := router.Retrieve(name) if err != nil { return err } if !r.HasBackend(backendName) { return ErrBackendNotFound } r.mutex.Lock() defer r.mutex.Unlock() routes := r.backends[backendName] routes = append(routes, ip) r.backends[backendName] = routes return nil }
func (r elbRouter) Routes(name string) ([]string, error) { backendName, err := router.Retrieve(name) if err != nil { return nil, err } var routes []string resp, err := r.elb().DescribeLoadBalancers(backendName) if err != nil { return nil, err } for _, instance := range resp.LoadBalancerDescriptions[0].Instances { routes = append(routes, instance.InstanceId) } return routes, nil }
func (r hipacheRouter) UnsetCName(cname, name string) error { backendName, err := router.Retrieve(name) if err != nil { return err } conn := connect() defer conn.Close() _, err = conn.Do("DEL", "cname:"+backendName) if err != nil { return &routeError{"unsetCName", err} } _, err = conn.Do("DEL", "frontend:"+cname) if err != nil { return &routeError{"unsetCName", err} } return nil }
func (hipacheRouter) Routes(name string) ([]string, error) { backendName, err := router.Retrieve(name) if err != nil { return nil, err } domain, err := config.GetString("hipache:domain") if err != nil { return nil, &routeError{"routes", err} } frontend := "frontend:" + backendName + "." + domain conn := connect() defer conn.Close() routes, err := redis.Strings(conn.Do("LRANGE", frontend, 0, -1)) if err != nil { return nil, &routeError{"routes", err} } return routes, nil }
func (hipacheRouter) Addr(name string) (string, error) { backendName, err := router.Retrieve(name) if err != nil { return "", err } domain, err := config.GetString("hipache:domain") if err != nil { return "", &routeError{"get", err} } frontend := "frontend:" + backendName + "." + domain conn := connect() defer conn.Close() reply, err := conn.Do("LRANGE", frontend, 0, 0) if err != nil { return "", &routeError{"get", err} } backends := reply.([]interface{}) if len(backends) < 1 { return "", errRouteNotFound } return fmt.Sprintf("%s.%s", backendName, domain), nil }
func (r hipacheRouter) SetCName(cname, name string) error { backendName, err := router.Retrieve(name) if err != nil { return err } domain, err := config.GetString("hipache:domain") if err != nil { return &routeError{"setCName", err} } if !r.validCName(cname) { err := errors.New(fmt.Sprintf("Invalid CNAME %s. You can't use Tsuru's application domain.", cname)) return &routeError{"setCName", err} } frontend := "frontend:" + backendName + "." + domain conn := connect() defer conn.Close() routes, err := redis.Strings(conn.Do("LRANGE", frontend, 0, -1)) if err != nil { return &routeError{"get", err} } if oldCName, err := redis.String(conn.Do("GET", "cname:"+backendName)); err == nil && oldCName != "" { err = r.UnsetCName(oldCName, backendName) if err != nil { return &routeError{"setCName", err} } } _, err = conn.Do("SET", "cname:"+backendName, cname) if err != nil { return &routeError{"set", err} } frontend = "frontend:" + cname for _, r := range routes { _, err := conn.Do("RPUSH", frontend, r) if err != nil { return &routeError{"setCName", err} } } return nil }
func (r hipacheRouter) RemoveRoute(name, address string) error { backendName, err := router.Retrieve(name) if err != nil { return err } domain, err := config.GetString("hipache:domain") if err != nil { return &routeError{"remove", err} } frontend := "frontend:" + backendName + "." + domain if err := r.removeElement(frontend, address); err != nil { return err } cname, err := r.getCName(backendName) if err != nil { return &routeError{"remove", err} } if cname == "" { return nil } return r.removeElement("frontend:"+cname, address) }
func (r hipacheRouter) RemoveBackend(name string) error { backendName, err := router.Retrieve(name) if err != nil { return err } domain, err := config.GetString("hipache:domain") if err != nil { return &routeError{"remove", err} } frontend := "frontend:" + backendName + "." + domain conn := connect() defer conn.Close() _, err = conn.Do("DEL", frontend) if err != nil { return &routeError{"remove", err} } err = router.Remove(backendName) if err != nil { return &routeError{"remove", err} } cname, err := r.getCName(backendName) if err != nil { return err } if cname == "" { return nil } _, err = conn.Do("DEL", "frontend:"+cname) if err != nil { return &routeError{"remove", err} } _, err = conn.Do("DEL", "cname:"+backendName) if err != nil { return &routeError{"remove", err} } return nil }