PHP bindings for the Go programming language (Golang)

PHP bindings for Go

API Documentation MIT License

This package implements support for executing PHP scripts, exporting Go variables for use in PHP contexts, attaching Go method receivers as PHP classes and returning PHP variables for use in Go contexts.

Both PHP 5.x and PHP 7.x series are supported.

Building

Building this package requires that you have PHP installed as a library. For most Linux systems, this can usually be found in the php-embed package, or variations thereof.

Once the PHP library is available, the bindings can be compiled with go build and are go get-able.

Note: Building against PHP 5.x requires that the php5 tag is provided, i.e.:

go get -tags php5 github.com/deuill/go-php

This is due to the fact that PHP 7.x is the default build target.

Status

Executing PHP script files as well as inline strings is supported and stable.

Binding Go values as PHP variables is allowed for most base types, and PHP values returned from eval'd strings can be converted and used in Go contexts as interface{} values.

It is possible to attach Go method receivers as PHP classes, with full support for calling expored methods, as well as getting and setting embedded fields (for struct-type method receivers).

Caveats

Be aware that, by default, PHP is not designed to be used in multithreaded environments (which severely restricts the use of these bindings with Goroutines) if not built with ZTS support. However, ZTS support has seen major refactoring between PHP 5 and PHP 7, and as such is currently unsupported by this package.

Currently, it is recommended to either sync use of seperate Contexts between Goroutines, or share a single Context among all running Goroutines.

Roadmap

Currently, the package lacks in several respects:

  • ZTS/multi-threading support. This basically means using Go-PHP in Goroutines is severely limited.
  • Documentation and examples, both package-level and external.
  • Performance. There's no reason to believe Go-PHP suffers from any serious performance issues in particular, but adding benchmarks, especially compared against vanilla PHP, might help.
  • Your feature request here?

These items will be tackled in order of significance (which may not be the order shown above).

Usage

Basic

Executing a script is simple:

package main

import (
    php "github.com/deuill/go-php"
    "os"
)

func main() {
    engine, _ := php.New()

    context, _ := engine.NewContext()
    context.Output = os.Stdout

    context.Exec("index.php")
    engine.Destroy()
}

The above will execute script file index.php located in the current folder and will write any output to the io.Writer assigned to Context.Output (in this case, the standard output).

Binding and returning variables

The following example demonstrates binding a Go variable to the running PHP context, and returning a PHP variable for use in Go:

package main

import (
    "fmt"
    php "github.com/deuill/go-php"
)

func main() {
    engine, _ := php.New()
    context, _ := engine.NewContext()

    var str string = "Hello"
    context.Bind("var", str)

    val, _ := context.Eval("return $var.' World';")
    fmt.Printf("%s", val.Interface())
    // Prints 'Hello World' back to the user.

    engine.Destroy()
}

A string value "Hello" is attached using Context.Bind under a name var (available in PHP as $var). A script is executed inline using Context.Eval, combinding the attached value with a PHP string and returning it to the user.

Finally, the value is returned as an interface{} using Value.Interface() (one could also use Value.String(), though the both are equivalent in this case).

License

All code in this repository is covered by the terms of the MIT License, the full text of which can be found in the LICENSE file.

Owner
Alex Palaistras
Code Person. Likes tabs for indentation.
Alex Palaistras
Comments
  • Installation Error on OS X 10.11.6

    Installation Error on OS X 10.11.6

    Hi, @deuill . I'm making a portable server to help my graphic designers friends on FrontEnd development with golang/echo framework. https://github.com/walker-walks/quick_serv They said it would be useful if the server executes php files. so I was trying to call and execute php from go in a way I don't have License problem..

    So I'm trying to use go-php library but I'm having the same issue with some people when I'm doing go get.

    engine/context.go:11:11: error: 'main/php.h' file not found with <angled> include; use "quotes" instead
     #include <main/php.h>
              ^~~~~~~~~~~~
              "main/php.h
    

    I don't know if it's correct but, I downloaded the php source file and put the php-7/main into go-php/engine/main and passed this part and them appeared another error which is.

    In file included from engine/context.go:11:
    ./main/php.h:35:10: fatal error: 'zend.h' file not found
    #include "zend.h"
             ^
    

    I moved all the files were in php-7/Zend to go-php/engine/main. and Now I have the issue below that I can't understand.

    In file included from engine/context.go:11:
    In file included from ./main/php.h:35:
    In file included from ./main/zend.h:31:
    In file included from ./main/zend_types.h:27:
    ./main/zend_portability.h:48:11: fatal error: 'zend_config.h' file not found
    # include <zend_config.h>
    

    I wold be very happy if you could give me any suggestions. thanks.

  • Installation Error

    Installation Error

    # go get -tags php5 github.com/deuill/go-php
    # github.com/deuill/go-php/engine
    work/src/github.com/deuill/go-php/engine/context.go:11:23: fatal error: main/php.h: No such file or directory
     // #include <main/php.h>
                           ^
    compilation terminated.
    
    
  • unknown type name 'uint32_t'

    unknown type name 'uint32_t'

    When I try to go-get go-php, I'm receiving the following error:

    workspace/src/github.com/deuill/go-php/engine/context.c: In function ‘context_eval’:
    workspace/src/github.com/deuill/go-php/engine/context.c:71:2: error: unknown type name ‘uint32_t’
      uint32_t compiler_options = CG(compiler_options);
      ^
    

    My gcc version is 4.8.5. I'm not familiar with C, so I'd be glad if you could help me to solve my issue.

  • Need a way to support mulitple include paths

    Need a way to support mulitple include paths

    I'm currently working in a docker to compile and run tests, and it happens that the docker container for golang is based upon Debian Jessie.

    On Jessie (and probably many other distributions), the correct include path for main/php.h is /usr/include/php5, which is not the value given in the various CGO headers.

    Any though on how to make this more portable ?

  • PHP 8.1.3

    PHP 8.1.3

    Hi, I'm trying to make it work in PHP8.1.3, but I find myself with a problem I can't really fix because I don't really understand Go. You can read the error here: https://gitlab.com/sailenicolas/gophp/-/jobs/2191492914

    Apparently the problematic function is: receiver_define.
    Basically this line: https://gitlab.com/sailenicolas/gophp/-/blob/php8/src/receiver.c#L236

    The call to zend_register_internal_class causes a panic. If you don't mind, is there any way to make it work? I'm asking if you can point me in the right direction. The function calls are as follows: TestEngineDefine -> e.Define -> C.receiver_define -> zend_register_internal_class() and there it throws PANIC. I already checked other SAPI modules, php-src and PHP7 internals, I can't find the problem from the PHP8 side, so I think the problem is in the Go tests (I am only assuming).

    The code is mostly the same...

    Sorry for my english.

  • Fix

    Fix "warning: initialization from incompatible pointer type"

    This pull request fixes the following error:

    engine.c:97:2: warning: initialization from incompatible pointer type [-Wincompatible-pointer-types]
      engine_log_message,          // Log Message
      ^~~~~~~~~~~~~~~~~~
    engine.c:97:2: note: (near initialization for ‘engine_module.log_message’)
    

    The extra parameter syslog_type_int was introduced in PHP 7.1, see this commit.

  •  error: unknown type name 'zend_string'

    error: unknown type name 'zend_string'

    $ go get github.com/deuill/go-php
    # github.com/deuill/go-php
    In file included from ../../../deuill/go-php/engine.go:14:
    In file included from include/receiver.h:15:
    include/php7/_receiver.h:12:34: error: unknown type name 'zend_string'; did you mean 'zend_stream'?
    static int _receiver_method_call(zend_string *method, zend_object *object, INTERNAL_FUNCTION_PARAMETERS);
                                     ^~~~~~~~~~~
                                     zend_stream
    /usr/include/php/Zend/zend_stream.h:60:3: note: 'zend_stream' declared here
    } zend_stream;
      ^
    In file included from ../../../deuill/go-php/engine.go:14:
    In file included from include/receiver.h:15:
    include/php7/_receiver.h:13:66: error: unknown type name 'zend_string'; did you mean 'zend_stream'?
    static zend_function *_receiver_method_get(zend_object **object, zend_string *name, const zval *key);
                                                                     ^~~~~~~~~~~
                                                                     zend_stream
    /usr/include/php/Zend/zend_stream.h:60:3: note: 'zend_stream' declared here
    } zend_stream;
      ^
    2 errors generated.
    
    
    $ which php
    /usr/local/bin/php
    
    $ which phpize
    /usr/bin/phpize
    
    $ which php-config
    /usr/local/bin/php-config
    
    $ uname -a
    Darwin bogon 16.5.0 Darwin Kernel Version 16.5.0: Fri Mar  3 16:52:33 PST 2017; root:xnu-3789.51.2~3/RELEASE_X86_64 x86_64
    
  • ubuntu 16.04 PHP7

    ubuntu 16.04 PHP7 "fatal error: main/php.h: No such file or directory"

    sorry, this may be a wrong place ? i've ubuntu 16.04, the php include path is located at /usr/include/php/20151012, is there any trick that will solve that issue using any ENV var ?

  • gc_possible_root: Assertion `(ref)->gc.u.v.type == 7 || (ref)->gc.u.v.type == 8' failed.

    gc_possible_root: Assertion `(ref)->gc.u.v.type == 7 || (ref)->gc.u.v.type == 8' failed.

    package php
    
    import (
        "testing"
        "github.com/stretchr/testify/assert"
        "github.com/deuill/go-php/engine"
    )
    
    func Test_map_value(t *testing.T) {
        should := assert.New(t)
        theEngine, err := engine.New()
        should.Nil(err)
        defer theEngine.Destroy()
        context, err := theEngine.NewContext()
        should.Nil(err)
        defer context.Destroy()
        context.Bind("hello", map[string]interface{}{})
    }
    
        for _, v := range c.values {
            v.Destroy()
        }
        c.values = nil
    
        C.context_destroy(c.context)
        c.context = nil
    

    when the values destroyed, then the context destroy will trigger gc_possible_root assertion error. Found in php-7.0.12

    Complete error message

    php.test: /home/xiaoju/disf-php/php-src/php-7.0.12/Zend/zend_gc.c:226: gc_possible_root: Assertion `(ref)->gc.u.v.type == 7 || (ref)->gc.u.v.type == 8' failed.
    SIGABRT: abort
    PC=0x7f051472e428 m=0
    signal arrived during cgo execution
    
  • php7: Allow for additional `php7.debian` build tag

    php7: Allow for additional `php7.debian` build tag

    The additional php7.debian build tag allows Go-PHP to be built against PHP7 on Debian (and Debian-derived, such as Ubuntu) distributions. This additional build tag is required due to the non-standard include and library file locations.

    Relates-To: #26

  • Doesn't work in Go 1.6

    Doesn't work in Go 1.6

    I try to compile with Go 1.6rc1. Here is compiler output:

    /usr/local/go/bin/go run -tags php7 /home/me/gocode/src/github.com/hello/world/src/embed_php7/main.go
    panic: runtime error: cgo argument has Go pointer to Go pointer
    
    goroutine 1 [running]:
    github.com/deuill/go-php/engine._cgoCheckPointer0(0x69aec0, 0xc820012500, 0x0, 0x0, 0x0, 0x0)
        ??:0 +0x4d
    github.com/deuill/go-php/engine.NewContext(0xc8200c0000, 0x0, 0x0)
        /home/me/gocode/src/github.com/deuill/go-php/engine/context.go:45 +0x152
    github.com/deuill/go-php/engine.(*Engine).NewContext(0xc820016f60, 0x0, 0x0, 0x0)
        /home/me/gocode/src/github.com/deuill/go-php/engine/engine.go:53 +0x2e
    main.main()
        /home/me/gocode/src/github.com/hello/world/src/embed_php7/main.go:10 +0x36
    exit status 2
    
  • Status of the project?

    Status of the project?

    There does not seem to be any updates since 2018? Is it still maintained?

    There is now PHP 8 out. PHP 7 achieved end of life. PHP 5 is probably not something which needs to be supported anymore. Would removing support for PHP 5 allow code cleanup and easier support for ZTS?

  • Compilation Error

    Compilation Error

    go:11:23: fatal error: main/php.h: No such file or directory // #include <main/php.h> ^ compilation terminated.

    OS -> windows 10.

    i don't know how to fix it.

  • would this package profit from this?

    would this package profit from this?

    Hello @deuill,

    would this package profit from https://github.com/basvanbeek/embed2-sapi ?

    Its not php7 but i think it would make it easy to use for concurrency php... with some trweaks.

    Regards, Josef

  • warning

    warning

    engine.c:43:10: warning: enumeration values 'SAPI_HEADER_DELETE_ALL' and 'SAPI_HEADER_SET_STATUS' not handled in switch [-Wswitch]
    engine.c:43:10: note: add missing switch cases
    # github.com/deuill/go-php
    receiver.c:79:1: warning: control reaches end of non-void function [-Wreturn-type]
    # github.com/deuill/go-php
    value.c:121:47: warning: incompatible pointer types passing 'unsigned long *' to parameter of type 'zend_ulong *' (aka 'unsigned long long *') [-Wincompatible-pointer-types]
    src/github.com/deuill/go-php/include/php7/_value.h:14:87: note: passing argument to parameter 'num_index' here
    /private/var/folders/w6/qc4d3cs57tb1zmnq81d91b_40000gn/T/___go_build_embed_go_darwin #gosetup
    Hello World[Mon Oct  8 14:54:30 2018]  Script:  '-'
    Zend/zend_string.h(122) :  Freeing 0x0000000009a01820 (40 bytes), script=-
    Last leak repeated 1 time
    === Total 2 memory leaks detected ===
    
  • Fix error logging with default engine configuration

    Fix error logging with default engine configuration

    By default, configuration values for log_errors and display_errors depend on how PHP has been configured, and need to be made consistent in order for functionality to conform to expectations.

    Additionally, the list of errors handled has been expanded to E_ALL instead of whatever the default value is.

T# Programming Language. Something like Porth, Forth but written in Go. Stack-oriented programming language.

The T# Programming Language WARNING! THIS LANGUAGE IS A WORK IN PROGRESS! ANYTHING CAN CHANGE AT ANY MOMENT WITHOUT ANY NOTICE! Something like Forth a

Jun 29, 2022
Yayx programming language is begginer friendly programming language.
Yayx programming language is begginer friendly programming language.

Yayx Yayx programming language is begginer friendly programming language. What have yayx: Easy syntax Dynamic types Can be compiled to outhers program

Dec 27, 2021
Yayx programming language is begginer friendly programming language.

Yayx Yayx programming language is begginer friendly programming language. What have yayx: Easy syntax Dynamic types Can be compiled to outhers program

May 20, 2022
This package is built for Embedding PHP into Golang.

GoEmPHP This package is built for Embedding PHP into Golang. It is easy to use: script = php.New() script.Startup() defer script.Close()

Jul 2, 2022
Gentee - script programming language for automation. It uses VM and compiler written in Go (Golang).

Gentee script programming language Gentee is a free open source script programming language. The Gentee programming language is designed to create scr

Dec 15, 2022
ReCT-Go-Compiler - A compiler for the ReCT programming language written in Golang

ReCT-Go-Compiler A compiler for the ReCT programming language written in Golang

Nov 30, 2022
ReCT-Go-Compiler - A compiler for the ReCT programming language written in Golang

ReCT-Go-Compiler A compiler for the ReCT programming language written in Golang

Nov 30, 2022
WindLang, A simple programming language built with golang 🍃
WindLang, A simple programming language built with golang 🍃

WindLang, A simple programming language built with golang ?? WindLang, A simple programming language built with golang ?? What is wind? Playground Coo

Dec 1, 2022
a dynamically typed, garbage collected, embeddable programming language built with Go

The agora programming language Agora is a dynamically typed, garbage collected, embeddable programming language. It is built with the Go programming l

Dec 30, 2022
Port of the lemon parser generator to the Go programming language

From the golang-nuts mailing list (with few modifications): --== intro ==-- Hi. I just want to announce a simple port of the lemon parser generator

Feb 17, 2022
An LL(1) parser generator for the Go programming language.

What is it? I have implemented an LL(1) parser generator for the Go programming language. I did this to build parse trees for my HAML parser. You can

Jan 18, 2022
The Slick programming language is an s-expression surface syntax for Go.

The Slick programming language The Slick programming language is a Lisp/Scheme-style s-expression surface syntax for the Go programming language, with

Jan 8, 2023
Pineapple Lang is a simple programming language demo implements by Go

Pineapple Lang is a simple programming language demo implements by Go. It includes a hand-written recursive descent parser and a simple interpreter, although the language is not even Turing-complete. But this repo's main goal is to give beginners of compilation principles a warm up and a simple look at how a programming language is built.

Dec 26, 2022
⛳ A minimal programming language inspired by Ink, JavaScript, and Python.

⛳ Golfcart My blog post: Creating the Golfcart Programming Language Getting Started Scope Rules Usage Building and tests Contributions License Golfcar

Sep 6, 2022
Simple, safe and compiled programming language.

The X Programming Language Simple, safe and compiled programming language. Table of Contents Overview OS Support Contributing License Overview The X p

Dec 28, 2022
A interpreter of SweetLang, is writed in Go Programming language.

SweetLang ( Soon ) A interpreter of SweetLang, is writed in Go Programming language. SweetLang is made with clarity and simplicity we try to make its

Oct 31, 2021
Monkey programming language project from 'Writing An Interpreter In Go'and 'Writing A Compiler In Go' Books
Monkey programming language project from 'Writing An Interpreter In Go'and 'Writing A Compiler In Go' Books

Monkey Monkey programming language ?? project from "Writing An Interpreter In Go

Dec 16, 2021
Go bindings for Lua C API - in progress

Go Bindings for the lua C API Simplest way to install: # go get github.com/aarzilli/golua/lua You can then try to run the examples: $ cd golua/_examp

Dec 28, 2022
naive go bindings to the CPython C-API

go-python Naive go bindings towards the C-API of CPython-2. this package provides a go package named "python" under which most of the PyXYZ functions

Dec 30, 2022