上篇笔记中,我们为保存用户选购的商品提供了场所。那么,这篇我们就要开始制造我们的购物车了。
首先,我们要为购物车定义一个类,这个类现在只做很简单的事情,就是保存用户选择的商品。我们管这个类叫“Cart”,我们将它保存在depot/app/models/cart.rb文件中。详细代码如下:
class Cart
attr_reader :items
def initialize
@items = []
end
def add_product(product)
@items << product
end
end
好了,我们的购物车就做好了。
(广告词:亲爱的顾客朋友们,你们好!欢迎你们的光临!我们已经为你们每一位准备了一台空间充足的购物车。请放心,不论你选购多少商品,我们的购物车都能装下,并保管好您所选购的商品。祝您购物愉快!)
哈哈,广告词不错吧?不过不能光说不练,接下来,我们要为每一位来我们这里购物的顾客准备一辆购物车。
我们知道,每位顾客访问我们的depot都会产生一个Session,并且我们上一篇笔记也准备好了在里面存储东西了。那么,我们就在需要的时候为每个Session创建一个购物车的实例吧。
打开depot/app/controllers/store_controller.rb文件,在里面添加如下代码:
def find_cart
session[:cart] ||= Cart.new
end
从上面的代码可以看出,其实我们并不是每位顾客一出现就给他/她一辆购物车的(顾客说了:“我只是来转转看看的,你们给我这么台车子,推着多麻烦阿!我又不给里面放东西!“)。而是在顾客看到某样商品,触动了他/她购物的欲望,想买下这件产品的时候,及时准确的让他/她的手边出现一辆购物车。怎么样?我们的服务不错把?(要是我们在逛超市的时候也能有这样的待遇该多好阿!)
在之前的笔记中,我们已经为我们页面上的每个产品添加了一个“Add to Cart“的按钮。那么我们希望用户在点击了这个按钮之后,按钮所对应的产品就被添加到了我们的购物车中。那么,这里就有两个问题:
1、我们怎么知道用户点击了产品的“Add to Cart“按钮?
2、我们知道了用户点击了“Add to Cart“的按钮,我们又怎么知道用户点击了哪个产品的按钮?
为了解决这两个问题,我们需要修改depot/app/views/store/index.html.erb这个文件中的第10行。
修改之前的代码:
<%= button_to "Add to Cart"%>
修改之后的代码:
<%= button_to "Add to Cart", :action => 'add_to_cart', :id => product %>
从上面的代码我们可以看到,我们把一个add_to_cart方法绑定给了按钮的点击动作,同时,在生成按钮的时候,把该按钮对应的产品ID绑定给了该按钮的id属性。这样,当用户点击这个按钮的时候,产品的id会作为Form的参数传递回来,我们通过在add_to_cart方法中取出这个参数值,就可以知道用户选购了那件产品了(因为在之前我们设计数据库时,那个id字段是自动累加的,也就确保了每样产品都有一个唯一的id与之对应)。
现在,我们该去实现我们的add_to_cart方法了。我们可以在depot/app/controllers/store_controller.rb中实现这个方法。详细代码如下:
def add_to_cart
product = Product.find(params[:id])
@cart = find_cart
@cart.add_product(product)
end
注意了,上面那个“params”对象在Rails中可是很重要的一个角色哦!它里面保存这所有从用户也民传回来的参数。我们和顾客的沟通可是就靠它了。这个对象中的所有参数都是以键值对的形式保存的,用起来还是很方便的。
上面做了这些,是不是就可以尝试一下我们购物按钮的效果了?不行,现在还不行。因为Rails需要为每一个页面调用的方法提供一个View。也就是说,我们的按钮调用了add_to_cart方法,我们要为这个方法创建了一个View。好,那我们就在depot/app/views/store目录下创建一个叫add_to_cart.html.erb的文件。文件中的代码如下:
<h2>Your Pragmatic Cart</h2>
<ul>
<% for item in @cart.items %>
<li><%=h item.title %></li>
<% end %>
</ul>
这段代码其实会在add_to_cart方法把产品放进用户的购物车终止后,给用户列一张用户选购了的商品清单。
好了,现在开启服务,打开浏览器访问store页面,点一下你的选购按钮试试看吧!怎么样,是不是还不赖?