Learning ColdBox: Multiple Updates uisng a Object
My venture in ColdBox has been so far very enjoyable. It has really changed the way I plan my applications. My stumble in to using objects (correctly) has also brought with it some challenges and changed my approach to building maintainable and reusable applications.
So far my blog entries on ColdBox have mainly been on objects, validation and persistent, all straight forward when doing simple updating/creating/deleting actions.
Anyway, going back to challenges and objects, my first real stumbling block came a few weeks ago. How do I insert multiple records from data that comes from a form using a object?
I asked this question on both the ColdBox forums and CFTALK list. They all make it sound so simple, not sure they had this in mind.
My problem was as follows: when creating/updating a product I need to insert/update or delete multiple records for the product options based on what the user ticked or not ticked. So my first attempt worked that's a start right? here goes....
First I populated all my options for the products in my view. Below is the option view created in my option tab.
2 <cfoutput>
3 <tr>
4 <td class="borderleft">
5 <input type="checkbox" <cfif current.idexists eq 1> checked="checked" </cfif> name="optionToUpdate" value="#rc.getOption.valueId#" /></td>
6 <td> #rc.option.value#</td>
7 <td> £
8 <input value="#NumberFormat(current.optionPrice,99.99)#" type="text" name="optionPrice_#rc.getOption.valueId#" size="3" />
9 extra</td>
10 <td> </td>
11 <td> </td>
12 </tr>
13 </cfoutput>
This form submits to my 'save' handler. So how do I handle all the product options? My options are recorded in a linking table due to my normalization, this sort of relationship allows multiple options to be assigned to a product. However this makes it very difficult for me because I will have to delete the option from the linking table or add it based on whether it's been ticked.
Save Handler
2 <cffunction name="productSave" access="public" returntype="void" output="false">
3 <cfargument name="Event" type="coldbox.system.beans.requestContext">
4 <cfscript>
5 var rc = event.getCollection();// RC Reference
6 var productBean = variables.storeService.createProductBean(); //Create Product Bean Ready For Population
7 var errors = ';
8
9
10 getPlugin('beanFactory').populateBean(productBean);// Populate Bean From RC Scope
11 errors = productBean.validate(rc);//Check For Validation Errors
12
13 if NOTT ArrayLen(errors)){//No Validation Errors For Product
14
15 if ( variables.storeService.saveProduct(productBean)) {//Update Was OK
16
17
18 if isdefinedd('rc.optiontoupdate')){//if we have any options update them
19 runEvent(event='store.updateOptions',private=true); // update all options
20 }
21
22
23
24 }
25
26 </cfscript>
Above is my 'save' handler , after the product object is populated and validated it creates/updates the product. If this was successful a private function 'updateOptions' is run. This is where I will 'try' and update my options.
The next code is not good, in fact it could be called a performance issue, but it works and well.
2 <cffunction name="updateOptions" access="private" returntype="any" output="false" hint="">
3 <cfargument name="Event" type="coldbox.system.beans.requestContext">
4 <cfscript>
5 var rc = event.getCollection();// RC Reference
6 var optionBean = variables.storeService.createProductOptionsBean(); //Create Bean Ready For Population
7
8 for(i=1;i lte listlen(#rc.optionToUpdate#,",");i++){
9 tempVal = #listgetat(rc.optionToUpdate,i,",")#;
10 rc.valueID = #tempVal#; //Option ID
11 rc.optionPrice = rc["optionPrice_" & #tempVal#]; //Option Price
12 getPlugin('beanFactory').populateBean(optionBean); //Populate Option Bean
13 variables.storeService.saveproductoptions(optionBean);//Save Option
14 }
15 </cfscript>
16 </cffunction>
I loop over each ticked option populate the option bean and update the database.
2 <cffunction name="saveproductoptions" access="public" output="false" returntype="boolean">
3 <cfargument name="bean" type="admin.model.objects.productoptions" required="true" />
4 <cfset result = variables.optionGateway.saveproductoptions(arguments.bean) />
5 <cfreturn result />
6 </cffunction>
In the DAO layer if the option exists its created if not its deleted.
2 <cffunction name="saveproductoptions" access="public" output="false" returntype="boolean">
3 <cfargument name="productoptions" type="admin.model.objects.productoptions" required="true" />
4 <cfset var success = false />
5 <cfif existsproductoptions(arguments.productoptions)>
6 <cfset success = updateproductoptions(arguments.productoptions) />
7 <cfelse>
8 <cfset success = deleteoptions(arguments.productoptions) />
9 </cfif>
10
11 <cfreturn success />
12 </cffunction>
This is my first attempt, I am thinking now maybe creating an array of objects and submit them all to the service layer in one go.




There are no comments for this entry.
[Add Comment] [Subscribe to Comments]