Hi ,

Thanks for the awesome module. With the help of this module I have created a custom route to display multiple content types. And I also checked the include,sort and pagination. Everything is working as expected. But Am trying to add a filter condition in the API URL but it doesn't seems to be working.

Can anyone help me out how can we add the filter parameter in the API call ?

Thanks in Advance.

Command icon Show commands

Start within a Git clone of the project using the version control instructions.

Or, if you do not have SSH keys set up on git.drupalcode.org:

Comments

suresh7787 created an issue. See original summary.

sam711’s picture

What you're describing sounds like JSON:API Cross Bundles (https://www.drupal.org/project/jsonapi_cross_bundles)

If you still need to do it yourself, have you looked at how this is done in \Drupal\jsonapi\Controller\EntityResource::getCollectionQuery? The $params array comes from getJsonApiParams.

May be this is worth a Trait 🤔

suresh7787’s picture

Hi sam711,

Thanks for your response. I have tried jsonapi_cross_bundles. The module works fine with with core jsonapi, but if the site has jsonapi_extras enabled, the cross bundles module didnt work as expected. (i.e) jsonapi/node throws 404.

If I disabled the jsonapi_extras it is working fine. So that is the reason, Am using jsonapi_resources module.

Let me have a look at your advise and will keep you posted.

Thanks again.

sarbazx’s picture

HI suresh7787,

Did you able to filter on custom resources? Can you share how did you did it?

Thanks.

ptmkenny’s picture

Title: How to check the filter parameter in the API call » Support JSON:API filters
Version: 8.x-1.0-beta3 » 8.x-1.x-dev
Priority: Normal » Major

Discussion with @mglaman on Slack:

ptmkenny
8 hours ago
Is it possible to use regular JSON:API filters (like /jsonapi/my-resource&filter[group-name][group][conjunction]=OR&filter[filter-name][condition][path]=n... on a JSON:API Resource created with the JSON:API Resources module? It seems they are not supported out of the box, but is it possible to get filter support working, or do I have to add my own parameters to the resource to use instead of filters?

mglaman
7 hours ago
I thought it’d work, as we expand filters like normal

mglaman
5 hours ago
I guess I’m wrong, we don’t provide methods for this

mglaman
5 hours ago
it was added in jsonapi_search_api but these helper methods should be applied in jsonapi_resources https://git.drupalcode.org/project/jsonapi_search_api/-/blob/8.x-1.x/src/Resource/IndexResource.php?ref_type=heads#L159-176

mglaman
5 hours ago
https://git.drupalcode.org/project/jsonapi_search_api/-/blob/8.x-1.x/src/Resource/IndexResource.php?ref_type=heads#L190-197

mglaman
5 hours ago
https://git.drupalcode.org/project/jsonapi_search_api/-/blob/8.x-1.x/src/Resource/IndexResource.php?ref_type=heads#L208-212

ptmkenny’s picture

Status: Active » Needs work

I started on an MR for this.

To get filters to work, you need to add the following code to the process() method of your custom JSON:API resource:

    $cacheability = new CacheableMetadata();
    if ($request->query->has(Filter::KEY_NAME)) {
      $this->applyFiltersToQuery($request, $entity_query, $cacheability);
    }

    if ($request->query->has(Sort::KEY_NAME)) {
      $this->applySortingToQuery($request, $entity_query, $cacheability);
    }

    $data = $this->loadResourceObjectDataFromEntityQuery($entity_query, $cacheability);

However, the filters don't currently work because I don't understand how to get the resource type (see the comment in the MR code).

Filtering support is available. It works for me, but your mileage may vary.

ptmkenny’s picture

An important note for filtering: the order of _jsonapi_resource_types in mymodule.routing.yml is important.

    _jsonapi_resource_types:
      ['node--base_for_entity_query', 'other_entity--bundle_type']

The first entity type listed must be the base for the entity query; if you put them in a random order, filters like entity_reference_field.referenced_entity_field will fail.

sarbazx’s picture

Hello,

is this fixed?

ptmkenny’s picture

@sarbazx No, it's not fixed. If it was fixed, the status would be "Fixed", not "Needs work".

I wrote the MR and it works for me. But it doesn't have any tests (which probably need to be created for it to be merged), and no one else has reported using it successfully, so I don't know how well it works for other use cases. For my own site, it's working great.

ptmkenny’s picture

With claude code, I made the following changes to the MR:

  src/Resource/EntityQueryResourceBase.php (+124/-8)
  - New imports: EntityFieldManagerInterface, ModuleHandlerInterface, TemporaryQueryGuard, FieldResolver, ResourceType.
  - Three new private properties + setters: setFieldResolver(), setFieldManager(), setModuleHandler().
  - applyFiltersToQuery() rewritten:
    - Early-return when Filter::KEY_NAME isn't on the request.
    - Resource type chosen by matching $query->getEntityTypeId() (replaces reset($route_resource_types) — no more silent
  dependence on routing order; throws a cacheable 400 with a specific message if no match).
    - Filter::createFromQueryParameter() now called with the injected $this->fieldResolver instead of
  \Drupal::service('jsonapi.field_resolver').
    - TemporaryQueryGuard::applyAccessControls() restored after the user filter is applied — closes the
  filter-as-information-oracle hole from commit f2841e8.
    - Catch narrowed to \UnexpectedValueException | \InvalidArgumentException; CacheableBadRequestHttpException propagates
   unwrapped to preserve original cacheability/message.
    - Docblock updated: real @throws CacheableBadRequestHttpException instead of the fictional @throws PluginException.
  - New private helper resolveFilterResourceType() does the entity-type-based lookup.
  - applySortingToQuery() untouched (sort fixes deferred to a follow-up).

  src/Unstable/DependencyInjection/JsonapiResourceClassResolver.php (+3)
  - In the EntityQueryResourceBase branch, wires jsonapi.field_resolver, entity_field.manager, module_handler via the new
  setters.

  tests/modules/jsonapi_resources_test/src/Resource/FeaturedNodes.php (+2)
  - Calls $this->applyFiltersToQuery($request, $query, $cacheability) so the canonical example demonstrates filter
  support.

  tests/src/Functional/JsonapiResourceTest.php (+55)
  - New testFilterOnFeaturedNodes(): creates 4 promoted + 1 non-promoted node, asserts (a) filter[title][value]=Bravo
  returns exactly the matching promoted node, (b) filtering for the non-promoted node's title returns zero results —
  confirming filter cannot override the resource's hard-coded promote=1 condition.
ptmkenny’s picture

Status: Needs work » Needs review

I have tested this locally against my React app.

With regard to the MR, I'm not sure if the new setter-injected dependencies are permissible or not:

  • \Drupal\jsonapi\Context\FieldResolver
  • \Drupal\Core\Entity\EntityFieldManagerInterface
  • \Drupal\Core\Extension\ModuleHandlerInterface

Other than that, I think this is ready for review, so I am removing the "Draft" status from the MR.

mglaman’s picture

Thanks ptmkenny! I'll get this reviewed and committed tomorrow

mglaman’s picture

Status: Needs review » Reviewed & tested by the community

  • mglaman committed 84d69503 on 8.x-1.x authored by ptmkenny
    feat: #3114758 Support JSON:API filters
    
    By: ptmkenny
    By: mglaman
    
mglaman’s picture

Status: Reviewed & tested by the community » Fixed

thank you, merged! I'll release soon

Now that this issue is closed, review the contribution record.

As a contributor, attribute any organization that helped you, or if you volunteered your own time.

Maintainers, credit people who helped resolve this issue.

ptmkenny’s picture

Thank you for fixing and committing, and thank you for the help getting this started in the first place!