feat(ansible): support uri basic auth flags
Co-Authored-By: Virgil <virgil@lethean.io>
This commit is contained in:
parent
2927fb4c78
commit
541d16b5a6
3 changed files with 44 additions and 0 deletions
|
|
@ -1813,6 +1813,9 @@ func moduleURIWithClient(_ *Executor, client sshRunner, args map[string]any) (*T
|
||||||
dest := getStringArg(args, "dest", "")
|
dest := getStringArg(args, "dest", "")
|
||||||
timeout := getIntArg(args, "timeout", 0)
|
timeout := getIntArg(args, "timeout", 0)
|
||||||
validateCerts := getBoolArg(args, "validate_certs", true)
|
validateCerts := getBoolArg(args, "validate_certs", true)
|
||||||
|
urlUsername := getStringArg(args, "url_username", "")
|
||||||
|
urlPassword := getStringArg(args, "url_password", "")
|
||||||
|
forceBasicAuth := getBoolArg(args, "force_basic_auth", false)
|
||||||
|
|
||||||
if url == "" {
|
if url == "" {
|
||||||
return nil, mockError("moduleURIWithClient", "uri: url required")
|
return nil, mockError("moduleURIWithClient", "uri: url required")
|
||||||
|
|
@ -1822,6 +1825,15 @@ func moduleURIWithClient(_ *Executor, client sshRunner, args map[string]any) (*T
|
||||||
curlOpts = append(curlOpts, "-s", "-S")
|
curlOpts = append(curlOpts, "-s", "-S")
|
||||||
curlOpts = append(curlOpts, "-X", method)
|
curlOpts = append(curlOpts, "-X", method)
|
||||||
|
|
||||||
|
if urlUsername != "" || urlPassword != "" {
|
||||||
|
curlOpts = append(curlOpts, "-u", shellQuote(urlUsername+":"+urlPassword))
|
||||||
|
if forceBasicAuth {
|
||||||
|
curlOpts = append(curlOpts, "--basic")
|
||||||
|
}
|
||||||
|
} else if forceBasicAuth {
|
||||||
|
curlOpts = append(curlOpts, "--basic")
|
||||||
|
}
|
||||||
|
|
||||||
// Headers
|
// Headers
|
||||||
if headers, ok := args["headers"].(map[string]any); ok {
|
if headers, ok := args["headers"].(map[string]any); ok {
|
||||||
for k, v := range headers {
|
for k, v := range headers {
|
||||||
|
|
|
||||||
14
modules.go
14
modules.go
|
|
@ -1587,6 +1587,9 @@ func (e *Executor) moduleURI(ctx context.Context, client sshExecutorClient, args
|
||||||
dest := getStringArg(args, "dest", "")
|
dest := getStringArg(args, "dest", "")
|
||||||
timeout := getIntArg(args, "timeout", 0)
|
timeout := getIntArg(args, "timeout", 0)
|
||||||
validateCerts := getBoolArg(args, "validate_certs", true)
|
validateCerts := getBoolArg(args, "validate_certs", true)
|
||||||
|
urlUsername := getStringArg(args, "url_username", "")
|
||||||
|
urlPassword := getStringArg(args, "url_password", "")
|
||||||
|
forceBasicAuth := getBoolArg(args, "force_basic_auth", false)
|
||||||
|
|
||||||
if url == "" {
|
if url == "" {
|
||||||
return nil, coreerr.E("Executor.moduleURI", "url required", nil)
|
return nil, coreerr.E("Executor.moduleURI", "url required", nil)
|
||||||
|
|
@ -1596,6 +1599,17 @@ func (e *Executor) moduleURI(ctx context.Context, client sshExecutorClient, args
|
||||||
curlOpts = append(curlOpts, "-s", "-S")
|
curlOpts = append(curlOpts, "-s", "-S")
|
||||||
curlOpts = append(curlOpts, "-X", method)
|
curlOpts = append(curlOpts, "-X", method)
|
||||||
|
|
||||||
|
// Basic auth is modelled explicitly so callers do not need to embed
|
||||||
|
// credentials in the URL.
|
||||||
|
if urlUsername != "" || urlPassword != "" {
|
||||||
|
curlOpts = append(curlOpts, "-u", shellQuote(urlUsername+":"+urlPassword))
|
||||||
|
if forceBasicAuth {
|
||||||
|
curlOpts = append(curlOpts, "--basic")
|
||||||
|
}
|
||||||
|
} else if forceBasicAuth {
|
||||||
|
curlOpts = append(curlOpts, "--basic")
|
||||||
|
}
|
||||||
|
|
||||||
// Headers
|
// Headers
|
||||||
if headers, ok := args["headers"].(map[string]any); ok {
|
if headers, ok := args["headers"].(map[string]any); ok {
|
||||||
for k, v := range headers {
|
for k, v := range headers {
|
||||||
|
|
|
||||||
|
|
@ -1517,6 +1517,24 @@ func TestModulesAdv_ModuleURI_Good_PostWithBodyAndHeaders(t *testing.T) {
|
||||||
assert.True(t, mock.containsSubstring("Authorization"))
|
assert.True(t, mock.containsSubstring("Authorization"))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestModulesAdv_ModuleURI_Good_UsesBasicAuthFlags(t *testing.T) {
|
||||||
|
e, mock := newTestExecutorWithMock("host1")
|
||||||
|
mock.expectCommand(`curl.*secure\.example\.com`, "OK\n200", "", 0)
|
||||||
|
|
||||||
|
result, err := moduleURIWithClient(e, mock, map[string]any{
|
||||||
|
"url": "https://secure.example.com/api",
|
||||||
|
"url_username": "apiuser",
|
||||||
|
"url_password": "apipass",
|
||||||
|
"force_basic_auth": true,
|
||||||
|
})
|
||||||
|
|
||||||
|
require.NoError(t, err)
|
||||||
|
assert.False(t, result.Failed)
|
||||||
|
assert.Equal(t, 200, result.RC)
|
||||||
|
assert.True(t, mock.hasExecuted(`-u .*apiuser:apipass`))
|
||||||
|
assert.True(t, mock.hasExecuted(`--basic`))
|
||||||
|
}
|
||||||
|
|
||||||
func TestModulesAdv_ModuleURI_Good_FormURLEncodedBody(t *testing.T) {
|
func TestModulesAdv_ModuleURI_Good_FormURLEncodedBody(t *testing.T) {
|
||||||
e, mock := newTestExecutorWithMock("host1")
|
e, mock := newTestExecutorWithMock("host1")
|
||||||
mock.expectCommand(`curl.*form\.example\.com`, "created\n201", "", 0)
|
mock.expectCommand(`curl.*form\.example\.com`, "created\n201", "", 0)
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue