clj-commons/seesaw

table hack failing

Opened this issue · 3 comments

I have a case where the table hack here is failing:
https://github.com/daveray/seesaw/blob/master/src/seesaw/table.clj#L71-L72

somehow, the mapping is lost causing this to execute:
https://github.com/daveray/seesaw/blob/master/src/seesaw/table.clj#L97-L102

so, in my case, when the hack is working, it looks like:

{:description 4, :category-list 10, :update? 8, :updated-date 5, :group-id 1, :installed-version 6, :name 0, :interface-version 9, :label 3, :version 7, :primary? 2}

and when it fails, it gets recreated looking like:

{"update?" 8, "categories" 10, "name" 3, "primary?" 2, "version" 9, "updated" 5, "addon-id" 0, "available" 7, "description" 4, "installed" 6, "group-id" 1}

I'm not sure what is causing my problem, but the fact that the ArrayIndexOutOfBoundsException is caught and a workaround is implemented indicates the hack doesn't always work.

I'm trying to figure out the best way of fixing this problem, perhaps with meta and implementing IObj to store the col-key mapping, but your comment here makes me think you had a definite idea of how it could be improved.

In theory, if I manually juggle the row key normalisation outside of seesaw and just use string keys, then even when the hack fails and is replaced with the bad mapping, it should still continue to work.

actually, it also looks like the mappings between keys and their labels is being lost.

in the example above, the field :category-list has the label "categories"

I found what was causing my problem. I was looking for the row and column of a particular value in the table outside of the event thread and then selecting that row (within the event thread) - many times very quickly and occasionally this problem would occur. Definitely some non-deterministic threading voodoo.

I don't mind your -1 -1 hack that much any more ;) but incorrectly re-creating the column-key-map when the java.lang.ArrayIndexOutOfBoundsException is thrown definitely obfuscated the matter. I'll open a PR with a suggestion for an improvement but I don't have a real solution.

This issue is being caused by the use of clojure.core/proxy-super. That function is not thread safe and one of the symptoms is that occasionally a proxy object will forget the overriding functions permanently if concurrent calls are made to the same method. It is difficult to resolve the problems with proxy without access to the Clojure compiler.

I think the easiest solution is to replace the use of proxy. I'm exploring using the proxy-plus library from RedPlanetLabs which is almost a drop-in replacement but there is still some work to do there implementing a proxy-super method for that proxy object. It shouldn't take long though (see redplanetlabs/proxy-plus#17 - it is technically possible).