Saltar al contenido

SOAP

El protocolo de mensajería XML de los servicios web clásicos: cómo viaja, qué forma tiene el sobre, cómo devuelve los errores, y las extensiones de seguridad y de datos binarios.

Qué es SOAP y cómo viaja

SOAP es un protocolo de intercambio de mensajes basado en XML. Define un sobre con una estructura fija en el que se mete lo que se quiere enviar, de modo que emisor y receptor sepan siempre dónde está la información y dónde los metadatos, independientemente del lenguaje en que estén escritos. Nació como acrónimo de Simple Object Access Protocol, pero desde la versión 1.2 la W3C retiró el acrónimo y el estándar se llama simplemente SOAP.

SOAP no dice cómo se transporta el sobre: eso lo decide la vinculación. La habitual con diferencia es HTTP, pero existen vinculaciones sobre correo electrónico o sobre colas de mensajes. Sobre HTTP, la petición se envía con POST y la respuesta llega con un código de estado 200 si todo ha ido bien, o 500 si el servicio ha devuelto un error de protocolo.

xml
POST /servicios/temario HTTP/1.1
Host: api.llegandoalcorte.com
Content-Type: application/soap+xml; charset=utf-8

<?xml version="1.0" encoding="UTF-8"?>
<soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope"
               xmlns:lac="https://llegandoalcorte.com/temario">
  <soap:Body>
    <lac:notaMediaDelTema>
      <lac:alumno>482</lac:alumno>
      <lac:tema>servicios-web</lac:tema>
    </lac:notaMediaDelTema>
  </soap:Body>
</soap:Envelope>

La razón de que siempre se use POST es que el mensaje viaja en el cuerpo de la petición, y una petición GET no lleva cuerpo. SOAP 1.2 llegó a definir además una vinculación con GET para operaciones de solo consulta, pero apenas se usa: en la práctica, un servicio SOAP se invoca con POST.

El nombre de la operación viaja dentro del sobre, no en la URL. Por eso a un servicio SOAP le basta un único punto de acceso para todas sus operaciones.

Para el examen

  • Qué es: un protocolo de mensajes en XML, con sobre de estructura fija

  • Desde la versión 1.2: ya no es un acrónimo

  • Método HTTP que usa: siempre POST, porque el mensaje va en el cuerpo

  • Dónde viaja el nombre de la operación: DENTRO del sobre

El sobre por dentro: Header, Body y Fault

El elemento raíz de todo mensaje SOAP es Envelope, y dentro caben dos hijos. Header es opcional y guarda los metadatos: credenciales, identificadores de transacción, direccionamiento, cualquier cosa que acompañe al mensaje sin ser el mensaje. Body es obligatorio y contiene la carga útil, es decir, la operación con sus parámetros o el resultado.

Los errores no se improvisan: van en un elemento Fault situado dentro del Body. Si el servicio devuelve un Fault sobre HTTP, el código de estado que acompaña es 500. Los nombres de los elementos internos cambiaron entre versiones, y es un detalle que se pregunta.

SOAP 1.1SOAP 1.2Para qué sirve
faultcodeCode y su ValueClasificar el error de forma procesable por la máquina
faultstringReason y su TextDescribir el error en lenguaje humano
detailDetailAñadir información específica de la aplicación
xml
<?xml version="1.0" encoding="UTF-8"?>
<soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope"
               xmlns:lac="https://llegandoalcorte.com/temario">
  <soap:Body>
    <soap:Fault>
      <soap:Code>
        <soap:Value>soap:Receiver</soap:Value>
      </soap:Code>
      <soap:Reason>
        <soap:Text xml:lang="es">El alumno 482 no tiene intentos registrados</soap:Text>
      </soap:Reason>
      <soap:Detail>
        <lac:codigoInterno>SIN-INTENTOS</lac:codigoInterno>
      </soap:Detail>
    </soap:Fault>
  </soap:Body>
</soap:Envelope>

Los tipos de datos que aparecen dentro del sobre se describen con XSD (XML Schema Definition), el lenguaje de esquema con el que se declara la estructura y las restricciones de un documento XML. Es lo que permite que el receptor valide el mensaje antes de procesarlo, y es también lo que rellena la sección types del WSDL.

Para el examen

  • Envelope: el sobre que lo envuelve todo

  • Header: opcional: metadatos como credenciales o transacción

  • Body: obligatorio: la carga útil

  • Fault: los errores, dentro del Body; sobre HTTP se acompañan del código 500

WS-Security

El perfil básico de interoperabilidad no cubre la seguridad, así que OASIS publicó WS-Security para taparlo. Su mecanismo es sencillo de describir: añade al mensaje SOAP una cabecera de seguridad dentro del Header, y en ella coloca las credenciales, la firma y la información de cifrado.

  • Firma de los mensajes con XML Signature, que garantiza la integridad y el origen.
  • Cifrado de los mensajes con XML Encryption, que garantiza la confidencialidad.
  • Autenticación del cliente con un testigo de usuario y contraseña (UsernameToken).
  • Autenticación del cliente con un testigo binario (BinarySecurityToken), que transporta certificados X.509, testigos SAML o tiques Kerberos.

La ventaja de WS-Security frente a cifrar el canal con TLS es que la protección viaja pegada al mensaje: sigue en pie aunque el mensaje atraviese varios intermediarios, y puede aplicarse solo a una parte del sobre.

Para el examen

  • Organismo: OASIS

  • Qué añade: una cabecera de seguridad al mensaje

  • Firma y cifrado: XML Signature y XML Encryption

  • Testigos: de usuario o binarios: X.509, SAML y Kerberos

  • Su ventaja: protege el mensaje, no solo el canal

MTOM: enviar datos binarios

XML es texto, así que meter un fichero binario dentro de un sobre SOAP obliga a codificarlo como texto y eso lo engorda alrededor de un tercio, además de forzar al receptor a analizarlo como XML. MTOM resuelve ese problema: el sobre SOAP viaja ligero y el binario se envía aparte, como una parte adjunta del mismo envío, siguiendo el formato MIME con el tipo application/xop+xml.

El resultado es que el servicio web sigue siendo un servicio SOAP normal y el fichero pesado circula por fuera del XML, sin pasar por el analizador. MTOM está incorporado a la versión 1.2 del WS-I Basic Profile.

MTOM no comprime nada: lo que hace es sacar el binario del cuerpo XML para que no haya que codificarlo como texto ni analizarlo.

Para el examen

  • Qué hace: saca el binario del cuerpo XML y lo envía como parte adjunta MIME

  • Para qué: no codificarlo como texto ni analizarlo

  • Lo que no hace: no comprime

  • Dónde está incluido: en el WS-I Basic Profile 1.2

Cómo se implementa: JAX-WS y el mundo .NET

En Java, la API para crear y consumir servicios SOAP es JAX-WS, con implementaciones como Apache CXF, Axis2, JBossWS o Metro. El programador no escribe XML: escribe una clase Java normal, le pone unas cuantas anotaciones y el motor se encarga de generar el WSDL, de convertir los objetos a XML y de vuelta, y de publicar el punto de acceso.

AnotaciónQué hacePropiedades que más se usan
@WebServiceMarca la clase como servicio webname, serviceName, targetNamespace, endpointInterface, portName
@WebMethodExpone un método concreto como operación del serviciooperationName, action, exclude
@WebParamAjusta cómo se expone un parámetro del métodoname, targetNamespace
@WebResultAjusta cómo se expone el valor devueltoname, targetNamespace
@RequestWrapperIndica la clase Java que envuelve la petición de una operaciónlocalName, className, targetNamespace
java
@WebService(
    name = "Temario",
    serviceName = "TemarioService",
    targetNamespace = "https://llegandoalcorte.com/temario")
public class TemarioEndpoint {

  @WebMethod(operationName = "notaMediaDelTema")
  @WebResult(name = "notaMedia")
  public double notaMedia(
      @WebParam(name = "alumno") long alumnoId,
      @WebParam(name = "tema") String temaSlug) {
    // consulta los intentos del alumno y calcula la media
  }
}

En la plataforma .NET la idea es la misma. Los servicios web clásicos se publican en ficheros con extensión .asmx, y el motor de ASP.NET genera por su cuenta la documentación del servicio y su WSDL: basta con añadir la consulta ?wsdl a la dirección del servicio para obtener el XML del contrato.

Para el examen

  • En Java: JAX-WS, con Apache CXF, Axis2 o Metro

  • Anotaciones: WebService, WebMethod, WebParam y WebResult

  • En .NET clásico: ficheros .asmx

  • Cómo se obtiene el WSDL: añadiendo ?wsdl a la dirección