• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/bin/bash
2# Copyright 2020 the V8 project authors. All rights reserved.
3# Use of this source code is governed by a BSD-style license that can be
4# found in the LICENSE file.
5
6# The purpose of this script is to make it easy to download/update
7# Visual Studio Code on Linux distributions where for whatever reason there
8# is no good way to do so via the package manager.
9
10# Version of this script: 2020.07.04
11
12# Basic checking of arguments: want at least one, and it's not --help.
13VERSION="$1"
14[ -z "$VERSION" -o \
15    "$VERSION" == "-h" -o \
16    "$VERSION" == "--help" -o \
17    "$VERSION" == "help" ] && {
18  echo "Usage: $0 <version>"
19  echo "<version> may be --auto for auto-detecting the latest available."
20  exit 1
21}
22
23die() {
24  echo "Error: $1"
25  exit 1
26}
27
28if [ "$VERSION" == "--auto" -o "$VERSION" == "auto" ]; then
29  echo "Searching online for latest available version..."
30  # Where to find the latest available version (we assume that it's mentioned
31  # in the first 1000 characters, which is true as of 2020-07).
32  AVAILABLE_PACKAGES_URL="https://packages.microsoft.com/repos/vscode/dists/stable/main/binary-amd64/Packages"
33  VERSION=$(curl "$AVAILABLE_PACKAGES_URL" --range 0-1000 --silent \
34            | grep "^Version: " \
35            | sed 's/[^0-9]*\([0-9.]*\).*/\1/')
36  if [ -z "$VERSION" ]; then
37    die "Detecting latest version failed, please specify it manually."
38  else
39    echo "Latest version found: $VERSION"
40  fi
41fi
42
43# Constant definitions for local paths. Edit these to your liking.
44VSCODE_DIR="$HOME/vscode"
45BACKUP_DIR="$HOME/vscode.prev"
46DOWNLOADS_DIR="$HOME/Downloads"
47DOWNLOAD_FILE="$DOWNLOADS_DIR/vscode-$VERSION.tar.gz"
48DESKTOP_FILE_DIR="$HOME/.local/share/applications"
49DESKTOP_FILE="$DESKTOP_FILE_DIR/code.desktop"
50
51# Constant definitions for remote/upstream things. Might need to be updated
52# when upstream changes things.
53# Where to find the version inside VS Code's installation directory.
54PACKAGE_JSON="$VSCODE_DIR/resources/app/package.json"
55ICON="$VSCODE_DIR/resources/app/resources/linux/code.png"
56# Where to download the archive.
57DOWNLOAD_URL="https://update.code.visualstudio.com/$VERSION/linux-x64/stable"
58CODE_BIN="$VSCODE_DIR/bin/code"
59
60# Check for "code" in $PATH; create a symlink if we can find a good place.
61SYMLINK=$(which code)
62if [ -z "$SYMLINK" ]; then
63  IFS=':' read -ra PATH_ARRAY <<< "$PATH"
64  for P in "${PATH_ARRAY[@]}"; do
65    if [ "$P" == "$HOME/bin" -o \
66         "$P" == "$HOME/local/bin" -o \
67         "$P" == "$HOME/.local/bin" ]; then
68      LOCALBIN="$P"
69      break
70    fi
71  done
72  if [ -n "$LOCALBIN" ]; then
73    echo "Adding symlink to $LOCALBIN..."
74    if [ ! -d "$LOCALBIN" ]; then
75      mkdir -p "$LOCALBIN" || die "Failed to create $LOCALBIN."
76    fi
77    ln -s "$CODE_BIN" "$LOCALBIN/code" || die "Failed to create symlink."
78  else
79    echo "Please put a symlink to $CODE_BIN somewhere on your \$PATH."
80  fi
81fi
82
83if [ ! -r "$DESKTOP_FILE" ]; then
84  echo "Creating .desktop file..."
85  mkdir -p "$DESKTOP_FILE_DIR" || die "Failed to create .desktop directory."
86  cat <<EOF > "$DESKTOP_FILE"
87#!/usr/bin/env xdg-open
88[Desktop Entry]
89Name=Visual Studio Code
90Comment=Code Editing. Redefined.
91GenericName=Text Editor
92Exec=$CODE_BIN --unity-launch %F
93Icon=$ICON
94Type=Application
95StartupNotify=false
96StartupWMClass=Code
97Categories=Utility;TextEditor;Development;IDE;
98MimeType=text/plain;inode/directory;
99Actions=new-empty-window;
100Keywords=vscode;
101
102X-Desktop-File-Install-Version=0.24
103
104[Desktop Action new-empty-window]
105Name=New Empty Window
106Exec=$CODE_BIN --new-window %F
107Icon=$ICON
108EOF
109  chmod +x "$DESKTOP_FILE" || die "Failed to make .desktop file executable."
110fi
111
112# Find currently installed version.
113if [ -d "$VSCODE_DIR" ]; then
114  if [ ! -r "$PACKAGE_JSON" ]; then
115    die "$PACKAGE_JSON file not found, this script must be updated."
116  fi
117  INSTALLED=$(grep '"version":' "$PACKAGE_JSON" \
118              | sed 's/[^0-9]*\([0-9.]*\).*/\1/')
119  echo "Detected installed version: $INSTALLED"
120  if [ "$VERSION" == "$INSTALLED" ] ; then
121    echo "You already have that version."
122    exit 0
123  else
124    echo "Updating from $INSTALLED to $VERSION..."
125  fi
126fi
127
128if [ ! -r "$DOWNLOAD_FILE" ]; then
129  echo "Downloading..."
130  if [ ! -d "$DOWNLOADS_DIR" ]; then
131    mkdir -p "$DOWNLOADS_DIR" || die "Failed to create $DOWNLOADS_DIR."
132  fi
133  wget "$DOWNLOAD_URL" -O "$DOWNLOAD_FILE" || die "Downloading failed."
134else
135  echo "$DOWNLOAD_FILE already exists; delete it to force re-download."
136fi
137
138echo "Extracting..."
139TAR_DIR=$(tar -tf "$DOWNLOAD_FILE" | head -1)
140[ -z "$TAR_DIR" ] && die "Couldn't read archive."
141TMP_DIR=$(mktemp -d)
142tar -C "$TMP_DIR" -xf "$DOWNLOAD_FILE" || {
143  rm -rf "$TMP_DIR"
144  die "Extracting failed."
145}
146
147if [ -d "$BACKUP_DIR" ]; then
148  echo "Deleting previous backup..."
149  rm -rf "$BACKUP_DIR"
150fi
151
152if [ -d "$VSCODE_DIR" ]; then
153  echo "Moving previous installation..."
154  mv "$VSCODE_DIR" "$BACKUP_DIR"
155fi
156
157echo "Installing new version..."
158mv "$TMP_DIR/$TAR_DIR" "$VSCODE_DIR"
159rmdir "$TMP_DIR"
160
161echo "All done, enjoy coding!"
162