purge code for the autotypist

Signed-off-by: Jeff Carr <jcarr@wit.com>
This commit is contained in:
Jeff Carr 2024-02-21 08:32:59 -06:00
parent 42c506c098
commit df0ff5af1c
12 changed files with 32 additions and 586 deletions

3
.gitignore vendored
View File

@ -2,6 +2,5 @@
go.mod go.mod
go.sum go.sum
/resources/*.so /resources/*.so
myrepos
autotypist
/files/* /files/*
submit-patchset

View File

@ -2,15 +2,15 @@
all: build all: build
reset reset
./autotypist ./submit-patchset
only-me: build only-me: build
reset reset
./autotypist --only-me ./submit-patchset --only-me
stderr: build stderr: build
echo "writing to /tmp/autotypist.log" echo "writing to /tmp/submit-patchset.log"
./autotypist >/tmp/autotypist.log 2>&1 ./submit-patchset >/tmp/submit-patchset.log 2>&1
goimports: goimports:
goimports -w *.go goimports -w *.go
@ -19,18 +19,15 @@ goimports:
gocui: build gocui: build
reset reset
./autotypist --gui gocui >/tmp/autotypist.log 2>&1 ./submit-patchset --gui gocui >/tmp/submit-patchset.log 2>&1
build: build:
echo "build it!" echo "build it!"
-rm resources/*.so
cp -a ~/go/src/go.wit.com/toolkits/*.so resources/
GO111MODULE=off go build -v -x GO111MODULE=off go build -v -x
install: install:
rm -f ~/go/src/go.wit.com/toolkits/*.so
go install -v -x go install -v -x
autotypist submit-patchset
check-git-clean: check-git-clean:
@git diff-index --quiet HEAD -- || (echo "Git repository is dirty, please commit your changes first"; exit 1) @git diff-index --quiet HEAD -- || (echo "Git repository is dirty, please commit your changes first"; exit 1)

View File

@ -14,11 +14,7 @@ import (
) )
var args struct { var args struct {
DownloadAll bool `arg:"--download-all" help:"download everything from go.wit.com"` OnlyMe bool `arg:"--only-me" help:"only scan repos from ~/.config/submitpatchsets`
GitPull bool `arg:"--git-pull" help:"do git pull in every repository"`
CheckoutUser bool `arg:"--switch-to-user-branch" help:"switch everything to your user branch"`
CheckoutDevel bool `arg:"--switch-to-devel-branch" help:"switch everything to the devel branch"`
OnlyMe bool `arg:"--only-me" help:"only scan repos from ~/.config/autotypist"`
} }
func init() { func init() {

60
docs.go
View File

@ -1,60 +0,0 @@
package main
import (
"fmt"
"os"
"path/filepath"
"go.wit.com/gui"
"go.wit.com/lib/gui/repolist"
"go.wit.com/lib/gui/shell"
"go.wit.com/log"
)
func docsBox(vbox *gui.Node) {
group := vbox.NewGroup("Docs")
group.NewButton("make 'go.work' file", func() {
me.autotypistWindow.Disable()
goSrcDir := me.goSrcPwd.String()
filename := filepath.Join(goSrcDir, "go.work")
f, err := os.OpenFile(filename, os.O_WRONLY|os.O_CREATE, 0600)
if err != nil {
return
}
defer f.Close()
fmt.Fprintln(f, "go 1.21.4")
fmt.Fprintln(f, "")
fmt.Fprintln(f, "use (")
for _, repo := range repolist.AllRepos() {
if repo.Exists("go.mod") {
fmt.Fprintln(f, "\t"+repo.Status.GoPath())
} else {
log.Info("missing go.mod for", repo.Status.Path())
repo.Status.MakeRedomod()
}
}
fmt.Fprintln(f, ")")
me.autotypistWindow.Enable()
})
group.NewButton("run pkgsite", func() {
tmp := me.userHomePwd.String()
tmpDir := filepath.Join(tmp, "go/src")
os.Chdir(tmpDir)
pkgsite := filepath.Join(tmp, "go/bin", "pkgsite")
os.Unsetenv("GO111MODULE")
go shell.Run([]string{pkgsite})
shell.Run([]string{"ping", "-c", "3", "git.wit.org"})
})
group.NewButton("open docs in browser (localhost:8080)", func() {
me.autotypistWindow.Disable()
defer me.autotypistWindow.Enable()
shell.OpenBrowser("http://localhost:8080")
})
}

View File

@ -2,9 +2,6 @@ package main
import ( import (
"go.wit.com/gui" "go.wit.com/gui"
"go.wit.com/lib/debugger"
"go.wit.com/lib/gui/gowit"
"go.wit.com/lib/gui/logsettings"
"go.wit.com/lib/gui/repolist" "go.wit.com/lib/gui/repolist"
"go.wit.com/log" "go.wit.com/log"
) )
@ -80,52 +77,5 @@ func globalDisplayOptions(vbox *gui.Node) {
log.Info("re-scanning repos now") log.Info("re-scanning repos now")
i, s := me.repos.View.ScanRepositories() i, s := me.repos.View.ScanRepositories()
log.Info("re-scanning repos done", i, s) log.Info("re-scanning repos done", i, s)
me.duration.SetText(s)
})
var tagsW *tagWindow
group1.NewButton("git tags Window", func() {
if tagsW == nil {
tagsW = makeTagWindow()
} else {
tagsW.win.Toggle()
}
})
var listallB *gui.Node
listallB = group1.NewButton("go.wit.com", func() {
listallB.Disable()
if me.lw == nil {
me.lw = gowit.ListWindow(me.repos.View)
}
if me.lw.Hidden() {
me.lw.Show()
} else {
me.lw.Hide()
}
listallB.Enable()
}) })
} }
func debuggerBox(vbox *gui.Node) {
group2 := vbox.NewGroup("Debugger")
group2.NewButton("logging Window", func() {
logsettings.LogWindow()
})
group2.NewButton("Debugger Window", func() {
debugger.DebugWindow()
})
}
func hidePerfect() {
for _, repo := range repolist.AllRepos() {
if repo.IsPerfect() {
if repo.Hidden() {
continue
}
repo.Hide()
// return
}
}
}

View File

@ -1,116 +0,0 @@
package main
import (
"os"
"path/filepath"
"strings"
"go.wit.com/gui"
"go.wit.com/lib/gui/repolist"
"go.wit.com/log"
)
func globalResetOptions(box *gui.Node) {
group2 := box.NewGroup("Global Destructive Options")
me.autoRebuildButton = group2.NewButton("rebuild autotypist", func() {
me.autoRebuildButton.Disable()
me.autoRebuildButton.SetLabel("running....")
attemptAutoRebuild()
me.autoRebuildButton.Enable()
me.autoRebuildButton.SetLabel("rebuild autotypist")
})
me.stopOnErrors = group2.NewCheckbox("Stop on errors")
me.stopOnErrors.SetChecked(true)
me.autoDryRun = group2.NewCheckbox("autotypist --dry-run")
me.autoDryRun.SetChecked(true)
buildOptions := group2.NewGrid("buildOptions", 2, 1)
buildOptions.NewLabel("start over")
me.deleteGoSrcPkgB = buildOptions.NewButton("rm ~/go/src & ~/go/pkg", func() {
var state string = me.deleteGoSrcPkgB.String()
for _, repo := range repolist.AllRepos() {
if repo.GoPath() == "go.wit.com/apps/autotypist" {
continue
}
if repo.Status.CheckDirty() {
log.Warn("repo is dirty. commit your changes first", repo.Status.Path())
me.deleteGoSrcPkgB.SetLabel("rm ~/go/src (can't. dirty repos)")
return
}
}
log.Warn("no repos have uncommited changes")
log.Warn("TODO: check things are pushed and check every dir in go/src/")
if strings.HasPrefix(state, "rm ~/go/src") {
me.deleteGoSrcPkgB.SetLabel("ARE YOU SURE?")
return
}
if me.deleteGoSrcPkgB.String() == "ARE YOU SURE?" {
me.deleteGoSrcPkgB.SetLabel("WE ARE NOT KIDDING")
return
}
var totals string = "All " + me.summary.totalGoOL.String() + " Repos?"
log.Info("totals =", totals)
if me.deleteGoSrcPkgB.String() == "WE ARE NOT KIDDING" {
me.deleteGoSrcPkgB.SetLabel(totals)
return
}
if me.deleteGoSrcPkgB.String() == totals {
homeDir := me.userHomePwd.String()
fullpath := filepath.Join(homeDir, "go")
gosrc := filepath.Join(fullpath, "src")
gopkg := filepath.Join(fullpath, "pkg")
quickCmd(fullpath, []string{"rm", "-rf", gosrc})
quickCmd(fullpath, []string{"chmod", "700", "-R", gopkg})
quickCmd(fullpath, []string{"rm", "-rf", gopkg})
if me.autoDryRun.Checked() {
me.deleteGoSrcPkgB.SetLabel("rm ~/go/src (uncheck dry-run)")
return
}
}
})
}
func attemptAutoRebuild() {
os.Setenv("GO111MODULE", "off")
version := "latest"
homeDir := me.userHomePwd.String()
quickCmd(homeDir, []string{"mkdir", "-p", "go/src/go.wit.com/apps/"})
fullpath := filepath.Join(homeDir, "go/src/go.wit.com/apps/")
quickCmd(fullpath, []string{"go", "get", "-v", "go.wit.com/apps/autotypist"})
quickCmd(fullpath, []string{"go", "get", "-v", "go.wit.com/toolkits/debian"})
quickCmd(fullpath, []string{"go", "get", "-v", "go.wit.com/toolkits/tree"})
quickCmd(fullpath, []string{"go", "get", "-v", "go.wit.com/toolkits/nocui"})
quickCmd(fullpath, []string{"go", "get", "-v", "go.wit.com/toolkits/gocui"})
quickCmd(fullpath, []string{"go", "get", "-v", "go.wit.com/toolkits/andlabs"})
os.Unsetenv("GO111MODULE")
quickCmd(homeDir, []string{"mkdir", "-p", "go/lib"})
fullpath = filepath.Join(homeDir, "go/src/go.wit.com/toolkits/nocui/")
libfile := filepath.Join(homeDir, "go/lib/nocui.so")
quickCmd(fullpath, []string{"go", "mod", "init"})
quickCmd(fullpath, []string{"go", "mod", "tidy"})
quickCmd(fullpath, []string{"go", "build", "-v", "-x", "-buildmode=plugin", "-o", libfile})
fullpath = filepath.Join(homeDir, "go/src/go.wit.com/toolkits/gocui/")
libfile = filepath.Join(homeDir, "go/lib/gocui.so")
quickCmd(fullpath, []string{"go", "mod", "init"})
quickCmd(fullpath, []string{"go", "mod", "tidy"})
quickCmd(fullpath, []string{"go", "build", "-v", "-x", "-buildmode=plugin", "-o", libfile})
fullpath = filepath.Join(homeDir, "go/src/go.wit.com/toolkits/andlabs/")
libfile = filepath.Join(homeDir, "go/lib/andlabs.so")
quickCmd(fullpath, []string{"go", "mod", "init"})
quickCmd(fullpath, []string{"go", "mod", "tidy"})
quickCmd(fullpath, []string{"go", "build", "-v", "-x", "-buildmode=plugin", "-o", libfile})
fullpath = filepath.Join(homeDir, "go/src/go.wit.com")
quickCmd(fullpath, []string{"go", "install", "-v", "go.wit.com/apps/autotypist@" + version})
}

View File

@ -1,123 +0,0 @@
package main
import (
"os"
"go.wit.com/lib/gui/repolist"
"go.wit.com/log"
)
/*
This will process the command line arguements like --git-pull
It should do them in a smart order. If any of them are called,
don't show the GUI at all and just exit.
*/
func argGitPull() bool {
log.Info("running git pull everywhere")
me.autotypistWindow.Hide()
cmd := []string{"git", "pull"}
var failed int = 0
for _, repo := range repolist.AllRepos() {
log.Info("Running:", repo.Status.Path(), cmd)
err, output := repo.RunCmd(cmd)
if err == nil {
log.Info(output)
} else {
failed += 1
log.Info("Something went wrong. Got err", err)
log.Info("output =", output)
return false
}
}
log.Info("Ran git pull in all repos. failure count =", failed)
return true
}
func argCheckoutDevel() bool {
log.Info("running git checkout devel everwhere")
me.autotypistWindow.Hide()
var failed int = 0
for _, repo := range repolist.AllRepos() {
if repo.CheckDirty() {
log.Info("skipping dirty repo", repo.Name())
continue
}
branch := repo.Status.GetDevelBranchName()
cmd := []string{"git", "checkout", branch}
log.Info("Running:", cmd, "in", repo.Name())
err, output := repo.RunCmd(cmd)
if err == nil {
log.Info("git checkout worked", output)
} else {
failed += 1
log.Info("git checkout failed")
log.Info("Something went wrong. Got err", err)
log.Info("output =", output)
// return false
}
}
log.Info("Ran git checkout in all repos. failure count =", failed)
return true
}
func argCheckoutUser() bool {
log.Info("running git checkout devel everwhere")
me.autotypistWindow.Hide()
var failed int = 0
for _, repo := range repolist.AllRepos() {
if repo.Status.CheckDirty() {
log.Info("skipping dirty repo", repo.Name())
continue
}
branch := repo.Status.GetUserBranchName()
cmd := []string{"git", "checkout", branch}
log.Info("Running:", cmd, "in", repo.Name())
err, output := repo.RunCmd(cmd)
if err == nil {
log.Info("git checkout worked", output)
} else {
failed += 1
log.Info("git checkout failed")
log.Info("Something went wrong. Got err", err)
log.Info("output =", output)
// return false
}
}
log.Info("Ran git checkout in all repos. failure count =", failed)
return true
}
func handleCmdLine() {
var doExit bool = false
if args.CheckoutDevel {
argCheckoutDevel()
doExit = true
} else {
log.Info("not switching to devel branches")
}
if args.CheckoutUser {
argCheckoutUser()
doExit = true
} else {
log.Info("not switching to user branches")
}
if args.GitPull {
if argGitPull() {
log.Info("git pull everywhere worked")
} else {
log.Info("git failed somewhere")
}
doExit = true
} else {
log.Info("not running git pull everywhere")
}
if doExit {
os.Exit(0)
}
}

32
main.go
View File

@ -1,33 +1,27 @@
package main package main
import ( // An app to submit patches for the 30 GO GUI repos
"embed"
"go.wit.com/lib/debugger" import (
"go.wit.com/lib/gadgets"
"go.wit.com/log" "go.wit.com/log"
"go.wit.com/gui" "go.wit.com/gui"
) )
//go:embed resources/*
var resToolkit embed.FS
func main() { func main() {
me = new(autoType) me = new(mainType)
me.myGui = gui.New() me.myGui = gui.New().Default()
me.myGui.InitEmbed(resToolkit)
me.myGui.Default()
me.autotypistWindow = me.myGui.NewWindow("autotypist: it types faster than you can.") me.mainWindow = gadgets.RawBasicWindow("submit & test patchsets")
me.mainbox = me.autotypistWindow.NewBox("bw hbox", true) me.mainWindow.Make()
me.mainWindow.Show()
me.mainbox = me.mainWindow.Box()
vbox1 := me.mainbox.NewVerticalBox("BOX1") vbox1 := me.mainbox.NewVerticalBox("BOX1")
globalDisplayOptions(vbox1) globalDisplayOptions(vbox1)
docsBox(vbox1)
if debugger.ArgDebug() {
debuggerBox(vbox1)
}
// disable the interface while everything is scanned // disable the interface while everything is scanned
me.Disable() me.Disable()
@ -35,8 +29,6 @@ func main() {
globalBuildOptions(vbox2) globalBuildOptions(vbox2)
me.summary = submitPatchesBox(vbox2) me.summary = submitPatchesBox(vbox2)
globalResetOptions(me.mainbox)
me.repos = makeRepoView() me.repos = makeRepoView()
// parse config file and scan for .git repos // parse config file and scan for .git repos
@ -46,10 +38,6 @@ func main() {
// TODO: should not really be necessary directly after init() // TODO: should not really be necessary directly after init()
me.repos.View.ScanRepositories() me.repos.View.ScanRepositories()
// process everything on the command line
// may exit here
handleCmdLine()
// processing is done. update the repo summary box // processing is done. update the repo summary box
me.summary.Update() me.summary.Update()

View File

@ -1,37 +0,0 @@
go.wit.com/log
go.wit.com/gui guimaster
go.wit.com/widget guimaster
go.wit.com/lib/debugger guimaster
go.wit.com/toolkits/tree guimaster
go.wit.com/toolkits/debian guimaster
go.wit.com/toolkits/nocui guimaster
go.wit.com/toolkits/gocui guimaster
go.wit.com/toolkits/andlabs guimaster
go.wit.com/lib/gadgets guimaster
go.wit.com/lib/gui/repostatus guimaster
go.wit.com/lib/gui/logsettings guimaster
go.wit.com/lib/gui/hostname guimaster
go.wit.com/lib/gui/linuxstatus guimaster
go.wit.com/lib/gui/digitalocean guimaster
go.wit.com/lib/gui/cloudflare guimaster
go.wit.com/lib/gui/shell guimaster
go.wit.com/apps/helloworld guimaster
go.wit.com/apps/basicwindow guimaster
go.wit.com/apps/gadgetwindow guimaster
go.wit.com/apps/control-panel-dns main
go.wit.com/apps/control-panel-digitalocean
go.wit.com/apps/control-panel-cloudflare master
go.wit.com/apps/control-panel-vpn
go.wit.com/apps/autotypist master
go.wit.com/apps/go.wit.com
go.wit.com/apps/guireleaser
go.wit.com/dev/davecgh/spew/ guimaster
go.wit.com/dev/alexflint/arg/ guimaster
go.wit.com/dev/alexflint/scalar/ guimaster
go.wit.com/dev/andlabs/ui guimaster devel jcarr
go.wit.com/dev/andlabs/libui guimaster devel jcarr

View File

@ -5,22 +5,21 @@ import (
"go.wit.com/lib/gadgets" "go.wit.com/lib/gadgets"
) )
var me *autoType var me *mainType
func (b *autoType) Disable() { func (b *mainType) Disable() {
b.mainbox.Disable() b.mainbox.Disable()
} }
func (b *autoType) Enable() { func (b *mainType) Enable() {
b.mainbox.Enable() b.mainbox.Enable()
} }
// this app's variables // this app's variables
type autoType struct { type mainType struct {
// allrepos map[string]*repo
myGui *gui.Node myGui *gui.Node
autotypistWindow *gui.Node mainWindow *gadgets.BasicWindow
// the main box. enable/disable this // the main box. enable/disable this
mainbox *gui.Node mainbox *gui.Node
@ -31,26 +30,10 @@ type autoType struct {
// our view of the repositories // our view of the repositories
repos *repoWindow repos *repoWindow
// #### autotypist Global Display Options // #### Sorting options for the repolist
autoHidePerfect *gui.Node autoHidePerfect *gui.Node
autoHideReadOnly *gui.Node autoHideReadOnly *gui.Node
// #### autotypist Global Build Options
// what to change all the branches to
// so, as a developer, you can move all the repos
// to the 'devel' branch and then test a devel branch build
// then switch back to your 'username' branch and do a build there
toMoveToBranch string
// this button will regenerate everyones go.mod & go.sum
rerunGoMod *gui.Node
// if checked, will stop trying to os.Exec() things after failure
stopOnErrors *gui.Node
// button to attempt to autorebuild
autoRebuildButton *gui.Node
// checkbox for --dry-run // checkbox for --dry-run
autoDryRun *gui.Node autoDryRun *gui.Node
@ -64,19 +47,11 @@ type autoType struct {
// what is being used as ~/go/src // what is being used as ~/go/src
goSrcPwd *gadgets.OneLiner goSrcPwd *gadgets.OneLiner
downloadEverythingButton *gui.Node
// delete ~/go/src & ~/go/pkg buttons
deleteGoSrcPkgB *gui.Node
// displays a summary of all the repos // displays a summary of all the repos
// has total dirty, total read-only // has total dirty, total read-only
// total patches, etc // total patches, etc
summary *patchSummary summary *patchSummary
// shows how long the scan went for
duration *gui.Node
// when switch to user or devel branches, autocreate them // when switch to user or devel branches, autocreate them
autoCreateBranches *gui.Node autoCreateBranches *gui.Node
@ -85,29 +60,3 @@ type autoType struct {
newBranch *gui.Node newBranch *gui.Node
setBranchB *gui.Node setBranchB *gui.Node
} }
/*
type repo struct {
hidden bool
lasttagrev string
lasttag string
giturl string
pLabel *gui.Node // path label
lastTag *gui.Node // last tagged version label
vLabel *gui.Node // version label
dirtyLabel *gui.Node // git state (dirty or not?)
goSumStatus *gui.Node // what is the state of the go.sum file
masterVersion *gui.Node // the master branch version
develVersion *gui.Node // the devel branch version
userVersion *gui.Node // the user branch version
endBox *gui.Node // a general box at the end of the row
statusButton *gui.Node // opens up the status window
diffButton *gui.Node // opens up the status window
status *repostatus.RepoStatus
}
*/

View File

@ -86,21 +86,13 @@ func submitPatchesBox(box *gui.Node) *patchSummary {
s.totalUserRepos.SetText(strconv.Itoa(repocount) + " go repos") s.totalUserRepos.SetText(strconv.Itoa(repocount) + " go repos")
}) })
// this Update is deprecated and probably should be the function above
/*
s.grid.NewButton("summary.Update()", func() {
// update the stats
s.Update()
})
*/
s.grid.NewButton("Make Patches", func() {
/* this used to be the way and should probably be revisited /* this used to be the way and should probably be revisited
s.grid.NewButton("Make Patches", func() {
for i, p := range s.allp { for i, p := range s.allp {
log.Info(i, p.Ref, p.RS.String()) log.Info(i, p.Ref, p.RS.String())
} }
*/
}) })
*/
s.grid.NextRow() s.grid.NextRow()
@ -139,8 +131,12 @@ func submitPatchesBox(box *gui.Node) *patchSummary {
s.grid.NewLabel("") s.grid.NewLabel("")
s.grid.NewLabel("") s.grid.NewLabel("")
s.grid.NewButton("merge from user", func() {}) s.grid.NewButton("merge from user", func() {
s.grid.NewButton("merge from devel", func() {}) log.Info("this should make a patchset of your patches")
})
s.grid.NewButton("merge from devel", func() {
log.Info("this probably should not exist")
})
s.grid.NextRow() s.grid.NextRow()
group1 = box.NewGroup("Create GUI Patch Set") group1 = box.NewGroup("Create GUI Patch Set")

View File

@ -1,93 +0,0 @@
package main
import (
"go.wit.com/gui"
"go.wit.com/log"
"go.wit.com/lib/gadgets"
"go.wit.com/lib/gui/repolist"
"go.wit.com/lib/gui/repostatus"
)
var tagW *tagWindow
type tagWindow struct {
win *gadgets.BasicWindow
box *gui.Node
grid *gui.Node
group *gui.Node
allTags []*gitTag
}
type gitTag struct {
rs *repostatus.RepoStatus
hidden bool
}
func makeTagWindow() *tagWindow {
if tagW != nil {
tagW.win.Toggle()
return tagW
}
tagW = new(tagWindow)
tagW.win = gadgets.NewBasicWindow(me.myGui, "git tag tasks")
tagW.win.Custom = func() {
log.Warn("got to close")
}
tagW.win.Make()
tagW.win.StandardClose()
tagW.win.Draw()
tagW.box = tagW.win.Box()
topGrid := tagW.box.RawGrid()
tagW.group = tagW.box.NewGroup("tags")
tagW.grid = tagW.box.RawGrid()
topGrid.NewButton("list all tags", func() {
me.autotypistWindow.Disable()
defer me.autotypistWindow.Enable()
for _, repo := range repolist.AllRepos() {
allTags := repo.AllTags()
for _, t := range allTags {
log.Info("found tag:", t.TagString(), "from", repo.Name())
}
}
}).SetProgName("TAGSLISTALL")
topGrid.NewButton("delete all dup tags", func() {
me.autotypistWindow.Disable()
defer me.autotypistWindow.Enable()
for _, repo := range repolist.AllRepos() {
if repo.GoPath() == "go.wit.com/lib/gadgets" {
// only do log for now
} else {
// continue
}
tagsW := repo.TagsBox()
tagsW.PruneSmart()
deleteTags := tagsW.List()
for _, t := range deleteTags {
tagW.grid.NewLabel(t.TagString())
tagW.grid.NewLabel(repo.Name())
tagW.grid.NewButton("delete", func() {
repo.DeleteTag(t)
})
tagW.grid.NextRow()
if me.autoDryRun.Checked() {
log.Info("delete tag --dry-run:", t.TagString(), "from", repo.Name())
} else {
log.Info("Deleting tag:", t.TagString(), "from", repo.Name())
go repo.DeleteTag(t)
log.Sleep(1)
}
}
}
})
return tagW
}
func (t *gitTag) Hide() {
t.hidden = true
}