All Downloads are FREE. Search and download functionalities are using the official Maven repository.

global.namespace.neuron.di.internal.ClassElement Maven / Gradle / Ivy

There is a newer version: 6.7.1
Show newest version
/*
 * Copyright © 2016 Schlichtherle IT Services
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     https://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package global.namespace.neuron.di.internal;

import global.namespace.neuron.di.java.BreedingException;
import global.namespace.neuron.di.java.CachingStrategy;

import java.lang.reflect.Method;
import java.util.Optional;

import static global.namespace.neuron.di.java.CachingStrategy.DISABLED;

@FunctionalInterface
interface ClassElement extends ClassInfo, Element {

    static  ClassElement of(final Class clazz) {
        final NeuronElement element = () -> clazz;
        return element.isNeuron() ? element : () -> clazz;
    }

    default CachingStrategy cachingStrategy() {
        return classCachingStrategy().orElse(DISABLED);
    }

    @Override
    default void accept(Visitor visitor) {
        visitor.visitClass(this);
    }

    default MethodElement element(final Method method) {

        abstract class Base {

            public Method method() {
                return method;
            }

            public boolean equals(final Object o) {
                if (this == o) {
                    return true;
                }
                if (!(o instanceof MethodInfo)) {
                    return false;
                }
                final MethodInfo that = (MethodInfo) o;
                return that.canEqual(this) && this.method().equals(that.method());
            }

            @Override
            public int hashCode() {
                return method().hashCode();
            }
        }

        final MethodInfo info = () -> method;
        final Optional declaredCachingStrategy = info.declaredCachingStrategy();
        if (info.isAbstract()) {
            if (info.hasParameters()) {
                throw new BreedingException("A synapse method must not have parameters: " + method);
            } else if (info.isVoid()) {
                throw new BreedingException("A synapse method must have a return value: " + method);
            }

            class RealSynapseElement extends Base implements SynapseElement {

                private final CachingStrategy cachingStrategy =
                        declaredCachingStrategy.orElseGet(ClassElement.this::cachingStrategy);

                @Override
                public CachingStrategy cachingStrategy() {
                    return cachingStrategy;
                }
            }

            return new RealSynapseElement();
        } else {
            if (declaredCachingStrategy.isPresent()) {
                if (info.hasParameters()) {
                    throw new BreedingException("A caching method must not have parameters: " + method);
                } else if (info.isVoid()) {
                    throw new BreedingException("A caching method must have a return value: " + method);
                }
            }

            class RealMethodElement extends Base implements MethodElement {

                private final CachingStrategy cachingStrategy = declaredCachingStrategy.orElse(DISABLED);

                @Override
                public CachingStrategy cachingStrategy() {
                    return cachingStrategy;
                }
            }

            return new RealMethodElement();
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy