Node.js调用java之node-java

0、前言

        故事的起源是这样:项目中用ioredis封装的模块,在定时、大数据量写入redis的情况下,内存激增,如果不是我对ioredis使用姿势有问题的话,那么就是在这种苛刻的情况下,node招架不住了,然后自然想到了jedis,官方推荐的redis的java客户端,大厂、线上都在大量使用,生态也非常的好。对于我们要在node中调用java,则基本需求是(1)、java封装接口,到处jar,node调用jar中的接口,传参拿值;(2)另一种比较少用,因为通用性不强,node中chilld_process运行jar包,当然jar中需要有java主函数,然后就在另一个线程中运行起来了,就没node什么事情了。本文主要讲的是第一种需求,因为这才是通用的使用方法。

1、环境搭建

  nodejs基本环境是自然的了。

(1)安装java(jdk、jre),自行百度,并配置环境变量;

(2)安装python2版本;

(3)全局安装node-gyp;

npm/cnpm i -g node-gyp

(4)全局安装window-build-tools;(由于下载下来的模块需要编译,所以需要这个工具,如果你本身安装了vs,就不需要这个东西,能自动检测到)

npm i --g --production windows-build-tools 

(4)安装node-java模块;

   虽然叫node-java,但模块本身是java

cnpm i java

         如果(1)~(3)你都配置好了,然后在vscode中运行npm i java时还是出错的话,良好的建议,打开控制台运行,vscode可能存在一些权限问题,至少我遇见过这样的事情,然后按照这种方法就成功了。

2、导出jar包

          我使用的时idea,其实各种ide都一个样,都能搞,这里说一下基本步骤:

        (1)创建一个java project

(2) 导入相关jar包(Jedis为例)

新建一个jar文件夹,将jars放进去,然后导入项目;

导入jar,点击项目结构进入

然后选择刚刚放置好的jars,点击勾选,确认即可

 然后可以开发接口了,这里简单一个写入redis的接口

package com.company;

import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
import redis.clients.jedis.JedisPoolConfig;
import redis.clients.jedis.Pipeline;

public class JedisTool {
    private Pipeline pl = null;
    private JedisPoolConfig poolConfig = null;
    private Jedis jr = null;
    private JedisPool jedisPool = null;

    public void initJedis() {
        this.poolConfig = new JedisPoolConfig();
        // 最大连接数
        this.poolConfig.setMaxTotal(4);
        // 最大空闲数
        this.poolConfig.setMaxIdle(1);
        // 最大允许等待时间
        this.poolConfig.setMaxWaitMillis(2000);
        //获得连接池
        this.jedisPool = new JedisPool(poolConfig,"127.0.0.1",6379);

        this.jr = this.jedisPool.getResource();

        this.pl = this.jr.pipelined();
    }

    public void usePipeline(int count) {
        try{
            for(int i=0;i<count;i++) {
                this.pl.set("abcdefgh" + Integer.toString(i), "abcdefghijklmnopqrstuvwxyzabcdefghijklmnopqrstuvwxyzabcdefghijklmnopqrstuvwxyz" + Integer.toString(i));
            }
            this.pl.sync();
        }catch (Exception e){
            e.printStackTrace();
        }finally {

        }
    }

    public Jedis getClient(){
        return this.jedisPool.getResource();
    }
}

接下来点击项目结构--》Artifact,点击左上加号--》form modules with dependencies

填写主类,这里改成接口类也是可以的(手动改,无法选择接口类)、点击完成、然后点击build--》build artifacts--》build

然后再项目中的out文件夹就生成了jar包。

3、nodejs调用jar

直接看代码吧,这里只是很简单的,但很实用。 

let java = require("java"); //引入nodejs的java模块

java.classpath.push("./testJedis.jar"); //导入编写的jar包

let JedisTool = java.import('com.company.JedisTool'); //package.class

let jedisTool = new JedisTool();

jedisTool.initJedis();  //方法调用

setInterval(() => {

  jedisTool.usePipeline(100000);

}, 1000);

还有很多使用方法,这里不一一列出了,有了node的java模块,你也可以在node中进行java开发了。

node-java文档 ,官方文档很详细,我虽然英语好,但是也是实在读不下去,挑自己感兴趣的学习即可。

4、总结

            本文简单记录了node调用java的方法,在生产项目中会增加许多可能,因为优秀的接口我们都值得使用,不管他是java还是c++。

            这个过程中有几点注意事项:

          (1)java模块的依赖问题,换台电脑还能不能用之类的事情,最起码要运行的机器需要java环境;

          (2)高版本编译的jar,装有低版本java的node调用jar会报错;

          (3)openJDK能否正常调用等待明天验证;

          (4)jar不能在nodejs的多线程使用,这个问题有待研究。

5、后续验证

(1)java模块的依赖问题,换台电脑还能不能用之类的事情,最起码要运行的机器需要java环境;

       这一点在其他机器上(windows)只需要安装同版本的java环境,并且将jvm.dll的路径添加到环境变量path中即可。

(2)openJDK能否正常调用(可以);

       由于nodejs安装java模块的时候需要编译且生唉成了一个.node,而.node并不跨平台,所以需要重新编译,在linux下使用java模块同样需要编译(java、javac、node-gyp,g++...)。但是linux有些系统只安装了java,并没有安装javac,所以需要安装javac,重新编译java模块源码。然后就可以愉快的使用了。

(3)开启多线程,只能有一个线程运行我们封装的jar包;

        经过验证,确实如此,查看官网,说是只能创建一个jvm,线程同属于一个进程,所以之。突然又会想到,那多进程呢,理论上是可以的,验证之后确实如此,进程之间相互隔离,所以可以创建多个jvm。

6、补充

中标麒麟下运行node调用java的注意事项

发布了49 篇原创文章 · 获赞 26 · 访问量 5万+

猜你喜欢

转载自blog.csdn.net/qianlixiaomage/article/details/105058464
今日推荐