php使用thrift操作hdfs

假定主机上已经安装了LAMP环境


1. 安装所需的依赖包

  也可以参考thift官网来安装 http://thrift.apache.org/docs/install/centos

  #yum install automake libtool flex bison pkgconfig gcc-c++ boost-devel libevent-devel zlib-devel python-devel ruby-devel php php-devel

2. 从http://thrift.apache.org/download/下载thrift源码包

3. 安装thrift

    ./configure --with-lua=no –prefix=/usr/local/thrift

(可能出现的错误  bison版本不够,升级bison2.5.*)

    make && make install

4. 安装php扩展

    cd /path/to/thrift-0.8.0/lib/php/src/ext/thrift_protocol

    phpize

    ./configure -enable-thrift_protocol -with-php-config=/usr/bin/php

    make

    make install

    修改php.ini,添加extension=thrift_protocol.so

5. 从http://hadoop.apache.org/releases.html#Download下载hadoop源码包

6. 解压并编译hadoop(注意必须先安装好java编译器,ant编译环境,以及libtool, autoconf等工具)

    tar zxvf hadoop-1.0.4.tar.gz

    cd hadoop-1.0.4

    ant compile

7. 启动hdfs以及thrift代理(hdfs集群配置请参考官方文档,不再累述)

    cd /path/to/hadoop-1.0.4

    bin/start-dfs.sh

     cd /path/to/hadoop-1.0.4/src/contrib/thriftfs/scripts/

     ./start_thrift_server.sh [port] (如果port为空,则随机一个port)

8. 准备php依赖库

    cp -r /path/to/thrift-0.8.0/lib/php  /usr/local/thrift/lib

    mkdir -p /usr/local/thrift/lib/php/src/packages

    cp -r /path/to/hadoop-1.0.4/src/contrib/thriftfs/gen-php/ /usr/local/thrift/lib/php/src/packages/hadoopfs/

9. php测试代码

<?php

error_reporting(E_ALL);
ini_set('display_errors', 'on');

$GLOBALS['THRIFT_ROOT'] = '/usr/local/thrift/lib/php/src';
define('THRIFT_ROOT', $GLOBALS['THRIFT_ROOT']);

/**
 * Init Autloader
*/
require_once THRIFT_ROOT . '/Thrift.php';
require_once THRIFT_ROOT . '/transport/TSocket.php';
require_once THRIFT_ROOT . '/transport/TBufferedTransport.php';
require_once THRIFT_ROOT . '/protocol/TBinaryProtocol.php';

$socket = new TSocket('192.168.1.12', 11511);
$socket->setSendTimeout(10000);
$socket->setRecvTimeout(20000);
$transport = new TBufferedTransport($socket);
$protocol = new TBinaryProtocol($transport);

require_once $THRIFT_ROOT . '/packages/hadoopfs/ThriftHadoopFileSystem.php';
$client = new ThriftHadoopFileSystemClient($protocol);

$transport->open();
try{

#$pathname = new Pathname(array('pathname' => '/user/hadoop/dir4test'));

#$fp = $client->open($pathname);

#var_dump($client->stat($pathname));

#var_dump($client->read($fp, 0, 1024));



$pathname = new Pathname(array('pathname' => '/user/hadoop/thrift'));

if(!$client->exists($pathname)){


$client->mkdirs($pathname);


print("Created dir". $pathname->pathname);


var_dump($client->stat($pathname));

}
}
catch(Exception $ex){

print_r($ex);
}
$transport->close();
?> 

thrift接口文件位于/src/contrib/thriftfs/if/hadoopfs.thrift,启动thrift服务的脚本位于/usr/local/hadoop/src/contrib/thriftfs/scripts/start_thrift_server.sh,PHP语言文件位于/usr/local/hadoop/src/contrib/thriftfs/gen-php,包括hadoopfs_types.php  ThriftHadoopFileSystem.php两个文件。
hadoopfs.thrift,包括4个结构,2个异常,19个service函数。以下将分别介绍结构和函数。

开启thrift sever的脚本如下(当然,首先应启动hadoop):

启动start_thrift_server.sh时可以指定启动端口 eg:sh start_thrift_server.sh 48566  不指定则随机分配

启动start_thrift_server.sh时报错为hadoop环境配置错误
Exception in thread “main” java.lang.NoClassDefFoundError: org/apache/ hadoop/conf/Configuration

解决方法,将Hadoop的classpath加到环境变量中,如:
export CLASSPATH=$HADOOP_HOME"hadoop-core-1.0.4.jar"

或者直接在/etc/profile里面加上变量的路径  然后执行source /etc/profile让其修改生效

如果不写端口,则侦听端口是随机的,无论哪种情况,注意一下启动的输出,其中有端口号。


补充:

单机状态测试时 本机必须同时安装hadoop环境和thrift

联机状态使用时 server机安装hadoop环境和thrift  php项目所在的客户机也要安装thrift
server机启动thrift服务 (sh start_thrift_server.sh 48566)
客户端机器链接时  socket(ip=server机ip,port=48566,……)

联机操作时自己遇见的问题,测试机执行时一切正常,但是联机时却老是报错
exception 'TTransportException' with message 'TSocket read 0 bytes' in /root/thrift/lib/php/src/transport/TSocket.php:263
问题:最后发现是因为客户端机器是32位系统,文件句柄id较长,32位机器溢出,致使write时找不到正确的文件句柄
解决:迁移64位机器后一切正常

接口结构,如下:

  • ThriftHandle:这个东西相当于文件句柄
  • Pathname:文件路径
  • FileStatus :实际上是文件的各种属性,包括名称、长度、文件/目录、块复制数、块大小,权限属性等。
  • BlockLocation :文件块的属性,包括位置属性,该块在文件中的偏移量,大小等。

接口service函数如下(本文thrift采用的是0.8.0):

  • setInactivityTimeoutPeriod:设置超时时间(s),如果超过此时间,服务器断开。
  • shutdown:断开与服务器的连接
  • create、createFile:这两个是创建文件,并输出文件句柄供写入,后一个函数提供了更多的文件属性参数来控制文件的创建。
  • open:以读写方式打开一个已存在的文件,输出文件句柄供操作。
  • append:以添加方式打开一个已存在的文件,输出为文件句柄。
  • write:向已打开的文件写入数据,返回是否成功。
  • read:向已打开的文件读取数据,与通常文件读取一样,需指定读取位置和读取大小。
  • close:关闭文件
  • rm:删除文件或目录,可以指定是否递归删除目录
  • rename:重新命名文件或目录
  • mkdirs:创建目录
  • exists:检查文件或目录是否存在
  • stat:获取文件或目录的属性,输出的是FileStatus结构。
  • listStatus:如果输入是一个目录,则输出是目录下所有文件的FileStatus结构(数组)
  • chmod:设置文件/目录的权限
  • chown:设置文件/目录的组和所有者
  • setReplication:设置文件的复制因子(多少份)
  • getFileBlockLocations:得到文件的块的信息,输出是BlockLocation数组。

以上这些接口除了具有复制因子、块等信息外,与通常的文件操作没有什么区别,因此对它们进行再次封装似乎没有必要,除非有特殊的要求。


php操作hdfs自己用的另外一种解决方案:

在项目所在机器装hadoop的client,并且安装jdk,把hadoop需要的jar包放到此机器上,php直接exec去调用java,通过java命令去执行jar包,jar包内部执行hdfs操作


参考文章:

http://blog.csdn.net/guxch/article/details/12163519
http://blog.csdn.net/jiangheng0535/article/details/12089023

http://dongxicheng.org/search-engine/scribe-installation/
http://www.thinksaas.cn/group/topic/234079/

http://www.docin.com/p-473359851.html

http://blog.csdn.net/gs_zhaoyang/article/details/13503527
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值