在上一篇博客中,安装好Gearman和php客户端后,现在尝试下跨语言通信。
注:Gearman最强悍的地方就是它可以支持不同语言直接的交互,client端是一种语言,worker端可以是另外一种语言!中间的交互具体转化细节都封装在jobserver中处理。
这里演示的例子是:官网上面的字符串反转。
worker.php + client.java或
worker.java + client.php
1. 环境:JDK1.7.0_25
所需jar包:java-gearman-service-0.6.6.jar, slf4j-api-1.6.4.jar, slf4j-simple-1.6.4.jar。可以直接到网上去下载。
2.代码:
Java语言
client端代码:
package com.gearman.demo;
import org.gearman.Gearman;
import org.gearman.GearmanClient;
import org.gearman.GearmanJobEvent;
import org.gearman.GearmanJobReturn;
import org.gearman.GearmanServer;
public class EchoClient {
public static void main(String... args) throws InterruptedException {
// 创建一个Gearman实例
Gearman gearman = Gearman.createGearman();
// 创建一个Gearman client
GearmanClient client = gearman.createGearmanClient();
/*
* 创建一个jobserver
*
* Parameter 1: job server的IP地址 Parameter 2: job server监听的端口
*
* job server收到client的job,并将其分发给注册worker
*  
* ; *
*/
GearmanServer server = gearman.createGearmanServer(
EchoWorker.ECHO_HOST, EchoWorker.ECHO_PORT);
// 告诉客户端,提交工作时它可以连接到该服务器
client.addServer(server);
/*
* 向job server提交工作
*
* Parameter 1: gearman function名字 Parameter 2: 传送给job server和worker的数据
*
* GearmanJobReturn返回job发热结果
*/
GearmanJobReturn jobReturn = client.submitJob(
EchoWorker.ECHO_FUNCTION_NAME, ("Hello World!").getBytes());
// 遍历作业事件,直到我们打到最后文件
while (!jobReturn.isEOF()) {
// 下一个作业事件
GearmanJobEvent event = jobReturn.poll();
switch (event.getEventType()) {
case GEARMAN_JOB_SUCCESS: // job执行成功
System.out.println(new String(event.getData()));
break;
case GEARMAN_SUBMIT_FAIL: // job提交失败
case GEARMAN_JOB_FAIL: // job执行失败
System.err.println(event.getEventType() + ": "
+ new String(event.getData()));
default:
}
}
// 关闭
gearman.shutdown();
}
}
worker端代码:
package com.gearman.demo;
import org.gearman.Gearman;
import org.gearman.GearmanFunction;
import org.gearman.GearmanFunctionCallback;
import org.gearman.GearmanServer;
import org.gearman.GearmanWorker;
public class EchoWorker implements GearmanFunction {
// function name
public static final String ECHO_FUNCTION_NAME = "reverse";
// job server地址
public static final String ECHO_HOST = "10.10.115.23";
// job server监听的端口
public static final int ECHO_PORT = 4730;
public static void main(String... args) {
// 创建一个Gearman实例
Gearman gearman = Gearman.createGearman();
/*
* 创建一个jobserver
*
* Parameter 1: job server的IP地址 Parameter 2: job server监听的端口
*
* job server收到client的job,并将其分发给注册worker
*  
* ; *
*/
GearmanServer server = gearman.createGearmanServer(
EchoWorker.ECHO_HOST, EchoWorker.ECHO_PORT);
// 创建一个Gearman的worker
GearmanWorker worker = gearman.createGearmanWorker();
// 告诉工人如何执行工作(主要实现了GearmanFunction接口)
worker.addFunction(EchoWorker.ECHO_FUNCTION_NAME, new EchoWorker());
// worker连接服务器
worker.addServer(server);
}
@Override
public byte[] work(String function, byte[] data,
GearmanFunctionCallback callback) throws Exception {
// work方法实现了GearmanFunction接口中的work方法,本实例中进行了字符串的反写
if (data != null) {
String str = new String(data);
StringBuffer sb = new StringBuffer(str);
return sb.reverse().toString().getBytes();
} else {
return "未接收到data".getBytes();
}
}
}
*ECHO_HOST = "192.168.125.131"为安装了Gearman并开启geramand服务的主机地址
*int ECHO_PORT = 4730默认端口为4730
原因是没有对log4j这个jar进行文件配置。
将log4j.properties文件放在src目录下就可以了。
例如log4j.properties文件内容如下:
log4j.rootLogger=debug, stdout, R
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.layout=org.apache.log4j.PatternLayoutlog4j.appender.stdout.layout.ConversionPattern=%5p - %m%n
log4j.appender.R=org.apache.log4j.RollingFileAppender
log4j.appender.R.File=firestorm.log
log4j.appender.R.MaxFileSize=100KB
log4j.appender.R.MaxBackupIndex=1
log4j.appender.R.layout=org.apache.log4j.PatternLayout
log4j.appender.R.layout.ConversionPattern=%p %t %c - %m%n
log4j.logger.com.codefutures=DEBUG
如果不行,就放在class所在目录就OK了!
PHP语言
client端:
<?php
$client = new GearmanClient();
$client->addServer();
print $client->do("reverse","Hello World!");
print "\n";
?>
worker端:
<?php
$worker= new GearmanWorker();
$worker->addServer();
$worker->addFunction("reverse","my_reverse_function");
echo "Starting worker ...";
while($worker->work());
function my_reverse_function($job)
{
return strrev($job->workload());
}
?>
3.测试
注:这里我将php文件放在:/home/user/projects/ 文件夹下,另外,*.java的文件在eclipse中新建的工程里面。
前提确保gearman正确安装,并正在运行。可以参考我的上一篇博客。
测试1:worker.php + EchoClient.java
$php worker.php
然后,再在eclipse中运行:EchoClient.java
eclipse console输出结果:
INFO - [10.10.115.23:4730] : Connected
INFO - [10.10.115.23:4730] : OUT : SUBMIT_JOB
INFO - [10.10.115.23:4730] : IN : JOB_CREATED
INFO - [10.10.115.23:4730] : IN : WORK_COMPLETE
!dlroW olleH
INFO - [10.10.115.23:4730] : Disconnected
运行成功!!
测试2:EchoWorker.java + client.php
先在eclipse中运行,EchoWorker.java
然后,再在命令行下输入:php client.php
命令行下输出结果:
!dlroW olleH
运行成功!!
至此,对Gearman的初步学习完成,现在开始研究Gearman的源码!