Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions cli/cmd/delete.go
Original file line number Diff line number Diff line change
Expand Up @@ -66,8 +66,8 @@ var _deleteCmd = &cobra.Command{
exit.Error(err)
}
} else {
// local only supports deploying 1 replica at a time so _flagDeleteForce will be ignored
deleteResponse, err = local.Delete(args[0], _flagDeleteKeepCache)
// local only supports deploying 1 replica at a time, so _flagDeleteForce is only useful when attempting to delete an API that has been deployed with different CLI version
deleteResponse, err = local.Delete(args[0], _flagDeleteKeepCache, _flagDeleteForce)
if err != nil {
exit.Error(err)
}
Expand Down
2 changes: 1 addition & 1 deletion cli/cmd/deploy.go
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ var _deployCmd = &cobra.Command{
exit.Error(err)
}

deployResponse, err = local.Deploy(env, configPath, projectFiles)
deployResponse, err = local.Deploy(env, configPath, projectFiles, _flagDeployDisallowPrompt)
if err != nil {
exit.Error(err)
}
Expand Down
54 changes: 52 additions & 2 deletions cli/local/api.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,17 +27,41 @@ import (
"github.com/cortexlabs/cortex/pkg/lib/files"
"github.com/cortexlabs/cortex/pkg/lib/msgpack"
"github.com/cortexlabs/cortex/pkg/lib/pointer"
"github.com/cortexlabs/cortex/pkg/lib/prompt"
"github.com/cortexlabs/cortex/pkg/lib/sets/strset"
"github.com/cortexlabs/cortex/pkg/types/spec"
"github.com/cortexlabs/cortex/pkg/types/userconfig"
)

var _deploymentID = "local"

func UpdateAPI(apiConfig *userconfig.API, configPath string, projectID string, awsClient *aws.Client) (*spec.API, string, error) {
func UpdateAPI(apiConfig *userconfig.API, configPath string, projectID string, deployDisallowPrompt bool, awsClient *aws.Client) (*spec.API, string, error) {
var incompatibleVersion string
encounteredVersionMismatch := false
prevAPISpec, err := FindAPISpec(apiConfig.Name)
if err != nil {
if errors.GetKind(err) != ErrAPINotDeployed {
if errors.GetKind(err) == ErrCortexVersionMismatch {
encounteredVersionMismatch = true
if incompatibleVersion, err = GetVersionFromAPISpec(apiConfig.Name); err != nil {
return nil, "", err
}

incompatibleMinorVersion := strings.Join(strings.Split(incompatibleVersion, ".")[:2], ".")
if consts.CortexVersionMinor != incompatibleMinorVersion && !deployDisallowPrompt {
prompt.YesOrExit(
fmt.Sprintf(
"api %s was deployed using CLI version %s but the current CLI version is %s; "+
"re-deploying %s with current CLI version %s might yield an unexpected outcome; any cached models won't be deleted\n\n"+
"it is recommended to download version %s of the CLI from https://docs.cortex.dev/v/%s/install, delete the API using version %s of the CLI and then re-deploy the API using the latest version of the CLI\n\n"+
"do you still want to re-deploy?",
apiConfig.Name, incompatibleMinorVersion, consts.CortexVersionMinor, apiConfig.Name, consts.CortexVersionMinor, incompatibleMinorVersion, incompatibleMinorVersion, incompatibleMinorVersion),
"", "",
)
}
if err := DeleteAPI(apiConfig.Name); err != nil {
return nil, "", err
}
} else if errors.GetKind(err) != ErrAPINotDeployed {
return nil, "", err
}
}
Expand Down Expand Up @@ -88,6 +112,13 @@ func UpdateAPI(apiConfig *userconfig.API, configPath string, projectID string, a
}

if prevAPISpec == nil && len(prevAPIContainers) == 0 {
if encounteredVersionMismatch {
return newAPISpec, fmt.Sprintf(
"creating api %s with current CLI version %s",
newAPISpec.Name,
consts.CortexVersion,
), nil
}
return newAPISpec, fmt.Sprintf("creating %s", newAPISpec.Name), nil
}

Expand Down Expand Up @@ -202,6 +233,25 @@ func FindAPISpec(apiName string) (*spec.API, error) {
return nil, ErrorAPINotDeployed(apiName)
}

func GetVersionFromAPISpec(apiName string) (string, error) {
apiWorkspace := filepath.Join(_localWorkspaceDir, "apis", apiName)
if !files.IsDir(apiWorkspace) {
return "", ErrorAPINotDeployed(apiName)
}

filepaths, err := files.ListDirRecursive(apiWorkspace, false)
if err != nil {
return "", errors.Wrap(err, "api", apiName)
}

for _, specPath := range filepaths {
if strings.HasSuffix(filepath.Base(specPath), "-spec.msgpack") {
return GetVersionFromAPISpecFilePath(specPath), nil
}
}
return "", ErrorAPINotDeployed(apiName)
}

func GetVersionFromAPISpecFilePath(path string) string {
fileName := filepath.Base(path)
return strings.Split(fileName, "-")[0]
Expand Down
48 changes: 40 additions & 8 deletions cli/local/delete.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,30 +18,62 @@ package local

import (
"fmt"
"strings"

"github.com/cortexlabs/cortex/pkg/consts"
"github.com/cortexlabs/cortex/pkg/lib/docker"
"github.com/cortexlabs/cortex/pkg/lib/errors"
"github.com/cortexlabs/cortex/pkg/lib/prompt"
"github.com/cortexlabs/cortex/pkg/operator/schema"
"github.com/cortexlabs/cortex/pkg/types/spec"
)

func Delete(apiName string, keepCache bool) (schema.DeleteResponse, error) {
func Delete(apiName string, keepCache, deleteForce bool) (schema.DeleteResponse, error) {
_, err := docker.GetDockerClient()
if err != nil {
return schema.DeleteResponse{}, err
}

var apiSpec *spec.API = nil
if !keepCache {
if apiSpec, err = FindAPISpec(apiName); err != nil {
return schema.DeleteResponse{}, err
if apiSpec, err = FindAPISpec(apiName); err != nil {
if errors.GetKind(err) == ErrCortexVersionMismatch {
var incompatibleVersion string
if incompatibleVersion, err = GetVersionFromAPISpec(apiName); err != nil {
return schema.DeleteResponse{}, err
}

incompatibleMinorVersion := strings.Join(strings.Split(incompatibleVersion, ".")[:2], ".")
if consts.CortexVersionMinor != incompatibleMinorVersion && !deleteForce {
prompt.YesOrExit(
fmt.Sprintf(
"api %s was deployed using CLI version %s but the current CLI version is %s; "+
"deleting %s with current CLI version %s might lead to an unexpected state; any cached models won't be deleted\n\n"+
"it is recommended to download version %s of the CLI from https://docs.cortex.dev/v/%s/install, delete the API using version %s of the CLI and then re-deploy the API using the latest version of the CLI\n\n"+
"do you still want to delete?",
apiName, incompatibleMinorVersion, consts.CortexVersionMinor, apiName, consts.CortexVersionMinor, incompatibleMinorVersion, incompatibleMinorVersion, incompatibleMinorVersion),
"", "",
)
}

if err = DeleteAPI(apiName); err != nil {
return schema.DeleteResponse{}, err
}
return schema.DeleteResponse{
Message: fmt.Sprintf("deleting api %s with current CLI version %s", apiName, consts.CortexVersion),
}, nil
}

return schema.DeleteResponse{}, DeleteAPI(apiName)
}

err = errors.FirstError(
DeleteAPI(apiName),
DeleteCachedModels(apiName, apiSpec.ModelIDs()),
)
if keepCache {
err = DeleteAPI(apiName)
} else {
err = errors.FirstError(
DeleteAPI(apiName),
DeleteCachedModels(apiName, apiSpec.ModelIDs()),
)
}
if err != nil {
return schema.DeleteResponse{}, err
}
Expand Down
4 changes: 2 additions & 2 deletions cli/local/deploy.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ import (
"github.com/cortexlabs/cortex/pkg/types/spec"
)

func Deploy(env cliconfig.Environment, configPath string, projectFileList []string) (schema.DeployResponse, error) {
func Deploy(env cliconfig.Environment, configPath string, projectFileList []string, deployDisallowPrompt bool) (schema.DeployResponse, error) {
configFileName := filepath.Base(configPath)

_, err := docker.GetDockerClient()
Expand Down Expand Up @@ -80,7 +80,7 @@ func Deploy(env cliconfig.Environment, configPath string, projectFileList []stri

results := make([]schema.DeployResult, len(apiConfigs))
for i, apiConfig := range apiConfigs {
api, msg, err := UpdateAPI(&apiConfig, configPath, projectID, awsClient)
api, msg, err := UpdateAPI(&apiConfig, configPath, projectID, deployDisallowPrompt, awsClient)
results[i].Message = msg
if err != nil {
results[i].Error = errors.Message(err)
Expand Down