Exemplo n.º 1
0
func (u GopathUpdater) Update(importPathPattern string) error {
	// TODO: This uses a legacy gist7802150 caching/cache-invalidation system. It's functional,
	//       but poorly documented, has known flaws (it does not allow concurrent updates),
	//       and very contributor-unfriendly (people don't like packages that have the word "gist" in
	//       the import path, even if's not actually a gist; which is understandable, since it's basically
	//       a package without a name that describes what it's for - that's something acceptable during
	//       rapid prototyping, but not for the finished product). Need to redesign it and replace with
	//       something better.
	//
	//       First step might be to simply drop the caching behavior and hope the user doesn't try
	//       to manually refresh their browser page very often.

	var updateErr = fmt.Errorf("import path pattern %q not found in GOPATH", importPathPattern)
	gist7802150.MakeUpdated(u.GoPackages)
	for _, goPackage := range u.GoPackages.List() {
		if rootPath := util.GetRootPath(goPackage); rootPath != "" {
			if gist7480523.GetRepoImportPathPattern(rootPath, goPackage.Bpkg.SrcRoot) == importPathPattern {

				vcs := goPackage.Dir.Repo.RepoRoot.VCS
				fmt.Printf("cd %s\n", rootPath)
				fmt.Printf("%s %s", vcs.Cmd, vcs.DownloadCmd)
				updateErr = vcs.Download(rootPath)

				// Invalidate cache of the package's local revision, since it's expected to change after updating.
				gist7802150.ExternallyUpdated(goPackage.Dir.Repo.VcsLocal.GetSources()[1].(gist7802150.DepNode2ManualI))

				break
			}
		}
	}
	return updateErr
}
Exemplo n.º 2
0
// Main index page handler.
func mainHandler(w http.ResponseWriter, req *http.Request) {
	if err := loadTemplates(); err != nil {
		fmt.Fprintln(w, "loadTemplates:", err)
		return
	}

	//started := time.Now()

	CommonHat(w)
	defer CommonTail(w)

	io.WriteString(w, `<div id="checking_updates"><h2 style="text-align: center;">Checking for updates...</h2></div>`)
	io.WriteString(w, `<div id="no_updates" style="display: none;"><h2 style="text-align: center;">No Updates Available</h2></div>`)
	defer io.WriteString(w, `<script>document.getElementById("checking_updates").style.display = "none";</script>`)

	flusher := w.(http.Flusher)
	flusher.Flush()

	notifier := w.(http.CloseNotifier)
	go func() {
		<-notifier.CloseNotify()

		//fmt.Println("Exiting, since the HTTP request was cancelled/interrupted.")
		//close(updateRequestChan)
	}()

	//fmt.Printf("Part 1: %v ms.\n", time.Since(started).Seconds()*1000)

	// rootPath -> []*gist7480523.GoPackage
	var goPackagesInRepo = make(map[string][]*gist7480523.GoPackage)

	gist7802150.MakeUpdated(goPackages)
	//fmt.Printf("Part 1b: %v ms.\n", time.Since(started).Seconds()*1000)
	if false {
		for _, goPackage := range goPackages.List() {
			if rootPath := util.GetRootPath(goPackage); rootPath != "" {
				goPackagesInRepo[rootPath] = append(goPackagesInRepo[rootPath], goPackage)
			}
		}
	} else {
		inChan := make(chan interface{})
		go func() { // This needs to happen in the background because sending input will be blocked on reading output.
			for _, goPackage := range goPackages.List() {
				inChan <- goPackage
			}
			close(inChan)
		}()
		reduceFunc := func(in interface{}) interface{} {
			goPackage := in.(*gist7480523.GoPackage)
			if rootPath := util.GetRootPath(goPackage); rootPath != "" {
				return gist7480523.NewGoPackageRepo(rootPath, []*gist7480523.GoPackage{goPackage})
			}
			return nil
		}
		outChan := gist7651991.GoReduce(inChan, 64, reduceFunc)
		for out := range outChan {
			repo := out.(gist7480523.GoPackageRepo)
			goPackagesInRepo[repo.RootPath()] = append(goPackagesInRepo[repo.RootPath()], repo.GoPackages()[0])
		}
	}

	//goon.DumpExpr(len(goPackages.List()))
	//goon.DumpExpr(len(goPackagesInRepo))

	//fmt.Printf("Part 2: %v ms.\n", time.Since(started).Seconds()*1000)

	updatesAvailable := 0

	inChan := make(chan interface{})
	go func() { // This needs to happen in the background because sending input will be blocked on reading output.
		for rootPath, goPackages := range goPackagesInRepo {
			inChan <- gist7480523.NewGoPackageRepo(rootPath, goPackages)
		}
		close(inChan)
	}()
	reduceFunc := func(in interface{}) interface{} {
		repo := in.(gist7480523.GoPackageRepo)

		goPackage := repo.GoPackages()[0]
		goPackage.UpdateVcsFields()

		if !shouldPresentUpdate(goPackage) {
			return nil
		}
		repoPresenter := presenter.New(&repo)
		return repoPresenter
	}
	outChan := gist7651991.GoReduce(inChan, 8, reduceFunc)

	for out := range outChan {
		//started2 := time.Now()

		repoPresenter := out.(presenter.Presenter)

		updatesAvailable++
		WriteRepoHtml(w, repoPresenter)

		flusher.Flush()

		//fmt.Printf("Part 2b: %v ms.\n", time.Since(started2).Seconds()*1000)

		/*log.Println("WriteRepoHtml")
		goon.DumpExpr(repoPresenter.Repo().ImportPathPattern())
		goon.DumpExpr(repoPresenter.Repo().ImportPaths())
		goon.DumpExpr(len(repoPresenter.Repo().GoPackages()))
		goon.DumpExpr(repoPresenter.Repo().GoPackages()[0].Bpkg.ImportPath)
		goon.DumpExpr(repoPresenter.Repo().GoPackages()[0].Dir.Repo.VcsLocal.LocalRev)
		goon.DumpExpr(repoPresenter.Repo().GoPackages()[0].Dir.Repo.VcsRemote.RemoteRev)
		goon.DumpExpr(repoPresenter.HomePage())
		goon.DumpExpr(repoPresenter.Image())
		var changes []presenter.Change
		if changesChan := repoPresenter.Changes(); changesChan != nil {
			for c := range changesChan {
				changes = append(changes, c)
			}
		}
		goon.DumpExpr(changes)*/
	}

	if updatesAvailable == 0 {
		io.WriteString(w, `<script>document.getElementById("no_updates").style.display = "";</script>`)
	}

	//fmt.Printf("Part 3: %v ms.\n", time.Since(started).Seconds()*1000)
}