github.com/juju/juju@v0.0.0-20240327075706-a90865de2538/core/charm/computedbase_test.go (about)

     1  // Copyright 2023 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package charm
     5  
     6  import (
     7  	"github.com/juju/charm/v12"
     8  	"github.com/juju/errors"
     9  	"github.com/juju/testing"
    10  	jc "github.com/juju/testing/checkers"
    11  	"go.uber.org/mock/gomock"
    12  	gc "gopkg.in/check.v1"
    13  
    14  	"github.com/juju/juju/core/base"
    15  )
    16  
    17  type computedBaseSuite struct {
    18  	testing.CleanupSuite
    19  }
    20  
    21  var _ = gc.Suite(&computedBaseSuite{})
    22  
    23  func (s *computedBaseSuite) TestComputedBase(c *gc.C) {
    24  	ctrl := gomock.NewController(c)
    25  	defer ctrl.Finish()
    26  	cm := NewMockCharmMeta(ctrl)
    27  	cm.EXPECT().Manifest().Return(&charm.Manifest{
    28  		Bases: []charm.Base{{
    29  			Name: "ubuntu",
    30  			Channel: charm.Channel{
    31  				Track: "18.04",
    32  				Risk:  "stable",
    33  			},
    34  		}, {
    35  			Name: "ubuntu",
    36  			Channel: charm.Channel{
    37  				Track: "20.04",
    38  				Risk:  "stable",
    39  			},
    40  		}},
    41  	}).AnyTimes()
    42  	bases, err := ComputedBases(cm)
    43  	c.Assert(err, jc.ErrorIsNil)
    44  	c.Assert(bases, jc.DeepEquals, []base.Base{
    45  		base.MustParseBaseFromString("ubuntu@18.04"),
    46  		base.MustParseBaseFromString("ubuntu@20.04"),
    47  	})
    48  }
    49  
    50  func (s *computedBaseSuite) TestComputedBaseNilManifest(c *gc.C) {
    51  	ctrl := gomock.NewController(c)
    52  	defer ctrl.Finish()
    53  	cm := NewMockCharmMeta(ctrl)
    54  	cm.EXPECT().Meta().Return(&charm.Meta{
    55  		Name:        "a",
    56  		Summary:     "b",
    57  		Description: "c",
    58  		Series:      []string{"bionic"},
    59  	}).AnyTimes()
    60  	cm.EXPECT().Manifest().Return(nil).AnyTimes()
    61  	bases, err := ComputedBases(cm)
    62  	c.Assert(err, jc.ErrorIsNil)
    63  	c.Assert(bases, jc.DeepEquals, []base.Base{
    64  		base.MustParseBaseFromString("ubuntu@18.04"),
    65  	})
    66  }
    67  
    68  func (s *computedBaseSuite) TestComputedBaseNilManifestKubernetes(c *gc.C) {
    69  	ctrl := gomock.NewController(c)
    70  	defer ctrl.Finish()
    71  	cm := NewMockCharmMeta(ctrl)
    72  	cm.EXPECT().Meta().Return(&charm.Meta{
    73  		Name:        "a",
    74  		Summary:     "b",
    75  		Description: "c",
    76  		Series:      []string{"kubernetes"},
    77  	}).AnyTimes()
    78  	cm.EXPECT().Manifest().Return(nil).AnyTimes()
    79  	bases, err := ComputedBases(cm)
    80  	c.Assert(err, jc.ErrorIsNil)
    81  	c.Assert(bases, jc.DeepEquals, []base.Base{
    82  		base.LegacyKubernetesBase(),
    83  	})
    84  }
    85  
    86  func (s *computedBaseSuite) TestComputedBaseError(c *gc.C) {
    87  	ctrl := gomock.NewController(c)
    88  	defer ctrl.Finish()
    89  	cm := NewMockCharmMeta(ctrl)
    90  	cm.EXPECT().Manifest().Return(&charm.Manifest{
    91  		Bases: []charm.Base{{
    92  			Name: "ubuntu",
    93  			Channel: charm.Channel{
    94  				Track: "18.04",
    95  				Risk:  "stable",
    96  			},
    97  		}, {
    98  			Name: "ubuntu",
    99  		}},
   100  	}).AnyTimes()
   101  	cm.EXPECT().Meta().Return(&charm.Meta{
   102  		Name:        "a",
   103  		Summary:     "b",
   104  		Description: "c",
   105  	}).AnyTimes()
   106  	_, err := ComputedBases(cm)
   107  	c.Assert(errors.IsNotValid(err), jc.IsTrue)
   108  }
   109  
   110  func (s *computedBaseSuite) TestBaseToUse(c *gc.C) {
   111  	trusty := base.MustParseBaseFromString("ubuntu@16.04")
   112  	jammy := base.MustParseBaseFromString("ubuntu@22.04")
   113  	focal := base.MustParseBaseFromString("ubuntu@20.04")
   114  	tests := []struct {
   115  		series         base.Base
   116  		supportedBases []base.Base
   117  		baseToUse      base.Base
   118  		err            string
   119  	}{{
   120  		series: base.Base{},
   121  		err:    "charm does not define any bases",
   122  	}, {
   123  		series:    trusty,
   124  		baseToUse: trusty,
   125  	}, {
   126  		series:         trusty,
   127  		supportedBases: []base.Base{focal, trusty},
   128  		baseToUse:      trusty,
   129  	}, {
   130  		series:         base.LatestLTSBase(),
   131  		supportedBases: []base.Base{focal, base.LatestLTSBase(), trusty},
   132  		baseToUse:      base.LatestLTSBase(),
   133  	}, {
   134  		series:         trusty,
   135  		supportedBases: []base.Base{jammy, focal},
   136  		err:            `base "ubuntu@16.04" not supported by charm.*`,
   137  	}}
   138  	for _, test := range tests {
   139  		base, err := BaseForCharm(test.series, test.supportedBases)
   140  		if test.err != "" {
   141  			c.Check(err, gc.ErrorMatches, test.err)
   142  			continue
   143  		}
   144  		c.Check(err, jc.ErrorIsNil)
   145  		c.Check(base.IsCompatible(test.baseToUse), jc.IsTrue)
   146  	}
   147  }
   148  
   149  func (s *computedBaseSuite) TestBaseIsCompatibleWithCharm(c *gc.C) {
   150  	ctrl := gomock.NewController(c)
   151  	defer ctrl.Finish()
   152  	cm := NewMockCharmMeta(ctrl)
   153  	cm.EXPECT().Manifest().Return(&charm.Manifest{
   154  		Bases: []charm.Base{{
   155  			Name: "ubuntu",
   156  			Channel: charm.Channel{
   157  				Track: "18.04",
   158  				Risk:  "stable",
   159  			},
   160  		}, {
   161  			Name: "ubuntu",
   162  			Channel: charm.Channel{
   163  				Track: "20.04",
   164  				Risk:  "stable",
   165  			},
   166  		}},
   167  	}).AnyTimes()
   168  	cm.EXPECT().Meta().Return(&charm.Meta{
   169  		Name: "my-charm",
   170  	}).AnyTimes()
   171  
   172  	focal := base.MustParseBaseFromString("ubuntu@20.04")
   173  	jammy := base.MustParseBaseFromString("ubuntu@22.04")
   174  
   175  	c.Assert(BaseIsCompatibleWithCharm(focal, cm), jc.ErrorIsNil)
   176  	c.Assert(BaseIsCompatibleWithCharm(jammy, cm), jc.Satisfies, IsUnsupportedBaseError)
   177  }
   178  
   179  func (s *computedBaseSuite) TestOSIsCompatibleWithCharm(c *gc.C) {
   180  	ctrl := gomock.NewController(c)
   181  	defer ctrl.Finish()
   182  	cm := NewMockCharmMeta(ctrl)
   183  	cm.EXPECT().Manifest().Return(&charm.Manifest{
   184  		Bases: []charm.Base{{
   185  			Name: "ubuntu",
   186  			Channel: charm.Channel{
   187  				Track: "18.04",
   188  				Risk:  "stable",
   189  			},
   190  		}, {
   191  			Name: "ubuntu",
   192  			Channel: charm.Channel{
   193  				Track: "20.04",
   194  				Risk:  "stable",
   195  			},
   196  		}},
   197  	}).AnyTimes()
   198  	cm.EXPECT().Meta().Return(&charm.Meta{
   199  		Name: "my-charm",
   200  	}).AnyTimes()
   201  
   202  	c.Assert(OSIsCompatibleWithCharm("ubuntu", cm), jc.ErrorIsNil)
   203  	c.Assert(OSIsCompatibleWithCharm("centos", cm), jc.ErrorIs, errors.NotSupported)
   204  }