README.md
May 11, 2026 · View on GitHub
C++ wrapper for Zend API
Requirements
- PHP 8.2 or later
- Linux/macOS/Windows
- GCC 9 or later (with C++17 support)
- Composer
Installation
Build libphpx.so
# Standard build (Release mode)
cmake .
make -j 4
sudo make install
sudo ldconfig
Debug Mode (for troubleshooting)
# Clean previous builds
cmake --build . --target clean
# Configure Debug mode (includes debug symbols and runtime checks)
cmake -DCMAKE_BUILD_TYPE=Debug .
# Compile
make -j 4
sudo make install
sudo ldconfig
Debug Mode Features:
- ✅ Generates complete debug symbols
- ✅ Disables compiler optimizations for easier debugging
- ✅ Enables runtime error checking
- ✅ More detailed compilation output
Quick Start
Create a New Extension Project
# Create extension project
composer create-project swoole/phpx-ext test
cd test
Basic Usage Example
Here's a complete example demonstrating modern PHPX extension development:
#include "phpx_ext.h"
// Include auto-generated arginfo header (generated by gen_stub.php)
BEGIN_EXTERN_C()
#include "your_extension_arginfo.h"
END_EXTERN_C()
using namespace php;
using namespace std;
// Method implementation using PHPX_METHOD macro
PHPX_METHOD(MyClass, __construct) {
// Initialize object properties
_this.set("name", args[0].toString());
_this.set("value", args[1].toInt());
return nullptr;
}
PHPX_METHOD(MyClass, greet) {
// Access object properties
auto name = _this.get("name");
auto value = _this.get("value");
// Return formatted string
return "Hello, " + name.toStdString() + "! Value: " + to_string(value.toInt());
}
PHPX_METHOD(MyClass, processData) {
// Work with Array type
Array input = args[0];
Array result;
// Iterate and transform
for (auto &item : input) {
result.append(item.value.toInt() * 2);
}
return result;
}
// Function implementation using PHPX_FUNCTION macro
PHPX_FUNCTION(my_extension_func) {
// Variant - universal type container
Variant str_var = "Hello PHPX";
Variant int_var = 42;
Variant float_var = 3.14159;
// Array operations
Array arr;
arr.set("name", "PHPX");
arr.set("version", 8.2);
arr.set("features", Array{"C++17", "Type-safe", "Modern API"});
// Object creation and method calls
Object datetime = newObject("DateTime");
auto formatted = datetime.call("format", {"Y-m-d H:i:s"});
// Facade functions - direct PHP function calls
php::var_dump(arr); // Debug output
php::print_r(datetime); // Print object
// File operations
auto content = php::file_get_contents("/etc/hosts");
if (content.isString()) {
echo("File length: ", content.length(), "\n");
}
// Array manipulation with references
Array numbers{1, 2, 3, 4, 5};
Reference ref = numbers.toReference();
php::sort(ref); // Sort array
php::array_push(ref, 6, 7, 8); // Push elements
RETURN_STRING("PHPX Demo Completed!");
}
// Extension entry point
PHPX_EXTENSION() {
Extension *ext = new Extension("my_extension", "1.0.0");
// Register lifecycle callbacks
ext->onStart = [ext]() noexcept {
// Register constants
ext->registerConstant("MY_EXT_VERSION", 10000);
// Register class with methods
Class *c = new Class("MyClass");
c->addProperty("name", "", ZEND_ACC_PUBLIC);
c->addProperty("value", 0, ZEND_ACC_PUBLIC);
c->registerFunctions(class_MyClass_methods); // From arginfo header
ext->registerClass(c);
// Register standalone functions
ext->registerFunction(PHPX_FN(my_extension_func));
};
// PHP info page configuration
ext->info({"my_extension support", "enabled"},
{
{"author", "Your Name"},
{"version", ext->version},
{"github", "https://github.com/your/repo"},
});
return ext;
}
Key Features:
- PHPX_METHOD/PHPX_FUNCTION: Modern macros for cleaner code
- Extension/Class API: Object-oriented extension registration
- Lambda callbacks: Flexible lifecycle management with
onStart,onShutdown, etc. - Type-safe wrappers:
Variant,Array,Object,Stringclasses - Facade functions: Direct PHP function calls via
php::namespace - Auto-generated arginfo: Use
gen_stub.phpto generate type information
Generate ArgInfo & Function Entries
php vendor/swoole/phpx/bin/gen_stub.php your_stub_dir
Build Your Extension
cd test
cmake .
make -j 4
make install
Load Your Extension
Edit php.ini and add:
extension=test.so
Test Your Extension
Create a test file test.php:
<?php
echo hello_world() . "\n";
?>
Run it:
php test.php
Expected output:
Hello, World!
Advanced Usage
1. Variant Type Usage
Variant is a universal type container that can hold any PHP value:
#include "phpx.h"
using namespace php;
// Create variants of different types
Variant str_var = "Hello PHPX";
Variant int_var = 42;
Variant float_var = 3.14159;
Variant bool_var = true;
Variant null_var;
// Type checking
if (str_var.isString()) {
echo("String: ", str_var.toCString());
}
if (int_var.isInt()) {
echo("Integer: ", int_var.toInt());
}
// Type conversion
auto str = int_var.toString(); // Convert to string
auto num = str_var.toInt(); // Convert to integer (0 if not numeric)
// Comparison
if (str_var.equals("Hello PHPX")) {
echo("Match!");
}
// Serialization
Variant serialized = str_var.serialize();
Variant unserialized = serialized.unserialize();
2. Array Type Usage
Array provides a C++ wrapper for PHP arrays with rich functionality:
#include "phpx.h"
using namespace php;
// Create arrays
Array arr;
arr.set("name", "PHPX");
arr.set("version", 8.2);
arr.set("features", Array{"C++17", "Type-safe", "Modern API"});
// Initialize with list
Array numbers{1, 2, 3, 4, 5};
Array map{{"key1", "value1"}, {"key2", "value2"}};
// Access elements
auto name = arr.get("name");
auto first = numbers[0];
// Check existence
if (arr.exists("name")) {
echo("Name exists");
}
// Iterate array
for (auto &item : arr) {
echo(item.key, ": ", item.value, "\n");
}
// Array operations
arr.append("new_element"); // Add element
arr.del("name"); // Remove element
auto count = arr.count(); // Get count
auto keys = arr.keys(); // Get all keys
// Nested arrays
Array nested;
nested.set("level1", Array{
{"level2", Array{"deep_value"}}
});
auto deep = nested.item("level1").item("level2");
// Reference for modification
Array nums{5, 2, 8, 1, 9};
Reference ref = nums.toReference();
php::sort(ref); // Sort in place
php::array_push(ref, 10, 11); // Push elements
3. Object Type Usage
Object wraps PHP objects and provides method calling capabilities:
#include "phpx.h"
using namespace php;
// Create object
Object datetime = newObject("DateTime");
// Call methods
auto formatted = datetime.call("format", {"Y-m-d H:i:s"});
echo("Current time: ", formatted.toCString());
// Set properties
Object stdclass = newObject("stdClass");
stdclass.set("name", "test");
stdclass.set("value", 42);
// Get properties
auto name = stdclass.get("name");
auto value = stdclass.get("value");
// Check property existence
if (stdclass.exists("name")) {
echo("Property exists");
}
// Create object with constructor arguments
Object arrayObj = newObject("ArrayObject", {
Array{1, 2, 3, 4, 5}
});
// Call method and get result
auto count = arrayObj.call("count");
echo("Count: ", count.toInt());
// Static method calls
auto result = Object::callStatic("DateTime", "createFromFormat", {
"Y-m-d", "2024-01-01"
});
4. Facade Encapsulation API
PHPX provides facade functions in the php:: namespace for direct PHP function calls:
#include "phpx.h"
#include "phpx_func.h"
using namespace php;
// Debug and output
php::var_dump(some_variable); // Debug output
php::print_r(some_variable); // Print readable
php::echo("Hello", " ", "World"); // Echo strings
// File operations
auto content = php::file_get_contents("/path/to/file.txt");
php::file_put_contents("/path/to/file.txt", "content");
// Array manipulation (requires reference)
Array arr{5, 2, 8, 1, 9};
Reference ref = arr.toReference();
php::sort(ref); // Sort array
php::rsort(ref); // Reverse sort
php::shuffle(ref); // Shuffle
php::array_push(ref, 10, 11); // Push elements
php::array_pop(ref); // Pop element
php::array_shift(ref); // Shift element
php::array_unshift(ref, 0); // Unshift element
// String operations
auto upper = php::strtoupper("hello");
auto lower = php::strtolower("HELLO");
auto length = php::strlen("hello");
auto pos = php::strpos("hello world", "world");
// Math operations
auto max_val = php::max({1, 2, 3, 4, 5});
auto min_val = php::min({1, 2, 3, 4, 5});
auto sum = php::array_sum(Array{1, 2, 3, 4, 5});
auto rand_val = php::rand(1, 100);
// JSON operations
Array data{{"name", "PHPX"}, {"version", 8.2}};
auto json_str = php::json_encode(data);
auto decoded = php::json_decode(json_str, true);
// Other useful functions
php::sleep(2); // Sleep 2 seconds
auto time = php::time(); // Current timestamp
auto date = php::date("Y-m-d H:i:s"); // Formatted date
5. Built-in Class Facade Encapsulation
PHPX provides facade classes for popular PHP extensions:
#include "phpx.h"
#include "phpx_class.h"
using namespace php;
// Redis example
Redis redis{};
redis.connect("127.0.0.1", 6379);
// String operations
redis.set("name", "PHPX");
redis.set("version", "8.2");
auto name = redis.get("name");
echo("Name: ", name.toCString());
// Check existence
if (redis.exists("name")) {
echo("Key exists");
}
// Multiple operations
redis.mset({
{"key1", "value1"},
{"key2", "value2"},
{"key3", "value3"}
});
auto values = redis.mget({"key1", "key2", "key3"});
// List operations
redis.rpush("mylist", "item1");
redis.rpush("mylist", "item2");
auto list_len = redis.llen("mylist");
// Hash operations
redis.hset("user:1", "name", "John");
redis.hset("user:1", "email", "john@example.com");
auto user_name = redis.hget("user:1", "name");
// Set expiration
redis.expire("name", 3600); // Expire in 1 hour
// Delete keys
redis.del("key1", "key2");
// Close connection
redis.close();
Note: To use Redis facade, ensure the Redis extension is loaded in your PHP environment.
Documentation
For more detailed documentation, please check:
Examples
Check out the examples directory for more comprehensive examples including:
- Bloom filter implementation
- Queue data structure
- RocksDB integration
- GTK application
- And more!
Language
License
PHPX is open-sourced software licensed under the Apache License 2.0.