java - 通过 Python 子进程启动 Minecraft 不起作用

标签 java python windows cmd minecraft

今天我尝试在 Windows 7 上通过命令行启动 Minecraft 客户端。它有效!使用此代码:

java -Xmx1024M -Djava.library.path="%APPDATA%\.minecraft\versions\1.7.10\1.7.10-natives" -cp "%APPDATA%\.minecraft\libraries\org\apache\logging\log4j\log4j-api\2.0-beta9\log4j-api-2.0-beta9.jar;%APPDATA%\.minecraft\libraries\org\apache\logging\log4j\log4j-core\2.0-beta9\log4j-core-2.0-beta9.jar;%APPDATA%\.minecraft\libraries\com\ibm\icu\icu4j-core-mojang\51.2\icu4j-core-mojang-51.2.jar;%APPDATA%\.minecraft\libraries\com\mojang\authlib\1.3\authlib-1.3.jar;%APPDATA%\.minecraft\libraries\io\netty\netty-all\4.0.10.Final\netty-all-4.0.10.Final.jar;%APPDATA%\.minecraft\libraries\java3d\vecmath\1.3.1\vecmath-1.3.1.jar;%APPDATA%\.minecraft\libraries\net\sf\trove4j\trove4j\3.0.3\trove4j-3.0.3.jar;%APPDATA%\.minecraft\libraries\net\sf\jopt-simple\jopt-simple\4.5\jopt-simple-4.5.jar;%APPDATA%\.minecraft\libraries\com\paulscode\codecjorbis\20101023\codecjorbis-20101023.jar;%APPDATA%\.minecraft\libraries\com\paulscode\codecwav\20101023\codecwav-20101023.jar;%APPDATA%\.minecraft\libraries\com\paulscode\librarylwjglopenal\20100824\librarylwjglopenal-20100824.jar;%APPDATA%\.minecraft\libraries\com\paulscode\libraryjavasound\20101123\libraryjavasound-20101123.jar;%APPDATA%\.minecraft\libraries\com\paulscode\soundsystem\20120107\soundsystem-20120107.jar;%APPDATA%\.minecraft\libraries\com\google\guava\guava\15.0\guava-15.0.jar;%APPDATA%\.minecraft\libraries\org\apache\commons\commons-lang3\3.1\commons-lang3-3.1.jar;%APPDATA%\.minecraft\libraries\commons-io\commons-io\2.4\commons-io-2.4.jar;%APPDATA%\.minecraft\libraries\net\java\jinput\jinput\2.0.5\jinput-2.0.5.jar;%APPDATA%\.minecraft\libraries\net\java\jinput\jinput-platform\2.0.5\jinput-platform-2.0.5-natives-windows.jar;%APPDATA%\.minecraft\libraries\net\java\jutils\jutils\1.0.0\jutils-1.0.0.jar;%APPDATA%\.minecraft\libraries\com\google\code\gson\gson\2.2.4\gson-2.2.4.jar;%APPDATA%\.minecraft\libraries\org\lwjgl\lwjgl\lwjgl\2.9.0\lwjgl-2.9.0.jar;%APPDATA%\.minecraft\libraries\org\lwjgl\lwjgl\lwjgl_util\2.9.0\lwjgl_util-2.9.0.jar;%APPDATA%\.minecraft\versions\1.7.10\1.7.10.jar" net.minecraft.client.main.Main --username [username] --version 1.7.10 --gameDir C:\Users\Jon\AppData\Roaming\.minec~1 --assetsDir C:\Users\Jon\AppData\Roaming\.minec~1\assets --accessToken [accessToken] --uuid [uuid] --userProperties {} --userType mojang

有点长,但是如果你设置了用户名、uuid 和 accessToken,它就可以正常工作。

现在我想用 Python 创建一个小型 Minecraft 启动器(小 gui 等),并且我知道我可以使用 subprocess 和 Popen 调用命令。

所以我尝试过 Popen:

import subprocess

# sc = start command
sc = ['java', '-Xmx1024M', '-Djava.library.path="%APPDATA%\\.minecraft\\versions\\1.7.10\\1.7.10-natives"', '-cp', '"%APPDATA%\\.minecraft\\libraries\\org\\apache\\logging\\log4j\\log4j-api\\2.0-beta9\\log4j-api-2.0-beta9.jar;%APPDATA%\\.minecraft\\libraries\\org\\apache\\logging\\log4j\\log4j-core\\2.0-beta9\\log4j-core-2.0-beta9.jar;%APPDATA%\\.minecraft\\libraries\\com\\ibm\\icu\\icu4j-core-mojang\\51.2\\icu4j-core-mojang-51.2.jar;%APPDATA%\\.minecraft\\libraries\\com\\mojang\\authlib\\1.3\\authlib-1.3.jar;%APPDATA%\\.minecraft\\libraries\\io\\netty\\netty-all\\4.0.10.Final\\netty-all-4.0.10.Final.jar;%APPDATA%\\.minecraft\\libraries\\java3d\\vecmath\\1.3.1\\vecmath-1.3.1.jar;%APPDATA%\\.minecraft\\libraries\\net\\sf\\trove4j\\trove4j\\3.0.3\\trove4j-3.0.3.jar;%APPDATA%\\.minecraft\\libraries\\net\\sf\\jopt-simple\\jopt-simple\\4.5\\jopt-simple-4.5.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\codecjorbis\\20101023\\codecjorbis-20101023.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\codecwav\\20101023\\codecwav-20101023.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\librarylwjglopenal\\20100824\\librarylwjglopenal-20100824.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\libraryjavasound\\20101123\\libraryjavasound-20101123.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\soundsystem\\20120107\\soundsystem-20120107.jar;%APPDATA%\\.minecraft\\libraries\\com\\google\\guava\\guava\\15.0\\guava-15.0.jar;%APPDATA%\\.minecraft\\libraries\\org\\apache\\commons\\commons-lang3\\3.1\\commons-lang3-3.1.jar;%APPDATA%\\.minecraft\\libraries\\commons-io\\commons-io\\2.4\\commons-io-2.4.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jinput\\jinput\\2.0.5\\jinput-2.0.5.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jinput\\jinput-platform\\2.0.5\\jinput-platform-2.0.5-natives-windows.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jutils\\jutils\\1.0.0\\jutils-1.0.0.jar;%APPDATA%\\.minecraft\\libraries\\com\\google\\code\\gson\\gson\\2.2.4\\gson-2.2.4.jar;%APPDATA%\\.minecraft\\libraries\\org\\lwjgl\\lwjgl\\lwjgl\\2.9.0\\lwjgl-2.9.0.jar;%APPDATA%\\.minecraft\\libraries\\org\\lwjgl\\lwjgl\\lwjgl_util\\2.9.0\\lwjgl_util-2.9.0.jar;%APPDATA%\\.minecraft\\versions\\1.7.10\\1.7.10.jar"', 'net.minecraft.client.main.Main', '--username', '[username]', '--version', '1.7.10', '--gameDir', 'C:\\Users\\Jon\\AppData\\Roaming\\.minecraft', '--assetsDir C:\\Users\\Jon\\AppData\\Roaming\\.minecraft\\assets', '--accessToken', '[accessToken]', '--uuid', '[uuid]', '--userProperties', '{}', '--userType', 'mojang']
p = subprocess.Popen(sc, stdout = subprocess.PIPE, stderr = subprocess.PIPE)
while True:
o = p.stdout.readline()
e = p.stderr.readline()
if o:
    print o
if e:
    print e
if o or e:
    pass
else:
    break

它不起作用,因为发生错误:

Exception in thread "main" java.lang.NoClassDefFoundError: org/apache/logging/log4j/LogManager

    at bao.<clinit>(SourceFile:84)

    at net.minecraft.client.main.Main.main(SourceFile:72)

Caused by: java.lang.ClassNotFoundException: org.apache.logging.log4j.LogManager


    at java.net.URLClassLoader$1.run(Unknown Source)

    at java.net.URLClassLoader$1.run(Unknown Source)

    at java.security.AccessController.doPrivileged(Native Method)

    at java.net.URLClassLoader.findClass(Unknown Source)

    at java.lang.ClassLoader.loadClass(Unknown Source)

    at sun.misc.Launcher$AppClassLoader.loadClass(Unknown Source)

    at java.lang.ClassLoader.loadClass(Unknown Source)

    ... 2 more

在普通命令行中该命令可以正常工作,没有任何问题,但只有在Python中才会出现问题。好吧,经过一番思考,我意识到我可以“管道”cmd.exe 和 java 命令+参数。

所以我也尝试过:

import subprocess

### as you can see, I've tried to replace the %appdata%-placeholder too

# start command
sc = ['java', '-Xmx1024M', '-Djava.library.path="%APPDATA%\\.minecraft\\versions\\1.7.10\\1.7.10-natives"', '-cp', '"%APPDATA%\\.minecraft\\libraries\\org\\apache\\logging\\log4j\\log4j-api\\2.0-beta9\\log4j-api-2.0-beta9.jar;%APPDATA%\\.minecraft\\libraries\\org\\apache\\logging\\log4j\\log4j-core\\2.0-beta9\\log4j-core-2.0-beta9.jar;%APPDATA%\\.minecraft\\libraries\\com\\ibm\\icu\\icu4j-core-mojang\\51.2\\icu4j-core-mojang-51.2.jar;%APPDATA%\\.minecraft\\libraries\\com\\mojang\\authlib\\1.3\\authlib-1.3.jar;%APPDATA%\\.minecraft\\libraries\\io\\netty\\netty-all\\4.0.10.Final\\netty-all-4.0.10.Final.jar;%APPDATA%\\.minecraft\\libraries\\java3d\\vecmath\\1.3.1\\vecmath-1.3.1.jar;%APPDATA%\\.minecraft\\libraries\\net\\sf\\trove4j\\trove4j\\3.0.3\\trove4j-3.0.3.jar;%APPDATA%\\.minecraft\\libraries\\net\\sf\\jopt-simple\\jopt-simple\\4.5\\jopt-simple-4.5.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\codecjorbis\\20101023\\codecjorbis-20101023.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\codecwav\\20101023\\codecwav-20101023.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\librarylwjglopenal\\20100824\\librarylwjglopenal-20100824.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\libraryjavasound\\20101123\\libraryjavasound-20101123.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\soundsystem\\20120107\\soundsystem-20120107.jar;%APPDATA%\\.minecraft\\libraries\\com\\google\\guava\\guava\\15.0\\guava-15.0.jar;%APPDATA%\\.minecraft\\libraries\\org\\apache\\commons\\commons-lang3\\3.1\\commons-lang3-3.1.jar;%APPDATA%\\.minecraft\\libraries\\commons-io\\commons-io\\2.4\\commons-io-2.4.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jinput\\jinput\\2.0.5\\jinput-2.0.5.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jinput\\jinput-platform\\2.0.5\\jinput-platform-2.0.5-natives-windows.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jutils\\jutils\\1.0.0\\jutils-1.0.0.jar;%APPDATA%\\.minecraft\\libraries\\com\\google\\code\\gson\\gson\\2.2.4\\gson-2.2.4.jar;%APPDATA%\\.minecraft\\libraries\\org\\lwjgl\\lwjgl\\lwjgl\\2.9.0\\lwjgl-2.9.0.jar;%APPDATA%\\.minecraft\\libraries\\org\\lwjgl\\lwjgl\\lwjgl_util\\2.9.0\\lwjgl_util-2.9.0.jar;%APPDATA%\\.minecraft\\versions\\1.7.10\\1.7.10.jar"', 'net.minecraft.client.main.Main', '--username', 'Microskype', '--version', '1.7.10', '--gameDir', 'C:\\Users\\Jon\\AppData\\Roaming\\.minecraft', '--assetsDir C:\\Users\\Jon\\AppData\\Roaming\\.minecraft\\assets', '--accessToken', '40b9d172b3fe4e3486e33a67ca3db075', '--uuid', 'e457b026-2e68-40b6-b38d-fcb3645ba318', '--userProperties', '{}', '--userType', 'mojang']
# new start command starting with cmd.exe and /C to pipe cmd.exe and the java command + parameters
nsc = ["cmd.exe", "/C"]

for one in sc:
    one = one.replace('%APPDATA%', 'C:\\Users\\Jon\\AppData\\Roaming')
    one = one.replace('%appdata%', 'C:\\Users\\Jon\\AppData\\Roaming')
    nsc.append(one)

p = subprocess.Popen(nsc, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
while True:
    o = p.stdout.readline()
    e = p.stderr.readline()
    if o:
        print o
    if e:
        print e
    if o or e:
        pass
    else:
        break

然后我尝试使用整个 Java 路径而不是 java,但我得到了 WindowsError: [Error 5] Access Denied。命令太长了吗? :D

我认为问题出在Windows上,但是一定有办法解决这个问题。 你有什么想法吗?

问候, 乔尼博伊

最佳答案

您可以尝试通过将 shell=True 添加到 Popen 构造函数来修改您的第一个版本吗?

import subprocess

# sc = start command
sc = ['java', '-Xmx1024M', '-Djava.library.path="%APPDATA%\\.minecraft\\versions\\1.7.10\\1.7.10-natives"', '-cp', '"%APPDATA%\\.minecraft\\libraries\\org\\apache\\logging\\log4j\\log4j-api\\2.0-beta9\\log4j-api-2.0-beta9.jar;%APPDATA%\\.minecraft\\libraries\\org\\apache\\logging\\log4j\\log4j-core\\2.0-beta9\\log4j-core-2.0-beta9.jar;%APPDATA%\\.minecraft\\libraries\\com\\ibm\\icu\\icu4j-core-mojang\\51.2\\icu4j-core-mojang-51.2.jar;%APPDATA%\\.minecraft\\libraries\\com\\mojang\\authlib\\1.3\\authlib-1.3.jar;%APPDATA%\\.minecraft\\libraries\\io\\netty\\netty-all\\4.0.10.Final\\netty-all-4.0.10.Final.jar;%APPDATA%\\.minecraft\\libraries\\java3d\\vecmath\\1.3.1\\vecmath-1.3.1.jar;%APPDATA%\\.minecraft\\libraries\\net\\sf\\trove4j\\trove4j\\3.0.3\\trove4j-3.0.3.jar;%APPDATA%\\.minecraft\\libraries\\net\\sf\\jopt-simple\\jopt-simple\\4.5\\jopt-simple-4.5.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\codecjorbis\\20101023\\codecjorbis-20101023.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\codecwav\\20101023\\codecwav-20101023.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\librarylwjglopenal\\20100824\\librarylwjglopenal-20100824.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\libraryjavasound\\20101123\\libraryjavasound-20101123.jar;%APPDATA%\\.minecraft\\libraries\\com\\paulscode\\soundsystem\\20120107\\soundsystem-20120107.jar;%APPDATA%\\.minecraft\\libraries\\com\\google\\guava\\guava\\15.0\\guava-15.0.jar;%APPDATA%\\.minecraft\\libraries\\org\\apache\\commons\\commons-lang3\\3.1\\commons-lang3-3.1.jar;%APPDATA%\\.minecraft\\libraries\\commons-io\\commons-io\\2.4\\commons-io-2.4.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jinput\\jinput\\2.0.5\\jinput-2.0.5.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jinput\\jinput-platform\\2.0.5\\jinput-platform-2.0.5-natives-windows.jar;%APPDATA%\\.minecraft\\libraries\\net\\java\\jutils\\jutils\\1.0.0\\jutils-1.0.0.jar;%APPDATA%\\.minecraft\\libraries\\com\\google\\code\\gson\\gson\\2.2.4\\gson-2.2.4.jar;%APPDATA%\\.minecraft\\libraries\\org\\lwjgl\\lwjgl\\lwjgl\\2.9.0\\lwjgl-2.9.0.jar;%APPDATA%\\.minecraft\\libraries\\org\\lwjgl\\lwjgl\\lwjgl_util\\2.9.0\\lwjgl_util-2.9.0.jar;%APPDATA%\\.minecraft\\versions\\1.7.10\\1.7.10.jar"', 'net.minecraft.client.main.Main', '--username', '[username]', '--version', '1.7.10', '--gameDir', 'C:\\Users\\Jon\\AppData\\Roaming\\.minecraft', '--assetsDir C:\\Users\\Jon\\AppData\\Roaming\\.minecraft\\assets', '--accessToken', '[accessToken]', '--uuid', '[uuid]', '--userProperties', '{}', '--userType', 'mojang']
p = subprocess.Popen(sc, stdout = subprocess.PIPE, stderr = subprocess.PIPE, shell=True)
while True:
    o = p.stdout.readline()
    e = p.stderr.readline()
    if o:
        print o
    if e:
        print e
    if o or e:
        pass
    else:
        break

关于java - 通过 Python 子进程启动 Minecraft 不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25960882/

相关文章:

java - 导入javax.xml.xpath无法解析

Python - 从字符串中手动删除特定字母

python - 如何从源代码构建支持 python2 和 3 的 vim80?

python - 限制 Django 中的 Markdown

eclipse - Atlassian SourceTree自定义 Action 对比

java - 需要高性能 Scala/Java 集合

java - 计算贝塞尔剪裁中的距离函数时遇到问题

java - 如何在报表中使用多个XML数据源

c - 如何创建未定义数量的线程并在 Windows 上的 c 中使用 WaitForMultipleObjects()

Java 错误 : incorrect time in MSK