From avi at beta4.com Fri Jul 2 23:06:57 2004 From: avi at beta4.com (Avi Bryant) Date: Fri Jul 2 23:07:03 2004 Subject: [Seaside] 2.5a6 Message-ID: Hi all, I've put a new alpha release up. The significant changes are: - I've incorporated a number of small fixes to the XHTML produced by Seaside, submitted by Michel Bany. For example, Seaside will no longer automatically assign "id" attributes to form inputs, because this was frequently leading to duplicate IDs. At the same time, I changed the doctype to XHTML Transitional from XHTML Strict, because there is still widespread use among Seaside users of deprecated attributes such as "border". - Sessions (and other request handlers) will be sent #unregistered when they are moved from the cache. This is a good place to close database connections and do other such cleanup. - A new pass has been added to the render loop, which sends #updateRoot: to every visible component or decoration. The argument to #updateRoot: is a WAHtmlRoot object, which is responsible for managing the contents of the section of the document, as well as the and tags (but not the contents of ). Any updates to these elements (adding attributes, adding tags to the head) must be done during the #updateRoot: pass, which happens before the full render pass. Useful methods on WAHtmlRoot include #title:, #docType:, #addScript:, #addStyle:, and accessors for the attributes of the , , and tags (#htmlAttributes, #headAttributes, #bodyAttributes). - The StyleGroup experiment has been removed, and replaced with WAStringLibrary. The idea behind StringLibrary is this: subclasses of StringLibrary implement methods that return string literals with either CSS or Javascript code. When configuring an application, you can add any libraries that have relevant scripts or styles, and all of the code in these libraries will be linked in to every page of the application. By default, applications include WAStandardStyles and WAStandardScripts; see these classes for examples. The pen icon on halos will now open up a Library Browser, which lets you (or a designer) easily edit these libraries. - WAHtmlAttributes now includes #addClass: so that you can easily add multiple (space separated) values to the "class" attribute. - Several fixes from the list: don't encode chars over 128, allow custom attributes on checkboxes, conform to VW's #on:do: in WAWalkback. Also included is work in progress on the new WACanvas rendering system, including a subclass (WARenderCompat) that provides backwards compatibility with WAHtmlRenderer. There's no real reason for anyone to use WARenderCompat over WAHtmlRenderer, but it will help me with migration: as I extend the canvas system, more and more of the methods of WARenderCompat will be able to use high level canvas methods rather than sends to #tag:do: and #attributes, which will provide a running status of the canvas classes. The next push is to get streaming truly working (at least with Swazoo, it may be too difficult with Comanche). At that point, I'll release 2.5b. Avi From jase at dufair.org Sat Jul 3 00:24:22 2004 From: jase at dufair.org (Jason Dufair) Date: Sat Jul 3 00:24:28 2004 Subject: [Seaside] Searchable archives Message-ID: Avi, Julian, et. al. - Would it be possible to make the Seaside list archives searchable somehow? -- Jason Dufair - jase@dufair.org http://www.dufair.org/ "The oldest one captains the bleak white ship of bone with palsied hands The one of middle years wears a hope like chains The youngest one cries tears of scarlet, and adjusts her latest smile" -- ToasterLeavings From avi at beta4.com Sat Jul 3 00:26:17 2004 From: avi at beta4.com (Avi Bryant) Date: Sat Jul 3 00:26:20 2004 Subject: [Seaside] Searchable archives In-Reply-To: References: Message-ID: On Jul 2, 2004, at 3:24 PM, Jason Dufair wrote: > Avi, Julian, et. al. - > > Would it be possible to make the Seaside list archives searchable > somehow? How about google? For example, search for "site:http://lists.squeakfoundation.org css". Avi From avi at beta4.com Sat Jul 3 04:36:27 2004 From: avi at beta4.com (Avi Bryant) Date: Sat Jul 3 04:36:30 2004 Subject: [Seaside] backlogSize Message-ID: I've noticed that sometimes when using Safari with Squeak and Seaside, it's very easy to get dropped connections from Comanche. This seems to be because of the #backlogSize: setting: if I increase it with "TcpListener backlogSize: 100", and then restart WAKom, the problem goes away. I see this more often when there are a lot of stylesheets being included (which makes sense - more parallel requests), but I don't see it at all from other browsers (from which I can only assume that Safari is somehow especially impatient with its timeouts - anyone have a fuller explanation?). Anyway, if anyone's been having the same or similar problems, don't forget about #backlogSize:. Avi From kamk at volny.cz Sat Jul 3 12:25:44 2004 From: kamk at volny.cz (Kamil Kukura) Date: Sat Jul 3 12:25:48 2004 Subject: [Seaside] Re: Searchable archives In-Reply-To: References: Message-ID: <40E689A8.3010604@volny.cz> Jason Dufair wrote: > Avi, Julian, et. al. - > > Would it be possible to make the Seaside list archives searchable > somehow? You can use this link: http://news.gmane.org/gmane.comp.lang.smalltalk.squeak.seaside/cutoff=1228 there's Search at bottom. -- Kamil From cdshaffer at acm.org Sat Jul 3 21:14:40 2004 From: cdshaffer at acm.org (C. David Shaffer) Date: Sat Jul 3 21:14:29 2004 Subject: [Seaside] Testing seaside components (second try) Message-ID: <40E705A0.2080702@acm.org> I spent a little time on the code that I posted previously and have attached a version with a few improvements: - most HTML input components are now supported (radio, checkbox, text, password, textarea) - a web-based test runner was added + if a component answers a non-nil #suite then its halo will show a test button...the "tile" halo button -- sorry :-( -- could someone draw a better one for me? + if an application answers a non-nil #suite then it will have a test link in the config app + a default implementation of WAComponent>>suite is provided which appends 'Test' to the class name and if said class exists, returns it as a test suite - several tests were written based off the the WAAllTests and other components provided I still need to write more tests based on the the components provided with Seaside. I also need to check if my code works in 2.5a6. The web-based test runner interface may not be the best idea since tests may take too long to complete (depending on your browser's timeout). I could for a periodic client refresh but I'm not sure if it is worth the trouble. Finally if anyone has any interest it porting this to VW, I'd like to help. I tried but I encountered two problems: namespace (easy to solve with text editor) and XML library differences. While this is still rough, I'm starting to feel that many parts of it are working reasonably well. If anyone is using or starts using this, I'd appreciate feedback. And yes, I'll write up a tutorial on how to use it but, as always, the example code should be a good start...look at SCSampleComponentTest and WAAllTestsTest. David From cdshaffer at acm.org Sat Jul 3 21:15:18 2004 From: cdshaffer at acm.org (C. David Shaffer) Date: Sat Jul 3 23:11:27 2004 Subject: [Seaside] Testing...here's the code, sorry Message-ID: <40E705C6.1030404@acm.org> -------------- next part -------------- SystemOrganization addCategory: #SeasideTesting! WADecoration subclass: #SCAnswerChecker instanceVariableNames: 'hasAnswer answerValue ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! TestCase subclass: #SCComponentTest instanceVariableNames: 'app requests pseudomain ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WARenderLoop subclass: #SCRenderLoop instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! SCComponentTest subclass: #SCSampleComponentTest instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! Object subclass: #SCSeasideStateMarker instanceVariableNames: 'sessionId continuationId ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! SCSeasideStateMarker subclass: #SCSeasideAnchor instanceVariableNames: 'fullUrl anchorNumber path label ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WAComponent subclass: #SCTestComponent1 instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WAComponent subclass: #SCTestComponent2 instanceVariableNames: 'firstSent secondSent thirdSent ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WAComponent subclass: #SCTestComponent3 instanceVariableNames: 'field1 field2 button1WasPressed button2WasPressed ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WAComponent subclass: #SCTestRunner instanceVariableNames: 'case result ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WAComponent subclass: #SCTestTracker instanceVariableNames: 'case ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WAApplication subclass: #SCTesterApplication instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! WARenderLoopMain subclass: #SCTestingPseudomain instanceVariableNames: 'renderLoop checker ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! Object subclass: #SCXMLElementWrapper instanceVariableNames: 'xmlElement ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! SCXMLElementWrapper subclass: #SCParsedSeasideDocument instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! SCXMLElementWrapper subclass: #SCSeasideForm instanceVariableNames: 'inputs buttons inputValues ' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! SCComponentTest subclass: #WAAllTestsTest instanceVariableNames: '' classVariableNames: '' poolDictionaries: '' category: 'SeasideTesting'! SCAnswerChecker class instanceVariableNames: ''! SCComponentTest class instanceVariableNames: ''! SCRenderLoop class instanceVariableNames: ''! SCSampleComponentTest class instanceVariableNames: ''! SCSeasideStateMarker class instanceVariableNames: ''! SCSeasideAnchor class instanceVariableNames: ''! SCTestComponent1 class instanceVariableNames: ''! SCTestComponent2 class instanceVariableNames: ''! SCTestComponent3 class instanceVariableNames: ''! SCTestRunner class instanceVariableNames: ''! SCTestTracker class instanceVariableNames: ''! SCTesterApplication class instanceVariableNames: ''! SCTestingPseudomain class instanceVariableNames: ''! SCXMLElementWrapper class instanceVariableNames: ''! SCParsedSeasideDocument class instanceVariableNames: ''! SCSeasideForm class instanceVariableNames: ''! WAAllTestsTest class instanceVariableNames: ''! !SCTesterApplication commentStamp: 'cds 6/18/2004 20:46' prior: 0! Just need to expose the session registry! !SCSeasideForm methodsFor: 'posting' stamp: 'cds 6/20/2004 21:08'! actionUrl ^ xmlElement attributeAt: 'action'! ! !SCSeasideForm methodsFor: 'inputs' stamp: 'cds 6/24/2004 10:28'! activateCheckboxWithId: stringId self setCheckboxWithId: stringId to: true! ! !SCSeasideForm methodsFor: 'inputs' stamp: 'cds 6/24/2004 00:25'! activateRadioButtonWithId: stringId | elem | elem _ self inputXMLElementWithId: stringId. (elem attributeAt: 'type') = 'radio' ifFalse: [self error: 'Not a radio button']. self inputWithName: (elem attributeAt: 'name') value: (elem attributeAt: 'value')! ! !SCXMLElementWrapper methodsFor: 'parts' stamp: 'cds 6/23/2004 14:04'! allElements | result | result _ OrderedCollection new. self allElementsIn: xmlElement addTo: result. ^ result! ! !SCXMLElementWrapper methodsFor: 'parts' stamp: 'cds 6/20/2004 18:16'! allElementsIn: element addTo: result result add: element. element elementsDo: [:subElement | self allElementsIn: subElement addTo: result]! ! !SCXMLElementWrapper methodsFor: 'parts' stamp: 'cds 6/20/2004 18:16'! allElementsNamed: tagName in: element addTo: result element name = tagName ifTrue: [result add: element] ifFalse: [element elementsDo: [:subElement | self allElementsNamed: tagName in: subElement addTo: result]]! ! !SCSeasideAnchor methodsFor: 'accessing' stamp: 'cds 6/18/2004 14:19'! anchorNumber ^anchorNumber! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/20/2004 09:49'! anchorNumber: number | num | num := number isString ifTrue: [number] ifFalse: [number asString]. ^self anchors detect: [:each | each anchorNumber = num] ifNone: []! ! !SCSeasideAnchor methodsFor: 'accessing' stamp: 'cds 6/18/2004 14:19'! anchorNumber: anObject anchorNumber := anObject! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/19/2004 21:55'! anchorWithId: aString ^self anchorWithId: aString ifNone: []! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/19/2004 21:54'! anchorWithId: aString ifNone: aBlock | res | res _ self elementWithId: aString ifNone: []. ^res ifNil: aBlock ifNotNil: [SCSeasideAnchor fromXMLElement: res]! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/23/2004 14:05'! anchorWithLabel: aString ^ self anchors detect: [:anchor | anchor label = aString] ifNone: []! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/20/2004 18:18'! anchors | result | result _ OrderedCollection new. self allElementsNamed: #a in: xmlElement addTo: result. result _ result select: [:each | each attributes includesKey: #href]. ^ result collect: [:each | SCSeasideAnchor fromXMLElement: each]! ! !SCTestingPseudomain methodsFor: 'accessing' stamp: 'cds 6/19/2004 20:46'! answerChecker ^checker! ! !SCAnswerChecker methodsFor: 'accessing' stamp: 'cds 6/19/2004 20:47'! answerValue ^answerValue! ! !SCSeasideAnchor methodsFor: 'converting' stamp: 'cds 6/19/2004 19:52'! asString ^ fullUrl! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 7/1/2004 11:48'! back self requests removeLast. ^ self requests last value! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 00:46'! backAndRefresh self back. ^self refresh! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/20/2004 18:18'! bodyElement ^ xmlElement elementAt: #body! ! !WAHtmlTest methodsFor: '*SeasideTesting' stamp: 'cds 6/24/2004 00:41'! booleanList ^booleanList! ! !SCTestComponent3 methodsFor: 'callbacks' stamp: 'cds 6/19/2004 22:46'! button1Pressed button1WasPressed _ true! ! !SCTestComponent3 methodsFor: 'accessing' stamp: 'cds 6/19/2004 22:46'! button1WasPressed ^button1WasPressed! ! !SCTestComponent3 methodsFor: 'callbacks' stamp: 'cds 6/19/2004 22:46'! button2Pressed button2WasPressed _ true! ! !SCTestComponent3 methodsFor: 'accessing' stamp: 'cds 6/19/2004 22:46'! button2WasPressed ^ button2WasPressed! ! !SCSeasideForm methodsFor: 'buttons' stamp: 'cds 6/25/2004 17:00'! buttonWithValue: aString ^self buttons detect: [:each | (each attributeAt: 'value' ifAbsent: []) = aString] ifNone: []! ! !SCSeasideForm methodsFor: 'buttons' stamp: 'cds 6/20/2004 18:32'! buttons ^buttons! ! !SCTestComponent1 class methodsFor: 'seaside' stamp: 'cds 6/19/2004 00:31'! canBeRoot ^true! ! !SCTestComponent2 class methodsFor: 'seaside' stamp: 'cds 6/18/2004 21:18'! canBeRoot ^true! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 19:54'! checkForSessionInUrl: aString | a | a _ SCSeasideAnchor fromHref: aString. ^a! ! !WAHtmlRenderer methodsFor: '*SeasideTesting-override' stamp: 'cds 6/24/2004 10:35'! checkboxWithValue: aBoolean callback: callbackBlock | value originalAttributes | value _ ValueHolder new. originalAttributes _ attributeBuffer. attributeBuffer _ nil. self hiddenInputWithCallback: [value contents: false]. attributeBuffer _ originalAttributes. self attributeAt: 'checked' put: aBoolean. self valueInputOfType: 'checkbox' value: 'true' callback: [value contents: true]. callbackBlock fixTemps. self hiddenInputWithCallback: [callbackBlock value: value contents]! ! !SCSeasideForm methodsFor: 'private-inputs' stamp: 'cds 6/24/2004 10:28'! clearInputWithName: aName ^ self inputValues removeKey: aName! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 7/1/2004 12:00'! component ^pseudomain component! ! !SCTestingPseudomain methodsFor: 'accessing' stamp: 'cds 6/19/2004 18:41'! component ^ renderLoop root! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 7/1/2004 12:00'! componentAnswered: value | checker | checker := pseudomain answerChecker. ^checker hasAnswer and: [checker answerValue = value]! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 7/1/2004 12:00'! configureApplicationForComponent: aComponent app preferenceAt: #deploymentMode put: true. pseudomain := SCTestingPseudomain new. app preferenceAt: #mainClass put: pseudomain! ! !SCSeasideStateMarker methodsFor: 'accessing' stamp: 'cds 6/18/2004 13:23'! continuationId ^continuationId! ! !SCSeasideStateMarker methodsFor: 'accessing' stamp: 'cds 6/18/2004 13:23'! continuationId: anObject continuationId := anObject! ! !SCTestingPseudomain methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 20:46'! createRoot | comp | checker _ SCAnswerChecker new. comp _ super createRoot. comp addDecoration: checker. ^ comp! ! !SCSeasideForm methodsFor: 'inputs' stamp: 'cds 6/24/2004 10:28'! deactivateCheckboxWithId: stringId self setCheckboxWithId: stringId to: false! ! !SCXMLElementWrapper methodsFor: 'parts' stamp: 'cds 6/20/2004 18:16'! elementWithId: aString ifNone: aBlock ^self allElements detect: [:each | (each attributeAt: 'id' ifAbsent: []) = aString] ifNone: aBlock! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/20/2004 20:51'! establishSession | req | req := HttpRequest readFromStream: (self httpGetRequestStreamFor: app baseUrl asString). ^SCParsedSeasideDocument fromResponse: (self issueRequestUntilNotMoved: req)! ! !SCTestComponent3 methodsFor: 'accessing' stamp: 'cds 6/19/2004 22:43'! field1 ^field1! ! !SCTestComponent3 methodsFor: 'accessing' stamp: 'cds 6/19/2004 22:43'! field1: anObject field1 := anObject! ! !SCTestComponent3 methodsFor: 'accessing' stamp: 'cds 6/19/2004 22:43'! field2 ^field2! ! !SCTestComponent3 methodsFor: 'accessing' stamp: 'cds 6/19/2004 22:43'! field2: anObject field2 := anObject! ! !SCTestComponent2 methodsFor: 'accessing' stamp: 'cds 6/18/2004 14:45'! firstSent ^firstSent! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/20/2004 20:51'! followAnchor: anAnchor | req | self assert: anAnchor notNil. req := HttpRequest readFromStream: (self httpGetRequestStreamFor: anAnchor asString). ^SCParsedSeasideDocument fromResponse: (self issueRequestUntilNotMoved: req)! ! !SCTestRunner class methodsFor: 'instance creation' stamp: 'cds 7/2/2004 15:20'! forCase: aTestCase ^ self new initializeForCase: aTestCase! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/19/2004 23:05'! formWithId: aString ^ self formWithId: aString ifNone: []! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/20/2004 18:27'! formWithId: aString ifNone: aBlock | res | res _ self elementWithId: aString ifNone: []. ^ res ifNil: aBlock ifNotNil: [SCSeasideForm fromXMLElement: res]! ! !SCParsedSeasideDocument methodsFor: 'parts' stamp: 'cds 6/20/2004 18:27'! forms | result | result _ OrderedCollection new. self allElementsNamed: #form in: xmlElement addTo: result. ^ result collect: [:each | SCSeasideForm fromXMLElement: each]! ! !SCSeasideAnchor class methodsFor: 'instance creation' stamp: 'cds 6/18/2004 13:23'! fromHref: aString ^self new initializeFromHref: aString! ! !SCParsedSeasideDocument class methodsFor: 'instance creation' stamp: 'cds 6/18/2004 15:22'! fromResponse: aResponse aResponse contents reset. ^ self fromStream: aResponse contents! ! !SCParsedSeasideDocument class methodsFor: 'instance creation' stamp: 'cds 6/20/2004 18:21'! fromStream: aStream | xmlDoc | xmlDoc _ XMLDOMParser parseDocumentFrom: aStream. ^ self fromXMLDoc: xmlDoc! ! !SCParsedSeasideDocument class methodsFor: 'instance creation' stamp: 'cds 6/20/2004 18:25'! fromXMLDoc: aDoc ^ self fromXMLElement: (aDoc elementAt: #html)! ! !SCSeasideAnchor class methodsFor: 'instance creation' stamp: 'cds 6/19/2004 19:45'! fromXMLElement: anXMLElement ^ self new initializeFromXMLElement: anXMLElement! ! !SCXMLElementWrapper class methodsFor: 'instance creation' stamp: 'cds 6/20/2004 18:17'! fromXMLElement: anElement ^ self new initializeFromXMLElement: anElement! ! !SCSeasideAnchor methodsFor: 'accessing' stamp: 'cds 6/19/2004 19:51'! fullUrl: aString fullUrl _ aString! ! !SCAnswerChecker methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 20:45'! handleAnswer: anObject (super handleAnswer: anObject) ifFalse: [hasAnswer _ true. answerValue _ anObject] ifTrue: [^true]. ^ false! ! !SCTesterApplication methodsFor: 'accessing' stamp: 'cds 6/18/2004 20:46'! handlerWithKey: aKey ^handlersByKey at: aKey ifAbsent: []! ! !SCAnswerChecker methodsFor: 'accessing' stamp: 'cds 6/19/2004 20:47'! hasAnswer ^hasAnswer! ! !WAComponent class methodsFor: '*SeasideTesting' stamp: 'cds 7/3/2004 14:58'! hasTestSuite ^self suite notNil! ! !SCSeasideForm methodsFor: 'posting' stamp: 'cds 6/25/2004 17:06'! httpDataWithButton: button | resultStream | resultStream _ WriteStream on: ''. button attributes at: 'name' ifPresent: [:buttonName | resultStream nextPutAll: buttonName. button attributes at: 'value' ifPresent: [:value | resultStream nextPut: $=; nextPutAll: value]. self inputValues notEmpty ifTrue: [resultStream nextPut: $&]]. self inputValues keys do: [:key | self writeHttpDataFor: key value: (self inputValues at: key) on: resultStream] separatedBy: [resultStream nextPut: $&]. ^ resultStream contents! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/21/2004 01:01'! httpGetRequestStreamFor: url ^ ('GET ' , url , ' HTTP/1.0' , String crlf) readStream! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/21/2004 01:34'! httpPostRequestStreamForUrl: url data: postData ^ ('POST ' , url , ' HTTP/1.0 ' , String crlf , 'Content-Length: ' , postData size printString , String crlf , 'Content-type: application/x-www-form-urlencoded' , String crlf , String crlf , postData) readStream! ! !XMLTokenizer methodsFor: '*SeasideTesting-overrides' stamp: 'cds 6/22/2004 23:49'! initEntities | ents | ents _ Dictionary new. ents at: 'amp' put: (DTDEntityDeclaration name: 'amp' value: $&); at: 'quot' put: (DTDEntityDeclaration name: 'amp' value: $"); at: 'apos' put: (DTDEntityDeclaration name: 'apos' value: $'); at: 'gt' put: (DTDEntityDeclaration name: 'gt' value: $>); at: 'lt' put: (DTDEntityDeclaration name: 'lt' value: $<); at: 'nbsp' put: (DTDEntityDeclaration name: 'nbsp' value: Character space). ^ ents! ! !SCTestComponent2 methodsFor: 'initialization' stamp: 'cds 6/19/2004 00:44'! initialize super initialize. self session registerObjectForBacktracking: self. firstSent _ false. secondSent _ false. thirdSent _ false! ! !SCTestRunner methodsFor: 'initialization' stamp: 'cds 7/3/2004 14:33'! initializeForCase: aTestCase case := aTestCase. result := aTestCase run! ! !SCSeasideAnchor methodsFor: 'initialize' stamp: 'cds 6/19/2004 19:51'! initializeFromHref: aString | parts | self fullUrl: aString. parts _ aString findTokens: '?'. parts isEmpty ifTrue: [^ self]. self path: parts first. parts size > 1 ifTrue: [(parts second findTokens: '&') do: [:each | self variableFromString: each]]! ! !SCSeasideAnchor methodsFor: 'initialize' stamp: 'cds 6/23/2004 14:09'! initializeFromXMLElement: anXMLElement self initializeFromHref: (anXMLElement attributeAt: 'href'). label _ anXMLElement contents first string! ! !SCSeasideForm methodsFor: 'initialize' stamp: 'cds 6/27/2004 00:07'! initializeFromXMLElement: anXMLElement super initializeFromXMLElement: anXMLElement. inputs _ OrderedCollection new. self allElementsNamed: #input in: xmlElement addTo: inputs. self allElementsNamed: #select in: xmlElement addTo: inputs. self allElementsNamed: #textarea in: xmlElement addTo: inputs. buttons _ inputs select: [:each | (each attributeAt: 'type' ifAbsent: []) = 'submit']. self initializeValuesFromCurrentInputs! ! !SCXMLElementWrapper methodsFor: 'initialize' stamp: 'cds 6/20/2004 18:17'! initializeFromXMLElement: anElement xmlElement _ anElement! ! !SCSeasideForm methodsFor: 'initialize' stamp: 'cds 6/25/2004 17:16'! initializeValuesFromCurrentInputs | value name shouldSet type | (inputs reject: [:each | (each attributeAt: 'type') = 'submit']) do: [:each | name _ each attributeAt: 'name'. value _ each attributes at: 'value' ifAbsent: []. shouldSet _ name notNil. type _ each attributeAt: 'type'. ((type = 'radio' or: [type = 'checkbox']) and: [(each attributeAt: 'checked' ifAbsent: []) ~= 'checked']) ifTrue: [shouldSet _ false]. shouldSet ifTrue: [self inputWithName: name value: value]]! ! !SCSeasideForm methodsFor: 'private-inputs' stamp: 'cds 6/20/2004 18:30'! inputValues ^ inputValues ifNil: [inputValues _ Dictionary new]! ! !SCSeasideForm methodsFor: 'private-inputs' stamp: 'cds 6/24/2004 00:17'! inputWithName: stringName value: stringValue (self inputXMLElementWithName: stringName) ifNil: [self error: 'No such input element']. self inputValues at: stringName put: stringValue! ! !SCSeasideForm methodsFor: 'private-inputs' stamp: 'cds 6/24/2004 00:13'! inputXMLElementWithId: anId ^inputs detect: [:each | (each attributes at: 'id' ifAbsent: []) = anId] ifNone: []! ! !SCSeasideForm methodsFor: 'private-inputs' stamp: 'cds 6/24/2004 00:17'! inputXMLElementWithName: aName ^ inputs detect: [:each | (each attributes at: 'name' ifAbsent: []) = aName] ifNone: []! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 7/1/2004 11:49'! issueRequest: anHttpRequest | result | result _ WAKom default processHttpRequest: anHttpRequest. self requests add: anHttpRequest -> result. ^result! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/20/2004 20:51'! issueRequestUntilNotMoved: anHttpRequest | response req newUrl | req := anHttpRequest. [response := self issueRequest: req. response status = #tempMoved] whileTrue: [self requests removeLast. newUrl := response fields at: 'Location'. self checkForSessionInUrl: newUrl. req := HttpRequest readFromStream: (self httpGetRequestStreamFor: newUrl)]. ^response! ! !SCSeasideAnchor methodsFor: 'accessing' stamp: 'cds 6/23/2004 14:06'! label ^label! ! !WAHtmlTest methodsFor: '*SeasideTesting' stamp: 'cds 6/25/2004 17:18'! message ^message! ! !SCSeasideForm methodsFor: 'private-inputs' stamp: 'cds 6/24/2004 00:20'! nameForElementWithId: aString ^ (self inputXMLElementWithId: aString) attributeAt: 'name'! ! !SCTestingPseudomain methodsFor: 'hack' stamp: 'cds 6/18/2004 20:31'! new ^self! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/18/2004 20:51'! newApplicationForComponent: aComponentClass app _ SCTesterApplication path: aComponentClass name. app configuration addAncestor: WARenderLoopConfiguration localConfiguration. app preferenceAt: #rootComponent put: aComponentClass. WADispatcher default registerEntryPoint: app at: aComponentClass name. self configureApplicationForComponent: aComponentClass. ^ app! ! !WAHtmlTest methodsFor: '*SeasideTesting' stamp: 'cds 6/25/2004 16:54'! number ^number! ! !SCSeasideForm methodsFor: 'private-inputs' stamp: 'cds 6/25/2004 16:52'! optionValuesByTextForSelect: aSelectElement | optionElements result | optionElements _ aSelectElement elements select: [:each | each name = 'option']. result _ Dictionary new. optionElements do: [:each | result at: (each contents first string) put: (each attributeAt: 'value') ]. ^result! ! !SCSeasideAnchor methodsFor: 'accessing' stamp: 'cds 6/19/2004 19:54'! path: aString path _ aString! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 7/1/2004 11:48'! refresh ^ SCParsedSeasideDocument fromResponse: (self issueRequestUntilNotMoved: self requests last key)! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/18/2004 15:13'! removeApplication WADispatcher default removeEntryPoint: app.! ! !SCTestRunner methodsFor: 'rendering' stamp: 'cds 7/3/2004 14:55'! renderBrowserAnchorFor: aTestCase on: html | browser | html anchorWithPopupAction: [browser _ WABrowser fullOnClass: aTestCase class. browser model selectedMessageName: aTestCase selector. self call: browser] extent: 825@560 text: 'Browse'! ! !WAHtmlTest methodsFor: '*SeasideTesting-override' stamp: 'cds 6/24/2004 10:30'! renderCheckboxesOn: html html text: booleanList. html paragraph. html cssId: 'checkbox-form'. html form: [booleanList do: [:assoc | html text: assoc key; space. html cssId: 'cb-' , assoc key asString. html checkboxWithValue: assoc value callback: [:b | assoc value: b]. html break]. html submitButton]! ! !SCTestComponent1 methodsFor: 'rendering' stamp: 'cds 6/19/2004 20:26'! renderContentOn: html html text: 'hello'! ! !SCTestComponent2 methodsFor: 'accessing' stamp: 'cds 6/19/2004 21:55'! renderContentOn: html self firstSent ifFalse: [html anchorWithAction: [self sendFirst] text: 'first link']. html text: 'hello'. self secondSent ifFalse: [html cssId: 'second'. html anchorWithAction: [self sendSecond] text: 'second link']. self thirdSent ifFalse: [ html cssId: 'third'. html anchorWithAction: [self sendThird] text: 'third link']! ! !SCTestComponent3 methodsFor: 'rendering' stamp: 'cds 6/19/2004 22:47'! renderContentOn: html html form: [html text: 'field1: '. html textInputOn: #field1 of: self. html br. html text: 'field2: '. html textInputOn: #field2 of: self. html br. html cssId: 'button1'. html submitButtonWithAction: [self button1Pressed]. html cssId: 'button2'. html submitButtonWithAction: [self button2Pressed]]! ! !SCTestRunner methodsFor: 'rendering' stamp: 'cds 7/3/2004 12:23'! renderContentOn: html html heading: case name level: 2. html text: result printString. html hr. self renderFailedOn: html. self renderErrorOn: html. self renderPassedOn: html. html br. html anchorWithAction: [self answer] text: 'close'! ! !WAHalo methodsFor: '*SeasideTesting-override' stamp: 'cds 7/3/2004 15:01'! renderContentOn: html html divClass: 'halo' with: [html divClass: 'halo-header' with: [html divClass: 'halo-icons' with: [html divClass: 'halo-mode' with: [html text: '['. html anchorWithAction: [self renderMode] text: 'R'. html text: ' | '. html anchorWithAction: [self sourceMode] text: 'S'. html text: ']']. html text: target class name. html space. self renderHalo: 'Halo-Debug' withPopup: [WABrowser fullOnClass: target class] on: html. self renderHalo: 'Halo-View' withPopup: [WAInspector on: target] on: html. self renderHalo: 'Halo-Paint' withPopup: [WAViewer on: target] on: html. (target class hasTestSuite) ifTrue: [self renderHalo: 'Halo-Tile' withPopup: [SCTestRunner forCase: target class suite] on: html]]]. html divClass: 'halo-contents' with: [self perform: mode contents with: html]]! ! !SCTestRunner methodsFor: 'rendering' stamp: 'cds 7/3/2004 14:56'! renderErrorOn: html html heading: 'Errors:' level: 3. result errors do: [:each | html cssClass: 'error-test'. html span: [html text: each printString]. html space. html anchorWithAction: [each debug] text: 'Debug'. html space. self renderBrowserAnchorFor: each on: html. html br]. html hr! ! !SCTestRunner methodsFor: 'rendering' stamp: 'cds 7/3/2004 14:52'! renderFailedOn: html html heading: 'Failed:' level: 3. result failures do: [:each | html cssClass: 'failed-test'. html span: each printString. html space. html anchorWithAction: [each debugAsFailure] text: 'Debug'. html space. self renderBrowserAnchorFor: each on: html. html br]. html hr! ! !SCTestRunner methodsFor: 'rendering' stamp: 'cds 7/3/2004 14:56'! renderPassedOn: html html heading: 'Passed:' level: 3. result passed do: [:each | html cssClass: 'passed-test'. html span: each printString. html space. self renderBrowserAnchorFor: each on: html. html br]. html hr! ! !WAHtmlTest methodsFor: '*SeasideTesting-override' stamp: 'cds 6/24/2004 00:34'! renderRadioButtonsOn: html html text: booleanList. html paragraph. html cssId: 'radio-form'. html form: [booleanList do: [:assoc | | group | group _ html radioGroup. html text: assoc key; space. html cssId: assoc key asString , '-on'. html radioButtonInGroup: group selected: assoc value callback: [assoc value: true]. html cssId: assoc key asString , '-off'. html radioButtonInGroup: group selected: assoc value not callback: [assoc value: false]. html break]. html submitButton]! ! !WADispatcherEditor methodsFor: '*SeasideTesting-override' stamp: 'cds 7/3/2004 15:01'! renderRowForEntryPoint: anEntryPoint named: aString on: html | rootClass | html tableRowWith: [html anchorWithUrl: anEntryPoint basePath do: aString] with: [html anchorWithAction: [self configure: anEntryPoint] text: 'configure'. html space; anchorWithAction: [self remove: anEntryPoint] text: 'remove'. rootClass _ anEntryPoint preferenceAt: #rootComponent. (rootClass notNil and: [rootClass hasTestSuite]) ifTrue: [html space; anchorWithAction: [self test: rootClass] text: 'test']]! ! !WAHtmlTest methodsFor: '*SeasideTesting-override' stamp: 'cds 6/25/2004 16:45'! renderSelectsOn: html html text: number. html paragraph. html cssId: 'select-form'. html form: [html cssId: 'select-list'. html selectFromList: (1 to: 10) selected: number callback: [:i | number _ i]. html submitButton]! ! !WAHtmlTest methodsFor: '*SeasideTesting-override' stamp: 'cds 6/25/2004 16:57'! renderSubmitButtonsOn: html html text: number. html paragraph. html cssId: 'button-form'. html form: [(1 to: 10) do: [:i | html submitButtonWithAction: [number _ i] text: i. html space]]! ! !WAHtmlTest methodsFor: '*SeasideTesting-override' stamp: 'cds 6/27/2004 00:07'! renderTextAreaOn: html html cssId: 'textarea-form'. html form: [html text: message. html paragraph. html cssId: 'textarea-message'. html textAreaWithValue: message callback: [:v | message _ v]. html break; submitButton]! ! !WAHtmlTest methodsFor: '*SeasideTesting-override' stamp: 'cds 6/25/2004 17:23'! renderTextInputOn: html html cssId: 'textInput-form'. html form: [html text: message. html paragraph. html cssId: 'text-message'. html textInputWithValue: message callback: [:v | message _ v]. html submitButton]! ! !SCComponentTest methodsFor: 'accessing' stamp: 'cds 6/18/2004 20:24'! requests ^requests ifNil: [requests _ OrderedCollection new]! ! !SCRenderLoop methodsFor: 'accessing' stamp: 'cds 6/19/2004 18:43'! root ^root! ! !SCTestComponent2 methodsFor: 'accessing' stamp: 'cds 6/18/2004 14:45'! secondSent ^secondSent! ! !SCSeasideForm methodsFor: 'inputs' stamp: 'cds 6/25/2004 16:53'! selectListWithId: aStringId optionWithText: text | elem d value | elem _ self inputXMLElementWithId: aStringId. elem name = 'select' ifFalse: [self error: 'Not a select']. ((d _ self optionValuesByTextForSelect: elem) includesKey: text) ifFalse: [self error: 'No such option']. value _ d at: text. self inputWithName: (elem attributeAt: 'name') value: value! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/22/2004 23:46'! selectedComponent ^self component contents selectedComponent! ! !SCTestComponent2 methodsFor: 'callbacks' stamp: 'cds 6/18/2004 14:45'! sendFirst firstSent _ true! ! !SCTestComponent2 methodsFor: 'callbacks' stamp: 'cds 6/18/2004 14:45'! sendSecond secondSent _ true! ! !SCTestComponent2 methodsFor: 'callbacks' stamp: 'cds 6/19/2004 20:39'! sendThird thirdSent _ true. self answer: 1234! ! !SCSeasideStateMarker methodsFor: 'accessing' stamp: 'cds 6/18/2004 13:23'! sessionId ^sessionId! ! !SCSeasideStateMarker methodsFor: 'accessing' stamp: 'cds 6/18/2004 13:23'! sessionId: anObject sessionId := anObject! ! !SCSeasideForm methodsFor: 'inputs' stamp: 'cds 6/24/2004 10:27'! setCheckboxWithId: stringId to: aBoolean | elem | elem _ self inputXMLElementWithId: stringId. (elem attributeAt: 'type') = 'checkbox' ifFalse: [self error: 'Not a checkbox']. aBoolean ifTrue: [self inputWithName: (elem attributeAt: 'name') value: (elem attributeAt: 'value')] ifFalse: [self clearInputWithName: (elem attributeAt: 'name')]! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 20:36'! setUp requests _ OrderedCollection new! ! !SCTestingPseudomain methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 18:43'! start: aRequest self session redirect. (renderLoop _ SCRenderLoop new root: self createRoot) run! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/21/2004 01:34'! submitForm: form pressingButton: button | req url | self assert: form notNil. url _ form actionUrl. req _ HttpRequest readFromStream: (self httpPostRequestStreamForUrl: url data: (form httpDataWithButton: button)). ^ SCParsedSeasideDocument fromResponse: (self issueRequestUntilNotMoved: req)! ! !WAComponent class methodsFor: '*SeasideTesting' stamp: 'cds 7/3/2004 14:59'! suite ^(Smalltalk hasClassNamed: self testSuiteName) ifTrue: [Smalltalk classNamed: self testSuiteName] ifFalse: []! ! !SCComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 20:25'! tearDown self removeApplication. ! ! !WADispatcherEditor methodsFor: '*SeasideTesting' stamp: 'cds 7/2/2004 15:22'! test: rootClass self call: (SCTestRunner forCase: rootClass suite)! ! !SCSampleComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 20:38'! testAnswer | result | self newApplicationForComponent: SCTestComponent2. result _ self establishSession. result _ self followAnchor: (result anchorNumber: 3). self assert: (self componentAnswered: 1234)! ! !SCSampleComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 20:36'! testBack | result | self newApplicationForComponent: SCTestComponent2. result _ self establishSession. result _ self followAnchor: (result anchorNumber: 1). self assert: self component firstSent. self deny: self component secondSent. result _ self followAnchor: (result anchorNumber: 1). self backAndRefresh. self assert: self component firstSent. self deny: self component secondSent! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/25/2004 17:01'! testButtons | result form | self newApplicationForComponent: WAHtmlTest. result _ self establishSession. form _ result formWithId: 'button-form'. result _ self submitForm: form pressingButton: (form buttonWithValue: '5'). self assert: self component number = 5. form _ result formWithId: 'button-form'. result _ self submitForm: form pressingButton: (form buttonWithValue: '1'). self assert: self component number = 1.! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/25/2004 16:45'! testCheckbox | result form | self newApplicationForComponent: WAHtmlTest. result _ self establishSession. form _ result formWithId: 'checkbox-form'. form activateCheckboxWithId: 'cb-a'. result _ self submitForm: form pressingButton: form buttons first. self assert: self component booleanList first value. form _ result formWithId: 'checkbox-form'. form deactivateCheckboxWithId: 'cb-a'. result _ self submitForm: form pressingButton: form buttons first. self deny: self component booleanList first value. ! ! !SCSampleComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 19:59'! testComponent1 | result | self newApplicationForComponent: SCTestComponent1. result := self establishSession. self assert: result bodyElement contents first string = 'hello'! ! !SCSampleComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/19/2004 21:56'! testComponent2 | result | self newApplicationForComponent: SCTestComponent2. result _ self establishSession. result _ self followAnchor: (result anchorNumber: 1). self assert: self component firstSent. self deny: self component secondSent. result _ self followAnchor: (result anchorWithId: 'second'). self assert: self component firstSent. self assert: self component secondSent! ! !SCSampleComponentTest methodsFor: 'as yet unclassified' stamp: 'cds 6/24/2004 00:19'! testComponent3 | result form | self newApplicationForComponent: SCTestComponent3. result _ self establishSession. form _ result forms first. form textInputWithId: 'field1' value: 'bob'. form textInputWithId: 'field2' value: 'jane'. result _ self submitForm: form pressingButton: form buttons first. self assert: self component field1 = 'bob'. self assert: self component field2 = 'jane'! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 7/3/2004 12:22'! testError | result form | self newApplicationForComponent: WAAllTests. result _ self establishSession. result _ self followAnchor: (result anchorWithLabel: 'Input'). self assert: self selectedComponent class = WAInputTest. self assert: self selectedComponent integer = 42. form _ result forms first. form textInputWithId: 'nilString' value: 'bob'. result _ self submitForm: form pressingButton: form buttons first. self zork! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/27/2004 18:47'! testException | result form | self newApplicationForComponent: WAExceptionTest. form _ self establishSession forms first. result _ self submitForm: form pressingButton: (form buttonWithValue: 'Yes'). self assert: result bodyElement elements first contents first string = 'Caught: Error: foo'! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 7/3/2004 14:54'! testFailure | result form | self newApplicationForComponent: WAAllTests. result _ self establishSession. result _ self followAnchor: (result anchorWithLabel: 'Input'). self assert: self selectedComponent class = WAInputTest. self assert: self selectedComponent integer = 42. form _ result forms first. form textInputWithId: 'nilString' value: 'bob'. result _ self submitForm: form pressingButton: form buttons first. self assert: self selectedComponent nilString = 'some other name'! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/27/2004 19:05'! testNavigation | result form | self newApplicationForComponent: WAAllTests. result _ self establishSession. result _ self followAnchor: (result anchorWithLabel: 'Input'). self assert: self selectedComponent class = WAInputTest. self assert: self selectedComponent integer = 42. form _ result forms first. form textInputWithId: 'nilString' value: 'bob'. result _ self submitForm: form pressingButton: form buttons first. self assert: self selectedComponent nilString = 'bob'. result _ self followAnchor: (result anchorWithLabel: 'Html'). self assert: self selectedComponent class = WAHtmlTest. form _ result formWithId: 'radio-form'. form activateRadioButtonWithId: 'a-on'. result _ self submitForm: form pressingButton: form buttons first. self assert: self selectedComponent booleanList first value. form _ result formWithId: 'radio-form'. form activateRadioButtonWithId: 'a-off'. result _ self submitForm: form pressingButton: form buttons first. self deny: self selectedComponent booleanList first value. result _ self followAnchor: (result anchorWithLabel: 'Parent'). self assert: self selectedComponent class = WAParentTest. result _ self followAnchor: (result anchorWithLabel: 'swap parent'). self assert: result bodyElement elements first contents first string = 'foo'. self assert: (result anchorWithLabel: 'Html') isNil. form _ result forms first. result _ self submitForm: form pressingButton: form buttons first. self assert: (result anchorWithLabel: 'Html') notNil! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/25/2004 17:17'! testSelect | result form | self newApplicationForComponent: WAHtmlTest. result _ self establishSession. form _ result formWithId: 'select-form'. form selectListWithId: 'select-list' optionWithText: '7'. result _ self submitForm: form pressingButton: form buttons first. self assert: self component number = 7. form _ result formWithId: 'select-form'. self should: [form selectListWithId: 'select-list' optionWithText: '15'] raise: Error. form selectListWithId: 'select-list' optionWithText: '2'. result _ self submitForm: form pressingButton: form buttons first. self assert: self component number = 2. self assert: (form buttonWithValue: '22') isNil! ! !WAComponent class methodsFor: '*SeasideTesting' stamp: 'cds 7/3/2004 15:00'! testSuiteName ^(self name , 'Test') asSymbol! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/27/2004 00:08'! testTextAreaInput | result form | self newApplicationForComponent: WAHtmlTest. result _ self establishSession. form _ result formWithId: 'textarea-form'. self assert: form xmlElement elements first contents first string = 'Hello world!!'. self assert: self component message = 'Hello world!!'. form textInputWithId: 'textarea-message' value: 'bob'. result _ self submitForm: form pressingButton: form buttons first. form _ result formWithId: 'textarea-form'. self assert: form xmlElement elements first contents first string = 'bob'. self assert: self component message = 'bob'! ! !WAAllTestsTest methodsFor: 'tests' stamp: 'cds 6/25/2004 17:24'! testTextInput | result form | self newApplicationForComponent: WAHtmlTest. result _ self establishSession. form _ result formWithId: 'textInput-form'. self assert: form xmlElement elements first contents first string = 'Hello world!!'. self assert: self component message = 'Hello world!!'. form textInputWithId: 'text-message' value: 'bob'. result _ self submitForm: form pressingButton: form buttons first. form _ result formWithId: 'textInput-form'. self assert: form xmlElement elements first contents first string = 'bob'. self assert: self component message = 'bob'! ! !SCSeasideForm methodsFor: 'inputs' stamp: 'cds 6/24/2004 00:21'! textInputWithId: stringId value: stringValue self inputWithName: (self nameForElementWithId: stringId) value: stringValue! ! !SCSeasideForm methodsFor: 'inputs' stamp: 'cds 6/24/2004 00:18'! textInputWithName: stringName value: stringValue self inputWithName: stringName value: stringValue ! ! !SCTestComponent2 methodsFor: 'accessing' stamp: 'cds 6/19/2004 00:41'! thirdSent ^thirdSent! ! !SCSeasideAnchor methodsFor: 'initialize' stamp: 'cds 6/18/2004 14:19'! variableFromString: aString | parts | parts _ aString findTokens: '='. parts isEmpty ifTrue: [^ nil]. parts size = 1 ifTrue: [^ self anchorNumber: parts first]. parts first = '_s' ifTrue: [^ self sessionId: parts second]. parts first = '_k' ifTrue: [^ self continuationId: parts second]! ! !SCSeasideForm methodsFor: 'posting' stamp: 'cds 6/24/2004 00:21'! writeHttpDataFor: key value: value on: stream | name | name _ key. value ifNil: [^ stream nextPutAll: name]. value isString ifTrue: [stream nextPutAll: name; nextPut: $=; nextPutAll: value] ifFalse: [value do: [:each | self writeHttpDataFor: key value: each on: stream] separatedBy: [stream nextPut: $&]]! ! !SCXMLElementWrapper methodsFor: 'parts' stamp: 'cds 6/25/2004 17:21'! xmlElement ^xmlElement! ! From mbany at cincom.com Mon Jul 5 09:34:39 2004 From: mbany at cincom.com (Bany, Michel) Date: Mon Jul 5 09:34:43 2004 Subject: [Seaside] Testing seaside components (second try) Message-ID: > Finally if anyone has any interest it porting this to VW, I'd > like to help. I tried but I encountered two problems: > namespace (easy to solve with text editor) and XML library differences. Would you be willing to create a package with it. We would then be able to use the package exporter and automate the port. Michel. -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.squeakfoundation.org/pipermail/seaside/attachments/20040705/232088af/attachment.htm From mbany at cincom.com Mon Jul 5 18:41:07 2004 From: mbany at cincom.com (Bany, Michel) Date: Mon Jul 5 18:41:14 2004 Subject: [Seaside] 2.5a5 ported to VW Message-ID: Skipped content of type multipart/alternative-------------- next part -------------- A non-text attachment was scrubbed... Name: Seaside 2.5a5 port notes.pdf Type: application/octet-stream Size: 16447 bytes Desc: not available Url : http://lists.squeakfoundation.org/pipermail/seaside/attachments/20040705/12c5adf5/Seaside2.5a5portnotes.obj From avi at beta4.com Mon Jul 5 20:07:53 2004 From: avi at beta4.com (Avi Bryant) Date: Mon Jul 5 20:08:04 2004 Subject: [Seaside] 2.5a5 ported to VW In-Reply-To: References: Message-ID: <3C43B6FD-CEAE-11D8-A1BB-000A95DB7844@beta4.com> On Jul 5, 2004, at 9:41 AM, Bany, Michel wrote: > Avi, > During the tests I made on the port I discovered a few bugs, a couple > of STLINT "code critics" and a couple of VW compile warnings > The port includes some fixes for those bugs that are documented > in the attached document. You may want to check them so that you > can come up with the "official" fixes. Thanks, Michel. I'll integrate these fixes as soon as possible. Avi From avi at beta4.com Mon Jul 5 21:00:51 2004 From: avi at beta4.com (Avi Bryant) Date: Mon Jul 5 21:01:01 2004 Subject: [Seaside] 2.5a5 ported to VW In-Reply-To: <3C43B6FD-CEAE-11D8-A1BB-000A95DB7844@beta4.com> References: <3C43B6FD-CEAE-11D8-A1BB-000A95DB7844@beta4.com> Message-ID: On Jul 5, 2004, at 11:07 AM, Avi Bryant wrote: > > On Jul 5, 2004, at 9:41 AM, Bany, Michel wrote: > >> Avi, >> During the tests I made on the port I discovered a few bugs, a couple >> of STLINT "code critics" and a couple of VW compile warnings >> The port includes some fixes for those bugs that are documented >> in the attached document. You may want to check them so that you >> can come up with the "official" fixes. > > Thanks, Michel. I'll integrate these fixes as soon as possible. I've updated SqueakMap to point to Seaside2.5a6-avi.2.mcz, which includes these fixes. If you're interested, here are my notes on them: -- Compile errors: * WAComponent>>removeDecoration: - fixed * WAComponent>>show:onAnswer: - not actually a problem Bugs: * Seaside fails when trying to enable halos on the WACanvasTest component - this is indeed a bug, but I don't like the fix: it ought to be possible to enable halos on any component, regardless of which renderer class it uses. I don't have a solution to this yet, but I don't see much value in including the workaround in the meantime; better to remind ourslves that this is broken. * Seaside fails when the URL is an empty character string - fixed. * The HTML tag is not properly closed, - oops, fixed. *In a composition, the last tag in a component may be left undisplayed, if its rendering class is a kind of WACanvas - fixed, though used #close as the polymorphic send across WARenderCanvas and WAHtmlRenderer to be more explicit. * Missing block argument variable in exception handler - fixed. * Message sent but not implemented (WAPresenter>>decorationChainDo:) - moved #renderOn: down to WAComponent instead. * Method implemented but not sent (WARegistry>>expiredHandlerForRequest:) - removed. * IE6 requires - fixed. * WAStyleCollection doesn't check for nil attrs - fixed. * WACallbackStream, #upToEnd fails with sorted collection - fixed. From whitney at cs.sdsu.edu Mon Jul 5 21:31:01 2004 From: whitney at cs.sdsu.edu (Roger Whitney) Date: Mon Jul 5 21:31:22 2004 Subject: [Seaside] VW Seaside behind apache problems Message-ID: I am trying to use VW Seaside running behind an Apache web server. I am using the Perl CGI gateway that comes with VW 7.2. I am using VW Seaside 2.5a5.21.1. The version of Seaside should not matter since the problem seems to be due to the difference way the VW WebToolkit handles direct http requests and requests forwarded from a web server. When I send a request to Seaside from Apache an exception this thrown in SeasideServlet>>convertRequest:. The exception is caused in this method by the expression: aWaveRequest requestURI path aWaveRequest is a instance of VisualWave.Request. The result of aWaveRequest requestURI is a string, which does not understand path. aWaveRequest requestURI eventually calls WebRequest>>uri which is the source of this problem. VisualWave.WebRequest>>uri ^httpRequest isNil ifTrue: [self envAt: 'PATH_INFO'] ifFalse: [httpRequest uri]. This method will either return a string or an VisualWave.URI object. It would be better to return a URI object in both cases, ie uri ^httpRequest isNil ifTrue: [VisualWave.URI readFrom: (self envAt: 'PATH_INFO') readStream] ifFalse: [httpRequest uri]. Once this problem is fixed one runs into another exception when Seaside>>convertRequest: executes aWaveRequest webRequest httpRequest httpHeaders as the message httpRequest returns nil. It turns out that (aWaveRequest webRequest) does contain the http header info, but does not contain an httpRequest object. Before I try to fix this does anyone know if these are real problems or have I just configured Apache & VisualWorks incorrectly? ---- Roger Whitney Department of Computer Science whitney@cs.sdsu.edu San Diego State University http://www.eli.sdsu.edu/ San Diego, CA 92182-7720 (619) 583-1978 (619) 594-3535 (office) (619) 594-6746 (fax) From mbany at cincom.com Tue Jul 6 13:34:21 2004 From: mbany at cincom.com (Bany, Michel) Date: Tue Jul 6 13:34:27 2004 Subject: [Seaside] 2.5a5 ported to VW Message-ID: Avi, My comments on your comments. > Compile errors: > * WAComponent>>removeDecoration: - fixed Some more change is needed: ... "Here too ==>" ifTrue: [dec owner: aDecoration owner. ^ self] ... > * WAComponent>>show:onAnswer: - not actually a problem OK, but it would help for the port if the following statement was added near the beginning of the method, if it does not hurt, of course : event := nil. > * Seaside fails when trying to enable halos on the WACanvasTest component - > this is indeed a bug, but I don't like the fix: it ought to > be possible to enable halos on any component, regardless of which > renderer class it uses. I don't have a solution to this yet, but I don't see > much value in including the workaround in the meantime; better to remind > ourselves that this is broken. A fix to the bug could consist in adding to WARenderCanvas the behavior that is expected by WAHalo (#divClass:with: #anchorWithAction:text: #imageWithForm:). Here is another possible suggestion for fixing the bug. Since it uses #divClass:with: #anchorWithAction:text: and #imageWithForm: WAHalo expects a WAHtmlRenderer or a WARendererCompat as its renderer. On the other hand it also needs the renderer for the target component. This means that WAHalo needs two renderers. Although I am not sure Seaside will allow two concurrent renderers on the same document, here is how I see it. WAHalo would instantiate a second renderer for rendering the halo like this : WAHalo>>renderContentOn: html | haloHtml | haloHtml := self rendererClass context: html context callbacks: html callbacks. haloHtml divClass: 'halo' with: [ ... etc ... haloHtml divClass: 'halo-contents' with: [self perform: mode contents with: html]. ]. html close. haloHtml close. WAHalo>>source: html | context haloHtml | haloHtml := self rendererClass context: html context callbacks: html callbacks. context := haloHtml context copy. context clearMode. context document: (WAPrettyPrintedDocument renderer: haloHtml). haloHtml divClass: 'halo-source' with: [target renderWithContext: context]. haloHtml close. Optimization is possible if the target's renderer happens to be directly usable. Note that WAHalo would need two renderers even if WAHalo was enhanced to use WARenderCanvas methods, because the target component may be using a non-canvas renderer. Michel. -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.squeakfoundation.org/pipermail/seaside/attachments/20040706/b1300d5c/attachment.htm From avi at beta4.com Tue Jul 6 19:44:02 2004 From: avi at beta4.com (Avi Bryant) Date: Tue Jul 6 19:44:07 2004 Subject: [Seaside] 2.5a5 ported to VW In-Reply-To: References: Message-ID: <11C8F39D-CF74-11D8-A1BB-000A95DB7844@beta4.com> On Jul 6, 2004, at 4:34 AM, Bany, Michel wrote: > > Compile errors: > > * WAComponent>>removeDecoration: - fixed > Some more change is needed:???? > ??????? ??????? ??????? ??????? ... > ??????? "Here too ==>"? ifTrue: [dec owner: aDecoration owner.? ^ self] Missed that, thank you. > > * WAComponent>>show:onAnswer: - not actually a problem > OK, but it would help for the port if the following statement was > added near the > beginning of the method, if it does not hurt, of course : > ??????? event := nil. Ok, sure. > A fix to the bug could consist in adding to WARenderCanvas the > behavior that > is expected by WAHalo (#divClass:with: #anchorWithAction:text: > #imageWithForm:). Yes, but I don't want every renderer to have to implement those methods. > Here is another possible suggestion for fixing the bug. > Since it uses #divClass:with: #anchorWithAction:text: and > #imageWithForm: > WAHalo expects a WAHtmlRenderer or a WARendererCompat as its renderer. > On the other hand it also needs the renderer for the target component. > This means that WAHalo needs two renderers. Yes, I think your solution works. It's a little messy, but Halos are a strange special case and are allowed to be messy... Avi From rbb at techgame.net Tue Jul 6 21:36:20 2004 From: rbb at techgame.net (Brian Brown) Date: Tue Jul 6 21:36:30 2004 Subject: [Seaside] Porting to 2.5a6 Message-ID: Hi all, In porting my app, I was using WAComponent>>clearDelegate to take the session back to a "home" state from a menu. 2.5 doesn't seem to have clearDelegate anymore... what is the new way of doing that? Is it related to WAComponent>>activeComponent? thanks! Brian From avi at beta4.com Tue Jul 6 21:53:35 2004 From: avi at beta4.com (Avi Bryant) Date: Tue Jul 6 21:53:38 2004 Subject: [Seaside] Porting to 2.5a6 In-Reply-To: References: Message-ID: <2AAEBAE1-CF86-11D8-A1BB-000A95DB7844@beta4.com> On Jul 6, 2004, at 12:36 PM, Brian Brown wrote: > Hi all, > > In porting my app, I was using WAComponent>>clearDelegate to take > the session back to a "home" state from a menu. 2.5 doesn't seem to > have clearDelegate anymore... what is the new way of doing that? Is it > related to WAComponent>>activeComponent? Hm... try this: WAComponent>>clearDelegate dec := self decoration. [dec == self] whileFalse: [dec isDelegation ifTrue: [^ self removeDecoration: dec]. dec := dec owner] Avi From rbb at techgame.net Tue Jul 6 23:12:12 2004 From: rbb at techgame.net (Brian Brown) Date: Tue Jul 6 23:12:23 2004 Subject: [Seaside] Next porting question :) Message-ID: <265F7AF0-CF91-11D8-8846-003065F89450@techgame.net> I'm running into lot's of Error: Unprocessed callbacks (with several items in the Array), from WARenderLoop. Where would I start to debug this sort of thing? Obviously the model is a lot different now that many things seem to be implemented in Decorations, but I'm currently lost and haven't yet figured out how the new structure works versus 2.4.... Seeking advice, Brian From m.bany at wanadoo.fr Tue Jul 6 23:14:57 2004 From: m.bany at wanadoo.fr (Michel Bany) Date: Tue Jul 6 23:14:49 2004 Subject: [Seaside] VW Seaside behind apache problems In-Reply-To: References: Message-ID: <40EB1651.2030609@wanadoo.fr> > Before I try to fix this does anyone know if these are real problems > or have I just configured Apache & VisualWorks incorrectly? > Yes, these are real problems. For now the VW port does not support the cgi interface. I will have a look and let you know. Thanks for your patience. Michel. From rbb at techgame.net Tue Jul 6 23:35:25 2004 From: rbb at techgame.net (Brian Brown) Date: Tue Jul 6 23:35:31 2004 Subject: [Seaside] Porting to 2.5a6 In-Reply-To: <2AAEBAE1-CF86-11D8-A1BB-000A95DB7844@beta4.com> References: <2AAEBAE1-CF86-11D8-A1BB-000A95DB7844@beta4.com> Message-ID: <644B8C8C-CF94-11D8-8846-003065F89450@techgame.net> > > Hm... try this: > > WAComponent>>clearDelegate > dec := self decoration. > [dec == self] whileFalse: > [dec isDelegation ifTrue: [^ self removeDecoration: dec]. > dec := dec owner] > > Avi > > Thanks. It seems to have gotten me on to the next error, so onward and upward :-) From avi at beta4.com Wed Jul 7 02:41:09 2004 From: avi at beta4.com (Avi Bryant) Date: Wed Jul 7 02:41:14 2004 Subject: [Seaside] Next porting question :) In-Reply-To: <265F7AF0-CF91-11D8-8846-003065F89450@techgame.net> References: <265F7AF0-CF91-11D8-8846-003065F89450@techgame.net> Message-ID: <570E81E0-CFAE-11D8-A1BB-000A95DB7844@beta4.com> On Jul 6, 2004, at 2:12 PM, Brian Brown wrote: > I'm running into lot's of Error: Unprocessed callbacks (with several > items in the Array), from WARenderLoop. > > Where would I start to debug this sort of thing? > > Obviously the model is a lot different now that many things seem to be > implemented in Decorations, but I'm currently lost and haven't yet > figured out how the new structure works versus 2.4.... That error basically means that some implementation of #children is missing or incorrect. If, for example, you clicked a link that was rendered by a subcomponent, where the subcomponent's parent didn't include it in #children, you would get that error (because the pass through the tree was unable to find the subcomponent that the action callback belongs to). Avi From rbb at techgame.net Wed Jul 7 03:13:27 2004 From: rbb at techgame.net (Brian Brown) Date: Wed Jul 7 03:13:59 2004 Subject: [Seaside] Next porting question :) In-Reply-To: <570E81E0-CFAE-11D8-A1BB-000A95DB7844@beta4.com> References: <265F7AF0-CF91-11D8-8846-003065F89450@techgame.net> <570E81E0-CFAE-11D8-A1BB-000A95DB7844@beta4.com> Message-ID: <1089162806.4538.9.camel@siniwali.ablelinktech.com> On Tue, 2004-07-06 at 18:41, Avi Bryant wrote: > On Jul 6, 2004, at 2:12 PM, Brian Brown wrote: > > > I'm running into lot's of Error: Unprocessed callbacks (with several > > items in the Array), from WARenderLoop. > > > > Where would I start to debug this sort of thing? > > > > Obviously the model is a lot different now that many things seem to be > > implemented in Decorations, but I'm currently lost and haven't yet > > figured out how the new structure works versus 2.4.... > > That error basically means that some implementation of #children is > missing or incorrect. If, for example, you clicked a link that was > rendered by a subcomponent, where the subcomponent's parent didn't > include it in #children, you would get that error (because the pass > through the tree was unable to find the subcomponent that the action > callback belongs to). > Ok, that makes sense... I suspected that it had to do with children; I must have missed some of the components when adding children method > Avi > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside From m.bany at wanadoo.fr Wed Jul 7 11:16:11 2004 From: m.bany at wanadoo.fr (Michel Bany) Date: Wed Jul 7 11:16:02 2004 Subject: [Seaside] VW Seaside behind apache problems In-Reply-To: References: Message-ID: <40EBBF5B.4000002@wanadoo.fr> Roger Whitney wrote: > Before I try to fix this does anyone know if these are real problems > or have I just configured Apache & VisualWorks incorrectly? > I published Seaside-WebToolKit (2.5a5.21.2) as an initial attempt to run behind Apache. Authentication by Seaside is disabled for now when running in this configuration, because I do not know how to configure Apache so that it transfers the credentials through the cgi (HTTP_AUTHORIZATION environment variable and SECURITY_HOLE_PASS_AUTHORIZATION). Michel. From mbany at cincom.com Wed Jul 7 14:04:24 2004 From: mbany at cincom.com (Bany, Michel) Date: Wed Jul 7 14:04:29 2004 Subject: [Seaside] 2.5a5 ported to VW Message-ID: Avi, Some more compiler warnings (undeclared) from VisualWorks WAApplicationEditor>>children "Delete this method ?" ^ Array with: configEditor configEditor is undeclared WAInputDialog>>renderContentOn: html html heading: message level: 3. "<==== Delete this line ?" html form: [ html defaultAction: [self answer: value]. html textInputWithValue: value callback: [:v | value := v]. html space. html submitButtonWithText: self label. ] message is undeclared WASimpleNavigation>>selectedController "Delete this method ?" ^ (controllers detect: [:ea | ea key = self selection] ifNone: [^ nil]) value controllers is undeclared> -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.squeakfoundation.org/pipermail/seaside/attachments/20040707/cbbdeedc/attachment.htm From kamk at volny.cz Thu Jul 8 16:18:39 2004 From: kamk at volny.cz (Kamil Kukura) Date: Thu Jul 8 16:22:00 2004 Subject: [Seaside] sessions not released nor getting unregistered Message-ID: <40ED57BF.1010101@volny.cz> I have my session (subclassed from WASession) and it is initialized okay. I gave it #unregistered method and I put there "Transcript show: 'session unregistered'" I see sessions get expired but they get never unregistered. They are never released as well; I must do manually "WARegistry clearAllHandlers" :( -- Kamil From avi at beta4.com Fri Jul 9 04:54:32 2004 From: avi at beta4.com (Avi Bryant) Date: Fri Jul 9 04:54:37 2004 Subject: [Seaside] sessions not released nor getting unregistered In-Reply-To: <40ED57BF.1010101@volny.cz> References: <40ED57BF.1010101@volny.cz> Message-ID: <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> On Jul 8, 2004, at 7:18 AM, Kamil Kukura wrote: > I have my session (subclassed from WASession) and it is initialized > okay. I gave it #unregistered method and I put there "Transcript show: > 'session unregistered'" > > I see sessions get expired but they get never unregistered. They are > never released as well; I must do manually "WARegistry > clearAllHandlers" :( They'll get unregistered and released at the same time, which will be some time after they're expired - in fact, some number of new session creations later, since that's what triggers the scavenging. We may want to have a background process that does that at set intervals instead. If you create a whole bunch of new sessions after expiring one, do you still not see anything on your transcript? Avi From julian at beta4.com Fri Jul 9 05:07:08 2004 From: julian at beta4.com (Julian Fitzell) Date: Fri Jul 9 05:07:16 2004 Subject: [Seaside] sessions not released nor getting unregistered In-Reply-To: <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> References: <40ED57BF.1010101@volny.cz> <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> Message-ID: <40EE0BDC.6060905@beta4.com> Avi Bryant wrote: > They'll get unregistered and released at the same time, which will be > some time after they're expired - in fact, some number of new session > creations later, since that's what triggers the scavenging. We may want > to have a background process that does that at set intervals instead. Well, I don't know if there needs to always be one or not... But anyway, we use a startup script to configure ports, etc. and I just put this at the end: delay := Delay forSeconds: 60. [[true] whileTrue: [delay wait. (WADispatcher default entryPoints at: 'cv') unregisterExpiredHandlers]] fork. Julian From kamk at volny.cz Tue Jul 13 11:59:25 2004 From: kamk at volny.cz (Kamil Kukura) Date: Tue Jul 13 12:02:06 2004 Subject: [Seaside] Re: sessions not released nor getting unregistered In-Reply-To: <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> References: <40ED57BF.1010101@volny.cz> <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> Message-ID: <40F3B27D.8080604@volny.cz> > They'll get unregistered and released at the same time, which will be > some time after they're expired - in fact, some number of new session > creations later, since that's what triggers the scavenging. We may want > to have a background process that does that at set intervals instead. > > If you create a whole bunch of new sessions after expiring one, do you > still not see anything on your transcript? Hmm, I don't see any message from my session's #unregister method writing to Transcript. Now I added #expire method, so I'll see if that message will get to my session. However, checking number of instances of my sessions, it now seems it's being kept on number 12-15 during development. Anyway, I was wondering why do I have lingering entry components after WARegistry>>clearAllHandlers. I found out, for some reasons, they are held by Halos weak dictionary. So I extracted creation of this dictionary to WAHalo class>>initialize. Maybe this initialization could go to #clearAllHandlers. -- Kamil From m.bany at wanadoo.fr Tue Jul 13 20:59:52 2004 From: m.bany at wanadoo.fr (Michel Bany) Date: Tue Jul 13 20:59:39 2004 Subject: [Seaside] Re: sessions not released nor getting unregistered In-Reply-To: <40F3B27D.8080604@volny.cz> References: <40ED57BF.1010101@volny.cz> <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> <40F3B27D.8080604@volny.cz> Message-ID: <40F43128.5010409@wanadoo.fr> Kamil Kukura wrote: >> They'll get unregistered and released at the same time, which will be >> some time after they're expired - in fact, some number of new session >> creations later, since that's what triggers the scavenging. We may >> want to have a background process that does that at set intervals >> instead. >> >> If you create a whole bunch of new sessions after expiring one, do >> you still not see anything on your transcript? > > > Hmm, I don't see any message from my session's #unregister method > writing to Transcript. Now I added #expire method, so I'll see if that > message will get to my session. However, checking number of instances > of my sessions, it now seems it's being kept on number 12-15 during > development. > > Anyway, I was wondering why do I have lingering entry components after > WARegistry>>clearAllHandlers. I found out, for some reasons, they are > held by Halos weak dictionary. So I extracted creation of this > dictionary to WAHalo class>>initialize. Maybe this initialization > could go to #clearAllHandlers. > Which version of Seaside are you using ? From s002 at landr.net Thu Jul 15 18:26:01 2004 From: s002 at landr.net (s002) Date: Thu Jul 15 18:25:35 2004 Subject: [Seaside] (no subject) Message-ID: <20040715162601.26369.qmail@mail.taricco.net> I'm assuming that, I should use Seaside components when building my web app. Would someone give me an example of how to use the WAFormDialog component? Is there a tutorial out there, somewhere? -Larry From s002 at landr.net Thu Jul 15 19:32:02 2004 From: s002 at landr.net (s002) Date: Thu Jul 15 19:31:34 2004 Subject: [Seaside] Form component help --Newbie Message-ID: <20040715173202.30520.qmail@mail.taricco.net> Oops!! forgot the Subject. In building a Seaside app, I'm assuming that, I should use Seaside components. Would someone give me an example of how to use the WAFormDialog component? Is there a tutorial out there, somewhere? -Larry From avi at beta4.com Fri Jul 16 10:35:47 2004 From: avi at beta4.com (Avi Bryant) Date: Fri Jul 16 10:35:57 2004 Subject: [Seaside] Form component help --Newbie In-Reply-To: <20040715173202.30520.qmail@mail.taricco.net> References: <20040715173202.30520.qmail@mail.taricco.net> Message-ID: <228B084E-D703-11D8-A1BB-000A95DB7844@beta4.com> On Jul 15, 2004, at 10:32 AM, s002 wrote: > Oops!! forgot the Subject. > In building a Seaside app, I'm assuming that, I should use Seaside > components. Would someone give me an example of how to use the > WAFormDialog > component? Is there a tutorial out there, somewhere? There isn't any tutorial for WAFormDialog - you'll have to look through the examples, the best of which are probably those in the Store example app (eg, WAStorePaymentEditor). A couple of things that might help: - press the hierarchy button when browsing WAFormDialog to get a browser on all of its subclasses - select the name of a subclass and press cmd-shift-N, which will bring up a list of methods in which that class is used There is however a general Seaside tutorial that discusses components. If you haven't gone through it yet, you should. http://beta4.com/seaside2/tutorial.html If you have more specific questions we can help with, please ask. Cheers, Avi From rh at 4096.sk Mon Jul 19 00:47:10 2004 From: rh at 4096.sk (radoslav hodnicak) Date: Mon Jul 19 00:48:31 2004 Subject: [Seaside] expiring pages Message-ID: I'm doing a sort of hierarchy/tree editor (it just displays boxes connected with lines) and for some actions, I want to set the previous pages as expired, so that the user can't use the back button to change things. I know about session isolate: [] but I can't quite figure out how to use it here. This is seaside 2.3. The component works like -render all nodes -action to add/delete node -repeat until save/cancel So for example after the user deletes a node I want to make the previous pages expired so that they can't go back and work with the deleted node. rado -- "Everyone wins, except art and people with brains or education" - Dr. Thorpe From renggli at iam.unibe.ch Mon Jul 19 11:36:43 2004 From: renggli at iam.unibe.ch (Lukas Renggli) Date: Mon Jul 19 11:36:49 2004 Subject: [Seaside] expiring pages In-Reply-To: References: Message-ID: <2551E534-D967-11D8-843E-000393CFE6C8@iam.unibe.ch> > I know about session isolate: [] but I can't quite figure out how to > use > it here. This is seaside 2.3. The component works like > > -render all nodes > -action to add/delete node > -repeat until save/cancel > > So for example after the user deletes a node I want to make the > previous > pages expired so that they can't go back and work with the deleted > node. Hi, as far as I remember Seaside 2.3 did #isolate: on the session level. In one of our older web-applications I found the following code, that does exactly what you requested: - create a subclass of your session class: WAControllerSession subclass: #MySession instanceVariableNames: 'transactionFilter ' classVariableNames: '' poolDictionaries: '' category: '' - add the following methods: MySession>>initialize super initialize. self isolate. MySession>>isolate transactionFilter := WATransaction new. self addFilter: transactionFilter MySession>>invalidate self removeFilter: transactionFilter. transactionFilter close. self bookmarkForExpiry. self isolate. - now you can call 'self session invalidate' from you component-actions to invalidate all the previous pages. I'm sure something similar can be done on component level with the decorator framework in Seaside 2.5. Hope this helps, Lukas -- Lukas Renggli http://renggli.freezope.org From keith_hodges at yahoo.co.uk Mon Jul 19 19:23:07 2004 From: keith_hodges at yahoo.co.uk (Keith P Hodges) Date: Mon Jul 19 19:23:28 2004 Subject: [Seaside] OT VW help In-Reply-To: <2551E534-D967-11D8-843E-000393CFE6C8@iam.unibe.ch> References: <2551E534-D967-11D8-843E-000393CFE6C8@iam.unibe.ch> Message-ID: I have just loaded up VW-nc on my Mac system 9 for the first time (yes I gave up on X due to disk corruption problems I couldnt fix) All the displays look ugly, the lineheight is not large enough to display the icons in heirarchical views, they all appear scrunched up and clipped overlapping each other. Where should I go for tech support? can anyone here help. I figure its a fonts issue of some kind. thanks in advance Keith From avi at beta4.com Mon Jul 19 20:41:23 2004 From: avi at beta4.com (Avi Bryant) Date: Mon Jul 19 20:41:28 2004 Subject: [Seaside] expiring pages In-Reply-To: References: Message-ID: <3BB58A62-D9B3-11D8-A1BB-000A95DB7844@beta4.com> On Jul 18, 2004, at 3:47 PM, radoslav hodnicak wrote: > I'm doing a sort of hierarchy/tree editor (it just displays boxes > connected with lines) and for some actions, I want to set the previous > pages as expired, so that the user can't use the back button to change > things. > > I know about session isolate: [] but I can't quite figure out how to > use > it here. This is seaside 2.3. The component works like > > -render all nodes > -action to add/delete node > -repeat until save/cancel > > So for example after the user deletes a node I want to make the > previous > pages expired so that they can't go back and work with the deleted > node. This sounds like a variation on #once:, which will expire each page immediately - you'd want to wrap it around the call to your editor component, so, self session once: [self call: HierarchyEditor new]. But that wouldn't do quite what you want, since you only want the expiry to happen after certain actions. So I think you need to implement your own filter, using WAOnce as an example. Unlike WAOnce, which records all the actionKeys it sees and then complains if it ever sees them a second time, you'd want to keep a list of "expiredKeys", and a list of "currentKeys", and have some message telling it to move all the currentKeys into the expired list, that would be sent after node deletion etc. This is probably a common enough requirement that a filter/decoration like this should be in the base. So let us know how it goes. Avi From DPennell at quallaby.com Mon Jul 19 21:01:40 2004 From: DPennell at quallaby.com (Pennell, David) Date: Mon Jul 19 20:59:38 2004 Subject: [Seaside] OT VW help Message-ID: I would suggest the VWNC mailing list - vwnc@cs.uiuc.edu. > -----Original Message----- > From: Keith P Hodges [mailto:keith_hodges@yahoo.co.uk] > Sent: Monday, July 19, 2004 1:23 PM > To: The Squeak Enterprise Aubergines Server - general discussion. > Subject: [Seaside] OT VW help > > I have just loaded up VW-nc on my Mac system 9 for the first > time (yes I gave up on X due to disk corruption problems I > couldnt fix) > > All the displays look ugly, the lineheight is not large > enough to display the icons in heirarchical views, they all > appear scrunched up and clipped overlapping each other. Where > should I go for tech support? can anyone here help. I figure > its a fonts issue of some kind. > > thanks in advance > > Keith > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside > From kamk at volny.cz Tue Jul 20 10:26:35 2004 From: kamk at volny.cz (Kamil Kukura) Date: Tue Jul 20 10:39:48 2004 Subject: [Seaside] Re: sessions not released nor getting unregistered In-Reply-To: <40F43128.5010409@wanadoo.fr> References: <40ED57BF.1010101@volny.cz> <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> <40F3B27D.8080604@volny.cz> <40F43128.5010409@wanadoo.fr> Message-ID: <40FCD73B.5010009@volny.cz> Michel Bany wrote: > Which version of Seaside are you using ? argh.. I just noticed you put there just one line besides of content of all my mail :) I was using 2.5a5 so I updated it today to 2.5a6 but I see no advance. I have my own WAFTSession subclassed from WASesion. In its #unregister I also put "self halt" just to get alarmed when it happens. I'm checking from time to time "WAFTSession allInstances size" and I see that it's growing and then drops at some point. But my session's #unregister is not being sent :( -- Kamil From kamk at volny.cz Tue Jul 20 10:31:49 2004 From: kamk at volny.cz (Kamil Kukura) Date: Tue Jul 20 10:44:56 2004 Subject: [Seaside] callbacks on radio buttons not executed Message-ID: <40FCD875.2010207@volny.cz> I use #radioButtonInGroup:withValue:on:of: and it does not set the object. It seems that it registers callback that's never called. I guess it expects element named after callback's registration but this radio buttons are named explicitely because of grouping. -- Kamil From julian at beta4.com Tue Jul 20 19:54:00 2004 From: julian at beta4.com (Julian Fitzell) Date: Tue Jul 20 19:54:07 2004 Subject: [Seaside] callbacks on radio buttons not executed In-Reply-To: <40FCD875.2010207@volny.cz> References: <40FCD875.2010207@volny.cz> Message-ID: <40FD5C38.3010708@beta4.com> Are you using it in conjunction with #radioGroup? You need to do, for example: MyComponent>>renderContentOn: html group := html radioGroup. html radioButtonInGroup: group withValue: 1 on: #foo of: self. html radioButtonInGroup: group withValue: 2 on: #foo of: self. html radioButtonInGroup: group withValue: 3 on: #foo of: self. Julian Kamil Kukura wrote: > I use #radioButtonInGroup:withValue:on:of: and it does not set the > object. It seems that it registers callback that's never called. I guess > it expects element named after callback's registration but this radio > buttons are named explicitely because of grouping. > From m.bany at wanadoo.fr Tue Jul 20 21:32:35 2004 From: m.bany at wanadoo.fr (Michel Bany) Date: Tue Jul 20 21:32:08 2004 Subject: [Seaside] Re: sessions not released nor getting unregistered In-Reply-To: <40FCD73B.5010009@volny.cz> References: <40ED57BF.1010101@volny.cz> <4DDA5300-D153-11D8-A1BB-000A95DB7844@beta4.com> <40F3B27D.8080604@volny.cz> <40F43128.5010409@wanadoo.fr> <40FCD73B.5010009@volny.cz> Message-ID: <40FD7353.6060505@wanadoo.fr> I'm checking from time to time "WAFTSession allInstances size" and I see that it's growing and then drops at some point. But my session's #unregister is not being sent :( I believe the method name you be spellt #unregistered rather than #unregister. Michel. From cdshaffer at acm.org Tue Jul 20 22:16:19 2004 From: cdshaffer at acm.org (C. David Shaffer) Date: Tue Jul 20 22:18:39 2004 Subject: [Seaside] SeasideTesting released on SqueakMap Message-ID: <40FD7D93.4040905@acm.org> Thanks to all of you that provided feedback on my SeasideTesting package! I have created a SqueakMap package for it: http://map1.squeakfoundation.org/sm/package/f1f1e290-e55f-47d1-b82a-9c2f4f1bedc1 and made the tutorial avaiable as well: http://www.shaffer-consulting.com/david/Seaside/TestingComponents/TestingComponents.html This new release has some improvements from the one I posted to the list previously: . you can debug errors during component rendering . I refactored the input component support to make dealing with the various components more uniform . the web test runner now supports viewing the responses generated during the test run (follow the History link) This will be my last release for Seaside 2.5a5 since my extensions to WAHalo tend to be fairly version dependent. There is still a fair amount to be done but I've been using it off and on for a couple weeks and I think that, if you're test infected, you'll find it makes a good framework upon which to build component tests. Feedback is always welcome ;-) David From cdshaffer at acm.org Wed Jul 21 05:31:24 2004 From: cdshaffer at acm.org (C. David Shaffer) Date: Wed Jul 21 05:31:30 2004 Subject: [Seaside] SeasideTesting released for Seaside 2.5a6 Message-ID: <40FDE38C.10405@acm.org> I updated my Halo code and made a new SqueakMap release so now this package works fine in 2.5a6. David From kamk at volny.cz Wed Jul 21 07:18:59 2004 From: kamk at volny.cz (Kamil Kukura) Date: Wed Jul 21 07:19:53 2004 Subject: [Seaside] Re: callbacks on radio buttons not executed In-Reply-To: <40FD5C38.3010708@beta4.com> References: <40FCD875.2010207@volny.cz> <40FD5C38.3010708@beta4.com> Message-ID: <40FDFCC3.1070108@volny.cz> Julian Fitzell wrote: > Are you using it in conjunction with #radioGroup? > > You need to do, for example: > > MyComponent>>renderContentOn: html > group := html radioGroup. > > html radioButtonInGroup: group withValue: 1 on: #foo of: self. > html radioButtonInGroup: group withValue: 2 on: #foo of: self. > html radioButtonInGroup: group withValue: 3 on: #foo of: self. Thanks for explanation. Now I got it to work though I had to correct this method little bit: I don't have such method as Symbol>>asMutator so I replaced it with .... callback: [anObject perform: (aSelector copyWith: $:) asSymbol with: value] as I saw in some other method of rendering engine. -- Kamil From julian at beta4.com Wed Jul 21 09:02:40 2004 From: julian at beta4.com (Julian Fitzell) Date: Wed Jul 21 09:02:49 2004 Subject: [Seaside] Re: callbacks on radio buttons not executed In-Reply-To: <40FDFCC3.1070108@volny.cz> References: <40FCD875.2010207@volny.cz> <40FD5C38.3010708@beta4.com> <40FDFCC3.1070108@volny.cz> Message-ID: <40FE1510.1050404@beta4.com> Kamil Kukura wrote: > Julian Fitzell wrote: > >> Are you using it in conjunction with #radioGroup? >> >> You need to do, for example: >> >> MyComponent>>renderContentOn: html >> group := html radioGroup. >> >> html radioButtonInGroup: group withValue: 1 on: #foo of: self. >> html radioButtonInGroup: group withValue: 2 on: #foo of: self. >> html radioButtonInGroup: group withValue: 3 on: #foo of: self. > > > Thanks for explanation. Now I got it to work though I had to correct > this method little bit: I don't have such method as Symbol>>asMutator so > I replaced it with > > .... > callback: > [anObject perform: (aSelector copyWith: $:) asSymbol with: value] > > as I saw in some other method of rendering engine. I assume you're using VW or something? Michel can probably make sure this gets added in the port or something. Also note that you don't have to use the ...on:of: version of the method. There is also #radioButtonInGroup:selected:callback: which takes a group, a boolean, and a callback block. So, for example: MyComponent>>renderContentOn: html group := html radioGroup. html radioButtonInGroup: group selected: (self foo = 1) callback: [:v | self foo: 1]. html radioButtonInGroup: group selected: (self foo = 2) callback: [:v | self performSomeActionOrOther]. Cheers, Julian From mbany at cincom.com Wed Jul 21 10:22:06 2004 From: mbany at cincom.com (Bany, Michel) Date: Wed Jul 21 10:22:10 2004 Subject: [Seaside] Re: callbacks on radio buttons not executed Message-ID: > > Kamil Kukura wrote: > > Now I got it to work though I had to correct this method little bit: > > I don't have such method as symbol>>asMutator > Julian Fitzell wrote: > I assume you're using VW or something? Michel can probably make sure > this gets added in the port or something. Kamil is using Seaside in Squeak. I also noticed that #asMutator (used by Seaside) was lacking in Squeak, and I recently added it to the VW port (2.5a5.21.0). Michel. -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.squeakfoundation.org/pipermail/seaside/attachments/20040721/c952701e/attachment.htm From rh at 4096.sk Wed Jul 21 10:54:17 2004 From: rh at 4096.sk (radoslav hodnicak) Date: Wed Jul 21 10:55:40 2004 Subject: [Seaside] Re: callbacks on radio buttons not executed In-Reply-To: <40FE1510.1050404@beta4.com> Message-ID: On Wed, 21 Jul 2004, Julian Fitzell wrote: > > this method little bit: I don't have such method as Symbol>>asMutator so > > I assume you're using VW or something? Michel can probably make sure > this gets added in the port or something. I had to patch this method too. There's no #asMutator in my squeak image From s002 at landr.net Wed Jul 21 16:26:19 2004 From: s002 at landr.net (LK) Date: Wed Jul 21 16:26:31 2004 Subject: [Seaside] onAnswer error on embedded component Message-ID: <40FE7D0B.9080301@landr.net> I'm calling a grid object from withing my may renderContentOn method. I get this error below. Do I need an #onAnswer method? What would I put in it? -Larry MessageNotUnderstood: PMLogsView>>onAnswer: * PMLogsView(Object)>>doesNotUnderstand: #onAnswer: self a PMLogsView aMessage a Message with selector: #onAnswer: and arguments: #([] in PMLogsTask(WAComponent)>>show:onAnswer:) * PMLogsTask(WAComponent)>>show:onAnswer: self a PMLogsTask aComponent a PMLogsView aBlock a Continuation delegation a WADelegation event nil v nil * [] in PMLogsTask(WAComponent)>>call: self a PMLogsTask aComponent a PMLogsView cc a Continuation This is the main render loop: PMLogsTask>>renderContentOn: html |db | db _ self connect. html cssId: 'banner'. html table: [ html tableRowWith: [ html divNamed: 'title' with: self title. html divNamed: 'subtitle' with: self subtitle. ] ]. self call: (PMLogsView new renderContentOn: html and: db). db logout. --- This is the embedded object. PMLogsView>>renderContentOn: html and: db | items | html table: [ html tableRow: [html tableHeading: 'View all Log Entries']]. html table: [ items _ db root at: 'logs'. items do: [:i | html tableRow: [html tableData: [i type ]. html tableData: [i entryDate]. html tableData: [i startTime]. html tableData: [i endTime]. html tableData: [i entryText]. ] ]. html tableRow: [] ] From mbany at cincom.com Wed Jul 21 17:42:05 2004 From: mbany at cincom.com (Bany, Michel) Date: Wed Jul 21 17:42:10 2004 Subject: [Seaside] onAnswer error on embedded component Message-ID: > self call: (PMLogsView new renderContentOn: html and: db). Your PMLogsView is not look like a callable component. I would just display the component like this: html render: (PMLogsView new db: db). with a new instance variable 'db' defined in the component and I would remove the second parameter from the renderContentOn:db: method Hope I understood well. Michel. -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.squeakfoundation.org/pipermail/seaside/attachments/20040721/c9a07ba2/attachment.htm From cdshaffer at acm.org Wed Jul 21 17:53:38 2004 From: cdshaffer at acm.org (C. David Shaffer) Date: Wed Jul 21 17:53:50 2004 Subject: [Seaside] onAnswer error on embedded component In-Reply-To: <40FE7D0B.9080301@landr.net> References: <40FE7D0B.9080301@landr.net> Message-ID: <40FE9182.4030600@acm.org> LK wrote: > I'm calling a grid object from withing my may renderContentOn method. > I get this error below. Do I need an #onAnswer method? What would I > put in it? > -Larry > PMLogsTask>>renderContentOn: html > > |db | > db _ self connect. > html cssId: 'banner'. > html table: [ > html tableRowWith: [ > html divNamed: 'title' with: self title. > html divNamed: 'subtitle' with: self subtitle. > ] > ]. > self call: (PMLogsView new renderContentOn: html and: db). This is a pretty common misunderstanding of #call:. #call: should generally not be called from #renderContentOn:, except with great care as one sees in WATask subclasses. What you really are doing is embedding a component, not calling it. So, to embed a component you need to pass it as an argument to #render: html render: pmLogsView now, notice that I didn't create the instance here...that's because if a component embeds another component it must include that component in its response to #children. So, what I'd suggest is something like this: add pmLogsView as an i-var to your class initialize pmLogsView := PMLogsView new. children ^Array with: pmLogsView renderContentOn: html | db | .... your code except the call: here... pmLogsView useDb: db during: [html render: pmLogsView] db logout Then in your PMLogsView add a db i-var and the method useDb: aDatabase during: aBlock db := aDatabase. aBlock ensure: [db := nil] That way your i-var doesn't keep the reference to the database around any longer than needed. Actually, what I'd really recommend is storing the db in a custom session subclass...if your app is bigger than these two classes then you'll eventually probably find that you need access to the database in many of your views. I believe that there is a tutorial around which shows you how to do this. Look at http://beta4.com/seaside2/docs.html as a possible starting place. David From julian at beta4.com Wed Jul 21 18:52:52 2004 From: julian at beta4.com (Julian Fitzell) Date: Wed Jul 21 18:53:14 2004 Subject: [Seaside] Re: callbacks on radio buttons not executed In-Reply-To: References: Message-ID: <40FE9F64.2000406@beta4.com> Ooo... that looks like my fault. Looks like Andrew at work added that method for our application there and it got used in seaside without me realizing it wasn't standard. I'll get a fix for that right away. Avi, any preference whether we should: - include #asMutator (attached); - rewrite this method using #copyWith: (actually slightly less intelligent, since it adds a colon even if the colon is already there); or - have it use #callbackForSelector:of: (a little weird, since we end up create a Message send inside the block so we can pass it the correct value) Julian radoslav hodnicak wrote: > On Wed, 21 Jul 2004, Julian Fitzell wrote: > > >>>this method little bit: I don't have such method as Symbol>>asMutator so >> >>I assume you're using VW or something? Michel can probably make sure >>this gets added in the port or something. > > > I had to patch this method too. There's no #asMutator in my squeak image > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside -------------- next part -------------- 'From Squeak3.6 of ''6 October 2003'' [latest update: #5429] on 21 July 2004 at 9:48:27 am'! !Symbol methodsFor: '*seaside' stamp: 'ac 4/12/2003 03:05'! asMutator ^ self last = $: ifTrue: [self] ifFalse: [(self, ':') asSymbol]! ! From avi at beta4.com Wed Jul 21 19:55:25 2004 From: avi at beta4.com (Avi Bryant) Date: Wed Jul 21 19:55:36 2004 Subject: [Seaside] Re: callbacks on radio buttons not executed In-Reply-To: <40FE9F64.2000406@beta4.com> References: <40FE9F64.2000406@beta4.com> Message-ID: <24DD8BE6-DB3F-11D8-B33C-000A95DB7844@beta4.com> On Jul 21, 2004, at 9:52 AM, Julian Fitzell wrote: > Ooo... that looks like my fault. Looks like Andrew at work added that > method for our application there and it got used in seaside without me > realizing it wasn't standard. > > I'll get a fix for that right away. > > Avi, any preference whether we should: > - include #asMutator (attached); > - rewrite this method using #copyWith: (actually slightly less > intelligent, since it adds a colon even if the colon is already > there); or > - have it use #callbackForSelector:of: (a little weird, since we end > up create a Message send inside the block so we can pass it the > correct value) #asMutator seems like a nice thing to have - might as well include it. Avi From avi at beta4.com Thu Jul 22 08:13:17 2004 From: avi at beta4.com (Avi Bryant) Date: Thu Jul 22 08:13:27 2004 Subject: [Seaside] 2.5 beta 1 Message-ID: <38CBF954-DBA6-11D8-B33C-000A95DB7844@beta4.com> Hi all, I feel like Seaside 2.5 has now settled down enough, and has accomplished enough of what I was shooting for, to freeze the feature set and move it into beta. I've put the first beta release on SqueakMap; this is essentially 2.5a6 with general fixes, and with modifications to WAHtmlDocument to allow streaming*. Anyone still using Seaside 2.3 should now feel pretty safe starting to port their code to 2.5 without feeling like there will be major changes to the system. This has been a pretty long alpha, I think due to my trying to bundle too many changes at once. Hopefully the beta will move along quicker. I'll be sitting here, eagerly awaiting bug reports... Have fun with it, Avi * Switching to a streaming mode should now require no changes to user code; however, a fully streaming configuration requires support from the webserver, and I haven't yet found a way to do this integration cleanly and portably. So although the streaming changes have eliminated an internal buffer (by hooking the document directly into the Response object), the Response object itself still buffers the output and gives it to the webserver as one chunk. From mbany at cincom.com Thu Jul 22 17:14:56 2004 From: mbany at cincom.com (Bany, Michel) Date: Thu Jul 22 17:15:03 2004 Subject: [Seaside] 2.5 beta 1 Message-ID: > I'll be sitting here, eagerly awaiting bug reports... ... Here is your first one, in WAHalo again :) The findStyles method creates a new rendering context that is not holding any request. You get a dnu when you need to access the request like in WABasicAuthentication>>renderContentOn: or like in the VW port when we need to access the native request to determine if we are running behind Apache. I changed findStyles like this : findStyles | context | context := WARenderingContext new document: WAStyleCollector new; actionUrl: WAUrl new. context request: self session currentRequest. target renderWithContext: context. ^ String streamContents: [:s | context document styles do: [:ea | s nextPutAll: ea; space]] Michel. -------------- next part -------------- An HTML attachment was scrubbed... URL: http://lists.squeakfoundation.org/pipermail/seaside/attachments/20040722/04a10fa0/attachment.htm From rh at 4096.sk Thu Jul 22 17:36:53 2004 From: rh at 4096.sk (radoslav hodnicak) Date: Thu Jul 22 17:38:17 2004 Subject: [Seaside] expiring pages In-Reply-To: <2551E534-D967-11D8-843E-000393CFE6C8@iam.unibe.ch> Message-ID: On Mon, 19 Jul 2004, Lukas Renggli wrote: > as far as I remember Seaside 2.3 did #isolate: on the session level. In > one of our older web-applications I found the following code, that does > exactly what you requested: [snip code] Thanks, it works. I have another problem now, and that is how to detect if the control flow "escaped" from #isolate: block (or something similar). For users' convenience, I've split some larger forms to several separate smaller forms. However now it happens that when they use the back button before completing the whole series of edit pages the object stays partially changed. Example ViewerComponent item1 item2 click on item1 => session isolate: [self call: (EditComponent on: item1)] EditComponent on item1 edit form 1 => edit form 2 => ... => final form with save/cancel now, user gets to form 2, the properties from form 1 are already changed in item1. user uses back button to get to Viewer page and starts to edit item2. I'm stuck with half-changed item1. Is there a way to do something so that the old isolate block gets completed/cancelled/whatever and I can rollback a transaction there? rado From julian at beta4.com Thu Jul 22 19:09:48 2004 From: julian at beta4.com (Julian Fitzell) Date: Thu Jul 22 19:09:56 2004 Subject: [Seaside] expiring pages In-Reply-To: References: Message-ID: <40FFF4DC.6090708@beta4.com> radoslav hodnicak wrote: > I have another problem now, and that is how to detect if the control flow > "escaped" from #isolate: block (or something similar). For users' > convenience, I've split some larger forms to several separate smaller > forms. However now it happens that when they use the back button before > completing the whole series of edit pages the object stays partially > changed. Example > > ViewerComponent > item1 > item2 > > click on item1 => session isolate: [self call: (EditComponent on: item1)] > > EditComponent on item1 > edit form 1 => edit form 2 => ... => final form with save/cancel > > > now, user gets to form 2, the properties from form 1 are already changed > in item1. user uses back button to get to Viewer page and starts to edit > item2. I'm stuck with half-changed item1. > > Is there a way to do something so that the old isolate block gets > completed/cancelled/whatever and I can rollback a transaction there? Ok, well #isolate: is not really transactional, it merely groups and expires pages. The only way seaside could deal with reverting that data is if you made it back-trackable, but you don't want to do that with model objects. So, other options? You can try to use your database's transactions (some people have played with having database transactions match up with #isolate: blocks). But what I do is to have a read-through proxy for the object. It uses #doesNotUnderstand to call any accessors through to the real object but when you call a setter it caches the data locally and only pushes those through when you tell it to write. This is made very easy in our case because we have a meta-model that describes our model objects and thus makes it clear which methods are variable setters, etc. In the general case, without such a meta-model, this would be harder. Anyway, hopefully that gives you a few places to start thinking... Julian From avi at beta4.com Thu Jul 22 20:55:52 2004 From: avi at beta4.com (Avi Bryant) Date: Thu Jul 22 20:56:47 2004 Subject: [Seaside] expiring pages In-Reply-To: References: Message-ID: On Jul 22, 2004, at 8:36 AM, radoslav hodnicak wrote: > ViewerComponent > item1 > item2 > > click on item1 => session isolate: [self call: (EditComponent on: > item1)] > > EditComponent on item1 > edit form 1 => edit form 2 => ... => final form with save/cancel > > now, user gets to form 2, the properties from form 1 are already > changed > in item1. user uses back button to get to Viewer page and starts to > edit > item2. I'm stuck with half-changed item1. > > Is there a way to do something so that the old isolate block gets > completed/cancelled/whatever and I can rollback a transaction there? The problem is that in the general case you don't know whether they used the back button (and thus no longer have access to form2, and so you'd want to roll item1 back), or whether they have two browser windows open, in which case it would be perfectly valid for them to be editing both item1 and item2 at once. If you assumed that they weren't going to do that, you could hack in a notion of "current model" - whenever you go to a new component, do something like self session currentModel: anItem where #currentModel: checks to see if the model has changed, and it if has, it: - snapshots the new model - rolls back the old model to the old snapshot - stores the new model and new snapshot When you hit the final form and the user hits save, you can send something like #clearModel which will nil out the model and snapshot so it doesn't get rolled back in the future. However, I personally prefer to allow the user to use as many browser windows as they want to. The only real solution here is what Julian suggested - don't operate on the real model object, but on a working copy of it, and then copy that back into the real object when the user hits save (rollforward?). This is where a proper in-image transactional system would be really nice, as we've discussed before. Avi From rh at 4096.sk Thu Jul 22 22:11:57 2004 From: rh at 4096.sk (radoslav hodnicak) Date: Thu Jul 22 22:13:20 2004 Subject: [Seaside] expiring pages In-Reply-To: Message-ID: On Thu, 22 Jul 2004, Avi Bryant wrote: > However, I personally prefer to allow the user to use as many browser > windows as they want to. The only real solution here is what Julian > suggested - don't operate on the real model object, but on a working > copy of it, and then copy that back into the real object when the user > hits save (rollforward?). This is where a proper in-image > transactional system would be really nice, as we've discussed before. I do have in-image transactions, from glorp (they only work on glorp objects but that's fine). I've just realised that I should use them backwards - my editor should operate on the copy saved by glorp for restoring the object, and do rollback on save and commit on cancel. lol this is twisted rado From avi at beta4.com Fri Jul 23 00:30:50 2004 From: avi at beta4.com (Avi Bryant) Date: Fri Jul 23 00:30:54 2004 Subject: [Seaside] SeasideTesting released on SqueakMap In-Reply-To: <40FD7D93.4040905@acm.org> References: <40FD7D93.4040905@acm.org> Message-ID: On Jul 20, 2004, at 1:16 PM, C. David Shaffer wrote: > This will be my last release for Seaside 2.5a5 since my extensions to > WAHalo tend to be fairly version dependent. There is still a fair > amount to be done but I've been using it off and on for a couple weeks > and I think that, if you're test infected, you'll find it makes a good > framework upon which to build component tests. Feedback is always > welcome ;-) Wow. I had a chance to take a look at this today, and it's a very nice piece of work. It's the only thing I've seen so far that makes it seem like testing web UIs could actually be feasible. I'll definitely be demoing this the next time I do a Seaside talk. Especially nice for demos (and for general use, I imagine) is being able to browse through the history of rendered pages - though it would be even cooler if their links worked. One thing this encourages is adding good CSS ids throughout the render, which is something that's always seemed overly clunky to me. That is, the necessity to put #cssClass: and #cssId:, as well as #div:, #span:, etc everywhere, clutters up the more interesting parts (like anchors and callbacks) of any given render method. Anyone have any good ideas to keep these separated? I'm just throwing out random thoughts here, but one possible pattern that occurs to me would be to introduce a higher level wrapper around the HtmlRenderer, that was specific to a particular component. For lack of a more imaginative name, let's call this a View. The idea would be that the *structure* of the rendering is still controlled by the component, but the specifics (the actual tags and ids) are filled in by the View. So, for example, take the following fairly typical render method: MyComponent>>renderItems: aCollection on: html html cssClass: 'item-list'. html unorderedList: [aCollection do: [:ea | html listItem: [html cssClass: 'item-choose'. html anchorWithAction: [self choose: ea] text: ea description. html spanClass: 'item-actions' with: [html anchorWithAction: [self remove: ea] text: '(remove)']]]] Would it be better, or just more confusing and cumbersome, to split this into something like: MyComponent>>renderItems: aCollection on: view view itemList: [aCollection do: [:ea | view item: [view chooseItem: [self choose: ea] text: ea description. view itemActions: [view removeItem: [self remove: ea]]]]] MyView>>itemList: aBlock html cssClass: 'item-list'. html unorderedList: aBlock MyView>>item: aBlock html listItem: aBlock MyView>>chooseItem: actionBlock text: aString html cssClass: 'item-choose'. html anchorWithAction: actionBlock text: aString MyView>>itemActions: aBlock html spanClass: 'item-actions' with: aBlock MyView>>removeItem: actionBlock html anchorWithAction: actionBlock text: '(remove)' Anyway, just a thought. Cheers, Avi From avi at beta4.com Fri Jul 23 00:59:13 2004 From: avi at beta4.com (Avi Bryant) Date: Fri Jul 23 00:59:17 2004 Subject: [Seaside] expiring pages In-Reply-To: References: Message-ID: On Jul 22, 2004, at 1:11 PM, radoslav hodnicak wrote: > On Thu, 22 Jul 2004, Avi Bryant wrote: > >> However, I personally prefer to allow the user to use as many browser >> windows as they want to. The only real solution here is what Julian >> suggested - don't operate on the real model object, but on a working >> copy of it, and then copy that back into the real object when the user >> hits save (rollforward?). This is where a proper in-image >> transactional system would be really nice, as we've discussed before. > > I do have in-image transactions, from glorp (they only work on glorp > objects but that's fine). I've just realised that I should use them > backwards - my editor should operate on the copy saved by glorp for > restoring the object, and do rollback on save and commit on cancel. > > lol this is twisted Yup, that's twisted all right. But won't glorp save the wrong thing to the database, then? Avi From cdshaffer at acm.org Fri Jul 23 07:10:24 2004 From: cdshaffer at acm.org (C. David Shaffer) Date: Fri Jul 23 07:14:23 2004 Subject: [Seaside] SeasideTesting released on SqueakMap In-Reply-To: References: <40FD7D93.4040905@acm.org> Message-ID: <41009DC0.90904@acm.org> Avi Bryant wrote: > > On Jul 20, 2004, at 1:16 PM, C. David Shaffer wrote: > >> This will be my last release for Seaside 2.5a5 since my extensions to >> WAHalo tend to be fairly version dependent. There is still a fair >> amount to be done but I've been using it off and on for a couple >> weeks and I think that, if you're test infected, you'll find it makes >> a good framework upon which to build component tests. Feedback is >> always welcome ;-) > > > Wow. I had a chance to take a look at this today, and it's a very > nice piece of work. It's the only thing I've seen so far that makes > it seem like testing web UIs could actually be feasible. I'll > definitely be demoing this the next time I do a Seaside talk. > Especially nice for demos (and for general use, I imagine) is being > able to browse through the history of rendered pages - though it > would be even cooler if their links worked. Thanks. With the current version the session and app are gone at the time you view the page history but I should have that corrected soon. I had a few other ideas for this feature too. I should be able to single step through the test case while viewing the current response in a browser other than Scamper :-) I can force mozilla to load a page under X using the "remote control" mechanism and while this might serve me well it would be platform dependent. If I accept the client-pull nature of these browsers then I could devise a way that a client refresh would bring the user's browser to the current test browser's view. So, you single step through your test and hit refresh on the browser when you want to see the current page. Also, I've found that being able to compare what a browser submitted to the server with what a test case submits to a server has been useful during the development of this package but I'm not sure if it will be useful when testing components. I would at least like to display the request that the test framework used to generate the page so you could see GET and POST data. Unfortunately I don't save the original request, just the one that was generated by the redirect. This is on my list to be fixed soon as well. > > One thing this encourages is adding good CSS ids throughout the > render, which is something that's always seemed overly clunky to me. > That is, the necessity to put #cssClass: and #cssId:, as well as > #div:, #span:, etc everywhere, clutters up the more interesting parts > (like anchors and callbacks) of any given render method. Anyone have > any good ideas to keep these separated? > I'm just throwing out random thoughts here, but one possible pattern > that occurs to me would be to introduce a higher level wrapper around > the HtmlRenderer, that was specific to a particular component. For > lack of a more imaginative name, let's call this a View. The idea > would be that the *structure* of the rendering is still controlled by > the component, but the specifics (the actual tags and ids) are filled > in by the View. So, for example, take the following fairly typical > render method: > [...example snipped...] I see how that helps a little with classes and document structure but I'm not sure if that helps with id's. I like it somewhat because it offers one layer greater of abstraction on the renderer...something which I wanted when thinking about generating other types of content (mainly other XML doctypes). So your application could have both an XMLView and a XHTMLView. Actually XMLView should be more specific to the target DOCTYPE etc. This kind of distinction doesn't seem possible with the renderer protocol which is more about XHTML generation. Anyway, this is off-topic a bit. As far as writing small, testable components goes I don't mind the clutter of adding id's to my forms and input elements (most of the time I reference anchors by their text). Most of the time my renderContentOn: is split into several separate rendering methods as you do in several of your components. While not as reusable as your "View" code, it keeps the clutter down to a minimum but has the advantage of keeping the generation of the component's portion of the content more localized in code. Again, I like the View idea for other reasons. Did the Seaside blog (Smallblog?) include generation of feeds in various syndication formats? If so, how was that done? David From m.bany at wanadoo.fr Fri Jul 23 08:29:05 2004 From: m.bany at wanadoo.fr (Michel Bany) Date: Fri Jul 23 08:28:36 2004 Subject: [Seaside] [VW] 2.5 beta 1 In-Reply-To: <38CBF954-DBA6-11D8-B33C-000A95DB7844@beta4.com> References: <38CBF954-DBA6-11D8-B33C-000A95DB7844@beta4.com> Message-ID: <4100B031.4070606@wanadoo.fr> I completed the port of 2.5a6.9 (basically identical to 2.5b1) to VW7.2 This port has a major difference with the previous ports since it also includes the complete set of Squeak Chronology classes (Duration, DateAndTime, etc.) ported from Squeak rather than copy/pasted as it was before. This has allowed me (I believe) to generate correct GMT time stamps in the HTTP responses, providing for better caching by the browsers and for better cookie expiration. To avoid name conflicts with three VisualWorks base classes, the Squeak Chronology subsystem is defined in the (new) Squeak namespace. The Seaside namespace now imports the Squeak namespace and, by default, uses the Squeak Chronology, i.e. Date today. Time now. will answer objects with the Squeak behavior, i.e. not exactly the VW behavior. I am hoping this will not break anything. During install the Squeak time zone is synchronized with the VW time zone and both are kindly set to CET (rather than the Santa Barbara default), see AAADocumentation>>adjustTimeZone. This port also includes my first attempt to run Seaside inside Swazoo. It supports both the Swazoo version found in the goodies area of the VW7.2 CD and the Swazoo version that can be found on the public Store repository. Unfortunately, IE6 does not appear to work with the Seaside-Swazoo combination because the "redirect" HTTP responses (302) from Swazoo do not work with IE6. This is a Swazoo problem, not Seaside and I did not find out why so far. Another issue is the encoding which is not correct, I am wondering if Swazoo performs any. Any Swazoo expert around ? Also, to satisfy St?phane :) Seaside can now be loaded with just one bundle, choose either SeasideForWebToolkit or SeasideForSwazoo Because two Swazoo versions are supported, you will be prompted for choosing which Swazoo version you want. The Seaside-Web Toolkit combination should work fine behind Apache. In the Seaside-Web Toolkit combination, Seaside is now re-initialized each timeWeb Toolkit is re-initialized, i.e. it is also re-initialized when the image is started. Michel. From rbb at techgame.net Fri Jul 23 17:52:57 2004 From: rbb at techgame.net (Brian Brown) Date: Fri Jul 23 17:53:08 2004 Subject: [Seaside] RE: cssClass and cssID (was testing framework) Message-ID: <5E1CD850-DCC0-11D8-989C-003065F89450@techgame.net> On Jul 22, 2004, at 4:30 PM, Avi Bryant wrote: > One thing this encourages is adding good CSS ids throughout the > render, which is something that's always seemed overly clunky to me. > That is, the necessity to put #cssClass: and #cssId:, as well as > #div:, #span:, etc everywhere, clutters up the more interesting parts > (like anchors and callbacks) of any given render method. Anyone have > any good ideas to keep these separated? I'm just throwing out random > thoughts here, but one possible pattern that occurs to me would be to > introduce a higher level wrapper around the HtmlRenderer, that was > specific to a particular component. For lack of a more imaginative > name, let's call this a View. The idea would be that the *structure* > of the rendering is still controlled by the component, but the > specifics (the actual tags and ids) are filled in by the View. So, > for example, take the following fairly typical render method: > > MyComponent>>renderItems: aCollection on: html > html cssClass: 'item-list'. > html unorderedList: > [aCollection do: > [:ea | > html listItem: > [html cssClass: 'item-choose'. > html anchorWithAction: [self choose: ea] text: ea description. > html spanClass: 'item-actions' with: [html anchorWithAction: [self > remove: ea] text: '(remove)']]]] > > Would it be better, or just more confusing and cumbersome, to split > this into something like: > > MyComponent>>renderItems: aCollection on: view > view itemList: > [aCollection do: > [:ea | > view item: > [view chooseItem: [self choose: ea] text: ea description. > view itemActions: [view removeItem: [self remove: ea]]]]] > > MyView>>itemList: aBlock > html cssClass: 'item-list'. > html unorderedList: aBlock > > MyView>>item: aBlock > html listItem: aBlock > > MyView>>chooseItem: actionBlock text: aString > html cssClass: 'item-choose'. > html anchorWithAction: actionBlock text: aString > > MyView>>itemActions: aBlock > html spanClass: 'item-actions' with: aBlock > > MyView>>removeItem: actionBlock > html anchorWithAction: actionBlock text: '(remove)' > > Anyway, just a thought. > > Cheers, > Avi > I think the second way introduces an unnecessary layer of abstraction - yes, each individual method is cleaner to read the CSS info, but overall it would be much more difficult building that component; I like the conciseness of the first one. What about the idea of assigning each component a default css name based on the name of the component. All elements rendered in that component would be in a namespace (from a CSS perspective) like: MyComponent.table MyComponent.h3 etc. This would follow the standard CSS inheritance, giving very fine grained control to each component only if desired. This doesn't help with
but those are structural anyway, and it is very useful to see what is being rendered inside of a particular div element when editing the render methods. Just for various text styles, spanClass:with: and spanNamed:with: don't seem too cumbersome. Using this scheme, a #spanText: could also be created that acted like #text: So instead of: html span: [html text: 'Some words'] you would have: html spanText: 'Some words'. "This span would be covered by the default css component name space." I may be missing some things here, and I certainly am not using CSS to it's full potential in my own Seaside work, but what do you think? Brian From avi at beta4.com Fri Jul 23 21:45:20 2004 From: avi at beta4.com (Avi Bryant) Date: Fri Jul 23 21:45:23 2004 Subject: [Seaside] RE: cssClass and cssID (was testing framework) In-Reply-To: <5E1CD850-DCC0-11D8-989C-003065F89450@techgame.net> References: <5E1CD850-DCC0-11D8-989C-003065F89450@techgame.net> Message-ID: On Jul 23, 2004, at 8:52 AM, Brian Brown wrote: > I think the second way introduces an unnecessary layer of abstraction > - yes, each individual method is cleaner to read the CSS info, but > overall it would be much more difficult building that component; I > like the conciseness of the first one. Probably true. > What about the idea of assigning each component a default css name > based on the name of the component. All elements rendered in that > component would be in a namespace (from a CSS perspective) like: > > MyComponent.table > MyComponent.h3 > > etc. This would follow the standard CSS inheritance, giving very fine > grained control to each component only if desired. Yes, this makes good sense. The question is, I guess, where you hang that class. Do you wrap every component in a div automatically? But some components should be in spans instead, and some probably shouldn't be in either. So are there methods #wantsDiv, #wantsSpan that can be overridden? Or maybe there are #divClass and #spanClass methods, and if either is overridden to return something non-nil, then the appropriate tag is used (and you could have, by default, divClass ^ self class name ) > This doesn't help with
but those are structural anyway, and it > is very useful to see what is being rendered inside of a particular > div element when editing the render methods. Just for various text > styles, spanClass:with: and spanNamed:with: don't seem too cumbersome. > Using this scheme, a #spanText: could also be created that acted like > #text: So instead of: > > html span: [html text: 'Some words'] > > you would have: > > html spanText: 'Some words'. There's no need for #spanText: - this will already work: html span: 'Some words'. Methods like #span: aren't actually expecting a block specifically (though a block is the most common thing to give them), they're expecting anything that implements #renderOn:. It's just that: BlockContext>>renderOn: aRenderer self value Avi From avi at beta4.com Fri Jul 23 21:46:36 2004 From: avi at beta4.com (Avi Bryant) Date: Fri Jul 23 21:46:44 2004 Subject: [Seaside] SeasideTesting released on SqueakMap In-Reply-To: <41009DC0.90904@acm.org> References: <40FD7D93.4040905@acm.org> <41009DC0.90904@acm.org> Message-ID: <02216502-DCE1-11D8-B33C-000A95DB7844@beta4.com> On Jul 22, 2004, at 10:10 PM, C. David Shaffer wrote: > Did the Seaside blog (Smallblog?) include generation of feeds in > various syndication formats? If so, how was that done? Just RSS. And the RSS output was totally separate from the Seaside UI. Avi From rbb at techgame.net Sat Jul 24 01:11:00 2004 From: rbb at techgame.net (Brian Brown) Date: Sat Jul 24 01:11:08 2004 Subject: [Seaside] RE: cssClass and cssID (was testing framework) In-Reply-To: References: <5E1CD850-DCC0-11D8-989C-003065F89450@techgame.net> Message-ID: <1090624260.8209.3.camel@siniwali.ablelinktech.com> On Fri, 2004-07-23 at 13:45, Avi Bryant wrote: > On Jul 23, 2004, at 8:52 AM, Brian Brown wrote: > > > I think the second way introduces an unnecessary layer of abstraction > > - yes, each individual method is cleaner to read the CSS info, but > > overall it would be much more difficult building that component; I > > like the conciseness of the first one. > > Probably true. > > > What about the idea of assigning each component a default css name > > based on the name of the component. All elements rendered in that > > component would be in a namespace (from a CSS perspective) like: > > > > MyComponent.table > > MyComponent.h3 > > > > etc. This would follow the standard CSS inheritance, giving very fine > > grained control to each component only if desired. > > Yes, this makes good sense. The question is, I guess, where you hang > that class. Do you wrap every component in a div automatically? But > some components should be in spans instead, and some probably shouldn't > be in either. So are there methods #wantsDiv, #wantsSpan that can be > overridden? Or maybe there are #divClass and #spanClass methods, and > if either is overridden to return something non-nil, then the > appropriate tag is used (and you could have, by default, > > divClass > ^ self class name > Yes, I was initially thinking you would wrap every component automatically, but having the #divClass and #spanClass would work well, and give a lot of control for components. We would only have to resort to the current way of doing things in limited cases. > There's no need for #spanText: - this will already work: > > html span: 'Some words'. > > Methods like #span: aren't actually expecting a block specifically > (though a block is the most common thing to give them), they're > expecting anything that implements #renderOn:. It's just that: > > BlockContext>>renderOn: aRenderer > self value > I probably should have tried it that way ;) Brian From s002 at landr.net Sat Jul 24 04:22:18 2004 From: s002 at landr.net (LK) Date: Sat Jul 24 04:22:44 2004 Subject: [Seaside] Deleting from GOODS. Message-ID: <4101C7DA.1070303@landr.net> OK, I've got a table that will display records from my GOODS database. Many thanks to Bany and Shaffer. Would someone tell me what's wrong with my delete: method.? I've taken code from a 'table tutorial' and modified it as follows: my PMLogsView class has an allRecords instance var which holds the PMLogs ( Ordered Collection ol PMLogItem objects). PMLogsView>>renderContentOn: html | | allRecords := db root at: 'logs'. html table: [ html tableRow: [html tableHeading: 'View all Log Entries']]. html attributeAt: 'cellspacing' put: 0; attributeAt: 'cellpadding' put: 5; attributeAt: 'border' put: 2. html table: [ allRecords do: [:i | html tableRow: [ html tableData: [html anchorWithAction: [self delete: i] text: 'Del']. html tableData: i type. html tableData: i entryDate. html tableData: i startTime. html tableData: i entryText. html tableData: i endTime. ]. ]. html tableRow: [] ] ----------------------------- The delete: method looks like this: PMLogsView>>delete: aRecord (self confirm: 'Are you sure you want to delete ', (aRecord entryText) printString, '?') ifTrue: [allRecords removeAt: aRecord] ---------------------------- When I excute it Seaside displays the following error: MessageNotUnderstood: PMLogItem>>< * PMLogItem(Object)>>doesNotUnderstand: #< self a PMLogItem aMessage a Message with selector: #< and arguments: #(1) * KKObjectProxy>>doesNotUnderstand: #< self a PMLogItem aMessage a Message with selector: #< and arguments: #(1) * PMLogs(OrderedCollection)>>at: self a PMLogs(a PMLogItem a PMLogItem a PMLogItem a PMLogItem) anInteger a PMLogItem * PMLogs(OrderedCollection)>>removeAt: self a PMLogs(a PMLogItem a PMLogItem a PMLogItem a PMLogItem) index a PMLogItem removed nil * KKObjectProxy>>doesNotUnderstand: #removeAt: self a PMLogs(a PMLogItem a PMLogItem a PMLogItem a PMLogItem) aMessage a Message with selector: #removeAt: and arguments: #(a PMLogItem) * PMLogsView>>delete: self a PMLogsView aRecord a PMLogItem * [] in PMLogsView>>renderContentOn: self a PMLogsView html a WAHtmlRenderer i a PMLogItem * WAActionCallback>>evaluateWithArgument: self a WAActionCallback anObject '' * WAActionCallback(WACallback)>>evaluateWithField: self a WAActionCallback anObject '' * WACallbackStream>>processCallbacksWithOwner: self a WACallbackStream anObject a PMLogsView callback a WAActionCallback * PMLogsView(WAPresenter)>>processCallbackStream: self a PMLogsView aCallbackStream a WACallbackStream * [] in PMLogsTask(WAPresenter)>>processChildCallbacks: self a PMLogsTask aStream a WACallbackStream ea a PMLogsView * PMLogsView(WAComponent)>>decorationChainDo: self a PMLogsView aBlock [] in PMLogsTask(WAPresenter)>>processChildCallbacks: * [] in PMLogsTask(WAComponent)>>nextPresentersDo: self a PMLogsTask aBlock [] in PMLogsTask(WAPresenter)>>processChildCallbacks: ea a PMLogsView * [] in PMLogsTask(WAComponent)>>childrenDo: self a PMLogsTask aBlock [] in PMLogsTask(WAComponent)>>nextPresentersDo: ea a PMLogsView * Array(SequenceableCollection)>>do: self #(a PMLogsView) aBlock [] in PMLogsTask(WAComponent)>>childrenDo: index 1 indexLimiT 1 * PMLogsTask(WAComponent)>>childrenDo: self a PMLogsTask aBlock [] in PMLogsTask(WAComponent)>>nextPresentersDo: ea a PMLogsView * PMLogsTask(WAComponent)>>nextPresentersDo: self a PMLogsTask aBlock [] in PMLogsTask(WAPresenter)>>processChildCallbacks: ea a PMLogsView * PMLogsTask(WAPresenter)>>processChildCallbacks: self a PMLogsTask aStream a WACallbackStream ea a PMLogsView * PMLogsTask(WAPresenter)>>processCallbackStream: self a PMLogsTask aCallbackStream a WACallbackStream * [] in WAToolFrame(WAPresenter)>>processChildCallbacks: self a WAToolFrame aStream a WACallbackStream ea a PMLogsTask * PMLogsTask(WAComponent)>>decorationChainDo: self a PMLogsTask aBlock [] in WAToolFrame(WAPresenter)>>processChildCallbacks: * [] in WAToolFrame(WAComponent)>>nextPresentersDo: self a WAToolFrame aBlock [] in WAToolFrame(WAPresenter)>>processChildCallbacks: ea a PMLogsTask * [] in WAToolFrame(WAComponent)>>childrenDo: self a WAToolFrame aBlock [] in WAToolFrame(WAComponent)>>nextPresentersDo: ea a PMLogsTask * Array(SequenceableCollection)>>do: self #(a PMLogsTask) aBlock [] in WAToolFrame(WAComponent)>>childrenDo: index 1 indexLimiT 1 * WAToolFrame(WAComponent)>>childrenDo: self a WAToolFrame aBlock [] in WAToolFrame(WAComponent)>>nextPresentersDo: ea a PMLogsTask * WAToolFrame(WAComponent)>>nextPresentersDo: self a WAToolFrame aBlock [] in WAToolFrame(WAPresenter)>>processChildCallbacks: ea a PMLogsTask * WAToolFrame(WAPresenter)>>processChildCallbacks: self a WAToolFrame aStream a WACallbackStream ea a PMLogsTask * WAToolFrame(WAPresenter)>>processCallbackStream: self a WAToolFrame aCallbackStream a WACallbackStream * [] in WARenderLoop>>processCallbacks: self a WARenderLoop aCallbackStream a WACallbackStream lastPosition 0 ea a WAToolFrame * WAToolFrame(WAComponent)>>decorationChainDo: self a WAToolFrame aBlock [] in WARenderLoop>>processCallbacks: * WARenderLoop>>processCallbacks: self a WARenderLoop aCallbackStream a WACallbackStream lastPosition 0 ea a WAToolFrame * WARenderLoop>>render self a WARenderLoop request a WARequest context a WARenderingContext document nil docRoot nil url nil response nil ea nil * [] in WARenderLoop>>run self a WARenderLoop notification nil * BlockContext>>on:do: self [] in WARenderLoop>>run exception WARenderNotification handlerAction [] in WARenderLoop>>withRenderNowHandler: handlerActive true * WARenderLoop>>withRenderNowHandler: self a WARenderLoop aBlock [] in WARenderLoop>>run n nil * [] in WARenderLoop>>run self a WARenderLoop notification nil * BlockContext>>on:do: self [] in WARenderLoop>>run exception WAPageExpired handlerAction [] in WARenderLoop>>withPageExpiredHandler: handlerActive true * WARenderLoop>>withPageExpiredHandler: self a WARenderLoop aBlock [] in WARenderLoop>>run n nil * [] in WARenderLoop>>run self a WARenderLoop notification nil * BlockContext>>repeat self [] in WARenderLoop>>run * WARenderLoop>>run self a WARenderLoop notification nil * WARenderLoopMain>>start: self a WARenderLoopMain aRequest a WARequest * WASession>>start: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest * [] in WASession>>performRequest: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest key nil continuation nil * Dictionary>>at:ifAbsent: self a Dictionary() key '_k' aBlock [] in WASession>>performRequest: assoc nil * WASession>>performRequest: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest key nil continuation nil * [] in WASession>>responseForRequest: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest * BlockContext>>on:do: self [] in WASession>>responseForRequest: exception Error handlerAction [] in WASession>>withErrorHandler: handlerActive false * [] in WASession>>withErrorHandler: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aBlock [] in WASession>>responseForRequest: e MessageNotUnderstood: PMLogItem>>< w nil * BlockContext>>on:do: self [] in WASession>>withErrorHandler: exception Warning handlerAction [] in WASession>>withErrorHandler: handlerActive true * WASession>>withErrorHandler: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aBlock [] in WASession>>responseForRequest: e MessageNotUnderstood: PMLogItem>>< w nil * [] in WASession>>responseForRequest: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest * BlockContext>>on:do: self [] in WASession>>responseForRequest: exception WACurrentSession handlerAction [] in WACurrentSession class(WADynamicVariable class)>>use:during: handlerActive true * WACurrentSession class(WADynamicVariable class)>>use:during: self WACurrentSession anObject a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aBlock [] in WASession>>responseForRequest: n WACurrentSession * [] in WASession>>responseForRequest: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest * [] in WASession>>withEscapeContinuation: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aBlock [] in WASession>>responseForRequest: cc a Continuation * Continuation class>>currentDo: self Continuation aBlock [] in WASession>>withEscapeContinuation: * WASession>>withEscapeContinuation: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aBlock [] in WASession>>responseForRequest: cc a Continuation * WASession>>responseForRequest: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest * [] in WASession>>incomingRequest: self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) aRequest a WARequest e nil * BlockContext>>on:do: self [] in WASession>>incomingRequest: exception Error handlerAction [] in WASession>>incomingRequest: handlerActive true * [] in WAProcessMonitor>>critical:ifError: self a WAProcessMonitor aBlock [] in WASession>>incomingRequest: errorBlock [] in WASession>>incomingRequest: value a WAResponse * BlockContext>>ensure: self [] in WAProcessMonitor>>critical:ifError: aBlock [] in WAProcessMonitor>>critical:ifError: returnValue nil * [] in WAProcessMonitor>>critical:ifError: self a WAProcessMonitor aBlock [] in WASession>>incomingRequest: errorBlock [] in WASession>>incomingRequest: value a WAResponse * [] in BlockContext>>newProcess self [] in WAProcessMonitor>>critical:ifError: Thanks for the help. -Larry From adi at netstyle.ch Sat Jul 24 11:54:57 2004 From: adi at netstyle.ch (Adrian Lienhard) Date: Sat Jul 24 11:55:05 2004 Subject: [Seaside] Deleting from GOODS. In-Reply-To: <4101C7DA.1070303@landr.net> References: <4101C7DA.1070303@landr.net> Message-ID: <855F5A27-DD57-11D8-A70F-000A95E07986@netstyle.ch> Hi Larry It should say "allRecords remove: aRecord" and not #removeAt: (latter takes an integer to remove an item from the ordered collection at a specific index). Adrian On Jul 24, 2004, at 4:22 AM, LK wrote: > OK, I've got a table that will display records from my GOODS database. > Many thanks to Bany and Shaffer. Would someone tell me what's wrong > with my delete: method.? I've taken code from a 'table tutorial' > and modified it as follows: > > my PMLogsView class has an allRecords instance var which holds the > PMLogs ( Ordered Collection ol PMLogItem objects). > > PMLogsView>>renderContentOn: html > | | > allRecords := db root at: 'logs'. > html table: [ > html tableRow: [html tableHeading: 'View all Log Entries']]. > html attributeAt: 'cellspacing' put: 0; attributeAt: 'cellpadding' > put: 5; attributeAt: 'border' put: 2. > html table: [ > allRecords do: [:i | > html tableRow: [ > html tableData: [html anchorWithAction: [self > delete: i] text: 'Del']. > html tableData: i type. > html tableData: i entryDate. > html tableData: i startTime. > html tableData: i entryText. > html tableData: i endTime. > ]. > ]. > html tableRow: [] > ] > ----------------------------- > The delete: method looks like this: > > PMLogsView>>delete: aRecord > (self confirm: 'Are you sure you want to delete ', (aRecord entryText) > printString, '?') > ifTrue: [allRecords removeAt: aRecord] > ---------------------------- > When I excute it Seaside displays the following error: > > > MessageNotUnderstood: PMLogItem>>< > > * PMLogItem(Object)>>doesNotUnderstand: #< > > self a PMLogItem > aMessage a Message with selector: #< and arguments: #(1) > > * KKObjectProxy>>doesNotUnderstand: #< > > self a PMLogItem > aMessage a Message with selector: #< and arguments: #(1) > > * PMLogs(OrderedCollection)>>at: > > self a PMLogs(a PMLogItem a PMLogItem a PMLogItem a > PMLogItem) > anInteger a PMLogItem > > * PMLogs(OrderedCollection)>>removeAt: > > self a PMLogs(a PMLogItem a PMLogItem a PMLogItem a > PMLogItem) > index a PMLogItem > removed nil > > * KKObjectProxy>>doesNotUnderstand: #removeAt: > > self a PMLogs(a PMLogItem a PMLogItem a PMLogItem a > PMLogItem) > aMessage a Message with selector: #removeAt: and arguments: > #(a PMLogItem) > > * PMLogsView>>delete: > > self a PMLogsView > aRecord a PMLogItem > > * [] in PMLogsView>>renderContentOn: > > self a PMLogsView > html a WAHtmlRenderer > i a PMLogItem > > * WAActionCallback>>evaluateWithArgument: > > self a WAActionCallback > anObject '' > > * WAActionCallback(WACallback)>>evaluateWithField: > > self a WAActionCallback > anObject '' > > * WACallbackStream>>processCallbacksWithOwner: > > self a WACallbackStream > anObject a PMLogsView > callback a WAActionCallback > > * PMLogsView(WAPresenter)>>processCallbackStream: > > self a PMLogsView > aCallbackStream a WACallbackStream > > * [] in PMLogsTask(WAPresenter)>>processChildCallbacks: > > self a PMLogsTask > aStream a WACallbackStream > ea a PMLogsView > > * PMLogsView(WAComponent)>>decorationChainDo: > > self a PMLogsView > aBlock [] in > PMLogsTask(WAPresenter)>>processChildCallbacks: > > * [] in PMLogsTask(WAComponent)>>nextPresentersDo: > > self a PMLogsTask > aBlock [] in > PMLogsTask(WAPresenter)>>processChildCallbacks: > ea a PMLogsView > > * [] in PMLogsTask(WAComponent)>>childrenDo: > > self a PMLogsTask > aBlock [] in PMLogsTask(WAComponent)>>nextPresentersDo: > ea a PMLogsView > > * Array(SequenceableCollection)>>do: > > self #(a PMLogsView) > aBlock [] in PMLogsTask(WAComponent)>>childrenDo: > index 1 > indexLimiT 1 > > * PMLogsTask(WAComponent)>>childrenDo: > > self a PMLogsTask > aBlock [] in PMLogsTask(WAComponent)>>nextPresentersDo: > ea a PMLogsView > > * PMLogsTask(WAComponent)>>nextPresentersDo: > > self a PMLogsTask > aBlock [] in > PMLogsTask(WAPresenter)>>processChildCallbacks: > ea a PMLogsView > > * PMLogsTask(WAPresenter)>>processChildCallbacks: > > self a PMLogsTask > aStream a WACallbackStream > ea a PMLogsView > > * PMLogsTask(WAPresenter)>>processCallbackStream: > > self a PMLogsTask > aCallbackStream a WACallbackStream > > * [] in WAToolFrame(WAPresenter)>>processChildCallbacks: > > self a WAToolFrame > aStream a WACallbackStream > ea a PMLogsTask > > * PMLogsTask(WAComponent)>>decorationChainDo: > > self a PMLogsTask > aBlock [] in > WAToolFrame(WAPresenter)>>processChildCallbacks: > > * [] in WAToolFrame(WAComponent)>>nextPresentersDo: > > self a WAToolFrame > aBlock [] in > WAToolFrame(WAPresenter)>>processChildCallbacks: > ea a PMLogsTask > > * [] in WAToolFrame(WAComponent)>>childrenDo: > > self a WAToolFrame > aBlock [] in WAToolFrame(WAComponent)>>nextPresentersDo: > ea a PMLogsTask > > * Array(SequenceableCollection)>>do: > > self #(a PMLogsTask) > aBlock [] in WAToolFrame(WAComponent)>>childrenDo: > index 1 > indexLimiT 1 > > * WAToolFrame(WAComponent)>>childrenDo: > > self a WAToolFrame > aBlock [] in WAToolFrame(WAComponent)>>nextPresentersDo: > ea a PMLogsTask > > * WAToolFrame(WAComponent)>>nextPresentersDo: > > self a WAToolFrame > aBlock [] in > WAToolFrame(WAPresenter)>>processChildCallbacks: > ea a PMLogsTask > > * WAToolFrame(WAPresenter)>>processChildCallbacks: > > self a WAToolFrame > aStream a WACallbackStream > ea a PMLogsTask > > * WAToolFrame(WAPresenter)>>processCallbackStream: > > self a WAToolFrame > aCallbackStream a WACallbackStream > > * [] in WARenderLoop>>processCallbacks: > > self a WARenderLoop > aCallbackStream a WACallbackStream > lastPosition 0 > ea a WAToolFrame > > * WAToolFrame(WAComponent)>>decorationChainDo: > > self a WAToolFrame > aBlock [] in WARenderLoop>>processCallbacks: > > * WARenderLoop>>processCallbacks: > > self a WARenderLoop > aCallbackStream a WACallbackStream > lastPosition 0 > ea a WAToolFrame > > * WARenderLoop>>render > > self a WARenderLoop > request a WARequest > context a WARenderingContext > document nil > docRoot nil > url nil > response nil > ea nil > > * [] in WARenderLoop>>run > > self a WARenderLoop > notification nil > > * BlockContext>>on:do: > > self [] in WARenderLoop>>run > exception WARenderNotification > handlerAction [] in WARenderLoop>>withRenderNowHandler: > handlerActive true > > * WARenderLoop>>withRenderNowHandler: > > self a WARenderLoop > aBlock [] in WARenderLoop>>run > n nil > > * [] in WARenderLoop>>run > > self a WARenderLoop > notification nil > > * BlockContext>>on:do: > > self [] in WARenderLoop>>run > exception WAPageExpired > handlerAction [] in WARenderLoop>>withPageExpiredHandler: > handlerActive true > > * WARenderLoop>>withPageExpiredHandler: > > self a WARenderLoop > aBlock [] in WARenderLoop>>run > n nil > > * [] in WARenderLoop>>run > > self a WARenderLoop > notification nil > > * BlockContext>>repeat > > self [] in WARenderLoop>>run > > * WARenderLoop>>run > > self a WARenderLoop > notification nil > > * WARenderLoopMain>>start: > > self a WARenderLoopMain > aRequest a WARequest > > * WASession>>start: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > > * [] in WASession>>performRequest: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > key nil > continuation nil > > * Dictionary>>at:ifAbsent: > > self a Dictionary() > key '_k' > aBlock [] in WASession>>performRequest: > assoc nil > > * WASession>>performRequest: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > key nil > continuation nil > > * [] in WASession>>responseForRequest: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > > * BlockContext>>on:do: > > self [] in WASession>>responseForRequest: > exception Error > handlerAction [] in WASession>>withErrorHandler: > handlerActive false > > * [] in WASession>>withErrorHandler: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aBlock [] in WASession>>responseForRequest: > e MessageNotUnderstood: PMLogItem>>< > w nil > > * BlockContext>>on:do: > > self [] in WASession>>withErrorHandler: > exception Warning > handlerAction [] in WASession>>withErrorHandler: > handlerActive true > > * WASession>>withErrorHandler: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aBlock [] in WASession>>responseForRequest: > e MessageNotUnderstood: PMLogItem>>< > w nil > > * [] in WASession>>responseForRequest: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > > * BlockContext>>on:do: > > self [] in WASession>>responseForRequest: > exception WACurrentSession > handlerAction [] in WACurrentSession > class(WADynamicVariable > class)>>use:during: > handlerActive true > > * WACurrentSession class(WADynamicVariable class)>>use:during: > > self WACurrentSession > anObject a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aBlock [] in WASession>>responseForRequest: > n WACurrentSession > > * [] in WASession>>responseForRequest: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > > * [] in WASession>>withEscapeContinuation: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aBlock [] in WASession>>responseForRequest: > cc a Continuation > > * Continuation class>>currentDo: > > self Continuation > aBlock [] in WASession>>withEscapeContinuation: > > * WASession>>withEscapeContinuation: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aBlock [] in WASession>>responseForRequest: > cc a Continuation > > * WASession>>responseForRequest: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > > * [] in WASession>>incomingRequest: > > self a WASession(/seaside/logs?_s=YGJFCkUdbwMVquFZ) > aRequest a WARequest > e nil > > * BlockContext>>on:do: > > self [] in WASession>>incomingRequest: > exception Error > handlerAction [] in WASession>>incomingRequest: > handlerActive true > > * [] in WAProcessMonitor>>critical:ifError: > > self a WAProcessMonitor > aBlock [] in WASession>>incomingRequest: > errorBlock [] in WASession>>incomingRequest: > value a WAResponse > > * BlockContext>>ensure: > > self [] in WAProcessMonitor>>critical:ifError: > aBlock [] in WAProcessMonitor>>critical:ifError: > returnValue nil > > * [] in WAProcessMonitor>>critical:ifError: > > self a WAProcessMonitor > aBlock [] in WASession>>incomingRequest: > errorBlock [] in WASession>>incomingRequest: > value a WAResponse > > * [] in BlockContext>>newProcess > > self [] in WAProcessMonitor>>critical:ifError: > > > Thanks for the help. > -Larry > > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside > > ___________________ Adrian Lienhard www.adrian-lienhard.ch www.netstyle.ch From s002 at landr.net Sat Jul 24 16:35:48 2004 From: s002 at landr.net (LK) Date: Sat Jul 24 16:35:56 2004 Subject: [Seaside] Deleting from GOODS. In-Reply-To: <855F5A27-DD57-11D8-A70F-000A95E07986@netstyle.ch> References: <4101C7DA.1070303@landr.net> <855F5A27-DD57-11D8-A70F-000A95E07986@netstyle.ch> Message-ID: <410273C4.1000505@landr.net> Adrian Lienhard wrote: > Hi Larry > > It should say "allRecords remove: aRecord" and not #removeAt: (latter > takes an integer to remove an item from the ordered collection at a > specific index). > > Adrian Thanks, That executed w/o error, but. nothing was removed from GOODS. I added this method: delete: aRecord from: aDatabase (self confirm: 'Are you sure you want to delete: ', (aRecord entryText) printString, '?') ifTrue: [allRecords remove: aRecord. aDatabase commit.]. It says that it cannot understand #commit. In workspace, db commit executes properly. What am I missing here????? -Larry > > On Jul 24, 2004, at 4:22 AM, LK wrote: > >> OK, I've got a table that will display records from my GOODS >> database. Many thanks to Bany and Shaffer. Would someone tell me >> what's wrong with my delete: method.? I've taken code from a >> 'table tutorial' and modified it as follows: >> >> my PMLogsView class has an allRecords instance var which holds the >> PMLogs ( Ordered Collection ol PMLogItem objects). >> >> PMLogsView>>renderContentOn: html >> | | >> allRecords := db root at: 'logs'. >> html table: [ >> html tableRow: [html tableHeading: 'View all Log Entries']]. >> html attributeAt: 'cellspacing' put: 0; attributeAt: 'cellpadding' >> put: 5; attributeAt: 'border' put: 2. >> html table: [ >> allRecords do: [:i | >> html tableRow: [ >> html tableData: [html anchorWithAction: [self >> delete: i from db] text: 'Del']. >> html tableData: i type. >> html tableData: i entryDate. >> html tableData: i startTime. >> html tableData: i entryText. >> html tableData: i endTime. >> ]. >> ]. >> html tableRow: [] >> ] >> ----------------------------- >> The delete: method looks like this: >> >> PMLogsView>>delete: aRecord >> (self confirm: 'Are you sure you want to delete ', (aRecord >> entryText) printString, '?') >> ifTrue: [allRecords removeAt: aRecord] >> ---------------------------- >> When I excute it Seaside displays the following error: > > ----- SNIP ----- From avi at beta4.com Sat Jul 24 23:33:52 2004 From: avi at beta4.com (Avi Bryant) Date: Sat Jul 24 23:33:57 2004 Subject: [Seaside] Deleting from GOODS. In-Reply-To: <410273C4.1000505@landr.net> References: <4101C7DA.1070303@landr.net> <855F5A27-DD57-11D8-A70F-000A95E07986@netstyle.ch> <410273C4.1000505@landr.net> Message-ID: <283AB590-DDB9-11D8-B33C-000A95DB7844@beta4.com> On Jul 24, 2004, at 7:35 AM, LK wrote: > Adrian Lienhard wrote: > >> Hi Larry >> >> It should say "allRecords remove: aRecord" and not #removeAt: (latter >> takes an integer to remove an item from the ordered collection at a >> specific index). >> >> Adrian > > Thanks, That executed w/o error, but. nothing was removed from GOODS. > I added this method: > delete: aRecord from: aDatabase > (self confirm: 'Are you sure you want to delete: ', (aRecord > entryText) printString, '?') > ifTrue: [allRecords remove: aRecord. > aDatabase commit.]. > > It says that it cannot understand #commit. In workspace, db commit > executes properly. What am I missing here????? Well, you must somehow have the wrong object passed in as aDatabase. When the MNU #commit error comes up, what class does it say aDatabase is? That might give you a clue as to what's going wrong. Avi From s002 at landr.net Mon Jul 26 18:34:17 2004 From: s002 at landr.net (s002) Date: Mon Jul 26 18:34:29 2004 Subject: [Seaside] Add button not showing it's page Message-ID: <20040726163417.32099.qmail@mail.taricco.net> I have an object that shows a record from a GOODS database. I created a link to 'add' a new record. When I click on the link, the screen flashes and stays at the recordlist page. Can someone help me. PMLogsView>>renderContentOn: html | | html table: [ html tableRow: [html tableHeading: 'View all Log Entries'; space; space; space. html tableData: [html anchorWithAction: [self renderAddOn: html] text: 'Add']]]. html attributeAt: 'cellspacing' put: 0; attributeAt: 'cellpadding' put: 5; attributeAt: 'border' put: 2. html table: [ allRecords do: [:i | html tableRow: [ html tableData: [html anchorWithAction: [self delete: i from: db] text: 'Del']. html tableData: i type. html tableData: i entryDate. html tableData: i startTime. html tableData: i entryText. html tableData: i endTime. ]. ]. html tableRow: [] ] ------ and here is the PMLogsView>>renderAddOn: html " show add new log form" aRecord := PMLogItem new. aRecord initialize. html form: [ html table: [ html tableRow: [html tableHeading: 'New Log Entry']]. html text: 'TEST NEW ENTRY PAGE'. html text: aRecord entryDate.] From avi at beta4.com Mon Jul 26 22:08:07 2004 From: avi at beta4.com (Avi Bryant) Date: Mon Jul 26 22:08:16 2004 Subject: [Seaside] 2.5b2 Message-ID: <82B76E3D-DF3F-11D8-96A0-000A95DB7844@beta4.com> Hi folks, Just released Seaside 2.5b2. The changes from b1, mostly thanks to Adrian Lienhard and Michel Bany, are: - added #orderedList: and #orderedList:do: to AbstractHtmlBuilder - fixed Application>>name to allow an empty basePath - fixed #findStyles to include the request in the context - fixed #valueInputOfType:value:callback: to use the raw string instead of throwing an error when it is expecting a number in the callback but doesn't find one - added a 'Cache-Control: No-cache' header to rendered pages by default I've also been experimenting some with Javascript's XMLHttpRequest support, and have included a preview of this work. You can read more in this blog post, and see an example in WALiveRequestTest: http://www.cincomsmalltalk.com/userblogs/avi/blogView? showComments=true&entry=3268075684 Like the Canvas work, this is *not* a supported part of Seaside 2.5, but since it's independent of the rest of the code I don't mind keeping the previews in the release. Avi From avi at beta4.com Mon Jul 26 22:15:05 2004 From: avi at beta4.com (Avi Bryant) Date: Mon Jul 26 22:15:15 2004 Subject: [Seaside] request termination Message-ID: <7BE57416-DF40-11D8-96A0-000A95DB7844@beta4.com> Here's something I'd like an opinion on: if the browser times out when waiting for a response, or the user hits the stop button, and the connection is dropped, Seaside still keeps chugging away on the request. Should we terminate the process instead? And if so, how do we get a notification from the webserver about the dropped connection in a portable way? At least in Squeak, terminating the process does make sure to run all the #ensure: blocks, and I expect/hope the same would be true in other dialects as well. So as long as people are careful, it shouldn't do *too* much damage to kill the process. It's also unlikely that the callback processing is what would take too long and timeout (barring an inifinite loop) - usually it would be the render phase getting terminated, which should be pretty harmless. A From avi at beta4.com Mon Jul 26 22:17:17 2004 From: avi at beta4.com (Avi Bryant) Date: Mon Jul 26 22:17:24 2004 Subject: [Seaside] Add button not showing it's page In-Reply-To: <20040726163417.32099.qmail@mail.taricco.net> References: <20040726163417.32099.qmail@mail.taricco.net> Message-ID: On Jul 26, 2004, at 9:34 AM, s002 wrote: > I have an object that shows a record from a GOODS database. I created > a link to 'add' a new record. When I click on the link, the screen > flashes and stays at the recordlist page. Can someone help me. > PMLogsView>>renderContentOn: html > | | > html table: [ > html tableRow: [html tableHeading: 'View all Log Entries'; space; > space; space. > html tableData: [html anchorWithAction: [self renderAddOn: html] > text: 'Add']]]. > html attributeAt: 'cellspacing' put: 0; attributeAt: 'cellpadding' > put: 5; attributeAt: 'border' put: 2. > html table: [ > allRecords do: [:i | > html tableRow: [ > html tableData: [html anchorWithAction: [self delete: i from: db] > text: 'Del']. > html tableData: i type. > html tableData: i entryDate. > html tableData: i startTime. > html tableData: i entryText. > html tableData: i endTime. > ]. > ]. > html tableRow: [] > ] You don't want two methods on the same class here, you want two different classes. So your #renderAddOn: method should be the #renderContentOn: of a PMLogsAddItem component. And then your 'Add' link should be this: html anchorWithAction: [self call: PMLogsAddItem new] text: 'Add'. Does that make sense? > and here is the > PMLogsView>>renderAddOn: html > " show add new log form" > aRecord := PMLogItem new. > aRecord initialize. > html form: [ > html table: [ > html tableRow: [html tableHeading: 'New Log Entry']]. > html text: 'TEST NEW ENTRY PAGE'. > html text: aRecord entryDate.] > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside From julian at beta4.com Mon Jul 26 22:42:40 2004 From: julian at beta4.com (Julian Fitzell) Date: Mon Jul 26 22:44:10 2004 Subject: [Seaside] Add button not showing it's page In-Reply-To: <20040726163417.32099.qmail@mail.taricco.net> References: <20040726163417.32099.qmail@mail.taricco.net> Message-ID: <41056CC0.1050007@beta4.com> Hi s002, Say, do you have a name? :) So the problem below is that you are using a render method as your callback, which is not at all what you want to do. Every time a request comes in, the callbacks are executed and then the root component is obtained and asked to render itself to be displayed to the user. Your callback needs to perform some action to cause the display state to change before the next render pass is executed. When you call #renderAddOn: in your callback, nothing changes that would cause PMLogsView to render itself any differently than the last time, which is why you see the same page drawn again. What you probably want to do here is have another component, say PMLogItemEditor, which you pass a new instance of PMLogItem into. For example you could write an action method like: addNewItem |item| item := PMLogItem new. "store the item however you do that" self call: (self editorComponentFor: item) And then in your render method use: html anchorWithAction: [self addNewItem] text: 'Add' Obviously you'd have to implement a #children method as well as #editorComponentFor: to keep track of the editor component... Julian s002 wrote: > I have an object that shows a record from a GOODS database. I created a > link to 'add' a new record. When I click on the link, the screen > flashes and stays at the recordlist page. Can someone help me. > PMLogsView>>renderContentOn: html > | | > html table: [ > html tableRow: [html tableHeading: 'View all Log Entries'; > space; space; space. > html tableData: [html anchorWithAction: [self renderAddOn: > html] text: 'Add']]]. > html attributeAt: 'cellspacing' put: 0; attributeAt: 'cellpadding' > put: 5; attributeAt: 'border' put: 2. > html table: [ > allRecords do: [:i | > html tableRow: [ > html tableData: [html anchorWithAction: [self > delete: i from: db] text: 'Del']. > html tableData: i type. > html tableData: i entryDate. > html tableData: i startTime. > html tableData: i entryText. > html tableData: i endTime. > ]. > ]. > html tableRow: [] > ] > ------ > and here is the > PMLogsView>>renderAddOn: html > " show add new log form" > aRecord := PMLogItem new. > aRecord initialize. > html form: [ > html table: [ > html tableRow: [html tableHeading: 'New Log Entry']]. > html text: 'TEST NEW ENTRY PAGE'. > html text: aRecord entryDate.] > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside From chris.double at double.co.nz Tue Jul 27 01:43:03 2004 From: chris.double at double.co.nz (Chris Double) Date: Tue Jul 27 01:43:15 2004 Subject: [Seaside] 2.5b2 In-Reply-To: <82B76E3D-DF3F-11D8-96A0-000A95DB7844@beta4.com> References: <82B76E3D-DF3F-11D8-96A0-000A95DB7844@beta4.com> Message-ID: <1090885383.30502.201124331@webmail.messagingengine.com> On Mon, 26 Jul 2004 13:08:07 -0700, "Avi Bryant" said: > I've also been experimenting some with Javascript's XMLHttpRequest > support, and have included a preview of this work. You can read more > in this blog post, and see an example in WALiveRequestTest: That is very cool. The WALiveRequestTest is nifty. Is it making a server request in the background when entering text in the input boxes and clicking the time button? It's fast! At first I thought it was javascript just changing the time locally but it's actually done by the server and the javascript is replacing the result from the server inline on the page right? Chris. -- Chris Double chris.double@double.co.nz From avi at beta4.com Tue Jul 27 04:52:54 2004 From: avi at beta4.com (Avi Bryant) Date: Tue Jul 27 04:53:06 2004 Subject: [Seaside] 2.5b2 In-Reply-To: <1090885383.30502.201124331@webmail.messagingengine.com> References: <82B76E3D-DF3F-11D8-96A0-000A95DB7844@beta4.com> <1090885383.30502.201124331@webmail.messagingengine.com> Message-ID: <0EFBF565-DF78-11D8-96A0-000A95DB7844@beta4.com> On Jul 26, 2004, at 4:43 PM, Chris Double wrote: > On Mon, 26 Jul 2004 13:08:07 -0700, "Avi Bryant" said: >> I've also been experimenting some with Javascript's XMLHttpRequest >> support, and have included a preview of this work. You can read more >> in this blog post, and see an example in WALiveRequestTest: > > That is very cool. The WALiveRequestTest is nifty. Is it making a > server > request in the background when entering text in the input boxes and > clicking the time button? It's fast! At first I thought it was > javascript just changing the time locally but it's actually done by the > server and the javascript is replacing the result from the server > inline > on the page right? > Right. From rbb at techgame.net Tue Jul 27 17:22:56 2004 From: rbb at techgame.net (Brian Brown) Date: Tue Jul 27 17:24:19 2004 Subject: [Seaside] request termination In-Reply-To: <7BE57416-DF40-11D8-96A0-000A95DB7844@beta4.com> References: <7BE57416-DF40-11D8-96A0-000A95DB7844@beta4.com> Message-ID: On Jul 26, 2004, at 2:15 PM, Avi Bryant wrote: > Here's something I'd like an opinion on: if the browser times out when > waiting for a response, or the user hits the stop button, and the > connection is dropped, Seaside still keeps chugging away on the > request. Should we terminate the process instead? And if so, how do > we get a notification from the webserver about the dropped connection > in a portable way? > This would be phenomenal! That is another issue I've had problems with in the past in OWF (Other Web Frameworks) The stop button doesn't mean a whole lot to them if you stop a big request in the middle. > At least in Squeak, terminating the process does make sure to run all > the #ensure: blocks, and I expect/hope the same would be true in other > dialects as well. So as long as people are careful, it shouldn't do > *too* much damage to kill the process. It's also unlikely that the > callback processing is what would take too long and timeout (barring > an inifinite loop) - usually it would be the render phase getting > terminated, which should be pretty harmless. > And we care about other dialects why? (Just kidding!) > A > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside From rbb at techgame.net Tue Jul 27 22:21:58 2004 From: rbb at techgame.net (Brian Brown) Date: Tue Jul 27 22:23:24 2004 Subject: [Seaside] 2.5b2 In-Reply-To: <0EFBF565-DF78-11D8-96A0-000A95DB7844@beta4.com> References: <82B76E3D-DF3F-11D8-96A0-000A95DB7844@beta4.com> <1090885383.30502.201124331@webmail.messagingengine.com> <0EFBF565-DF78-11D8-96A0-000A95DB7844@beta4.com> Message-ID: <9C7E0EE8-E00A-11D8-9F69-003065F89450@techgame.net> On Jul 26, 2004, at 8:52 PM, Avi Bryant wrote: >> That is very cool. The WALiveRequestTest is nifty. Is it making a >> server >> request in the background when entering text in the input boxes and >> clicking the time button? It's fast! At first I thought it was >> javascript just changing the time locally but it's actually done by >> the >> server and the javascript is replacing the result from the server >> inline >> on the page right? >> > > Right. > This is seriously cool stuff. I'll definitely be using this. thanks Avi! From s002 at landr.net Wed Jul 28 05:58:37 2004 From: s002 at landr.net (LK) Date: Wed Jul 28 05:59:07 2004 Subject: [Seaside] Deleting from GOODS. In-Reply-To: <283AB590-DDB9-11D8-B33C-000A95DB7844@beta4.com> References: <4101C7DA.1070303@landr.net> <855F5A27-DD57-11D8-A70F-000A95E07986@netstyle.ch> <410273C4.1000505@landr.net> <283AB590-DDB9-11D8-B33C-000A95DB7844@beta4.com> Message-ID: <4107246D.5020509@landr.net> Avi Bryant wrote: > > On Jul 24, 2004, at 7:35 AM, LK wrote: > >> Adrian Lienhard wrote: >> >>> Hi Larry >>> >>> It should say "allRecords remove: aRecord" and not #removeAt: >>> (latter takes an integer to remove an item from the ordered >>> collection at a specific index). >>> >>> Adrian >> >> >> Thanks, That executed w/o error, but. nothing was removed from GOODS. >> I added this method: >> delete: aRecord from: aDatabase >> (self confirm: 'Are you sure you want to delete: ', (aRecord >> entryText) printString, '?') >> ifTrue: [allRecords remove: aRecord. >> aDatabase commit.]. >> >> It says that it cannot understand #commit. In workspace, db commit >> executes properly. What am I missing here????? > > > Well, you must somehow have the wrong object passed in as aDatabase. > When the MNU #commit error comes up, what class does it say aDatabase > is? That might give you a clue as to what's going wrong. > > Avi > It says aDatabase is nil. So, it's not getting passed to the PMLogsView method properly. Moving the db connect method to the PMLogsView class solves the problem. But, it would be nice if the database connection was opened in the object that calls PMLogsView, and passed to the subcomponents. PMLogsTask>>RenderLoop db := dbConnection new.. PMLogsView ( which would include calls to PMLogsAddItem, PMLogsModifyItem, PMLogsDeleteITem, etc which would need access to the db connection in order to do #commit and #refresh) . . . db logout. ----------------- How would I make the db object available to nested subcomponents? -Larry From s002 at landr.net Wed Jul 28 06:42:53 2004 From: s002 at landr.net (LK) Date: Wed Jul 28 06:43:16 2004 Subject: [Seaside] Add button not showing it's page In-Reply-To: <41056CC0.1050007@beta4.com> References: <20040726163417.32099.qmail@mail.taricco.net> <41056CC0.1050007@beta4.com> Message-ID: <41072ECD.3080807@landr.net> Sorry, I'm Larry Kelly. the addNewItem needs a #children method? What would go in it? I'm unclear what the #children method is for? Sorry to be so dense.:) -Larry Julian Fitzell wrote: > Hi s002, > > Say, do you have a name? :) > > So the problem below is that you are using a render method as your > callback, which is not at all what you want to do. > > Every time a request comes in, the callbacks are executed and then the > root component is obtained and asked to render itself to be displayed > to the user. Your callback needs to perform some action to cause the > display state to change before the next render pass is executed. > > When you call #renderAddOn: in your callback, nothing changes that > would cause PMLogsView to render itself any differently than the last > time, which is why you see the same page drawn again. > > What you probably want to do here is have another component, say > PMLogItemEditor, which you pass a new instance of PMLogItem into. For > example you could write an action method like: > > addNewItem > |item| > item := PMLogItem new. > "store the item however you do that" > self call: (self editorComponentFor: item) > > And then in your render method use: > > html anchorWithAction: [self addNewItem] text: 'Add' > > Obviously you'd have to implement a #children method as well as > #editorComponentFor: to keep track of the editor component... > > Julian > > s002 wrote: > >> I have an object that shows a record from a GOODS database. I >> created a link to 'add' a new record. When I click on the link, the >> screen flashes and stays at the recordlist page. Can someone help me. >> PMLogsView>>renderContentOn: html >> | | >> html table: [ >> html tableRow: [html tableHeading: 'View all Log Entries'; >> space; space; space. >> html tableData: [html anchorWithAction: [self >> renderAddOn: html] text: 'Add']]]. >> html attributeAt: 'cellspacing' put: 0; attributeAt: >> 'cellpadding' put: 5; attributeAt: 'border' put: 2. >> html table: [ >> allRecords do: [:i | >> html tableRow: [ >> html tableData: [html anchorWithAction: [self >> delete: i from: db] text: 'Del']. >> html tableData: i type. >> html tableData: i entryDate. >> html tableData: i startTime. >> html tableData: i entryText. >> html tableData: i endTime. >> ]. >> ]. >> html tableRow: [] >> ] >> ------ >> and here is the >> PMLogsView>>renderAddOn: html >> " show add new log form" >> aRecord := PMLogItem new. >> aRecord initialize. >> html form: [ >> html table: [ >> html tableRow: [html tableHeading: 'New Log Entry']]. >> html text: 'TEST NEW ENTRY PAGE'. >> html text: aRecord entryDate.] >> _______________________________________________ >> Seaside mailing list >> Seaside@lists.squeakfoundation.org >> http://lists.squeakfoundation.org/listinfo/seaside > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside > > From avi at beta4.com Wed Jul 28 06:44:33 2004 From: avi at beta4.com (Avi Bryant) Date: Wed Jul 28 06:44:39 2004 Subject: [Seaside] Deleting from GOODS. In-Reply-To: <4107246D.5020509@landr.net> References: <4101C7DA.1070303@landr.net> <855F5A27-DD57-11D8-A70F-000A95E07986@netstyle.ch> <410273C4.1000505@landr.net> <283AB590-DDB9-11D8-B33C-000A95DB7844@beta4.com> <4107246D.5020509@landr.net> Message-ID: On Jul 27, 2004, at 8:58 PM, LK wrote: > It says aDatabase is nil. So, it's not getting passed to the > PMLogsView method properly. Moving the db connect method to the > PMLogsView class solves the problem. But, it would be nice if the > database connection was opened in the object that calls PMLogsView, > and passed to the subcomponents. > > PMLogsTask>>RenderLoop > db := dbConnection new.. > PMLogsView ( which would include calls to PMLogsAddItem, > PMLogsModifyItem, PMLogsDeleteITem, etc which would need access to the > db connection in order to do #commit and #refresh) > . . . > db logout. > ----------------- > How would I make the db object available to nested subcomponents? The usual way is to access it through the session, which is available to any component through #session, or anything else through "WACurrentSession value". Just subclass WASession to include a db instance variable, and configure your app to use that session class. Brian Brown has some documentation of this pattern here: http://www.techgame.net/projects/Seaside/wiki/SetupSessionForGOODS Avi From rbb at techgame.net Wed Jul 28 07:30:37 2004 From: rbb at techgame.net (Brian Brown) Date: Wed Jul 28 07:31:26 2004 Subject: [Seaside] Add button not showing it's page In-Reply-To: <41072ECD.3080807@landr.net> References: <20040726163417.32099.qmail@mail.taricco.net> <41056CC0.1050007@beta4.com> <41072ECD.3080807@landr.net> Message-ID: <1090992636.31386.8.camel@siniwali.ablelinktech.com> On Tue, 2004-07-27 at 22:42, LK wrote: > Sorry, I'm Larry Kelly. > > the addNewItem needs a #children method? What would go in it? I'm > unclear what the #children method is for? Sorry to be so dense.:) > -Larry > The #children method is a recent addition to Seaside; the renderer uses it to determine what should be rendered. What goes in it are all the components of a component (or subcomponents if you will). For example, if you have a component ParentComponent that has two instance variables; child1 and child2. For to make this really easy to try, put an initialize method on ParentComponent: initialize child1 := WACounter new. child2 := WACounter new. Then in ParentComponent>>renderContentOn: renderContentOn: html html heading: 'Check out my children!' level: 3. html render: child1; br; render child2. In order for callbacks to work properly, in this case you would have a #children like this: children ^ Array with: child1 with: child2 Please note that if you put sub components that have forms rendered from the renderContent on of a component, they will show up fine even if not being returned from #children. You just won't be able to actually submit the forms without a traceback. :) HTH, Brian > Julian Fitzell wrote: > > > Hi s002, > > > > Say, do you have a name? :) > > > > So the problem below is that you are using a render method as your > > callback, which is not at all what you want to do. > > > > Every time a request comes in, the callbacks are executed and then the > > root component is obtained and asked to render itself to be displayed > > to the user. Your callback needs to perform some action to cause the > > display state to change before the next render pass is executed. > > > > When you call #renderAddOn: in your callback, nothing changes that > > would cause PMLogsView to render itself any differently than the last > > time, which is why you see the same page drawn again. > > > > What you probably want to do here is have another component, say > > PMLogItemEditor, which you pass a new instance of PMLogItem into. For > > example you could write an action method like: > > > > addNewItem > > |item| > > item := PMLogItem new. > > "store the item however you do that" > > self call: (self editorComponentFor: item) > > > > And then in your render method use: > > > > html anchorWithAction: [self addNewItem] text: 'Add' > > > > Obviously you'd have to implement a #children method as well as > > #editorComponentFor: to keep track of the editor component... > > > > Julian > > > > s002 wrote: > > > >> I have an object that shows a record from a GOODS database. I > >> created a link to 'add' a new record. When I click on the link, the > >> screen flashes and stays at the recordlist page. Can someone help me. > >> PMLogsView>>renderContentOn: html > >> | | > >> html table: [ > >> html tableRow: [html tableHeading: 'View all Log Entries'; > >> space; space; space. > >> html tableData: [html anchorWithAction: [self > >> renderAddOn: html] text: 'Add']]]. > >> html attributeAt: 'cellspacing' put: 0; attributeAt: > >> 'cellpadding' put: 5; attributeAt: 'border' put: 2. > >> html table: [ > >> allRecords do: [:i | > >> html tableRow: [ > >> html tableData: [html anchorWithAction: [self > >> delete: i from: db] text: 'Del']. > >> html tableData: i type. > >> html tableData: i entryDate. > >> html tableData: i startTime. > >> html tableData: i entryText. > >> html tableData: i endTime. > >> ]. > >> ]. > >> html tableRow: [] > >> ] > >> ------ > >> and here is the > >> PMLogsView>>renderAddOn: html > >> " show add new log form" > >> aRecord := PMLogItem new. > >> aRecord initialize. > >> html form: [ > >> html table: [ > >> html tableRow: [html tableHeading: 'New Log Entry']]. > >> html text: 'TEST NEW ENTRY PAGE'. > >> html text: aRecord entryDate.] > >> _______________________________________________ > >> Seaside mailing list > >> Seaside@lists.squeakfoundation.org > >> http://lists.squeakfoundation.org/listinfo/seaside > > > > _______________________________________________ > > Seaside mailing list > > Seaside@lists.squeakfoundation.org > > http://lists.squeakfoundation.org/listinfo/seaside > > > > > > _______________________________________________ > Seaside mailing list > Seaside@lists.squeakfoundation.org > http://lists.squeakfoundation.org/listinfo/seaside From julian at beta4.com Wed Jul 28 07:32:31 2004 From: julian at beta4.com (Julian Fitzell) Date: Wed Jul 28 07:32:39 2004 Subject: [Seaside] Add button not showing it's page In-Reply-To: <41072ECD.3080807@landr.net> References: <20040726163417.32099.qmail@mail.taricco.net> <41056CC0.1050007@beta4.com> <41072ECD.3080807@landr.net> Message-ID: <41073A6F.1090201@beta4.com> LK wrote: > Sorry, I'm Larry Kelly. > the addNewItem needs a #children method? What would go in it? I'm > unclear what the #children method is for? Sorry to be so dense.:) > -Larry Hi Larry, not a problem. So a component's #children method is supposed to return an array of all the subcomponents it is currently displaying within itself. Unfortunately it was me who was being dense for even mentioning it in this context: you don't need to implement a #children method when you call another component. I think I must have confused myself between what you had been trying to do and the solution I was suggesting for you. You could probably ignore all the #editorComponentFor: stuff I was talking about as well as #children for now and just implement addItem more like: addItem self call: (PMLogItemEditor new item: PMLogItem new) (noting again that you need to do something with the new item to store it somewhere presumably). To explain #children a little more, since I brought it up, let's look at WAMultiCounter as an example that needs to implement #children. It's render method looks like: renderContentOn: html counters do: [:ea | html render: ea] separatedBy: [html horizontalRule] and it implements #children as follows: children ^ counters Seaside uses #children when handling callbacks, decorations, etc. to make sure each of the embedded components has its chance to do processing. You can see some weird behaviour if you don't have #children properly defined in those cases. Cheers, Julian -- Julian Fitzell -- Beta4 Productions julian@beta4.com -- http://www.beta4.com Seaside: http://www.beta4.com/seaside2 From kamk at volny.cz Wed Jul 28 11:03:47 2004 From: kamk at volny.cz (Kamil Kukura) Date: Wed Jul 28 11:07:50 2004 Subject: [Seaside] Re: 2.5b2 In-Reply-To: <82B76E3D-DF3F-11D8-96A0-000A95DB7844@beta4.com> References: <82B76E3D-DF3F-11D8-96A0-000A95DB7844@beta4.com> Message-ID: <41076BF3.70703@volny.cz> Avi Bryant wrote: > Hi folks, > > Just released Seaside 2.5b2. The changes from b1, mostly thanks to > Adrian Lienhard and Michel Bany, are: I just upgraded to this version and here are some remarks: - still don't have asMutator used in WAHtmlRenderer)>>radioButtonInGroup:withValue:on:of: so I needed to backfix this. - using scripts and styles in external files I had to put everything regarding ... content into #updateRoot: while holding on its super's counterpart. I use #addHeadElement: so now I'm not sure if it will survive next versions. More on that below. - now updating document's title from #updateRoot: in the root component. Perhaps there could be better way for a component to alternate document's title. Now back to your announcement. > I've also been experimenting some with Javascript's XMLHttpRequest > support, and have included a preview of this work. You can read more > in this blog post, and see an example in WALiveRequestTest: > > http://www.cincomsmalltalk.com/userblogs/avi/blogView? > showComments=true&entry=3268075684 Urgh, what that space after question mark... Anyway, it's cool to see support for client-side scripting. Btw, I call these "continuation" web applications as "web-terminal applications" and scripting turns web browser to great terminal front-end. To me it's like next evolution of IBM's 3270 batch terminal :) > Like the Canvas work, this is *not* a supported part of Seaside 2.5, > but since it's independent of the rest of the code I don't mind keeping > the previews in the release. Well, but I see all of WAStandardScripts and WAStandardStyles in every application configured. First I was shocked why simple counter has so many stylesheets attached to it. I must admit I don't understand library browser much. I think WARenderedHtmlRoot>>write[Script|Style]:on: is quite rough. I see there idea of "EITI - Everything In The Image" but I guess there could be finer control for styles/scripts inclusion. How do you like the idea of having classes such as WAScriptContent having #scriptType and #isDeferred that would correspond to