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

feat: improved handling of clone and group fields #193

Merged
merged 25 commits into from
Apr 24, 2024
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
29da8c9
- this allows the Schema to load, but still doesn't fully solve the p…
jasonbahl Apr 5, 2024
dfd3701
- update Registry to determine clone interfaces that should be applie…
jasonbahl Apr 8, 2024
5c23a50
- composer fix-cs
jasonbahl Apr 8, 2024
2164ffb
- update repeater
jasonbahl Apr 8, 2024
7a43e86
- update logic in the clone field to better handle prefixed and non-p…
jasonbahl Apr 8, 2024
c804b07
- add tests for issue 172 including specific ACF Field Group Exports
jasonbahl Apr 9, 2024
29736bb
- composer check-cs / fix-cs
jasonbahl Apr 9, 2024
75329b1
- modify the JavaScript in main.js that collects form fields to send …
jasonbahl Apr 17, 2024
499c392
- bail earlier if field groups are already identified as having been …
jasonbahl Apr 17, 2024
d23170a
- prevent duplicate registration of connections for WPGraphQL v1.24 a…
jasonbahl Apr 17, 2024
4bf0557
Merge branch 'fix/interface-recursion' into fix/172-cloning-group-fields
jasonbahl Apr 17, 2024
112f8cb
- phpcs
jasonbahl Apr 17, 2024
c703c0c
- update phpstan/constants.php to be compatible with latest stubs
jasonbahl Apr 18, 2024
ca9adbb
- update phpstan/constants.php to be compatible with latest stubs
jasonbahl Apr 18, 2024
7b5d0f7
- update `get_parent_graphql_type_name` to reduce unnecessary recursion
jasonbahl Apr 18, 2024
ff391e8
- use acf_get_fields instead of acf_get_raw_fields
jasonbahl Apr 18, 2024
4c6e695
- update FieldConfig to check for values prefixed with `_` for resolu…
jasonbahl Apr 18, 2024
829ca4e
- composer fix-cs
jasonbahl Apr 18, 2024
1079ce3
- update app.setup.sh to allow testing against different branches of …
jasonbahl Apr 19, 2024
e4761ca
- add test for issue #197 (test passes against this PR branch: https:…
jasonbahl Apr 19, 2024
24152cf
- revert the change to acf_get_raw_fields back to acf_get_fields
jasonbahl Apr 22, 2024
43d2b91
- add another test for issue 172 (noted in the comments)
jasonbahl Apr 22, 2024
7ebc8a4
- composer fix-phpcs
jasonbahl Apr 22, 2024
6f56781
Merge commit 'd44413e138f947625195405be861d734b3cf6d4d' into fix/172-…
jasonbahl Apr 23, 2024
054a010
- revert the change to use acf_get_fields instead of acf_get_raw_fields
jasonbahl Apr 24, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
39 changes: 14 additions & 25 deletions src/FieldType/CloneField.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,21 @@ public static function register_field_type(): void {
'clone',
[
'graphql_type' => static function ( FieldConfig $field_config, AcfGraphQLFieldType $acf_field_type ) {

$sub_field_group = $field_config->get_raw_acf_field();
$parent_type = $field_config->get_parent_graphql_type_name( $sub_field_group );
$field_name = $field_config->get_graphql_field_name();
$registry = $field_config->get_registry();
$type_name = Utils::format_type_name( $parent_type . ' ' . $field_name );
$prefix_name = $sub_field_group['prefix_name'] ?? false;

// If the "Clone" field has not set a "prefix_name",
// return NULL to prevent registering a new type
// The cloned
if ( ! $prefix_name ) {
return 'NULL';
}

$cloned_fields = array_filter(
array_map(
static function ( $cloned ) {
Expand All @@ -44,38 +52,19 @@ static function ( $cloned ) use ( $field_config ) {
)
);


if ( ! empty( $cloned_group_interfaces ) ) {
if ( ! $prefix_name ) {
register_graphql_interfaces_to_types( $cloned_group_interfaces, [ $parent_type ] );
} else {
$type_name = self::register_prefixed_clone_field_type( $type_name, $sub_field_group, $cloned_fields, $field_config );
register_graphql_interfaces_to_types( $cloned_group_interfaces, [ $type_name ] );
return $type_name;
}
$type_name = self::register_prefixed_clone_field_type( $type_name, $sub_field_group, $cloned_fields, $field_config );
register_graphql_interfaces_to_types( $cloned_group_interfaces, [ $type_name ] );
return $type_name;
}


// If the "Clone" field has cloned individual fields
if ( ! empty( $cloned_fields ) ) {

// If the clone field is NOT set to use "prefix_name"
if ( ! $prefix_name ) {

// Map over the cloned fields and register them to the parent type
foreach ( $cloned_fields as $cloned_field ) {
$field_config = $registry->map_acf_field_to_graphql( $cloned_field, $sub_field_group );
if ( ! empty( $field_config['name'] ) ) {
register_graphql_field( $parent_type, $field_config['name'], $field_config );
}
}

// If the Clone field is set to use "prefix_name"
// Register a new Object Type with the cloned fields, and return
// the new type.
} else {
return self::register_prefixed_clone_field_type( $type_name, $sub_field_group, $cloned_fields, $field_config );
}
return self::register_prefixed_clone_field_type( $type_name, $sub_field_group, $cloned_fields, $field_config );
}

// Bail by returning a NULL type
return 'NULL';
},
Expand Down
2 changes: 1 addition & 1 deletion src/FieldType/FlexibleContent.php
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,7 @@ static function ( $field ) use ( $layout ) {
$layout_sub_fields = ! empty( $layout['sub_fields'] ) && is_array( $layout['sub_fields'] ) ? $layout['sub_fields'] : [];

$layout['sub_fields'] = array_merge( $sub_fields, $layout_sub_fields );

$layouts[] = $layout;
}
}
Expand Down
32 changes: 32 additions & 0 deletions src/FieldType/Group.php
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,38 @@ public static function register_field_type(): void {
$sub_field_group['graphql_field_name'] = $type_name;
$sub_field_group['parent'] = $sub_field_group['key'];

// Determine if the group is a clone field
$cloned_type = null;

// if the field group is actually a cloned field group, we
// can return the GraphQL Type of the cloned field group
if ( isset( $sub_field_group['_clone'] ) ) {
$cloned_from = acf_get_field( $sub_field_group['_clone'] );

if ( ! empty( $cloned_from['clone'] ) && is_array( $cloned_from['clone'] ) ) {
foreach ( $cloned_from['clone'] as $clone_field ) {
$cloned_group = acf_get_field_group( $clone_field );

if ( ! $cloned_group ) {
continue;
}

if ( ! $field_config->get_registry()->should_field_group_show_in_graphql( $cloned_group ) ) {
continue;
}

$cloned_type = $field_config->get_registry()->get_field_group_graphql_type_name( $cloned_group );
break;
}
}
}

// If the group is a clone field, return the cloned type instead of registering
// another Type in the registry
if ( $cloned_type ) {
return Utils::format_type_name( $cloned_type . ' ' . $field_name );
}

$field_config->get_registry()->register_acf_field_groups_to_graphql(
[
$sub_field_group,
Expand Down
35 changes: 29 additions & 6 deletions src/FieldType/Repeater.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,15 +24,38 @@ public static function register_field_type(): void {
$sub_field_group['graphql_field_name'] = $type_name;
$sub_field_group['locations'] = null;

if ( ! empty( $sub_field_group['__key'] ) ) {
$cloned_from = acf_get_field( $sub_field_group['__key'] );
$cloned_parent = ! empty( $cloned_from ) ? $field_config->get_parent_graphql_type_name( $cloned_from ) : null;
if ( ! empty( $cloned_parent ) ) {
$type_name = Utils::format_type_name( $cloned_parent . ' ' . $field_name );
return [ 'list_of' => $type_name ];
// Determine if the group is a clone field
$cloned_type = null;

// if the field group is actually a cloned field group, we
// can return the GraphQL Type of the cloned field group
if ( isset( $sub_field_group['_clone'] ) ) {
$cloned_from = acf_get_field( $sub_field_group['_clone'] );

if ( ! empty( $cloned_from['clone'] ) && is_array( $cloned_from['clone'] ) ) {
foreach ( $cloned_from['clone'] as $clone_field ) {
$cloned_group = acf_get_field_group( $clone_field );

if ( ! $cloned_group ) {
continue;
}

if ( ! $field_config->get_registry()->should_field_group_show_in_graphql( $cloned_group ) ) {
continue;
}

$cloned_type = $field_config->get_registry()->get_field_group_graphql_type_name( $cloned_group );
break;
}
}
}

// If the group is a clone field, return the cloned type instead of registering
// another Type in the registry
if ( $cloned_type ) {
return [ 'list_of' => Utils::format_type_name( $cloned_type . ' ' . $field_name ) ];
}


$field_config->get_registry()->register_acf_field_groups_to_graphql(
[
Expand Down
34 changes: 31 additions & 3 deletions src/Registry.php
Original file line number Diff line number Diff line change
Expand Up @@ -311,16 +311,44 @@ public function register_initial_graphql_types(): void {
*
* @param array<mixed> $acf_field_group The ACF Field Group config
*
* @return array<mixed>
* @return array<string> The interface names that the Field Group should apply
* @throws \GraphQL\Error\Error
*/
public function get_field_group_interfaces( array $acf_field_group ): array {
$fields_interface = $this->get_field_group_graphql_type_name( $acf_field_group ) . '_Fields';
$interfaces = isset( $acf_field_group['interfaces'] ) && is_array( $acf_field_group['interfaces'] ) ? $acf_field_group['interfaces'] : [];
$interfaces[] = 'AcfFieldGroup';
$interfaces[] = $fields_interface;
$interfaces = array_unique( array_values( $interfaces ) );
return array_unique( $interfaces );

$fields = $this->get_acf_fields( $acf_field_group );
$clone_field_interfaces = [];
if ( ! empty( $fields ) ) {
foreach ( $fields as $field ) {
// if the field is a clone field, track it
if ( ! empty( $field['clone'] ) && is_array( $field['clone'] ) ) {
foreach ( $field['clone'] as $clone_field ) {
$cloned_group = acf_get_field_group( $clone_field );

if ( ! $cloned_group ) {
continue;
}

if ( ! $this->should_field_group_show_in_graphql( $cloned_group ) ) {
continue;
}

$cloned_type_name = $this->get_field_group_graphql_type_name( $cloned_group );
$clone_field_interfaces[] = $cloned_type_name . '_Fields';
}
}
}
}

if ( ! empty( $clone_field_interfaces ) ) {
$interfaces = array_merge( $interfaces, $clone_field_interfaces );
}

return array_unique( array_values( $interfaces ) );
}

/**
Expand Down
Loading