`
fly_bluewolf
  • 浏览: 6253 次
  • 来自: ...
最近访客 更多访客>>
文章分类
社区版块
存档分类
最新评论

对于Agile Web Development with Rails, 2nd 中cart的疑惑

阅读更多
最近在看Agile Web Development with Rails第二版,同时在研究rails 2.1。在网上下载了Agile Web Development with Rails第三版的源码,发现第三版对于product全部采用了REST的方式实现了,但是对于cart的实现同第二版没有任何变化,还是放在StoreController中。
class ProductsController < ApplicationController
  # GET /products
  # GET /products.xml
  def index
    @products = Product.find(:all)

    respond_to do |format|
      format.html # index.html.erb
      format.xml  { render :xml => @products }
    end
  end

  # GET /products/1
  # GET /products/1.xml
  def show
    @product = Product.find(params[:id])

    respond_to do |format|
      format.html # show.html.erb
      format.xml  { render :xml => @product }
    end
  end

  # GET /products/new
  # GET /products/new.xml
  def new
    @product = Product.new

    respond_to do |format|
      format.html # new.html.erb
      format.xml  { render :xml => @product }
    end
  end

  # GET /products/1/edit
  def edit
    @product = Product.find(params[:id])
  end

  # POST /products
  # POST /products.xml
  def create
    @product = Product.new(params[:product])

    respond_to do |format|
      if @product.save
        flash[:notice] = 'Product was successfully created.'
        format.html { redirect_to(@product) }
        format.xml  { render :xml => @product, :status => :created, :location => @product }
      else
        format.html { render :action => "new" }
        format.xml  { render :xml => @product.errors, :status => :unprocessable_entity }
      end
    end
  end

  # PUT /products/1
  # PUT /products/1.xml
  def update
    @product = Product.find(params[:id])

    respond_to do |format|
      if @product.update_attributes(params[:product])
        flash[:notice] = 'Product was successfully updated.'
        format.html { redirect_to(@product) }
        format.xml  { head :ok }
      else
        format.html { render :action => "edit" }
        format.xml  { render :xml => @product.errors, :status => :unprocessable_entity }
      end
    end
  end

  # DELETE /products/1
  # DELETE /products/1.xml
  def destroy
    @product = Product.find(params[:id])
    @product.destroy

    respond_to do |format|
      format.html { redirect_to(products_url) }
      format.xml  { head :ok }
    end
  end
end

class StoreController < ApplicationController  
  def add_to_cart
    begin
      product = Product.find(params[:id])
    rescue ActiveRecord::RecordNotFound
      logger.error("Attempt to access invalid product #{params[:id]}")
      redirect_to_index("Invalid product")
    else
      @cart = find_cart
      @current_item = @cart.add_product(product)
      if request.xhr?
        respond_to { |format| format.js }
      else
        redirect_to_index
      end
    end
  end
end

个人觉得/store/add_to_cart/1似乎很不REST,感觉cart应该有个单独的CartController,这样才比较REST。
不知道是否是由于第3版的代码没有完成的而造成的。
分享到:
评论
7 楼 fly_bluewolf 2008-06-22  
庄表伟 写道
我的理解是:

Controller应该分为两类:
一类是面向资源的,也就是CRUD的简单封装。
一类是面向Web请求的,自然会千奇百怪。

REST化的Controller,在做Web Service的时候,显得很自然,在做Web Page的时候,就总会有些格格不入的地方。

也许,这两类Controller,应该用在不同的层次上。

做个类比,cart就类似我们在supermarket中的手推车,用户在bookstore中浏览,就类似我们在超市中购物,用户挑选好一件东西,就放入到手推车中。在现实中,超市也不会把用户使用的手推车(cart)记录到微机系统中,也就说并不会持久化这些信息,这个跟我们在storebook看到cart的实现一致。但对用户这个角度来说,却可以认为cart也是一种资源,我们可以向手推车中进行CRUD操作吧(增加一件商品或拿出一件商品)。
如果把controller分成两种,一种是简单的REST化的controller,做CRUD的简单封装。我认为REST在企业级应用中就失去了它的意义,企业级应用不会只是简单的CRUD应用吧。
6 楼 neodoxy 2008-06-22  
庄表伟 写道
我的理解是:

Controller应该分为两类:
一类是面向资源的,也就是CRUD的简单封装。
一类是面向Web请求的,自然会千奇百怪。

REST化的Controller,在做Web Service的时候,显得很自然,在做Web Page的时候,就总会有些格格不入的地方。

也许,这两类Controller,应该用在不同的层次上。

就这个问题而言,还是可行的
因为在这个例子里cart没有被实现成一个ActiveRecord对象,也不是一种资源,当然可以用面向资源的方式实现,但对于AWD这本入门级的书籍的入门篇章来说,似乎复杂性太高了,这或许是Dave采用REST-RPC风格的一个原因吧
5 楼 庄表伟 2008-06-21  
我的理解是:

Controller应该分为两类:
一类是面向资源的,也就是CRUD的简单封装。
一类是面向Web请求的,自然会千奇百怪。

REST化的Controller,在做Web Service的时候,显得很自然,在做Web Page的时候,就总会有些格格不入的地方。

也许,这两类Controller,应该用在不同的层次上。
4 楼 fly_bluewolf 2008-06-21  
neodoxy 写道
让整个Rails社区向REST转变不是单靠激进就能解决的
那其实并不能简单地诠释为激进,而是一种决断力,敢于和主流背道而驰也是需要极大的勇气的

所以我认为他不应该还会在这部书里使用REST-RPC的方式
3 楼 neodoxy 2008-06-20  
让整个Rails社区向REST转变不是单靠激进就能解决的
那其实并不能简单地诠释为激进,而是一种决断力,敢于和主流背道而驰也是需要极大的勇气的
2 楼 fly_bluewolf 2008-06-20  
neodoxy 写道
这是最常见的REST-RPC方法
也就是REST和RPC混合的架构
按照REST的标准,语义完全体现在URL上,动作全部基于CRUD,这对于习惯了RPC模式的程序员来说瞬间的转变太难了,所以Rails2.0提供了对于RPC式的REST的支持,也允许这样做

你说的没错,可是在我印象中DHH可是非常激进的,ROR是坚决站在REST一方的,所以说这部书里应该不会出现这种REST-RPC的方式吧?
1 楼 neodoxy 2008-06-20  
这是最常见的REST-RPC方法
也就是REST和RPC混合的架构
按照REST的标准,语义完全体现在URL上,动作全部基于CRUD,这对于习惯了RPC模式的程序员来说瞬间的转变太难了,所以Rails2.0提供了对于RPC式的REST的支持,也允许这样做

相关推荐

Global site tag (gtag.js) - Google Analytics