Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mark existing URL Metrics as stale when a new tag visitor is registered #1705

Conversation

ShyamGadde
Copy link
Contributor

@ShyamGadde ShyamGadde commented Nov 26, 2024

Summary

Fixes #1424

Relevant technical choices

plugins/optimization-detective/optimization.php Outdated Show resolved Hide resolved
plugins/optimization-detective/detection.php Outdated Show resolved Hide resolved
plugins/optimization-detective/detection.php Outdated Show resolved Hide resolved
plugins/optimization-detective/helper.php Outdated Show resolved Hide resolved
plugins/optimization-detective/hooks.php Outdated Show resolved Hide resolved
@ShyamGadde ShyamGadde marked this pull request as ready for review November 27, 2024 14:22
Copy link

The following accounts have interacted with this PR and/or linked issues. I will continue to update these lists as activity occurs. You can also manually ask me to refresh this list by adding the props-bot label.

If you're merging code through a pull request on GitHub, copy and paste the following into the bottom of the merge commit message.

Co-authored-by: ShyamGadde <shyamgadde@git.wordpress.org>
Co-authored-by: westonruter <westonruter@git.wordpress.org>

To understand the WordPress project's expectations around crediting contributors, please review the Contributor Attribution page in the Core Handbook.

@ShyamGadde
Copy link
Contributor Author

Code in question:

/**
* Gets a sample URL metric.
*
* @phpstan-param array{
* url?: string,
* viewport_width?: int,
* viewport_height?: int,
* element?: ElementDataSubset,
* elements?: array<ElementDataSubset>
* } $params Params.
*
* @return OD_URL_Metric URL metric.
*/
public function get_sample_url_metric( array $params ): OD_URL_Metric {
$params = array_merge(
array(
'url' => home_url( '/' ),
'viewport_width' => 480,
'elements' => array(),
),
$params
);
if ( array_key_exists( 'element', $params ) ) {
$params['elements'][] = $params['element'];
}
return new OD_URL_Metric(
array(
'url' => home_url( '/' ),
'viewport' => array(
'width' => $params['viewport_width'],
'height' => $params['viewport_height'] ?? ceil( $params['viewport_width'] / 2 ),
),
'timestamp' => microtime( true ),
'elements' => array_map(
function ( array $element ): array {
return array_merge(
array(
'isLCP' => false,
'isLCPCandidate' => $element['isLCP'] ?? false,
'intersectionRatio' => 1,
'intersectionRect' => $this->get_sample_dom_rect(),
'boundingClientRect' => $this->get_sample_dom_rect(),
),
$element
);
},
$params['elements']
),
)
);
}

@westonruter, while working on this PR, I came across this code and had a quick question. On line 93, shouldn’t it use $params['url'] instead of home_url( '/' )? It seems like if a URL is passed in the $params argument, it doesn’t get used. Is this intentional?

Just thought I’d flag it while I noticed it—thanks!

@westonruter
Copy link
Member

You're right! That seems to be an oversight in the tests.

@westonruter westonruter added [Type] Enhancement A suggestion for improvement of an existing feature [Plugin] Optimization Detective Issues for the Optimization Detective plugin labels Nov 27, 2024
@@ -46,6 +46,11 @@ function od_register_endpoint(): void {
'required' => true,
'pattern' => '^[0-9a-f]{32}$',
),
'eTag' => array(
Copy link
Member

Choose a reason for hiding this comment

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

See other comment about calling this rather current_etag.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done in 371e998.

plugins/optimization-detective/class-od-url-metric.php Outdated Show resolved Hide resolved
plugins/optimization-detective/class-od-url-metric.php Outdated Show resolved Hide resolved
@@ -539,6 +541,7 @@ export default async function detect( {

const url = new URL( restApiEndpoint );
url.searchParams.set( 'slug', urlMetricSlug );
url.searchParams.set( 'eTag', currentETag );
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 a bit confusing that this is here rather than (also?) added as urlMetric.eTag (or urlMetric.etag). In the end they will need to be identical of course, so it does make sense. Just an observation. Maybe this should be called current_etag to better disambiguate?

Copy link
Contributor Author

@ShyamGadde ShyamGadde Nov 28, 2024

Choose a reason for hiding this comment

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

Renamed the arg in 371e998.

@@ -208,6 +210,12 @@ public static function get_json_schema(): array {
'required' => true,
'readonly' => true, // Omit from REST API.
),
'eTag' => array(
Copy link
Member

Choose a reason for hiding this comment

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

I wonder if we should make this just 'etag'. In HTTP it is "ETag", and a lower case "eTag" feels like it would maybe be something else, like an "electronic tag" or something.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Makes sense. Done in 08f8f8a.

*
* @param string $slug Slug (hash of normalized query vars).
* @param string $etag ETag.
Copy link
Member

Choose a reason for hiding this comment

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

Consider $current_etag instead.

@@ -173,12 +173,13 @@ function od_get_url_metrics_storage_hmac( string $slug, string $url, ?int $cache
*
* @param string $hmac HMAC.
* @param string $slug Slug (hash of normalized query vars).
* @param string $etag ETag.
Copy link
Member

Choose a reason for hiding this comment

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

Ditto on $current_etag.

@@ -182,6 +188,7 @@ function od_handle_rest_request( WP_REST_Request $request ) {
// Now supply the readonly args which were omitted from the REST API params due to being `readonly`.
'timestamp' => microtime( true ),
'uuid' => wp_generate_uuid4(),
'eTag' => $request->get_param( 'eTag' ),
Copy link
Member

Choose a reason for hiding this comment

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

This is good. It makes sense that the ETag wouldn't be provided with the URL Metric object in the JSON body since it's not something that the client collects from the document. In this way it is similar to the uuid and url, although in theory the url and etag could be provided with in the urlMetric object even though they will just be ignored.

@@ -216,10 +206,23 @@ function od_optimize_template_output_buffer( string $buffer ): string {
*/
do_action( 'od_register_tag_visitors', $tag_visitor_registry );

$visitors = iterator_to_array( $tag_visitor_registry );
$current_etag = implode( ',', array_keys( $visitors ) );
Copy link
Member

Choose a reason for hiding this comment

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

An important point here: similar to the slug, i think the etag actually should be hashed:

Suggested change
$current_etag = implode( ',', array_keys( $visitors ) );
$current_etag = md5( implode( ',', array_keys( $visitors ) ) );

The key reason here is that when expanding the scope here to address the parent issue #1466, there will be much more data to include in the ETag. So I suggest that there be a new function created, like od_compute_current_etag() which takes $tag_visitor_registry as an argument. For now it could look like:

function od_compute_current_etag( OD_Tag_Visitor_Registry $tag_visitor_registry ) {
    $data = array(
        'tag_visitors' => array_keys( iterator_to_array( $tag_visitor_registry ) ),
    );
    return md5( serialize( $data ) );
}

Then later when working on #1466 the $data can be expanded to include things like the IDs and post_modified times for the posts in the loop, what the current queried object is, and so on.

Copy link
Contributor Author

@ShyamGadde ShyamGadde Nov 28, 2024

Choose a reason for hiding this comment

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

Done in 8fe38f7.

@westonruter
Copy link
Member

The test cases for Embed Optimizer and Image Prioritizer are not fixed yet, as I'm uncertain if the approach used in Optimization Detective's test cases is the best path forward.

Suggestions or feedback on the Optimization Detective test cases would be appreciated before proceeding.

@ShyamGadde I believe I've worked out a solution for the testing problem by introducing a filter for allowing extensions to customize the parameters that go into constructing an ETag. For #1466 this will be useful in case sites want to fine-tune what internal state of a page goes into constructing an ETag.

@westonruter
Copy link
Member

Signing off for the day.

ShyamGadde and others added 12 commits December 1, 2024 22:02
Co-authored-by: Weston Ruter <westonruter@google.com>
…ction constructor

Signed-off-by: Shyamsundar Gadde <shyamsundar.gadde@rtcamp.com>
Signed-off-by: Shyamsundar Gadde <shyamsundar.gadde@rtcamp.com>
Signed-off-by: Shyamsundar Gadde <shyamsundar.gadde@rtcamp.com>
Signed-off-by: Shyamsundar Gadde <shyamsundar.gadde@rtcamp.com>
Signed-off-by: Shyamsundar Gadde <shyamsundar.gadde@rtcamp.com>
Signed-off-by: Shyamsundar Gadde <shyamsundar.gadde@rtcamp.com>
Copy link
Member

@westonruter westonruter left a comment

Choose a reason for hiding this comment

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

Whew! This was more involved than I expected. Great work!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
[Plugin] Optimization Detective Issues for the Optimization Detective plugin [Type] Enhancement A suggestion for improvement of an existing feature
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Activation of plugin that registers a new tag visitor should automatically make URL Metrics stale
2 participants