emqx_rule_sqlparser.erl 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103
  1. %%--------------------------------------------------------------------
  2. %% Copyright (c) 2020-2022 EMQ Technologies Co., Ltd. All Rights Reserved.
  3. %%
  4. %% Licensed under the Apache License, Version 2.0 (the "License");
  5. %% you may not use this file except in compliance with the License.
  6. %% You may obtain a copy of the License at
  7. %%
  8. %% http://www.apache.org/licenses/LICENSE-2.0
  9. %%
  10. %% Unless required by applicable law or agreed to in writing, software
  11. %% distributed under the License is distributed on an "AS IS" BASIS,
  12. %% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. %% See the License for the specific language governing permissions and
  14. %% limitations under the License.
  15. %%--------------------------------------------------------------------
  16. -module(emqx_rule_sqlparser).
  17. -include("rule_engine.hrl").
  18. -export([parse/1]).
  19. -export([ select_fields/1
  20. , select_is_foreach/1
  21. , select_doeach/1
  22. , select_incase/1
  23. , select_from/1
  24. , select_where/1
  25. ]).
  26. -import(proplists, [ get_value/2
  27. , get_value/3
  28. ]).
  29. -record(select, {fields, from, where, is_foreach, doeach, incase}).
  30. -opaque(select() :: #select{}).
  31. -type const() :: {const, number()|binary()}.
  32. -type variable() :: binary() | list(binary()).
  33. -type alias() :: binary() | list(binary()).
  34. -type field() :: const() | variable()
  35. | {as, field(), alias()}
  36. | {'fun', atom(), list(field())}.
  37. -export_type([select/0]).
  38. %% Parse one select statement.
  39. -spec(parse(string() | binary()) -> {ok, select()} | {error, term()}).
  40. parse(Sql) ->
  41. try case rulesql:parsetree(Sql) of
  42. {ok, {select, Clauses}} ->
  43. {ok, #select{
  44. is_foreach = false,
  45. fields = get_value(fields, Clauses),
  46. doeach = [],
  47. incase = {},
  48. from = get_value(from, Clauses),
  49. where = get_value(where, Clauses)
  50. }};
  51. {ok, {foreach, Clauses}} ->
  52. {ok, #select{
  53. is_foreach = true,
  54. fields = get_value(fields, Clauses),
  55. doeach = get_value(do, Clauses, []),
  56. incase = get_value(incase, Clauses, {}),
  57. from = get_value(from, Clauses),
  58. where = get_value(where, Clauses)
  59. }};
  60. Error -> {error, Error}
  61. end
  62. catch
  63. _Error:Reason:StackTrace ->
  64. {error, {Reason, StackTrace}}
  65. end.
  66. -spec(select_fields(select()) -> list(field())).
  67. select_fields(#select{fields = Fields}) ->
  68. Fields.
  69. -spec(select_is_foreach(select()) -> boolean()).
  70. select_is_foreach(#select{is_foreach = IsForeach}) ->
  71. IsForeach.
  72. -spec(select_doeach(select()) -> list(field())).
  73. select_doeach(#select{doeach = DoEach}) ->
  74. DoEach.
  75. -spec(select_incase(select()) -> list(field())).
  76. select_incase(#select{incase = InCase}) ->
  77. InCase.
  78. -spec(select_from(select()) -> list(binary())).
  79. select_from(#select{from = From}) ->
  80. From.
  81. -spec(select_where(select()) -> tuple()).
  82. select_where(#select{where = Where}) ->
  83. Where.