我目前正在使用FSharp.Data.SqlClient,但我对任务的任何解决方案感兴趣。
我有一个Web客户端,后端用F#编写。在Web客户端中,用户可以设置10-20个过滤器并向我的F#后端发出GET请求。 URL如下所示:
# work
img_url = 'http://img.mangastream.com/cdn/manga/51/3140/006.png'
img_filename = 'my_img.png'
urllib.request.urlretrieve(img_url, img_filename)
此网址中的任何数字都是过滤条件。如果相应过滤器的值为零,则相应字段上没有过滤器。
现在我需要在后端构建SQL查询。虽然可能的过滤器数量为3-4,但我使用的是模式匹配:
http://mybackend.com/get/1/0/34/ ....
但是当滤波器的数量大于3-4时,很难为所有参数组合编写模式匹配。
我认为我需要动态构建SQL查询。 URL中的每个非零参数都必须将type GetEObyOrg1Org2AsutpParent = SqlCommandProvider<"SELECT * FROM ITEM WHERE ORGID1 = @org1 AND ORGID2 = @org2 AND ASUTPID = @asutp AND PARENTAUTOINCID = @parent", "name=MobileConnectionProvider", ResultType.Tuples>
type GetEObyOrg1Org2Org3AsutpParent = SqlCommandProvider<"SELECT * FROM ITEM WHERE ORGID1 = @org1 AND ORGID2 = @org2 AND ORGID3 = @org3 AND ASUTPID = @asutp AND PARENTAUTOINCID = @parent", "name=MobileConnectionProvider", ResultType.Tuples>
match (asutpid, orgId1, orgId2, orgId3) with
| "0", _, "0", "0" ->
let cmd = new GetEObyOrg1Org2AsutpParent()
cmd.Execute(org1 = orgId1, parent = parentAid)
| "0", _, _ , "0" ->
let cmd = new GetEObyOrg1Org2Org3AsutpParent()
cmd.Execute(org1 = orgId1, org2 = orgId2, parent = parentAid)
表达式添加到SQL语句中。但我不能这样做:
AND Field = Value
type GetEObyOrg1AsutpParent = SqlCommandProvider<Query, "name=MobileConnectionProvider", ResultType.Tuples>
参数是这个表达式必须是文字,而我不能用语法构造文字表达:
Query
在我的案例中,最好的方法是什么?
答案 0 :(得分:1)
我认为在这样的情况下,核心库的SqlDataConnection
类型提供商可能更适合。然后,您应该能够使用标准IQueryable
操作动态添加其他WHERE
子句,例如:
type MyDb = SqlDataConnection<...>
let items = MyDb.GetContext().Item
let q1 = if asutpid = 0 then items else items.Where(fun i -> i.Asutpid = asutpid)
let q2 = if orgId1 = 0 then q1 else q1.Where(fun i -> i.OrgId1 = orgid1)
...