php / php/php-src

[Soap] [DateTime] SoapVar mandatory for Datetime? Also from_xml still needed in SoapClient?

Abierto
#21,981 10 comentarios 0 reacciones 1 asignado Ver en GitHub

@devnexen ya está trabajando en esto.

Desde el 8/5/2026.

  • #21996 de @devnexen — abierto
Extension: soap Feature Status: Needs Triage
Lenguaje dominante
C
Estrellas
40.4k
Forks
8.2k
Merge medio
2 d 13 h
PR fusionados (30 d)
96

Descripción

Description

Trying to reproduce (now fixed) Problem: https://bugs.php.net/bug.php?id=44383
Also, there: https://github.com/php/php-src/issues/11725

i used this WSDL for testing from the first link:

<?xml version ="1.0" encoding ="UTF-8" ?> 
    <wsdl:definitions name="GetCurrentDate" 
      targetNamespace="http://localhost"
      xmlns:tns="http://localhost"
      xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
      xmlns:xsd="http://www.w3.org/2001/XMLSchema"
      xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
      xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">

      <wsdl:message name="GetCurrentDateRequest" />
      <wsdl:message name="GetCurrentDateResponse">
        <wsdl:part name="currentDate" type="xsd:datetime" />
      </wsdl:message>
  
      <wsdl:portType name="GetCurrentDatePortType">
        <wsdl:operation name="getCurrentDate">
          <wsdl:input message="tns:GetCurrentDateRequest" />
          <wsdl:output message="tns:GetCurrentDateResponse" />
        </wsdl:operation>
      </wsdl:portType>

      <wsdl:binding name="GetCurrentDateBinding" type="tns:GetCurrentDatePortType">
        <soap:binding style="rpc"
          transport="http://schemas.xmlsoap.org/soap/http" />
        <wsdl:operation name="getCurrentDate">
          <soap:operation soapAction="http://localhost#getCurrentDate" />
          <wsdl:input>
            <soap:body use="encoded"
              namespace="urn:xmethods-delayed-quotes"
          encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
          </wsdl:input>
          <wsdl:output>
            <soap:body use="encoded"
              namespace="urn:xmethods-delayed-quotes"
              encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" />
          </wsdl:output>
        </wsdl:operation>
      </wsdl:binding>

      <wsdl:service name="GetCurrentDateService">
        <wsdl:port name="GetCurrentDatePortType" binding="GetCurrentDateBinding">
          <soap:address location="http://localhost/server.php" />
        </wsdl:port>
      </wsdl:service>
    </wsdl:definitions>

The following code for the server.php

<?php

    function getCurrentDate() {
       #return new DateTime("now", new DateTimeZone("UTC"));
       return new SoapVar(new DateTime("now", new DateTimeZone("UTC")), XSD_DATETIME);
    }

      $server = new SoapServer('bug.wsdl', [

		'cache_wsdl' => WSDL_CACHE_NONE
		]);
      $server->addFunction('getCurrentDate');
      $server->handle();

First i noticed, that it still wants me to use SoapVar which is different from the https://bugs.php.net/bug.php?id=44383 example
@ndossche maybe knows why?

Second in my Client, i still need to define "from_xml"
only "to_xml" was implemented by https://github.com/php/php-src/issues/11725

My client.php

<?php

class ABC
{
    protected static array $typeMap = [
        [
            "type_ns" => "http://www.w3.org/2001/XMLSchema",
            "type_name" => "date",
            "from_xml" => [self::class, "fromXSDDate"],
            #"to_xml"    => [self::class, 'toXSDDate'],
        ],
        [
            "type_ns" => "http://www.w3.org/2001/XMLSchema",
            "type_name" => "dateTime",
            "from_xml" => [self::class, "fromXSDDate"],
            #"to_xml"    => [self::class, 'toXSDDate'],
        ],
    ];

    public static function fromXSDDate(?string $string): ?DateTimeInterface
    {
        if (is_null($string)) {
            return null;
        }
        var_dump($string);
        #=> "<currentDate xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:type="xsd:dateTime">2026-05-08T07:41:50.152132Z</currentDate>"
        $string = (string) simplexml_load_string($string);
        var_dump($string); #=> "2026-05-08T07:41:50.152132Z"

        # format doesn't seems to be parsable
        #$return = DateTime::createFromFormat(DateTimeInterface::RFC3339_EXTENDED, $string, new DateTimeZone("UTC"));
        $return = new DateTime($string, new DateTimeZone("UTC"));
        var_dump(DateTime::getLastErrors());
        return $return;
    }

    #public static function toXSDDate(?DateTimeInterface $dateTime): ?string
    #{
    #    if (is_null($dateTime)) {
    #        return null;
    #    }
    #    return $dateTime->format(DateTimeInterface::ATOM);
    #}

    public function getCurrentDate()
    {
        $client = new SoapClient("bug.wsdl", [
            "typemap" => self::$typeMap,
            "trace" => 1,
            "cache_wsdl" => WSDL_CACHE_NONE,
        ]);
        var_dump($client->__getFunctions());
        try {
            $date = $client->getCurrentDate();
            var_dump($date);
            echo "last response: " . $client->__getLastResponse();
            echo "current date: " .
                $date->format(DateTimeInterface::ATOM) .
                PHP_EOL;
        } catch (Exception $e) {
            var_dump($client->__getLastResponse());
            throw $e;
        }
    }
}

$abc = new ABC();
$abc->getCurrentDate();

without typemap on the client, getCurrentDate() returns string instead of DateTimeInterface, so it still does need from_xml

Second, "2026-05-08T07:41:50.152132Z" doesn't seem to be a format that can be parsed by createFromFormat, but need to be parsed by new DateTime directly?

It looks like RFC3339_EXTENDED
with s.vP at the end, but it's s.up with u a small p.
Why does ext-soap use something that isn't part of the format constants?

PHP Version
PHP 8.4.19 (cli) (built: Mar 12 2026 23:34:12) (NTS)
Copyright (c) The PHP Group
Built by https://github.com/docker-library/php
Zend Engine v4.4.19, Copyright (c) Zend Technologies
    with Zend OPcache v8.4.19, Copyright (c), by Zend Technologies
    with Xdebug v3.5.0, Copyright (c) 2002-2025, by Derick Rethans
Operating System

No response

Guía de contribución

Abrir la guía de contribución

Primeros pasos

  1. Lee el issue completo y luego la guía de contribución del proyecto.
  2. Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
  3. Haz un fork del repositorio y trabaja en una rama.
  4. Abre un pull request que haga referencia al número del issue.

Evaluación

Este issue todavía no se ha evaluado.

Recibe los nuevos issues en tu correo

Un resumen breve de issues de GitHub para principiantes.