Skip to content

Commit

Permalink
feat: follow XDG Base Directory Specification
Browse files Browse the repository at this point in the history
  • Loading branch information
mochaaP committed Jan 10, 2025
1 parent 4ece259 commit 1b389b1
Show file tree
Hide file tree
Showing 12 changed files with 60 additions and 63 deletions.
16 changes: 10 additions & 6 deletions cmd/init.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,9 @@ import (
"encoding/gob"
"fmt"
"os"
"path"

vt "github.com/VirusTotal/vt-go"
"github.com/mitchellh/go-homedir"
"github.com/adrg/xdg"
"github.com/spf13/cobra"
)

Expand Down Expand Up @@ -51,7 +50,7 @@ func NewInitCmd() *cobra.Command {

Run: func(cmd *cobra.Command, args []string) {

fmt.Printf(vtBanner)
fmt.Print(vtBanner)

apiKey := cmd.Flags().Lookup("apikey").Value.String()

Expand All @@ -68,13 +67,13 @@ func NewInitCmd() *cobra.Command {
os.Exit(1)
}

dir, err := homedir.Dir()
relCache, err := xdg.CacheFile("vt-cli/relationships")
if err != nil {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
}

relCacheFile, err := os.Create(path.Join(dir, ".vt.relationships.cache"))
relCacheFile, err := os.Create(relCache)
if err != nil {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
Expand All @@ -88,7 +87,12 @@ func NewInitCmd() *cobra.Command {
os.Exit(1)
}

configFilePath := path.Join(dir, ".vt.toml")
configFilePath, err := xdg.ConfigFile("vt-cli/vt.toml")
if err != nil {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
}

configFile, err := os.Create(configFilePath)
if err != nil {
fmt.Fprintln(os.Stderr, err)
Expand Down
21 changes: 10 additions & 11 deletions cmd/privileges.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import (

func NewPrivilegeCmd(target string) *cobra.Command {
cmd := &cobra.Command{
Use: "privileges",
Use: "privileges",
Short: fmt.Sprintf("Change %s privileges", target),
}

Expand All @@ -21,23 +21,22 @@ func NewPrivilegeCmd(target string) *cobra.Command {
return cmd
}


type Privilege struct {
Granted bool `json:"granted"`
Granted bool `json:"granted"`
ExpirationDate int64 `json:"expiration_date"`
}

type Privileges map[string]Privilege

func NewPrivilegeGrantCmd(target string) *cobra.Command {
cmd := &cobra.Command{
Use: fmt.Sprintf("grant [%sname] [privilege]...", target),
Short: fmt.Sprintf("Grant privileges to a %s", target),
Use: fmt.Sprintf("grant [%sname] [privilege]...", target),
Short: fmt.Sprintf("Grant privileges to a %s", target),
Example: fmt.Sprintf(" vt %s privileges grant my%s intelligence downloads-tier-2", target, target),
Args: cobra.MinimumNArgs(2),
Args: cobra.MinimumNArgs(2),
RunE: func(cmd *cobra.Command, args []string) error {
var expirationDate int64
if expiration:= viper.GetString("expiration"); expiration != "" {
if expiration := viper.GetString("expiration"); expiration != "" {
var err error
expirationDate, err = strconv.ParseInt(expiration, 10, 64)
if err != nil {
Expand Down Expand Up @@ -68,18 +67,18 @@ func NewPrivilegeGrantCmd(target string) *cobra.Command {
},
}

cmd.Flags().StringP("" +
cmd.Flags().StringP(""+
"expiration", "e", "",
"expiration time for the granted privileges (UNIX timestamp or YYYY-MM-DD)")
return cmd
}

func NewPrivilegeRevokeCmd(target string) *cobra.Command {
return &cobra.Command{
Use: fmt.Sprintf("revoke [%sname] [privilege]...", target),
Short: fmt.Sprintf("Revoke privileges from a %s", target),
Use: fmt.Sprintf("revoke [%sname] [privilege]...", target),
Short: fmt.Sprintf("Revoke privileges from a %s", target),
Example: fmt.Sprintf(" vt %s privileges revoke my%s intelligence downloads-tier-2", target, target),
Args: cobra.MinimumNArgs(2),
Args: cobra.MinimumNArgs(2),
RunE: func(cmd *cobra.Command, args []string) error {
privileges := Privileges{}
for _, arg := range args[1:] {
Expand Down
11 changes: 7 additions & 4 deletions cmd/relationship.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,20 +19,23 @@ import (
"fmt"
"github.com/VirusTotal/vt-cli/utils"
"os"
"path"
"sync"

vt "github.com/VirusTotal/vt-go"
homedir "github.com/mitchellh/go-homedir"
"github.com/adrg/xdg"
"github.com/spf13/cobra"
"github.com/spf13/viper"
)

var objectRelationshipsMap map[string][]vt.RelationshipMeta

func init() {
home, _ := homedir.Dir()
f, err := os.Open(path.Join(home, ".vt.relationships.cache"))
cachePath, err := xdg.SearchCacheFile("vt-cli/relationships")
if err != nil {
return
}

f, err := os.Open(cachePath)
if err == nil {
defer f.Close()
dec := gob.NewDecoder(f)
Expand Down
3 changes: 1 addition & 2 deletions cmd/url.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,6 @@ var urlCmdExample = ` vt url https://www.virustotal.com
vt url f1177df4692356280844e1d5af67cc4a9eccecf77aa61c229d483b7082c70a8e
cat list_of_urls | vt url -`


// Regular expressions used for validating a URL identifier.
var urlID = regexp.MustCompile(`[0-9a-fA-F]{64}`)

Expand All @@ -55,7 +54,7 @@ func NewURLCmd() *cobra.Command {
}
r := utils.NewMappedStringReader(
utils.StringReaderFromCmdArgs(args),
func (url string) string {
func(url string) string {
if urlID.MatchString(url) {
// The user provided a URL identifier as returned by
// VirusTotal's API, which consists in the URL's SHA-256.
Expand Down
4 changes: 2 additions & 2 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,14 @@ go 1.22.0

require (
github.com/VirusTotal/vt-go v1.0.1
github.com/adrg/xdg v0.5.3
github.com/briandowns/spinner v1.23.1
github.com/cavaliergopher/grab/v3 v3.0.1
github.com/dustin/go-humanize v1.0.1
github.com/fatih/color v1.17.0
github.com/gobwas/glob v0.2.3
github.com/gosuri/uitable v0.0.4
github.com/k0kubun/go-ansi v0.0.0-20180517002512-3bf9e2903213
github.com/mitchellh/go-homedir v1.1.0
github.com/plusvic/go-ansi v0.0.0-20180516115420-9879244c4340
github.com/spf13/cobra v1.8.1
github.com/spf13/pflag v1.0.5
Expand Down Expand Up @@ -45,7 +45,7 @@ require (
go.uber.org/atomic v1.9.0 // indirect
go.uber.org/multierr v1.9.0 // indirect
golang.org/x/exp v0.0.0-20230905200255-921286631fa9 // indirect
golang.org/x/sys v0.18.0 // indirect
golang.org/x/sys v0.26.0 // indirect
golang.org/x/term v0.1.0 // indirect
golang.org/x/text v0.14.0 // indirect
gopkg.in/ini.v1 v1.67.0 // indirect
Expand Down
8 changes: 4 additions & 4 deletions go.sum
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
github.com/VirusTotal/vt-go v1.0.1 h1:rj/qugIY8XNC6ogwOaeJAGCOsb3nmY63+yuDMtHOx0Q=
github.com/VirusTotal/vt-go v1.0.1/go.mod h1:u1+HeRyl/gQs67eDgVEWNE7+x+zCyXhdtNVrRJR5YPE=
github.com/adrg/xdg v0.5.3 h1:xRnxJXne7+oWDatRhR1JLnvuccuIeCoBu2rtuLqQB78=
github.com/adrg/xdg v0.5.3/go.mod h1:nlTsY+NNiCBGCK2tpm09vRqfVzrc2fLmXGpBLF0zlTQ=
github.com/briandowns/spinner v1.23.1 h1:t5fDPmScwUjozhDj4FA46p5acZWIPXYE30qW2Ptu650=
github.com/briandowns/spinner v1.23.1/go.mod h1:LaZeM4wm2Ywy6vO571mvhQNRcWfRUnXOs0RcKV0wYKM=
github.com/cavaliergopher/grab/v3 v3.0.1 h1:4z7TkBfmPjmLAAmkkAZNX/6QJ1nNFdv3SdIHXju0Fr4=
Expand Down Expand Up @@ -43,8 +45,6 @@ github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWE
github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
github.com/mattn/go-runewidth v0.0.16 h1:E5ScNMtiwvlvB5paMFdw9p4kSQzbXFikJ5SQO6TULQc=
github.com/mattn/go-runewidth v0.0.16/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w=
github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y=
github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
github.com/mitchellh/mapstructure v1.5.0 h1:jeMsZIYE/09sWLaz43PL7Gy6RuMjD2eJVyuac5Z2hdY=
github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo=
github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM=
Expand Down Expand Up @@ -101,8 +101,8 @@ golang.org/x/sync v0.6.0 h1:5BMeUDZ7vkXGfEr1x9B4bRcTH4lpkTkpdh0T/J+qjbQ=
golang.org/x/sync v0.6.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.18.0 h1:DBdB3niSjOA/O0blCZBqDefyWNYveAYMNF1Wum0DYQ4=
golang.org/x/sys v0.18.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/sys v0.26.0 h1:KHjCJyddX0LoSTb3J+vWpupP9p0oznkqVk/IfjymZbo=
golang.org/x/sys v0.26.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/term v0.1.0 h1:g6Z6vPFA9dYBAF7DWcH6sCcOntplXsDKcliusYijMlw=
golang.org/x/term v0.1.0/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ=
Expand Down
21 changes: 10 additions & 11 deletions utils/filter.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,19 +25,18 @@ import (
// excluding keys matching any of the patterns in "exclude". The logic for
// determining if a key matches the pattern goes as follow:
//
// * The path for the key is computed. If the key is in the top-level map its
// path is the key itself, if the key is contained within a nested map its
// path is the concatenation of the parent's path and the key, using a dot (.)
// as a separator. The path for "key" in {a:{b:{key:val}}} is a.b.key.
// - The path for the key is computed. If the key is in the top-level map its
// path is the key itself, if the key is contained within a nested map its
// path is the concatenation of the parent's path and the key, using a dot (.)
// as a separator. The path for "key" in {a:{b:{key:val}}} is a.b.key.
//
// * The path is matched against the pattern, which can contain asterisks (*)
// as a placeholder for any character different from a dot (.) and ** as a
// placeholder for any character including a dot. For more information go to:
// https://godoc.org/github.com/gobwas/glob#Compile
//
// * If the path matches any pattern in "include" the key is included in the
// resulting map, as long as it doesn't match a pattern in "exclude".
// - The path is matched against the pattern, which can contain asterisks (*)
// as a placeholder for any character different from a dot (.) and ** as a
// placeholder for any character including a dot. For more information go to:
// https://godoc.org/github.com/gobwas/glob#Compile
//
// - If the path matches any pattern in "include" the key is included in the
// resulting map, as long as it doesn't match a pattern in "exclude".
func FilterMap(m map[string]interface{}, include, exclude []string) map[string]interface{} {
includeGlob := make([]glob.Glob, len(include))
excludeGlob := make([]glob.Glob, len(exclude))
Expand Down
6 changes: 2 additions & 4 deletions utils/filter_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
// 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
// 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,
Expand Down Expand Up @@ -77,9 +77,7 @@ var testCases = []testCase{
include: []string{"foo"},
exclude: []string{"**.quux"},
input: testMap,
output: map[string]interface{}{

},
output: map[string]interface{}{},
},

testCase{
Expand Down
2 changes: 1 addition & 1 deletion utils/pqueue_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
// 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
// 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,
Expand Down
19 changes: 7 additions & 12 deletions vt/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,30 +14,25 @@
package main

import (
"fmt"
"os"
"path"

"github.com/VirusTotal/vt-cli/cmd"
homedir "github.com/mitchellh/go-homedir"
"github.com/adrg/xdg"
"github.com/spf13/cobra"
"github.com/spf13/viper"
)

// initConfig reads in config file and ENV variables if set.
func initConfig() {

// Find home directory.
home, err := homedir.Dir()
if err != nil {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
// Search config in XDG config directory and current directory
for _, v := range xdg.ConfigDirs {
viper.AddConfigPath(path.Join(v, "vt-cli"))
}

// Search config in home directory and current directory
viper.AddConfigPath(home)
viper.AddConfigPath(".")
// Config file must be named .vt + format extension (.toml, .json, etc)
viper.SetConfigName(".vt")
// Config file must be named vt + format extension (.toml, .json, etc)
viper.SetConfigName("vt")

// The prefix for all environment variables will be VTCLI_. Examples:
// VTCLI_PROXY, VTCLI_APIKEY.
Expand Down
2 changes: 1 addition & 1 deletion yaml/yaml.go
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,7 @@ func (enc *Encoder) encodeMap(m reflect.Value, indent int, prefix string) (err e
// If the key is an empty string or starts with some non-letter character
// let's enclose the key in double quotes.
firstChar, kLen := utf8.DecodeRuneInString(k.String())
if kLen == 0 || (firstChar != '_' && !unicode.IsLetter(firstChar)) {
if kLen == 0 || (firstChar != '_' && !unicode.IsLetter(firstChar)) {
keyPrinter(enc.w, "\"%s\": ", k)
} else {
keyPrinter(enc.w, "%s: ", k)
Expand Down
10 changes: 5 additions & 5 deletions yaml/yaml_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
// 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
// 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,
Expand Down Expand Up @@ -98,7 +98,7 @@ var tests = []T{
"uno": "1",
"dos": "2",
"tres": "3",
"": "",
"": "",
"#foo": "foo",
"|foo": "foo",
"_foo": "foo",
Expand Down Expand Up @@ -180,7 +180,7 @@ var tests = []T{
},
yaml: Y(fmt.Sprintf(`
Foo_date: 10000 # %v
`, time.Unix(10000, 0))),
`, time.Unix(10000, 0))),
},
{
data: struct {
Expand All @@ -190,7 +190,7 @@ var tests = []T{
},
yaml: Y(fmt.Sprintf(`
Bar_date: 10000 # %v
`, time.Unix(10000, 0))),
`, time.Unix(10000, 0))),
},
{
data: struct {
Expand All @@ -200,7 +200,7 @@ var tests = []T{
},
yaml: Y(fmt.Sprintf(`
Baz_date: 1.618312811e+09 # %v
`, time.Unix(1618312811, 0))),
`, time.Unix(1618312811, 0))),
},
}

Expand Down

0 comments on commit 1b389b1

Please sign in to comment.