<div class="gmail_quote"><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex;">Nick and I sorted this out this evening. I assume he&#39;ll write up a summary... ;)<br></blockquote>
<div> </div><div>Indeed. If I understood the problem it&#39;s that capturing the exception in a closure isn&#39;t sufficient, you need to break-off a continuation containing the process to be debugged, then use that continuation to debug the problem.</div>
<div><br></div><div>The #handleException: code becomes:</div><div><br></div><div><div>handleException: ex</div><div><span class="Apple-tab-span" style="white-space:pre">        </span>| renderContinuation shouldDebug |</div><div>
<span class="Apple-tab-span" style="white-space:pre">        </span>renderContinuation := self createRenderContinuation.</div><div><span class="Apple-tab-span" style="white-space:pre">        </span></div><div><span class="Apple-tab-span" style="white-space:pre">        </span>[</div>
<div><span class="Apple-tab-span" style="white-space:pre">        </span>shouldDebug := self session presenter call: (WAWalkback current exception: ex) ]</div><div><span class="Apple-tab-span" style="white-space:pre">        </span>on: WARenderNotification </div>
<div><span class="Apple-tab-span" style="white-space:pre">        </span>do: [ :exDontCare |</div><div><span class="Apple-tab-span" style="white-space:pre">                </span>&quot;redirect the main page to the error location&quot;</div><div>
<span class="Apple-tab-span" style="white-space:pre">                </span>self requestContext respond: </div><div><span class="Apple-tab-span" style="white-space:pre">                        </span>[ :response | </div><div><span class="Apple-tab-span" style="white-space:pre">                        </span>response</div>
<div><span class="Apple-tab-span" style="white-space:pre">                                </span>contentType: WAMimeType textHtml;</div><div><span class="Apple-tab-span" style="white-space:pre">                                </span>nextPutAll: (WARenderCanvas builder</div><div>
<span class="Apple-tab-span" style="white-space:pre">                                        </span>fullDocument: true;</div><div><span class="Apple-tab-span" style="white-space:pre">                                        </span>scriptGeneratorClass: JQScriptGenerator; &quot;removes the onload from body&quot;</div>
<div><span class="Apple-tab-span" style="white-space:pre">                                        </span>render: [ :html | </div><div><span class="Apple-tab-span" style="white-space:pre">                                                </span>html script: &#39;parent.parent.window.location.replace(&quot;&#39;, renderContinuation registerForUrl greaseString, &#39;&quot;)&#39; ] )] ].</div>
<div><br></div><div><span class="Apple-tab-span" style="white-space:pre">        </span>shouldDebug ifTrue: [ </div><div><span class="Apple-tab-span" style="white-space:pre">                </span>GRPlatform current openDebuggerOn: ex ]</div>
</div><div><br></div><div>Explanation:</div><div><br></div><div>#call: creates a continuation. However we trap the WARenderNotification to allow us to render our own response. #call ,  #answer:(s) true if the user clicks to debug the process. When #call: returns, it restores the state prior to being called and the code continues executing at:</div>
<div><br></div><div> shouldDebug ifTrue: [ GRPlatform current openDebuggerOn: ex ]</div><div><br></div><div>As the state has been restored we can open a debugger on the exception and debug the original problem.</div><div>
<br></div><div>For comparison, our first implementation captured the continuation explicitly,  though we decided the above solution was neater:</div><div><br></div><div>the lines:</div><div><br></div><div><div>    shouldDebug := self session presenter call: (WAWalkback current exception: ex) ]</div>
<div>on: WARenderNotification </div><div>do: [ :exDontCare |</div></div><div><br></div><div>where replaced by:</div><div><br></div><div><div>shouldDebug := GRPlatform current seasideSuspendFlowDo: [ :cc |</div><div><span class="Apple-tab-span" style="white-space:pre">                </span>session presenter show: (WAWalkback current exception: ex) onAnswer: [:answer | cc value: answer ].</div>
</div><div><br></div><div>with the call to self requestContext respond: [...] inside the #seasideSuspendFlowDo:</div><div><br></div><div>I extracted the code to create the render continuation into a method #createRenderContinuation. If I understand correctly in Seaside3.1 there will be methods on WARequestContext to allow you to create continuations, which for example can be used to create a url for a callback from inside an actionContinuation block.</div>
<div><br></div><div>I hope I haven&#39;t made the explanation more confusing than the code....</div><div><br></div><div>Nick</div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex;">
<div class="gmail_quote"><div><div></div><div class="h5">On Tue, Aug 30, 2011 at 10:05 AM, Nick Ager <span dir="ltr">&lt;<a href="mailto:nick.ager@gmail.com" target="_blank">nick.ager@gmail.com</a>&gt;</span> wrote:<br>

</div></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div><div></div><div class="h5">Hi,<div><br></div><div>I&#39;m using a hidden iframe in my file upload component. If an error occurs during uploading, the error page is rendered in the hidden iframe - which means I end up debugging by inspecting the http responses in the browsers development tools. Not ideal so I thought I&#39;d trap the error and present the page myself. In the exception trap I send a script to the page which redirects the parent window to the error page - &#39;parent.parent.window.location.replace(..error url..)&#39; This works well apart from when I click on the &quot;debug&quot; link, the debugger in the Pharo reports: &quot;Error: context not in self&quot; and doesn&#39;t shows an unrelated (to the original error) stack trace.</div>



<div><br></div><div>I&#39;ve patched together my error handling code, by examining the error handling filter in Seaside. I&#39;ve had to add an accessor on WASession&gt;&gt;#continuations, which probably indicates there is an easier way to achieve my goal:</div>



<div><br></div><div><div>handleException: ex</div><div><span style="white-space:pre-wrap">        </span>| session requestContext key continuation renderContinuation |</div><div><span style="white-space:pre-wrap">        </span>requestContext := self requestContext.</div>



<div><span style="white-space:pre-wrap">        </span>session := requestContext session.</div><div><span style="white-space:pre-wrap">        </span>key := requestContext request fields at: session actionField.</div>
<div><span style="white-space:pre-wrap">        </span>continuation := session continuations at: key.</div><div><span style="white-space:pre-wrap">        </span>renderContinuation := continuation createRenderContinuation.</div>
<div><span style="white-space:pre-wrap">        </span>session presenter show: (WAWalkback current exception: ex) onAnswer: [:answer | </div><div><span style="white-space:pre-wrap">                </span>answer ifTrue: [ </div>
<div><span style="white-space:pre-wrap">                        </span>self flag: #todo. &quot;work out why I get the error: &#39;Error: context not in self&#39;&quot;</div><div><span style="white-space:pre-wrap">                        </span>GRPlatform current openDebuggerOn: ex ] ].</div>



<div><br></div><div><span style="white-space:pre-wrap">        </span>&quot;redirect the main page to the error location&quot;</div><div><span style="white-space:pre-wrap">        </span>self requestContext respond: </div>
<div><span style="white-space:pre-wrap">                </span>[ :response | </div><div><span style="white-space:pre-wrap">                </span>response</div><div><span style="white-space:pre-wrap">                        </span>contentType: WAMimeType textHtml;</div>



<div><span style="white-space:pre-wrap">                        </span>nextPutAll: (WARenderCanvas builder</div><div><span style="white-space:pre-wrap">                                </span>fullDocument: true;</div><div><span style="white-space:pre-wrap">                                </span>scriptGeneratorClass: JQScriptGenerator; &quot;removes the onload from body&quot;</div>



<div><span style="white-space:pre-wrap">                                </span>render: [ :html | </div><div><span style="white-space:pre-wrap">                                        </span>html script: &#39;parent.parent.window.location.replace(&quot;&#39;, renderContinuation registerForUrl  greaseString, &#39;&quot;)&#39; ] )]</div>



</div><div><br></div><div>I&#39;ve a horrible feeling I&#39;m missing an obvious, simpler solution</div><div><br></div><div>Thanks,</div><div><br></div><font color="#888888"><div>Nick</div>
</font><br></div></div>_______________________________________________<br>
seaside mailing list<br>
<a href="mailto:seaside@lists.squeakfoundation.org" target="_blank">seaside@lists.squeakfoundation.org</a><br>
<a href="http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside" target="_blank">http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside</a><br>
<br></blockquote></div><br>
<br>_______________________________________________<br>
seaside mailing list<br>
<a href="mailto:seaside@lists.squeakfoundation.org">seaside@lists.squeakfoundation.org</a><br>
<a href="http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside" target="_blank">http://lists.squeakfoundation.org/cgi-bin/mailman/listinfo/seaside</a><br>
<br></blockquote></div><br>