Open matepaiva opened 3 years ago
I'd find such an interface
a great addition. But I'd also add the value
of set_conditional_logic
to the interface
. Like:
{
institutionalContents {
nodes {
title
excerpt
action { # this name comes from set_conditional_logic.field
conditionalLogicValue # this comes from set_conditional_logic.value
... on NewsletterSubscribeAction { # this name comes from set_conditional_logic.value + set_conditional_logic.field
textFieldPlaceholder
textFieldLabel
buttonText
}
... on LinkAction {
href
label
}
}
}
}
}
@benada002, the conditionalLogicValue
would be more or less the same as the __typename
of the Inline Fragment
, wouldn't it?
Yes, you're completely right. But I think in case your logic is based on a boolean value it would be kind of nice to have it. Or how are planning on handling a boolean value?
Or if you want to show the value somewhere (I don't know how likely this situation is) but in this case you'd have to clean __typename
to use it since the field name is also included in the __typename
, right?
Oh, I see. Because it's actually overriding the action
field (in the example). Maybe we could avoid overriding it nesting all conditional fields in conditionalFields
?
Other thing that I am not sure is how to handle when set_conditional_logic
has other properties, for example:
Field::make( 'text', 'crb_facebook', 'Facebook URL' )
->set_conditional_logic( array(
'relation' => 'AND', // Optional, defaults to "AND"
array(
'field' => 'crb_show_socials',
'value' => 'yes', // Optional, defaults to "". Should be an array if "IN" or "NOT IN" operators are used.
'compare' => '=', // Optional, defaults to "=". Available operators: =, <, >, <=, >=, IN, NOT IN
)
) ),
If you're using an interface (https://graphql.org/learn/schema/#interfaces and https://www.wpgraphql.com/functions/register_graphql_interface_type/) I don't think you need nesting. I also belive a reason field is a better choice, because then you would also get the right type?!
Is your second concern more about the __typename
length if you join it together, and it would have multiple rules (like for the example in your comment: CrbFacebookAndCrbShowSocialsYesAnotherFieldNameAnotherValue
)?
Sorry, I have to step back a bit because I think my initial concept is wrong. To expose the GraphQL query below, I should not use conditional fields. I should use complex fields with multiple groups.
{
institutionalContents {
nodes {
action {
type: __typename
... on InstitutionalContentActionLink {
href
label
style
}
... on InstitutionalContentActionNewsletterSubscribe {
label
style
}
}
}
}
}
So the query above would be something like this in carbon fields:
Container::make('post_meta', 'Configurar ação')
->where('post_type', '=', $post_type)
->add_fields([
Field::make('complex', 'action', 'Ação')
->set_required(true)
->set_max(1)
->add_fields('link', 'Link', [
Field::make('text', 'href', 'href')->set_attribute('placeholder', '/assine-agora ou https://...'),
Field::make('text', 'label', 'Texto')->set_attribute('placeholder', 'ex.: Assine agora'),
Field::make('select', 'style', 'Estilo')
->set_options([
'primary' => 'Primário',
'secondary' => 'Secundário',
'tertiary' => 'Terciário',
])
->set_default_value('primary')
])
->add_fields('newsletter_subscribe', 'Assine à newsletter', [
Field::make('text', 'label', 'Texto')->set_default_value('Assine agora'),
Field::make('select', 'style', 'Estilo')
->set_options([
'primary' => 'Primário',
'secondary' => 'Secundário',
'tertiary' => 'Terciário',
])
->set_default_value('primary')
])
]);
});
That said, I don't think we actually need to create anything special for set_conditional_logic
. My bad for introducing the idea. It's not necessary to expose the set_conditional_logic
because they have nothing to do with the front-office, they are only used to handle back-office logic. For instance, set_conditional_logic
is not exposed via REST.
Although we could create a way to expose automatically the container above as a query. For now I am making it by hand and it's ok because it's a small project, but I think it could be a great improvement in this plugin.
I am using the code below to expose it by hand today:
add_action('graphql_register_types', function () use ($post_type) {
register_graphql_object_type('InstitutionalContentActionLink', ['fields' => [
'label' => ['type' => 'String'],
'href' => ['type' => 'String'],
'style' => ['type' => 'String']
]]);
register_graphql_object_type('InstitutionalContentActionNewsletterSubscribe', ['fields' => [
'label' => ['type' => 'String'],
'style' => ['type' => 'String'],
]]);
register_graphql_union_type('InstitutionalContentAction', [
'typeNames' => [
'InstitutionalContentActionLink',
'InstitutionalContentActionNewsletterSubscribe'
],
'resolveType' => function ($institutionalContentAction) {
$type = $institutionalContentAction['_type'] ?? null;
switch ($type) {
case 'link':
return 'InstitutionalContentActionLink';
case 'newsletter_subscribe':
return 'InstitutionalContentActionNewsletterSubscribe';
default:
return '';
}
}
]);
register_graphql_field('InstitutionalContent', 'action', [
'type' => 'InstitutionalContentAction',
'resolve' => fn ($institutionalContent) => carbon_get_post_meta($institutionalContent->ID, 'action')[0] ?? null
]);
});
I was thinking in a good semantic way of matching Conditional Fields with GraphQL. Something like that:
The idea is using
Inline Fragments
, grouping fields with the sameset_conditional_logic
within the sameCarbon Container
. I don't know if it is a good idea so I want to know your opinion. In the case above, the carbon fields would be something like that:Please have a look @Mooxdesign @ojohnny @moxxuk @benada002 :)