github.com/juju/charm/v11@v11.2.0/base_test.go (about)

     1  // Copyright 2020 Canonical Ltd.
     2  // Licensed under the LGPLv3, see LICENCE file for details.
     3  
     4  package charm_test
     5  
     6  import (
     7  	"encoding/json"
     8  	"strings"
     9  
    10  	"github.com/juju/os/v2"
    11  	"github.com/juju/testing"
    12  	jc "github.com/juju/testing/checkers"
    13  	"github.com/juju/utils/v3/arch"
    14  	gc "gopkg.in/check.v1"
    15  
    16  	"github.com/juju/charm/v11"
    17  )
    18  
    19  type baseSuite struct {
    20  	testing.CleanupSuite
    21  }
    22  
    23  var _ = gc.Suite(&baseSuite{})
    24  
    25  func (s *baseSuite) TestParseBase(c *gc.C) {
    26  	tests := []struct {
    27  		str        string
    28  		parsedBase charm.Base
    29  		err        string
    30  	}{
    31  		{
    32  			str:        "ubuntu",
    33  			parsedBase: charm.Base{},
    34  			err:        `base string must contain exactly one @. "ubuntu" not valid`,
    35  		}, {
    36  			str:        "windows",
    37  			parsedBase: charm.Base{},
    38  			err:        `base string must contain exactly one @. "windows" not valid`,
    39  		}, {
    40  			str:        "mythicalos@channel",
    41  			parsedBase: charm.Base{},
    42  			err:        `invalid base string "mythicalos@channel": os "mythicalos" not valid`,
    43  		}, {
    44  			str:        "ubuntu@20.04/stable",
    45  			parsedBase: charm.Base{Name: strings.ToLower(os.Ubuntu.String()), Channel: mustParseChannel("20.04/stable")},
    46  		}, {
    47  			str:        "windows@win10/stable",
    48  			parsedBase: charm.Base{Name: strings.ToLower(os.Windows.String()), Channel: mustParseChannel("win10/stable")},
    49  		}, {
    50  			str:        "ubuntu@20.04/edge",
    51  			parsedBase: charm.Base{Name: strings.ToLower(os.Ubuntu.String()), Channel: mustParseChannel("20.04/edge")},
    52  		},
    53  	}
    54  	for i, v := range tests {
    55  		comment := gc.Commentf("test %d", i)
    56  		s, err := charm.ParseBase(v.str)
    57  		if v.err != "" {
    58  			c.Check(err, gc.ErrorMatches, v.err, comment)
    59  		} else {
    60  			c.Check(err, jc.ErrorIsNil, comment)
    61  		}
    62  		c.Check(s, jc.DeepEquals, v.parsedBase, comment)
    63  	}
    64  }
    65  
    66  func (s *baseSuite) TestParseBaseWithArchitectures(c *gc.C) {
    67  	tests := []struct {
    68  		str        string
    69  		baseString string
    70  		archs      []string
    71  		parsedBase charm.Base
    72  		err        string
    73  	}{
    74  		{
    75  			baseString: "ubuntu@",
    76  			str:        "ubuntu on amd64",
    77  			archs:      []string{"amd64"},
    78  			parsedBase: charm.Base{},
    79  			err:        `invalid base string "ubuntu@" with architectures "amd64": channel not valid`,
    80  		}, {
    81  			baseString: "windows@",
    82  			str:        "windows",
    83  			parsedBase: charm.Base{},
    84  			err:        `invalid base string "windows@": channel not valid`,
    85  		}, {
    86  			baseString: "mythicalos@channel",
    87  			str:        "mythicalos",
    88  			parsedBase: charm.Base{},
    89  			err:        `invalid base string "mythicalos@channel": os "mythicalos" not valid`,
    90  		}, {
    91  			baseString: "ubuntu@20.04/stable",
    92  			archs:      []string{arch.AMD64, "ppc64"},
    93  			str:        "ubuntu@20.04/stable on amd64, ppc64el",
    94  			parsedBase: charm.Base{
    95  				Name:          strings.ToLower(os.Ubuntu.String()),
    96  				Channel:       mustParseChannel("20.04/stable"),
    97  				Architectures: []string{arch.AMD64, arch.PPC64EL}},
    98  		}, {
    99  			baseString: "windows@win10/stable",
   100  			archs:      []string{"testme"},
   101  			str:        "windows@win10/stable",
   102  			parsedBase: charm.Base{},
   103  			err:        `invalid base string "windows@win10/stable" with architectures "testme": architecture "testme" not valid`,
   104  		},
   105  	}
   106  	for i, v := range tests {
   107  		comment := gc.Commentf("test %d", i)
   108  		s, err := charm.ParseBase(v.baseString, v.archs...)
   109  		if v.err != "" {
   110  			c.Check(err, gc.ErrorMatches, v.err, comment)
   111  		} else {
   112  			c.Check(err, jc.ErrorIsNil, comment)
   113  		}
   114  		c.Check(s, jc.DeepEquals, v.parsedBase, comment)
   115  	}
   116  }
   117  
   118  func (s *baseSuite) TestStringifyBase(c *gc.C) {
   119  	tests := []struct {
   120  		base charm.Base
   121  		str  string
   122  	}{
   123  		{
   124  			base: charm.Base{Name: strings.ToLower(os.Ubuntu.String()), Channel: mustParseChannel("20.04/stable")},
   125  			str:  "ubuntu@20.04/stable",
   126  		}, {
   127  			base: charm.Base{Name: strings.ToLower(os.Windows.String()), Channel: mustParseChannel("win10/stable")},
   128  			str:  "windows@win10/stable",
   129  		}, {
   130  			base: charm.Base{Name: strings.ToLower(os.Ubuntu.String()), Channel: mustParseChannel("20.04/edge")},
   131  			str:  "ubuntu@20.04/edge",
   132  		}, {
   133  			base: charm.Base{
   134  				Name:          strings.ToLower(os.Ubuntu.String()),
   135  				Channel:       mustParseChannel("20.04/stable"),
   136  				Architectures: []string{arch.AMD64},
   137  			},
   138  			str: "ubuntu@20.04/stable on amd64",
   139  		}, {
   140  			base: charm.Base{
   141  				Name:          strings.ToLower(os.Ubuntu.String()),
   142  				Channel:       mustParseChannel("20.04/stable"),
   143  				Architectures: []string{arch.AMD64, arch.PPC64EL},
   144  			},
   145  			str: "ubuntu@20.04/stable on amd64, ppc64el",
   146  		},
   147  	}
   148  	for i, v := range tests {
   149  		comment := gc.Commentf("test %d", i)
   150  		c.Assert(v.base.Validate(), jc.ErrorIsNil)
   151  		c.Assert(v.base.String(), gc.Equals, v.str, comment)
   152  	}
   153  }
   154  
   155  func (s *baseSuite) TestJSONEncoding(c *gc.C) {
   156  	sys := charm.Base{
   157  		Name:    "ubuntu",
   158  		Channel: mustParseChannel("20.04/stable"),
   159  	}
   160  	bytes, err := json.Marshal(sys)
   161  	c.Assert(err, jc.ErrorIsNil)
   162  	c.Assert(string(bytes), gc.Equals, `{"name":"ubuntu","channel":{"track":"20.04","risk":"stable"}}`)
   163  	sys2 := charm.Base{}
   164  	err = json.Unmarshal(bytes, &sys2)
   165  	c.Assert(err, jc.ErrorIsNil)
   166  	c.Assert(sys2, jc.DeepEquals, sys)
   167  }
   168  
   169  // MustParseChannel parses a given string or returns a panic.
   170  // Used for unit tests.
   171  func mustParseChannel(s string) charm.Channel {
   172  	c, err := charm.ParseChannelNormalize(s)
   173  	if err != nil {
   174  		panic(err)
   175  	}
   176  	return c
   177  }