//수행도중 에러가 나도 S_OK 리턴 //에러시 cardinality는 0이 된다. static HRESULT GetCardinality(int hConn, WCHAR* tableName, ULARGE_INTEGER* cardinality) { CComBSTR query; T_CCI_ERROR error; int hReq, res, ind; query.Append("select count(*) from "); query.Append(tableName); hReq = cci_prepare(hConn, CW2A(query.m_str), 0, &error); if (hReq < 0) return S_OK; res = cci_execute(hReq, CCI_EXEC_QUERY_ALL, 0, &error); if (res < 0) return S_OK; res = cci_cursor(hReq, 1, CCI_CURSOR_FIRST, &error); if(res<0) return S_OK; res = cci_fetch(hReq, &error); if(res<0) return S_OK; res = cci_get_data(hReq, 1, CCI_A_TYPE_INT, &cardinality->QuadPart, &ind); if(res<0) return S_OK; cci_close_req_handle(hReq); return S_OK; }
bool DbExecute(int qid){ int ret = cci_execute(qid, 0, 0, &cciErr); if(ret >= 0) return true; else return false; }
int CubTest(){ int nColCount = 0, nLen = 0; int i = 0, nDB = 0, nRet = 0, nReq = 0; char *pszBuff = NULL; T_CCI_COL_INFO *pcciCol; T_CCI_SQLX_CMD cciCmdType; assert((nDB = cci_connect(DB_SERVER, DB_PORT, DB_NAME, DB_USER_ID, DB_USER_PW)) >= 0); assert((nReq = cci_prepare(nDB, "SELECT * FROM athlete", 0, &cciErr)) >= 0); assert((pcciCol = cci_get_result_info(nReq, &cciCmdType, &nColCount)) != NULL); for (i = 1; i <= nColCount; i++) { printf("%s\t", CCI_GET_RESULT_INFO_NAME(pcciCol, i)); } printf("\n"); assert(cci_execute(nReq, 0, 0, &cciErr) >= 0); while (1) { if ( cci_cursor(nReq, 1, CCI_CURSOR_CURRENT, &cciErr) == CCI_ER_NO_MORE_DATA ) break; assert(cci_fetch(nReq, &cciErr) >= 0); for (i = 1; i<= nColCount; i++) { assert(cci_get_data(nReq, i, CCI_A_TYPE_STR, &pszBuff, &nLen) >= 0); printf("%s\t", pszBuff); } printf("\n"); } assert(cci_close_req_handle(nReq) >= 0); assert(cci_disconnect(nDB, &cciErr) >= 0); return 0; }
// NOTICE: 가능하면 이 함수에서 에러가 발생하면 안 된다. // query 중 에러가 발생할 만한 여지가 있는 것은 ReadData 시에 // 모두 찾아내야 한다. // 그렇지 않으면 deferred update 모드에서 SetData()는 성공했는데 // Update()가 실패하게 된다. HRESULT CCUBRIDRowsetRow::WriteData(int hConn, int hReq, CComBSTR &strTableName) { ATLTRACE(atlTraceDBProvider, 3, "CCUBRIDRowsetRow::WriteData(1)\n"); HRESULT hr = S_OK; // query 생성 CComBSTR query; { switch(m_status) { case DBPENDINGSTATUS_DELETED: // delete from <table> where <table>=? query.Append("delete from "); query.Append("["); query.Append(strTableName); query.Append("]"); query.Append(" where "); query.Append("["); query.Append(strTableName); query.Append("]"); query.Append("=?"); break; case DBPENDINGSTATUS_NEW: // insert into <table>(<column>,<column>) values(<value>,<value>) { CComBSTR column; CComBSTR value; for(DBORDINAL i=0;i<m_cColumns;i++) { ATLCOLUMNINFO *m_pInfoCur = &m_pInfo[i]; if(m_pInfoCur->iOrdinal==0) continue; // skip bookmark column column.Append("["); column.Append(m_pInfoCur->pwszName); column.Append("]"); value.Append(BuildColumnValue(m_pInfoCur, m_rgColumns+i)); if(i!=m_cColumns-1) { column.Append(","); value.Append(","); } } query.Append("insert into "); query.Append("["); query.Append(strTableName); query.Append("]"); query.Append("("); query.Append(column); query.Append(") values("); query.Append(value); query.Append(")"); } break; case DBPENDINGSTATUS_CHANGED: { // TODO: 중간에 실패하면 되돌리지를 못한다. for(DBORDINAL i=0;i<m_cColumns;i++) { ATLCOLUMNINFO *pInfoCur = &m_pInfo[i]; if(pInfoCur->iOrdinal==0) continue; // skip bookmark column CCUBRIDRowsetRowColumn *pCol = m_rgColumns+i; HRESULT hr = pCol->WriteData(hReq, (int) m_iRowset, pInfoCur); if(FAILED(hr)) return hr; } return S_OK; } /* Query Base: view에 적용불가 // update <table> set <column>=<value>, <column>=<value> where <table>=? { CComBSTR set; for(DBORDINAL i=0;i<m_cColumns;i++) { ATLCOLUMNINFO *m_pInfoCur = &m_pInfo[i]; if(m_pInfoCur->iOrdinal==0) continue; // skip bookmark column set.Append(m_pInfoCur->pwszName); set.Append("="); set.Append(BuildColumnValue(m_pInfoCur, m_rgColumns+i)); if(i!=m_cColumns-1) set.Append(","); } query.Append("update "); query.Append("["); query.Append(strTableName); query.Append("]"); query.Append(" set "); query.Append(set); query.Append(" where "); query.Append("["); query.Append(strTableName); query.Append("]"); query.Append("=?"); } */ break; default: return DB_E_ERRORSOCCURRED; } } //#ifdef _DEBUG // { // // ATLTRACE는 한번에 1024문자까지 밖에 출력하지 못한다. // // 그래서 이렇게 출력한다. // ATLTRACE(atlTraceDBProvider, 2, "Execute Query = "); // CW2A local(query); // for(size_t i=0;i<strlen(local);) // { // char buf[513]; memcpy(buf, local+i, 512); buf[512] = 0; // ATLTRACE(atlTraceDBProvider, 2, "%s", buf); // i += 512; // } // ATLTRACE(atlTraceDBProvider, 2, "\n"); // } //#endif // prepare query int hLocalReq; { T_CCI_ERROR err_buf; hLocalReq = cci_prepare(hConn, CW2A(query), 0, &err_buf); if (hLocalReq<0) return RaiseError(DB_E_ERRORSOCCURRED, 1, __uuidof(IRowset), err_buf.err_msg); } // execute query { if(m_status==DBPENDINGSTATUS_DELETED || m_status==DBPENDINGSTATUS_CHANGED) cci_bind_param(hLocalReq, 1, CCI_A_TYPE_STR, m_szOID, CCI_U_TYPE_OBJECT, 0); T_CCI_ERROR err_buf; int rc = cci_execute(hLocalReq, 0, 0, &err_buf); if(rc<0) { cci_close_req_handle(hLocalReq); if(err_buf.err_code==-670) // constraint violation code 맞나? return RaiseError(DB_E_INTEGRITYVIOLATION, 0, __uuidof(IRowset)); else return RaiseError(DB_E_ERRORSOCCURRED, 1, __uuidof(IRowset), err_buf.err_msg); } else if(rc==0) { if(m_status==DBPENDINGSTATUS_DELETED) hr = DB_E_DELETEDROW; } else { ATLASSERT(rc==1); } } cci_close_req_handle(hLocalReq); return hr; }