001// *************************************************************************************************************************** 002// * Licensed to the Apache Software Foundation (ASF) under one or more contributor license agreements. See the NOTICE file * 003// * distributed with this work for additional information regarding copyright ownership. The ASF licenses this file * 004// * to you under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance * 005// * with the License. You may obtain a copy of the License at * 006// * * 007// * http://www.apache.org/licenses/LICENSE-2.0 * 008// * * 009// * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an * 010// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the * 011// * specific language governing permissions and limitations under the License. * 012// *************************************************************************************************************************** 013package org.apache.juneau.remoteable; 014 015import static org.apache.juneau.internal.ClassUtils.*; 016import static org.apache.juneau.internal.CollectionUtils.*; 017import static org.apache.juneau.internal.ReflectionUtils.*; 018import static org.apache.juneau.internal.StringUtils.*; 019 020import java.lang.reflect.*; 021import java.util.*; 022 023/** 024 * Contains the meta-data about a remoteable interface. 025 * 026 * <p> 027 * Captures the information in {@link Remoteable @Remoteable} and {@link RemoteMethod @RemoteMethod} annotations for 028 * caching and reuse. 029 * 030 * <h5 class='section'>See Also:</h5> 031 * <ul class='doctree'> 032 * <li class='link'><a class='doclink' href='../../../../overview-summary.html#juneau-rest-client.3rdPartyProxies'>Overview > juneau-rest-client > Interface Proxies Against 3rd-party REST Interfaces</a> 033 * </ul> 034 */ 035public class RemoteableMeta { 036 037 private final Map<Method,RemoteableMethodMeta> methods; 038 039 /** 040 * Constructor. 041 * 042 * @param c The interface class annotated with a {@link Remoteable @Remoteable} annotation (optional). 043 * @param restUrl The absolute URL of the remote REST interface that implements this proxy interface. 044 */ 045 public RemoteableMeta(Class<?> c, String restUrl) { 046 Remoteable r = getAnnotation(Remoteable.class, c); 047 048 String expose = r == null ? "DECLARED" : r.expose(); 049 if (! isOneOf(expose, "ALL", "DECLARED", "ANNOTATED")) 050 throw new RemoteableMetadataException(c, "Invalid value specified for ''expose'' annotation. Valid values are [ALL,ANNOTATED,DECLARED]."); 051 052 Map<Method,RemoteableMethodMeta> _methods = new LinkedHashMap<>(); 053 for (Method m : expose.equals("DECLARED") ? c.getDeclaredMethods() : c.getMethods()) { 054 if (isPublic(m)) { 055 RemoteMethod rm = c.getAnnotation(RemoteMethod.class); 056 if (rm != null || ! expose.equals("ANNOTATED")) 057 _methods.put(m, new RemoteableMethodMeta(restUrl, m)); 058 } 059 } 060 061 this.methods = unmodifiableMap(_methods); 062 } 063 064 /** 065 * Returns the metadata about the specified method on this interface proxy. 066 * 067 * @param m The method to look up. 068 * @return Metadata about the method, or <jk>null</jk> if no metadata was found. 069 */ 070 public RemoteableMethodMeta getMethodMeta(Method m) { 071 return methods.get(m); 072 } 073}