gopkg.in/frapposelli/wwhrd.v0@v0.2.1/cli.go (about)

     1  package main
     2  
     3  import (
     4  	"fmt"
     5  	"os"
     6  	"strings"
     7  
     8  	"github.com/jessevdk/go-flags"
     9  	log "github.com/sirupsen/logrus"
    10  )
    11  
    12  type cliOpts struct {
    13  	List        `command:"list" alias:"ls" description:"List licenses"`
    14  	Check       `command:"check" alias:"chk" description:"Check licenses against config file"`
    15  	VersionFlag func() error `long:"version" short:"v" description:"Show CLI version"`
    16  
    17  	Quiet func() error `short:"q" long:"quiet" description:"quiet mode, do not log accepted packages"`
    18  }
    19  
    20  type List struct {
    21  }
    22  
    23  type Check struct {
    24  	File string `short:"f" long:"file" description:"input file" default:".wwhrd.yml"`
    25  }
    26  
    27  const VersionHelp flags.ErrorType = 1961
    28  
    29  var (
    30  	version = "dev"
    31  	commit  = "1961213"
    32  	date    = "1961-02-13T20:06:35Z"
    33  )
    34  
    35  func setQuiet() error {
    36  	log.SetLevel(log.ErrorLevel)
    37  	return nil
    38  }
    39  
    40  func newCli() *flags.Parser {
    41  	opts := cliOpts{
    42  		VersionFlag: func() error {
    43  			return &flags.Error{
    44  				Type:    VersionHelp,
    45  				Message: fmt.Sprintf("version %s\ncommit %s\ndate %s\n", version, commit, date),
    46  			}
    47  		},
    48  		Quiet: setQuiet,
    49  	}
    50  	parser := flags.NewParser(&opts, flags.HelpFlag|flags.PassDoubleDash)
    51  	parser.LongDescription = "What would Henry Rollins do?"
    52  
    53  	return parser
    54  }
    55  
    56  func (l *List) Execute(args []string) error {
    57  
    58  	log.SetFormatter(&log.TextFormatter{ForceColors: true})
    59  
    60  	root, err := rootDir()
    61  	if err != nil {
    62  		return err
    63  	}
    64  
    65  	pkgs, err := WalkImports(root)
    66  	if err != nil {
    67  		return err
    68  	}
    69  	lics := GetLicenses(root, pkgs)
    70  
    71  	for k, v := range lics {
    72  		if v.Recognized() {
    73  			log.WithFields(log.Fields{
    74  				"package": k,
    75  				"license": v.Type,
    76  			}).Info("Found License")
    77  		} else {
    78  			log.WithFields(log.Fields{
    79  				"package": k,
    80  			}).Warning("Did not find recognized license!")
    81  		}
    82  	}
    83  
    84  	return nil
    85  }
    86  
    87  func (c *Check) Execute(args []string) error {
    88  
    89  	log.SetFormatter(&log.TextFormatter{ForceColors: true})
    90  
    91  	t, err := ReadConfig(c.File)
    92  	if err != nil {
    93  		err = fmt.Errorf("Can't read config file: %s", err)
    94  		return err
    95  	}
    96  
    97  	root, err := rootDir()
    98  	if err != nil {
    99  		return err
   100  	}
   101  
   102  	pkgs, err := WalkImports(root)
   103  	if err != nil {
   104  		return err
   105  	}
   106  	lics := GetLicenses(root, pkgs)
   107  
   108  	// Make a map out of the blacklist
   109  	blacklist := make(map[string]bool)
   110  	for _, v := range t.Blacklist {
   111  		blacklist[v] = true
   112  	}
   113  
   114  	// Make a map out of the whitelist
   115  	whitelist := make(map[string]bool)
   116  	for _, v := range t.Whitelist {
   117  		whitelist[v] = true
   118  	}
   119  
   120  	// Make a map out of the exceptions list
   121  	exceptions := make(map[string]bool)
   122  	exceptionsWildcard := make(map[string]bool)
   123  	for _, v := range t.Exceptions {
   124  		if strings.HasSuffix(v, "/...") {
   125  			exceptionsWildcard[strings.TrimRight(v, "/...")] = true
   126  		} else {
   127  			exceptions[v] = true
   128  		}
   129  	}
   130  
   131  PackageList:
   132  	for pkg, lic := range lics {
   133  		contextLogger := log.WithFields(log.Fields{
   134  			"package": pkg,
   135  			"license": lic.Type,
   136  		})
   137  
   138  		// License is whitelisted and not specified in blacklist
   139  		if whitelist[lic.Type] && !blacklist[lic.Type] {
   140  			contextLogger.Info("Found Approved license")
   141  			continue PackageList
   142  		}
   143  
   144  		// if we have exceptions wildcards, let's run through them
   145  		if len(exceptionsWildcard) > 0 {
   146  			for wc, _ := range exceptionsWildcard {
   147  				if strings.HasPrefix(pkg, wc) {
   148  					// we have a match
   149  					contextLogger.Warn("Found exceptioned package")
   150  					continue PackageList
   151  				}
   152  			}
   153  		}
   154  
   155  		// match single-package exceptions
   156  		if _, exists := exceptions[pkg]; exists {
   157  			contextLogger.Warn("Found exceptioned package")
   158  			continue PackageList
   159  		}
   160  
   161  		// no matches, it's a non-approved license
   162  		contextLogger.Error("Found Non-Approved license")
   163  		err = fmt.Errorf("Non-Approved license found")
   164  
   165  	}
   166  
   167  	return err
   168  }
   169  
   170  func rootDir() (string, error) {
   171  	root, err := os.Getwd()
   172  	if err != nil {
   173  		return "", err
   174  	}
   175  
   176  	info, err := os.Lstat(root)
   177  	if err != nil {
   178  		return "", err
   179  	}
   180  	if info.Mode()&os.ModeSymlink != 0 {
   181  		root, err = os.Readlink(root)
   182  		if err != nil {
   183  			return "", err
   184  		}
   185  	}
   186  	return root, nil
   187  }