I need a help to do a mysql query [closed] - php

It's difficult to tell what is being asked here. This question is ambiguous, vague, incomplete, overly broad, or rhetorical and cannot be reasonably answered in its current form. For help clarifying this question so that it can be reopened, visit the help center.
Closed 9 years ago.
I have these three tables below in DB
Tables
`accounts` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(32) NOT NULL DEFAULT '',
`password` varchar(255) NOT NULL,
`salt` varchar(40) NOT NULL DEFAULT '',
`premdays` int(11) NOT NULL DEFAULT '0',
`lastday` int(10) unsigned NOT NULL DEFAULT '0',
`email` varchar(255) NOT NULL DEFAULT '',
`key` varchar(32) NOT NULL DEFAULT '0',
`blocked` tinyint(1) NOT NULL DEFAULT '0' COMMENT 'internal usage',
`warnings` int(11) NOT NULL DEFAULT '0',
`group_id` int(11) NOT NULL DEFAULT '1',
`page_access` int(11) DEFAULT NULL,
`page_lastday` int(11) DEFAULT NULL,
`email_new` varchar(255) DEFAULT NULL,
`email_new_time` int(15) DEFAULT NULL,
`rlname` varchar(255) DEFAULT NULL,
`location` varchar(255) DEFAULT NULL,
`created` int(16) DEFAULT NULL,
`email_code` varchar(255) DEFAULT NULL,
`next_email` int(11) DEFAULT NULL,
`premium_points` int(11) DEFAULT NULL,
`nickname` char(48) DEFAULT NULL,
`avatar` char(48) DEFAULT NULL,
`about_me` text,
`vip_time` int(15) NOT NULL,
`event_points` int(11) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`),
UNIQUE KEY `name` (`name`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=4 ;
`players` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
`group_id` int(11) NOT NULL DEFAULT '1',
`account_id` int(11) NOT NULL DEFAULT '0',
`online` tinyint(1) 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 `group_id` (`group_id`),
KEY `online` (`online`),
KEY `deleted` (`deleted`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=11 ;
`gamecodes` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`gamecode` varchar(50) NOT NULL,
`accountname` varchar(50) NOT NULL,
`premium_points` int(11) NOT NULL,
`alreadyused` varchar(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=15 ;
This is my .PHP that insert FORM's information into TABLE GAME CODES
<?php
function anti_injection($sql)
{
$sql = preg_replace(sql_regcase("/(from|select|insert|delete|where|drop table|show tables|#|\*|--|\\\\)/"),"",$sql);
$sql = trim($sql);
$sql = strip_tags($sql);
$sql = addslashes($sql);
return $sql;
}
$accountorname = anti_injection($_POST['accountorname']);
$gamecode = $_POST['gamecode'];
$category = $_POST['category'];
$premiumpoints = anti_injection($_POST['premiumpoints']);
switch ($category) {
case 'accountname':
$insertquery = "INSERT INTO gamecodes (gamecode, accountname, premium_points, alreadyused) VALUES ('$gamecode','$accountorname',$premiumpoints,'N')";
break;
case 'charactername':
$insertquery = "INSERT INTO gamecodes (gamecode, accountname, premium_points, alreadyused)
SELECT '$gamecode',accounts.name,$premiumpoints,'N'
FROM accounts
JOIN players
ON accounts.id = players.account_id
WHERE players.name = '$accountorname'";
break;
}
$result = mysql_query($insertquery);
?>
The problems are:
in case 'accountname':, before INSERT it must check if informed account is valid in table ACCOUNTS.
in case 'charactername':, before INSERT it must check if informed character name is valid in table PLAYERS
I could not do, can someone help me?

$selectquery = "SELECT * from accounts where accountname='$accountname'";
$selectresult = mysql_query($selectquery);
if (mysql_num_rows($selectresult)) {
// account exists, now you can do the INSERT
}
NOTICE!
The mysql extension is deprecated as of PHP 5.5.0, and will be removed in the future. Instead, the MySQLi or PDO_MySQL extension should be used.

You can use a function for that purpose like this one:
function Validate($table, $name)
{
if ($res = mysql_query("SELECT Count(*) as isvalid FROM $table WHERE name = '$name'"))
{
$isvalid = 0;
#extract(mysql_fetch_assoc($res));
if ($isvalid == 0) return false;
else return true;
}
}
So you call this way:
case 'accountname':
if (Validate("accounts", $accountorname)) {
// Do things
}
case 'charactername':
if (Validate("players", $accountorname)) {
// Do things
}
I didn't tested it and I confess that is not the best approach, but it should do what you want.
By the way, your SQL injection functions have some breach holes. You have to filter all your inputs cause user can alter the input data of any control in the browser. Consider reviewing that.

You could always do another query to check before you do this. With this you'll still run the risk of someone deleting the account in between the queries. If that's a concern for you, you should look into transactions.
$shouldinsert = false;
switch ($category) {
case 'accountname':
$result = mysql_query("SELECT count(*) as account_count FROM accounts WHERE name = '$accountorname'");
$shouldinsert = mysql_num_rows($result) > 0;
$insertquery = "INSERT INTO gamecodes (gamecode, accountname, premium_points, alreadyused) VALUES ('$gamecode','$accountorname',$premiumpoints,'N')";
break;
case 'charactername':
//I'm not quite sure how to check if a charactername is 'valid' but this should get you started
$result = mysql_query("SELECT count(*) as account_count FROM players WHERE name = '$charactername'");
$shouldinsert = mysql_num_rows($result) > 0;
$insertquery = "INSERT INTO gamecodes (gamecode, accountname, premium_points, alreadyused)
SELECT '$gamecode',accounts.name,$premiumpoints,'N'
FROM accounts
JOIN players
ON accounts.id = players.account_id
WHERE players.name = '$accountorname'";
break;
}
if($shouldinsert) {
mysql_query($insertquery);
}

Related

PDO query updating a datetime column not in query

A PDO prepared update statement is somehow updating the datetime column for the selected record in the table, even though that particular datetime column is not even in the query.
if(isset($_POST['editCriteria']))
{
$value = $_POST['editCriteria'];
$editusername = $value['editusername'];
$hiddenUsername = $value['hiddenUsername'];
$editfullname = $value['editfullname'];
$editemail = $value['editemail'];
$edituserlevel = $value['edituserlevel'];
$editdivision = $value['editdivision'];
$editdept = $value['editdept'];
$editphone = $value['editphone'];
try
{
$dbc->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$update = $dbc->prepare("UPDATE users_edi SET username = :uname,
fullname = :fname, userlevel = :ulevel, email = :uemail,
division = :udivision, dept = :udept, phone = :uphone WHERE username = :hname");
$update->execute([
'uname' => $editusername,
'fname' => $editfullname,
'ulevel' => $edituserlevel,
'uemail' => $editemail,
'udivision' => $editdivision,
'udept' => $editdept,
'uphone' => $editphone,
'hname' => $hiddenUsername
]);
if($update)
{
echo "Success: User has been updated.";
}
}
catch(PDOException $e)
{
echo "Error: " . $e->getMessage();
}
}
In the database table, there is a column called lastLoginDate that is being updated to the current datetime.
If you'll notice in the update statement above, the query does not include lastLoginDate.
How is lastLoginDate being updated when it's not even in the query?
Upon using the SHOW CREATE TABLE command, there was indeed a trigger on the lastLoginDate column.
CREATE TABLE `users_edi` (
`username` varchar(30) NOT NULL DEFAULT '',
`fullname` varchar(50) DEFAULT NULL,
`userlevel` tinyint(1) unsigned NOT NULL,
`ipaddress` varchar(30) DEFAULT NULL,
`email` varchar(150) DEFAULT NULL,
`entrydate` datetime DEFAULT NULL,
`division` varchar(35) DEFAULT NULL,
`password` varchar(32) DEFAULT NULL,
`userid` varchar(32) DEFAULT NULL,
`timestamp` int(11) unsigned NOT NULL,
`job_title` varchar(30) DEFAULT NULL,
`dept` varchar(50) DEFAULT NULL,
`phone` varchar(11) DEFAULT NULL,
`lastLoginDate` datetime DEFAULT NULL ON UPDATE CURRENT_TIMESTAMP, // <-- here
PRIMARY KEY (`username`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
I will have to ask another question on how to remove this trigger.

PDO update query runs changes no rows. No errors

So I'm running a PDO update working, and for some reason it won't update the table...
$business_id = 9874128;
$hidden = 1;
$query = "UPDATE business_property_overrides SET hidden=? WHERE business_id=?";
try {
$stmt = $pdo->prepare($query);
$stmt->execute(array($business_id, $hidden));
}
For some reason this won't update, even though I get no errors. The existing tables schema looks like this, and the data is:
There is an existing data set with business_id = 9874128 and hidden set to 0, but it won't update when I run the above code.
CREATE TABLE `business_property_overrides` (
`business_id` int(11) NOT NULL,
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(512) NOT NULL,
`apt_type` varchar(25) DEFAULT NULL,
`apt_num` varchar(9) DEFAULT NULL,
`street_address` varchar(255) DEFAULT NULL,
`city` varchar(255) DEFAULT NULL,
`state` varchar(255) DEFAULT NULL,
`zip` varchar(25) DEFAULT NULL,
`phone` varchar(11) DEFAULT NULL,
`url` varchar(512) DEFAULT NULL,
`hours` varchar(100) DEFAULT NULL,
`openhours` varchar(100) DEFAULT NULL,
`location` point DEFAULT NULL,
`yelp` varchar(512) DEFAULT '0',
`twitter` varchar(512) DEFAULT '0',
`hidden` tinyint(1) DEFAULT '0',
`merged` int(11) DEFAULT NULL,
`closed` tinyint(1) DEFAULT '0',
PRIMARY KEY (`id`),
UNIQUE KEY `business_id` (`business_id`),
UNIQUE KEY `id` (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=9874134 DEFAULT CHARSET=utf8;
The hidden is TINYINT 1 characters long, you are assigning it business_id which is 7 characters long, that is the error.
Change
$stmt->execute(array($business_id, $hidden));
To:
$stmt->execute(array($hidden,$business_id))
As I've already commented over here, or you can simply use the placeholders of taking no care about the occurence like as
$query = "UPDATE business_property_overrides SET hidden = :hidden WHERE business_id = :business_id";
try {
$stmt = $pdo->prepare($query);
$stmt->execute(array(":business_id" => $business_id, ":hidden" => $hidden));
}

How to write nested query MySQL PHP

I'm developing a page to edit board meetings and I want to display all board members who did not attend specific meeting as a checkox located below who attend as an edit in case of user want to add more so I did this:
My code:
$q = "SELECT * FROM `boardteam`";
$r = mysql_query($q);
while ($dbfield = mysql_fetch_assoc($r))
{
$member_id =$dbfield['nationalID'];
$query = "SELECT `attendance` FROM `meetingattendance` WHERE `meetingID` = '$mid' AND `attendance`!= '$member_id'";
$res = mysql_query($query);
if ($res)
{
$tname ="";
switch ($dbfield['titleName'])
{
case "Dr":
$tname .= "د.";
break;
case "Ms":
$tname .= "السيدة.";
break;
case "Mr":
$tname .= "السيد.";
break;
}
$At .= "<input type='checkbox' name='moreAttendence[]' dir='rtl' value=".$dbfield['nationalID']."><div class='styled-checkbox'>".$tname." ".$dbfield['fName']." ".$dbfield['sName']." ".$dbfield['lName']."</div><br>";
}
}
DB:
CREATE TABLE `boardteam` (
`nationalID` int(10) NOT NULL,
`titleName` char(2) NOT NULL,
`fName` char(20) NOT NULL,
`sName` char(20) NOT NULL,
`lName` char(20) NOT NULL,
`gender` char(1) NOT NULL,
`birthDate` date DEFAULT NULL,
`materialStatus` char(15) DEFAULT NULL,
`jobTitle` varchar(100) NOT NULL,
`jobLocation` varchar(20) DEFAULT NULL,
`employer` varchar(100) DEFAULT NULL,
`email` varchar(100) NOT NULL,
`photo` varchar(255) DEFAULT NULL,
`academicGrade` char(15) DEFAULT NULL,
`employmentStartDate` date NOT NULL,
`employmentEndDate` date NOT NULL,
`employmentType` char(20) DEFAULT NULL,
`employmentStatus` char(15) DEFAULT NULL,
`jobStartDate` date DEFAULT NULL,
`jobNumber` int(10) DEFAULT NULL,
`cv` varchar(255) DEFAULT NULL,
PRIMARY KEY (`nationalID`)
)
CREATE TABLE `meetingattendance` (
`meetingID` int(11) NOT NULL,
`attendance` int(10) DEFAULT NULL,
`absence` int(10) DEFAULT NULL,
`reason` varchar(255) DEFAULT NULL,
`additionalAttendance` varchar(255) DEFAULT NULL,
KEY `absence` (`absence`),
KEY `meeingID` (`meetingID`),
KEY `attendance` (`attendance`),
CONSTRAINT `meetingattendane_ibfk_1` FOREIGN KEY (`meetingID`) REFERENCES `boardmeetings` (`meetingID`),
CONSTRAINT `meetingattendane_ibfk_2` FOREIGN KEY (`attendance`) REFERENCES `boardteam` (`nationalID`),
CONSTRAINT `meetingattendane_ibfk_3` FOREIGN KEY (`absence`) REFERENCES `boardteam` (`nationalID`)
)
With my code I got all board members including who attend, How to fix that ??
You need to use a LEFT JOIN in order to find people in the boardTeam who were not in a specific meeting. eg:
SELECT b.*, m.attendance
FROM boardTeam b
LEFT JOIN meetingattendance m
ON b.nationalID = m.attendance AND m.meetingID = $mid
WHERE m.meetingID IS NULL
If you want to get ALL board members, and then determine within PHP if they attended the meeting or not, simply remove the m.attendance IS NULL clause, as such:
SELECT b.*, m.attendance as attendance
FROM boardTeam b
LEFT JOIN meetingattendance m
ON b.nationalID = m.attendance AND m.meetingID = $mid
and now when you loop through the response rows in php, you can test as such (assuming you fetch your rows one by one into a $row variable):
if($row['attendance'] != null)
{
// attended meeting
}
else
{
// did not attend meeting
}
Also, as mentioned in the comments, use mysqli, or pdo instead of pure mysql_ functions
Example fiddle here: http://sqlfiddle.com/#!9/ba7d4/6

Recipe Finder with PHP and MySQL based on Ingredients

I am developing a cooking recipe-website and i want to create a recipe finder based on the used incredients.
My current finder only works with 3 ingredients right.
The Finder should return the right recipe(s) based on the used incredients (should work with 1-n*)
My Tables:
CREATE TABLE IF NOT EXISTS `INGREDIENTS` (
`ingredients_id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(45) NOT NULL,
PRIMARY KEY (`ingredients_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=17 ;
CREATE TABLE IF NOT EXISTS `INGREDIENTS_POS` (
`ingredients_pos_id` int(11) NOT NULL AUTO_INCREMENT,
`ingredients_id` int(11) NOT NULL,
`ingredients_unit` varchar(20) NOT NULL,
PRIMARY KEY (`ingredients_pos_id`),
KEY `ingredients_detail_fk` (`ingredients_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=17 ;
CREATE TABLE IF NOT EXISTS `RECIPES` (
`recipes_id` int(11) NOT NULL AUTO_INCREMENT,
`title` varchar(50) COLLATE utf8_bin NOT NULL,
`text` varchar(2000) COLLATE utf8_bin NOT NULL,
`count_persons` int(11) NOT NULL,
`duration` int(11) NOT NULL,
`user_id` int(11) NOT NULL,
`date` datetime NOT NULL,
`accepted` int(11) NOT NULL DEFAULT '0',
PRIMARY KEY (`recipes_id`),
KEY `recipes_user_fk` (`user_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin AUTO_INCREMENT=88 ;
CREATE TABLE IF NOT EXISTS `RECIPES_POS` (
`recipes_pos_id` int(11) NOT NULL AUTO_INCREMENT,
`recipes_id` int(11) NOT NULL,
`ingredients_id` int(11) NOT NULL,
`ingredients_value` int(11) NOT NULL,
PRIMARY KEY (`recipes_pos_id`),
KEY `recipe_pos_rec_id` (`recipes_id`),
KEY `recipes_pos_ingredient_fk` (`ingredients_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=58 ;
My buggy Solution (doesn't support count from 1-n):
<?php
include 'db_connect.php';
$q = urldecode(mysql_real_escape_string($_GET['q']));
$parameter = explode ('$',$q);
$var = 0;
//print_r($parameter);
foreach($parameter as $ing)
{
//echo $ing;
$sql = "SELECT ingredients_id FROM INGREDIENTS WHERE name='".$ing."'";
$result = mysql_query($sql,$db) or exit('{"Data":null,"Message":null,"Code":500}');
$row = mysql_fetch_array($result);
$arr_id[$var] = $row['ingredients_id'];
$var++;
}
//print_r($arr_id);
$sql = "SELECT r.recipes_id FROM RECIPES r, RECIPES_POS rp WHERE r.recipes_id = rp.recipes_id ";
foreach($arr_id as $id)
{
$sql .= "AND rp.ingredients_id =".$id . " ";
}
//echo $sql;
$result = mysql_query($sql,$db) or exit('{"Data":null,"Message":null,"Code":500}');
mysql_close($db);
$rec;
while($row = mysql_fetch_array($result))
{
//echo "test";
$_GET['id'] = $row['recipes_id'];
$rec= include('get_recipe_byID.php');
}
//print_r(mysql_fetch_array($result));
if (count($arr_id) == 0)
{
echo '{"Data":null,"Message":null,"Code":404}';
die();
}
?>
I need a better solution for that chase.
Maybe SQL itself will help me to find the right recipes
thx
That query helped me a lot:
select r.recipes_id
from RECIPES r
inner join RECIPES_POS rp on r.recipes_id = rp.recipes_id
where rp.ingredients_id in (4, 6)
group by r.recipes_id
having count(distinct rp.ingredients_id) = 2

id not changing correctly

If I register a user using this table:
CREATE TABLE IF NOT EXISTS `users`
(
`id` INT(11) NOT NULL AUTO_INCREMENT,
`md5_id` VARCHAR(200) NOT NULL,
`full_name` TINYTEXT CHARACTER SET latin1 COLLATE latin1_general_ci
NOT NULL,
`user_name` VARCHAR(10) NOT NULL,
`user_email` VARCHAR(30) NOT NULL,
`user_level` TINYINT(4) NOT NULL DEFAULT '1',
`pwd` VARCHAR(220) NOT NULL,
`nationality` VARCHAR(30) NOT NULL,
`department` VARCHAR(20) NOT NULL,
`birthday` DATE NOT NULL,
`date` DATE NOT NULL DEFAULT '0000-00-00',
`users_ip` VARCHAR(200) NOT NULL,
`activation_code` INT(10) NOT NULL DEFAULT '0',
`banned` INT(1) NOT NULL,
`ckey` VARCHAR(200) NOT NULL,
`ctime` VARCHAR(220) NOT NULL,
`approved` INT(1) NOT NULL DEFAULT '1',
PRIMARY KEY (`id`)
)
ENGINE=INNODB
DEFAULT CHARSET=latin1
AUTO_INCREMENT=3;
and then once logged in to 'myaccount.php' use this code to enter values into another table, the language table:
if (empty($_SESSION['$user_id'])) { // user not logged in; redirect to somewhere else }
if (!empty($_POST['doLanguage']) && $_POST['doLanguage'] == 'Submit') {
$result = mysql_query("SELECT `id` FROM users WHERE `banned` = '0' order by id desc");
list($id) = mysql_fetch_row($result);
session_start();
$_SESSION['user_id'] = $id;
foreach ($_POST as $key => $value) if (empty($err)) {
for ($i = 0;$i < count($_POST["other"]);$i++) {
$native = mysql_real_escape_string($_POST['native'][$i]);
$other = mysql_real_escape_string($_POST['other'][$i]);
$other_list = mysql_real_escape_string($_POST['other_list'][$i]);
$other_read = mysql_real_escape_string($_POST['other_read'][$i]);
$other_spokint = mysql_real_escape_string($_POST['other_spokint'][$i]);
$other_spokprod = mysql_real_escape_string($_POST['other_spokprod'][$i]);
$other_writ = mysql_real_escape_string($_POST['other_writ'][$i]);
$sql_insert = "INSERT into `language`
(`user_id`,`native`,`other`,`other_list`,`other_read`, `other_spokint`
,`other_spokprod`,`other_writ` )
VALUES
('$id','$native','$other','$other_list','$other_read','$other_spokint',
'$other_spokprod','$other_writ') ";
mysql_query($sql_insert, $link) or die("Insertion Failed:" . mysql_error());
}
header("Location: myaccount.php?id=' . $_SESSION[user_id] .'");
exit();
}
}
}
All is fine until , for example I register id=3 (in users table) and then log back into id=1 and change their details in the language table, then their user_id in the language table (which is foreign key to id in users table) is 3 when it should be 1. To make things simple, the id in users table should be same as the user_id in the language table. But when going back and changing data in the languages table the user_id stays the same as the last id that registered!
Please help!
This query you have:
$result = mysql_query("SELECT `id` FROM users WHERE `banned` = '0' order by id desc");
What is the purpose of it? You are assigning to $id the first value it finds, yet the query doesn't look for user name or anything else. You probably want to user $_SESSION['$user_id'] instead of $id as your user's ID.

Categories