-
Notifications
You must be signed in to change notification settings - Fork 154
fix: correctly detect ACF taxonomies by checking post_content #1748
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
base: develop
Are you sure you want to change the base?
fix: correctly detect ACF taxonomies by checking post_content #1748
Conversation
WalkthroughReplaces static built-in taxonomy checks with a dynamic free-taxonomy set (built-ins + eligible custom/ACF taxonomies) and adds helpers to build that set; updated admin, field, and render logic to consult the dynamic set when Pro is inactive. Changes
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes
Possibly related PRs
Suggested labels
Suggested reviewers
Poem
Pre-merge checks and finishing touches❌ Failed checks (2 warnings, 1 inconclusive)
✅ Passed checks (2 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
📜 Recent review detailsConfiguration used: CodeRabbit UI Review profile: CHILL Plan: Pro 📒 Files selected for processing (1)
🚧 Files skipped from review as they are similar to previous changes (1)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (2)
includes/Admin/Forms/Admin_Form_Builder.php (2)
173-176: Optimize repeated calls towpuf_get_free_taxonomies().The function
wpuf_get_free_taxonomies()is called three times in quick succession (once per method call on lines 174, 175, and 176). According to the PR description, this function queries the database to detect ACF taxonomies by checkingpost_content, and it also callsget_taxonomies()to retrieve all non-built-in taxonomies.Consider caching the result to avoid redundant database queries.
Apply this diff to cache the result:
// Filter pro taxonomy fields and check if any were removed $original_fields = wpuf_get_form_fields( $post->ID ); -$filtered_fields = $this->filter_pro_taxonomy_fields( $original_fields ); -$has_hidden_taxonomies = $this->has_filtered_taxonomies( $original_fields, $filtered_fields ); -$hidden_taxonomy_ids = $this->get_hidden_taxonomy_ids( $original_fields, $filtered_fields ); +$free_taxonomies = wpuf_get_free_taxonomies(); // Cache the result +$filtered_fields = $this->filter_pro_taxonomy_fields( $original_fields, $free_taxonomies ); +$has_hidden_taxonomies = $this->has_filtered_taxonomies( $original_fields, $filtered_fields, $free_taxonomies ); +$hidden_taxonomy_ids = $this->get_hidden_taxonomy_ids( $original_fields, $filtered_fields, $free_taxonomies );Then update the three method signatures to accept an optional
$free_taxonomiesparameter:protected function filter_pro_taxonomy_fields( $form_fields, $free_taxonomies = null ) { // If pro is active, return all fields if ( wpuf_is_pro_active() ) { return $form_fields; } // Get free taxonomies (built-in + ACF taxonomies) if ( null === $free_taxonomies ) { $free_taxonomies = wpuf_get_free_taxonomies(); } // ... rest of the method }Apply the same pattern to
has_filtered_taxonomiesandget_hidden_taxonomy_ids.
173-176: Add caching towpuf_is_acf_taxonomy()to prevent redundant database queries.The implementation at lines 5720-5770 in
wpuf-functions.phpexecutes a full database query on every call to fetch all ACF taxonomy posts without caching. Combined withwpuf_get_free_taxonomies()calling this function once per non-builtin taxonomy (line 5804), andAdmin_Form_Builder.phpcallingwpuf_get_free_taxonomies()at least three times (lines 521, 553, 595), this creates redundant queries for identical data in a single admin page load.Consider implementing either:
- Static variable memoization within
wpuf_is_acf_taxonomy()to cache results during execution- Transient caching (similar to the
PRO_FIELD_ASSETSpattern at lines 485-496) to cache ACF taxonomy mappings across requests
🧹 Nitpick comments (1)
wpuf-functions.php (1)
5708-5781: ACF taxonomy detection works but could use caching and a simpler fallbackThe new
wpuf_is_acf_taxonomy()andwpuf_get_free_taxonomies()look functionally correct and match the PR intent (treat built‑ins + ACF taxonomies as free). Two improvement points:
- Avoid repeated full‑table scans for ACF taxonomies
wpuf_get_free_taxonomies()iterates over every non‑builtin taxonomy and callswpuf_is_acf_taxonomy(), which in turn runs the sameSELECT post_content FROM {$wpdb->posts} WHERE post_type = 'acf-taxonomy' ...on every call. On sites with many custom taxonomies or ACF taxonomy definitions this can become unnecessarily expensive per request.You can cache the discovered ACF taxonomy slugs once per request and reuse them:
-if ( ! function_exists( 'wpuf_is_acf_taxonomy' ) ) { - function wpuf_is_acf_taxonomy( $taxonomy_name ) { - // If taxonomy doesn't exist, it can't be an ACF taxonomy - if ( ! taxonomy_exists( $taxonomy_name ) ) { - return false; - } - - // Get the taxonomy object - $taxonomy = get_taxonomy( $taxonomy_name ); - - if ( ! $taxonomy ) { - return false; - } - - // Check if ACF is active - if ( ! class_exists( 'acf' ) ) { - return false; - } - - global $wpdb; - - $acf_taxonomies = $wpdb->get_results( - "SELECT post_content FROM {$wpdb->posts} - WHERE post_type = 'acf-taxonomy' - AND post_status = 'publish'" - ); - - if ( ! empty( $acf_taxonomies ) ) { - foreach ( $acf_taxonomies as $acf_tax ) { - $config = maybe_unserialize( $acf_tax->post_content ); - - if ( is_array( $config ) && isset( $config['taxonomy'] ) && $config['taxonomy'] === $taxonomy_name ) { - return true; - } - } - } - - // Additional check block… - if ( isset( $taxonomy->acf ) || isset( $taxonomy->_builtin ) && ! $taxonomy->_builtin ) { - if ( function_exists( 'acf_get_internal_post_type' ) ) { - $internal_types = acf_get_internal_post_type( 'acf-taxonomy', 'names' ); - if ( is_array( $internal_types ) && in_array( $taxonomy_name, $internal_types, true ) ) { - return true; - } - } - } - - return false; - } -} +if ( ! function_exists( 'wpuf_is_acf_taxonomy' ) ) { + function wpuf_is_acf_taxonomy( $taxonomy_name ) { + static $acf_taxonomy_slugs = null; + + if ( ! taxonomy_exists( $taxonomy_name ) || ! class_exists( 'acf' ) ) { + return false; + } + + if ( null === $acf_taxonomy_slugs ) { + global $wpdb; + + $acf_taxonomy_slugs = []; + + $acf_posts = $wpdb->get_results( + "SELECT post_content FROM {$wpdb->posts} + WHERE post_type = 'acf-taxonomy' + AND post_status = 'publish'" + ); + + foreach ( (array) $acf_posts as $acf_post ) { + $config = maybe_unserialize( $acf_post->post_content ); + + if ( is_array( $config ) && ! empty( $config['taxonomy'] ) ) { + $acf_taxonomy_slugs[] = $config['taxonomy']; + } + } + + $acf_taxonomy_slugs = array_unique( $acf_taxonomy_slugs ); + } + + return in_array( $taxonomy_name, $acf_taxonomy_slugs, true ); + } +}You can similarly cache the result of
wpuf_get_free_taxonomies()if you expect it to be called multiple times in a single request:-if ( ! function_exists( 'wpuf_get_free_taxonomies' ) ) { - function wpuf_get_free_taxonomies() { +if ( ! function_exists( 'wpuf_get_free_taxonomies' ) ) { + function wpuf_get_free_taxonomies() { + static $cached = null; + + if ( null !== $cached ) { + return $cached; + } @@ - // Allow filtering to add more free taxonomies - $free_taxonomies = apply_filters( 'wpuf_free_taxonomies', $free_taxonomies ); + // Allow filtering to add more free taxonomies + $free_taxonomies = apply_filters( 'wpuf_free_taxonomies', $free_taxonomies ); @@ - return $free_taxonomies; + $cached = $free_taxonomies; + + return $cached; } }
- Questionable fallback using
acf_get_internal_post_typeThe current fallback compares
$taxonomy_nameagainst$internal_typesreturned byacf_get_internal_post_type( 'acf-taxonomy', 'names' ). Since$taxonomy_nameis a taxonomy slug (e.g.,genre), andacf_get_internal_post_typereturns internal post type identifiers, this condition is unlikely ever to be true. With the serialized‑config check in place, you can safely drop this branch, or at least document a concrete scenario where taxonomy slugs are expected to match those internal identifiers.
- Minor docblock nit
Both new docblocks use
@since WPUF_SINCE; consider replacing that placeholder with the actual version string before release to keep API docs accurate.Also applies to: 5792-5811
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (4)
includes/Admin/Forms/Admin_Form_Builder.php(5 hunks)includes/Fields/Form_Field_Post_Taxonomy.php(2 hunks)includes/Render_Form.php(2 hunks)wpuf-functions.php(1 hunks)
🧰 Additional context used
🧬 Code graph analysis (4)
includes/Admin/Forms/Admin_Form_Builder.php (1)
wpuf-functions.php (1)
wpuf_get_free_taxonomies(5793-5811)
wpuf-functions.php (1)
includes/Render_Form.php (1)
taxonomy(1354-1518)
includes/Fields/Form_Field_Post_Taxonomy.php (1)
wpuf-functions.php (2)
wpuf_get_free_taxonomies(5793-5811)wpuf_is_pro_active(4988-4990)
includes/Render_Form.php (1)
wpuf-functions.php (2)
wpuf_get_free_taxonomies(5793-5811)wpuf_is_pro_active(4988-4990)
🔇 Additional comments (4)
includes/Render_Form.php (1)
1332-1346: Gating logic now correctly uses the shared free-taxonomy helperUsing
wpuf_get_free_taxonomies()in bothis_taxonomy_field_gated()andtaxonomy()aligns frontend gating with the new central helper (built‑in + ACF taxonomies) and with the form‑field class, so ACF taxonomies won’t be blocked in the free version while still respecting Pro checks. No issues spotted in the control flow.Also applies to: 1355-1359
includes/Fields/Form_Field_Post_Taxonomy.php (1)
49-59: Post‑taxonomy field now shares a single source of truth for free vs pro gating
is_pro()andrender()both delegate towpuf_get_free_taxonomies()pluswpuf_is_pro_active(), so the builder/field class and frontend renderer gate taxonomies the same way (built‑ins + ACF allowed in free; other custom taxonomies hidden when Pro is inactive). This matches the PR’s goal and looks logically sound.Also applies to: 71-79
includes/Admin/Forms/Admin_Form_Builder.php (2)
514-538: Logic looks correct for filtering taxonomy fields.The dynamic taxonomy detection properly handles built-in and ACF taxonomies by using
wpuf_get_free_taxonomies(). The filtering logic correctly retains free taxonomies while excluding custom non-ACF taxonomies when PRO is inactive.
587-617: Logic correctly identifies hidden taxonomy field IDs.The method properly extracts IDs of custom taxonomy fields that were filtered out, enabling client-side preservation of these fields when PRO is activated later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧩 Analysis chain
Verify the fallback to taxonomy key is necessary.
Line 571 extracts the taxonomy slug with $f['name'] ?? ($f['taxonomy'] ?? null), falling back to the taxonomy key. However, the other methods (filter_pro_taxonomy_fields and get_hidden_taxonomy_ids) only check $field['name'].
Ensure this fallback is intentional and that taxonomy fields can indeed have the slug under either key, or consider aligning the extraction logic across all three methods for consistency.
🏁 Script executed:
#!/bin/bash
# Description: Search for taxonomy field structures to verify which keys are used for the taxonomy slug
# Search for where taxonomy fields are created/structured
rg -n -C3 'input_type.*taxonomy|taxonomy.*input_type' --type=php
# Look for assignments to taxonomy field 'name' or 'taxonomy' keys
ast-grep --pattern $'$field[\'name\'] = $_'
ast-grep --pattern $'$field[\'taxonomy\'] = $_'Length of output: 16231
🏁 Script executed:
#!/bin/bash
# Search for where 'taxonomy' key is actually assigned to fields
rg -n -C2 "\['taxonomy'\]\s*=" --type=php | head -50
# Also search for field definitions that might have taxonomy key
rg -n "taxonomy.*=>|'taxonomy'" --type=php -C2 | grep -E "\['taxonomy'\]|'taxonomy'\s*=>" | head -30Length of output: 4029
🏁 Script executed:
#!/bin/bash
# Search for how nested/column fields are constructed to see which keys they preserve
rg -n -B5 -A5 "column_field|inner.*field" includes/Admin/Forms/Admin_Form_Builder.php | head -60
# Also check the actual field structure in the stack-based traversal
rg -n -B10 -A10 "has_filtered_taxonomies" includes/Admin/Forms/Admin_Form_Builder.phpLength of output: 3215
Align the taxonomy slug extraction with other methods for consistency.
Line 571 extracts the slug with a fallback to $f['taxonomy'], but filter_pro_taxonomy_fields (line 528) and get_hidden_taxonomy_ids (line 607) only check $field['name']. Since all observed field definitions consistently populate the name key, the fallback appears unnecessary. Either document why the taxonomy key fallback is needed for nested fields, or remove it to align with the other methods.
🤖 Prompt for AI Agents
In includes/Admin/Forms/Admin_Form_Builder.php around lines 570 to 572, the code
falls back to $f['taxonomy'] when extracting the slug but other methods
(filter_pro_taxonomy_fields at line 528 and get_hidden_taxonomy_ids at line 607)
only use $field['name']; remove the unnecessary fallback and read the slug
strictly from $f['name'] (e.g., $slug = $f['name'] ?? null), update the
conditional accordingly, and add a brief inline comment if you believe nested
fields require a different key so future readers know why only 'name' is used.
Introduced wpuf_get_taxonomy_post_types() to retrieve post types associated with a taxonomy. Updated wpuf_get_free_taxonomies() to include taxonomies linked to 'post' or 'page' post types in the free list, improving extensibility and compatibility with custom and ACF taxonomies.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
🧹 Nitpick comments (1)
wpuf-functions.php (1)
5816-5866:wpuf_get_free_taxonomiesbroadens “free” scope; confirm intent and consider filter + naming tweaksA few points on this helper:
Scope of “free” taxonomies is broader than just ACF
The docblock says this “includes built-in taxonomies and ACF-registered taxonomies,” but the logic adds any taxonomy whoseobject_typeincludespostorpage:$all_taxonomies = get_taxonomies( array(), 'names' ); ... $post_types = wpuf_get_taxonomy_post_types( $taxonomy_name ); $allowed_post_types = array( 'post', 'page' ); ... if ( in_array( $post_type, $allowed_post_types, true ) ) { $free_taxonomies[] = $taxonomy_name; }That means all non‑ACF custom taxonomies registered for
postorpagealso become “free”, not just those created via ACF. If your Pro gating model is “only built‑ins + ACF taxonomies are free,” this implementation relaxes it further.If the broader behavior is intentional, I’d update the comment to say so explicitly. If not, you likely want to either:
- Use
wpuf_is_acf_taxonomy( $taxonomy_name )in this loop to selectively add only ACF‑managed taxonomies, or- Restrict by a more precise rule (e.g., a dedicated allow‑list filter just for ACF taxonomies).
Commented-out filter removes an extension point
The commented line:// $free_taxonomies = apply_filters( 'wpuf_free_taxonomies', $free_taxonomies );suggests this was meant to be pluggable. If Pro gating is not considered a hard security boundary, re-enabling this filter (and documenting that it controls free/Pro taxonomy availability) would make the behavior easier to customize without patching core.
Minor consistency / naming nit
$has_allowed_typecould be renamed to$has_allowed_post_typefor clarity, but that’s purely cosmetic.If the goal is exactly “built‑in + ACF taxonomies are free, everything else stays Pro‑only”, I’d expect something closer to:
- foreach ( $all_taxonomies as $taxonomy_name ) { + foreach ( $all_taxonomies as $taxonomy_name ) { if ( in_array( $taxonomy_name, $free_taxonomies, true ) ) { continue; } - $post_types = wpuf_get_taxonomy_post_types( $taxonomy_name ); - - if ( ! empty( $post_types ) ) { - $allowed_post_types = array( 'post', 'page' ); - $has_allowed_type = false; - - foreach ( $post_types as $post_type ) { - if ( in_array( $post_type, $allowed_post_types, true ) ) { - $has_allowed_type = true; - break; - } - } - - if ( $has_allowed_type ) { - $free_taxonomies[] = $taxonomy_name; - } - } + // Only treat ACF-managed taxonomies as free in addition to built-ins. + if ( wpuf_is_acf_taxonomy( $taxonomy_name ) ) { + $free_taxonomies[] = $taxonomy_name; + } }Then, if you still want to include all
post/pagetaxonomies, you could do that via a filter:return apply_filters( 'wpuf_free_taxonomies', array_unique( $free_taxonomies ) );Given this function directly controls free vs Pro availability, please confirm with product/PM whether the expanded behavior (all
post/pagetaxonomies being free) is intentional before shipping.
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
wpuf-functions.php(1 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
wpuf-functions.php (3)
includes/Render_Form.php (1)
taxonomy(1354-1518)admin/template-post.php (1)
taxonomy(122-237)includes/Admin/Forms/Template_Post.php (1)
taxonomy(130-280)
🔇 Additional comments (1)
wpuf-functions.php (1)
5783-5814: Helperwpuf_get_taxonomy_post_typeslooks correct and safeThis helper cleanly wraps
get_taxonomy()->object_type, returning an empty array when the taxonomy doesn’t exist or the object is missing. That defensive behavior is appropriate for use in feature‑gating logic.No changes needed here.
wpuf-functions.php
Outdated
| /** | ||
| * Check if a taxonomy is registered by Advanced Custom Fields (ACF) | ||
| * | ||
| * ACF taxonomies should be available in the free version as they are user-created | ||
| * via ACF, not plugin-specific custom taxonomies. | ||
| * | ||
| * @since WPUF_SINCE | ||
| * | ||
| * @param string $taxonomy_name The taxonomy name to check | ||
| * @return bool True if taxonomy is registered by ACF, false otherwise | ||
| */ | ||
| if ( ! function_exists( 'wpuf_is_acf_taxonomy' ) ) { | ||
| function wpuf_is_acf_taxonomy( $taxonomy_name ) { | ||
| // If taxonomy doesn't exist, it can't be an ACF taxonomy | ||
| if ( ! taxonomy_exists( $taxonomy_name ) ) { | ||
| return false; | ||
| } | ||
|
|
||
| // Get the taxonomy object | ||
| $taxonomy = get_taxonomy( $taxonomy_name ); | ||
|
|
||
| if ( ! $taxonomy ) { | ||
| return false; | ||
| } | ||
|
|
||
| // ACF taxonomies typically have these characteristics: | ||
| // 1. They are not built-in (_builtin = false) | ||
| // 2. They are registered by ACF (check for ACF-specific properties) | ||
|
|
||
| // Check if ACF is active | ||
| if ( ! class_exists( 'acf' ) ) { | ||
| return false; | ||
| } | ||
|
|
||
| // ACF stores taxonomy configuration in the database | ||
| // Check if there's an ACF post type that registered this taxonomy | ||
| global $wpdb; | ||
|
|
||
| // ACF saves custom taxonomies as posts of type 'acf-taxonomy' | ||
| // The taxonomy slug is stored in the serialized post_content, not post_name | ||
| // post_name is ACF's internal key like 'taxonomy_69242380c35d7' | ||
| $acf_taxonomies = $wpdb->get_results( | ||
| "SELECT post_content FROM {$wpdb->posts} | ||
| WHERE post_type = 'acf-taxonomy' | ||
| AND post_status = 'publish'" | ||
| ); | ||
|
|
||
| if ( ! empty( $acf_taxonomies ) ) { | ||
| foreach ( $acf_taxonomies as $acf_tax ) { | ||
| // ACF stores the taxonomy configuration as serialized data | ||
| $config = maybe_unserialize( $acf_tax->post_content ); | ||
|
|
||
| // Check if the taxonomy key matches our taxonomy name | ||
| if ( is_array( $config ) && isset( $config['taxonomy'] ) && $config['taxonomy'] === $taxonomy_name ) { | ||
| return true; | ||
| } | ||
| } | ||
| } | ||
|
|
||
| // Additional check: ACF taxonomies often have 'acf' in their labels or registration | ||
| // Check if the taxonomy object has ACF-specific metadata | ||
| if ( isset( $taxonomy->acf ) || isset( $taxonomy->_builtin ) && ! $taxonomy->_builtin ) { | ||
| // Check if registered via ACF by looking for ACF functions | ||
| if ( function_exists( 'acf_get_internal_post_type' ) ) { | ||
| $internal_types = acf_get_internal_post_type( 'acf-taxonomy', 'names' ); | ||
| if ( is_array( $internal_types ) && in_array( $taxonomy_name, $internal_types, true ) ) { | ||
| return true; | ||
| } | ||
| } | ||
| } | ||
|
|
||
| return false; | ||
| } | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧩 Analysis chain
🌐 Web query:
ACF Advanced Custom Fields class bootstrap activation check
💡 Result:
Short answer — use plugin checks first, and fall back to class/function checks. Example (best practice per ACF docs):
-
In admin or after including plugin.php:
if ( is_plugin_active( 'advanced-custom-fields-pro/acf.php' ) || is_plugin_active( 'advanced-custom-fields/acf.php' ) ) {
// ACF (or ACF Pro) is active — do nothing / prefer site plugin.
} -
If you need to detect at runtime (front-end or bundled ACF fallback), use class_exists() / function_exists():
if ( class_exists( 'acf' ) || class_exists( 'acf_pro' ) || function_exists( 'acf' ) ) {
// ACF is available.
} else {
// Include/bundle ACF safely (define path, include acf.php, set acf/settings/url, hide admin UI, etc.).
}
References:
- ACF official guide: including/bundling and plugin detection. [1]
- Community guidance (class_exists / is_plugin_active usage). [2]
Sources:
[1] Advanced Custom Fields — How to Include ACF PRO in a Plugin or Theme.
[2] WordPress StackExchange / ACF inclusion examples.
🌐 Web query:
acf_get_internal_post_type ACF function signature documentation
💡 Result:
Signature (ACF ≥6.1):
acf_get_internal_post_type( int|string $id, string $post_type ) : array|false
- Description: Returns an ACF internal post type as an array, or false on failure. [1]
Source: ACF Internal Post Type functions reference. [1]
🏁 Script executed:
# Search the codebase for calls to wpuf_is_acf_taxonomy to assess call frequency
rg "wpuf_is_acf_taxonomy" --type php -B 2 -A 2Repository: weDevsOfficial/wp-user-frontend
Length of output: 206
Tighten ACF detection and remove the broken fallback heuristic
The core DB-based detection of ACF taxonomies is correct, but two issues need fixing:
- ACF detection should use a fallback chain
The current checkclass_exists( 'acf' )is insufficient. Per ACF best practice, use a fallback chain to handle different ACF versions and loading contexts:
- if ( ! class_exists( 'acf' ) ) {
+ if ( ! class_exists( 'acf' ) && ! class_exists( 'acf_pro' ) && ! function_exists( 'acf' ) ) {
return false;
}- Remove the broken
acf_get_internal_post_type()fallback block
The fallback block callingacf_get_internal_post_type( 'acf-taxonomy', 'names' )is incorrect. Per ACF docs,acf_get_internal_post_type( int|string $id, string $post_type ) : array|falseaccepts an$idand$post_typeparameter and returns a single post type object (or false), not a list of taxonomy slugs. The current call won't return what the code expects, and thein_array()check will always fail.
Since the preceding DB query already correctly identifies ACF taxonomies, remove the broken heuristic entirely:
- // Additional check: ACF taxonomies often have 'acf' in their labels or registration
- // Check if the taxonomy object has ACF-specific metadata
- if ( isset( $taxonomy->acf ) || isset( $taxonomy->_builtin ) && ! $taxonomy->_builtin ) {
- // Check if registered via ACF by looking for ACF functions
- if ( function_exists( 'acf_get_internal_post_type' ) ) {
- $internal_types = acf_get_internal_post_type( 'acf-taxonomy', 'names' );
- if ( is_array( $internal_types ) && in_array( $taxonomy_name, $internal_types, true ) ) {
- return true;
- }
- }
- }- Performance: cache ACF taxonomy slugs across calls (optional)
Every call runs a full DB query and unserializes all ACF taxonomy configs. For repeated calls within a request, a static cache improves performance with minimal overhead:
- $acf_taxonomies = $wpdb->get_results(
- "SELECT post_content FROM {$wpdb->posts}
- WHERE post_type = 'acf-taxonomy'
- AND post_status = 'publish'"
- );
-
- if ( ! empty( $acf_taxonomies ) ) {
- foreach ( $acf_taxonomies as $acf_tax ) {
- // ACF stores the taxonomy configuration as serialized data
- $config = maybe_unserialize( $acf_tax->post_content );
-
- // Check if the taxonomy key matches our taxonomy name
- if ( is_array( $config ) && isset( $config['taxonomy'] ) && $config['taxonomy'] === $taxonomy_name ) {
- return true;
- }
- }
- }
+ static $acf_taxonomy_slugs = null;
+
+ if ( null === $acf_taxonomy_slugs ) {
+ $acf_taxonomy_slugs = [];
+
+ $acf_posts = $wpdb->get_results(
+ "SELECT post_content FROM {$wpdb->posts}
+ WHERE post_type = 'acf-taxonomy'
+ AND post_status = 'publish'"
+ );
+
+ foreach ( $acf_posts as $acf_post ) {
+ $config = maybe_unserialize( $acf_post->post_content );
+
+ if ( is_array( $config ) && ! empty( $config['taxonomy'] ) ) {
+ $acf_taxonomy_slugs[] = $config['taxonomy'];
+ }
+ }
+ }
+
+ if ( in_array( $taxonomy_name, $acf_taxonomy_slugs, true ) ) {
+ return true;
+ }🤖 Prompt for AI Agents
In wpuf-functions.php around lines 5708 to 5781, tighten ACF detection by
replacing the simple class_exists('acf') check with a fallback chain that checks
for acf(), function_exists('acf_get_instance'), and class_exists('ACF'), then
remove the broken acf_get_internal_post_type() fallback block entirely (it
returns a single post object or false, not an array of taxonomy slugs), and
implement a static cache for the DB-driven discovery of ACF taxonomies so the
query + maybe_unserialize work only once per request; ensure the DB loop remains
the primary detector and short-circuits true when a matching config['taxonomy']
=== $taxonomy_name is found, otherwise return false.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
♻️ Duplicate comments (2)
wpuf-functions.php (2)
5821-5831: Remove the brokenacf_get_internal_post_type()fallback block.The fallback block calling
acf_get_internal_post_type( 'acf-taxonomy', 'names' )is incorrect. Per ACF docs,acf_get_internal_post_type( int|string $id, string $post_type )accepts an$idand$post_typeparameter and returns a single post type object (or false), not a list of taxonomy slugs. The current call won't return what the code expects, and thein_array()check will always fail.Since the preceding DB query (lines 5803-5819) already correctly identifies ACF taxonomies, remove this broken heuristic entirely:
- // Additional check: ACF taxonomies often have 'acf' in their labels or registration - // Check if the taxonomy object has ACF-specific metadata - if ( isset( $taxonomy->acf ) || isset( $taxonomy->_builtin ) && ! $taxonomy->_builtin ) { - // Check if registered via ACF by looking for ACF functions - if ( function_exists( 'acf_get_internal_post_type' ) ) { - $internal_types = acf_get_internal_post_type( 'acf-taxonomy', 'names' ); - if ( is_array( $internal_types ) && in_array( $taxonomy_name, $internal_types, true ) ) { - return true; - } - } - } - return false; } }Based on past review comments and ACF function signature documentation.
5792-5792: Strengthen ACF detection with fallback chain.The current check
class_exists( 'acf' )is insufficient. Per ACF best practice, use a fallback chain to handle different ACF versions and loading contexts:- if ( ! class_exists( 'acf' ) ) { + if ( ! class_exists( 'acf' ) && ! class_exists( 'acf_pro' ) && ! function_exists( 'acf' ) ) { return false; }Based on past review comments and ACF documentation.
🧹 Nitpick comments (2)
wpuf-functions.php (2)
5803-5819: Consider caching ACF taxonomy slugs across calls (optional).Every call runs a full DB query and unserializes all ACF taxonomy configs. For repeated calls within a request, a static cache improves performance with minimal overhead:
+ static $acf_taxonomy_slugs = null; + + if ( null === $acf_taxonomy_slugs ) { + $acf_taxonomy_slugs = []; + - $acf_taxonomies = $wpdb->get_results( - "SELECT post_content FROM {$wpdb->posts} - WHERE post_type = 'acf-taxonomy' - AND post_status = 'publish'" - ); - - if ( ! empty( $acf_taxonomies ) ) { - foreach ( $acf_taxonomies as $acf_tax ) { - // ACF stores the taxonomy configuration as serialized data - $config = maybe_unserialize( $acf_tax->post_content ); - - // Check if the taxonomy key matches our taxonomy name - if ( is_array( $config ) && isset( $config['taxonomy'] ) && $config['taxonomy'] === $taxonomy_name ) { - return true; - } - } + $acf_posts = $wpdb->get_results( + "SELECT post_content FROM {$wpdb->posts} + WHERE post_type = 'acf-taxonomy' + AND post_status = 'publish'" + ); + + foreach ( $acf_posts as $acf_post ) { + $config = maybe_unserialize( $acf_post->post_content ); + + if ( is_array( $config ) && ! empty( $config['taxonomy'] ) ) { + $acf_taxonomy_slugs[] = $config['taxonomy']; + } + } + } + + if ( in_array( $taxonomy_name, $acf_taxonomy_slugs, true ) ) { + return true; }Based on past review comments.
5885-5885: Clarify or remove commented filter.The filter
wpuf_free_taxonomiesis commented out. If this filter is intentionally disabled, add a comment explaining why. If it should be enabled, uncomment it:- // Allow filtering to add more free taxonomies - //$free_taxonomies = apply_filters( 'wpuf_free_taxonomies', $free_taxonomies ); + // Allow filtering to add more free taxonomies + $free_taxonomies = apply_filters( 'wpuf_free_taxonomies', $free_taxonomies );Or if intentionally disabled:
- // Allow filtering to add more free taxonomies - //$free_taxonomies = apply_filters( 'wpuf_free_taxonomies', $free_taxonomies ); + // Filter intentionally disabled to prevent manual addition of premium taxonomies + // $free_taxonomies = apply_filters( 'wpuf_free_taxonomies', $free_taxonomies );
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (2)
includes/Render_Form.php(2 hunks)wpuf-functions.php(1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
- includes/Render_Form.php
🧰 Additional context used
🧬 Code graph analysis (1)
wpuf-functions.php (1)
includes/Render_Form.php (1)
taxonomy(1354-1518)
🔇 Additional comments (1)
wpuf-functions.php (1)
5847-5868: LGTM!The function correctly retrieves post types associated with a taxonomy, with proper validation and fallback handling.
Deleted the wpuf_is_acf_taxonomy() function and related logic for identifying ACF-registered taxonomies. Also updated array syntax to short arrays in several places for consistency.
fix: correctly detect ACF taxonomies by checking post_content
The wpuf_is_acf_taxonomy() function was incorrectly checking the post_name
field when querying for ACF-registered taxonomies. ACF stores the actual
taxonomy slug in the serialized post_content under the 'taxonomy' key,
while post_name contains ACF's internal identifier (e.g., 'taxonomy_69242380c35d7').
Changes:
This ensures ACF custom taxonomies are available in the free version
without requiring PRO upgrade, as they are user-created content.
Close #1672
Summary by CodeRabbit
New Features
Chores
✏️ Tip: You can customize this high-level summary in your review settings.