github.com/juju/juju@v0.0.0-20240430160146-1752b71fcf00/api/export_test.go (about) 1 // Copyright 2012, 2013, 2022 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package api 5 6 import ( 7 "context" 8 "net/url" 9 10 "github.com/go-macaroon-bakery/macaroon-bakery/v3/httpbakery" 11 "github.com/juju/clock" 12 "github.com/juju/errors" 13 "github.com/juju/names/v5" 14 "gopkg.in/macaroon.v2" 15 16 "github.com/juju/juju/core/network" 17 jujuproxy "github.com/juju/juju/proxy" 18 "github.com/juju/juju/rpc/jsoncodec" 19 ) 20 21 var ( 22 CertDir = &certDir 23 SlideAddressToFront = slideAddressToFront 24 FacadeVersions = &facadeVersions 25 26 LoginDeviceAPICall = &loginDeviceAPICall 27 GetDeviceSessionTokenAPICall = &getDeviceSessionTokenAPICall 28 LoginWithSessionTokenAPICall = &loginWithSessionTokenAPICall 29 LoginWithClientCredentialsAPICall = &loginWithClientCredentialsAPICall 30 ) 31 32 func DialAPI(info *Info, opts DialOpts) (jsoncodec.JSONConn, string, error) { 33 result, err := dialAPI(context.TODO(), info, opts) 34 if err != nil { 35 return nil, "", err 36 } 37 // Replace the IP address in the URL with the 38 // host name so that tests can check it more 39 // easily. 40 u, _ := url.Parse(result.urlStr) 41 u.Host = result.addr 42 return result.conn, u.String(), nil 43 } 44 45 // CookieURL returns the cookie URL of the connection. 46 func CookieURL(c Connection) *url.URL { 47 return c.(*state).cookieURL 48 } 49 50 // ServerRoot is exported so that we can test the built URL. 51 func ServerRoot(c Connection) string { 52 return c.(*state).serverRoot() 53 } 54 55 // UnderlyingConn returns the underlying transport connection. 56 func UnderlyingConn(c Connection) jsoncodec.JSONConn { 57 return c.(*state).conn 58 } 59 60 // RPCConnection defines the methods that are called on the rpc.Conn instance. 61 type RPCConnection rpcConnection 62 63 // TestingStateParams is the parameters for NewTestingState, so that you can 64 // only set the bits that you actually want to test. 65 type TestingStateParams struct { 66 Address string 67 ModelTag string 68 APIHostPorts []network.MachineHostPorts 69 FacadeVersions map[string][]int 70 ServerScheme string 71 ServerRoot string 72 RPCConnection RPCConnection 73 Clock clock.Clock 74 Broken, Closed chan struct{} 75 Proxier jujuproxy.Proxier 76 } 77 78 // NewTestingState creates an api.State object that can be used for testing. It 79 // isn't backed onto an actual API server, so actual RPC methods can't be 80 // called on it. But it can be used for testing general behaviour. 81 func NewTestingState(params TestingStateParams) Connection { 82 var modelTag names.ModelTag 83 if params.ModelTag != "" { 84 t, err := names.ParseModelTag(params.ModelTag) 85 if err != nil { 86 panic("invalid model tag") 87 } 88 modelTag = t 89 } 90 st := &state{ 91 client: params.RPCConnection, 92 clock: params.Clock, 93 addr: params.Address, 94 modelTag: modelTag, 95 hostPorts: params.APIHostPorts, 96 facadeVersions: params.FacadeVersions, 97 serverScheme: params.ServerScheme, 98 serverRootAddress: params.ServerRoot, 99 broken: params.Broken, 100 closed: params.Closed, 101 proxier: params.Proxier, 102 } 103 return st 104 } 105 106 func ExtractMacaroons(conn Connection) ([]macaroon.Slice, error) { 107 st, ok := conn.(*state) 108 if !ok { 109 return nil, errors.Errorf("conn must be a real connection") 110 } 111 return httpbakery.MacaroonsForURL(st.bakeryClient.Client.Jar, st.cookieURL), nil 112 }