github.com/hasnat/dolt/go@v0.0.0-20210628190320-9eb5d843fbb7/libraries/doltcore/env/actions/workspace.go (about) 1 // Copyright 2020 Dolthub, Inc. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package actions 16 17 import ( 18 "context" 19 "errors" 20 21 "github.com/dolthub/dolt/go/libraries/doltcore/doltdb" 22 "github.com/dolthub/dolt/go/libraries/doltcore/env" 23 "github.com/dolthub/dolt/go/libraries/doltcore/ref" 24 ) 25 26 var ErrUnmergedWorkspaceDelete = errors.New("attempted to delete a workspace that is not fully merged into master; use `-f` to force") 27 var ErrCOWorkspaceDelete = errors.New("attempted to delete checked out workspace") 28 var ErrBranchNameExists = errors.New("workspace name must not be existing branch name") 29 30 func CreateWorkspace(ctx context.Context, dEnv *env.DoltEnv, name, startPoint string) error { 31 return CreateWorkspaceOnDB(ctx, dEnv.DoltDB, name, startPoint, dEnv.RepoState.CWBHeadRef()) 32 } 33 34 func CreateWorkspaceOnDB(ctx context.Context, ddb *doltdb.DoltDB, name, startPoint string, headRef ref.DoltRef) error { 35 isBranch, err := IsBranchOnDB(ctx, ddb, name) 36 if err != nil { 37 return err 38 } 39 if isBranch { 40 return ErrBranchNameExists 41 } 42 43 if !doltdb.IsValidUserBranchName(name) { 44 return doltdb.ErrInvWorkspaceName 45 } 46 47 workRef := ref.NewWorkspaceRef(name) 48 49 hasRef, err := ddb.HasRef(ctx, workRef) 50 if err != nil { 51 return err 52 } 53 if hasRef { 54 return ErrAlreadyExists 55 } 56 57 cs, err := doltdb.NewCommitSpec(startPoint) 58 if err != nil { 59 return err 60 } 61 62 cm, err := ddb.Resolve(ctx, cs, headRef) 63 if err != nil { 64 return err 65 } 66 67 return ddb.NewWorkspaceAtCommit(ctx, workRef, cm) 68 } 69 70 func IsWorkspaceOnDB(ctx context.Context, ddb *doltdb.DoltDB, str string) (bool, error) { 71 dref := ref.NewWorkspaceRef(str) 72 return ddb.HasRef(ctx, dref) 73 } 74 75 func IsWorkspace(ctx context.Context, dEnv *env.DoltEnv, str string) (bool, error) { 76 return IsWorkspaceOnDB(ctx, dEnv.DoltDB, str) 77 } 78 79 func DeleteWorkspace(ctx context.Context, dEnv *env.DoltEnv, workspaceName string, opts DeleteOptions) error { 80 var dref ref.DoltRef 81 if opts.Remote { 82 var err error 83 dref, err = ref.NewRemoteRefFromPathStr(workspaceName) 84 if err != nil { 85 return err 86 } 87 } else { 88 dref = ref.NewWorkspaceRef(workspaceName) 89 if ref.Equals(dEnv.RepoState.CWBHeadRef(), dref) { 90 return ErrCOWorkspaceDelete 91 } 92 } 93 94 return DeleteWorkspaceOnDB(ctx, dEnv.DoltDB, dref, opts) 95 } 96 97 func DeleteWorkspaceOnDB(ctx context.Context, ddb *doltdb.DoltDB, dref ref.DoltRef, opts DeleteOptions) error { 98 hasRef, err := ddb.HasRef(ctx, dref) 99 100 if err != nil { 101 return err 102 } else if !hasRef { 103 return doltdb.ErrWorkspaceNotFound 104 } 105 106 if !opts.Force && !opts.Remote { 107 ms, err := doltdb.NewCommitSpec("master") 108 if err != nil { 109 return err 110 } 111 112 master, err := ddb.Resolve(ctx, ms, nil) 113 if err != nil { 114 return err 115 } 116 117 cs, err := doltdb.NewCommitSpec(dref.String()) 118 if err != nil { 119 return err 120 } 121 122 cm, err := ddb.Resolve(ctx, cs, nil) 123 if err != nil { 124 return err 125 } 126 127 isMerged, _ := master.CanFastReverseTo(ctx, cm) 128 if err != nil && err != doltdb.ErrUpToDate { 129 return err 130 } 131 if !isMerged { 132 return ErrUnmergedWorkspaceDelete 133 } 134 } 135 136 return ddb.DeleteWorkspace(ctx, dref) 137 }