36 : attachment{&attachment},
37 statusWrapper{attachment.getClient()},
38 calendarConverter{attachment.getClient()},
39 numericConverter{attachment.getClient()}
44 unsigned flags = fb::IStatement::PREPARE_PREFETCH_METADATA;
47 flags |= fb::IStatement::PREPARE_PREFETCH_LEGACY_PLAN;
50 flags |= fb::IStatement::PREPARE_PREFETCH_DETAILED_PLAN;
52 statementHandle.reset(attachment.
getHandle()->prepare(&statusWrapper, transaction.
getHandle().get(),
53 static_cast<unsigned>(sql.length()), sql.data(), options.
getDialect(), flags));
56 statementHandle->setCursorName(&statusWrapper, options.
getCursorName()->c_str());
59 cursorFlags = fb::IStatement::CURSOR_TYPE_SCROLLABLE;
61 type =
static_cast<StatementType>(statementHandle->getType(&statusWrapper));
67 throw FbCppException(
"Cannot use SET TRANSACTION command with Statement class. Use Transaction class");
72 "Cannot use COMMIT command with Statement class. Use the commit method from the Transaction class");
77 "Cannot use ROLLBACK command with Statement class. Use the rollback method from the Transaction class");
81 throw FbCppException(
"Unsupported statement type: BLOB segment operations");
88 std::vector<std::byte>& message)
93 message.resize(metadata->getMessageLength(&statusWrapper));
97 const auto count = metadata->getCount(&statusWrapper);
98 descriptors.reserve(count);
100 for (
unsigned index = 0u; index < count; ++index)
105 .scale = metadata->getScale(&statusWrapper, index),
106 .length = metadata->getLength(&statusWrapper, index),
109 .isNullable =
static_cast<bool>(metadata->isNullable(&statusWrapper, index)),
110 .name = metadata->getField(&statusWrapper, index),
111 .relation = metadata->getRelation(&statusWrapper, index),
112 .alias = metadata->getAlias(&statusWrapper, index),
113 .owner = metadata->getOwner(&statusWrapper, index),
114 .charSetId = metadata->getCharSet(&statusWrapper, index),
115 .subType = metadata->getSubType(&statusWrapper, index),
118 switch (descriptor.originalType)
122 builder.reset(metadata->getBuilder(&statusWrapper));
124 builder->setType(&statusWrapper, index, SQL_VARYING);
130 builder.reset(metadata->getBuilder(&statusWrapper));
132 builder->setType(&statusWrapper, index, SQL_TIME_TZ);
138 builder.reset(metadata->getBuilder(&statusWrapper));
140 builder->setType(&statusWrapper, index, SQL_TIMESTAMP_TZ);
150 descriptor.offset = metadata->getOffset(&statusWrapper, index);
151 descriptor.nullOffset = metadata->getNullOffset(&statusWrapper, index);
153 *
reinterpret_cast<std::int16_t*
>(&message[descriptor.nullOffset]) = FB_TRUE;
156 descriptors.push_back(descriptor);
161 metadata.reset(builder->getMetadata(&statusWrapper));
162 message.resize(metadata->getMessageLength(&statusWrapper));
164 for (
unsigned index = 0u; index < count; ++index)
166 auto& descriptor = descriptors[index];
167 descriptor.offset = metadata->getOffset(&statusWrapper, index);
168 descriptor.nullOffset = metadata->getNullOffset(&statusWrapper, index);
170 *
reinterpret_cast<std::int16_t*
>(&message[descriptor.nullOffset]) = FB_TRUE;
175 inMetadata.reset(statementHandle->getInputMetadata(&statusWrapper));
176 processMetadata(inMetadata, inDescriptors, inMessage);
178 outMetadata.reset(statementHandle->getOutputMetadata(&statusWrapper));
179 processMetadata(outMetadata, outDescriptors, outMessage);
181 outRow = std::make_unique<Row>(attachment.
getClient(), outDescriptors, std::span{outMessage});
185 : attachment{o.attachment},
186 statusWrapper{std::move(o.statusWrapper)},
187 calendarConverter{std::move(o.calendarConverter)},
188 numericConverter{std::move(o.numericConverter)},
189 statementHandle{std::move(o.statementHandle)},
190 resultSetHandle{std::move(o.resultSetHandle)},
191 inMetadata{std::move(o.inMetadata)},
192 inDescriptors{std::move(o.inDescriptors)},
193 inMessage{std::move(o.inMessage)},
194 outMetadata{std::move(o.outMetadata)},
195 outDescriptors{std::move(o.outDescriptors)},
196 outMessage{std::move(o.outMessage)},
197 outRow{std::make_unique<Row>(attachment->getClient(), outDescriptors, std::span{outMessage})},
199 cursorFlags{o.cursorFlags},
200 currentRow{o.currentRow}
203 o.currentRow =
false;
210 attachment = o.attachment;
211 statusWrapper = std::move(o.statusWrapper);
212 calendarConverter = std::move(o.calendarConverter);
213 numericConverter = std::move(o.numericConverter);
214 statementHandle = std::move(o.statementHandle);
215 resultSetHandle = std::move(o.resultSetHandle);
216 inMetadata = std::move(o.inMetadata);
217 inDescriptors = std::move(o.inDescriptors);
218 inMessage = std::move(o.inMessage);
219 outMetadata = std::move(o.outMetadata);
220 outDescriptors = std::move(o.outDescriptors);
221 outMessage = std::move(o.outMessage);
222 outRow = std::make_unique<Row>(attachment->getClient(), outDescriptors, std::span{outMessage});
224 cursorFlags = o.cursorFlags;
225 currentRow = o.currentRow;
228 o.currentRow =
false;
270 resultSetHandle->close(&statusWrapper);
271 resultSetHandle.reset();
276 const auto outMessageData = outMessage.data();
280 for (
const auto& descriptor : outDescriptors)
281 *
reinterpret_cast<std::int16_t*
>(&outMessageData[descriptor.nullOffset]) = FB_TRUE;
288 resultSetHandle.reset(statementHandle->openCursor(&statusWrapper, transaction.
getHandle().get(),
289 inMetadata.get(), inMessage.data(), outMetadata.get(), cursorFlags));
290 currentRow = resultSetHandle->fetchNext(&statusWrapper, outMessageData) == fb::IStatus::RESULT_OK;
294 statementHandle->execute(&statusWrapper, transaction.
getHandle().get(), inMetadata.get(), inMessage.data(),
295 outMetadata.get(), outMessageData);
296 currentRow = !outDescriptors.empty();