5

我有一个在 tomcat 上运行的应用程序,其中一种方法是从 jpeg 图像创建一个简单的缩略图。这些功能离线工作正常,一周前也在tomcat上工作。但现在我收到以下错误:

java.lang.NoClassDefFoundError
java.lang.Class.forName0(Native Method)
java.lang.Class.forName(Class.java:164)
java.awt.GraphicsEnvironment.getLocalGraphicsEnvironment(GraphicsEnvironment.java:68)
java.awt.image.BufferedImage.createGraphics(BufferedImage.java:1141)
eval.impl.ImageEval.getThumbnail(ImageEval.java:155)
eval.impl.ImageServlet.doGet(ImageServlet.java:79)
javax.servlet.http.HttpServlet.service(HttpServlet.java:690)
javax.servlet.http.HttpServlet.service(HttpServlet.java:803)

我认为我没有改变任何应该影响这一点的东西(实际上我根本没有根据 svn 存储库改变函数),所以它一定是一个库问题。但我无法弄清楚缺少什么。以下是发生错误的 getThumbnail 函数的实际行:

        BufferedImage thumbImage = new BufferedImage(thumbWidth, 
            thumbHeight, BufferedImage.TYPE_INT_RGB);
    Graphics2D graphics2D = thumbImage.createGraphics();
    graphics2D.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
            RenderingHints.VALUE_INTERPOLATION_BILINEAR);
    graphics2D.drawImage(simage, 0, 0, thumbWidth, thumbHeight, null);

[编辑] 我决定稍微更新一下问题描述。是的,他似乎无法从 java.awt 中找到一些类或与之相关的类。但它们确实存在于 jvm 的服务器上。Java 无头模式并不能解决问题。在另一个项目中,完全相同的代码,但在此服务器上的axis2 webservice 内工作正常。[/编辑]

4

7 回答 7

7

看来您已经更改了 Tomcat 的配置。

要么您已更改为 al{0,1}[iu]n[iu]x 框,要么安装在具有不同于您测试它的安全控制的虚拟机上。

显然

 GraphicsEnvironment.getLocalGraphicsEnvironment()

正在尝试访问属性:java.awt.graphicsenv

这可能会返回 null 或一些不存在的类名,然后加载并抛出 ClassNotFoundException。1

解决方案似乎是指定“java.awt.headless”属性。

这是一个类似的问题:java.awt.Color error

试试这个搜索,它会显示与您类似的情况。

我记得在 sun bugs 数据库中也有一些东西。

找到解决方案后发布!

1.图形环境.java

编辑

不是日食!!

在我的原始帖子中,有一个指向引发异常的类的源代码的链接。

因为我看起来你很想念它,所以我会在这里为你发布:

       public static synchronized GraphicsEnvironment getLocalGraphicsEnvironment() {
          if (localEnv == null) {
               // Y O U R   E R R O R  O R I G I N A T E S    H E R E !!! 
              String nm = (String) java.security.AccessController.doPrivileged
                  (new sun.security.action.GetPropertyAction
                   ("java.awt.graphicsenv", null));

              try {
  //                      long t0 = System.currentTimeMillis();
                  localEnv =
                      (GraphicsEnvironment) Class.forName(nm).newInstance();
  //              long t1 = System.currentTimeMillis();
  //              System.out.println("GE creation took " + (t1-t0)+ "ms.");
                  if (isHeadless()) {
                      localEnv = new HeadlessGraphicsEnvironment(localEnv);
                  }
              } catch (ClassNotFoundException e) {
                  throw new Error("Could not find class: "+nm);
              } catch (InstantiationException e) {
                  throw new Error("Could not instantiate Graphics Environment: "
                                  + nm);
              } catch (IllegalAccessException e) {
                  throw new Error ("Could not access Graphics Environment: "
                                   + nm);
              }
          }

          return localEnv;
      }

这就是被执行的。

在您似乎没有阅读的原始帖子中,我说代码正在访问属性“java.awt.graphicsenv”

如果使用轴的其他项目没有相同的问题,则可能是因为它可能在不同的 tomcat 配置中运行,或者轴库允许访问该属性。但我们不能确定。那是纯粹的猜测。那么为什么不测试以下内容并查看打印的内容:

        String nm = (String) java.security.AccessController.doPrivileged
            (new sun.security.action.GetPropertyAction
             ("java.awt.graphicsenv", null));

    System.out.println("java.awt.graphicsenv = " + nm );

它打印空然后你现在是什么问题。您的系统中没有该属性,或者安全性禁止您使用它。

从这里很难告诉你:“去编辑文件 xyz 并添加:fail = false ”所以你必须做你的工作并尝试找出真正的原因是什么。

首先研究正在执行的代码是什么(我刚刚发布了),然后了解它的作用以及所有“AccessController.doPrivileged”是如何工作的。(您可以为此使用 Google + StackOverflow)。

于 2009-06-04T17:44:33.250 回答
5

我们遇到了类似的问题,经过多次故障排除后,它被确定与该java.awt.headless物业有关。通过将 JVM 选项显式设置为

-Djava.awt.headless=true
于 2011-11-11T13:32:59.783 回答
3

一周前运行,现在不是。

因此,您在“工作”和“不工作”之间进行了一些更改。

回到工作配置(如果可以的话),并严格跟踪您所做的更改。如果您没有工作配置的备份,那么请仔细回顾您在工作和非工作之间所做的事情,直到找到您所做的更改。

它可能不是代码 - 它可能是配置文件等。

祝你好运,

-R

于 2009-06-04T17:50:13.867 回答
1

该服务器是否在服务器模式下运行 java - 我听说 AWT 类中没有加载。

于 2009-06-04T17:29:05.350 回答
1

如果您在 *nix 上部署它,并且您不再运行 X 窗口系统,那就可以解释了。即使您这样做,如果您没有将 DISPLAY 系统变量导出到启动 JVM 的进程,或者如果您导出了但它实际上无效,则可能会导致此类问题。

那至少可以解释为什么您没有更改tomcat中的任何配置,但仍然有问题。

于 2009-06-04T18:12:00.273 回答
0

如果您NoClassDefFoundError根本没有消息,那么这意味着两件事:

  1. JVM 已尝试加载类但失败。通常,这意味着 JVM 无法完成该类的静态初始化,即为任何static 字段分配值并运行任何static { }块。通常,这是因为缺少执行此静态初始化所需的类。
  2. 您使用的是 Java 5,而不是 Java 6。(在 Java 6 中,您会收到“Could not initialize class xyz ”消息。)

问题类似乎是其名称是系统属性值的一类java.awt.graphicsenv。我会从找出这个属性的价值开始。当你尝试实例化这个类时会发生什么?

于 2009-06-04T20:19:27.233 回答
0

由于您从 AWT 代码中得到 NoClassDefFoundError,看起来 Java 无法加载 X Windows 库。请注意,即使您在无头模式下运行($DISPLAY 不指向 X Windows 服务器),AWT 仍然需要 X11 库的某些子集来渲染图像。例如,请参阅此参考:

http://javatechniques.com/blog/linux-x11-libraries-for-headless-mode

如果某些东西停止工作并且您的 Java 代码没有更改,则可能是 X11 库在您的机器上被移动或卸载,或者由于某些其他原因,您的 LD_LIBRARY_PATH 环境变量不再指向它们。

于 2011-12-05T18:02:41.550 回答