// Copyright 2018 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package modfetch

import (
	"sync"

	"cmd/go/internal/par"
)

// A cachingRepo is a cache around an underlying Repo,
// avoiding redundant calls to ModulePath, Versions, Stat, Latest, and GoMod (but not Zip).
// It is also safe for simultaneous use by multiple goroutines
// (so that it can be returned from Lookup multiple times).
// It serializes calls to the underlying Repo.
type cachingRepo struct {
	path  string
	cache par.Cache // cache for all operations

	mu sync.Mutex // protects r's methods
	r  Repo
}

func newCachingRepo(r Repo) *cachingRepo {
	return &cachingRepo{
		r:    r,
		path: r.ModulePath(),
	}
}

func (r *cachingRepo) ModulePath() string {
	return r.path
}

func (r *cachingRepo) Versions(prefix string) ([]string, error) {
	type cached struct {
		list []string
		err  error
	}
	c := r.cache.Do("versions:"+prefix, func() interface{} {
		r.mu.Lock()
		defer r.mu.Unlock()
		list, err := r.r.Versions(prefix)
		return cached{list, err}
	}).(cached)

	if c.err != nil {
		return nil, c.err
	}
	return append([]string(nil), c.list...), nil
}

func (r *cachingRepo) Stat(rev string) (*RevInfo, error) {
	type cached struct {
		info *RevInfo
		err  error
	}
	c := r.cache.Do("stat:"+rev, func() interface{} {
		r.mu.Lock()
		defer r.mu.Unlock()
		info, err := r.r.Stat(rev)
		return cached{info, err}
	}).(cached)

	if c.err != nil {
		return nil, c.err
	}
	info := *c.info
	return &info, nil
}

func (r *cachingRepo) Latest() (*RevInfo, error) {
	type cached struct {
		info *RevInfo
		err  error
	}
	c := r.cache.Do("latest:", func() interface{} {
		r.mu.Lock()
		defer r.mu.Unlock()
		info, err := r.r.Latest()
		return cached{info, err}
	}).(cached)

	if c.err != nil {
		return nil, c.err
	}
	info := *c.info
	return &info, nil
}

func (r *cachingRepo) GoMod(rev string) ([]byte, error) {
	type cached struct {
		text []byte
		err  error
	}
	c := r.cache.Do("gomod:", func() interface{} {
		r.mu.Lock()
		defer r.mu.Unlock()
		text, err := r.r.GoMod(rev)
		return cached{text, err}
	}).(cached)

	if c.err != nil {
		return nil, c.err
	}
	return append([]byte(nil), c.text...), nil
}

func (r *cachingRepo) Zip(version, tmpdir string) (string, error) {
	r.mu.Lock()
	defer r.mu.Unlock()
	return r.r.Zip(version, tmpdir)
}
