Flying Saucer in Lotus Notes
I was trying to convert simple XHTML-files to PDF, and used Flying Saucer and iText to do so. It worked without problems in Java, however, when I tried to make a Lotus Notes agent with the same code, I got an exception I am unsure how to deal with.
The code:
import lotus.domino.*;
import java.io.*;
import com.lowagie.text.DocumentException;
import org.xhtmlrenderer.pdf.ITextRenderer;
import org.xhtmlrenderer.util.XRLog;
import java.util.*;
public class JavaAgent extends AgentBase {
public void NotesMain() {
try {
Session session = getSession();
AgentContext agentContext = session.getAgentContext();
String received = agentContext.getDocumentContext().
getItemValueString(&q开发者_如何学Gouot;Query_String");
String[] split;
split = received.split("&");
String url = split[1];
split = url.split("/");
String outputFile = split[split.length-1];
String direc = session.getEnvironmentString("Directory", true);
outputFile = direc + "\\" + outputFile + ".pdf";
OutputStream os = new FileOutputStream(outputFile);
ITextRenderer renderer = new ITextRenderer();
renderer.setDocument(url);
renderer.layout();
renderer.createPDF(os);
os.close();
System.exit(0);
} catch(Exception e) {
e.printStackTrace();
}
}
}
This yields the following:
09-05-2011 13:33:29 HTTP JVM: Could not initialize configuration for Flying Saucer library. Message is: Can't find resource for bundle java.util.PropertyResourceBundle, key access_properties_not_allowed
09-05-2011 13:33:29 HTTP JVM: java.util.MissingResourceException: Can't find resource for bundle java.util.PropertyResourceBundle, key access_properties_not_allowed
09-05-2011 13:33:29 HTTP JVM: at java.util.MissingResourceException.(MissingResourceException.java:50)
09-05-2011 13:33:29 HTTP JVM: at java.util.ResourceBundle.getObject(ResourceBundle.java:400)
09-05-2011 13:33:29 HTTP JVM: at java.util.ResourceBundle.getString(ResourceBundle.java:421)
09-05-2011 13:33:29 HTTP JVM: at lotus.notes.JavaString.getString(Unknown Source)
09-05-2011 13:33:29 HTTP JVM: at lotus.notes.AgentSecurityManager.checkPropertiesAccess(Unknown Source)
09-05-2011 13:33:30 HTTP JVM: at java.lang.System.getProperties(System.java:323)
09-05-2011 13:33:30 HTTP JVM: at org.xhtmlrenderer.util.Configuration.loadSystemProperties(Configuration.java:419)
09-05-2011 13:33:30 HTTP JVM: at org.xhtmlrenderer.util.Configuration.(Configuration.java:147)
09-05-2011 13:33:30 HTTP JVM: at org.xhtmlrenderer.util.Configuration.instance(Configuration.java:742)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.util.Configuration.valueFor(Configuration.java:463)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.util.Configuration.isTrue(Configuration.java:709)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.util.XRLog.init(XRLog.java:250)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.util.XRLog.log(XRLog.java:203)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.util.XRLog.render(XRLog.java:194)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.util.XRLog.render(XRLog.java:190)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.layout.SharedContext.(SharedContext.java:107)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.pdf.ITextRenderer.(ITextRenderer.java:111)
09-05-2011 13:33:31 HTTP JVM: at org.xhtmlrenderer.pdf.ITextRenderer.(ITextRenderer.java:102)
09-05-2011 13:33:31 HTTP JVM: at JavaAgent.NotesMain(Unknown Source)
09-05-2011 13:33:31 HTTP JVM: at lotus.domino.AgentBase.runNotes(Unknown Source)
09-05-2011 13:33:31 HTTP JVM: at lotus.domino.NotesThread.run(Unknown Source)
The offending line is
ITextRenderer renderer = new ITextRenderer();
Googling "access_properties_not_allowed" gives literally nothing.
1) Agents in Notes/Domino have an additional security feature in the Agent properties that sets the security level of the agent. By default, this setting is set to not allow restricted operations (the default setting is "Do not allow restricted operations").
In order for the agent to run the property it must be set to one of the following options:
"Allow restricted operations" "Allow restricted operations with full administration rights"
The property is found on the second tab, the key tab, of the Agent Properties dialog box.
2) As "road to yamburg" already explained, the JVM's Security Manager is not allowing access to the system's properties because the security policy does not specify to allow this action. You must change the security policy of the Java Virtual Machine (JVM) in order to allow access to the system properties. To do this, you can add the line "permission java.security.AllPermission;" to the "/jvm/lib/security/java.policy" file in the Notes/Domino directory.
The java.policy file will look similar to this after making the change:
grant {
permission java.security.AllPermission;
permission java.util.PropertyPermission "java.version", "read";
permission java.util.PropertyPermission "java.vendor", "read";
permission java.util.PropertyPermission "java.vendor.url", "read";
permission java.util.PropertyPermission "java.class.version", "read";
permission java.util.PropertyPermission "os.name", "read";
// ... and so on ...
}
Once the client/server is restarted, any Java program requiring access to System.getProperties() will now be granted access.
This is likely the security configuration:
XhtmlRenderer tries to read its configuration from System properties:
09-05-2011 13:33:30 HTTP JVM: at java.lang.System.getProperties(System.java:323)
09-05-2011 13:33:30 HTTP JVM: at org.xhtmlrenderer.util.Configuration.loadSystemProperties(Configuration.java:419)
But it is not allowed (SecurityManager),
09-05-2011 13:33:29 HTTP JVM: at lotus.notes.AgentSecurityManager.checkPropertiesAccess(Unknown Source)
There must be an exception thrown, caught and an error message needs to be produced. That error message have to be loaded from a resource bundle, but the bundle is not found.
09-05-2011 13:33:29 HTTP JVM: Could not initialize configuration for Flying Saucer library. Message is: Can't find resource for bundle java.util.PropertyResourceBundle, key access_properties_not_allowed
Solution:
- Try to find security properties for Lotus Domino JVM (don't know where they may be or should be), and let the code to read system properties
Or
- Make a patch to org.xhtmlrenderer package to catch security exceptions and handle them on their own.
精彩评论