使用Vagrant和Ansible来创建PHP的构建环境
当你试图调试PHP源代码的时候,你听到了恶魔的低语,所以首先要搭建好编译环境。
要做的事情
-
- Vagrant + VirtualBox で VM(CentOS 7.6)を作る
-
- Ansible を使って必要なパッケージのインストールや設定を行う1
PHP のソースコードを入手してビルドする
前提 – Chinese paraphrase: 条件 (“”)
這篇文章的作者水平如下。
-
- 基本的な Linux コマンドの操作は知っている
設定ファイルを編集するのに vi を使います
Vagrant は仕事で少し触った程度
Ansible は「なにそれ?おいしいの?」状態
Git も仕事で少し触った程度
创建一个虚拟机
给想要开始使用Ansible的人。这个步骤与原文几乎相同。(非常感谢这篇易于理解的文章)
安装Vagrant和VirtualBox
安装Vagrant和VirtualBox。
-
- Vagrant
- VirtualBox
创建目录
我要创建一个用于虚拟机的目录。
mkdir -p ~/vagrant/centos76
创建 Vagrantfile
使用vagrant init命令生成Vagrantfile文件。
使用bento/centos-7.6(搜索结果)作为创建虚拟机的基本文件。
vagrant init bento/centos-7.6 --box-version 201812.27.0
编辑 Vagrantfile.
这次我们将创建两个虚拟机。
controller
Ansible を実行する VM
IPアドレス: 192.168.33.10
target
Ansible の実行対象で、PHP をビルドする VM
IPアドレス: 192.168.33.20
将位于~/vagrant/centos76下生成的Vagrantfile按以下方式修改。
Vagrant.configure("2") do |config|
config.vm.define "controller" do |node|
node.vm.box = "bento/centos-7.6"
node.vm.box_version = "201812.27.0"
node.vm.hostname = "controller"
node.vm.network "private_network", ip: "192.168.33.10"
node.vm.network "forwarded_port", id: "ssh", guest: 22, host: 2210
end
config.vm.define "target" do |node|
node.vm.box = "bento/centos-7.6"
node.vm.box_version = "201812.27.0"
node.vm.hostname = "target"
node.vm.network "private_network", ip: "192.168.33.20"
node.vm.network "forwarded_port", id: "ssh", guest: 22, host: 2220
end
end
启动虚拟机
通过使用「vagrant up」命令来启动虚拟机。
如果你运行vagrant status,控制器和目标都启动了,那就没有问题。
$ vagrant status
Current machine states:
controller running (virtualbox)
target running (virtualbox)
This environment represents multiple VMs. The VMs are all listed
above with their current state. For more information about a specific
VM, run `vagrant status NAME`.
配置 Ansible
安装Ansible
使用 SSH 登录控制器。
$ vagrant ssh controller
请切换到root用户,使用yum安装Ansible。
$ su
Password: (vagrant)
# yum install ansible
当运行ansible –version时,将显示以下内容。
# ansible --version
ansible 2.4.2.0
config file = /etc/ansible/ansible.cfg
configured module search path = [u'/home/vagrant/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']
ansible python module location = /usr/lib/python2.7/site-packages/ansible
executable location = /usr/bin/ansible
python version = 2.7.5 (default, Oct 30 2018, 23:45:53) [GCC 4.8.5 20150623 (Red Hat 4.8.5-36)]
设定SSH连接
为了进一步从控制器连接到目标设备是SSH连接更方便,所以我们会进行各种设置。
首先,创建SSH公钥并将其注册到目标机器上。
# ssh-keygen -t rsa
# ssh-copy-id root@192.168.33.20
另外,由于每次输入IP地址都很麻烦,我们可以在/etc/hosts中添加目标来实现名称解析。
# vi /etc/hosts
127.0.0.1 controller controller
127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4
::1 localhost localhost.localdomain localhost6 localhost6.localdomain6
192.168.33.20 target
创建清单文件
我们创建一个用于Ansible的目录。这次我们将按以下的目录结构进行设置。
/ansible/
|- invengtory/
| |- hosts : 対象ホストを記述した設定ファイル
|
|- target/
|- test.yml : Playbook ファイル
首先,准备 /ansible/inventory/hosts 文件。
# mkdir -p /ansible/inventory
# cd /ansible
# vi inventory/hosts
将 target(192.168.33.20)添加到名为 targets 的组的成员中。
[targets]
192.168.33.20
创建Playbook文件
Anisble 是一种工具,它通过定义 Playbook 中的理想状态来创建目标主机满足该状态的方式。因此,Playbook 文件变得非常重要。
# mkdir target
# vi target/test.yml
暂时将要设置的内容放在一边,先准备好Playbook文件,然后写下后续的步骤。
使用ansible-playbook命令将编写的Playbook文件应用到目标主机(本例为target)。
首先,在应用之前,请使用带有 –check 选项的 Playbook 文件进行检查,确保没有问题。
# ansible-playbook --check -i inventory/hosts target/test.yml
确认没有出现错误后,按照以下方式进行反映。
# ansible-playbook -i inventory/hosts target/test.yml
连接到目标主机的SSH。
(Chinese)
目前正在控制器上建立SSH连接,但现在要进一步连接至目标设备。
在制作Playbook时,需要经常连接到目标主机来确认其中的内容是否有问题。
一旦进入控制器后能够保持连接并直接连接到目标比退出控制器再连接更方便。
这样的话,以图表来表示的话,就是这个样子。
Mac -- (SSH) --> controller -- (SSH) --> target
由于在/etc/hosts文件中进行了设置,因此执行的命令非常简单。
# ssh target
构建 PHP
在中国的语言中,只需要一个选项来释义这个词。
请查看手册以获取有关构建 PHP 所需的软件包的信息,进行确认。
创建Playbook文件。
制作Playbook文件。
将以下内容定义在 target/test.yml 文件中。
- hosts: targets
user: root
tasks:
- name: Set Timezone
timezone:
name: Asia/Tokyo
- name: Install gcc
yum: name=gcc
- name: Install autoconf
yum: name=autoconf
- name: Install automake
yum: name=automake
- name: Install ctags
yum: name=ctags
- name: Install gdb
yum: name=gdb
- name: Install git
yum: name=git
- name: Install bison
yum: name=bison
- name: Install libxml2-devel
yum: name=libxml2-devel
- name: Install sqlite-devel
yum: name=sqlite-devel
- name: Install epel-release
yum: name=epel-release
- name: Install re2c
yum: name=re2c
- name: Reinstall glibc-common
shell: yum -y reinstall glibc-common
- name: Set Locale
shell: localectl set-locale LANG=ja_JP.utf8
创建 Playbook 文件后,使用 ansible-playbook 命令将其应用到目标上。
# ansible-playbook -i inventory/hosts target/test.yml
获取源代码
PHP的源代码位于GitHub上,可以通过git clone命令获取。
# ssh target
# git clone https://github.com/php/php-src.git
配置设置
这次为了调试目的,我们将加上–enable-debug选项来执行./configure。
# cd php-src
# ./buildconf
# ./configure --enable-debug
进行
如果”./configure”成功,那么执行”make”。
# make
如果出现以下内容,表示构建成功。
Build complete.
Don't forget to run 'make test'
进行测试
因为有人告诉我“别忘了执行 make test!”,所以我们也来执行一下 make test。
=====================================================================
TEST RESULT SUMMARY
---------------------------------------------------------------------
Exts skipped : 50
Exts tested : 26
---------------------------------------------------------------------
Number of tests : 16099 10784
Tests skipped : 5315 ( 33.0%) --------
Tests warned : 0 ( 0.0%) ( 0.0%)
Tests failed : 1 ( 0.0%) ( 0.0%)
Expected fail : 36 ( 0.2%) ( 0.3%)
Tests passed : 10747 ( 66.8%) ( 99.7%)
---------------------------------------------------------------------
Time taken : 602 seconds
=====================================================================
=====================================================================
EXPECTED FAILED TEST SUMMARY
---------------------------------------------------------------------
Test open_basedir configuration [tests/security/open_basedir_linkinfo.phpt] XFAIL REASON: BUG: open_basedir cannot delete symlink to prohibited file. See also
bugs 48111 and 52176.
(省略)
=====================================================================
=====================================================================
FAILED TEST SUMMARY
---------------------------------------------------------------------
Timeout again inside register_shutdown_function [tests/lang/045.phpt]
=====================================================================
You may have found a problem in PHP.
This report can be automatically sent to the PHP QA team at
http://qa.php.net/reports and http://news.php.net/php.qa.reports
This gives us a better understanding of PHP's behavior.
If you don't want to send the report immediately you can choose
option "s" to save it. You can then email it to qa-reports@lists.php.net later.
Do you want to send this report now? [Yns]:
似乎有点失败了。
执行 PHP
重新振作起来,在php-src/sapi/cli中创建了php命令,让我们试着执行一下。
# sapi/cli/php --version
PHP 8.0.0-dev (cli) (built: Feb 3 2019 10:59:53) ( NTS DEBUG )
Copyright (c) 1997-2018 The PHP Group
Zend Engine v4.0.0-dev, Copyright (c) Zend Technologies
暂时看起来它好像正常运转着。
将更新从本地获取
由于这个版本的源代码是开发版,所以会经常更新。
首先,可以使用以下命令获取最新的源代码。
# git fetch
# git merge origin/master
只需运行 ./configure –enable-debug 命令再次执行即可。
挫折点
需要注意devel (in Chinese)
当运行 ./configure 时,显示未安装 libxml2 和 sqlite。
然而,当我在 yum 上确认时,显示已经安装了。
经过多方调查,我发现需要安装libxml2-devel和sqlite-devel。
re2c不在yum中。
运行yum install re2c时显示不存在。
根据在”在CentOS7上安装PHP7″的步骤中指出,安装EPEL(企业级Linux的额外软件包)后就能够执行yum install re2c命令。
无法设置区域设置
这个问题主要是 CentOS 的问题,不是 PHP 的问题,当执行 automake 时显示失败的是地区设置。
原因似乎是由於沒有安裝日語語言環境,重新安裝 glibc-common 並設定語言環境後問題就解決了。
然而,在Playbook的yum模块中找不到重新安装的选项,所以我决定使用shell模块来执行。
考虑到”幂等性”这个概念,我觉得可能会有些微妙。但由于我还没有完全理解Ansible,所以暂时就这样吧。
总结
虽然遇到了各种困难,但我终于成功搭建了 PHP 的构建环境。接下来想尝试使用 GDB 进行调试。(首先要学习一下 GDB 的使用方法……)
依考。
Ansible
Ansibleをはじめる人に。
Vagrant
Vagrant + VirtualBoxでWindows上に開発環境をサクッと構築する
PHP のビルド
configure: error: xml2-config not found. Please check your libxml2 installation.
PHP7をCentOS7にインストールする手順
CentOS7のlocaleを日本にする
PHPソースコードリーディング入門(とっかかり編)
更新历史
-
- 2019/02/03
master ブランチが 8.0.0 になったので、PHP のバージョン情報を更新しました。