Saltar al contenido principal

Visión general

Casdoor ahora puede usarse como un SAML IdP. Hasta este punto, Casdoor ha soportado las características principales de SAML 2.0.

Configuración en SP

En general, el SP requiere tres campos obligatorios: Single Sign-On, Issuer y Public Certificate. La mayoría de los SP pueden obtener estos campos cargando el archivo de metadatos XML o la URL de metadatos XML para autocompletar.

Los metadatos del punto final SAML en Casdoor son <Endpoint of casdoor>/api/saml/metadata?application=admin/<application name>. Supongamos que el punto final de Casdoor es https://door.casdoor.com, y contiene una aplicación llamada app-built-in. El punto final de metadatos XML será:

https://door.casdoor.com/api/saml/metadata?application=admin/app-built-in

También puede encontrar los metadatos en la página de edición de la aplicación. Haga clic en el botón para copiar la URL y péguela en el navegador para descargar los metadatos XML.

metadatos

Configuración en Casdoor IdP

Casdoor soporta tanto GET como POST SAMLResponse. Casdoor necesita saber qué tipos de solicitudes soporta el SP cuando Casdoor envía la SAMLResponse al SP. Necesita configurar la aplicación en Casdoor basándose en el tipo de SAMLResponse que soporta su SP.

When integrating Casdoor as a SAML IdP with external identity providers (like Azure AD), the /api/acs endpoint receives SAML responses. This endpoint is configured to accept cross-origin POST requests, allowing IdPs from different domains to send authentication data.

información

Si completa la URL de respuesta, Casdoor enviará la SAMLResponse mediante la solicitud POST. Si la URL de respuesta está vacía, Casdoor usará la solicitud GET. Puede que se pregunte cómo sabe Casdoor la URL de respuesta del SP si la URL de respuesta está vacía. De hecho, Casdoor puede obtener la URL llamada AssertionConsumerServiceURL analizando la SAMLRequest y enviar la solicitud con SAMLResponse a AssertionConsumerServiceURL. La URL de respuesta sobrescribirá la AssertionConsumerServiceURL en SAMLRequest.

  • URL de respuesta: Escriba la URL del ACS que verifica la respuesta SAML.

    URL de respuesta

  • URL de redirección: Escriba un nombre único. Esto puede llamarse Audience o Entity ID en su SP. Asegúrese de completar la misma URL de redirección aquí como en su SP.

    ID de entidad

SAML attributes

Some SP will require you to provide external attributes in SAML Response, you can add those in SAML attributes table. And you can insert user's field to it.

If your service provider only requires the NameID field and doesn't need additional user attributes (Email, Name, DisplayName, Roles), you can enable the Disable SAML attributes option in the application settings. When enabled, Casdoor will omit these attributes from the SAML response, which can help avoid XML namespace issues with certain SPs that have strict validation requirements.

For examle

NombreName formatValue
https://www.aliyun.com/SAML-Role/Attributes/RoleSessionNameUnspecified$user.name
https://www.aliyun.com/SAML-Role/Attributes/RoleUnspecifiedacs:ram::1879818006829152:role/$user.roles,acs:ram::1879818006829152:saml-provider/testa

will generate response with external saml:Attribute

<saml:Attribute Name="https://www.aliyun.com/SAML-Role/Attributes/RoleSessionName" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified">
<saml:AttributeValue xsi:type="xs:string">admi122n@outlook.com</saml:AttributeValue>
</saml:Attribute>
<saml:Attribute Name="https://www.aliyun.com/SAML-Role/Attributes/Role" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified">
<saml:AttributeValue xsi:type="xs:string"> acs:ram::1879818006829152:role/role1,acs:ram::1879818006829152:saml-provider/testa</saml:AttributeValue>
<saml:AttributeValue xsi:type="xs:string"> acs:ram::1879818006829152:role/role2,acs:ram::1879818006829152:saml-provider/testa</saml:AttributeValue>
</saml:Attribute>
información

We only support insert $user.owner,$user.name,$user.email,$user.id,$user.phone,$user.roles,$user.permissions,$user.groups

Perfil de usuario

Después de iniciar sesión con éxito, el perfil de usuario en la SAMLResponse devuelta de Casdoor tiene tres campos. Los atributos en el XML y los atributos del usuario en Casdoor se mapean de la siguiente manera:

Nombre de atributo XMLCampo de usuario
Correo electrónicoemail
Nombre para mostrardisplayName
Namename

Vea https://en.wikipedia.org/wiki/SAML_2.0 para más información sobre SAML y sus diferentes versiones.

Un ejemplo

gosaml2 es una implementación de SAML 2.0 para Proveedores de Servicios basada en etree y goxmldsig, una implementación pura de Go de firmas digitales XML. Usamos esta biblioteca para probar SAML 2.0 en Casdoor como se muestra a continuación.

Suponga que puede acceder a Casdoor a través de http://localhost:7001/, y su Casdoor contiene una aplicación llamada app-built-in, que pertenece a una organización llamada built-in. Las URLs, http://localhost:6900/acs/example y http://localhost:6900/saml/acs/example, deben agregarse a las URLs de redirección en app-built-in.

import (
"crypto/x509"
"fmt"
"net/http"

"io/ioutil"

"encoding/base64"
"encoding/xml"

saml2 "github.com/russellhaering/gosaml2"
"github.com/russellhaering/gosaml2/types"
dsig "github.com/russellhaering/goxmldsig"
)

func main() {
res, err := http.Get("http://localhost:7001/api/saml/metadata?application=admin/app-built-in")
if err != nil {
panic(err)
}

rawMetadata, err := ioutil.ReadAll(res.Body)
if err != nil {
panic(err)
}

metadata := &types.EntityDescriptor{}
err = xml.Unmarshal(rawMetadata, metadata)
if err != nil {
panic(err)
}

certStore := dsig.MemoryX509CertificateStore{
Roots: []*x509.Certificate{},
}

for _, kd := range metadata.IDPSSODescriptor.KeyDescriptors {
for idx, xcert := range kd.KeyInfo.X509Data.X509Certificates {
if xcert.Data == "" {
panic(fmt.Errorf("metadata certificate(%d) must not be empty", idx))
}
certData, err := base64.StdEncoding.DecodeString(xcert.Data)
if err != nil {
panic(err)
}

idpCert, err := x509.ParseCertificate(certData)
if err != nil {
panic(err)
}

certStore.Roots = append(certStore.Roots, idpCert)
}
}

randomKeyStore := dsig.RandomKeyStoreForTest()

sp := &saml2.SAMLServiceProvider{
IdentityProviderSSOURL: metadata.IDPSSODescriptor.SingleSignOnServices[0].Location,
IdentityProviderIssuer: metadata.EntityID,
ServiceProviderIssuer: "http://localhost:6900/acs/example",
AssertionConsumerServiceURL: "http://localhost:6900/v1/_saml_callback",
SignAuthnRequests: true,
AudienceURI: "http://localhost:6900/saml/acs/example",
IDPCertificateStore: &certStore,
SPKeyStore: randomKeyStore,
}

http.HandleFunc("/v1/_saml_callback", func(rw http.ResponseWriter, req *http.Request) {
err := req.ParseForm()
if err != nil {
rw.WriteHeader(http.StatusBadRequest)
return
}
samlReponse := req.URL.Query().Get("SAMLResponse")
assertionInfo, err := sp.RetrieveAssertionInfo(samlReponse)
if err != nil {
fmt.Println(err)
rw.WriteHeader(http.StatusForbidden)
return
}
fmt.Println(assertionInfo)
if assertionInfo.WarningInfo.InvalidTime {
fmt.Println("here12:", assertionInfo.WarningInfo.InvalidTime)
rw.WriteHeader(http.StatusForbidden)
return
}

if assertionInfo.WarningInfo.NotInAudience {
fmt.Println(assertionInfo)
fmt.Println("here13:", assertionInfo.WarningInfo.NotInAudience)
rw.WriteHeader(http.StatusForbidden)
return
}

fmt.Fprintf(rw, "NameID: %s\n", assertionInfo.NameID)

fmt.Fprintf(rw, "Assertions:\n")

for key, val := range assertionInfo.Values {
fmt.Fprintf(rw, " %s: %+v\n", key, val)
}
fmt.Println(assertionInfo.Values.Get("FirstName"))
fmt.Fprintf(rw, "\n")

fmt.Fprintf(rw, "Warnings:\n")
fmt.Fprintf(rw, "%+v\n", assertionInfo.WarningInfo)
})

println("Visit this URL To Authenticate:")
authURL, err := sp.BuildAuthURL("")
if err != nil {
panic(err)
}

println(authURL)

println("Supply:")
fmt.Printf(" SP ACS URL : %s\n", sp.AssertionConsumerServiceURL)

err = http.ListenAndServe(":6900", nil)
if err != nil {
panic(err)
}
}

Ejecute el código anterior, y la consola mostrará el siguiente mensaje.

Visit this URL To Authenticate:
http://localhost:7001/login/saml/authorize/admin/app-built-in?SAMLRequest=lFVbk6K8Fv0rFvNo2QR...
Supply:
SP ACS URL : http://localhost:6900/v1/_saml_callback

Haga clic en la URL para autenticarse, y se mostrará la página de inicio de sesión de Casdoor.

iniciar sesión

Después de autenticarse, recibirá los mensajes de respuesta como se muestra a continuación.

respuesta