updates_check.go (92 lines of code) (raw):
// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License. You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied. See the License for the
// specific language governing permissions and limitations
// under the License.
package openserverless
import (
"errors"
"fmt"
"io/fs"
"os"
"time"
"github.com/go-git/go-git/v5"
)
const LATESTCHECK = ".latestcheck"
func checkUpdated(base string, timeInterval time.Duration) {
trace("checkUpdated", base)
olaris_base := joinpath(base, getOpsBranch())
latest_check_path := joinpath(olaris_base, LATESTCHECK)
olaris_path := joinpath(olaris_base, "olaris")
// if no olaris dir, no update check
if !isDir(olaris_path) {
return
}
// get info on latest_check file
file, ok := checkLatestFile(latest_check_path)
if !ok {
return
}
mtime := file.ModTime()
now := time.Now().Local()
diff := now.Sub(mtime)
if diff >= timeInterval {
fmt.Println("Checking for updates...")
// touch latest_check file ONLY if enough time has passed
touchLatestCheckFile(latest_check_path)
// check if remote olaris is newer
if checkRemoteOlarisNewer(olaris_path) {
fmt.Print("New tasks available! Use 'ops -update' to update.\n\n")
} else {
fmt.Print("Tasks up to date!\n\n")
}
}
}
func checkLatestFile(path string) (fs.FileInfo, bool) {
file, err := os.Stat(path)
if errors.Is(err, os.ErrNotExist) {
debug("latestcheck file not found, skipping update check")
return nil, false
} else if err != nil {
debug("failed to access .latestcheck file info", err)
return nil, false
}
return file, true
}
func createLatestCheckFile(base string) {
// create latest_check file
_, err := os.Create(joinpath(base, LATESTCHECK))
if err != nil {
warn("failed to set latest_check file", err)
}
}
func touchLatestCheckFile(latest_check_path string) {
trace("touch latest_check file", latest_check_path)
currentTime := time.Now().Local()
err := os.Chtimes(latest_check_path, currentTime, currentTime)
if err != nil {
warn("failed to set latest update check", err)
}
}
func checkRemoteOlarisNewer(olaris_path string) bool {
trace("checkRemoteOlarisNewer", olaris_path)
repo, err := git.PlainOpen(olaris_path)
if err != nil {
warn("failed to check olaris folder", err)
return false
}
localRef, err := repo.Head()
if err != nil {
warn("failed to check olaris folder", err)
return false
}
remote, err := repo.Remote("origin")
if err != nil {
warn("failed to check remote olaris", err)
return false
}
_ = remote.Fetch(&git.FetchOptions{})
remoteRefs, err := remote.List(&git.ListOptions{})
if err != nil {
warn("failed to check remote olaris", err)
return false
}
// check ref is in refs
for _, remoteRef := range remoteRefs {
if localRef.Name().String() == remoteRef.Name().String() {
// is hash different?
if localRef.Hash().String() != remoteRef.Hash().String() {
return true
}
}
}
return false
}