/** * Copyright (C) 2013-2014 Project-Vethrfolnir * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. */ package com.vethrfolnir.game.services.dao; import java.security.MessageDigest; import java.sql.*; import java.util.ArrayList; import com.vethrfolnir.game.module.MuAccount; import com.vethrfolnir.game.network.mu.MuClient; import com.vethrfolnir.game.network.mu.crypt.MuCryptUtils; import com.vethrfolnir.game.templates.AccountCharacterInfo; import com.vethrfolnir.game.templates.AccountInfo; /** * @author Vlad * */ public class AccountDAO extends DAO { public AccountInfo getInfo(String accountName) { return enqueueAndWait((Connection con, Procedure<?> proc, Object... buff)-> { PreparedStatement st = con.prepareStatement("select password, accessLevel, lastAccess, creationDate from accounts where accountName = ?"); st.setString(1, accountName); ResultSet rs = st.executeQuery(); if(rs.next()) { int p = 1; byte[] passData = MuCryptUtils.toByte(rs.getString(p++)); // password hex string int accessLevel = rs.getInt(p++); Date lastAccess = rs.getDate(p++); Date creationDate = rs.getDate(p++); return new AccountInfo(passData, accessLevel, lastAccess, creationDate); } return null; }); } /** * @param accountName * @return */ public byte[] getPassword(String accountName) { return enqueueAndWait((con, prco, buff) -> { PreparedStatement st = con.prepareStatement("select password from accounts where accountName=?"); st.setString(1, accountName); ResultSet rs = st.executeQuery(); if(rs.next()) { String name = rs.getString(1); return MuCryptUtils.toByte(name); // password hex string } return null; }); } /** * @param accountName * @return */ public int getLobbyCharacterSize(String accountName) { return enqueueAndWait((con, proc, buff) -> { int count = 0; PreparedStatement st = con.prepareStatement("select count(*) from characters where accountName = ?"); st.setString(1, accountName); ResultSet rs = st.executeQuery(); if(rs.next()) { count = rs.getInt(1); } return count; }); } public ArrayList<AccountCharacterInfo> getLobbyCharacters(MuAccount account) { final ArrayList<AccountCharacterInfo> infos = new ArrayList<>(); enqueueVoidAndWait((Connection con, Object... buff)-> { PreparedStatement st = con.prepareStatement("select charId, slot, name, level, accessLevel, classId, wearSet from characters where accountName = ?"); st.setString(1, account.getAccountName()); ResultSet rs = st.executeQuery(); while(rs.next()) { AccountCharacterInfo info = new AccountCharacterInfo(); int pointer = 1; info.charId = rs.getInt(pointer++); info.slot = rs.getInt(pointer++); info.name = rs.getString(pointer++); info.level = rs.getInt(pointer++); info.access = rs.getInt(pointer++); info.classId = rs.getInt(pointer++); // Slot used account.getSlots().set(info.slot, true); byte[] wearSet = rs.getBytes(pointer++); if(wearSet != null) { for (int i = 0; i < wearSet.length; i++) info.wearBytes[i] = wearSet[i] & 0xFF; } infos.add(info); } }); return infos; } public void createCharacter(String accountName, AccountCharacterInfo info, int mapId, int x, int y) { enqueueVoidAndWait((con, buff) -> { int pointer = 1; PreparedStatement st = con.prepareStatement("insert into characters(accountName, name, charId, slot, classId, mapId, x, y) values(?,?,?,?,?,?,?,?)"); st.setString(pointer++, accountName); st.setString(pointer++, info.name); st.setInt(pointer++, info.charId); st.setInt(pointer++, info.slot); st.setInt(pointer++, info.classId); st.setInt(pointer++, mapId); st.setInt(pointer++, x); st.setInt(pointer++, y); st.execute(); }); } /** * @param name * @return */ public boolean isNameFree(String name) { return enqueueAndWait((con, proc, buff)-> { PreparedStatement st = con.prepareStatement("select name from characters where name=?"); st.setString(1, name); return st.executeQuery().next(); }); } /** * @param name */ public void deleteCharacter(String name) { enqueueVoidAndWait((con, buff)-> { PreparedStatement st = con.prepareStatement("delete from characters where name=?"); st.setString(1, name); st.execute(); }); } public void updateAccount(MuAccount account) { enqueueVoid((con, buff) -> { PreparedStatement st = con.prepareStatement("update accounts set lastAccess=?, ip=? where accountName=?"); st.setDate(1, new Date(System.currentTimeMillis())); st.setString(3, account.getClient().getHostAddress()); st.setString(4, account.getAccountName()); st.execute(); }); } /** * @param accountName * @param password */ public void createAccount(final String accountName, final String password, final MuClient client) { enqueueVoid((Connection con, Object... buff)-> { int pointer = 1; PreparedStatement st = con.prepareStatement("insert into accounts values(?,?,?,?,?,?)"); st.setString(pointer++, accountName); MessageDigest md = MessageDigest.getInstance("md5"); byte[] hash = md.digest(password.getBytes("UTF-8")); st.setString(pointer++, MuCryptUtils.toString(hash)); st.setInt(pointer++, 0x00); // access level st.setDate(pointer++, new Date(System.currentTimeMillis())); // last access st.setDate(pointer++, new Date(System.currentTimeMillis())); // Creation Date st.setString(pointer++, client.getHostAddress()); st.execute(); }); } /** * @param client */ public void update(final MuClient client) { enqueueVoid((Connection con, Object... buff)-> { int pointer = 1; PreparedStatement st = con.prepareStatement("update accounts set lastAccess=?, ip = ? where accountName = ?"); st.setDate(pointer++, new Date(System.currentTimeMillis())); st.setString(pointer++, client.getHostAddress()); st.setString(pointer++, client.getAccount().getAccountName()); st.execute(); }); } }