Retrieving all titles for each category using php - php

Please can anyone suggest how I can go about achieving this in php I have two tables categories and article. The categories table has two fields id and names
article table contains id category_id title. One category can be tie to many article title in the article table. Please how can I retrieve all titles belonging to each categories in my article table without using the get variable.
The below code is retrieving just each categories but not pulling the article titles for each
Categories Class
public static function find_all_categoryid() {
return self::find_by_sql("SELECT a.title, b.names, b.id FROM article a LEFT OUTER JOIN article_categories b ON a.category_id=b.id GROUP BY a.category_id");
}
Index Page
<?php $cats = Categories::find_all_categoryid(); ?>
<?php foreach($cats as $cat): ?>
<h4><?php echo $cat->names; ?></h4>
<p><?php echo $cat->title; ?></p>
<?php endforeach; ?>
can anyone please assist. Thank you

Related

Table with INNER JOIN, how to update

I have two tables for Categories and Subcategories.
Categories has (categorie_id and categories_name) columns;
SubCategories has (subCategorie_id, subCategorie_display, categorie_id, subCategory_name) columns.
I did a LEFT OUTER JOIN query to obtain all the records in Subcategories, and match the ones that have the same categorie_id. Here is my code:
("SELECT subCategorie_id, subCategorie_name, subCategorie_display, categories.categorie_name, subCategories.categorie_id
FROM subCategories
LEFT OUTER JOIN categories ON categories.categorie_id = subCategories.categorie_id");
Now i have a form in which the content is displayed. I wan't to be able to edit that form, and update the table with the updated content. This is my query:
("UPDATE subCategories
LEFT OUTER JOIN categories
ON categories.categorie_id = subCategories.categorie_id
SET subCategorie_display='$display', subCategories.categorie_id='$catID',subCategorie_name='$name'
WHERE subCategorie_id='$id'")
What i get from this query is a new row with the correct content, but the one i wanted to edit, stays like it was.
Here is my HTML:
<select id="choosecat" name="choosecat" required>
<?php foreach($categoriesAll as $categorie) {
if($subcat->categorie_id == $categorie->categorie_id) { ?>
<option selected value="<?php echo $categorie->categorie_id; ?>"><?php echo $categorie->categorie_name; ?></option>
<?php } else { ?>
<option value="<?php echo $categorie->categorie_id; ?>"><?php echo $categorie->categorie_name; ?></option>
<?php } }?>
</select>
How can i fix this?
Already searched other answers but none worked.
Ok, so i found the bug.
The problem was in my form action, the link was calling a wrong id.

Displaying a User's Posts by Category

Afternoon All,
Looking for some direction with listing posts by category.
I have begun coding a CMS (as a PHP beginner) and up until now all was going well.
I have made a link to pre-set categories (Category 1, Category 2 etc etc)
I also have a categories table with ID and Category name.
A table for users posts with CatID and category name in it as well
I'm guessing I would need to join tables to be able to list any posts in specific category (Select Cat 1 to see all Cat 1 posts. Same for Cat 2, 3 etc etc)
When a user adds a post it fills the category name in users posts table but I get no CAT ID and nothing added into categories table so how do i call on this to display categorised posts?
I have a feeling I am probably thinking to much into things and over-complicating what should probably be simple to do.
Ihe code i have at the moment (see below) has no effect at all?
Please help point me in the right direction, I have tried everything.
Many thanks to all in advance
CODE:
$catSql ="SELECT ID, Category
FROM categories
LEFT JOIN users_posts
ON CatID, category, BlogID";
$catQry = mysqli_query($link, $catSql);
while ($row = mysqli_fetch_assoc($catQry)){
if($row['category_name'] != $lastCategory)
{
$lastCategory = $row['category'];
echo "<br /><strong>$lastCategory</strong>";
}
echo $row['category'] . ' <br />';
}
Your SQL is wrong I think this should work
$catSql = "SELECT *
FROM categories
LEFT JOIN users_posts
ON categories.ID = users_posts.CatID";
Your SQL for listing posts could check to see if a categoryID exists in the URL, and if it does, use it to filter the results.. Then, you would just need to create some links to the same page to add the required category id to the URL.
<a href='?cat=1'>Cat 1</a> | <a href='?cat=2'>Cat 2</a> | etc..
SQL
$sql = "SELECT * FROM POSTS";
if(isset($_GET['cat'])){
$catID = (int)$_GET['cat']; //or something similar
$sql .= " LEFT JOIN category USING categoryID WHERE categoryID = $catID";
}

Php SQL inner join?

So I'm making a portfolio website where I can post and edit blogs.
I'm making the blog edit page and I'm having trouble with combining two table together.
The first table is for the blogs and the second table holds all the different blog categories.
Here's how I'm getting the blog posts:
$qStr = "SELECT post_title, post_content, post_description, post_active, category_id FROM posts WHERE post_id = {$post_id}";
Here's how I'm getting the blog categories:
$qStr = "SELECT category_name FROM categories WHERE category_id = {$category_id}";
So in my edit blog post page I have a dropdown box that I need to show which category that blog post is in, and be able to change it. I have a category_id in my blog table. My question is how do I get the dropdown to show which category the post is under?
Right now my drop down code looks like this (note: Right now I'm just populating the dropdown with all the categories)
<div class="form-group">
<label for="categorySelect" class="col-lg-2 control-label">Category</label>
<div class="col-lg-3">
<select class="form-control" id="categorySelect">
<?php
foreach ($categories as $cat) {
echo("<option>{$cat['category_name']}</option>");
}
?>
</select>
</div>
</div>
You need to set up the selected attribute for select (option) element, something like this:
<?php
foreach ($categories as $cat) {
if ($cat['category_name'] == $category_of_your_post)
echo "<option selected=\"selected\">{$cat['category_name']}</option>";
else
echo "<option>{$cat['category_name']}</option>";
}
?>
BTW, I think that you have the wrong queries (if I understood correctly your question). Basically you need to retrieve the category_id of your post and perform an equality question against the array of categories:
$qStrBlog = "SELECT post_title, post_content, post_description, post_active, category_id FROM posts WHERE post_id = {$post_id}";
$qStrCat = "SELECT category_id, category_name FROM categories";
And then:
<?php
foreach ($categories as $cat) {
if ($cat['category_id'] == $blog_data['category_id'])
echo "<option selected=\"selected\">{$cat['category_name']}</option>";
else
echo "<option>{$cat['category_name']}</option>";
}
?>
You have two options:
Add a selected attribute with an if-condition in the foreach loop:
foreach ($categories as $cat) {
echo '<option';
if ($cat['category_id'] == $post['category_id']) echo ' selected';
echo '>'.$cat['category_name'].'</option>';
}
Or use an INNER JOIN on the post SELECT query:
$qStr = "SELECT p.post_title, p.post_content, p.post_description, p.post_active, p.category_id, c.category_name FROM posts INNER JOIN categories c ON c.category_id = p.category_id WHERE post_id = {$post_id}";
and throw the first option element as the "default currently selected" option:
<select class="form-control" id="categorySelect">
<option value="<?= $post['category_id'] ?>"><?= $post['category_name'] ?> (current)</option>
<?php
foreach ($categories as $cat) {
echo("<option>{$cat['category_name']}</option>");
}
?>
</select>
I've made the assumption that you've correctly loaded your result from the first SELECT query into $post. Note that if it's possible to not set a Category to a Post, you should use LEFT JOIN instead and wrap the first option element output contingent on $post['category_id'] not being empty.

navigation list is duplicating

i was given help previously on how to join multiple tables together to get this navigation list to work, as you can see i have done this, but now i am trying to output the navigation in my list, but it is duplicating the top and bottom categories based on how many products are in those categories: this is previous link that shows my table setup:
Joining 2 tables with foreign key id
Here is my code trying to echo out the navigation correctly.
try
{
$result = $pdo->query('SELECT product.*, bottom_category.bottom_name, top_category.top_name
FROM product
INNER JOIN bottom_category ON bottom_category.id = product.bottom_category_id
INNER JOIN top_category ON top_category.id = bottom_category.top_category_id
ORDER BY top_category.id,bottom_category.id');
} // end try
catch (PDOException $e)
{
echo 'There was a error fetching the products.' . $e->getMessage();
exit();
} // end catch
$products = array();
foreach ($result as $row)
{
$products[] = array('top_name' => $row['top_name'],
'bottom_name' => $row['bottom_name']);
}
?>
<div class="sidebar">
<h4 class="sidebar-header">Select Products</h4>
<form class="nav-search-form">
<input type="search" name="search" placeholder="Search products">
</form>
<nav class="sidebar-links">
<ul>
<li><a id="red" href="/semtronics/index.php">New Products</a></li>
<?php
foreach ($products as $product):
?>
<li><?php echo htmlspecialchars($product['top_name']);?>
<ul>
<li><?php echo htmlspecialchars($product['bottom_name']);?></li>
</ul>
</li>
<?php endforeach; ?>
</ul>
</nav>
</div><!-- sidebar -->
Now it all works the only problem is it is duplicating the navigation list based on how many products are linked to that category.
I think you need another solution for this task.
You don't need product here
Query what you need is:
select bottom_category.name as bottom_name, top_category.name as top_name
from bottom_category
inner join top_category on top_category.id = bottom_category.top_category_id
order by top_category.id, bottom_category.id
I was thinking that you need something from product table in your code, but if no - use SQL query above.
Or you need data from product table ?
If you need from product you can run
select bottom_category.name as bottom_name, top_category.name as top_name
from product
inner join bottom_category on bottom_category.id = product.bottom_category_id
inner join top_category on top_category.id = bottom_category.top_category_id
group by product.bottom_category_id
order by top_category.id, bottom_category.id
But be careful, you don't know which row from product would be used in this case

How to display all comments per article (PHP & SQL)?

So I have two tables, article and comments (which has one-to-many relationship (1 article - many comments)). This is how the table is structured:
Articles - id (prikey), title, publicationDate, content
Comments - com_id (prikey), author, comment, id (foreign key)
I used this to query the two tables:
SELECT * FROM articles as a INNER JOIN comments as c ON a.id = c.id
Previously, I was only displaying the articles table using this:
<?php
while($row = mysqli_fetch_array($query)) {
echo "
<div id='article'>
<header>
<hgroup>
<h2>".$row['title']."</h2>
<h4>Posted on ".$row['publicationDate']."</h4>
</hgroup>
</header><p>".$row['content']."</p></div>";
}
?>
This displays all articles (with date, title, content, etc.). Now there are comments. How do I edit the php code (or if my query is incorrect, how to write the query), so that it shows all articles and all comments per article as in:
Article One
-- Comment 1
-- Comment 2, etc.
Article Two
-- Comment 1
-- Comment 2, etc.
An alternative would be to split the query into two.
The first would bring back the articles you want...
SELECT * FROM article;
Once you have those, you can get all the IDs and use something like the following
SELECT * FROM comments WHERE article_id IN (".$list.");
This restricts the MySQL queries to 2 whilst getting all the data you need. After this loop around the article data, and in that loop, loop around the comments data.
This also means that, unlike using GROUP_CONCAT, you will also have author data to use.
It's not a very eloquent solution, but should work.
Query:
SELECT c.author, c.comment,
a.id article_id, a.title, a.publicationDate, a.content
FROM comments c
RIGHT JOIN articles a
ON c.id = a.id
PHP:
<?php
$lastArticleId = 0;
$isNewArticle = false;
while($row = mysqli_fetch_array($query)) {
$isNewArticle = ($lastArticleId != $row['article_id']) ? true : false;
if($isNewArticle) {
$lastArticleId = $row['article_id']; ?>
<div class="article">
<header>
<hgroup>
<h2><?php echo $row['title']; ?></h2>
<h4>Posted on <?php echo $row['publicationDate']; ?></h4>
</hgroup>
</header>
<p><?php echo $row['content']; ?></p>
</div>
<?php
}
if($row['comment'] != '') { ?>
<p><strong><?php echo $row['author']; ?></strong> - <?php echo $row['comment']; ?></p>
<?php
} ?>
<?php
} ?>
Use something like
SELECT a.article
,GROUP_CONCAT(CONCAT('<p>', c.comment, '</p>') SEPARATOR "\n") as comments
FROM
article a
INNER JOIN comment c ON (c.article_id = a.id)
WHERE a.id = '12454';
You may have to fiddle a bit with the separator.
See: http://dev.mysql.com/doc/refman/5.0/en/group-by-functions.html#function_group-concat
Do note however:
The result is truncated to the maximum length that is given by the group_concat_max_len system variable, which has a default value of 1024. The value can be set higher, although the effective maximum length of the return value is constrained by the value of max_allowed_packet. The syntax to change the value of group_concat_max_len at runtime is as follows, where val is an unsigned integer:
SET [GLOBAL | SESSION] group_concat_max_len = val;
See here how to change max_allowed_packet
http://dev.mysql.com/doc/refman/5.5/en/server-system-variables.html#sysvar_max_allowed_packet
Look into MySQL GROUP_CONCAT which will return a comma delimited list of items. You can then explode that for your comments section.
once a person will comment on a article insert article id with that comment and later get them accordingly something like this
once a person will select an article to read send article id in the $_GET to your article page so you can excess the article id.Once a person will comment on that article insert it as follows
$sql = mysql_query("INSERT INTO comments_table (subject,article_id,comments) VALUES ('$subject','$_GET['id']','$comments')");
and later when you pulling them do it the same way as you have the article id in the $_GET
you can access it run a query like this
$fetch = mysql_query("SELECT * FROM comments WHERE article_id = $_GET['id'] ORDER BY id DESC") or die(mysql_error());
Hope this will work

Categories