Java/Compose Desktop项目中进行python调用

写在前面

开发compose desktop项目爬网站时遇到验证码处理不方便需要借助python庞大的处理能力,这时需要再项目中调用python去执行获取结果,这里记录一下使用过程。

本次开发记录基于:python 3.9,compose 1.3 java17

工具:Pycharm IntelliJ IDEA

适用场景:java项目使用python,不想再单独安装python环境,直接集成进java项目

正文

记录使用验证码识别的探索

  1. 开发python项目
    使用开源识别框架ddddocr进行验证码识别,测试下来准确度还不错

  2. 安装打包工具 PyInstaller 官网文档参考

  3. 编写打包配置 package.py如:

    from PyInstaller.utils.hooks import collect_data_files
    from PyInstaller.utils.hooks import collect_submodules
    from PyInstaller.utils.hooks import copy_metadata
    
    # python3 package.py
    
    # 定义PyInstaller的打包选项
    options = {
        "name": "main",
        "onefile": True,
        "hidden-imports": collect_submodules("ddddocr"),
        "datas": collect_data_files("ddddocr"),
        "metadata": copy_metadata("ddddocr")
    }
    
    # 使用options配置PyInstaller
    import PyInstaller.__main__
    path_list = [file[0] for file in options["datas"]]
    prefix = '--add-data='
    suffix = ':ddddocr'
    newlist = []
    for item in path_list:
        newlist.append(f'{prefix}{item}{suffix}')
    print(newlist)
    metadataList = [file[0] for file in options["metadata"]]
    
    PyInstaller.__main__.run([
        "main.py",
        "--name=%s" % options["name"],
        "--onedir",
        # "--hidden-imports=%s" % ",".join(options["hidden-imports"]),
        # "--add-metadata=%s" % ",".join(metadataList),
        "--distpath=%s" % "dist",
        "--workpath=%s" % "build",
        "--specpath=%s" % ".",
    ].__add__(newlist))
    
    
  4. 执行python3 package.py

  5. 在dist目录即可获取到包含python解释器的项目,如果配置参数是–onedir就是一个目录如果是–onefile就是一个可执行文件

  6. 这个目录下的文件就是我们需要的等下拷贝到java项目resources目录下
    如图:Java/Compose Desktop项目中进行python调用_第1张图片
    7.编写java测试代码进行调用测试

 import java.io.BufferedReader
import java.io.File
import java.io.InputStreamReader

fun main(args: Array<String>) {
    val args1 = arrayOf(ClassLoader.getSystemClassLoader().getResource("main/main").path, data)
    var result = ""
    var error = ""
    runCatching {
        val proc = Runtime.getRuntime().exec(args1)
        proc.errorStream.bufferedReader().readText().also {
            error = it
        }
        val lines = BufferedReader(InputStreamReader(proc.inputStream)).readLines()
        println(lines)
        result = lines.lastOrNull() ?: ""
        proc.waitFor()
        //0-成功 1-调用失败 2-Python文件执行失败
        println("执行结果:" + proc.exitValue())
        if (proc.exitValue() == 0) {
            println("result:$result")
        } else {
            println("error:$error")
        }
    }.onFailure {
        println(it)
    }

}

其中 ClassLoader.getSystemClassLoader().getResource("main/main").path是获取资源目录下可执行文件的
8.调试使用即可

以上便是我的开发过程,遇到问题切记不可照搬,理解应用。

你可能感兴趣的:(python,java,开发语言,pyinstall)