have_posts() outputting false on 'single.php' when should be true - php

Hey fellow WordPress dev's / php masters. Long story short, I am using WordPress (and I never use WordPress - sorry!) and when I go to view the individual post rendered from single.php, the 'have_posts()' function is returning false. The template is rendered and I am not having any issues with the template rendering, I am simply having an issue with 'have_posts()' showing false and not outputting the blog post.
I downloaded WordPress 5.0.3, am running on MAMP and have used this method previously without any issues. All in all, I am trying to really keep my template files organized and I am using get_template_part to retrieve sections of the theme.
My current structure is:
single.php -
<?php
get_template_part('template-parts/blog/_single/blog-post-banner'); // Renders perfect
?>
<div class="light-grey">
<div class="container">
<div class="row no-margin">
<div class="col s12 l9 mb-0-l">
<?php get_template_part('template-parts/blog/_single/blog-post'); // Renders perfect ?>
</div>
<div class="col s12 l3 mb-0-l">
<?php get_template_part('template-parts/blog/side-bar'); // Renders perfect ?>
</div>
</div>
</div>
</div>
And of course the real culprit the blog-post partial -
<?php
if (have_posts()) :
the_post(); ?>
<div class="row no-margin">
<div class="col s12 no-margin relative">
<img src="<?php the_post_thumbnail_url('medium_size'); ?>" alt="<?php the_title(); ?>" class="block">
</div>
<div class="col s12">
<div class="white p-2-s p-3-l">
<?php the_content(); ?>
</div>
</div>
</div>
<?php else :?>
<div class="col s12 no-margin">
<div class="white p-2-s p-3-l"><p>Sorry, we couldn't find the post you were looking for.</p></div>
</div>
<?php endif; ?>
Again, the templates are rendering perfect but the 'have_posts()' is returning false and spitting out my 'else' part of my statement. I have used this method in another template and it worked perfectly before (although I will admit, I love to develop in node and WordPress and php have really made me beat my head against the wall at times lol). Is there something I missed?
I have checked my functions.php which I have written from scratch, and there isn't a single thing in there that might affect the post but if you need to see it, I would be happy to share it (I have disabled each portion of the functions.php to check if it would help and no luck). I don't have any plugins added, not even the default included ones (I am a dork that wants to build most everything from scratch so I know how it works).
Am I wrong in that the output to 'have_posts()' should be true on the single.php page? Did I do something wrong with my partials? The banner does use the 'the_title()' tag and 'the_date()' tag but both php tags are properly closed. Would really appreciate some insight on why I am getting false on this. Thanks everyone!
** EDIT ** - When I went to debug the blog-post partial and var_dump the have_posts(), I placed it above the if statement and everything rendered. Looked like so:
<?php
var_dump(have_posts()); // <---------------- Added this and it rendered
if (have_posts()) :
the_post(); ?>
The var_dump output false but then if I did it a second time, it now renders true. Any ideas as to why? For the time being, I am storing a have_posts() in a random variable so there is no output and the post is now showing. While I am happy the post is now showing, I know this isn't necessarily a 'solid fix'. Any ideas with this?

So first I just want to say, #Jeppe you had it right the whole time. If I could mark your comment correct (and if you can, please show me how) I would.
To anyone else who stumbles across this post, it comes down to using the 'rewind_posts()' function. All in all, I have a loop somewhere in my code, that I can't identify as the culprit, that is essentially forcing my 'have_posts()' function to return false because I haven't reset it / rewound it according to WordPress.
My solution was to simply take my old code:
<?php
if (have_posts) :
the_post;
?>
and add the rewind_posts() function above the if statement:
<?php
rewind_posts(); // <---------- This guy right here.
if (have_posts) :
the_post;
?>
This will rewind WordPress's loop and allow have_posts() to print true.

Related

<!--nextpage--> somehow causes the layout to be skewed

I'm using the <!--nextpage--> function to page break and split the page on Wordpress.
The problem is, whenever <!--nextpage--> is inserted, the position of sidebar is moved to where it shouldn't be.
It's like this on page.php:
<div class="main">
<?php
if (have_posts()) :
...
?>
<?php wp_link_pages(); ?>
</div>
<?php get_sidebar(); ?>
So if I understand correctly, .main and get_sidebar are on the same level.
But when I actually make some page using this template, an output is like this:
<div class="main">
<div class="section">
...
<div class="content">
// pagination is inserted here
</div>
<aside class="sidebar">
...
</aside>
</div>
</div>
In other words, get_sidebar(aside tag) automatically moves into .section.
This is extremely confusing to me, and really don't know what to do here.
Why does Wordpress decide to put it inside of .section? Why can't it be faithful to the template?
Now the sidebar is positioned at the end of content instead of being on the right side.
What are the possible causes and solution to this issue?
Thank you for reading.

PHP and HTML: Nested foreach loops with HTML interspersed

I'm trying to put together a layout of items with an Accordion layout (from Bootstrap). In order to fill the accordions, I reach into a pgsql db to gather the data, and I'm able to retrieve this data.
What I'm having issues with is getting the data to show up at all. Right now I'm getting an HTML 500. It might be a layout issue or it might be a PHP interpretation issue (maybe out of depth? or something not visible to PHP), but I'm having issues determining which is the culprit.
I say this because I have a fairly complicated arrangement I'm attempting to make.
A sample:
<?php
// db connection info goes here
// pgsql query info goes here
$i = 0;
$result = pg_fetch_all($getData);
?>
<!-- Starting the container accordion -->
<div class="panel-group" id="main-accordion">
<?php
foreach($result as $row):
$title1 = $row['title1'];
$title2 = $row['title2'];
?>
<div class="panel panel-default">
<div class="panel-heading">
<h4 class="panel-title">
<a data-toggle="collapse" data-parent="#main-accordion" href="#<?=$row['id']?>">
(<?=$row['category']?>) <?=$title1?> - <?=$title2?>
</a>
</h4>
</div>
<div id="<?=$row['id']?>" class="panel-collapse collapse">
<!-- The body of the accordion, contents go here. -->
<div class="panel-body">
<?php
// another pgsql query here
$newresult = pg_fetch_all($newgetData);
?>
<!-- In the accordion body, a new group of accordions. This is doable if hardcoded -->
<div class="panel-group" id="sub-accordion-<?=$i?>">
<?php
// I think this is where the issues start??
foreach($newresult as $newrow):
$subtitle = $newrow['subtitle'];
?>
<div class="panel panel-default">
<div class="panel-heading">
<h4 class="panel-title">
<a data toggle="collapse" data-parent="#sub-accordion" href="#<?=$newrow['subid']?>">
<?=$subtitle?>
</a>
</h4>
</div>
<div id="<?=$newrow['subid']?>" class="panel-collapse panel">
<div class="panel-body">
<!-- contents go here -->
</div>
</div>
</div>
<?php endforeach; ?>
</div>
</div>
</div>
<?php
$i++;
endforeach; ?>
</div>
</div>
So, now my questions for the web dev people with HTML PHP and Bootstrap exp.:
Is it possible to nest foreach loops in this fashion without falling back to echo statements to print out the HTML (because ew)? Will it actually create (repeat) the HTML for the accordion objects this way or do I need to modify something here?
What might be triggering the HTML 500?
I realize this is a tough question to answer without live working code to mess with. If anyone knows a good resource to quickly sandbox a full stack for demo purposes I would be glad to know of it so I can put up some "working" code.
EDIT 1: User Sean pointed out that the sub-accordion is in a loop. Added in an iterator that modifies this id as the goal is to have multiple sub-accordions, not with the same id.
EDIT 2: Might have solved my own questions:
1. Turns out I used the wrong method when retrieving the ajax request: used PHP's $_POST['var'] instead of $_GET['var']
2. There was one syntax error on one of my shorthand PHP tags.
Now things are showing up! But, the formatting is still wrong. I can deal with that. Thank you all for all your help!
In your PHP.ini short tags might be turned off. In that case you either turned on or if you have no access to PHP.ini, then you should not use short echo tags `, try changing it to

WordPress ignoring is_page() conditional

<?php if( is_home() || is_page(10)): ?>
<div class="text-center col-xl-12 col-lg-12 col-md-12 col-sm-12 col-xs-12">
<?php elseif(is_single() && !is_page(10)): ?>
<div class="text-center col-xl-9 col-lg-9 col-md-9 col-xs-12">
<?php endif; ?>
All I'm trying to do is change the classes assigned to this <div> if you are on a single post, which works fine, but I can't get it under control when viewing a contact page, which it seems to recognize as a single post. This is fine, but I want to exclude one page from this effect.
I've tried is_page('Contact'), is_page('contact'), and is_page(10)
None of them seem to return true in any case, I even deleted all other conditionals and just had it print something if its the contact page, but it still doesn't return true and has no effect.
I've done a lot of searching and all I can find says I'm using it correctly.. I'm at a loss as to why it wouldn't return true?
Am I using php if statements incorrectly and it's been an 'oops, it worked' scenario thus far?
The url to the page ends with ?page_id=10, the page is titled 'Contact'
I could create a page template, but it seems more than what I need here, the contact page is painfully simple, and all I really need to do is center the four lines of text appropriately using bootstrap. Works fine across all other pages of the website, and changes the <div> appropriately if you're on the homepage or viewing a single post.
As requested, the full index.php code is below. Thanks to anyone who is willing to look at this. It is nothing massive, I am relatively new so please excuse my excessive commenting - I'm still learning.
Full index.php: https://pastebin.com/nnG0ny99
You can try using:
global $post;
<?php if( is_home() || $post->ID == 10): ?>
<div class="text-center col-xl-12 col-lg-12 col-md-12 col-sm-12 col-xs-12">
<?php elseif(is_singular() && $post->ID != 10): ?>
<div class="text-center col-xl-9 col-lg-9 col-md-9 col-xs-12">
<?php endif; ?>
That way you are getting the actual post id rather than the page id.
Edit: try to change is_single() to is_singular() as saNs suggested in his answer.
Make sure you're not using is_page() in the loop.
From https://developer.wordpress.org/reference/functions/is_page/
"Due to certain global variables being overwritten during The Loop, is_page() will not work. In order to call it after The Loop, you must call wp_reset_query() first."
is_single() works for "any post type, except attachments and pages"(https://developer.wordpress.org/reference/functions/is_single/) So it will always evaluate to false for pages.
Use is_singular() instead.

Display parent div only if populated with content

Is there a way to only display a parent (wrapping) if it's actually been populated with content?
The reason I ask is in Wordpress I'm using Advanced Custom Fields to create additional text areas on the homepage of the website. The content is added to the page inside divs, like this:
<section class="band">
<div class="wrap">
<?php the_field('services'); ?>
</div>
</section>
If the field is left blank, obviously the markup that surrounds remains on the page and due to the margin/padding they have set on them it leaves a big empty stripe across the page.
I know little Wordpress (and PHP in general), I assume this must be possible? I've had a play around with if/else statements but had no luck.
Can anyone advise on this?
You could do it this way:
<?php if( get_field('services') ) : ?>
<section class="band">
<div class="wrap">
<?php the_field('services'); ?>
</div>
</section>
<?php endif; ?>

Using columns in Wordpress page that include header

I'm a little bit of a newb when it comes to PHP, but know enough to get around and would like to know if this can be done. sample
I want to break my wordpress page into 2 columns, but also want to have the header in the 1st column.... along with other text. I don't want the header floating over both columns...
The second column will house images only...
is that possible? In my head it makes sense, but then when I try and work it out, I'm just not sure....
And I just got thinking... I have my home page static with the smooth slider on it, so that is now going to cause more grief.
Any help, advice or pointers would be greatly appreciated.
Thanks in advance
This is more CSS/HTML than PHP, however that's fine. The first thing you need to do is understand how to make a two column layout. Then you will need to have the post title in the first column, something like this:
<article>
<div id="col1">
<h1>Post Title</h1>
Lorem ipsum dolor sit amet...
</div>
<div id="col2">
<img src="" />
</div>
</article>
To make this into WordPress you will of course need to add the WordPress Tags:
<div id="col1">
<h1><?php the_title(); ?></h1>
<?php the_content(); ?>
</div>
Finally, adding the image(s) on the right. It can be done easily using WordPress' built in functionality, if you only need one image: (Note you will have to add something in your theme's functions.php file as per the WordPress Docs)
<div id="col2">
<?php
if ( has_post_thumbnail() ) { // check if the post has a Post Thumbnail assigned to it.
the_post_thumbnail();
}
?>
</div>
To add multiple images, it gets more complex and you'll have to start looking for a plugin to achieve that goal.

Categories