Skip to content

Conversation

@miguelpeixe
Copy link
Member

@miguelpeixe miguelpeixe commented Dec 4, 2024

Add support for syncing the post thumbnail when distributing content.

Testing

  1. Make sure you have a network setup with at least 1 hub and 1 node
  2. On the hub, create a new post with a featured image, grab the post ID, and use the WP shell to distribute to the node:
$post_id = 0; // Change to your post ID.
$site_urls = [ 'http://node1.local' ]; // Change to match your setup urls.
Newspack_Network\Content_Distribution::set_post_distribution( $post_id, $site_urls );
Newspack_Network\Content_Distribution::distribute_post( $post_id );
  1. Visit the media library and confirm the post thumbnail was created
  2. Confirm the post is added as a draft and the thumbnail is assigned
  3. In the original post, change the featured image and save
  4. Visit the media library in node1 and confirm that the previous featured image has been deleted and the new one was created
  5. Confirm the new featured image was also updated in the post
  6. In the original post, delete the featured image and save
  7. Back in node1, confirm in the media library that the featured image has been deleted
  8. Confirm in the linked post that no featured image is assigned

Comment on lines 361 to 364
// Delete existing thumbnail attachment.
if ( $current_thumbnail_id ) {
wp_delete_attachment( $current_thumbnail_id, true );
}
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When syncing the post thumbnail, whether the distributed post is updating the featured image or deleting it, the destination site will permanently delete the orphan image.

I'm not sure if this is too aggressive, but I also don't like the idea of lingering orphan images.

The current approach can be problematic if:

  • The site starts using the synced attachment in other content
  • The site unlinked the post, changed the featured image to something local, and re-linked the post - deleting their local attachment

We can prevent the last one above by adding a meta to the synced attachment so only those get deleted.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's probably a pretty expensive query, but do you think it's worth checking if other posts are using the image before deleting it?

There is also the use case that the image is used in the post body.

Copy link
Member Author

@miguelpeixe miguelpeixe Dec 9, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've decided to not delete the attachment for now. Instead, we set a post meta to not lose track of the attachments that came via distribution and we can decide later how to deal with them. WDYT? e5d1418

I think a post content query is not viable, even if executed via cron. It's very expensive...

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think that makes sense. I like the idea with the postmeta. Better have a bit too much media than media missing.

@miguelpeixe miguelpeixe self-assigned this Dec 6, 2024
@miguelpeixe miguelpeixe marked this pull request as ready for review December 6, 2024 13:18
@miguelpeixe miguelpeixe requested a review from a team as a code owner December 6, 2024 13:18
@miguelpeixe miguelpeixe requested a review from naxoc December 6, 2024 13:18
Base automatically changed from feat/content-distribution-class to epic/content-distribution December 9, 2024 11:52
Copy link
Member

@naxoc naxoc left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks good and tests well. (The unit-test is broken, but that is from the updated-date-PR I think).

I added some comments about the image deletion though. I think there are use cases we can get in trouble with.

Comment on lines 361 to 364
// Delete existing thumbnail attachment.
if ( $current_thumbnail_id ) {
wp_delete_attachment( $current_thumbnail_id, true );
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's probably a pretty expensive query, but do you think it's worth checking if other posts are using the image before deleting it?

There is also the use case that the image is used in the post body.


$attachment_id = media_sideload_image( $thumbnail_url, $post_id, '', 'id' );
if ( is_wp_error( $attachment_id ) ) {
return;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A silent error here is probably fine, so this is a question more than a request – but do we have a way to log stuff like this?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good call! We have a Debugger class, added a log in 23b93e6

@miguelpeixe
Copy link
Member Author

Thank you for the review, @naxoc!

I've addressed the comments and fixed the tests in 9c7212b

@miguelpeixe miguelpeixe requested a review from naxoc December 9, 2024 18:53
Copy link
Member

@naxoc naxoc left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good to go!
ok

@miguelpeixe miguelpeixe merged commit f2de08c into epic/content-distribution Dec 9, 2024
@miguelpeixe miguelpeixe deleted the feat/content-distribution-featured-image branch December 9, 2024 21:10
naxoc added a commit that referenced this pull request Dec 12, 2024
* feat: content distribution class

* feat: insert linked post

* refactor: use site url instead of ID

* chore: lint

* feat: return errors on post insert

* chore: lint

* feat: support webhooks request priority

* feat: unlink functionality and unit tests

* chore: lint

* feat: introduce 'linked_post_inserted' hook and listener

* chore: lint

* fix: listener hook name

* fix: typo

* chore: better docblocks

* chore: remove redundant code

* test: persist post hash

* test: remove unnecessary assertion

* refactor: distribute_post() to use handle_post_updated() method

* refactor: post hash is now network post id

* chore: update comment

* chore: Add CLI command for distribute

* feat: content distribution class (#155)

* feat: content distribution class

* feat: insert linked post

* refactor: use site url instead of ID

* chore: lint

* feat: return errors on post insert

* chore: lint

* feat: support webhooks request priority

* feat: unlink functionality and unit tests

* chore: lint

* feat: introduce 'linked_post_inserted' hook and listener

* chore: lint

* fix: listener hook name

* fix: typo

* chore: better docblocks

* chore: remove redundant code

* test: persist post hash

* test: remove unnecessary assertion

* refactor: distribute_post() to use handle_post_updated() method

* refactor: post hash is now network post id

* chore: update comment

* feat(content-distribution): prevent older content updating linked posts (#156)

* feat(content-distribution): handle post thumbnail (#157)

* Add network util class

* Almost done except for a few todos

* refactor: OOP for distributed and linked posts (#160)

* chore: Require php 8.1

* chore: Update to use util class

Also use new incoming/outgoing classes

* fix: Include correct classname

The old classname "Linked_Post" was still used instead of
"Incoming_Post" causing sync to fail.

## How to test
Probably eyeballing is enough

* chore: Add validation of outgoing post

Also move inclusion of the content distribution CLI class to better
respect the flag we are introdocuing

* chore: phpcs

* fix(content-distribution): debug post update and remove deprecated config (#165)

* fix: Don't return payload on all posts

* fix: post handling

* chore: move try-catch

* chore: Move check for networked urls

* Move more

* Move things again

* chore: Add a mock networked node

* chore: add one more node to the mock nodes

* Add a test

---------

Co-authored-by: Miguel Peixe <miguel.peixe@automattic.com>
matticbot pushed a commit that referenced this pull request Jan 10, 2025
# [2.4.0-alpha.1](v2.3.4...v2.4.0-alpha.1) (2025-01-10)

### Bug Fixes

* **content-distribution:** post insertion hook and additional meta for incoming post event ([#173](#173)) ([48df13c](48df13c))
* load text domain on init hook ([#171](#171)) ([01fb89c](01fb89c))

### Features

* content distribution - experimental ([#168](#168)) ([dc837d8](dc837d8))
* **content-distribution:** add CLI command for distribute post ([#159](#159)) ([7a43b86](7a43b86)), closes [#155](#155) [#156](#156) [#157](#157) [#160](#160) [#165](#165)
* **content-distribution:** canonical url ([#177](#177)) ([5ca60ce](5ca60ce))
* **content-distribution:** capability and admin page ([#176](#176)) ([5285285](5285285))
* **content-distribution:** control distribution meta and prevent multiple dispatches ([#170](#170)) ([e76a2dc](e76a2dc))
* **content-distribution:** editor plugin for distribution ([#167](#167)) ([e10aef4](e10aef4))
* **content-distribution:** handle status changes ([#166](#166)) ([4af5da1](4af5da1))
* **content-distribution:** log incoming post errors ([#182](#182)) ([74c9119](74c9119))
* **content-distribution:** posts column ([#178](#178)) ([8e07640](8e07640))
* **content-distribution:** reserved taxonomies ([#174](#174)) ([a2c54d2](a2c54d2))
* **content-distribution:** sync comment and ping statuses ([#179](#179)) ([90c5425](90c5425))
* **content-distribution:** sync post meta ([#163](#163)) ([353a3d8](353a3d8))
* **event-log:** collapse data ([#180](#180)) ([956219d](956219d))
* limit purchase of a network membership ([#169](#169)) ([deb2683](deb2683))
matticbot pushed a commit that referenced this pull request Jan 20, 2025
# [2.4.0](v2.3.4...v2.4.0) (2025-01-20)

### Bug Fixes

* **content-distribution:** post insertion hook and additional meta for incoming post event ([#173](#173)) ([48df13c](48df13c))
* load text domain on init hook ([#171](#171)) ([01fb89c](01fb89c))

### Features

* content distribution - experimental ([#168](#168)) ([dc837d8](dc837d8))
* **content-distribution:** add CLI command for distribute post ([#159](#159)) ([7a43b86](7a43b86)), closes [#155](#155) [#156](#156) [#157](#157) [#160](#160) [#165](#165)
* **content-distribution:** canonical url ([#177](#177)) ([5ca60ce](5ca60ce))
* **content-distribution:** capability and admin page ([#176](#176)) ([5285285](5285285))
* **content-distribution:** control distribution meta and prevent multiple dispatches ([#170](#170)) ([e76a2dc](e76a2dc))
* **content-distribution:** editor plugin for distribution ([#167](#167)) ([e10aef4](e10aef4))
* **content-distribution:** handle status changes ([#166](#166)) ([4af5da1](4af5da1))
* **content-distribution:** log incoming post errors ([#182](#182)) ([74c9119](74c9119))
* **content-distribution:** posts column ([#178](#178)) ([8e07640](8e07640))
* **content-distribution:** reserved taxonomies ([#174](#174)) ([a2c54d2](a2c54d2))
* **content-distribution:** sync comment and ping statuses ([#179](#179)) ([90c5425](90c5425))
* **content-distribution:** sync post meta ([#163](#163)) ([353a3d8](353a3d8))
* **event-log:** collapse data ([#180](#180)) ([956219d](956219d))
* limit purchase of a network membership ([#169](#169)) ([deb2683](deb2683))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants