001/* -*- mode: Java; c-basic-offset: 2; indent-tabs-mode: nil; coding: utf-8-unix -*-
002 *
003 * Copyright © 2025 microBean™.
004 *
005 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with
006 * the License. You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on
011 * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the
012 * specific language governing permissions and limitations under the License.
013 */
014package org.microbean.event;
015
016import java.util.Collection;
017
018import org.microbean.assign.Matcher;
019import org.microbean.assign.Qualifiers;
020
021import org.microbean.attributes.Attributes;
022
023import static java.util.Objects.requireNonNull;
024
025/**
026 * A {@link Matcher} encapsulating <a
027 * href="https://jakarta.ee/specifications/cdi/4.0/jakarta-cdi-spec-4.0#observer_resolution">CDI-compatible event
028 * qualifier matching rules</a>.
029 *
030 * @author <a href="https://about.me/lairdnelson/" target="_top">Laird Nelson</a>
031 *
032 * @see #test(Collection, Collection)
033 */
034public final class EventQualifiersMatcher implements Matcher<Collection<? extends Attributes>, Collection<? extends Attributes>> {
035
036
037  /*
038   * Instance fields.
039   */
040
041
042  private final Qualifiers qualifiers;
043
044
045  /*
046   * Constructors.
047   */
048
049
050  /**
051   * Creates a new {@link EventQualifiersMatcher}.
052   *
053   * @param qualifiers a {@link Qualifiers}; must not be {@code null}
054   *
055   * @exception NullPointerException if {@code qualifiers} is {@code null}
056   */
057  public EventQualifiersMatcher(final Qualifiers qualifiers) {
058    super();
059    this.qualifiers = requireNonNull(qualifiers, "qualifiers");
060  }
061
062
063  /*
064   * Instance methods.
065   */
066
067
068  /**
069   * Returns {@code true} if and only if either the {@linkplain org.microbean.assign.Qualifiers#qualifiers(Collection)
070   * qualifiers present} in {@code receiverAttributes} are {@linkplain Collection#isEmpty() empty}, or if the collection
071   * of {@linkplain org.microbean.assign.Qualifiers#qualifiers(Collection) qualifiers present} in {@code
072   * payloadAttributes} {@linkplain Collection#containsAll(Collection) contains all} of the {@linkplain
073   * org.microbean.assign.Qualifiers#qualifiers(Collection) qualifiers present} in {@code receiverAttributes}.
074   *
075   * @param receiverAttributes a {@link Collection} of {@link Attributes} instances; must not be {@code null}
076   *
077   * @param payloadAttributes a {@link Collection} of {@link Attributes} instances; must not be {@code null}
078   *
079   * @return {@code true} if and only if either the {@linkplain org.microbean.assign.Qualifiers#qualifiers(Collection)
080   * qualifiers present} in {@code receiverAttributes} are {@linkplain Collection#isEmpty() empty}, or if the collection
081   * of {@linkplain org.microbean.assign.Qualifiers#qualifiers(Collection) qualifiers present} in {@code
082   * payloadAttributes} {@linkplain Collection#containsAll(Collection) contains all} of the {@linkplain
083   * org.microbean.assign.Qualifiers#qualifiers(Collection) qualifiers present} in {@code receiverAttributes}
084   *
085   * @exception NullPointerException if either argument is {@code null}
086   */
087  @Override // Matcher<Collection<? extends NamedAttributeMap<?>>, Collection<? extends NamedAttributeMap<?>>>
088  public final boolean test(final Collection<? extends Attributes> receiverAttributes,
089                            final Collection<? extends Attributes> payloadAttributes) {
090    // "An event is delivered to an observer method if...the observer method has no event qualifiers or has a subset of
091    // the event qualifiers."
092    final Collection<? extends Attributes> receiverQualifiers = qualifiers.qualifiers(receiverAttributes);
093    return receiverQualifiers.isEmpty() || qualifiers.qualifiers(payloadAttributes).containsAll(receiverQualifiers);
094  }
095
096}