Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow one pseudo-JS module to access the ModuleInstance of another module #2293

Open
na-- opened this issue Dec 13, 2021 · 1 comment
Open
Labels
evaluation needed proposal needs to be validated or tested before fully implementing it in k6 refactor

Comments

@na--
Copy link
Member

na-- commented Dec 13, 2021

(Extracted from #2226, and somewhat connected to #2258 and #1802)

It would be quite nice if one pseudo-JS module is able to access the modules.Instance of another module. For example, if k6/ws is able to access the module instance of k6/http, though ideally any module (regardless of built-in or extension) should be able to access any other module.

This will allow us to move a lot of the (mostly) HTTP-specific cruft from lib.State to a much more appropriate place:

k6/lib/state.go

Lines 56 to 63 in 922c963

// Networking equipment.
Transport http.RoundTripper
Dialer DialContexter
CookieJar *cookiejar.Jar
TLSConfig *tls.Config
// Rate limits.
RPSLimit *rate.Limiter

But still allow other parts of the codebase (like k6/ws and k6/grpc) to access the default HTTP transport or cookie jar, when they need to.

@na-- na-- added refactor evaluation needed proposal needs to be validated or tested before fully implementing it in k6 labels Dec 13, 2021
@na--
Copy link
Member Author

na-- commented Dec 13, 2021

As a bonus, the lengthy initialization of HTTP-specific things that currently happens during VU init:

k6/js/runner.go

Lines 157 to 224 in 922c963

var cipherSuites []uint16
if r.Bundle.Options.TLSCipherSuites != nil {
cipherSuites = *r.Bundle.Options.TLSCipherSuites
}
var tlsVersions lib.TLSVersions
if r.Bundle.Options.TLSVersion != nil {
tlsVersions = *r.Bundle.Options.TLSVersion
}
tlsAuth := r.Bundle.Options.TLSAuth
certs := make([]tls.Certificate, len(tlsAuth))
nameToCert := make(map[string]*tls.Certificate)
for i, auth := range tlsAuth {
for _, name := range auth.Domains {
cert, err := auth.Certificate()
if err != nil {
return nil, err
}
certs[i] = *cert
nameToCert[name] = &certs[i]
}
}
dialer := &netext.Dialer{
Dialer: r.BaseDialer,
Resolver: r.Resolver,
Blacklist: r.Bundle.Options.BlacklistIPs,
BlockedHostnames: r.Bundle.Options.BlockedHostnames.Trie,
Hosts: r.Bundle.Options.Hosts,
}
if r.Bundle.Options.LocalIPs.Valid {
var ipIndex uint64
if idLocal > 0 {
ipIndex = idLocal - 1
}
dialer.Dialer.LocalAddr = &net.TCPAddr{IP: r.Bundle.Options.LocalIPs.Pool.GetIP(ipIndex)}
}
tlsConfig := &tls.Config{
InsecureSkipVerify: r.Bundle.Options.InsecureSkipTLSVerify.Bool, //nolint:gosec
CipherSuites: cipherSuites,
MinVersion: uint16(tlsVersions.Min),
MaxVersion: uint16(tlsVersions.Max),
Certificates: certs,
NameToCertificate: nameToCert,
Renegotiation: tls.RenegotiateFreelyAsClient,
}
transport := &http.Transport{
Proxy: http.ProxyFromEnvironment,
TLSClientConfig: tlsConfig,
DialContext: dialer.DialContext,
DisableCompression: true,
DisableKeepAlives: r.Bundle.Options.NoConnectionReuse.Bool,
MaxIdleConns: int(r.Bundle.Options.Batch.Int64),
MaxIdleConnsPerHost: int(r.Bundle.Options.BatchPerHost.Int64),
}
if forceHTTP1() {
transport.TLSNextProto = make(map[string]func(string, *tls.Conn) http.RoundTripper) // send over h1 protocol
} else {
_ = http2.ConfigureTransport(transport) // send over h2 protocol
}
cookieJar, err := cookiejar.New(nil)
if err != nil {
return nil, err
}

Would be moved to a much more appropriate place in the k6/http module, e.g. here:

mi.defaultClient = &Client{
// TODO: configure this from lib.Options and get rid of some of the
// things in the VU State struct that should be here. See
// https://github.com/grafana/k6/issues/2293

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
evaluation needed proposal needs to be validated or tested before fully implementing it in k6 refactor
Projects
None yet
Development

No branches or pull requests

1 participant