I'm not sure you've got this whole shopping cart thing clear.

I've put together a quick example of how I'd go about it.

Save the two files below as shoppingcart.cfc and callingpage.cfm in the same directory.

Watch out for line wrapping problems.

Spike

shoppingcart.cfc

************************************************************

<cfcomponent displayname="shoppingCart">

<cfset init()>

<cffunction name="init" access="public" output="false" returntype="boolean" hint="Initializes the cart if it has not been initialized yet">
<cfif not isDefined('instance')>
<cfset instance = structNew()>
<cfset instance.aItems = arrayNew(1)>
<cfset instance.timestamp = Now()>
<cfset instance.IDs = "">
</cfif>
<cfreturn true>
</cffunction>


<cffunction name="addItem" access="public" output="false" returntype="boolean" hint="Adds an item to the cart. A cart item is a structure with any number of keys. The only required key is 'ID' which must be uniqe for every item in the cart.">
<cfargument name="item" type="struct" required="yes">
<!--- Make sure the item has an id and that the id is unique --->
<cfif not structKeyExists(arguments.item,'id')>
<cfthrow type="shoppingCart.invalidItem" message="The item does not have an id key" detail="All items added to the shopping cart must have a unique ID key to ensure that duplicate items cannot be created and multiple items are not deleted if the user refreshes the page.">
</cfif>
<cfif listFind(instance.IDs,arguments.item.id)>
<cfthrow type="shoppingCart.invalidItem" message="The item does not have a unique id key" detail="All items added to the shopping cart must have a unique ID key to ensure that duplicate items cannot be created and multiple items are not deleted if the user refreshes the page.">
</cfif>


<cfset instance.IDs = listAppend(instance.IDs,arguments.item.id)>

<cfreturn arrayAppend(instance.aItems,duplicate(arguments.item))>

</cffunction>

<cffunction name="removeItem" access="public" output="false" returntype="boolean" hint="Removes an item from the cart based on the ID passed in.">
<cfargument name="id" type="string" required="yes">
<cfset var index = "">
<!--- Make sure the item has an id and that the id is unique --->
<cfif NOT listFind(instance.IDs,arguments.id)>
<cfthrow type="shoppingCart.invalidItemID" message="The item you tried to delete does not exist" detail="The item id passed to the removeItem() method does not correspond to any items in the cart.">
</cfif>


<cfset index = listFind(instance.IDs,arguments.id)>

<cfreturn arrayDeleteAt(instance.aItems,index)>

</cffunction>

<cffunction name="getCartItems" access="public" output="false" returntype="array" hint="Returns an array of items in the order they were added to the cart">
<cfreturn instance.aItems>
</cffunction>


<cffunction name="getTimeStamp" access="public" output="false" returntype="date" hint="Returns the timestamp when the cart was created">
<cfreturn instance.timestamp>
</cffunction>


<cffunction name="clearCart" access="public" output="false" returntype="boolean" hint="Clears the cart removing all items">
<cfset instance.aItems = arrayNew(1)>
<cfreturn true>
</cffunction>


</cfcomponent>

*****************************************************************


callingpage.cfm ***************************************************************** <cfapplication name="cartexample" sessionmanagement="yes">


<cfset session.cart = createObject('component','shoppingcart')>



<cfdump var="#session.cart.getCartItems()#" label="After Initialization">


<cfset firstID = createUUID()>
<cfset myItem = structNew()>
<cfset myItem.priceperunit = 120>
<cfset myItem.name = "Some useful thing">
<cfset myItem.quantity = 2>
<cfset myItem.id = firstID>

<cfset session.cart.addItem(myItem)>

<cfdump var="#session.cart.getCartItems()#" label="After adding first item">

<cfset secondID = createUUID()>
<cfset myItem = structNew()>
<cfset myItem.priceperunit = 30>
<cfset myItem.name = "Another useful thing">
<cfset myItem.quantity = 1>
<cfset myItem.id = secondID>

<cfset session.cart.addItem(myItem)>

<cfdump var="#session.cart.getCartItems()#" label="After adding second item">

<cfset thirdID = createUUID()>
<cfset myItem = structNew()>
<cfset myItem.priceperunit = 10>
<cfset myItem.name = "A third useful thing">
<cfset myItem.quantity = 25>
<cfset myItem.id = thirdID>

<cfset session.cart.addItem(myItem)>

<cfdump var="#session.cart.getCartItems()#" label="After adding third item">

<cfset session.cart.removeItem(secondID)>

<cfdump var="#session.cart.getCartItems()#" label="After removing second item">

<cfset session.cart.clearCart(secondID)>

<cfdump var="#session.cart.getCartItems()#" label="After clearing cart">
******************************************************************

Beattie, Barry wrote:

thanx again Mark. It's leading to a couple of more questions, I'm afraid...



Neither - you aren't calling the method on a CFC. You are trying to call

it on a struct.


you've confused me now. The only thing I've done different from usual is not
used an argument in invoking the component and the CFC not having
properties. Perhaps I'm getting confused with CFC interfaces seemimg to be
like structs themselves, not like real objects eg: COM (actually, they feel
more like VBScript classes than objects).



        <cfproperty name="aProducts" type="array">
        
        <!--- contructor --->     
        <cfscript>
                //place to store my carts
                this.aProducts = ArrayNew(1);
        </cfscript>


Ummm... why the array? is this for an array of structures or a struct of
arrays?




<!--- application.cfm --->

<cfif NOT isDefined("session.cart")>
<cfscript>
        session.cart = CreateObject(type, "com.Cart");
</cfscript>
</cfif>


- Hence all data is stored in the CFC - and is specific TO the CFC, and

nothing else (which gives lower coupling).


so the instance is stored in the session? How does session.cart get updated
with new cart contents within the CFC? and what would you do if cookies or a
db have to be used instead? you've made a good point about the loose
coupling but it's satisfying the other side (tight cohesion) that worries me
on this bit.

thanx
barry.b


-----Original Message----- From: Mark M [mailto:[EMAIL PROTECTED] Sent: Monday, 29 September 2003 12:18 PM To: CFAussie Mailing List Subject: [cfaussie] Re: CFC error: "Method selection Exception" (was: Shopping carts: Arr ays Vs Structs)



1) so I'm calling the method wrong? or not invoking the component
correctly?


Neither - you aren't calling the method on a CFC. You are trying to call it
on a struct. Hence the error. Dump out the 'objCart' variable, and I think you
will find what I mean.



2) >> A shopping cart should only manage the shopping cart.  It
shouldn't
look at if it exists or not.

yes good point but I was trying to tie the storage of cart data
totally into
the CFC. IMHO only the CFC should care how the cart data is stored
and not
be dependant on other files. The CFC becomes the data store
interface. If
the chosen storage doesn't exist, create it.


That is fine - however I would have built it like this:


<!--- component cart --->
<cfcomponent displayname="Cart">

<cfproperty name="aProducts" type="array">

<!--- contructor --->
<cfscript>
//place to store my carts
this.aProducts = ArrayNew(1);
</cfscript>

<cffunction name="AddToCart" access="public" output="false">
<cfargument name="key" required="true" type="numeric">
<cfargument name="value" required="true" type="numeric">
<!--- add the item --->
<cfscript>
StructInsert(this.aProducts, arguments.key, arguments.value);
</cfscript>
</cffunction>

</cfcomponent>



<!--- application.cfm --->


<cfif NOT isDefined("session.cart")>
<cfscript>
        session.cart = CreateObject(type, "com.Cart");
</cfscript>
</cfif>

- Hence all data is stored in the CFC - and is specific TO the CFC, and
nothing else (which gives lower coupling).


HTH

Mark

---
You are currently subscribed to cfaussie as: [EMAIL PROTECTED]
To unsubscribe send a blank email to [EMAIL PROTECTED]

MX Downunder AsiaPac DevCon - http://mxdu.com/





--- You are currently subscribed to cfaussie as: [EMAIL PROTECTED] To unsubscribe send a blank email to [EMAIL PROTECTED]

MX Downunder AsiaPac DevCon - http://mxdu.com/

Reply via email to