quasar协程结合消息队列的游戏服务器框架——项目

需要掌握:

    基于分布式消息队列的服务器框架;

    对进程、线程、协程有概念;

    有异步开发思想。

背景:

    项目中经常有异步rpc调用,需要写回调方法,语法上看着不顺眼(有点小傲娇),想通过同步的写法实现异步操作。

研究:

   在网上找了一下java的协程框架,主要有quasar、kilim两种,还有一些协程插件(同事以前项目用过,有一些坑),主要研究了一下quasar,原理不讲了,网上很多。

    研究中发现其实协程并不适合有状态的消息队列模式(或者我没想到解法),个人感觉比较适合平行执行多个相同逻辑的框架,比如web项目线程池结构,可以做成协程池,当协程执行数据库等IO阻塞操作的时候,就可以让出CPU给别的协程,性能提升的例子网上也有很多。

    就我做的项目结构而言,预计会增加性能开销,换来的是语法的便捷。

环境配置

    maven环境

 
                org.apache.maven.plugins
                maven-compiler-plugin
                
                    8
                    8
                
            
            
                com.vlkan
                quasar-maven-plugin
                0.7.3
                
                    true
                    true
                    true
                
                
                    
                        compile
                        
                            instrument
                        
                    
                
            

 

  
            co.paralleluniverse
            quasar-core
            0.8.0
        

    启动jvm参数,-javaagent:path_to_quasar-core-0.8.0.jar,path_to_quasar-core-0.8.0.jar为在本地的的jar包路径,别无脑复制。

代码准备

    先看一个网上的例子

    

public class QuasarIncreasingEchoApp {
    static public Integer doAll() throws ExecutionException, InterruptedException {
        final IntChannel increasingToEcho = Channels.newIntChannel(0); // Synchronizing channel (buffer = 0)
        final IntChannel echoToIncreasing = Channels.newIntChannel(0); // Synchronizing channel (buffer = 0)
        final Channel channel = Channels.newChannel(0);

        Fiber increasing = new Fiber<>("INCREASER", new SuspendableCallable() { @Override public Integer run() throws SuspendExecution, InterruptedException {
            ////// The following is enough to test instrumentation of synchronizing methods
            // synchronized(new Object()) {}

            int curr = 0;
            for (int i = 0; i < 10 ; i++) {
                Fiber.sleep(10);
                System.out.println("INCREASER sending: " + curr);
                increasingToEcho.send(curr);
                curr = echoToIncreasing.receive();
                System.out.println("INCREASER received: " + curr);
                curr++;
                System.out.println("INCREASER now: " + curr);
            }
            System.out.println("INCREASER closing channel and exiting");
            increasingToEcho.close();
            return curr;
        } }).start();

        Fiber echo = new Fiber("ECHO", new SuspendableRunnable() { @Override public void run() throws SuspendExecution, InterruptedException {
            Integer curr;
            while (true) {
                Fiber.sleep(1000);
                curr = increasingToEcho.receive();
                System.out.println("ECHO received: " + curr);

                if (curr != null) {
                    System.out.println("ECHO sending: " + curr);
                    echoToIncreasing.send(curr);
                } else {
                    System.out.println("ECHO detected closed channel, closing and exiting");
                    echoToIncreasing.close();
                    return;
                }
            }
        } }).start();

        try {
            increasing.join();
            echo.join();
        } catch (ExecutionException e) {
            e.printStackTrace();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }

        return increasing.get();
    }

    static public void main(String[] args) throws ExecutionException, InterruptedException {
        System.out.println(doAll());
    }

输出结果为

INCREASER sending: 0
ECHO received: 0
ECHO sending: 0
INCREASER received: 0
INCREASER now: 1
INCREASER sending: 1
ECHO received: 1
ECHO sending: 1
INCREASER received: 1
INCREASER now: 2
INCREASER sending: 2
ECHO received: 2
ECHO sending: 2
INCREASER received: 2
INCREASER now: 3
INCREASER sending: 3
ECHO received: 3
ECHO sending: 3
INCREASER received: 3
INCREASER now: 4
INCREASER sending: 4
ECHO received: 4
ECHO sending: 4
…………

    协程内是阻塞的,但是协程阻塞不会影响该线程下的其他线程,线程的sleep也不会影响协程的运行。

    项目中的类

    进程类:Process,内含Map,一个进程包含多个线程,主线程

    线程类:Thread,内含Map,一个线程包含多个服务,真实线程

    服务类:Service,逻辑模块单元,根据需求划分服务

    协程类:

    

你可能感兴趣的:(java服务器,协程,java,协程,quasar)