2020-12-09 15:31:34 +00:00
package cmd
import (
"fmt"
"os"
"strings"
"testing"
"github.com/cloudskiff/driftctl/pkg/config"
"github.com/cloudskiff/driftctl/test"
"github.com/cloudskiff/driftctl/test/mocks"
"github.com/spf13/cobra"
"github.com/stretchr/testify/assert"
)
func TestDriftctlCmd_Help ( t * testing . T ) {
cmd := NewDriftctlCmd ( mocks . MockBuild { } )
cases := [ ] struct {
args [ ] string
} {
{ args : [ ] string { } } ,
{ args : [ ] string { "help" } } ,
{ args : [ ] string { "--help" } } ,
{ args : [ ] string { "-h" } } ,
}
for _ , tt := range cases {
output , err := test . Execute ( & cmd . Command , tt . args ... )
if output == "" {
t . Errorf ( "Unexpected output: %v" , output )
}
if err != nil {
t . Errorf ( "Unexpected error: %v" , err )
}
expected := cmd . UsageString ( )
if ! strings . Contains ( output , expected ) {
t . Errorf ( "Expected to contain: \n %v\nGot:\n %v" , expected , output )
}
}
}
func TestDriftctlCmd_Version ( t * testing . T ) {
cmd := NewDriftctlCmd ( mocks . MockBuild { } )
output , err := test . Execute ( & cmd . Command , "version" )
if output == "" {
t . Errorf ( "Unexpected output: %v" , output )
}
if err != nil {
t . Errorf ( "Unexpected error: %v" , err )
}
expected := "dev-dev\n"
if output != expected {
t . Errorf ( "Expected %v, got %v" , expected , output )
}
}
2021-01-20 13:04:33 +00:00
func TestDriftctlCmd_Completion ( t * testing . T ) {
cmd := NewDriftctlCmd ( mocks . MockBuild { } )
output , err := test . Execute ( & cmd . Command , "completion" , "bash" )
if output == "" {
t . Errorf ( "Unexpected output: %v" , output )
}
if err != nil {
t . Errorf ( "Unexpected error: %v" , err )
}
expected := "# bash completion for driftctl"
if ! strings . Contains ( output , expected ) {
t . Errorf ( "Expected to contain: \n %v\nGot:\n %v" , expected , output )
}
}
2020-12-09 15:31:34 +00:00
func TestDriftctlCmd_Scan ( t * testing . T ) {
cases := [ ] struct {
env map [ string ] string
args [ ] string
err error
} {
{ } ,
{
env : map [ string ] string {
"DCTL_TO" : "test" ,
} ,
2021-02-15 13:24:20 +00:00
err : fmt . Errorf ( "unsupported cloud provider 'test'\nValid values are: aws+tf,github+tf" ) ,
2020-12-09 15:31:34 +00:00
} ,
{
env : map [ string ] string {
"DCTL_TO" : "test" ,
} ,
args : [ ] string { "--to" , "aws+tf" } ,
} ,
{
env : map [ string ] string {
"DCTL_FROM" : "test" ,
} ,
2021-04-24 21:31:57 +00:00
err : fmt . Errorf ( "Unable to parse from flag 'test': \nAccepted schemes are: tfstate://,tfstate+s3://,tfstate+http://,tfstate+https://,tfstate+tfcloud://" ) ,
2020-12-09 15:31:34 +00:00
} ,
{
env : map [ string ] string {
"DCTL_FROM" : "test" ,
} ,
args : [ ] string { "--from" , "tfstate://terraform.tfstate" } ,
} ,
{
env : map [ string ] string {
"DCTL_OUTPUT" : "test" ,
} ,
2021-06-09 14:06:21 +00:00
err : fmt . Errorf ( "Unable to parse output flag 'test': \nAccepted formats are: console://,html://PATH/TO/FILE.html,json://PATH/TO/FILE.json,plan://PATH/TO/FILE.json" ) ,
2020-12-09 15:31:34 +00:00
} ,
{
env : map [ string ] string {
"DCTL_OUTPUT" : "test" ,
} ,
args : [ ] string { "--output" , "console://" } ,
} ,
{
env : map [ string ] string {
"DCTL_FILTER" : "Type='test'" ,
} ,
err : fmt . Errorf ( "unable to parse filter expression: SyntaxError: Expected tRbracket, received: tUnknown" ) ,
} ,
{
env : map [ string ] string {
"DCTL_FILTER" : "Type='test'" ,
} ,
args : [ ] string { "--filter" , "Type=='test'" } ,
} ,
}
config . Init ( )
for index , c := range cases {
t . Run ( fmt . Sprintf ( "%d" , index ) , func ( t * testing . T ) {
if c . env != nil && len ( c . env ) > 0 {
for key , val := range c . env {
_ = os . Setenv ( key , val )
defer os . Unsetenv ( key )
}
}
cmd := NewDriftctlCmd ( mocks . MockBuild { } )
scanCmd , _ , _ := cmd . Find ( [ ] string { "scan" } )
scanCmd . RunE = func ( _ * cobra . Command , args [ ] string ) error { return nil }
args := append ( [ ] string { "scan" } , c . args ... )
_ , err := test . Execute ( & cmd . Command , args ... )
if c . err == nil && err != nil || c . err != nil && err == nil {
t . Fatalf ( "Got error '%s', expected '%s'" , err , c . err )
}
if c . err != nil && err != nil && err . Error ( ) != c . err . Error ( ) {
t . Fatalf ( "Got error '%s', expected '%s'" , err . Error ( ) , c . err . Error ( ) )
}
} )
}
}
func TestDriftctlCmd_Invalid ( t * testing . T ) {
cmd := NewDriftctlCmd ( mocks . MockBuild { } )
cases := [ ] struct {
args [ ] string
expected string
} {
{ args : [ ] string { "test" } , expected : ` unknown command "test" for "driftctl" ` } ,
{ args : [ ] string { "-t" } , expected : ` unknown shorthand flag: 't' in -t ` } ,
{ args : [ ] string { "--test" } , expected : ` unknown flag: --test ` } ,
}
for _ , tt := range cases {
_ , err := test . Execute ( & cmd . Command , tt . args ... )
if err == nil {
t . Errorf ( "Invalid arg should generate error" )
}
if err . Error ( ) != tt . expected {
t . Errorf ( "Expected %v, got %v" , tt . expected , err )
}
}
}
func TestDriftctlCmd_ShouldCheckVersion ( t * testing . T ) {
cases := [ ] struct {
Name string
IsRelease bool
args [ ] string
2020-12-17 10:10:33 +00:00
env map [ string ] string
2020-12-09 15:31:34 +00:00
expected bool
} {
{
Name : "When we are in release mode and no args, should check for update" ,
IsRelease : true ,
args : [ ] string { "" } ,
expected : true ,
} ,
{
Name : "Don't check for update for version cmd" ,
IsRelease : true ,
args : [ ] string { "version" } ,
expected : false ,
} ,
{
Name : "Don't check for update for help cmd" ,
IsRelease : true ,
args : [ ] string { "help" } ,
expected : false ,
} ,
{
Name : "Don't check for update for cmd --help" ,
IsRelease : true ,
args : [ ] string { "scan" , "--help" } ,
expected : false ,
} ,
{
Name : "Don't check for update for cmd -h" ,
IsRelease : true ,
args : [ ] string { "scan" , "-h" } ,
expected : false ,
} ,
{
Name : "Don't check for update when no check flag present" ,
IsRelease : true ,
args : [ ] string { "--no-version-check" } ,
expected : false ,
} ,
{
Name : "Don't check for update in dev mode" ,
IsRelease : false ,
args : [ ] string { "" } ,
expected : false ,
} ,
2020-12-17 10:10:33 +00:00
{
2021-01-29 09:15:31 +00:00
Name : "Don't check for update when env DCTL_NO_VERSION_CHECK set" ,
2020-12-17 10:10:33 +00:00
IsRelease : true ,
env : map [ string ] string {
2021-01-29 09:15:31 +00:00
"DCTL_NO_VERSION_CHECK" : "foo" ,
2020-12-17 10:10:33 +00:00
} ,
expected : false ,
} ,
2020-12-09 15:31:34 +00:00
{
Name : "Should not return error when launching sub command" ,
IsRelease : false ,
args : [ ] string { "scan" , "--from" , "tfstate://terraform.tfstate" } ,
expected : false ,
} ,
2021-01-20 13:04:33 +00:00
{
Name : "Don't check for update for completion cmd" ,
IsRelease : true ,
args : [ ] string { "completion" , "bash" } ,
expected : false ,
} ,
2020-12-09 15:31:34 +00:00
}
for _ , c := range cases {
t . Run ( c . Name , func ( tt * testing . T ) {
assert := assert . New ( tt )
2020-12-17 10:10:33 +00:00
os . Clearenv ( )
for key , val := range c . env {
os . Setenv ( key , val )
}
2020-12-09 15:31:34 +00:00
cmd := NewDriftctlCmd ( mocks . MockBuild { Release : c . IsRelease } )
os . Args = append ( [ ] string { "driftctl" } , c . args ... )
result := cmd . ShouldCheckVersion ( )
2020-12-17 10:10:33 +00:00
assert . Equal ( c . expected , result )
2020-12-09 15:31:34 +00:00
} )
}
}
func TestContainCmd ( t * testing . T ) {
cases := [ ] struct {
args [ ] string
cmd string
expected bool
} {
{ args : [ ] string { } , cmd : "" , expected : false } ,
{ args : [ ] string { "scan" } , cmd : "version" , expected : false } ,
{ args : [ ] string { "version" } , cmd : "version" , expected : true } ,
}
for _ , tt := range cases {
if got := contains ( tt . args , tt . cmd ) ; got != tt . expected {
t . Errorf ( "Expected %v, got %v" , tt . expected , got )
}
}
}