1

我在 Persistent 中定义了一对多关系,但无法弄清楚如何创建一个可以将一个外键作为输入的表单。将我的用例简化为:

Person
  name String

Car
  personId PersonId 
  name Text
  type Text

现在,当我尝试为 Car 生成表单时,personId 的字段类型应该是什么?我尝试过这样的事情,但得到一个错误:

entryForm :: Maybe Car -> Form Car
entryForm car = renderDivs $ Car
    <$> areq   personIdField   "Person" Nothing
    <*> areq   textField   "Car Name" ( carName <$> car)
    <*> areq   textField  "Type" ( carType <$> car)

当我运行上面我得到错误: Not in scope: `personIdField'.

我试过intField了,它说:

Couldn't match expected type `KeyBackend
                                persistent-1.2.1:Database.Persist.Sql.Types.SqlBackend Person'
            with actual type `Text'
Expected type: Field
                 m0
                 (KeyBackend
                    persistent-1.2.1:Database.Persist.Sql.Types.SqlBackend Person)
  Actual type: Field m0 Text
In the first argument of `areq', namely `intField'
In the second argument of `(<$>)', namely
  `areq intField "Person" Nothing

理想情况下,我想填充人名的下拉列表(如果没有太多),或者当人名太多时有一个自由格式的文本字段(例如,自动完成)。关于如何将外键作为用户输入的任何建议?

更新

我尝试如下使用 selectField 但不确定我是否正确执行此操作。我仍然收到错误消息。首先,我创建了一个 where 语句来获取 personId:

 where
   personId = do  
       person <- runDB $ selectFirst [] [Asc PersonName] 
       case person of
           Just (Entity pId p) -> return pId
           -- Nothing             -> ???

然后我将我的第一个 areq 更改为

 <$> areq (selectField [("First", personId)]) "Person Name" Nothing

谢谢!

4

1 回答 1

3

我能够弄清楚如何正确使用 selectField。这就是我最终做的事情:

where
    people = do
        entities <- runDB $ selectList [] [Asc PersonName]
        optionsPairs $ map (\p -> (personName $ entityVal p, entityKey p)) entities

表单字段变为:

<$> areq   (selectField people) "Person Name" Nothing

我还没有想出自由形式的条目,但这是一个好的开始。

于 2013-07-23T06:29:14.620 回答