1#include <Functions/FunctionFactory.h>
2#include <Functions/FunctionsStringArray.h>
3
4namespace DB
5{
6
7class ExtractURLParameterNamesImpl
8{
9private:
10 Pos pos;
11 Pos end;
12 bool first;
13
14public:
15 static constexpr auto name = "extractURLParameterNames";
16 static String getName() { return name; }
17
18 static size_t getNumberOfArguments() { return 1; }
19
20 static void checkArguments(const DataTypes & arguments)
21 {
22 if (!isString(arguments[0]))
23 throw Exception("Illegal type " + arguments[0]->getName() + " of first argument of function " + getName() + ". Must be String.",
24 ErrorCodes::ILLEGAL_TYPE_OF_ARGUMENT);
25 }
26
27 /// Returns the position of the argument that is the column of rows
28 size_t getStringsArgumentPosition()
29 {
30 return 0;
31 }
32
33 void init(Block & /*block*/, const ColumnNumbers & /*arguments*/) {}
34
35 /// Called for each next string.
36 void set(Pos pos_, Pos end_)
37 {
38 pos = pos_;
39 end = end_;
40 first = true;
41 }
42
43 /// Get the next token, if any, or return false.
44 bool get(Pos & token_begin, Pos & token_end)
45 {
46 if (pos == nullptr)
47 return false;
48
49 if (first)
50 {
51 first = false;
52 pos = find_first_symbols<'?', '#'>(pos, end);
53 }
54 else
55 pos = find_first_symbols<'&', '#'>(pos, end);
56
57 if (pos + 1 >= end)
58 return false;
59 ++pos;
60
61 while (true)
62 {
63 token_begin = pos;
64
65 pos = find_first_symbols<'=', '&', '#', '?'>(pos, end);
66 if (pos == end)
67 return false;
68 else
69 token_end = pos;
70
71 if (*pos == '?')
72 {
73 ++pos;
74 continue;
75 }
76
77 break;
78 }
79
80 return true;
81 }
82};
83
84struct NameExtractURLParameterNames { static constexpr auto name = "extractURLParameterNames"; };
85using FunctionExtractURLParameterNames = FunctionTokens<ExtractURLParameterNamesImpl>;
86
87void registerFunctionExtractURLParameterNames(FunctionFactory & factory)
88{
89 factory.registerFunction<FunctionExtractURLParameterNames>();
90}
91
92}
93