See Issue #135. nokogiri in jruby envronments is at fault. I don't have jruby, so I can't investigate. If you can figure out the cause of this bug, then I will by all means fix it.
I've debugged it up to the line https://github.com/weshatheleopard/rubyXL/blob/master/lib/rubyXL/objects/ooxml_object.rb#L300 where cp:coreProperties/, where there's a file written called core.xml.
MRI and JRuby then both call https://github.com/sparklemotion/nokogiri/blob/master/lib/nokogiri/xml/document.rb#L82 with the name cp:coreProperties and the args
but MRI creates the element, while JRuby throws the exception:
Java::OrgW3cDom::DOMException: NAMESPACE_ERR: An attempt is made to create or change an object in a way which is incorrect with regard to namespaces.
Hi, I've just tried the current master branch with JRuby 1.7.21 and I'm sorry to say that the error still exists when executing the above example:
...
jruby-1.7.21 :005 > workbook.write('/tmp/abc.xlsx')
Java::OrgW3cDom::DOMException: NAMESPACE_ERR: An attempt is made to create or change an object in a way which is incorrect with regard to namespaces.
from org.apache.xerces.dom.ElementNSImpl.setName(Unknown Source)
from org.apache.xerces.dom.ElementNSImpl.<init>(Unknown Source)
from org.apache.xerces.dom.CoreDocumentImpl.createElementNS(Unknown Source)
from nokogiri.XmlNode.init(XmlNode.java:343)
from nokogiri.XmlNode.rbNew(XmlNode.java:298)
from nokogiri.XmlNode$INVOKER$s$0$0$rbNew.call(XmlNode$INVOKER$s$0$0$rbNew.gen)
from org.jruby.internal.runtime.methods.DynamicMethod.call(DynamicMethod.java:218)
from org.jruby.runtime.callsite.CachingCallSite.callBlock(CachingCallSite.java:211)
from org.jruby.runtime.callsite.CachingCallSite.call(CachingCallSite.java:217)
from org.jruby.ast.CallTwoArgBlockPassNode.interpret(CallTwoArgBlockPassNode.java:62)
from org.jruby.ast.LocalAsgnNode.interpret(LocalAsgnNode.java:123)
from org.jruby.ast.NewlineNode.interpret(NewlineNode.java:105)
from org.jruby.ast.BlockNode.interpret(BlockNode.java:71)
from org.jruby.evaluator.ASTInterpreter.INTERPRET_METHOD(ASTInterpreter.java:74)
from org.jruby.internal.runtime.methods.InterpretedMethod.call(InterpretedMethod.java:268)
from org.jruby.internal.runtime.methods.DefaultMethod.call(DefaultMethod.java:235)
... 229 levels...
from org.jruby.ast.BlockNode.interpret(BlockNode.java:71)
from org.jruby.evaluator.ASTInterpreter.INTERPRET_METHOD(ASTInterpreter.java:74)
from org.jruby.internal.runtime.methods.InterpretedMethod.call(InterpretedMethod.java:182)
from org.jruby.internal.runtime.methods.DefaultMethod.call(DefaultMethod.java:203)
from org.jruby.runtime.callsite.CachingCallSite.cacheAndCall(CachingCallSite.java:326)
from org.jruby.runtime.callsite.CachingCallSite.call(CachingCallSite.java:170)
from home.hk.$_dot_rvm.rubies.jruby_minus_1_dot_7_dot_21.bin.irb.__file__(/home/hk/.rvm/rubies/jruby-1.7.21/bin/irb:13)
from home.hk.$_dot_rvm.rubies.jruby_minus_1_dot_7_dot_21.bin.irb.load(/home/hk/.rvm/rubies/jruby-1.7.21/bin/irb)
from org.jruby.Ruby.runScript(Ruby.java:867)
from org.jruby.Ruby.runScript(Ruby.java:860)
from org.jruby.Ruby.runNormally(Ruby.java:729)
from org.jruby.Ruby.runFromMain(Ruby.java:578)
from org.jruby.Main.doRunFromMain(Main.java:395)
from org.jruby.Main.internalRun(Main.java:290)
from org.jruby.Main.run(Main.java:217)
from org.jruby.Main.main(Main.java:197)
jruby-1.7.21 :006 >
I've tried it with the newest version of nokogiri (1.6.6.2) and an older version (1.6.3.1), with the same result above.
I don't have time at the moment to create a proper pull request, but I've been working around this problem with a monkey-patch, that I thought would be valuable to share:
module RubyXL
module OOXMLObjectInstanceMethods
def write_xml_with_strict_mode(xml = nil, *args)
if xml && Nokogiri.jruby?
xml.to_java.strict_error_checking = false
end
write_xml_without_strict_mode(xml, *args)
end
alias_method_chain :write_xml, :strict_mode
end
end
I've also made a patch, but no tests for it, so likely not acceptable as a pull request. The patch looks like:
diff --git a/lib/rubyXL/objects/ooxml_object.rb b/lib/rubyXL/objects/ooxml_object.rb
index c83b704a..11ee2fbc 100644
--- a/lib/rubyXL/objects/ooxml_object.rb
+++ b/lib/rubyXL/objects/ooxml_object.rb
@@ -270,6 +270,9 @@ module RubyXL
if xml.nil? then
seed_xml = Nokogiri::XML('<?xml version = "1.0" standalone ="yes"?>')
seed_xml.encoding = 'UTF-8'
+ if Nokogiri.jruby?
+ seed_xml.to_java.strict_error_checking = false
+ end
result = self.write_xml(seed_xml)
return result if result == ''
seed_xml << result
nokogiri 1.10.7 (java) (tried downgrading as well)
jruby 9.2.0.0 (2.5.0)
ruby 2.5.1p57
java version "1.8.0_181"
Unhandled Java exception: org.w3c.dom.DOMException: NAMESPACE_ERR: An attempt is made to create or change an object in a way which is incorrect with regard to namespaces.
org.w3c.dom.DOMException: NAMESPACE_ERR: An attempt is made to create or change an object in a way which is incorrect with regard to namespaces.
setName at org/apache/xerces/dom/ElementNSImpl:-1
at org/apache/xerces/dom/ElementNSImpl:-1
createElementNS at org/apache/xerces/dom/CoreDocumentImpl:-1
init at nokogiri/XmlNode.java:340
rbNew at nokogiri/XmlNode.java:298
call at nokogiri/XmlNode$INVOKER$s$0$0$rbNew.gen:-1
call at org/jruby/internal/runtime/methods/DynamicMethod.java:214
call at org/jruby/runtime/callsite/CachingCallSite.java:209
invokeOther20:new at usr/local/Cellar/jruby/$9_dot_2_dot_0_dot_0/libexec/lib/ruby/gems/shared/gems/nokogiri_minus_1_dot_10_dot_7_minus_java/lib/nokogiri/xml//usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/nokogiri-1.10.7-java/lib/nokogiri/xml/document.rb:89
create_element at /usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/nokogiri-1.10.7-java/lib/nokogiri/xml/document.rb:89
call at org/jruby/internal/runtime/methods/CompiledIRMethod.java:75
call at org/jruby/internal/runtime/methods/CompiledIRMethod.java:124
call at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:219
call at org/jruby/internal/runtime/methods/DynamicMethod.java:218
call at org/jruby/runtime/callsite/CachingCallSite.java:230
invokeOther72:create_element at usr/local/Cellar/jruby/$9_dot_2_dot_0_dot_0/libexec/lib/ruby/gems/shared/gems/rubyXL_minus_3_dot_4_dot_11/lib/rubyXL/objects//usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/rubyXL-3.4.11/lib/rubyXL/objects/ooxml_object.rb:304
write_xml at /usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/rubyXL-3.4.11/lib/rubyXL/objects/ooxml_object.rb:304
call at org/jruby/internal/runtime/methods/CompiledIRMethod.java:75
call at org/jruby/internal/runtime/methods/CompiledIRMethod.java:98
call at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:154
call at org/jruby/internal/runtime/methods/DynamicMethod.java:202
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:344
call at org/jruby/runtime/callsite/CachingCallSite.java:170
invokeOther51:write_xml at usr/local/Cellar/jruby/$9_dot_2_dot_0_dot_0/libexec/lib/ruby/gems/shared/gems/rubyXL_minus_3_dot_4_dot_11/lib/rubyXL/objects//usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/rubyXL-3.4.11/lib/rubyXL/objects/ooxml_object.rb:275
write_xml at /usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/rubyXL-3.4.11/lib/rubyXL/objects/ooxml_object.rb:275
call at org/jruby/internal/runtime/methods/CompiledIRMethod.java:75
call at org/jruby/internal/runtime/methods/CompiledIRMethod.java:85
call at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:121
call at org/jruby/internal/runtime/methods/DynamicMethod.java:194
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:323
call at org/jruby/runtime/callsite/CachingCallSite.java:139
processCall at org/jruby/ir/interpreter/InterpreterEngine.java:344
interpret at org/jruby/ir/interpreter/StartupInterpreterEngine.java:72
interpret at org/jruby/ir/interpreter/InterpreterEngine.java:84
INTERPRET_METHOD at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:169
call at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:156
call at org/jruby/internal/runtime/methods/DynamicMethod.java:202
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:344
call at org/jruby/runtime/callsite/CachingCallSite.java:170
invokeOther4:add_to_zip at usr/local/Cellar/jruby/$9_dot_2_dot_0_dot_0/libexec/lib/ruby/gems/shared/gems/rubyXL_minus_3_dot_4_dot_11/lib/rubyXL/objects//usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/rubyXL-3.4.11/lib/rubyXL/objects/root.rb:51
block in stream at /usr/local/Cellar/jruby/9.2.0.0/libexec/lib/ruby/gems/shared/gems/rubyXL-3.4.11/lib/rubyXL/objects/root.rb:51
yieldDirect at org/jruby/runtime/CompiledIRBlockBody.java:162
yieldDirect at org/jruby/runtime/MixedModeIRBlockBody.java:126
yield at org/jruby/runtime/BlockBody.java:114
yield at org/jruby/runtime/Block.java:165
select_bang at org/jruby/RubyArray.java:2658
call at org/jruby/RubyArray$INVOKER$i$0$0$select_bang.gen:-1
call at org/jruby/internal/runtime/methods/JavaMethod.java:537
call at org/jruby/runtime/callsite/CachingCallSite.java:80
callIter at org/jruby/runtime/callsite/CachingCallSite.java:89
interpret at org/jruby/ir/instructions/CallBase.java:519
processCall at org/jruby/ir/interpreter/InterpreterEngine.java:360
interpret at org/jruby/ir/interpreter/StartupInterpreterEngine.java:72
INTERPRET_BLOCK at org/jruby/ir/interpreter/Interpreter.java:129
commonYieldPath at org/jruby/runtime/MixedModeIRBlockBody.java:153
doYield at org/jruby/runtime/IRBlockBody.java:187
yield at org/jruby/runtime/BlockBody.java:116
yield at org/jruby/runtime/Block.java:165
each at org/jruby/RubyArray.java:1801
call at org/jruby/RubyArray$INVOKER$i$0$0$each.gen:-1
call at org/jruby/internal/runtime/methods/JavaMethod.java:537
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:301
call at org/jruby/runtime/callsite/CachingCallSite.java:82
callIter at org/jruby/runtime/callsite/CachingCallSite.java:89
interpret at org/jruby/ir/instructions/CallBase.java:519
processCall at org/jruby/ir/interpreter/InterpreterEngine.java:360
interpret at org/jruby/ir/interpreter/StartupInterpreterEngine.java:72
INTERPRET_BLOCK at org/jruby/ir/interpreter/Interpreter.java:129
commonYieldPath at org/jruby/runtime/MixedModeIRBlockBody.java:153
doYield at org/jruby/runtime/IRBlockBody.java:187
yield at org/jruby/runtime/BlockBody.java:116
yield at org/jruby/runtime/Block.java:165
yield at org/jruby/ir/runtime/IRRuntimeHelpers.java:459
interpret at org/jruby/ir/instructions/YieldInstr.java:83
processOtherOp at org/jruby/ir/interpreter/StartupInterpreterEngine.java:179
interpret at org/jruby/ir/interpreter/StartupInterpreterEngine.java:104
INTERPRET_METHOD at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:103
call at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:90
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:301
call at org/jruby/runtime/callsite/CachingCallSite.java:82
callIter at org/jruby/runtime/callsite/CachingCallSite.java:89
interpret at org/jruby/ir/instructions/CallBase.java:519
processCall at org/jruby/ir/interpreter/InterpreterEngine.java:360
interpret at org/jruby/ir/interpreter/StartupInterpreterEngine.java:72
interpret at org/jruby/ir/interpreter/InterpreterEngine.java:78
INTERPRET_METHOD at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:136
call at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:123
call at org/jruby/internal/runtime/methods/DynamicMethod.java:194
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:323
call at org/jruby/runtime/callsite/CachingCallSite.java:139
processCall at org/jruby/ir/interpreter/InterpreterEngine.java:344
interpret at org/jruby/ir/interpreter/StartupInterpreterEngine.java:72
INTERPRET_BLOCK at org/jruby/ir/interpreter/Interpreter.java:129
commonYieldPath at org/jruby/runtime/MixedModeIRBlockBody.java:153
doYield at org/jruby/runtime/IRBlockBody.java:187
yield at org/jruby/runtime/BlockBody.java:116
yield at org/jruby/runtime/Block.java:165
ensureYieldClose at org/jruby/RubyIO.java:1185
open at org/jruby/RubyIO.java:1179
call at org/jruby/RubyIO$INVOKER$s$0$0$open.gen:-1
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:301
call at org/jruby/runtime/callsite/CachingCallSite.java:82
callIter at org/jruby/runtime/callsite/CachingCallSite.java:89
interpret at org/jruby/ir/instructions/CallBase.java:519
processCall at org/jruby/ir/interpreter/InterpreterEngine.java:360
interpret at org/jruby/ir/interpreter/StartupInterpreterEngine.java:72
interpret at org/jruby/ir/interpreter/InterpreterEngine.java:84
INTERPRET_METHOD at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:169
call at org/jruby/internal/runtime/methods/MixedModeIRMethod.java:156
call at org/jruby/internal/runtime/methods/DynamicMethod.java:202
call at org/jruby/internal/runtime/methods/AliasMethod.java:65
cacheAndCall at org/jruby/runtime/callsite/CachingCallSite.java:344
call at org/jruby/runtime/callsite/CachingCallSite.java:170