func (b *BrickEntry) DestroyCheck(db *bolt.DB, executor executors.Executor) error { godbc.Require(db != nil) godbc.Require(b.TpSize > 0) godbc.Require(b.Info.Size > 0) // Get node hostname var host string err := db.View(func(tx *bolt.Tx) error { node, err := NewNodeEntryFromId(tx, b.Info.NodeId) if err != nil { return err } host = node.ManageHostName() godbc.Check(host != "") return nil }) if err != nil { return err } // Create request req := &executors.BrickRequest{} req.Name = b.Info.Id req.Size = b.Info.Size req.TpSize = b.TpSize req.VgId = b.Info.DeviceId // Check brick on node return executor.BrickDestroyCheck(host, req) }
func (b *BrickEntry) Destroy(db *bolt.DB, executor executors.Executor) error { godbc.Require(db != nil) godbc.Require(b.TpSize > 0) godbc.Require(b.Info.Size > 0) if b.State != BRICK_STATE_ONLINE { return nil } // Get node hostname var host string err := db.View(func(tx *bolt.Tx) error { node, err := NewNodeEntryFromId(tx, b.Info.NodeId) if err != nil { return err } host = node.ManageHostName() godbc.Check(host != "") return nil }) if err != nil { return err } // Create request req := &executors.BrickRequest{} req.Name = b.Info.Id req.Size = b.Info.Size req.TpSize = b.TpSize req.VgId = b.Info.DeviceId // Delete brick on node logger.Info("Deleting brick %v", b.Info.Id) err = executor.BrickDestroy(host, req) if err != nil { b.State = BRICK_STATE_FAILED return err } b.State = BRICK_STATE_DELETED godbc.Ensure(b.State == BRICK_STATE_DELETED) return nil }
func (b *BrickEntry) Create(db *bolt.DB, executor executors.Executor) error { godbc.Require(db != nil) godbc.Require(b.TpSize > 0) godbc.Require(b.Info.Size > 0) // Get node hostname var host string err := db.View(func(tx *bolt.Tx) error { node, err := NewNodeEntryFromId(tx, b.Info.NodeId) if err != nil { return err } host = node.ManageHostName() godbc.Check(host != "") return nil }) if err != nil { return err } // Create request req := &executors.BrickRequest{} req.Name = b.Info.Id req.Size = b.Info.Size req.TpSize = b.TpSize req.VgId = b.Info.DeviceId req.PoolMetadataSize = b.PoolMetadataSize // Create brick on node logger.Info("Creating brick %v", b.Info.Id) info, err := executor.BrickCreate(host, req) if err != nil { return err } b.Info.Path = info.Path b.State = BRICK_STATE_ONLINE godbc.Ensure(b.Info.Path != "") godbc.Ensure(b.State == BRICK_STATE_ONLINE) return nil }
func (v *VolumeEntry) createVolume(db *bolt.DB, executor executors.Executor, brick_entries []*BrickEntry) error { godbc.Require(db != nil) godbc.Require(brick_entries != nil) // Create a volume request for executor with // the bricks allocated vr, host, err := v.createVolumeRequest(db, brick_entries) if err != nil { return err } // Create the volume _, err = executor.VolumeCreate(host, vr) if err != nil { return err } // Get all brick hosts stringset := utils.NewStringSet() for _, brick := range vr.Bricks { stringset.Add(brick.Host) } hosts := stringset.Strings() v.Info.Mount.GlusterFS.Hosts = hosts // Save volume information v.Info.Mount.GlusterFS.MountPoint = fmt.Sprintf("%v:%v", hosts[0], vr.Name) // Set glusterfs mount volfile-servers options v.Info.Mount.GlusterFS.Options = make(map[string]string) v.Info.Mount.GlusterFS.Options["backup-volfile-servers"] = strings.Join(hosts[1:], ",") godbc.Ensure(v.Info.Mount.GlusterFS.MountPoint != "") return nil }
func (v *VolumeEntry) Expand(db *bolt.DB, executor executors.Executor, allocator Allocator, sizeGB int) (e error) { // Allocate new bricks in the cluster brick_entries, err := v.allocBricksInCluster(db, allocator, v.Info.Cluster, sizeGB) if err != nil { return err } // Setup cleanup function defer func() { if e != nil { logger.Debug("Error detected, cleaning up") // Remove from db db.Update(func(tx *bolt.Tx) error { for _, brick := range brick_entries { v.removeBrickFromDb(tx, brick) } err := v.Save(tx) godbc.Check(err == nil) return nil }) } }() // Create bricks err = CreateBricks(db, executor, brick_entries) if err != nil { logger.Err(err) return err } // Setup cleanup function defer func() { if e != nil { logger.Debug("Error detected, cleaning up") DestroyBricks(db, executor, brick_entries) } }() // Create a volume request to send to executor // so that it can add the new bricks vr, host, err := v.createVolumeRequest(db, brick_entries) if err != nil { return err } // Expand the volume _, err = executor.VolumeExpand(host, vr) if err != nil { return err } // Increase the recorded volume size v.Info.Size += sizeGB // Save volume entry err = db.Update(func(tx *bolt.Tx) error { // Save brick entries for _, brick := range brick_entries { err := brick.Save(tx) if err != nil { return err } } return v.Save(tx) }) return err }
func (v *VolumeEntry) Destroy(db *bolt.DB, executor executors.Executor) error { logger.Info("Destroying volume %v", v.Info.Id) // Get the entries from the database brick_entries := make([]*BrickEntry, len(v.Bricks)) var sshhost string db.View(func(tx *bolt.Tx) error { for index, id := range v.BricksIds() { brick, err := NewBrickEntryFromId(tx, id) if err != nil { logger.LogError("Brick %v not found in db: %v", id, err) continue } brick_entries[index] = brick // Set ssh host to send volume commands if sshhost == "" { node, err := NewNodeEntryFromId(tx, brick.Info.NodeId) if err != nil { logger.LogError("Unable to determine brick node: %v", err) return err } sshhost = node.ManageHostName() } } return nil }) // :TODO: What if the host is no longer available, we may need to try others // Stop volume err := executor.VolumeDestroy(sshhost, v.Info.Name) if err != nil { logger.LogError("Unable to delete volume: %v", err) return err } // Destroy bricks err = DestroyBricks(db, executor, brick_entries) if err != nil { logger.LogError("Unable to delete bricks: %v", err) return err } // Remove from entries from the db err = db.Update(func(tx *bolt.Tx) error { for _, brick := range brick_entries { err = v.removeBrickFromDb(tx, brick) if err != nil { logger.Err(err) // Everything is destroyed anyways, just keep deleting the others // Do not return here } } // Remove volume from cluster cluster, err := NewClusterEntryFromId(tx, v.Info.Cluster) if err != nil { logger.Err(err) // Do not return here.. keep going } cluster.VolumeDelete(v.Info.Id) err = cluster.Save(tx) if err != nil { logger.Err(err) // Do not return here.. keep going } // Delete volume v.Delete(tx) return nil }) return err }