예제 #1
0
func (self *CoordinatorImpl) DropDatabase(user common.User, db string) error {
	if !user.IsClusterAdmin() {
		return fmt.Errorf("Insufficient permission to drop database")
	}

	return self.raftServer.DropDatabase(db)
}
예제 #2
0
func (self *Permissions) AuthorizeDeleteClusterAdmin(user common.User) (ok bool, err common.AuthorizationError) {
	if !user.IsClusterAdmin() {
		return false, common.NewAuthorizationError("Insufficient permissions to delete cluster admin")
	}

	return true, ""
}
예제 #3
0
func (self *CoordinatorImpl) ListContinuousQueries(user common.User, db string) ([]*protocol.Series, error) {
	if !user.IsClusterAdmin() && !user.IsDbAdmin(db) {
		return nil, common.NewAuthorizationError("Insufficient permissions to list continuous queries")
	}

	queries := self.clusterConfiguration.GetContinuousQueries(db)
	points := []*protocol.Point{}

	for _, query := range queries {
		queryId := int64(query.Id)
		queryString := query.Query
		timestamp := time.Now().Unix()
		sequenceNumber := uint64(1)
		points = append(points, &protocol.Point{
			Values: []*protocol.FieldValue{
				&protocol.FieldValue{Int64Value: &queryId},
				&protocol.FieldValue{StringValue: &queryString},
			},
			Timestamp:      &timestamp,
			SequenceNumber: &sequenceNumber,
		})
	}
	seriesName := "continuous queries"
	series := []*protocol.Series{&protocol.Series{
		Name:   &seriesName,
		Fields: []string{"id", "query"},
		Points: points,
	}}
	return series, nil
}
예제 #4
0
func (self *Permissions) AuthorizeChangeClusterAdminPassword(user common.User) (ok bool, err common.AuthorizationError) {
	if !user.IsClusterAdmin() {
		return false, common.NewAuthorizationError("Insufficient permissions to change cluster admin password")
	}

	return true, ""
}
예제 #5
0
func (self *CoordinatorImpl) ListClusterAdmins(requester common.User) ([]string, error) {
	if !requester.IsClusterAdmin() {
		return nil, common.NewAuthorizationError("Insufficient permissions")
	}

	return self.clusterConfiguration.GetClusterAdmins(), nil
}
예제 #6
0
func (self *CoordinatorImpl) DropDatabase(user common.User, db string) error {
	if !user.IsClusterAdmin() {
		return common.NewAuthorizationError("Insufficient permission to drop database")
	}

	if self.clusterConfiguration.IsSingleServer() {
		if err := self.datastore.DropDatabase(db); err != nil {
			return err
		}
	} else {
		servers, _ := self.clusterConfiguration.GetServersToMakeQueryTo(&db)
		for _, server := range servers {
			if err := self.handleDropDatabase(server.server, db); err != nil {
				return err
			}
		}
	}

	// don't delete the metadata, we need the replication factor to be
	// able to replicate the request properly
	if err := self.raftServer.DropDatabase(db); err != nil {
		return err
	}

	return nil
}
예제 #7
0
func (self *CoordinatorImpl) ChangeDbUserPermissions(requester common.User, db, username, readPermissions, writePermissions string) error {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) {
		return common.NewAuthorizationError("Insufficient permissions")
	}

	return self.raftServer.ChangeDbUserPermissions(db, username, readPermissions, writePermissions)
}
예제 #8
0
func (self *CoordinatorImpl) CreateDbUser(requester common.User, db, username, password string) error {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) {
		return common.NewAuthorizationError("Insufficient permissions")
	}

	if username == "" {
		return fmt.Errorf("Username cannot be empty")
	}

	if !isValidName(username) {
		return fmt.Errorf("%s isn't a valid username", username)
	}

	hash, err := cluster.HashPassword(password)
	if err != nil {
		return err
	}

	self.CreateDatabase(requester, db, uint8(1)) // ignore the error since the db may exist
	if self.clusterConfiguration.GetDbUser(db, username) != nil {
		return fmt.Errorf("User %s already exists", username)
	}
	matchers := []*cluster.Matcher{&cluster.Matcher{true, ".*"}}
	log.Debug("(raft:%s) Creating user %s:%s", self.raftServer.(*RaftServer).raftServer.Name(), db, username)
	return self.raftServer.SaveDbUser(&cluster.DbUser{cluster.CommonUser{
		Name:     username,
		Hash:     string(hash),
		CacheKey: db + "%" + username,
	}, db, matchers, matchers, false})
}
예제 #9
0
func (self *CoordinatorImpl) ForceCompaction(user common.User) error {
	if !user.IsClusterAdmin() {
		return fmt.Errorf("Insufficient permissions to force a log compaction")
	}

	return self.raftServer.ForceLogCompaction()
}
예제 #10
0
func (self *CoordinatorImpl) ListDbUsers(requester common.User, db string) ([]common.User, error) {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) {
		return nil, common.NewAuthorizationError("Insufficient permissions")
	}

	return self.clusterConfiguration.GetDbUsers(db), nil
}
예제 #11
0
func (self *Permissions) AuthorizeDropDatabase(user common.User) (ok bool, err common.AuthorizationError) {
	if !user.IsClusterAdmin() {
		return false, common.NewAuthorizationError("Insufficient permissions to drop database")
	}

	return true, ""
}
예제 #12
0
func (self *CoordinatorImpl) CreateSubscription(requester common.User, subscription *cluster.Subscription) error {
	if !requester.IsClusterAdmin() {
		return common.NewAuthorizationError("Insufficient permissions")
	}

	return self.raftServer.SaveSubscription(subscription)
	return nil
}
예제 #13
0
func (self *CoordinatorImpl) ListDatabases(user common.User) ([]string, error) {
	if !user.IsClusterAdmin() {
		return nil, fmt.Errorf("Insufficient permission to list databases")
	}

	dbs := self.clusterConfiguration.GetDatabases()
	return dbs, nil
}
예제 #14
0
func (self *CoordinatorImpl) ListDatabases(user common.User) ([]*cluster.Database, error) {
	if !user.IsClusterAdmin() {
		return nil, common.NewAuthorizationError("Insufficient permissions to list databases")
	}

	dbs := self.clusterConfiguration.GetDatabases()
	return dbs, nil
}
예제 #15
0
func (self *CoordinatorImpl) DeleteContinuousQuery(user common.User, db string, id uint32) error {
	if !user.IsClusterAdmin() && !user.IsDbAdmin(db) {
		return common.NewAuthorizationError("Insufficient permissions to delete continuous query")
	}

	err := self.raftServer.DeleteContinuousQuery(db, id)
	if err != nil {
		return err
	}
	return nil
}
예제 #16
0
func (self *CoordinatorImpl) ListSubscriptions(user common.User) error /*([]*Subscription, error)*/ {
	if !user.IsClusterAdmin() {
		return common.NewAuthorizationError("Insufficient permissions to list subscriptions")
	}

	fmt.Println("I reached coordinator listsubscriptions")
	subscriptions := self.clusterConfiguration.GetSubscriptions()
	fmt.Println(subscriptions)
	return nil
	//return subscriptions, nil
}
예제 #17
0
func (self *CoordinatorImpl) SubscribeTimeSeries(user common.User) error /*([]*Subscription, error)*/ {
	if !user.IsClusterAdmin() {
		return common.NewAuthorizationError("Insufficient permissions to make a subscription")
	}

	fmt.Println("subscribing to a database")

	//subscriptions := self.clusterConfiguration.GetSubscriptions()
	//return subscriptions, nil
	return nil
}
예제 #18
0
func (self *CoordinatorImpl) DropDatabase(user common.User, db string) error {
	if !user.IsClusterAdmin() {
		return common.NewAuthorizationError("Insufficient permission to drop database")
	}

	if err := self.raftServer.DropDatabase(db); err != nil {
		return err
	}

	return self.datastore.DropDatabase(db)
}
예제 #19
0
func (self *CoordinatorImpl) CreateClusterAdminUser(requester common.User, username string) error {
	if !requester.IsClusterAdmin() {
		return fmt.Errorf("Insufficient permissions")
	}

	if self.clusterConfiguration.clusterAdmins[username] != nil {
		return fmt.Errorf("User %s already exists", username)
	}

	return self.raftServer.SaveClusterAdminUser(&clusterAdmin{CommonUser{Name: username}})
}
예제 #20
0
func (self *CoordinatorImpl) ChangeDbUserPassword(requester common.User, db, username, password string) error {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) && !(requester.GetDb() == db && requester.GetName() == username) {
		return common.NewAuthorizationError("Insufficient permissions")
	}

	hash, err := cluster.HashPassword(password)
	if err != nil {
		return err
	}
	return self.raftServer.ChangeDbUserPassword(db, username, hash)
}
예제 #21
0
func (self *CoordinatorImpl) CreateDatabase(user common.User, db string) error {
	if !user.IsClusterAdmin() {
		return fmt.Errorf("Insufficient permission to create database")
	}

	err := self.raftServer.CreateDatabase(db)
	if err != nil {
		return err
	}
	return nil
}
예제 #22
0
func (self *CoordinatorImpl) CreateDatabase(user common.User, db string, replicationFactor uint8) error {
	if !user.IsClusterAdmin() {
		return common.NewAuthorizationError("Insufficient permission to create database")
	}

	err := self.raftServer.CreateDatabase(db, replicationFactor)
	if err != nil {
		return err
	}
	return nil
}
예제 #23
0
func (self *CoordinatorImpl) GetDbUser(requester common.User, db string, username string) (common.User, error) {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) {
		return nil, common.NewAuthorizationError("Insufficient permissions")
	}

	dbUser := self.clusterConfiguration.GetDbUser(db, username)
	if dbUser == nil {
		return nil, fmt.Errorf("Invalid username %s", username)
	}

	return dbUser, nil
}
예제 #24
0
func (self *CoordinatorImpl) DeleteDbUser(requester common.User, db, username string) error {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) {
		return common.NewAuthorizationError("Insufficient permissions")
	}

	user := self.clusterConfiguration.GetDbUser(db, username)
	if user == nil {
		return fmt.Errorf("User %s doesn't exist", username)
	}
	user.CommonUser.IsUserDeleted = true
	return self.raftServer.SaveDbUser(user)
}
예제 #25
0
// Distributes the query across the cluster and combines the results. Yields as they come in ensuring proper order.
// TODO: make this work even if there is a downed server in the cluster
func (self *CoordinatorImpl) DistributeQuery(user common.User, db string, query *parser.SelectQuery, localOnly bool, yield func(*protocol.Series) error) error {
	if self.clusterConfiguration.IsSingleServer() || localOnly {
		return self.datastore.ExecuteQuery(user, db, query, yield, nil)
	}
	servers, replicationFactor := self.clusterConfiguration.GetServersToMakeQueryTo(&db)
	id := atomic.AddUint32(&self.requestId, uint32(1))
	userName := user.GetName()
	isDbUser := !user.IsClusterAdmin()
	responseChannels := make([]chan *protocol.Response, 0, len(servers)+1)
	queryString := query.GetQueryString()
	var localServerToQuery *serverToQuery
	for _, server := range servers {
		if server.server.Id == self.clusterConfiguration.localServerId {
			localServerToQuery = server
		} else {
			request := &protocol.Request{Type: &queryRequest, Query: &queryString, Id: &id, Database: &db, UserName: &userName, IsDbUser: &isDbUser}
			if server.ringLocationsToQuery != replicationFactor {
				r := server.ringLocationsToQuery
				request.RingLocationsToQuery = &r
			}
			responseChan := make(chan *protocol.Response, 3)
			server.server.MakeRequest(request, responseChan)
			responseChannels = append(responseChannels, responseChan)
		}
	}

	local := make(chan *protocol.Response)
	nextPointMap := make(map[string]*NextPoint)

	// TODO: this style of wrapping the series in response objects with the
	//       last point time is duplicated in the request handler. Refactor...
	sendFromLocal := func(series *protocol.Series) error {
		response := createResponse(nextPointMap, series, nil)
		local <- response
		return nil
	}
	responseChannels = append(responseChannels, local)
	// TODO: wire up the willreturnsingleseries method and uncomment this line and delete the next one.
	//	isSingleSeriesQuery := query.WillReturnSingleSeries()
	isSingleSeriesQuery := false

	go func() {
		var ringFilter func(database, series *string, time *int64) bool
		if replicationFactor != localServerToQuery.ringLocationsToQuery {
			ringFilter = self.clusterConfiguration.GetRingFilterFunction(db, localServerToQuery.ringLocationsToQuery)
		}
		self.datastore.ExecuteQuery(user, db, query, sendFromLocal, ringFilter)
		local <- &protocol.Response{Type: &endStreamResponse}
		close(local)
	}()
	self.streamResultsFromChannels(isSingleSeriesQuery, query.Ascending, responseChannels, yield)
	return nil
}
예제 #26
0
func (self *CoordinatorImpl) ListSeries(user common.User, database string) ([]*protocol.Series, error) {
	if self.clusterConfiguration.IsSingleServer() {
		dbs := []string{}
		self.datastore.GetSeriesForDatabase(database, func(db string) error {
			dbs = append(dbs, db)
			return nil
		})
		return seriesFromListSeries(dbs), nil
	}
	servers, replicationFactor := self.clusterConfiguration.GetServersToMakeQueryTo(&database)
	id := atomic.AddUint32(&self.requestId, uint32(1))
	userName := user.GetName()
	isDbUser := !user.IsClusterAdmin()
	responseChannels := make([]chan *protocol.Response, 0, len(servers)+1)
	for _, server := range servers {
		if server.server.Id == self.clusterConfiguration.localServerId {
			continue
		}
		request := &protocol.Request{Type: &listSeriesRequest, Id: &id, Database: &database, UserName: &userName, IsDbUser: &isDbUser}
		if server.ringLocationsToQuery != replicationFactor {
			r := server.ringLocationsToQuery
			request.RingLocationsToQuery = &r
		}
		responseChan := make(chan *protocol.Response, 3)
		server.server.protobufClient.MakeRequest(request, responseChan)
		responseChannels = append(responseChannels, responseChan)
	}

	local := make(chan *protocol.Response)

	responseChannels = append(responseChannels, local)

	go func() {
		dbs := []string{}
		self.datastore.GetSeriesForDatabase(database, func(db string) error {
			dbs = append(dbs, db)
			return nil
		})
		seriesArray := seriesFromListSeries(dbs)
		for _, series := range seriesArray {
			local <- &protocol.Response{Type: &listSeriesResponse, Series: series}
		}
		local <- &protocol.Response{Type: &endStreamResponse}
		close(local)
	}()
	seriesArray := []*protocol.Series{}
	self.streamResultsFromChannels(true, true, responseChannels, func(series *protocol.Series) error {
		seriesArray = append(seriesArray, series)
		return nil
	})
	return seriesArray, nil
}
예제 #27
0
func (self *CoordinatorImpl) SetDbAdmin(requester common.User, db, username string, isAdmin bool) error {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) {
		return common.NewAuthorizationError("Insufficient permissions")
	}

	user := self.clusterConfiguration.GetDbUser(db, username)
	if user == nil {
		return fmt.Errorf("Invalid username %s", username)
	}
	user.IsAdmin = isAdmin
	self.raftServer.SaveDbUser(user)
	return nil
}
예제 #28
0
func (self *CoordinatorImpl) ChangeClusterAdminPassword(requester common.User, username, password string) error {
	if !requester.IsClusterAdmin() {
		return fmt.Errorf("Insufficient permissions")
	}

	user := self.clusterConfiguration.clusterAdmins[username]
	if user == nil {
		return fmt.Errorf("Invalid user name %s", username)
	}

	user.changePassword(password)
	return self.raftServer.SaveClusterAdminUser(user)
}
예제 #29
0
func (self *CoordinatorImpl) DeleteClusterAdminUser(requester common.User, username string) error {
	if !requester.IsClusterAdmin() {
		return fmt.Errorf("Insufficient permissions")
	}

	user := self.clusterConfiguration.clusterAdmins[username]
	if user == nil {
		return fmt.Errorf("User %s doesn't exists", username)
	}

	user.CommonUser.IsUserDeleted = true
	return self.raftServer.SaveClusterAdminUser(user)
}
예제 #30
0
func (self *CoordinatorImpl) ChangeDbUserPassword(requester common.User, db, username, password string) error {
	if !requester.IsClusterAdmin() && !requester.IsDbAdmin(db) && !(requester.GetDb() == db && requester.GetName() == username) {
		return fmt.Errorf("Insufficient permissions")
	}

	dbUsers := self.clusterConfiguration.dbUsers[db]
	if dbUsers == nil || dbUsers[username] == nil {
		return fmt.Errorf("Invalid username %s", username)
	}

	dbUsers[username].changePassword(password)
	return self.raftServer.SaveDbUser(dbUsers[username])
}