Zapytanie - odczyt z bazy danych.

0

witam, w jaki sposób mogę ten kod przerobić zeby czytało account_id z accounts.
kod wyglada tak

    query << "SELECT `name` FROM `players` WHERE `account_id` = " << accno;
0

zrobiłem to tak

    query << "SELECT `name` FROM `players` WHERE `account_id` FROM `accounts` = " << accno << " AND `deleted` = 0 FROM `players` "; 

error mysql_real_query<>: SELECTnameFROMplayersWHEREaccount_idFROMaccounts= 123 ANDdeleted= 0 FROMplayers- MYSQL ERROR: you have an error in your SQL syntax: check the manual that corresponds to your MySQL serwer version for the right syntax to use near FROMaccounts= 123 ANDdeleted= 0 FROMplayers at line 1 <1064>

pomoże ktoś?

0

query << "SELECT account_id FROM nazwa_tabeli WHERE account_id = " << accno;

// PL:

Wybierz z bazy danych 'account_id' Z tabeli ... GDZIE account_id jest równe accno

0

pomoże ktoś? OMG

0

??????????

0

ciągle potrzebuje pomocy

    query << "SELECT `name` FROM `players` WHERE `account_id` = " << accno << " AND `deleted` = 0";
    if(!(result = db->storeQuery(query.str())))
        return account;

    do
    {
        std::string ss = result->getDataString("name");
        account.charList.push_back(ss.c_str());
    } 

chce w tym kodzie zeby account_id czytało z accounts
w tej chwili czyta z players ten kto sie zna to rozumie kod i nie muszę tłumaczyć

0

Grubo ... poczytaj najpierw o złączeniach tabel @Shakaz ma rację rozwiązanie masz podane ale nie masz gotowca i wydaje Ci się, że rozwiązania brak. Nie znam bazy danych, która mogłaby zrobić select coś from coś where coś from
Jeżeli faktycznie chcesz tabelę players połączyć z accounts to musisz użyć JOIN czyli np tak:

select cos from tab1 inner join tab2 on (tab1.IDPolaDoZlaczenia = Tab2.IDPolaDoZlaczeniaZTab1PrawdopodobnieForeginKey) where cos

Nie podałeś struktury, nie zrobiłeś przykładu na sql fiddle, nie podałeś nawet co chcesz uzyskać i dziwisz się, że nikt Ci gotowca nie daje ...

0
woolfik napisał(a):

Grubo ... poczytaj najpierw o złączeniach tabel @Shakaz ma rację rozwiązanie masz podane ale nie masz gotowca i wydaje Ci się, że rozwiązania brak. Nie znam bazy danych, która mogłaby zrobić select coś from coś where coś from
Jeżeli faktycznie chcesz tabelę players połączyć z accounts to musisz użyć JOIN czyli np tak:

select cos from tab1 inner join tab2 on (tab1.IDPolaDoZlaczenia = Tab2.IDPolaDoZlaczeniaZTab1PrawdopodobnieForeginKey) where cos

Nie podałeś struktury, nie zrobiłeś przykładu na sql fiddle, nie podałeś nawet co chcesz uzyskać i dziwisz się, że nikt Ci gotowca nie daje ...

to mi podaj opcje jak mogę coś takiego zrobić żeby działało w 100% tylko przykład
może zrobic 3x query? do każdego zapytania osobno czy lepiej tym joinem
jestem troche zielony ale co do tamtego postu to **** przecież koleś przekopiował to samo co miałem w pierwszym poście tylko zmienił z angielskiego na polski boshe...

0

Ech podaj nam tutaj DDL (kod obiektów sql czyli CREATE TABLE ...) obu tabel players i accounts to zobaczę co się da zrobić

0
woolfik napisał(a):

Ech podaj nam tutaj DDL (kod obiektów sql czyli CREATE TABLE ...) obu tabel players i accounts to zobaczę co się da zrobić

accounts

SET FOREIGN_KEY_CHECKS=0;

-- ----------------------------
-- Table structure for accounts
-- ----------------------------
DROP TABLE IF EXISTS `accounts`;
CREATE TABLE `accounts` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(32) NOT NULL DEFAULT '',
  `password` varchar(255) NOT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `name` (`name`)
) ENGINE=InnoDB AUTO_INCREMENT=1528016 DEFAULT CHARSET=latin1;

-- ----------------------------
-- Records of accounts
-- ----------------------------
DROP TRIGGER IF EXISTS `ondelete_accounts`;
DELIMITER ;;
CREATE TRIGGER `ondelete_accounts` BEFORE DELETE ON `accounts` FOR EACH ROW BEGIN
	DELETE FROM `bans` WHERE `type` IN (3, 4) AND `value` = OLD.`id`;
END
;;
DELIMITER ;

players

DROP TABLE IF EXISTS `players`;
CREATE TABLE `players` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(255) NOT NULL,
  `account_id` int(11) NOT NULL DEFAULT '0',
  `deleted` int(11) NOT NULL DEFAULT '0',
  PRIMARY KEY (`id`),
  UNIQUE KEY `name` (`name`,`deleted`),
  KEY `account_id` (`account_id`),
  KEY `deleted` (`deleted`),
  CONSTRAINT `players_ibfk_1` FOREIGN KEY (`account_id`) REFERENCES `accounts` (`id`) ON DELETE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
0

wydaje mi się, że coś takiego powinno wystarczyć:

select p.name from accounts a inner join players p on (a.id = p.account_id) where p.deleted = 0 and a.account_id = <co tam chcesz>

Ewentualnie jeśli może się zdarzyć, że nie ma odpowiednika dla tabeli accounts w tabeli players to możesz inner join zmienić na left outer join ale wydaje mi się, że nie trzeba.

0
woolfik napisał(a):

wydaje mi się, że coś takiego powinno wystarczyć:

select p.name from accounts a inner join players p on (a.id = p.account_id) where p.deleted = 0 and a.account_id = <co tam chcesz>

Ewentualnie jeśli może się zdarzyć, że nie ma odpowiednika dla tabeli accounts w tabeli players to możesz inner join zmienić na left outer join ale wydaje mi się, że nie trzeba.

error
user image

0

@Programistyczny ahhh i mamy Ci wywrozyc cos Ty tam narobil tak? ahhh... to blad jest w piatej linijce tej funkcji ktorej wywolujesz.

Problem masz ze zle utworzyles zapytanie i masz problem przez to ze skladnia (a raczej mysql ma)

0
fasadin napisał(a):

@Programistyczny ahhh i mamy Ci wywrozyc cos Ty tam narobil tak? ahhh... to blad jest w piatej linijce tej funkcji ktorej wywolujesz.

Problem masz ze zle utworzyles zapytanie i masz problem przez to ze skladnia (a raczej mysql ma)

dobrze zrobiłem

 query << "SELECT p.name FROM accounts a INNER JOIN players p ON (a.id = p.account_id) WHERE p.deleted = 0 AND a.account_id = ";
1

Ja dobrze widzę, że za = w AND a.account_id nie ma niczego?

0
hipekk napisał(a):

Ja dobrze widzę, że za = w AND a.account_id nie ma niczego?

a teraz? co jest zle
user image

0
  1. Wklejaj swoje zapytanie a nie treść błędu
  2. Masz jasno napisane: kolumna account_id jest wieloznaczna (występuje zarówno w tabeli accounts jak i players). Chyba p.account_id chciałeś użyć.
0
hipekk napisał(a):
  1. Wklejaj swoje zapytanie a nie treść błędu
  2. Masz jasno napisane: kolumna account_id jest wieloznaczna. Chyba p.account_idchciałeś użyć.

kod

 query << "SELECT p.name FROM accounts a INNER JOIN players p ON (a.id = p.account_id) WHERE p.deleted = 0 AND a.account_id = account_id";

taki jest kod
ma być = p.account_id?

@fasadin przepraszam ;]

0

Jeżeli wklepiesz a.account_id = p.account_id to zapytanie powinno działać, ale wydaje mi się, że nie o to Ci chodzi.
Wychodzi na to że chcesz wyniki w których a.id = p.account_id = a.account_id?

0
hipekk napisał(a):

Jeżeli wklepiesz a.account_id = p.account_id to zapytanie powinno działać, ale wydaje mi się, że nie o to Ci chodzi.
Wychodzi na to że chcesz wyniki w których a.id = p.account_id = a.account_id?

chodzi mi dokładnie o to co w pierwszym poście napisałem chce zmienić account_id z players na name z accounts

zmieniłem na account_id na p.account_id to teraz wyskakuje ze zła nazwa konta i hasło

     query << "SELECT p.name FROM accounts a INNER JOIN players p ON (a.id = p.account_id) WHERE p.deleted = 0 AND a.account_id = p.account_id";
0

zmieniłem na account_id na p.account_id to teraz wyskakuje ze zła nazwa konta i hasło

To wpisz poprawne dane.

chce zmienić account_id z players na name z accounts

Chcesz w miejsce id wstawić nazwę?
Jesteś pewny, że to ten sam typ danych?

0

@Programistyczny to jest jakis czeski film co robisz. Skoro łączysz a.id = p.account_id to ten ostatni warunek where jest albo głupi albo w ogóle niepotrzebny...

1

Weź parę głębokich wdechów i spróbuj tego:

query << "SELECT p.name FROM accounts a INNER JOIN players p ON (a.id = p.account_id) WHERE p.deleted = 0 AND a.account_id ="<< accno;

0
EroSanin napisał(a):

Weź parę głębokich wdechów i spróbuj tego:

query << "SELECT p.name FROM accounts a INNER JOIN players p ON (a.id = p.account_id) WHERE p.deleted = 0 AND a.account_id ="<< accno;

wyskakuje ze złe hasło lub nazwa konta a wpisuję w 100% dobre

0

No to usługodawca Cię oszukuje :P.

Pokaż cały kod (oczywiście wrażliwe dane zmień).

0

cały kod wygląda tak
to jest orginal bez ruszania

#include "ioaccountsql.h"
#include <iostream>
#include <iomanip>

#include "tools.h"
#include "database.h"

Account IOAccountSQL::loadAccount(uint32_t accno)
{
    Account account;
    time_t lastDay;
    Database* db = Database::getInstance();
    DBQuery query;

    query << "SELECT `id`, `password`, `premdays`, `rkey`, `email`, `premium_points` FROM `accounts` WHERE `id` = " << accno << " LIMIT 1";
    DBResult* result;
    if(!(result = db->storeQuery(query.str())))
        return account;

    account.accnumber = result->getDataInt("id");
    account.password = result->getDataString("password");
    account.premDays = result->getDataInt("premdays");
    account.key = result->getDataString("rkey");
    account.email = result->getDataString("email");
    account.premium_points = result->getDataInt("premium_points");

    query.str("");
    result->free();
//i tutaj zmienialem
  //orginal  query << "SELECT `name` FROM `players` WHERE `account_id` = " << accno << " AND `deleted` = 0";
query << "SELECT p.name FROM accounts a INNER JOIN players p ON (a.id = p.account_id) WHERE p.deleted = 0 AND a.account_id ="<< accno;
    if(!(result = db->storeQuery(query.str())))
        return account;

    do
    {
        std::string ss = result->getDataString("name");
        account.charList.push_back(ss.c_str());
    }
    while(result->next());

    result->free();
    account.charList.sort();

    return account;
}

bool IOAccountSQL::saveAccount(Account account)
{
    Database* db = Database::getInstance();
    DBQuery query;

    query << "UPDATE `accounts` SET `premdays` = " << account.premDays << ", `email` = '" << account.email << "', `premium_points` = " << account.premium_points << " WHERE `id` = " << account.accnumber << db->getUpdateLimiter();

    return db->executeQuery(query.str());
}

bool IOAccountSQL::getPassword(uint32_t accno, const std::string &name, std::string &password)
{
    Database* db = Database::getInstance();
    DBQuery query;
    query << "SELECT `password` FROM `accounts` WHERE `id` = " << accno << " LIMIT 1";

    DBResult* result;
    if(!(result = db->storeQuery(query.str())))
        return false;

    if(name.empty())
    {
        password = result->getDataString("password");
        result->free();
        return true;
    }

    std::string tmpPassword = result->getDataString("password");
    result->free();
    query.str("");

    query << "SELECT `name` FROM `players` WHERE `account_id` = " << accno;
    if(!(result = db->storeQuery(query.str())))
        return false;

    do
    {
        if(result->getDataString("name") != name)
            continue;

        password = tmpPassword;
        result->free();
        return true;
    }
    while(result->next());

    result->free();
    return false;
}

bool IOAccountSQL::accountExists(uint32_t accno)
{
    Database* db = Database::getInstance();
    DBQuery query;
    query << "SELECT `id` FROM `accounts` WHERE `id` = " << accno << " LIMIT 1";

    DBResult* result;
    if(!(result = db->storeQuery(query.str())))
        return false;

    result->free();
    return true;
}

database.h

#include "scheduler.h"

#include "database.h"
#include "databasemysql.h"

#ifdef __MYSQL_ALT_INCLUDE__
#include "errmsg.h"
#else
#include <mysql/errmsg.h>
#endif
#include <iostream>

#include "luascript.h"
#include "game.h"
extern LuaScript g_config;
extern Game g_game;
DatabaseMySQL::DatabaseMySQL()
{
    m_connected = false;
    if(!mysql_init(&m_handle))
    {
        std::cout << std::endl << "Failed to initialize MySQL connection handler." << std::endl;
        return;
    }

    uint32_t readTimeout = g_config.MYSQL_READ_TIMEOUT;
    if(readTimeout)
        mysql_options(&m_handle, MYSQL_OPT_READ_TIMEOUT, (const char*)&readTimeout);

    uint32_t writeTimeout = g_config.MYSQL_WRITE_TIMEOUT;
    if(writeTimeout)
        mysql_options(&m_handle, MYSQL_OPT_WRITE_TIMEOUT, (const char*)&writeTimeout);

    connect();
    if(mysql_get_client_version() <= 50019)
    {
        //MySQL servers <= 5.0.19 has a bug where MYSQL_OPT_RECONNECT is (incorrectly) reset by mysql_real_connect calls
        //See http://dev.mysql.com/doc/refman/5.0/en/mysql-options.html for more information.
        std::cout << std::endl << "> WARNING: Outdated MySQL server detected, consider upgrading to a newer version." << std::endl;
    }

    int32_t keepAlive = g_config.SQL_KEEPALIVE;
    if(keepAlive)
        g_game.addEvent(makeTask((keepAlive * 1000), boost::bind(&DatabaseMySQL::keepAlive, this)));
}

bool DatabaseMySQL::getParam(DBParam_t param)
{
    switch(param)
    {
    case DBPARAM_MULTIINSERT:
        return true;
    default:
        break;
    }

    return false;
}

bool DatabaseMySQL::rollback()
{
    if(!m_connected)
        return false;

    if(mysql_rollback(&m_handle))
    {
        std::cout << "mysql_rollback() - MYSQL ERROR: " << mysql_error(&m_handle) << " (" << mysql_errno(&m_handle) << ")" << std::endl;
        return false;
    }

    return true;
}

bool DatabaseMySQL::commit()
{
    if(!m_connected)
        return false;

    if(mysql_commit(&m_handle))
    {
        std::cout << "mysql_commit() - MYSQL ERROR: " << mysql_error(&m_handle) << " (" << mysql_errno(&m_handle) << ")" << std::endl;
        return false;
    }

    return true;
}

bool DatabaseMySQL::executeQuery(const std::string &query)
{
    if(!m_connected)
        return false;

    bool state = true;
    if(mysql_real_query(&m_handle, query.c_str(), query.length()))
    {
        int32_t error = mysql_errno(&m_handle);
        if((error == CR_UNKNOWN_ERROR || error == CR_SERVER_LOST || error == CR_SERVER_GONE_ERROR) && reconnect())
            return executeQuery(query);

        state = false;
        std::cout << "mysql_real_query(): " << query << " - MYSQL ERROR: " << mysql_error(&m_handle) << " (" << error << ")" << std::endl;
    }

    if(MYSQL_RES* tmp = mysql_store_result(&m_handle))
    {
        mysql_free_result(tmp);
        tmp = NULL;
    }

    return state;
}

DBResult* DatabaseMySQL::storeQuery(const std::string &query)
{
    if(!m_connected)
        return NULL;

    int32_t error = 0;
    if(mysql_real_query(&m_handle, query.c_str(), query.length()))
    {
        error = mysql_errno(&m_handle);
        if((error == CR_UNKNOWN_ERROR || error == CR_SERVER_LOST || error == CR_SERVER_GONE_ERROR) && reconnect())
            return storeQuery(query);

        std::cout << "mysql_real_query(): " << query << " - MYSQL ERROR: " << mysql_error(&m_handle) << " (" << error << ")" << std::endl;
        return NULL;

    }

    if(MYSQL_RES* tmp = mysql_store_result(&m_handle))
    {
        DBResult* res = (DBResult*)new MySQLResult(tmp);
        return verifyResult(res);
    }

    error = mysql_errno(&m_handle);
    if((error == CR_UNKNOWN_ERROR || error == CR_SERVER_LOST || error == CR_SERVER_GONE_ERROR) && reconnect())
        return storeQuery(query);

    std::cout << "mysql_store_result(): " << query << " - MYSQL ERROR: " << mysql_error(&m_handle) << " (" << error << ")" << std::endl;
    return NULL;
}

std::string DatabaseMySQL::escapeBlob(const char* s, uint32_t length)
{
    if(!s)
        return "''";

    char* output = new char[length * 2 + 1];
    mysql_real_escape_string(&m_handle, output, s, length);

    std::string res = "'";
    res += output;
    res += "'";

    delete[] output;
    return res;
}

void DatabaseMySQL::keepAlive()
{
    int32_t delay = g_config.SQL_KEEPALIVE;
    if(delay)
    {
        if(time(NULL) > (m_use + delay) && mysql_ping(&m_handle))
            reconnect();

        g_game.addEvent(makeTask((delay * 1000), boost::bind(&DatabaseMySQL::keepAlive, this)));
    }
}

bool DatabaseMySQL::connect()
{
    if(m_connected)
    {
        m_connected = false;
        mysql_close(&m_handle);
    }

    if(!mysql_real_connect(&m_handle, g_config.SQL_HOST.c_str(), g_config.SQL_USER.c_str(),
                           g_config.SQL_PASS.c_str(), g_config.SQL_DB.c_str(), g_config.SQL_PORT, NULL, 0))
    {
        std::cout << "Failed connecting to database - MYSQL ERROR: " << mysql_error(&m_handle) << " (" << mysql_errno(&m_handle) << ")" << std::endl;
        return false;
    }

    m_connected = true;
    m_attempts = 0;
    return true;
}

bool DatabaseMySQL::reconnect()
{
    while(m_attempts <= MAX_RECONNECT_ATTEMPTS)
    {
        m_attempts++;
        if(connect())
            return true;
    }

    std::cout << "Unable to reconnect - too many attempts, limit exceeded!" << std::endl;
    return false;
}

int32_t MySQLResult::getDataInt(const std::string &s)
{
    listNames_t::iterator it = m_listNames.find(s);
    if(it != m_listNames.end())
    {
        if(!m_row[it->second])
            return 0;

        return atoi(m_row[it->second]);
    }

    if(refetch())
        return getDataInt(s);

    std::cout << "Error during getDataInt(" << s << ")." << std::endl;
    return 0; // Failed
}

uint64_t MySQLResult::getDataLong(const std::string &s)
{
    listNames_t::iterator it = m_listNames.find(s);
    if(it != m_listNames.end())
    {
        if(!m_row[it->second])
            return 0;

        return atoll(m_row[it->second]);
    }

    if(refetch())
        return getDataLong(s);

    std::cout << "Error during getDataLong(" << s << ")." << std::endl;
    return 0; // Failed
}

std::string MySQLResult::getDataString(const std::string &s)
{
    listNames_t::iterator it = m_listNames.find(s);
    if(it != m_listNames.end())
    {
        if(!m_row[it->second])
            return "";

        return std::string(m_row[it->second]);
    }

    if(refetch())
        return getDataString(s);

    std::cout << "Error during getDataString(" << s << ")." << std::endl;
    return ""; // Failed
}

const char* MySQLResult::getDataStream(const std::string &s, uint64_t &size)
{
    listNames_t::iterator it = m_listNames.find(s);
    if(it != m_listNames.end())
    {
        if(!m_row[it->second])
        {
            size = 0;
            return NULL;
        }

        size = mysql_fetch_lengths(m_handle)[it->second];
        return m_row[it->second];
    }

    if(refetch())
        return getDataStream(s, size);

    std::cout << "Error during getDataStream(" << s << ")." << std::endl;
    size = 0;
    return NULL; // Failed
}

void MySQLResult::free()
{
    if(m_handle)
    {
        mysql_free_result(m_handle);
        m_handle = NULL;

        m_listNames.clear();
        delete this;
    }
    else
        std::cout << "[Warning - MySQLResult::free] Trying to free already freed result." << std::endl;
}

bool MySQLResult::next()
{
    m_row = mysql_fetch_row(m_handle);
    return m_row;
}

void MySQLResult::fetch()
{
    m_listNames.clear();
    int32_t i = 0;

    MYSQL_FIELD* field;
    while((field = mysql_fetch_field(m_handle)))
        m_listNames[field->name] = i++;
}

bool MySQLResult::refetch()
{
    if(m_attempts >= MAX_REFETCH_ATTEMPTS)
        return false;

    fetch();
    ++m_attempts;
    return true;
}

MySQLResult::MySQLResult(MYSQL_RES* result)
{
    m_attempts = 0;
    if(result)
    {
        m_handle = result;
        fetch();
    }
    else
        delete this;
}
 
0

A tak zapytam jeszcze: łączysz się z bazą lokalną czy na zewnątrz? Próbowałeś połączyć się z tą bazą (używając tych samych danych) z innego programu?

1 użytkowników online, w tym zalogowanych: 0, gości: 1