Add an experimental installer for wasm-pack

This commit kicks off the addition of installers for wasm-pack, with the main
goals of being:

* Users should have a one-click (ideally) solution to download and install
  wasm-pack.
* We should ideally not have to worry about picking up "heavy" dependencies in
  wasm-pack like C++ or C code (if necessary).

The general idea here is very similar to rustup (and in fact a good deal of code
is copied from them!). The installation worklow for wasm-pack in theory after
this commit looks like:

1. First, a users visits the installer landing page. A preview is available at
   https://alexcrichton.github.io/wasm-pack/installer/. Clearly this page needs
   a better stylesheet!

2. The user performs the instructions presented on the page. The website
   automatically detects what platform you're running on, basically giving you a
   curl/sh script or a Windows installer. There's various options for seeing
   other installers as well, and the fallback of `cargo install` is presented if
   we don't recognize the platform (or if we don't think we have precompiled
   binaries).

3a. On Unix, users execute a curl/sh script like:

    ```
    curl https://alexcrichton.github.io/wasm-pack/installer/init.sh -sSf | sh
    ```

    This command will download the shell script included in this PR, which will
    in turn do some further platform detection (like OSX vs Linux) and then
    download the most recent version of `wasm-pack` from GitHub releases. This
    is then extracted, the `wasm-pack` binary is renamed to `wasm-pack-init`,
    and then that binary is run. The binary will refuse by default to overwrite
    a previous installation, but that can be overridden with the `-f` flag.

3b. On Windows users download a binary. This binary, when run, will pop up a
    console window. This window will have the same output as the shell script
    installer, and will wait at the end of its execution to ensure the user has
    time to read everything.

And... that's it! The deployment process for all this looks like so:

* All CI builds will update the website and shell script (published to
  gh-pages). A small script at `docs/installer/build-installer.rs` fills in the
  current version number inferred from `Cargo.toml`.

* Tagged CI builds will publish releases, as usual.

* "Pushing a release" is done by bumping the version number in `Cargo.toml`.
  When bumped all online installers will now point to the new release. There
  will be a window of time, though, when the version number is bumped and the
  release hasn't finished building on CI. In this case users will get errors
  (unfortunately).

This is all still a work-in-progress and feedback is definitely appreicated and
welcome on all this!
master
Alex Crichton 7 years ago
parent 0bd0b5a4e0
commit 69e5af8fe2
  1. 8
      .appveyor.yml
  2. 1
      .gitignore
  3. 18
      .travis.yml
  4. 1
      Cargo.lock
  5. 1
      Cargo.toml
  6. 30
      docs/installer/build-installer.rs
  7. 106
      docs/installer/index.html
  8. 190
      docs/installer/init.sh
  9. 92
      docs/installer/wasm-pack.js
  10. 122
      src/installer.rs
  11. 20
      src/main.rs

@ -19,23 +19,25 @@ test_script:
before_deploy:
- ps: |
$NAME = "wasm-pack-${env:APPVEYOR_REPO_TAG_NAME}-${env:TARGET}"
$NAME = "wasm-pack-${env:APPVEYOR_REPO_TAG_NAME}-x86_64-pc-windows-msvc"
New-Item -Path $NAME -ItemType directory
Copy-Item target/release/wasm-pack.exe "${NAME}/"
Copy-Item target/release/wasm-pack.exe wasm-pack-init.exe
Copy-Item LICENSE-MIT "${NAME}/"
Copy-Item LICENSE-APACHE "${NAME}/"
Copy-Item README.md "${NAME}/"
7z a -ttar "${NAME}.tar" "${NAME}"
7z a "${NAME}.tar.gz" "${NAME}.tar"
Push-AppveyorArtifact "${NAME}.tar.gz"
Push-AppveyorArtifact wasm-pack-init.exe
deploy:
artifact: /.*\.tar.gz/
artifact: /.*\.tar.gz/, /.*\.exe/
description: 'Appveyor Automated Release'
provider: GitHub
draft: false
prerelease: false
autho_token:
auth_token:
secure: iHsRUqwGf/Zh7OuYpHOWQL8buaOL+c8/6kXLRly8V2j0LCUo7CcDs0NxQ0vl2bhZ
on:
appveyor_repo_tag: true

1
.gitignore vendored

@ -3,3 +3,4 @@ target/
tests/.crates.toml
tests/bin
wasm-pack.log
/build-installer

@ -14,6 +14,9 @@ cache:
directories:
- /home/travis/.cargo
GH_TOKEN: &GH_TOKEN
secure: fx0rR5Ii1KcsydexE6QpkDbqItNdj3Lt6L5yFZaKKB/ejw9M555NkXA+0GZqV0sLZ54qfR8zTaXAf6eBFKgcG9etaCl7vTXqsvDrlssth82oki1zufP39uuoOy4WgFq8OfACOtUq7opDAgYmpaGzlFiny+c5j7asGwDtAU1Fc3JeJsvAnxHKg9+0spXFD6kBQd5CWpqDXv2rLFK0b8IM2fHAzd0PiJZQWqz//2Cj/r9rTiewtIzqigctAfOgFwYoQvfdM+0mKb4pefG+zXEGfxxQr4r5hqZ6UMO7hto3Jnm9LRjNR8dNaDQCqQ0bkdLTAMTC3nV/gZPM679yQU3KHueVjg9pleNzuKnuBgYmH9+BrlG1dW68kqA+6Xh+wIJYrLuagWhJDlCtiU6PM5QAbFg3mabPIBG3M2IHTrOVATme+iW5vpROARhgjbQEF235DyvZaT+Tml3+PY+PfcRax2DVUhvGQViv4tzppbT0PjjBlEbGct49cFLGdqZIJBiVrYW24I2QkENTnUgZsFIBuJlVCBHZwZlLo9ldVvu4XTMKw65z42zoTzobjtbC1QPEZPiaJXSxC7W569fqL/ORXwGToFk6rQjXwEqDP2okGiusR75LXrZD6qFibNpqeypRFtqOzntsOfTUGrlaN1yTt/6dz0V0j9uI7a9/CHVcblI=
DEPLOY_TO_GITHUB: &DEPLOY_TO_GITHUB
before_deploy:
- git config --local user.name "Ashley Williams"
@ -25,14 +28,11 @@ DEPLOY_TO_GITHUB: &DEPLOY_TO_GITHUB
- tar czvf $name.tar.gz $name
deploy:
provider: releases
api_key:
secure: fx0rR5Ii1KcsydexE6QpkDbqItNdj3Lt6L5yFZaKKB/ejw9M555NkXA+0GZqV0sLZ54qfR8zTaXAf6eBFKgcG9etaCl7vTXqsvDrlssth82oki1zufP39uuoOy4WgFq8OfACOtUq7opDAgYmpaGzlFiny+c5j7asGwDtAU1Fc3JeJsvAnxHKg9+0spXFD6kBQd5CWpqDXv2rLFK0b8IM2fHAzd0PiJZQWqz//2Cj/r9rTiewtIzqigctAfOgFwYoQvfdM+0mKb4pefG+zXEGfxxQr4r5hqZ6UMO7hto3Jnm9LRjNR8dNaDQCqQ0bkdLTAMTC3nV/gZPM679yQU3KHueVjg9pleNzuKnuBgYmH9+BrlG1dW68kqA+6Xh+wIJYrLuagWhJDlCtiU6PM5QAbFg3mabPIBG3M2IHTrOVATme+iW5vpROARhgjbQEF235DyvZaT+Tml3+PY+PfcRax2DVUhvGQViv4tzppbT0PjjBlEbGct49cFLGdqZIJBiVrYW24I2QkENTnUgZsFIBuJlVCBHZwZlLo9ldVvu4XTMKw65z42zoTzobjtbC1QPEZPiaJXSxC7W569fqL/ORXwGToFk6rQjXwEqDP2okGiusR75LXrZD6qFibNpqeypRFtqOzntsOfTUGrlaN1yTt/6dz0V0j9uI7a9/CHVcblI=
file_glob: true
api_key: *GH_TOKEN
file: wasm-pack-$TRAVIS_TAG-$TARGET.tar.gz
skip_cleanup: true
on:
branch: master
condition: $DEPLOY = 1
tags: true
matrix:
@ -59,18 +59,20 @@ matrix:
- (test -x $HOME/.cargo/bin/mdbook || cargo install --vers "^0.1" mdbook)
- cargo install-update -a
script:
- cd docs && mdbook build
- (cd docs && mdbook build)
- rustc ./docs/installer/build-installer.rs
- ./build-installer
deploy:
provider: pages
skip-cleanup: true
github-token: $GITHUB_TOKEN
github-token: *GH_TOKEN
local-dir: docs/book
keep-history: false
on:
branch: master
# dist linux binary
- env: JOB=dist-linux TARGET=x86_64-unknown-linux-musl DEPLOY=1
- env: JOB=dist-linux TARGET=x86_64-unknown-linux-musl
rust: nightly
before_script: rustup target add $TARGET
script: cargo build --release --target $TARGET --locked --features vendored-openssl
@ -81,7 +83,7 @@ matrix:
<<: *DEPLOY_TO_GITHUB
# dist OSX binary
- env: JOB=dist-osx MACOSX_DEPLOYMENT_TARGET=10.7 DEPLOY=1 TARGET=x86_64-apple-darwin
- env: JOB=dist-osx MACOSX_DEPLOYMENT_TARGET=10.7 TARGET=x86_64-apple-darwin
os: osx
rust: nightly
script: cargo build --release --target $TARGET --locked

1
Cargo.lock generated

@ -900,6 +900,7 @@ dependencies = [
name = "wasm-pack"
version = "0.4.2"
dependencies = [
"atty 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)",
"console 0.6.1 (registry+https://github.com/rust-lang/crates.io-index)",
"copy_dir 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
"curl 0.4.14 (registry+https://github.com/rust-lang/crates.io-index)",

@ -9,6 +9,7 @@ readme = "README.md"
categories = ["wasm"]
[dependencies]
atty = "0.2.11"
console = "0.6.1"
curl = "0.4.13"
failure = "0.1.2"

@ -0,0 +1,30 @@
use std::fs;
fn main() {
fs::create_dir_all("docs/book/installer").unwrap();
fs::copy(
"docs/installer/wasm-pack.js",
"docs/book/installer/wasm-pack.js",
).unwrap();
let index = fs::read_to_string("docs/installer/index.html").unwrap();
fs::write(
"docs/book/installer/index.html",
fixup(&index),
).unwrap();
let init = fs::read_to_string("docs/installer/init.sh").unwrap();
fs::write(
"docs/book/installer/init.sh",
fixup(&init),
).unwrap();
}
fn fixup(input: &str) -> String {
let manifest = fs::read_to_string("Cargo.toml").unwrap();
let version = manifest.lines()
.find(|line| line.starts_with("version ="))
.unwrap();
let version = &version[version.find('"').unwrap() + 1..version.rfind('"').unwrap()];
input.replace("$VERSION", &format!("v{}", version))
}

@ -0,0 +1,106 @@
<!DOCTYPE html>
<head>
<meta charset="utf-8">
<title>wasm-pack</title>
<style>
body {
text-align: center;
margin: 100px;
font-size: 150%;
}
#main {
padding: 100px;
}
.instructions {
padding: 100px;
border: 1px solid black;
}
.winlink {
display: block;
}
</style>
</head>
<body>
<div id='main'>
Install wasm-pack! A tool with a blurb here.
</div>
<div id="platform-instructions-unix" style="display: none;">
<pre>curl https://rustwasm.github.io/wasm-pack/installer/init.sh -sSf | sh</pre>
<p>
You appear to be running Unix. If not,
<a class="default-platform-button" href="#">display all supported installers</a>.
</p>
</div>
<div id="platform-instructions-win64" class="instructions" style="display: none;">
<p>
You appear to be running windows 64-bit, download and run
<a class='winlink' href="https://github.com/rustwasm/wasm-pack/releases/download/$VERSION/wasm-pack-init.exe">wasm-pack-init.exe</a>
then follow the onscreen
instructions.
</p>
<hr/>
<p>
If you're a Windows Subsystem for Linux user run the following in your
terminal, then follow the onscreen instructions to install wasm-pack.
</p>
<pre>curl https://rustwasm.github.io/wasm-pack/installer/init.sh -sSf | sh</pre>
<hr/>
<p>
You appear to be running Windows 64-bit. If not,
<a class="default-platform-button" href="#">
display all supported installers
</a>.
</p>
</div>
<div id="platform-instructions-unknown" class="instructions" style="display: none;">
<p>I don't recognize your platform.</p>
<p>
We would appreciate it if you
<a href="https://github.com/rustwasm/wasm-pack/issues/new">reported an issue</a>,
along with the following values:
</p>
<div>
<div>navigator.platform:</div>
<div id="nav-plat"></div>
<div>navigator.appVersion:</div>
<div id="nav-app"></div>
</div>
</div>
<div id="platform-instructions-default" class="instructions">
<div>
<p>
To install wasm-pack, if you are running Unix,<br/>
run the following in your terminal, then follow the onscreen
instructions.
</p>
<pre>curl https://rustwasm.github.io/wasm-pack/installer/init.sh -sSf | sh</pre>
</div>
<hr/>
<div>
<p>
If you are running Windows 64-bit,<br/>download and run
<a class='winlink' href="https://github.com/rustwasm/wasm-pack/releases/download/$VERSION/wasm-pack-init.exe">wasm-pack-init.exe</a>
then follow the onscreen instructions.
</p>
</div>
<hr/>
<div>
<p>
For all other platforms, run the following in your terminal:
</p>
<pre>cargo install wasm-pack</pre>
</div>
</div>
<script type="text/javascript" src="wasm-pack.js"></script>

@ -0,0 +1,190 @@
#!/bin/bash
# Copyright 2016 The Rust Project Developers. See the COPYRIGHT
# file at the top-level directory of this distribution and at
# http://rust-lang.org/COPYRIGHT.
#
# Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
# http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
# <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
# option. This file may not be copied, modified, or distributed
# except according to those terms.
# This is just a little script that can be downloaded from the internet to
# install wasm-pack. It just does platform detection, downloads the installer
# and runs it.
set -u
UPDATE_ROOT="https://github.com/rustwasm/wasm-pack/releases/download/$VERSION"
main() {
downloader --check
need_cmd uname
need_cmd mktemp
need_cmd chmod
need_cmd mkdir
need_cmd rm
need_cmd rmdir
need_cmd tar
need_cmd which
need_cmd dirname
get_architecture || return 1
local _arch="$RETVAL"
assert_nz "$_arch" "arch"
local _ext=""
case "$_arch" in
*windows*)
_ext=".exe"
;;
esac
which rustup > /dev/null 2>&1
need_ok "failed to find Rust installation, is rustup installed?"
local _rustup=`which rustup`
local _tardir="wasm-pack-$VERSION-${_arch}"
local _url="$UPDATE_ROOT/${_tardir}.tar.gz"
local _dir="$(mktemp -d 2>/dev/null || ensure mktemp -d -t wasm-pack)"
local _file="$_dir/input.tar.gz"
local _wasmpack="$_dir/wasm-pack$_ext"
local _wasmpackinit="$_dir/wasm-pack-init$_ext"
printf '%s\n' 'info: downloading wasm-pack' 1>&2
ensure mkdir -p "$_dir"
downloader "$_url" "$_file"
if [ $? != 0 ]; then
say "failed to download $_url"
say "this may be a standard network error, but it may also indicate"
say "that wasm-pack's release process is not working. When in doubt"
say "please feel free to open an issue!"
exit 1
fi
ensure tar xf "$_file" --strip-components 1 -C "$_dir"
mv "$_wasmpack" "$_wasmpackinit"
# The installer may want to ask for confirmation on stdin for various
# operations. We were piped through `sh` though so we probably don't have
# access to a tty naturally. If it looks like we're attached to a terminal
# (`-t 1`) then pass the tty down to the installer explicitly.
if [ -t 1 ]; then
"$_wasmpackinit" "$@" < /dev/tty
else
"$_wasmpackinit" "$@"
fi
local _retval=$?
ignore rm -rf "$_dir"
return "$_retval"
}
get_architecture() {
local _ostype="$(uname -s)"
local _cputype="$(uname -m)"
if [ "$_ostype" = Darwin -a "$_cputype" = i386 ]; then
# Darwin `uname -s` lies
if sysctl hw.optional.x86_64 | grep -q ': 1'; then
local _cputype=x86_64
fi
fi
case "$_ostype" in
Linux)
local _ostype=unknown-linux-musl
;;
Darwin)
local _ostype=apple-darwin
;;
MINGW* | MSYS* | CYGWIN*)
local _ostype=pc-windows-msvc
;;
*)
err "no precompiled binaries available for OS: $_ostype"
;;
esac
case "$_cputype" in
x86_64 | x86-64 | x64 | amd64)
local _cputype=x86_64
;;
*)
err "no precompiled binaries available for CPU architecture: $_cputype"
esac
local _arch="$_cputype-$_ostype"
RETVAL="$_arch"
}
say() {
echo "wasm-pack-init: $1"
}
err() {
say "$1" >&2
exit 1
}
need_cmd() {
if ! check_cmd "$1"
then err "need '$1' (command not found)"
fi
}
check_cmd() {
command -v "$1" > /dev/null 2>&1
return $?
}
need_ok() {
if [ $? != 0 ]; then err "$1"; fi
}
assert_nz() {
if [ -z "$1" ]; then err "assert_nz $2"; fi
}
# Run a command that should never fail. If the command fails execution
# will immediately terminate with an error showing the failing
# command.
ensure() {
"$@"
need_ok "command failed: $*"
}
# This is just for indicating that commands' results are being
# intentionally ignored. Usually, because it's being executed
# as part of error handling.
ignore() {
"$@"
}
# This wraps curl or wget. Try curl first, if not installed,
# use wget instead.
downloader() {
if check_cmd curl
then _dld=curl
elif check_cmd wget
then _dld=wget
else _dld='curl or wget' # to be used in error message of need_cmd
fi
if [ "$1" = --check ]
then need_cmd "$_dld"
elif [ "$_dld" = curl ]
then curl -sSfL "$1" -o "$2"
elif [ "$_dld" = wget ]
then wget "$1" -O "$2"
else err "Unknown downloader" # should not reach here
fi
}
main "$@" || exit 1

@ -0,0 +1,92 @@
var platforms = ["default", "unknown", "win64", "unix"];
var platform_override = null;
function detect_platform() {
"use strict";
if (platform_override !== null) {
return platforms[platform_override];
}
var os = "unknown";
if (navigator.platform == "Linux x86_64") {os = "unix";}
if (navigator.platform == "Linux i686") {os = "unix";}
if (navigator.platform == "Linux i686 on x86_64") {os = "unix";}
if (navigator.platform == "Linux aarch64") {os = "unix";}
if (navigator.platform == "Linux armv6l") {os = "unix";}
if (navigator.platform == "Linux armv7l") {os = "unix";}
if (navigator.platform == "Linux armv8l") {os = "unix";}
if (navigator.platform == "Linux ppc64") {os = "unix";}
if (navigator.platform == "Linux mips") {os = "unix";}
if (navigator.platform == "Linux mips64") {os = "unix";}
if (navigator.platform == "Mac") {os = "unix";}
// if (navigator.platform == "Win32") {os = "win32";}
if (navigator.platform == "Win64" ||
navigator.userAgent.indexOf("WOW64") != -1 ||
navigator.userAgent.indexOf("Win64") != -1) { os = "win64"; }
if (navigator.platform == "FreeBSD x86_64") {os = "unix";}
if (navigator.platform == "FreeBSD amd64") {os = "unix";}
if (navigator.platform == "NetBSD x86_64") {os = "unix";}
if (navigator.platform == "NetBSD amd64") {os = "unix";}
// I wish I knew by now, but I don't. Try harder.
if (os == "unknown") {
// if (navigator.appVersion.indexOf("Win")!=-1) {os = "win32";}
if (navigator.appVersion.indexOf("Mac")!=-1) {os = "unix";}
// rust-www/#692 - FreeBSD epiphany!
if (navigator.appVersion.indexOf("FreeBSD")!=-1) {os = "unix";}
}
// Firefox Quantum likes to hide platform and appVersion but oscpu works
if (navigator.oscpu) {
// if (navigator.oscpu.indexOf("Win32")!=-1) {os = "win32";}
if (navigator.oscpu.indexOf("Win64")!=-1) {os = "win64";}
if (navigator.oscpu.indexOf("Mac")!=-1) {os = "unix";}
if (navigator.oscpu.indexOf("Linux")!=-1) {os = "unix";}
if (navigator.oscpu.indexOf("FreeBSD")!=-1) {os = "unix";}
if (navigator.oscpu.indexOf("NetBSD")!=-1) {os = "unix";}
}
return os;
}
function adjust_for_platform() {
"use strict";
var platform = detect_platform();
platforms.forEach(function (platform_elem) {
var platform_div = document.getElementById("platform-instructions-" + platform_elem);
platform_div.style.display = "none";
if (platform == platform_elem ||
(platform == 'unknown' && platform_elem == 'default')) {
platform_div.style.display = "block";
}
});
}
function go_to_default_platform() {
platform_override = 0;
adjust_for_platform();
}
function set_up_default_platform_buttons() {
var defaults_buttons = document.getElementsByClassName('default-platform-button');
for (var i = 0; i < defaults_buttons.length; i++) {
defaults_buttons[i].onclick = go_to_default_platform;
}
}
function fill_in_bug_report_values() {
var nav_plat = document.getElementById("nav-plat");
var nav_app = document.getElementById("nav-app");
nav_plat.textContent = navigator.platform;
nav_app.textContent = navigator.appVersion;
}
(function () {
adjust_for_platform();
set_up_default_platform_buttons();
fill_in_bug_report_values();
}());

@ -0,0 +1,122 @@
//! Self-installation of `wasm-pack`
//!
//! This module contains one public function which will self-install the
//! currently running executable as `wasm-pack`. Our goal is to install this in
//! a place that's already in `PATH`, ideally in an idiomatic location. To that
//! end we place `wasm-pack` next to the `rustup` executable in `PATH`.
//!
//! This installer is run directly (probably by clicking on it) on Windows,
//! meaning it will pop up a console (as we're a console app). Output goes to
//! the console and users interact with it through the console. On Unix this is
//! intended to be run from a shell script (docs/installer/init.sh) which is
//! downloaded via curl/sh, and then the shell script downloads this executable
//! and runs it.
//!
//! This may get more complicated over time (self upates anyone?) but for now
//! it's pretty simple! We're largely just moving over our currently running
//! executable to a different path.
use std::env;
use std::fs;
use std::io;
use std::path::Path;
use std::process;
use atty;
use failure::{Error, ResultExt};
use which;
pub fn install() -> ! {
if let Err(e) = do_install() {
eprintln!("{}", e);
for cause in e.iter_causes() {
eprintln!("Caused by: {}", cause);
}
}
// On Windows we likely popped up a console for the installation. If we were
// to exit here immediately then the user wouldn't see any error that
// happened above or any successful message. Let's wait for them to say
// they've read everything and then continue.
if cfg!(windows) {
println!("Press enter to close this window...");
let mut line = String::new();
drop(io::stdin().read_line(&mut line));
}
process::exit(0);
}
fn do_install() -> Result<(), Error> {
// Find `rustup.exe` in PATH, we'll be using its installation directory as
// our installation directory.
let rustup = match which::which("rustup") {
Ok(path) => path,
Err(_) => {
bail!(
"failed to find an installation of `rustup` in `PATH`, \
is rustup already installed?"
);
}
};
let installation_dir = match rustup.parent() {
Some(parent) => parent,
None => bail!("can't install when `rustup` is at the root of the filesystem"),
};
let destination = installation_dir
.join("wasm-pack")
.with_extension(env::consts::EXE_EXTENSION);
if destination.exists() {
confirm_can_overwrite(&destination)?;
}
// Our relatively simple install step!
let me = env::current_exe()?;
fs::copy(&me, &destination)
.with_context(|_| format!("failed to copy executable to `{}`", destination.display()))?;
println!(
"info: successfully installed wasm-pack to `{}`",
destination.display()
);
// ... and that's it!
Ok(())
}
fn confirm_can_overwrite(dst: &Path) -> Result<(), Error> {
// If the `-f` argument was passed, we can always overwrite everything.
if env::args().any(|arg| arg == "-f") {
return Ok(());
}
// If we're not attached to a TTY then we can't get user input, so there's
// nothing to do except inform the user about the `-f` flag.
if !atty::is(atty::Stream::Stdin) {
bail!(
"existing wasm-pack installation found at `{}`, pass `-f` to \
force installation over this file, otherwise aborting \
installation now",
dst.display()
);
}
// It looks like we're at an interactive prompt, so ask the user if they'd
// like to overwrite the previous installation.
eprintln!(
"info: existing wasm-pack installation found at `{}`",
dst.display()
);
eprint!("info: would you like to overwrite this file? [y/N]: ");
let mut line = String::new();
io::stdin()
.read_line(&mut line)
.with_context(|_| "failed to read stdin")?;
if line.starts_with("y") || line.starts_with("Y") {
return Ok(());
}
bail!("aborting installation");
}

@ -1,31 +1,43 @@
extern crate atty;
#[macro_use]
extern crate failure;
#[macro_use]
extern crate human_panic;
extern crate structopt;
extern crate wasm_pack;
extern crate which;
use failure::Fail;
use std::env;
use structopt::StructOpt;
use wasm_pack::{command::run_wasm_pack, error::Error, logger, Cli};
use wasm_pack::{command::run_wasm_pack, logger, Cli};
mod installer;
fn main() {
setup_panic!();
if let Err(e) = run() {
eprintln!("{}", e);
for cause in Fail::iter_causes(&e) {
for cause in e.iter_causes() {
eprintln!("Caused by: {}", cause);
}
::std::process::exit(1);
}
}
fn run() -> Result<(), Error> {
fn run() -> Result<(), failure::Error> {
// Deprecate `init`
if let Some("init") = env::args().nth(1).as_ref().map(|arg| arg.as_str()) {
println!("wasm-pack init is deprecated, consider using wasm-pack build");
}
if let Ok(me) = env::current_exe() {
// If we're actually running as the installer then execute our
// self-installation, otherwise just continue as usual.
if me.file_stem().and_then(|s| s.to_str()) == Some("wasm-pack-init") {
installer::install();
}
}
let args = Cli::from_args();
let log = logger::new(&args.cmd, args.verbosity)?;
run_wasm_pack(args.cmd, &log)?;

Loading…
Cancel
Save