1 /*
2 * Copyright (c) 2022 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15 #ifdef RELATIONAL_STORE
16 #include "prepared_stmt.h"
17 #include "db_constant.h"
18
19 namespace DistributedDB {
PreparedStmt(ExecutorOperation opCode,const std::string & sql,const std::vector<std::string> & bindArgs)20 PreparedStmt::PreparedStmt(ExecutorOperation opCode, const std::string &sql, const std::vector<std::string> &bindArgs)
21 : opCode_(opCode), sql_(sql), bindArgs_(bindArgs) {}
22
23
SetOpCode(ExecutorOperation opCode)24 void PreparedStmt::SetOpCode(ExecutorOperation opCode)
25 {
26 opCode_ = opCode;
27 }
28
SetSql(std::string sql)29 void PreparedStmt::SetSql(std::string sql)
30 {
31 sql_ = std::move(sql);
32 }
33
SetBindArgs(std::vector<std::string> bindArgs)34 void PreparedStmt::SetBindArgs(std::vector<std::string> bindArgs)
35 {
36 bindArgs_ = std::move(bindArgs);
37 }
38
GetOpCode() const39 PreparedStmt::ExecutorOperation PreparedStmt::GetOpCode() const
40 {
41 return opCode_;
42 }
43
GetSql() const44 const std::string &PreparedStmt::GetSql() const
45 {
46 return sql_;
47 }
48
GetBindArgs() const49 const std::vector<std::string> &PreparedStmt::GetBindArgs() const
50 {
51 return bindArgs_;
52 }
53
IsValid() const54 bool PreparedStmt::IsValid() const
55 {
56 return opCode_ == ExecutorOperation::QUERY && !sql_.empty() && bindArgs_.size() <= DBConstant::MAX_SQL_ARGS_COUNT;
57 }
58
CalcLength() const59 uint32_t PreparedStmt::CalcLength() const
60 {
61 uint32_t length = Parcel::GetIntLen() + // current version
62 Parcel::GetIntLen() + // opcode_
63 Parcel::GetStringLen(sql_) + // sql_
64 Parcel::GetIntLen(); // bindArgs_.size()
65 for (const auto &bindArg : bindArgs_) {
66 length += Parcel::GetStringLen(bindArg); // bindArgs_
67 }
68 return Parcel::GetEightByteAlign(length);
69 }
70
71 // Before call this func. You should check if the object is valid.
Serialize(Parcel & parcel) const72 int PreparedStmt::Serialize(Parcel &parcel) const
73 {
74 // version
75 (void)parcel.WriteInt(CURRENT_VERSION);
76
77 // opcode
78 (void)parcel.WriteInt(static_cast<int>(opCode_));
79
80 // string
81 (void)parcel.WriteString(sql_);
82
83 // bindArgs
84 (void)parcel.WriteInt(static_cast<int>(bindArgs_.size()));
85 for (const auto &bindArg : bindArgs_) {
86 (void)parcel.WriteString(bindArg);
87 if (parcel.IsError()) {
88 return -E_PARSE_FAIL;
89 }
90 }
91
92 (void)parcel.EightByteAlign();
93 if (parcel.IsError()) {
94 return -E_PARSE_FAIL;
95 }
96 return E_OK;
97 }
98
DeSerialize(Parcel & parcel)99 int PreparedStmt::DeSerialize(Parcel &parcel)
100 {
101 // clear the object
102 bindArgs_.clear();
103
104 // version
105 int version = 0;
106 (void)parcel.ReadInt(version);
107 if (parcel.IsError() || version <= 0 || version > CURRENT_VERSION) {
108 return -E_PARSE_FAIL;
109 }
110
111 // VERSION 1
112 if (version >= VERSION_1) {
113 // opcode
114 int opCode = 0;
115 (void)parcel.ReadInt(opCode);
116 if (parcel.IsError() || opCode <= MIN_LIMIT || opCode >= MAX_LIMIT) {
117 return -E_PARSE_FAIL;
118 }
119 opCode_ = static_cast<ExecutorOperation>(opCode);
120
121 // sql
122 (void)parcel.ReadString(sql_);
123
124 // bindArgs
125 int argsCount = 0;
126 (void)parcel.ReadInt(argsCount);
127 if (parcel.IsError() || argsCount < 0 || argsCount > static_cast<int>(DBConstant::MAX_SQL_ARGS_COUNT)) {
128 return -E_PARSE_FAIL;
129 }
130 for (int i = 0; i < argsCount; ++i) {
131 std::string bindArg;
132 (void)parcel.ReadString(bindArg);
133 if (parcel.IsError()) {
134 return -E_PARSE_FAIL;
135 }
136 bindArgs_.emplace_back(std::move(bindArg));
137 }
138 }
139
140 (void)parcel.EightByteAlign();
141 return E_OK;
142 }
143 }
144 #endif