What is the simplest way of putting another mysql query inside a where clause in php.
For example I have tried:
$sql = "SELECT app, description FROM all-apps WHERE app!='(SELECT user, app FROM users-apps WHERE user="$user_name")'";
I need to bring up all the apps entries in the database. and then check if the user has the same app name in his list. if so it will not show up.
Basically there are 2 databases one has all apps and the other one has apps which the users have used and I need the query to find all the apps the user has not used.
Please comment bellow if this question is up to standard. Please have an opinion so I can fix on my mistakes in the future.
A few changes needed
"SELECT app, description FROM all-apps WHERE app NOT IN (SELECT app FROM users-apps WHERE user='{$user_name}')";
Note that this and your original query may leave you vulnerable to sql injection. Please use PDO prepared statements.
Thanks, with all of your help I was able to get this query to work:
$sql = "SELECT * FROM all_apps WHERE app NOT IN (SELECT app FROM users_apps WHERE user='{$user_name}') ";
This works by first selecting one table. Then choosing what column you want the WHERE to be. Then put IN if you want it to be in or NOT IN. Then in brackets your second query. Make sure to have it only select the one column. The IN clause also works if there are multiple results.
Related
I have made a makegroup.php site which is supposed to create a group, and put the person in the connection table between UserID and GroupID.
..but I am not sure how to go on. The logged in user is saved in session variable $usid, but how what about GroupID? How do I fetch that right after on another page? Need I make this in steps? Including quick DB scheme.
Thanks in advance.
I guess GrouID is autonumeric?
So you leave db create the id for you.
Also loos like you are trying to concat the $groupname value
$sql = "INSERT INTO group (Groupname) VALUES ('".$groupname."') ";
But you dont want do that because that method is vulnerable to SQL Injection attack
Use parametrized values instead
How can I prevent SQL injection in PHP?
I was running a site I purchased that I thought was fairly unhackable. However, after having an attack, I found it was not. He informed me of the vulnerability, however my question is what user input could have been done to get all the users usernames like he did? Here is the code...
$un=$_GET['username'];
$q=$db->query("SELECT * FROM users WHERE login_name='$un' OR username='$un'");
I realize that this is highley hackable. Therefore, I changed the site over to prepared statements to prevent this from happening again. I just want to know what he could have entered to get all the users usernames.
Someone posted the script on github, you can find it here:
https://github.com/sat312/Mafia-Game-Script/blob/master/checkun.php
' OR 1=1;
In the URL:
/yourScript.php?username=%27%20OR%201%3D1%3B
The idea is that since data is mixed with the command, you can just finish the command with data.
You get $un from the user, so I can type anything I want and it'll get substituted into your query. It's called a SQL Injection attack.
Lets say $un = ' OR 1 = 1;-- then your query becomes:
SELECT * FROM users WHERE login_name='' OR 1 = 1;--' OR username='' OR 1 = 1;--'
What will happen? this gets executed:
SELECT * FROM users WHERE login_name='' OR 1 = 1;
This will return every row in the table.
He may have used the GROUP_CONCAT statement in MySql which basically groups a column in multiple rows into a single row (see Can I concatenate multiple MySQL rows into one field? for more information). He may have terminated the original SQL statement or UNIONED it with his own and added a LIMIT and ORDER BY to ensure his result got returned and commented out the remained of the original statement.
This is one possibility, but there are probably a few others.
I have browser game. There is message send form.
I didn't make real escape string function to the "message_content" variable.
There is any option, that the user could make after the insert of the message, any update ?
I mean that the user could write a sql code in the message_content that can UPDATE values in the sql? Like update users set gold = '9999' where username = 'my_username'
THANKS ALOT....
And that it only a question. Don't worry i already made mysql_real_escape_string...
Please learn about using parametrized queries, preferably with the PDO module, to protect your web app. http://bobby-tables.com/php has examples to get you started.
The mysql_query function doesn't allow the execution of multiple statements at once. So the often mentioned example of Robert'; DROP TABLE Students; -- won’t work.
This also means that the exploitation is restricted to the statement type. So if the injection point is in an INSERT statement, the vulnerability can only be exploited to insert arbitrary values into that specific table.
However, one can still inject arbitrary data from the database into that table. And if the attacker addresses the message to himself, he will be able to read arbitrary data from the database and may also be able to read and write arbitrary files on the server.
If you don't escape the user input the following can happen:
Imagine this query:
SELECT * FROM user WHERE login='$login'
where $loginis the user's input.
Now the user insers the following content in the variable: '; DROP TABLE user; --
The following query will be executed:
SELECT * FROM user WHERE login=''; DROP TABLE user; --'
It's a very generic example, but I hope you get the idea
Suppose the website is written in PHP which disables multiple statements. If the query looks like this:
Select id From TableX Where num = >userInput<
Is it impossible to Update or Delete record by SQL Injection? Is it possible to get the content from another table, like tableB, which may not be union-compatible?
Thanks in advance.
userInput = -1 union select GetCharCode(SomeStringField, CharPosition) from SomeTable where SomeCondition, where GetCharCode returns the code of character in CharPosition of SomeStringField (you need to write some DB-specific code there) will help you to get the value of SomeStringField by looping through possible CharPositions, and thus bypass the problem of tableB not being "union-compatible".
I am curious about questions like "How to inject", "How to break in", "How to steal some info", implying getting step by step instructions - are such questions welcome on this site or not?
Instead of hard coding sql queries like Select * from users where user_id =220202 can these be made dynamic like Select * from $users where $user_id = $input.
Reason i ask is when changes are needed to table/column names i can just update it in one place and don't have to ask developers to go line by line to find all references to update. It is very time consuming. And I do not like the idea of exposing database stuff in the code.
My major concern is load time. Like with dynamic pages, the database has to fetch the page content, same way if queries are dynamic first system has to lookup the references then execute the queries, so does it impact load times?
I am using codeignitor PHP.
If it is possible then the next question is where to store all the references? In the app, in a file, in the DB, and how?
---EDIT:
Even better: Can the SQL query itself be made dynamic? I can just reference $sqlA instead of the whole query? This way if I have to re-write the query I can just update 1 file.
Because you are using Codeigniter, I would reccomend utilizing the Active Record Class to accomplish what you are trying to do.
The active record class enables you to build queries dynamically in steps allowing you to build them logically. So to take your example using active record...
( this could be accomplished with less code, I'm just trying to illustrate Active Record )
$this->db->select('*');
$this->db->from($table);
$this->db->where($user_id, $input);
and so to show what I mean about building the query logically, you can build whatever logic you want INTO the query building process. Lets say you have a $limit variable that you set if you want to limit the number of results you get. BUT if it isn't set (or NULL) you don't want to set the limit clause.
if ( $isset($limit) ) {
$this->db->limit($limit);
}
and now to execute your query now that it has been built
$query = $this->db->get();
Then just deal with $query with your database class just like you would any other CodeIgniter query object.
Of course you can, if that's what you wish. I'd rather recommend you taking more time to design you database but changes in the schema are inevitable in the long run.
I don't think load time would be an issue with this because ussually the bottleneck in this applications is in the database.
Finally my recommendation is to save this in a file just by declaring the column names as php variables
It depends on the database driver(s) you are using. The old PHP database drivers did not support placeholders (PHP 3.x). The modern (PDO) ones do. You write the SQL with question marks:
SELECT * FROM Users WHERE User_ID = ?
You then provide the value of the user ID when you execute the query.
However, you cannot provide the column name like this - only values. But you could prepare a statement from a string such as:
SELECT * FROM Users WHERE $user_id = ?
Then you provide the value at execute time.
mysql_query() takes a string and it doesn't need to be a constant string, it can be a variable.
$SQL = "SELECT foo FROM bar b";
SQLSet = mysql_query($SQL);
Aa you can see, you can use ordinary string manipulation to build your whole SQL query.
$SQL="SELECT * FROM MyTable";
$BuzID = 5;
$Filter = "Buz=".$BuzID;
if (is_numeric($BuzID)) SQL .= " WHERE ".$Filter;
SQLSet = mysql_query($SQL);
This will expand to "SELECT * FROM MyTable WHERE Buz=5" if $BuzID is set to any number.
If not the statement will just be "SELECT * FROM MyTable"
As you can see, you can build very complex SQL statements on the fly without need of variable support in the SQL server.
IF you want constants such as database name, user login, you can but them in a separate include located outside the public directory.
SecretStuff.inc.php
$__DatabaseName = "localhost";
$__UserName = "DatabaseAccess";
$__Password = "E19A4F72B4AA091C6D2";
Or have the whole PHP database connection code in the same file.