Okay so I have an ajax request that leads to a file called inc/ajax/del_images.php which delete's the image a user selected to delete
Edit_post.php:
<form class="form-control" action="" autocomplete="off" method="post" enctype="multipart/form-data">
<img id="img" src="some url from database">
<button id="delete-img" data-id="W12kwd2">Delete img</button>
<img id="img" src="some url from database">
<button id="delete-img" data-id="T93pm3P">Delete img</button>
</form>
data-id is the id of the img in the database table
Also images and buttons and gen from php which i didnt include as it adds no value to post
Ajax on edit_post:
$("#delete-img").on('click', function() {
$.ajax({
url: 'inc/ajax/del_images.php',
type: "POST",
data: {
img_id: $(this).attr("data-id")
},
cache: false,
success: function(result){
console.log(result);
}
});
)};
Then in del_images.php:
session_start();
if(isset($_POST['img_id'])){
//image id
$iid = $_POST['img_id'];
//let's check if this image id is valid/in the database
require("conn_user.php");
$stmt = $conn->prepare("SELECT * FROM `images` WHERE `ID` = ?");
$stmt->bind_param("s", $iid);
$stmt->execute();
$stmt_results = $stmt->get_result(); // get result
$row_get = $stmt_results->fetch_assoc();
if($stmt_results->num_rows > 0){
//img with the id was found
//now check if the current user is the owner of post with post[ID] related to the image[ID]
$stmt = $conn->prepare("SELECT * FROM `posts` WHERE `ID` = ?");
$stmt->bind_param("s", $row_get['post_id']);
$stmt->execute();
$stmt_results = $stmt->get_result(); // get result
$row_get_post = $stmt_results->fetch_assoc();
if($stmt_results->num_rows > 0){
//post was found lets check $_SESSION with poster id(in DB)
if($_SESSION['uid'] == $row_get_post['poster_id']){
//this means the current user is the owner of post aswell as the image
//now delete the image cuz the user is the owner which means its safe
$stmt = $conn->prepare("DELETE FROM `images` WHERE ID = ?");
$stmt->bind_param("s", $iid);
$stmt->execute();
$delete_results = $stmt->store_results(); // get result
if($delete_results->affected_rows == 1){
//image was deleted return info so page
print_r('image deleted!');
}else{
print_r('image could not be deleted!');
}
}else{
//id didnt match prop a hacker so force kick and admin review
//code removed for this post
}
}else{ //post not found this will never happen but if it does just add error output }
}else{
//img not found please tell the user
//this code was removed for simplicity of the post
}
}
MY DATABASES :
images table
| ID | post_ID | url |
| :--------:| :--------:|:--------:|
| W12kwd2 | 1 | mNDNJD3324kmWD382n3r.png |
| T93pm3P | 1 | In3u2n329dnjJDEJKDde.jpg |
| Wo90dmp | 2 | JNMduwio3232ndsakdew.jpeg|
posts table
| ID | post_title | poster_id |
| :--------: | :--------: |:--------: |
| 1| What a title | 1 |
| 2| Can you code?| 1|
| 3| Ajax, why and how | 4 |
MY ISSUE :
The issue
So another user can't delete another users image cuz i am check that they are the owner of the post of which the image is related too but lets say the user is busy editing post 1 the edit post url will look like this edit_post?post_id=1 which is fine but the user can in the buttons data-id insert the id of images related to post ID 2 and delete them cuz he is the owner of post ID 2 aswell(you can see it from db example) now first i think lets just get the id from the url but any idiot who knows how frontend works will be able to check the js to just insert the value they want for the url id= so how can i limit this so that a user can only delete the images of the post that they are currently editing without having to work with a frontend supply id
i tough maybe to use a $_SESSION['current_edit'] = "current id of post which they clicked edit on" but the issue leads what is they have multi tabs cuz they editing more that one post I know i need to work with some type of supplied id but how can i lock it down so that users can't delete images of other posts they own while editing another post.
FOOTER NOTE*
if I need to supply more info and edit the post to be more clear of more specific please tell me and i will do it as i know StackOverflow is a clean and well maintained site ~ Have a great day :)
delete image from folder PHP
This post may help you.
What you need to do.
query the id from database with ajax
then fetch the url column.
Delete the file by unlinking the url line you called to whatever your file system is.
That's all the process.
Related
I'm using OctoberCMS based on Laravel, with the official User plugin.
I'm making a gallery where frontend users can upload files.
The user is the owner of their uploaded file and is the only one that has permission to edit.
My question, is this the correct way to design and handle user record ownership? All user upload records will be mixed together in one database table mysite_gallery_ and will be sorted and displayed in html with filters, such as viewing all uploads by a specific username.
Will this be slow? Should each user have their own table? Will it be secure enough to prevent another user, bot, or hack script from editing a file record they don't own?
MySQL Table
All upload records are saved to the table mysite_gallery_.
| id | username | filename | slug | title | tags |
| ---- | ---------- | ---------- | -------- | --------- | -------------------- |
| 1 | matt | xyz123 | xyz123 | My File | space, galaxy, stars |
Record Ownership
At upload, my custom Upload component uses Laravel to create a record in the database of the file's title, slug, tags, etc.
To define ownership I have the Upload component save the user's username to the record.
# Get Current User
$user = '';
if (Auth::check()) {
$user = Auth::getUser();
$user = $user->username;
}
# Create Record
$gallery = new Gallery();
$gallery->username = $user;
$gallery->filename = $name;
$gallery->title = $title;
$gallery->slug = $slug;
$gallery->tags = $tags;
$gallery->save();
Edit Record
If the user wants to edit the file properties, such as title, Laravel checks if current user matches the username in the record. If user is owner, it allows edit.
# Get File Record Owner
$owner = '';
if (Gallery::where('filename', '=', $filename)->exists()) {
$record = Gallery::where('filename', '=', $filename)->first();
$owner = $record->username;
}
# Authenticate Current User is Owner
$is_owner = false;
if (Auth::check()) {
# Get Current User
$user = Auth::getUser();
# Check if User is Owner
if ($user->username == $owner) {
$is_owner = true;
}
}
# Edit Record
if ($is_owner == true) {
# Update Record
Gallery::where('filename', '=', $filename)->update(['title' => $title]);
return Redirect::back();
}
It is a better idea to use the users id instead of the username. It'll take less space in the database and is also faster.
Also I would put the tags in another table. Although this depends on how you use the tags. If you have them in another table then it would be easier to get all the uploads for a tag for example.
I am trying to display records of a particular job that has already been done by someone else before a new provider sees it. If the status is open, there should not be any information to be displayed as supposedly, no one has made any report about it. If the status is awarded, then necessary data should be displayed. Right now, the information to be shown are viewable. The problem the data is displayed in every job post even it is not the report for such a job.
Example,
Job ID | Title | Description | Subject | Job Status
2 | Math Tutor | I need Math tutor! I need Math tuto... | Mathematics | Open
1 | English Tutor | Edited... | French | Awarded
If I click "Open", I should not be able to see any record because it is still not done. If I click "Awarded", I should see details about the job. Right now, the data is showing properly for JOB ID 1 which was already awarded. However, the same data is shown as well in JOB ID 2.
How do I properly display the data in its proper place? I've been trying everything to do it. I included the JOB ID to be displayed to see if there's something wrong with it. But there's none, it shows JOB ID 1 in both jobs 1 and 2. How do I display it just in job 1 where it belongs?
Here's my code in controller:
public function view_tutors_tutorials()
{
$this->validateRole('provider');
$this->load->model('tutorial_model');
$this->load->model('auth_model');
$data['subject_list'] = $this->array_to_select( $this->tutorial_model->get_all_subjects(), 'id','name');
$my_preference = $this->tutorial_model->get_tutors_tutorials(isset($_GET['subject_id'])?$_GET['subject_id']:'0', isset($_GET['sort_by'])?$_GET['sort_by']:'');
$data['my_preference'] = $my_preference;
$this->load->view('provider/view_tutors_tutorials', $data);
}
and this in my model:
public function get_tutors_tutorials($subject_id = NULL, $sort_by = NULL)
{
//responsible for displaying job contracts for provider user.
$this->db->select('tutorial.status as status, tutorial.client_id as client_id, tutorial.id as tutorial_id, subject.name as name, tutorial.title as title, tutorial.description as description, tutorial.start_date as start_date, tutorial.update_date_time as update_date_time,tutorial_proposal.provider_id as provider_id,provider.first_name as first_name,provider.last_name as last_name,tutorial.contract_status as contract_status,tutorial.provider_feedback as provider_feedback,tutorial.client_notetoself as client_notetoself,tutorial.client_feedback as client_feedback,tutorial.provider_notetoself as provider_notetoself,tutorial.material_used,tutorial.recommendation')->from('tutorial');
$this->db->join('subject', 'subject.id = tutorial.subject_id');
$this->db->join('tutorial_proposal', 'tutorial_proposal.provider_id = tutorial.provider_id');
$this->db->join('provider', 'provider.id = tutorial_proposal.provider_id');
$this->db->where('tutorial.status', 'Awarded');
if ( ! empty($subject_id) )
{
$this->db->where('subject_id', $subject_id);
}
//if there's no sort selection made, the jobs will be sorted from newest to oldest
if ( empty($sort_by))
{
$sort_by = "update_date_time desc";
}
$this->db->order_by($sort_by);
$query = $this->db->get();
return $query->result_array();
}
I look forward to getting any help.
You need to remove where condition for status in you model's query :
$this->db->where('tutorial.status', 'Awarded'); // this should be removed
Also make sure, your subject_id passed properly.
Firstly, I havent been able to find anything useful on the subject, anywhere really.
I'm trying to make something somewhat simular to a forum,
A small explanation,
(And yes, I know its not seo, but I'm only looking for functionality atm.)
Lets say you go to example.com/?1, Then the database entry with the ID of 1 would be displayed on the index page, If you go to example.com/?3 then the DB entry with the ID of 3 would be displayed, etc..
DB Structure
----------------------------------------
| id | label | description | parent_id |
|---------------------------------------
| 1 | General | NULL | 0 |
| 2 | Public | NULL | 1 |
| 3 | Private | NULL | 1 |
----------------------------------------
PHP Code
if ($stmt = $mysqli->prepare("SELECT id, label, description, parent_id FROM categories")) {
$stmt->execute(); // Execute the query.
$stmt->store_result();
$stmt->bind_result($id, $label, $desc, $parent); // Get variables from result.
while ($stmt->fetch()) {
if(isset($id)) {
echo "Hello, This is the $label category";
}
}
}
What i'm missing is a way to get the users current "isset" (.com/?10, .com/?5, ETC) Before the query is run so i can check for that isset in the DB and get the correct values, right now it's outputting all rows in the DB, I would highly appreciate any help with it :)
If you know of a better way of doing something like this(without using a framework), please let me know!
From a terminology standpoint, it sounds like you are interested in understand what parameters are passed in the request's query string.
In your case, you are doing something a little weird in that be having URI format like /?* where * is integer ID value, you would actually be passing a variably named parameter. Since you don't know what the parameter name is, you would have to do something like
$ids_in_query_string = array_keys($_GET);
To store the key names which infer which ID(s) were requested.
What I would suggest is to form your query string like /?id=*, that way you always know which key in $_GET to check against. For example:
$id = null;
if (!empty($_GET['id']) && is_numeric($_GET['id'])) {
$id = $_GET['id'];
}
if (!is_null($id)) {
// perform your query for selected ID
} else {
// do something else
}
I'm still new to PHP and MySQL. I'm currently working on a random quote generator website. When a user visits for the first time or refreshes the page, the PHP code fetches a random row from the MySQL table and echos the results.
If a user likes a particular quote, I want him/her to be able to bookmark the page the quote is contained in. I believe this requires a unique URL for each random code that is generated. I can't figure out how to do this with the code I currently have and would like anyone's help.
This is my table so far:
+----+-----------+-----------+
| id | quote | source |
+----+-----------+-----------+
| 1 | hello | test1 |
| 2 | world | test2 |
| 3 | random | test3 |
+----+-----------+-----------+
This is my code so far:
<?php
require('connection.php');
// Last query result stored in sessions superglobal to avoid immediately repeating a random quote
session_start();
if (empty($_SESSION['lastresult'])) {
$_SESSION['lastresult'] = null;
}
$query = "SELECT * FROM `test` WHERE `id` != '%s' ORDER BY RAND() LIMIT 1";
$query = sprintf($query, mysql_real_escape_string($_SESSION['lastresult']));
$result = mysqli_query($dbc, $query) or die(mysql_error());
if (mysqli_num_rows($result) == 1) {
while ($row = mysqli_fetch_array($result, MYSQLI_ASSOC)) {
$_SESSION['lastresult'] = $row['id'];
echo '<p>' . $row['quote'] . '</p>' . '<p>' . $row['source'] . '</p>';
}
} else {
echo '<p>Sorry, there was an error. Please try again by refreshing the page or clicking the query button.</p>';
}
?>
Any other code advice would also be appreciated.
There are three ways that spring to mind.
All require you to implement a version if the page that takes a quote id, similar to the one #DanGoodspeed suggests in his comment against your question.
Add a link from you existing page to the new id driven page with a label 'bookmark this page to return'. Not ideal, but very simple.
Add some JavaScript in your existing page to update the URL after loading to include the id, therefore making it appear as if it was the other. See this answer Modify the URL without reloading the page for details.
Instead of using the page you have now, generate a new page (using much of what you have already written) that returns a location redirect header with a URL that has a random id in it.
I am stuck on how to create tags for each post on my site. I am not sure how to add the tags into database.
Currently...
I have 3 tables:
+---------------------+ +--------------------+ +---------------------+
| Tags | | Posting | | PostingTags |
+---------------------+ +--------------------+ +---------------------+
| + TagID | | + posting_id | | + posting_id |
+---------------------+ +--------------------+ +---------------------+
| + TagName | | + title | | + tagid |
+---------------------+ +--------------------+ +---------------------+
The Tags table is just the name of the tags(ex: 1 PHP, 2 MySQL,3 HTML)
The posting (ex: 1 What is PHP?, 2 What is CSS?, 3 What is HTML?)
The postingtags shows the relation between posting and tags.
When users type a posting, I insert the data into the "posting" table. It automatically inserts the posting_id for each post(posting_id is a primary key).
$title = mysqli_real_escape_string($dbc, trim($_POST['title']));
$query4 = "INSERT INTO posting (title) VALUES ('$title')";
mysqli_query($dbc, $query4);
HOWEVER, how do I insert the tags for each post?
When users are filling out the form, there is a checkbox area for all the tags available and they check off whatever tags they want. (I am not doing where users type in the tags they want just yet)
This shows each tag with a checkbox. When users check off each tag, it gets stored in an array called "postingtag[]".
<label class="styled">Select Tags:</label>
<?php
$dbc = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME);
$query5 = "SELECT * FROM tags ORDER BY tagname";
$data5 = mysqli_query($dbc, $query5);
while ($row5 = mysqli_fetch_array($data5)) {
echo '<li><input type="checkbox" name="postingtag[]"
value="'.$row5['tagname'].'" ">'.$row5['tagname'].'</li>';
}
?>
My question is how do I insert the tags in the array ("postingtag") into my "postingtags" table?
Should I...
$postingtag = $_POST["postingtag"];
foreach($postingtag as $value){
$query5 = "INSERT INTO postingtags (posting_id, tagID)
VALUES (____, $value)";
mysqli_query($dbc, $query5);
}
1.In this query, how do I get the posting_id value of the post?
I am stuck on the logic here, so if someone can help me explain the next step, I would appreciate it!
Is there an easier way to insert tags?
PostingTags is a Many-To-Many mapping table. You are correct in your assessment of the data you need, but I don't see how we can help you find it.
1.In this query, how do I get the posting_id value of the post?
Does your application not know this when the user is selecting tags? You're going to need to know what post is actually being edited before you can assign tags to it. Is this a completely separate page where the user is picking tags? If it is, you'll need to create a hidden field in your webform that passes the posting_id from one page to the next.
Otherwise, it just becomes an issue of determining the last primary key used when you inserted into the postings table. For that, you need to call mysqli::insert_id like this:
//This is the first snippet of code you posted
$title = mysqli_real_escape_string($dbc, trim($_POST['title']));
$query4 = "INSERT INTO posting (title) VALUES ('$title')";
mysqli_query($dbc, $query4);
$posting_id = $dbc->insert_id;
I am stuck on the logic here, so if someone can help me explain the next step, I would appreciate it!
Do you understand now?
Is there an easier way to insert tags?
Not if you want your users to be able to insert an arbitrary number of tags to a post.
My question is how do I insert the tags in the array ("postingtag") into my "postingtags" table?
Your code does the job fine, though I would be doing everything as prepared statements. Prepared statements prevent SQL injection attacks so that you don't have to remember to escape everything that goes into the query. It's also a much less verbose way of doing things:
//This is the last snippet of code you posted
//Populate postid as specified in the first part of this answer.
$dbc = mysqli_connect(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME);
foreach($postingtag as $tag) {
$sql = 'INSERT INTO postingtags (posting_id, tagID) VALUES (?, ?);';
$insertStatement = $dbc->prepare($sql);
$insertStatement->bind_param('ii', $postid, $tag);
$insertStatement->execute();
}