Retrieve wordpress posts with featured image via SQL - php

I'm using this query in a PHP script outside Wordpress to retrieve entries with their featured images
SELECT ( SELECT guid FROM wp_posts WHERE id = m.meta_value ) AS url
FROM wp_posts p, wp_postmeta m
WHERE p.post_type = 'post'
AND p.post_status = 'publish'
AND p.id = m.post_id
AND m.meta_key = '_thumbnail_id'
...and it works fine.
But this way I get full-size image URL. I need to retrieve 'medium' or 'thumbnail' sizes of these images.
¿Any way to achieve this?

here is the response :
SELECT TITRE,DESCR,URL, CONCAT(LEFT(IMG, LENGTH(IMG) - LOCATE('.',
REVERSE(IMG))),'-150x150.',SUBSTRING_INDEX(IMG, '.', -1)) AS IMG FROM (
SELECT
p.`post_title` AS TITRE,
(SELECT `meta_value` FROM wp_postmeta WHERE `post_id` = p.`ID` and `meta_key`='_yoast_wpseo_metadesc') AS DESCR,
p.`guid` AS URL,
(SELECT `guid` FROM wp_posts WHERE id = m.meta_value) AS IMG
FROM wp_posts p, wp_postmeta m
WHERE p.post_type = 'post'
AND p.post_status = 'publish'
AND p.id = m.post_id
AND m.meta_key = '_thumbnail_id') TT
where DESCR is not null

The following query, adapted from the above, solved my particular problem which was simply to grab the last four posts and their featured images. Plus the post_name from which I could construct a pretty URL
SELECT title, post_name, date, content, CONCAT(LEFT(image, LENGTH(image) - LOCATE('.', REVERSE(image))),'-150x150.',SUBSTRING_INDEX(image, '.', -1)) AS image
FROM (
SELECT
p.post_title AS title,
p.post_status AS 'status',
p.post_date AS date,
p.post_content AS content,
p.post_name AS post_name,
(SELECT `guid` FROM wp_posts WHERE id = m.meta_value) AS image
FROM wp_posts p, wp_postmeta m
WHERE p.post_type = 'post'
AND p.post_status = 'publish'
AND p.id = m.post_id
AND m.meta_key = '_thumbnail_id'
ORDER BY date DESC
LIMIT 4
) TT
Of course from there it's easy to make an excerpt etc using:
for($i=0; $i< $num_rows; $i++){
$post_content = mysql_result($query_result, $i, "content");
$post_excerpt = substr($post_content, 0, 90);
$post_permalink = $post_url . mysql_result($query_result, $i, "post_name");
echo $post_permalink; //etc
}

You can try this query for thumbnail size , for medium image i am not sure about the right size if you know the dimension then make custom alias as i made below using the SUBSTRING_INDEX to get the extension of file then i have used CONCAT function with the post_name column and the dimensions + extension ,similarly you can do this for medium size , As all upload goes to the upload folder you can analyze the generated thumbs name are original attachment name + -150x150 or other dimensions so from this logic your thumbs get the name with the dimensions, the attachments of post are stored in post_meta with the post id and having key name _wp_attachment_metadata which stores all the information about different sizes of file but in a serialized form so in mysql query you cannot unserialize the data
SELECT
CONCAT(p.`post_name` ,'-150x150.',
SUBSTRING_INDEX(( SELECT `guid` FROM wp_posts WHERE id = m.meta_value ), '.', -1) )
AS `thumbnail`,
(SELECT guid FROM wp_posts WHERE id = m.meta_value ) AS `full`
FROM wp_posts p, wp_postmeta m
WHERE p.post_type = 'post'
AND p.post_status = 'publish'
AND p.id = m.post_id
AND m.meta_key = '_thumbnail_id'
This query works for me to get thumbnail of size 150*150 hope it works for you also

SELECT
p.ID,
p.post_title AS title,
p.post_name AS post_name,
(SELECT meta_value from wp_postmeta where post_id = m.meta_value and meta_key='_wp_attachment_metadata') AS meta_value
FROM
wp_posts p,
wp_postmeta m
WHERE
p.post_type = 'post'
AND p.post_status = 'publish'
AND p.id = m.post_id
AND m.meta_key = '_thumbnail_id'
ORDER BY
p.post_date DESC
LIMIT 5;
And then use unserialize PHP function with meta_value

Related

Retrieve all WooCommerce products without image that are in stock via SQL

I use this query sql to retrieve all products without image
SELECT id
FROM `wp_posts`
WHERE id NOT IN (SELECT post_id FROM `wp_postmeta` WHERE `meta_key` =
'_thumbnail_id')
AND `post_type` = 'product'
AND `post_status` = 'publish'
Now I would retrieve all products without image and stock status in stock, is there a way to do it?
The following SQL Query will allow you to retrieve products without image that are "In stock":
SELECT ID
FROM wp_posts p
INNER JOIN wp_postmeta pm ON p.ID = pm.post_id
WHERE ID NOT IN (SELECT post_id FROM wp_postmeta WHERE meta_key = '_thumbnail_id')
AND p.post_type = 'product'
AND p.post_status = 'publish'
AND pm.meta_key = '_stock_status'
AND pm.meta_value = 'instock'
Or you can query it using WPDB Class through php like:
global $wpdb;
$product_ids = $wpdb->get_col( "
SELECT ID
FROM {$wpdb->prefix}posts p
INNER JOIN {$wpdb->prefix}postmeta pm ON p.ID = pm.post_id
WHERE ID NOT IN (SELECT post_id FROM {$wpdb->prefix}postmeta WHERE meta_key = '_thumbnail_id')
AND p.post_type = 'product'
AND p.post_status = 'publish'
AND pm.meta_key = '_stock_status'
AND pm.meta_value = 'instock'
");
// Raw output
print_r($product_ids);

Fetch data from wordpress DB

I have 2 meta keys which i want attached to particular post type in a single instance, and i created the sql query
SELECT DISTINCT p.ID, p.post_title, pmo.meta_value, pmj.meta_value
FROM wp_posts AS p
RIGHT JOIN wp_postmeta AS pmo ON p.ID = pmo.post_id
RIGHT JOIN wp_postmeta AS pmj ON p.ID = pmj.post_id
WHERE (pmo.meta_key = '_order_meta' AND pmj.meta_key = '_order_jobs')
AND p.post_type = '_order'
AND p.post_status = 'publish'
ORDER BY p.ID DESC LIMIT 10
But when i var dump the data.
it only shows the last 'meta_value', although i am fetching 2 meta_vales

wpdb query - How to display the result even if values are missing?

I have read that if there is data missing from the '$wpdb->get_results' query, then the result will be completely empty.
My query is as follows:
$results = $wpdb->get_results("
SELECT
( SELECT guid FROM ch_posts WHERE id = m.meta_value ) AS thumbnail, ID, post_title, post_name, SUBSTR(post_content, 20) AS content, post_date, t.name AS category
FROM ch_posts, ch_postmeta m
JOIN ch_term_relationships tr
JOIN ch_terms t ON t.term_id = tr.term_taxonomy_id
JOIN ch_term_taxonomy tx ON tr.term_taxonomy_id = tx.term_taxonomy_id
WHERE post_status = 'publish'
AND post_author = $user_ID
AND post_type = 'product'
AND ch_posts.ID = m.post_id
AND m.meta_key = '_thumbnail_id'
AND tr.object_id = ch_posts.ID
AND tx.taxonomy = 'product_cat'
");
then
foreach ($results as $result) { }
Because my post has a missing 'thumbnail' record, the entire results set does not get displayed. Is it possible to modify my query to show the results that are found and just ignore the ones that are missing? Or replace the missing values with something else?
I have tried using CASE, But to no avail.
Any help will be most welcome
1st, your query is not full. Show the whole query. 2nd, you're getting thumbnail url in a wrong way. 3rd, join should not be inner for tables that are for getting thumbnail. Example of getting 20 last posts with thumbnail (NULL is none)
SELECT `posts`.`ID` AS `ID`, `posts`.`post_title` AS `title`, `posts`.`post_name` AS `slug`, `posts`.`post_content` AS `content`, `posts`.`post_excerpt` AS `excerpt`, `thumb_link` FROM `wp_posts` AS `posts`
LEFT JOIN (select `thumb`.`post_id` AS `object_id`, `thumbs_link`.`meta_value` AS `thumb_link` from `wp_postmeta` AS `thumb`
LEFT JOIN`wp_postmeta` AS thumbs_link ON (`thumbs_link`.`post_id` = `thumb`.`meta_value`)
AND `thumbs_link`.meta_key = "_wp_attached_file" WHERE `thumb`.`meta_key` = '_thumbnail_id'
GROUP BY `thumb`.`post_id` ) AS `thumb` ON `thumb`.`object_id` = `posts`.`ID`
WHERE `posts`.`post_status` = 'publish'
ORDER BY `posts`.`ID` DESC
LIMIT 20

SQL join table result of 2 statements

I am trying to get data with SQL from my Wordpress database by a JOIN, but I do not get it working.
What I need:
Posts where the meta_key "gtp_product_dont_show" exists and where the meta_value not is "true".
And posts where the meta_key "gtp_product_dont_show" does not exists.
My Problem:
I now only get the results where posts have a meta_key "gtp_product_dont_show", but there are also posts which don't have this key, and I need these as well.
This is what I have now:
SELECT
ID, post_title
FROM
wp_posts p
JOIN wp_postmeta m ON
p.ID = m.post_id AND
m.meta_key = 'gtp_product_dont_show' AND
m.meta_value != 'true'
WHERE
post_type = 'products' AND
post_status = 'publish'
Output:
You need a left join:
SELECT ID, post_title
FROM wp_posts p LEFT JOIN
wp_postmeta m
ON p.ID = m.post_id AND
m.meta_key = 'gtp_product_dont_show'
WHERE (m.meta_value is null or m.meta_value <> 'true') and
post_type = 'products' AND
post_status = 'publish';
The left join looks for an appropriate key in the wp_postmeta table. The where clause then says "keep a record when there is no match or the value is not true" -- which I think is the logic you are looking for.
You're looking for this?
SELECT
ID, post_title
FROM
wp_posts p
WHERE
post_type = 'products' AND
post_status = 'publish' AND
not exists (
select 1
from wp_postmeta m
where
p.ID = m.post_id AND
m.meta_key = 'gtp_product_dont_show' AND
m.meta_value = 'true')
This will fetch all the rows from wp_posts, but leave out those where row is found from wp_postmeta where meta_key is gtp_product_dont_show and value is true.
You can use the OR operator to consider both conditions. Try this:
SELECT stuff
FROM myTable
JOIN otherTable ON
(m.meta_key = 'gtp_product_dont_show' AND m.meta_value != 'true') OR
(m.meta_key != 'gtp_product_dont_show')
...
Just a side note, I don't recommend storing booleans as strings like that. You should consider using a TINYINT() where boolean fields are stored as 0 for false, or 1 for true.

sql statement for querying wp posts from specific category

i want to query wordpress posts from specific category parent but the problem is that there is no such column on wp_posts table so i need to join but my skills on the sql is not good so i need some help ,
here is the query i use for querying posts
$query = "SELECT c.*
FROM {$wpdb->prefix}posts p,
{$wpdb->prefix}comments c WHERE p.ID = c.comment_post_ID AND c.comment_approved > 0 AND p.post_type = 'product' AND p.post_status = 'publish' AND
p.comment_count > 0 ORDER BY ".$order_by." LIMIT 0, ". $number_of_comments;
}
and here is some snippet i found for joining term_taxonomy_id
$answer = $wpdb->get_results("SELECT post_title, post_content, term_taxonomy_id FROM wp_posts LEFT JOIN wp_term_relationships ON wp_posts.ID = wp_term_relationships.object_id WHERE SUBSTRING(post_title,1,1)='T' AND term_taxonomy_id=6");
the proplem i can't seem to figure how to use this example on my query neither thinking of simpler solutions so i can query from specific parent category , thanks for your help
here is the query i used and worked ..
$query = "SELECT c.*
FROM
{$wpdb->prefix}comments c ,
{$wpdb->prefix}posts p JOIN $wpdb->term_relationships TR
ON p.ID=TR.object_id
JOIN $wpdb->term_taxonomy T
ON TR.term_taxonomy_id=T.term_taxonomy_id
JOIN $wpdb->terms TS
ON T.term_id = TS.term_id
WHERE p.ID = c.comment_post_ID AND c.comment_approved > 0 AND p.post_type = 'product' AND p.post_status = 'publish' AND
p.comment_count > 0 AND T.taxonomy = 'product_cat' AND T.term_id='$term_cat' ORDER BY ".$order_by." LIMIT 0, ". $number_of_comments;
}
you would be looking at something like this:
global $wpdb;
$wpdb->show_errors();
$ur=$wpdb->get_results( $wpdb->prepare(
"
SELECT *
FROM $wpdb->posts P
JOIN $wpdb->term_relationships TR
ON P.ID=TR.object_id // identify link column
JOIN $wpdb->term_taxonomy T
ON TR.term_taxonomy_id=T.term_taxonomy_id
JOIN $wpdb->terms TS
ON T.term_id = TS.term_id
WHERE P.post_type = %d // use wild chars (define below, this one equals carmarket)
AND P.post_status = %f
AND T.taxonomy= %s
",
'carmarket',
'publish',
'carmake'
) );
$wpdb->print_error();
var_dump($ur);

Categories