func dbContainerRename(db *sql.DB, oldName string, newName string) error { if !strings.Contains(newName, shared.SnapshotDelimiter) && !shared.ValidHostname(newName) { return fmt.Errorf("Invalid container name") } tx, err := dbBegin(db) if err != nil { return err } str := fmt.Sprintf("UPDATE containers SET name = ? WHERE name = ?") stmt, err := tx.Prepare(str) if err != nil { tx.Rollback() return err } defer stmt.Close() shared.Log.Debug( "Calling SQL Query", log.Ctx{ "query": "UPDATE containers SET name = ? WHERE name = ?", "oldName": oldName, "newName": newName}) if _, err := stmt.Exec(newName, oldName); err != nil { tx.Rollback() return err } return txCommit(tx) }
func dbContainerCreate(db *sql.DB, name string, args containerLXDArgs) (int, error) { if args.Ctype == cTypeRegular && !shared.ValidHostname(name) { return 0, fmt.Errorf("Invalid container name") } id, err := dbContainerIDGet(db, name) if err == nil { return 0, DbErrAlreadyDefined } tx, err := dbBegin(db) if err != nil { return 0, err } ephemInt := 0 if args.Ephemeral == true { ephemInt = 1 } str := fmt.Sprintf("INSERT INTO containers (name, architecture, type, ephemeral) VALUES (?, ?, ?, ?)") stmt, err := tx.Prepare(str) if err != nil { tx.Rollback() return 0, err } defer stmt.Close() result, err := stmt.Exec(name, args.Architecture, args.Ctype, ephemInt) if err != nil { tx.Rollback() return 0, err } id64, err := result.LastInsertId() if err != nil { tx.Rollback() return 0, fmt.Errorf("Error inserting %s into database", name) } // TODO: is this really int64? we should fix it everywhere if so id = int(id64) if err := dbContainerConfigInsert(tx, id, args.Config); err != nil { tx.Rollback() return 0, err } if err := dbContainerProfilesInsert(tx, id, args.Profiles); err != nil { tx.Rollback() return 0, err } if err := dbDevicesAdd(tx, "container", int64(id), args.Devices); err != nil { tx.Rollback() return 0, err } return id, txCommit(tx) }
func (c *containerLXD) Rename(newName string) error { oldName := c.NameGet() if !c.IsSnapshot() && !shared.ValidHostname(newName) { return fmt.Errorf("Invalid container name") } if c.IsRunning() { return fmt.Errorf("renaming of running container not allowed") } if c.IsSnapshot() { if err := c.Storage.ContainerSnapshotRename(c, newName); err != nil { return err } } else { if err := c.Storage.ContainerRename(c, newName); err != nil { return err } } if err := dbContainerRename(c.daemon.db, oldName, newName); err != nil { return err } results, err := dbContainerGetSnapshots(c.daemon.db, oldName) if err != nil { return err } for _, sname := range results { sc, err := containerLXDLoad(c.daemon, sname) if err != nil { shared.Log.Error( "containerDeleteSnapshots: Failed to load the snapshotcontainer", log.Ctx{"container": oldName, "snapshot": sname}) continue } baseSnapName := filepath.Base(sname) newSnapshotName := newName + shared.SnapshotDelimiter + baseSnapName if err := sc.Rename(newSnapshotName); err != nil { shared.Log.Error( "containerDeleteSnapshots: Failed to rename a snapshotcontainer", log.Ctx{"container": oldName, "snapshot": sname, "err": err}) } } c.name = newName // Recreate the LX Container c.c = nil c.init() return nil }
func containerValidName(name string) error { if strings.Contains(name, shared.SnapshotDelimiter) { return fmt.Errorf( "The character '%s' is reserved for snapshots.", shared.SnapshotDelimiter) } if !shared.ValidHostname(name) { return fmt.Errorf("Container name isn't a valid hostname.") } return nil }