Glide install skips fetch when it is up to date

For 'glide install', this lazily computes whether the existing vendor
checkouts are already at the right commit. If they are, those deps are
skipped during the concurrent update.

This is safe to do in install because the dependency graph is already
computed, so there should never be a case where the glide.lock file does
not contain a negotiable dependency graph.
diff --git a/repo/installer.go b/repo/installer.go
index fee26c4..420ac27 100644
--- a/repo/installer.go
+++ b/repo/installer.go
@@ -111,8 +111,8 @@
 
 	msg.Info("Downloading dependencies. Please wait...")
 
-	ConcurrentUpdate(newConf.Imports, cwd, i, newConf)
-	ConcurrentUpdate(newConf.DevImports, cwd, i, newConf)
+	LazyConcurrentUpdate(newConf.Imports, cwd, i, newConf)
+	LazyConcurrentUpdate(newConf.DevImports, cwd, i, newConf)
 	return newConf, nil
 }
 
@@ -302,6 +302,43 @@
 	return conf.Imports
 }
 
+// LazyConcurrentUpdate updates only deps that are not already checkout out at the right version.
+//
+// This is only safe when updating from a lock file.
+func LazyConcurrentUpdate(deps []*cfg.Dependency, cwd string, i *Installer, c *cfg.Config) error {
+
+	newDeps := []*cfg.Dependency{}
+	for _, dep := range deps {
+		destPath := filepath.Join(i.VendorPath(), dep.Name)
+
+		// Get a VCS object for this directory
+		repo, err := dep.GetRepo(destPath)
+		if err != nil {
+			newDeps = append(newDeps, dep)
+			continue
+		}
+
+		ver, err := repo.Version()
+		if err != nil {
+			newDeps = append(newDeps, dep)
+			continue
+		}
+
+		if ver == dep.Reference {
+			msg.Info("--> Found desired version %s %s!", dep.Name, dep.Reference)
+			continue
+		}
+
+		msg.Debug("--> Queue %s for update (%s != %s).", dep.Name, ver, dep.Reference)
+		newDeps = append(newDeps, dep)
+	}
+	if len(newDeps) > 0 {
+		return ConcurrentUpdate(newDeps, cwd, i, c)
+	}
+
+	return nil
+}
+
 // ConcurrentUpdate takes a list of dependencies and updates in parallel.
 func ConcurrentUpdate(deps []*cfg.Dependency, cwd string, i *Installer, c *cfg.Config) error {
 	done := make(chan struct{}, concurrentWorkers)
diff --git a/repo/vcs.go b/repo/vcs.go
index 31bed50..3f5f80d 100644
--- a/repo/vcs.go
+++ b/repo/vcs.go
@@ -203,14 +203,14 @@
 		}
 
 		ver := dep.Reference
-		// Referenes in Git can begin with a ^ which is similar to semver.
+		// References in Git can begin with a ^ which is similar to semver.
 		// If there is a ^ prefix we assume it's a semver constraint rather than
 		// part of the git/VCS commit id.
 		if repo.IsReference(ver) && !strings.HasPrefix(ver, "^") {
 			msg.Info("--> Setting version for %s to %s.\n", dep.Name, ver)
 		} else {
 
-			// Create the constraing first to make sure it's valid before
+			// Create the constraint first to make sure it's valid before
 			// working on the repo.
 			constraint, err := semver.NewConstraint(ver)