1

我正在尝试开发一个 URL 调度程序来根据 URL 执行不同的操作。例如:

至于现在,我得到了以下有效的代码:

dispatch(uri) =
match uri with
  | {path= [edit] query=[("id", parameter)] ...} -> Customer.edit(parameter)
  | {path= [delete] query=[("sid", parameter)] ...} -> Customer.delete(parameter)
  | {~path ...} -> start()

server = Server.simple_dispatch(dispatch)

然而,在我的第一次尝试中,我有:

  | {path= [edit] query=["id", parameter] ...} -> Customer.edit(parameter)
  | {path= [delete] query=[("id", parameter)] ...} -> Customer.delete(parameter)

但是编译器会因为两行中都有“id”而引发错误,显然第一行是“覆盖”第二行。我的问题是:

  • 如何为两行保持相同的参数名称“id”而不会出错?
  • 可以处理多少个不同类型的参数?例如 localhost:8080/edit?id=2&ask=true&showImage=0
  • 模式“...”是干什么用的?

提前致谢

4

1 回答 1

1

我不认为你展示的代码真的有效:)。例如尝试:

/delete?id="xxx"
/edit?sid="xxx"

你会看到发送了错误的资源。问题是您放了引号edit并且delete没有引号,因此它们被视为模式变量并且将匹配任何内容(并绑定到匹配的值)。这正是您的第一个变体不起作用的原因——这两种模式在变量重命名(编辑/删除)之前都是相同的。你想要的(我认为)是:

dispatch =
| {path = ["edit"] query=[("id", parameter)] ...} -> Customer.edit(parameter)
| {path = ["delete"] query=[("id", parameter)] ...} -> Customer.delete(parameter)
| {~path ...} -> start()

如何拥有多个参数?

只需将您的模式匹配(第一行)扩展到:

| {path = ["edit"] query=[("id", id), ("ask", ask), ("showImage", showImage)] ...} -> Customer.edit(id, ask, showImage)

但是这种匹配是危险的,因为它只有在恰好有这些查询参数并且完全按照这个顺序时才会起作用。如果您不能确定,最好这样做:

| {path = ["edit"] ~query ...} ->
    id = List.assoc("id", query) ? ""
    ask = List.assoc("ask", query) ? ""
   showImage = List.assoc("showImage", query) ? ""
    Customer.edit(id, ask, showImage)

现在顺序无关紧要,如果参数丢失,?将使用默认值(之后)。

模式“...”是干什么用的?

您正在匹配一个uri类型为: 的变量,该变量的Uri.relative字段不仅仅是pathquery...意味着记录中可能有更多字段,但我们不关心它们(没有点,记录应该只有明确提到的字段)。

于 2011-12-01T11:19:26.520 回答