Skip to content

Commit

Permalink
Merge branch 'version/0-42-0-RC1' into DX-2224
Browse files Browse the repository at this point in the history
  • Loading branch information
MDrakos committed Oct 23, 2023
2 parents bf15df1 + fb0e921 commit 999b04a
Show file tree
Hide file tree
Showing 76 changed files with 844 additions and 562 deletions.
13 changes: 13 additions & 0 deletions cmd/state-installer/cmd.go
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,19 @@ func main() {
logging.Debug("Original Args: %v", os.Args)
logging.Debug("Processed Args: %v", processedArgs)

// Store sessionToken to config
for _, envVar := range []string{constants.OverrideSessionTokenEnvVarName, constants.SessionTokenEnvVarName} {
sessionToken, ok := os.LookupEnv(envVar)
if !ok {
continue
}
err := cfg.Set(anaConst.CfgSessionToken, sessionToken)
if err != nil {
multilog.Error("Unable to set session token: " + errs.JoinMessage(err))
}
break
}

an = sync.New(anaConst.SrcStateInstaller, cfg, nil, out)
an.Event(anaConst.CatInstallerFunnel, "start")

Expand Down
18 changes: 3 additions & 15 deletions cmd/state-installer/installer.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ import (

svcApp "github.com/ActiveState/cli/cmd/state-svc/app"
svcAutostart "github.com/ActiveState/cli/cmd/state-svc/autostart"
anaConst "github.com/ActiveState/cli/internal/analytics/constants"
"github.com/ActiveState/cli/internal/config"
"github.com/ActiveState/cli/internal/constants"
"github.com/ActiveState/cli/internal/errs"
Expand All @@ -30,10 +29,9 @@ import (
)

type Installer struct {
out output.Outputer
cfg *config.Instance
payloadPath string
sessionToken string
out output.Outputer
cfg *config.Instance
payloadPath string
*Params
}

Expand All @@ -49,13 +47,6 @@ func NewInstaller(cfg *config.Instance, out output.Outputer, payloadPath string,
}

func (i *Installer) Install() (rerr error) {
// Store sessionToken to config
if i.sessionToken != "" && i.cfg.GetString(anaConst.CfgSessionToken) == "" {
if err := i.cfg.Set(anaConst.CfgSessionToken, i.sessionToken); err != nil {
return errs.Wrap(err, "Failed to set session token")
}
}

// Store update tag
if i.updateTag != "" {
if err := i.cfg.Set(updater.CfgUpdateTag, i.updateTag); err != nil {
Expand Down Expand Up @@ -145,9 +136,6 @@ func (i *Installer) InstallPath() string {

// sanitizeInput cleans up the input and inserts fallback values
func (i *Installer) sanitizeInput() error {
if sessionToken, ok := os.LookupEnv(constants.SessionTokenEnvVarName); ok {
i.sessionToken = sessionToken
}
if tag, ok := os.LookupEnv(constants.UpdateTagEnvVarName); ok {
i.updateTag = tag
}
Expand Down
81 changes: 1 addition & 80 deletions cmd/state-installer/test/integration/installer_int_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,17 +8,14 @@ import (
"runtime"
"strings"
"testing"
"time"

"github.com/ActiveState/termtest"
"github.com/stretchr/testify/suite"

"github.com/ActiveState/cli/internal/condition"
"github.com/ActiveState/cli/internal/config"
"github.com/ActiveState/cli/internal/constants"
"github.com/ActiveState/cli/internal/environment"
"github.com/ActiveState/cli/internal/fileutils"
"github.com/ActiveState/cli/internal/httputil"
"github.com/ActiveState/cli/internal/installation"
"github.com/ActiveState/cli/internal/osutils"
"github.com/ActiveState/cli/internal/subshell"
Expand All @@ -37,7 +34,7 @@ func (suite *InstallerIntegrationTestSuite) TestInstallFromLocalSource() {
ts := e2e.New(suite.T(), false)
defer ts.Close()

suite.SetupRCFile(ts)
ts.SetupRCFile()
suite.T().Setenv(constants.HomeEnvVarName, ts.Dirs.HomeDir)

dir, err := ioutil.TempDir("", "system*")
Expand Down Expand Up @@ -193,66 +190,6 @@ func (suite *InstallerIntegrationTestSuite) TestInstallErrorTips() {
"error tips should be displayed in shell created by installer")
}

func (suite *InstallerIntegrationTestSuite) TestStateTrayRemoval() {
suite.OnlyRunForTags(tagsuite.Installer, tagsuite.Critical)
ts := e2e.New(suite.T(), false)
defer ts.Close()

dir := installationDir(ts)

// Install a release version that still has state-tray.
version := "0.35.0-SHAb78e2a4"
var cp *e2e.SpawnedCmd
if runtime.GOOS != "windows" {
oneLiner := fmt.Sprintf("sh <(curl -q https://platform.activestate.com/dl/cli/pdli01/install.sh) -f -n -t %s -v %s", dir, version)
cp = ts.SpawnCmdWithOpts(
"bash", e2e.OptArgs("-c", oneLiner),
e2e.OptAppendEnv(fmt.Sprintf("%s=%s", constants.OverwriteDefaultSystemPathEnvVarName, dir)),
)
} else {
b, err := httputil.GetDirect("https://platform.activestate.com/dl/cli/pdli01/install.ps1")
suite.Require().NoError(err)

ps1File := filepath.Join(ts.Dirs.Work, "install.ps1")
suite.Require().NoError(fileutils.WriteFile(ps1File, b))

cp = ts.SpawnCmdWithOpts("powershell.exe", e2e.OptArgs(ps1File, "-f", "-n", "-t", dir, "-v", version),
e2e.OptAppendEnv("SHELL="),
e2e.OptAppendEnv(fmt.Sprintf("%s=%s", constants.OverwriteDefaultSystemPathEnvVarName, dir)),
)
}
cp.Expect("Installation Complete", termtest.OptExpectTimeout(5*time.Minute))

// Verify state-tray is there.
svcExec, err := installation.ServiceExecFromDir(dir)
suite.Require().NoError(err)
trayExec := strings.Replace(svcExec, constants.StateSvcCmd, "state-tray", 1)
suite.FileExists(trayExec)
updateDialogExec := strings.Replace(svcExec, constants.StateSvcCmd, "state-update-dialog", 1)
// suite.FileExists(updateDialogExec) // this is not actually installed...

// Run the installer, which should remove state-tray and clean up after it.
cp = ts.SpawnCmdWithOpts(
suite.installerExe,
e2e.OptArgs("-f", "-n", "-t", dir),
e2e.OptAppendEnv(constants.UpdateBranchEnvVarName+"=release"),
e2e.OptAppendEnv(fmt.Sprintf("%s=%s", constants.OverwriteDefaultSystemPathEnvVarName, dir)),
)
cp.Expect("Installing", termtest.OptExpectTimeout(10*time.Second))
cp.Expect("Done", termtest.OptExpectTimeout(30*time.Second))

// Verify state-tray is no longer there.
suite.NoFileExists(trayExec)
suite.NoFileExists(updateDialogExec)

// Verify state can still be run and has a newly updated version.
stateExec, err := installation.StateExecFromDir(dir)
suite.Require().NoError(err)
cp = ts.SpawnCmdWithOpts(stateExec, e2e.OptArgs("--version"))
suite.Assert().NotContains(cp.Output(), version)
cp.ExpectExitCode(0)
}

func (suite *InstallerIntegrationTestSuite) TestInstallerOverwriteServiceApp() {
suite.OnlyRunForTags(tagsuite.Installer)
if runtime.GOOS != "darwin" {
Expand Down Expand Up @@ -286,22 +223,6 @@ func (suite *InstallerIntegrationTestSuite) TestInstallerOverwriteServiceApp() {
cp.ExpectExitCode(0)
}

func (suite *InstallerIntegrationTestSuite) SetupRCFile(ts *e2e.Session) {
if runtime.GOOS == "windows" {
return
}

cfg, err := config.New()
suite.Require().NoError(err)

subshell := subshell.New(cfg)
rcFile, err := subshell.RcFile()
suite.Require().NoError(err)

err = fileutils.CopyFile(rcFile, filepath.Join(ts.Dirs.HomeDir, filepath.Base(rcFile)))
suite.Require().NoError(err)
}

func (suite *InstallerIntegrationTestSuite) AssertConfig(ts *e2e.Session) {
if runtime.GOOS != "windows" {
// Test bashrc
Expand Down
8 changes: 8 additions & 0 deletions cmd/state/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ import (
"github.com/ActiveState/cli/internal/prompt"
_ "github.com/ActiveState/cli/internal/prompt" // Sets up survey defaults
"github.com/ActiveState/cli/internal/rollbar"
"github.com/ActiveState/cli/internal/runbits/legacy/projectmigration"
"github.com/ActiveState/cli/internal/runbits/panics"
"github.com/ActiveState/cli/internal/subshell"
"github.com/ActiveState/cli/internal/svcctl"
Expand Down Expand Up @@ -211,6 +212,13 @@ func run(args []string, isInteractive bool, cfg *config.Instance, out output.Out
// Set up prompter
prompter := prompt.New(isInteractive, an)

// This is an anti-pattern. DO NOT DO THIS! Normally we should be passing prompt and out as
// arguments everywhere it is needed. However, we need to support legacy projects with commitId in
// activestate.yaml, and whenever that commitId is needed, we need to prompt the user to migrate
// their project. This would result in a lot of boilerplate for a legacy feature, so we're
// working around it with package "globals".
projectmigration.Register(prompter, out)

// Set up conditional, which accesses a lot of primer data
sshell := subshell.New(cfg)

Expand Down
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -133,7 +133,7 @@ require (
github.com/power-devops/perfstat v0.0.0-20210106213030-5aafc221ea8c // indirect
github.com/remyoudompheng/bigfft v0.0.0-20200410134404-eec4a21b6bb0 // indirect
github.com/rivo/uniseg v0.2.0 // indirect
github.com/sergi/go-diff v1.3.1
github.com/sergi/go-diff v1.3.2-0.20230802210424-5b0b94c5c0d3
github.com/src-d/gcfg v1.4.0 // indirect
github.com/stretchr/objx v0.5.0 // indirect
github.com/tklauser/go-sysconf v0.3.12 // indirect
Expand Down
2 changes: 2 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -941,6 +941,8 @@ github.com/sergi/go-diff v1.0.0/go.mod h1:0CfEIISq7TuYL3j771MWULgwwjU+GofnZX9QAm
github.com/sergi/go-diff v1.1.0/go.mod h1:STckp+ISIX8hZLjrqAeVduY0gWCT9IjLuqbuNXdaHfM=
github.com/sergi/go-diff v1.3.1 h1:xkr+Oxo4BOQKmkn/B9eMK0g5Kg/983T9DqqPHwYqD+8=
github.com/sergi/go-diff v1.3.1/go.mod h1:aMJSSKb2lpPvRNec0+w3fl7LP9IOFzdc9Pa4NFbPK1I=
github.com/sergi/go-diff v1.3.2-0.20230802210424-5b0b94c5c0d3 h1:n661drycOFuPLCN3Uc8sB6B/s6Z4t2xvBgU1htSHuq8=
github.com/sergi/go-diff v1.3.2-0.20230802210424-5b0b94c5c0d3/go.mod h1:A0bzQcvG0E7Rwjx0REVgAGH58e96+X0MeOfepqsbeW4=
github.com/shibukawa/configdir v0.0.0-20170330084843-e180dbdc8da0 h1:Xuk8ma/ibJ1fOy4Ee11vHhUFHQNpHhrBneOCNHVXS5w=
github.com/shibukawa/configdir v0.0.0-20170330084843-e180dbdc8da0/go.mod h1:7AwjWCpdPhkSmNAgUv5C7EJ4AbmjEB3r047r3DXWu3Y=
github.com/shirou/gopsutil/v3 v3.23.8 h1:xnATPiybo6GgdRoC4YoGnxXZFRc3dqQTGi73oLvvBrE=
Expand Down
60 changes: 37 additions & 23 deletions installers/install.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -113,40 +113,54 @@ function error([string] $msg)
Write-Host $msg -ForegroundColor Red
}

if (!$script:VERSION) {
$version = $script:VERSION
if (!$version) {
# If the user did not specify a version, formulate a query to fetch the JSON info of the latest
# version, including where it is.
$jsonURL = "$script:BASEINFOURL/?channel=$script:CHANNEL&platform=windows&source=install"
} elseif (!($script:VERSION | Select-String -Pattern "-SHA" -SimpleMatch)) {
} elseif (!($version | Select-String -Pattern "-SHA" -SimpleMatch)) {
# If the user specified a partial version (i.e. no SHA), formulate a query to fetch the JSON
# info of that version's latest SHA, including where it is.
$jsonURL = "$script:BASEINFOURL/?channel=$script:CHANNEL&platform=windows&source=install&target-version=$script:VERSION"
$versionNoSHA = $version
$version = ""
$jsonURL = "$script:BASEINFOURL/?channel=$script:CHANNEL&platform=windows&source=install&target-version=$versionNoSHA"
} else {
# If the user specified a full version with SHA, formulate a query to fetch the JSON info of
# that version.
$versionNoSHA = $version -replace "-SHA.*", ""
$jsonURL = "$script:BASEINFOURL/?channel=$script:CHANNEL&platform=windows&source=install&target-version=$versionNoSHA"
}

if ($jsonURL) {
# If the user specified no version or a partial version we need to use the json URL to get the
# actual installer URL.
try {
$infoJson = ConvertFrom-Json -InputObject (download $jsonURL)
} catch [System.Exception] {
}
if (!$infoJson) {
if (!$script:VERSION) {
# Fetch version info.
try {
$infoJson = ConvertFrom-Json -InputObject (download $jsonURL)
} catch [System.Exception] {
}
if (!$infoJson) {
if (!$version) {
Write-Error "Unable to retrieve the latest version number"
} else {
} else {
Write-Error "Could not download a State Tool Installer for the given command line arguments"
}
Write-Error $_.Exception.Message
exit 1
}
Write-Error $_.Exception.Message
exit 1
}

# Extract checksum.
$checksum = $infoJson.Sha256

if (!$version) {
# If the user specified no version or a partial version we need to use the json URL to get the
# actual installer URL.
$version = $infoJson.Version
$checksum = $infoJson.Sha256
$relUrl = $infoJson.Path
} else {
# If the user specified a full version, strip the SHA to get the folder name of the installer
# URL. Then we can construct the installer URL.
$versionNoSHA = $script:VERSION -replace "-SHA.*", ""
$relUrl = "$script:CHANNEL/$versionNoSHA/windows-amd64/state-windows-amd64-$script:VERSION.zip"
# If the user specified a full version, construct the installer URL.
if ($version -ne $infoJson.Version) {
Write-Error "Unknown version: $version"
exit 1
}
$relUrl = "$script:CHANNEL/$versionNoSHA/windows-amd64/state-windows-amd64-$version.zip"
}

# Fetch the requested or latest version.
Expand All @@ -167,9 +181,9 @@ catch [System.Exception]
exit 1
}

# Verify checksum if possible.
# Verify checksum.
$hash = (Get-FileHash -Path $zipPath -Algorithm SHA256).Hash
if ($checksum -and $hash -ne $checksum)
if ($hash -ne $checksum)
{
Write-Warning "SHA256 sum did not match:"
Write-Warning "Expected: $checksum"
Expand Down
43 changes: 26 additions & 17 deletions installers/install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -117,32 +117,41 @@ if [ -z "$VERSION" ]; then
elif [ -z "`echo $VERSION | grep -o '\-SHA'`" ]; then
# If the user specified a partial version (i.e. no SHA), formulate a query to fetch the JSON info
# of that version's latest SHA, including where it is.
JSONURL="$BASE_INFO_URL?channel=$CHANNEL&source=install&platform=$OS&target-version=$VERSION"
VERSIONNOSHA="$VERSION"
VERSION=""
JSONURL="$BASE_INFO_URL?channel=$CHANNEL&source=install&platform=$OS&target-version=$VERSIONNOSHA"
else
# If the user specified a full version with SHA, formulate a query to fetch the JSON info of that
# version.
VERSIONNOSHA="`echo $VERSION | sed 's/-SHA.*$//'`"
JSONURL="$BASE_INFO_URL?channel=$CHANNEL&source=install&platform=$OS&target-version=$VERSIONNOSHA"
fi

# Fetch version info.
$FETCH $INSTALLERTMPDIR/info.json $JSONURL || exit 1
if [ ! -z "`grep -o Invalid $INSTALLERTMPDIR/info.json`" ]; then
error "Could not download a State Tool installer for the given command line arguments"
exit 1
fi

if [ ! -z "$JSONURL" ]; then
# Extract checksum.
SUM=`cat $INSTALLERTMPDIR/info.json | sed -ne 's/.*"sha256":[ \t]*"\([^"]*\)".*/\1/p'`

if [ -z "$VERSION" ]; then
# If the user specified no version or a partial version we need to use the json URL to get the
# actual installer URL.
$FETCH $INSTALLERTMPDIR/info.json $JSONURL || exit 1
if [ ! -z "`grep -o Invalid $INSTALLERTMPDIR/info.json`" ]; then
error "Could not download a State Tool installer for the given command line arguments"
exit 1
fi

# Parse info.
VERSION=`cat $INSTALLERTMPDIR/info.json | sed -ne 's/.*"version":[ \t]*"\([^"]*\)".*/\1/p'`
if [ -z "$VERSION" ]; then
error "Unable to retrieve the latest version number"
exit 1
fi
SUM=`cat $INSTALLERTMPDIR/info.json | sed -ne 's/.*"sha256":[ \t]*"\([^"]*\)".*/\1/p'`
RELURL=`cat $INSTALLERTMPDIR/info.json | sed -ne 's/.*"path":[ \t]*"\([^"]*\)".*/\1/p'`
rm $INSTALLERTMPDIR/info.json

else
# If the user specified a full version, strip the SHA to get the folder name of the installer URL.
# Then we can construct the installer URL.
VERSIONNOSHA="`echo $VERSION | sed 's/-SHA.*$//'`"
# If the user specified a full version, construct the installer URL.
if [ "$VERSION" != "`cat $INSTALLERTMPDIR/info.json | sed -ne 's/.*"version":[ \t]*"\([^"]*\)".*/\1/p'`" ]; then
error "Unknown version: $VERSION"
exit 1
fi
RELURL="$CHANNEL/$VERSIONNOSHA/$OS-amd64/state-$OS-amd64-$VERSION$DOWNLOADEXT"
fi

Expand All @@ -162,8 +171,8 @@ if [ $? -ne 0 -o \( "`echo $FETCH | grep -o 'curl'`" = "curl" -a ! -z "`grep -o
exit 1
fi

# Verify checksum if possible.
if [ ! -z "$SUM" -a "`$SHA256SUM -b $INSTALLERTMPDIR/$ARCHIVE | cut -d ' ' -f1`" != "$SUM" ]; then
# Verify checksum.
if [ "`$SHA256SUM -b $INSTALLERTMPDIR/$ARCHIVE | cut -d ' ' -f1`" != "$SUM" ]; then
error "SHA256 sum did not match:"
error "Expected: $SUM"
error "Received: `$SHA256SUM -b $INSTALLERTMPDIR/$ARCHIVE | cut -d ' ' -f1`"
Expand Down
Loading

0 comments on commit 999b04a

Please sign in to comment.