summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--pkg/api/handlers/compat/auth.go59
-rw-r--r--pkg/api/server/register_auth.go24
-rw-r--r--pkg/api/server/swagger.go9
-rw-r--r--pkg/domain/entities/system.go11
-rw-r--r--test/apiv2/60-auth.at24
-rw-r--r--test/apiv2/rest_api/test_rest_v2_0_0.py11
6 files changed, 110 insertions, 28 deletions
diff --git a/pkg/api/handlers/compat/auth.go b/pkg/api/handlers/compat/auth.go
new file mode 100644
index 000000000..2c152fbc2
--- /dev/null
+++ b/pkg/api/handlers/compat/auth.go
@@ -0,0 +1,59 @@
+package compat
+
+import (
+ "context"
+ "encoding/json"
+ "fmt"
+ "net/http"
+ "strings"
+
+ DockerClient "github.com/containers/image/v5/docker"
+ "github.com/containers/image/v5/types"
+ "github.com/containers/podman/v3/pkg/api/handlers/utils"
+ "github.com/containers/podman/v3/pkg/domain/entities"
+ "github.com/containers/podman/v3/pkg/registries"
+ docker "github.com/docker/docker/api/types"
+ "github.com/pkg/errors"
+)
+
+func stripAddressOfScheme(address string) string {
+ for _, s := range []string{"https", "http"} {
+ address = strings.TrimPrefix(address, s+"://")
+ }
+ return address
+}
+
+func Auth(w http.ResponseWriter, r *http.Request) {
+ var authConfig docker.AuthConfig
+ err := json.NewDecoder(r.Body).Decode(&authConfig)
+ if err != nil {
+ utils.Error(w, "Something went wrong.", http.StatusInternalServerError, errors.Wrapf(err, "failed to parse request"))
+ return
+ }
+
+ skipTLS := types.NewOptionalBool(false)
+ if strings.HasPrefix(authConfig.ServerAddress, "https://localhost/") || strings.HasPrefix(authConfig.ServerAddress, "https://localhost:") || strings.HasPrefix(authConfig.ServerAddress, "localhost:") {
+ // support for local testing
+ skipTLS = types.NewOptionalBool(true)
+ }
+
+ fmt.Println("Authenticating with existing credentials...")
+ sysCtx := types.SystemContext{
+ AuthFilePath: "",
+ DockerCertPath: "",
+ DockerInsecureSkipTLSVerify: skipTLS,
+ SystemRegistriesConfPath: registries.SystemRegistriesConfPath(),
+ }
+ registry := stripAddressOfScheme(authConfig.ServerAddress)
+ if err := DockerClient.CheckAuth(context.Background(), &sysCtx, authConfig.Username, authConfig.Password, registry); err == nil {
+ utils.WriteResponse(w, http.StatusOK, entities.AuthReport{
+ IdentityToken: "",
+ Status: "Login Succeeded",
+ })
+ } else {
+ utils.WriteResponse(w, http.StatusBadRequest, entities.AuthReport{
+ IdentityToken: "",
+ Status: "login attempt to " + authConfig.ServerAddress + " failed with status: " + err.Error(),
+ })
+ }
+}
diff --git a/pkg/api/server/register_auth.go b/pkg/api/server/register_auth.go
index 1e5474462..56e115e30 100644
--- a/pkg/api/server/register_auth.go
+++ b/pkg/api/server/register_auth.go
@@ -1,13 +1,33 @@
package server
import (
+ "net/http"
+
"github.com/containers/podman/v3/pkg/api/handlers/compat"
"github.com/gorilla/mux"
)
func (s *APIServer) registerAuthHandlers(r *mux.Router) error {
- r.Handle(VersionedPath("/auth"), s.APIHandler(compat.UnsupportedHandler))
+ // swagger:operation POST /auth compat auth
+ // ---
+ // summary: Check auth configuration
+ // tags:
+ // - system (compat)
+ // produces:
+ // - application/json
+ // parameters:
+ // - in: body
+ // name: authConfig
+ // description: Authentication to check
+ // schema:
+ // $ref: "#/definitions/AuthConfig"
+ // responses:
+ // 200:
+ // $ref: "#/responses/SystemAuthResponse"
+ // 500:
+ // $ref: "#/responses/InternalError"
+ r.Handle(VersionedPath("/auth"), s.APIHandler(compat.Auth)).Methods(http.MethodPost)
// Added non version path to URI to support docker non versioned paths
- r.Handle("/auth", s.APIHandler(compat.UnsupportedHandler))
+ r.Handle("/auth", s.APIHandler(compat.Auth)).Methods(http.MethodPost)
return nil
}
diff --git a/pkg/api/server/swagger.go b/pkg/api/server/swagger.go
index 92efb8ef3..12fd083bb 100644
--- a/pkg/api/server/swagger.go
+++ b/pkg/api/server/swagger.go
@@ -226,3 +226,12 @@ type swagSystemPruneReport struct {
entities.SystemPruneReport
}
}
+
+// Auth response
+// swagger:response SystemAuthResponse
+type swagSystemAuthResponse struct {
+ // in:body
+ Body struct {
+ entities.AuthReport
+ }
+}
diff --git a/pkg/domain/entities/system.go b/pkg/domain/entities/system.go
index a1cfb4481..4b8383613 100644
--- a/pkg/domain/entities/system.go
+++ b/pkg/domain/entities/system.go
@@ -107,3 +107,14 @@ type ComponentVersion struct {
type ListRegistriesReport struct {
Registries []string
}
+
+// swagger:model AuthConfig
+type AuthConfig struct {
+ types.AuthConfig
+}
+
+// AuthReport describes the response for authentication check
+type AuthReport struct {
+ IdentityToken string
+ Status string
+}
diff --git a/test/apiv2/60-auth.at b/test/apiv2/60-auth.at
index 378955cd7..cfde519c1 100644
--- a/test/apiv2/60-auth.at
+++ b/test/apiv2/60-auth.at
@@ -5,25 +5,19 @@
start_registry
-# FIXME FIXME FIXME: remove the 'if false' for use with PR 9589
-if false; then
-
-# FIXME FIXME: please forgive the horrible POST params format; I have an
-# upcoming PR which should fix that.
-
# Test with wrong password. Confirm bad status and appropriate error message
-t POST /v1.40/auth "\"username\":\"${REGISTRY_USERNAME}\",\"password\":\"WrOnGPassWord\",\"serveraddress\":\"localhost:$REGISTRY_PORT/\"" \
+t POST /v1.40/auth username=$REGISTRY_USERNAME password=WrOnGPassWord serveraddress=localhost:$REGISTRY_PORT/ \
400 \
.Status~'.* invalid username/password'
-# Test with the right password. Confirm status message and reasonable token
-t POST /v1.40/auth "\"username\":\"${REGISTRY_USERNAME}\",\"password\":\"${REGISTRY_PASSWORD}\",\"serveraddress\":\"localhost:$REGISTRY_PORT/\"" \
+# Test with the right password. Confirm status message
+t POST /v1.40/auth username=$REGISTRY_USERNAME password=$REGISTRY_PASSWORD serveraddress=localhost:$REGISTRY_PORT/ \
200 \
.Status="Login Succeeded" \
- .IdentityToken~[a-zA-Z0-9]
-
-# FIXME: now what? Try something-something using that token?
-token=$(jq -r .IdentityToken <<<"$output")
-# ...
+ .IdentityToken=""
-fi # FIXME FIXME FIXME: remove when working
+# Same test with url scheme provided
+t POST /v1.40/auth username=$REGISTRY_USERNAME password=$REGISTRY_PASSWORD serveraddress=https://localhost:$REGISTRY_PORT/ \
+ 200 \
+ .Status="Login Succeeded" \
+ .IdentityToken=""
diff --git a/test/apiv2/rest_api/test_rest_v2_0_0.py b/test/apiv2/rest_api/test_rest_v2_0_0.py
index c0b61ea85..d7910f555 100644
--- a/test/apiv2/rest_api/test_rest_v2_0_0.py
+++ b/test/apiv2/rest_api/test_rest_v2_0_0.py
@@ -555,17 +555,6 @@ class TestApi(unittest.TestCase):
self.assertIn(name, payload["VolumesDeleted"])
self.assertGreater(payload["SpaceReclaimed"], 0)
- def test_auth_compat(self):
- r = requests.post(
- PODMAN_URL + "/v1.40/auth",
- json={
- "username": "bozo",
- "password": "wedontneednopasswords",
- "serveraddress": "https://localhost/v1.40/",
- },
- )
- self.assertEqual(r.status_code, 404, r.content)
-
def test_version(self):
r = requests.get(PODMAN_URL + "/v1.40/version")
self.assertEqual(r.status_code, 200, r.content)