fix dblink transaction bug
This commit is contained in:
@ -197,18 +197,21 @@ int ObDelUpdLogPlan::generate_dblink_raw_plan()
|
||||
LOG_WARN("failed to allocate link dml as top", K(ret));
|
||||
} else if (OB_FAIL(make_candidate_plans(top))) {
|
||||
LOG_WARN("failed to make candidate plans", K(ret));
|
||||
} else if (OB_FAIL(static_cast<ObLogLink *>(top)->set_link_stmt())) {
|
||||
LOG_WARN("failed to set link stmt", K(ret));
|
||||
} else {
|
||||
set_plan_root(top);
|
||||
bool has_reverse_link = false;
|
||||
if (OB_FAIL(ObDblinkUtils::has_reverse_link_or_any_dblink(stmt, has_reverse_link))) {
|
||||
LOG_WARN("failed to exec has_reverse_link", K(ret));
|
||||
} else if (OB_FAIL(ObDblinkUtils::gather_dblink_id(stmt, static_cast<ObLogLinkDml *>(top)->get_related_dblink_ids()))) {
|
||||
LOG_WARN("failed to exec gather_dblink_id", K(ret));
|
||||
} else {
|
||||
uint64_t dblink_id = stmt->get_dblink_id();
|
||||
top->set_dblink_id(dblink_id);
|
||||
static_cast<ObLogLinkDml *>(top)->set_reverse_link(has_reverse_link);
|
||||
static_cast<ObLogLinkDml *>(top)->set_dml_type(stmt->get_stmt_type());
|
||||
if (OB_FAIL(static_cast<ObLogLink *>(top)->set_link_stmt())) {
|
||||
LOG_WARN("failed to set link stmt", K(ret));
|
||||
}
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
|
||||
@ -210,39 +210,22 @@ int ObLogLink::set_link_stmt(const ObDMLStmt* stmt)
|
||||
print_param.for_dblink_ = 1;
|
||||
// only link scan need print flashback query for dblink table
|
||||
ObOptimizerContext *opt_ctx = NULL;
|
||||
ObQueryCtx *query_ctx = NULL;
|
||||
ObSQLSessionInfo *session = NULL;
|
||||
int64_t session_query_timeout_us = 0;
|
||||
int64_t hint_query_timeout_us = 0;
|
||||
if (OB_ISNULL(stmt) || OB_ISNULL(plan) ||
|
||||
OB_ISNULL(opt_ctx = &get_plan()->get_optimizer_context()) ||
|
||||
OB_ISNULL(session = opt_ctx->get_session_info()) ||
|
||||
OB_ISNULL(print_param.exec_ctx_ = opt_ctx->get_exec_ctx())) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("get unexpected null", KP(opt_ctx), KP(stmt), KP(session), KP(plan), K(ret));
|
||||
} else if (NULL == (query_ctx = stmt->get_query_ctx())) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("get unexpected null", K(ret));
|
||||
} else if (FALSE_IT(hint_query_timeout_us = query_ctx->get_query_hint_for_update().get_global_hint().query_timeout_)) {
|
||||
} else if (OB_FAIL(session->get_query_timeout(session_query_timeout_us))) {
|
||||
LOG_WARN("failed to get session query timeout", K(ret));
|
||||
} else if (-1 == hint_query_timeout_us &&
|
||||
FALSE_IT(query_ctx->get_query_hint_for_update().get_global_hint().merge_query_timeout_hint(session_query_timeout_us))) {
|
||||
// do nothing
|
||||
} else if (FALSE_IT(query_ctx->get_query_hint_for_update().get_global_hint().set_flashback_read_tx_uncommitted(true))) {
|
||||
} else if (OB_FAIL(mark_exec_params(const_cast<ObDMLStmt*>(stmt)))) {
|
||||
LOG_WARN("failed to mark exec params", K(ret));
|
||||
} else if (OB_FAIL(ObSQLUtils::reconstruct_sql(plan->get_allocator(), stmt, sql, opt_ctx->get_schema_guard(), print_param))) {
|
||||
} else if (OB_FAIL(ObSQLUtils::reconstruct_sql(plan->get_allocator(), stmt, sql, opt_ctx->get_schema_guard(), print_param, NULL, session))) {
|
||||
LOG_WARN("failed to reconstruct link sql", KP(stmt), KP(plan), K(get_dblink_id()), K(ret));
|
||||
} else {
|
||||
stmt_fmt_buf_ = sql.ptr();
|
||||
stmt_fmt_len_ = sql.length();
|
||||
LOG_DEBUG("loglink succ to reconstruct link sql", K(sql));
|
||||
}
|
||||
if (-1 == hint_query_timeout_us) { // restore query_timeout_hint
|
||||
query_ctx->get_query_hint_for_update().get_global_hint().reset_query_timeout_hint();
|
||||
}
|
||||
query_ctx->get_query_hint_for_update().get_global_hint().set_flashback_read_tx_uncommitted(false);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@ -30,10 +30,12 @@ public:
|
||||
virtual int get_explain_name_internal(char *buf, const int64_t buf_len, int64_t &pos) override;
|
||||
virtual int get_plan_item_info(PlanText &plan_text, ObSqlPlanItem &plan_item) override;
|
||||
inline void set_dml_type(stmt::StmtType type) { dml_type_ = type; }
|
||||
inline ObIArray<int64_t> &get_related_dblink_ids() { return related_dblink_ids_; }
|
||||
private:
|
||||
virtual bool print_flashback_query() const override { return false; };
|
||||
private:
|
||||
stmt::StmtType dml_type_;
|
||||
common::ObSEArray<int64_t, 8, common::ModulePageAllocator, true> related_dblink_ids_; // all dblinks related in this link dml sql
|
||||
};
|
||||
|
||||
} // namespace sql
|
||||
|
||||
@ -4255,46 +4255,18 @@ int ObSelectLogPlan::generate_normal_raw_plan()
|
||||
int ObSelectLogPlan::generate_dblink_raw_plan()
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObQueryCtx *query_ctx = NULL;
|
||||
// dblink_info hint
|
||||
int64_t tx_id = -1;
|
||||
int64_t tm_sessid = -1;
|
||||
uint32_t tm_sessid = 0;
|
||||
bool xa_trans_stop_check_lock = false;
|
||||
uint64_t dblink_id = OB_INVALID_ID;
|
||||
const ObSelectStmt *stmt = get_stmt();
|
||||
ObLogicalOperator *top = NULL;
|
||||
if (OB_ISNULL(stmt)) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("unexpected null ptr", K(ret));
|
||||
} else if (NULL == (query_ctx = stmt->get_query_ctx())) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("get unexpected null", K(ret));
|
||||
} else if (FALSE_IT(dblink_id = stmt->get_dblink_id())) {
|
||||
} else if (0 == dblink_id) { //dblink id = 0 means @!/@xxxx!
|
||||
ObSQLSessionInfo *session = get_optimizer_context().get_session_info();
|
||||
oceanbase::sql::ObReverseLink *reverse_dblink_info = NULL;
|
||||
if (NULL == session) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("get unexpected null", K(ret), KP(session));
|
||||
} else if (OB_FAIL(session->get_dblink_context().get_reverse_link(reverse_dblink_info))) {
|
||||
LOG_WARN("failed to get reverse link info from session", K(ret), K(session->get_sessid()));
|
||||
} else if (NULL == reverse_dblink_info) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("get unexpected null", K(ret));
|
||||
} else {
|
||||
// set dblink_info, to unparse a link sql with dblink_info hint
|
||||
query_ctx->get_query_hint_for_update().get_global_hint().merge_dblink_info_hint(
|
||||
reverse_dblink_info->get_tx_id(),
|
||||
reverse_dblink_info->get_tm_sessid());
|
||||
LOG_DEBUG("set tx_id_ and tm_sessid to stmt",
|
||||
K(reverse_dblink_info->get_tx_id()),
|
||||
K(reverse_dblink_info->get_tm_sessid()));
|
||||
}
|
||||
} else {
|
||||
// save dblink_info hint
|
||||
tx_id = query_ctx->get_query_hint_for_update().get_global_hint().get_dblink_tx_id_hint();
|
||||
tm_sessid = query_ctx->get_query_hint_for_update().get_global_hint().get_dblink_tm_sessid_hint();
|
||||
// reset dblink hint, to unparse a link sql without dblink_info hint
|
||||
query_ctx->get_query_hint_for_update().get_global_hint().reset_dblink_info_hint();
|
||||
dblink_id = stmt->get_dblink_id();
|
||||
}
|
||||
if (OB_FAIL(ret)) {
|
||||
//do nothing
|
||||
@ -4319,13 +4291,6 @@ int ObSelectLogPlan::generate_dblink_raw_plan()
|
||||
} else {
|
||||
top->mark_is_plan_root();
|
||||
top->get_plan()->set_plan_root(top);
|
||||
if (0 == dblink_id) {
|
||||
// reset dblink info, to avoid affecting the next execution flow
|
||||
query_ctx->get_query_hint_for_update().get_global_hint().reset_dblink_info_hint();
|
||||
} else {
|
||||
// restore dblink_info hint, ensure that the next execution process can get the correct dblink_info
|
||||
query_ctx->get_query_hint_for_update().get_global_hint().merge_dblink_info_hint(tx_id, tm_sessid);
|
||||
}
|
||||
LOG_TRACE("succeed to allocate loglinkscan", K(dblink_id));
|
||||
}
|
||||
return ret;
|
||||
|
||||
Reference in New Issue
Block a user