2012-11-07 48 views
8

Tôi là người mới sử dụng Haskell.Trả lại trạng thái lỗi trong Haskell và Yesod

Tôi đang cố viết một máy chủ Webdav nhỏ bằng cách sử dụng Yesod Framework và được mô hình hóa sau mã WebdavServlet trong mã nguồn Apache Tomcat 7. Tôi đã gặp sự cố khi trả lại lỗi từ một trong các chức năng của tôi.

Dịch vụ webdav của tôi phải trả về XML hoặc JSON, tùy thuộc vào giá trị của tiêu đề Accept được người gọi gửi. Tôi định nghĩa một kiểu dữ liệu được gọi là RepXmlJson:

import Yesod 

data RepXmlJson = RepXmlJson RepXml RepJson 

instance HasReps RepXmlJson where 
    chooseRep (RepXmlJson (RepXml xml) (RepJson json)) = chooseRep 
    [ (typeXml, xml) 
    , (typeJson, json) 
    ] 

Tôi đang sử dụng kiểu dữ liệu này như là giá trị trả về các dịch vụ của mình, đặc biệt là lockWebdavR chức năng. Tôi đang cố trả lại trạng thái 423 (bị khóa) nếu tài nguyên hiện bị khóa. Mã của tôi trông như thế này:

import qualified Data.ByteString as B 
import qualified Data.Map  as M 
import qualified Data.Text  as T 
import qualified Network.Wai  as W 

mkYesodSub "Webdav" [] [parseRoutes| 
/WebdavR COPY DELETE LOCK MKCOL MOVE OPTIONS PROPFIND PROPPATCH PUT UNLOCK 
|] 

type WebdavHandler yesod = GHandler Webdav yesod 

webdavLocked423 :: Status 
webdavLocked423 = Status 423 "Locked" 

isLockedRequest :: Yesod master => Request -> WebdavHandler master Bool 
-- isLockedRequest definition omitted for brevity 

lockWebdavR :: Yesod master => WebdavHandler master RepXmlJson 
lockWebdavR = do 
    request <- getRequest 
    locked <- isLockedRequest request 
    if locked 
    then return $ 
     W.responseLBS webdavLocked423 [("Content-Type", "text/plain")] "" 
    else return undefined 

Tôi nhận được lỗi sau:

Webdav.hs:94:10: 
    Couldn't match expected type `RepXmlJson' 
       with actual type `W.Response' 
    Expected type: GHandler Webdav master RepXmlJson 
     Actual type: GHandler Webdav master W.Response 
    In the expression: 
     return 
     $ W.responseLBS webdavLocked423 [("Content-Type", "text/plain")] "" 
    In a stmt of a 'do' block: 
     if locked then 
      return 
      $ W.responseLBS webdavLocked423 [("Content-Type", "text/plain")] "" 
     else 
      return undefined 

Tôi đã tìm kiếm thông qua các cuốn sách "Developing Web Applications with Haskell and Yesod", nhưng không thể tìm thấy một ví dụ về trả lại một lỗi của các loại thích hợp (Rep...) .

Làm cách nào để tạo một RepXmlJson với trạng thái lỗi chính xác?

Trả lời

5

Việc hoàn tất thủ tục thông thường luôn dẫn đến mã trạng thái 200. Để ghi đè điều đó, bạn phải gửi phản hồi theo cách khác. Trong trường hợp của bạn, bạn có thể thử sendResponseStatus. Các khả năng khác sẽ là sendWaiResponseredirectWith, mặc dù tôi nghi ngờ điều sau sẽ hữu ích.

+0

Tôi đã thay đổi giá trị trả lại thành 'sendResponseStatus webdavLocked423 $ RepXmlJson (RepXml" ") (RepJson" ")' và nó biên dịch. Cảm ơn. BTW, cuốn sách hay. – Ralph

+0

Tôi sử dụng 'invalidArgs [" Không thể phân tích cú pháp refs "]' để trả lời với lỗi 400. Nhưng không hiểu điều gì xảy ra với thông điệp của tôi ... – cies

Các vấn đề liên quan