PHP to Go使用Unix域套接字

I'm trying to use a Unix socket to have PHP send IPC messages to Go. Everything seems to work, except that PHP seems to keep reading the response from the socket, and won't let go. (The browser load-spinner keeps going, and there's no page render.) I'm using flag PHP_NORMAL_READ in the PHP:socket_read() function, and explicitly sending " " from Go.

Watching the Go process in the terminal, everything appears to work correctly on that end.

Edit: I think it was a browser caching issue. If I send different data back for PHP to echo, everything works as expected. I also switched to fmt.Fprintln() to make sure I wasn't getting the newline wrong.

Go:

package main

import (
    "net"
    "fmt"
    "log"
    "os"
)

const socket_addr = "/tmp/odc_ws.sock"

func echoServer(c net.Conn){
    buf := make([]byte, 512)
    size, err := c.Read(buf)
    if err != nil {
        log.Fatal("Read error: ", err)
    }
    data := buf[0:size]     
    fmt.Println("Server received: ", string(data))

    // NEW CODE
    t := time.Now()
    retMsg := fmt.Sprintf("OK+ at %s", t)
    size, err = fmt.Fprintln(c, retMsg)     

    //size, err = c.Write(ok)

    if err == nil{
        fmt.Println("Wrote this many bytes: ", size)
    } else {
        log.Fatal("Write error: ", err)
    }
}

func main(){
    l, err := net.Listen("unix", socket_addr)
    if err != nil{
        fmt.Println("On noes: %s", err)
        return
    }
    defer l.Close()
    for{
        fd, err := l.Accept()
        if err != nil{
            log.Fatal("Accept error", err)
        }
        go echoServer(fd)
    }

}

PHP:

ob_implicit_flush();
$socket_file = "/tmp/odc_ws.sock";

if (($socket = socket_create(AF_UNIX, SOCK_STREAM, 0)) === false) {
    echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "<br>";
}
if (socket_connect($socket, $socket_file) === false) {
    echo "socket_connect() failed: reason: " . socket_strerror(socket_last_error($sock)) . "<br>";
}

$msg = 'PHP sent Go a message at ' . date('H:i:s');
$write_res = socket_write($socket, $msg, $msg_len = strlen($msg));
if($write_res != $msg_len){
    echo '<div>Socket write error: ' . socket_strerror( socket_last_error($socket) ) . '</div>';
}

while($read = socket_read($socket, 512, PHP_NORMAL_READ)){
    echo "<div>Server says: $read</div>";
}
socket_close($socket);

It is not a PHP issue; you are not closing the server connection, so PHP continues to wait for more data. Add a defer c.Close():

func echoServer(c net.Conn){
    defer c.Close()

    buf := make([]byte, 512)
    size, err := c.Read(buf)
    if err != nil {

PHP_NORMAL_READ is to force socket_read to read lines of text rather than binary streams.

From the PHP docs on socket_read (emphasis mine)

socket_read() returns the data as a string on success, or FALSE on error (including if the remote host has closed the connection)