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.httppart.bean;
014
015import static org.apache.juneau.internal.CollectionUtils.*;
016
017import java.lang.annotation.*;
018import java.lang.reflect.*;
019import java.util.*;
020
021import org.apache.juneau.annotation.*;
022import org.apache.juneau.cp.*;
023import org.apache.juneau.http.annotation.*;
024import org.apache.juneau.httppart.*;
025import org.apache.juneau.reflect.*;
026
027/**
028 * Represents the metadata gathered from a getter method of a class annotated with {@link Request}.
029 *
030 * <h5 class='section'>See Also:</h5><ul>
031 *    <li class='link'><a class="doclink" href="../../../../../index.html#jm.HttpPartSerializersParsers">HTTP Part Serializers and Parsers</a>
032 * </ul>
033 */
034public class RequestBeanPropertyMeta {
035
036   static RequestBeanPropertyMeta.Builder create(HttpPartType partType, Class<? extends Annotation> c, MethodInfo m) {
037      HttpPartSchema.Builder sb = HttpPartSchema.create().name(m.getPropertyName());
038      m.forEachAnnotation(Schema.class, x -> true, x -> sb.apply(x));
039      m.forEachAnnotation(c, x -> true, x -> sb.apply(x));
040      return new Builder().partType(partType).schema(sb.build()).getter(m.inner());
041   }
042
043   //-----------------------------------------------------------------------------------------------------------------
044   // Instance
045   //-----------------------------------------------------------------------------------------------------------------
046
047   private final Method getter;
048   private final HttpPartType partType;
049   private final Optional<HttpPartSerializer> serializer;
050   private final HttpPartParser parser;
051   private final HttpPartSchema schema;
052
053   RequestBeanPropertyMeta(Builder b, HttpPartSerializer serializer, HttpPartParser parser) {
054      this.partType = b.partType;
055      this.schema = b.schema;
056      this.getter = b.getter;
057      this.serializer = optional(schema.getSerializer() == null ? serializer : BeanCreator.of(HttpPartSerializer.class).type(schema.getSerializer()).run());
058      this.parser = schema.getParser() == null ? parser : BeanCreator.of(HttpPartParser.class).type(schema.getParser()).run();
059   }
060
061   static class Builder {
062      HttpPartType partType;
063      HttpPartSchema schema;
064      Method getter;
065
066      Builder getter(Method value) {
067         getter = value;
068         return this;
069      }
070
071      Builder partType(HttpPartType value) {
072         partType = value;
073         return this;
074      }
075
076      Builder schema(HttpPartSchema value) {
077         schema = value;
078         return this;
079      }
080
081      RequestBeanPropertyMeta build(HttpPartSerializer serializer, HttpPartParser parser) {
082         return new RequestBeanPropertyMeta(this, serializer, parser);
083      }
084   }
085
086   /**
087    * Returns the HTTP part name for this property (query parameter name for example).
088    *
089    * @return The HTTP part name, or <jk>null</jk> if it doesn't have a part name.
090    */
091   public String getPartName() {
092      return schema == null ? null : schema.getName();
093   }
094
095   /**
096    * Returns the name of the Java method getter that defines this property.
097    *
098    * @return
099    *    The name of the Java method getter that defines this property.
100    *    <br>Never <jk>null</jk>.
101    */
102   public Method getGetter() {
103      return getter;
104   }
105
106   /**
107    * Returns the HTTP part type for this property (query parameter for example).
108    *
109    * @return
110    *    The HTTP part type for this property.
111    *    <br>Never <jk>null</jk>.
112    */
113   public HttpPartType getPartType() {
114      return partType;
115   }
116
117   /**
118    * Returns the serializer to use for serializing the bean property value.
119    *
120    * @return The serializer to use for serializing the bean property value.
121    */
122   public Optional<HttpPartSerializer> getSerializer() {
123      return serializer;
124   }
125
126   /**
127    * Returns the parser to use for parsing the bean property value.
128    *
129    * @param _default The default parsing to use if not defined on the annotation.
130    * @return The parsing to use for serializing the bean property value.
131    */
132   public HttpPartParserSession getParser(HttpPartParserSession _default) {
133      return parser == null ? _default : parser.getPartSession();
134   }
135
136   /**
137    * Returns the schema information gathered from annotations on the method and return type.
138    *
139    * @return
140    *    The schema information gathered from annotations on the method and return type.
141    *    <br>Never <jk>null</jk>.
142    */
143   public HttpPartSchema getSchema() {
144      return schema;
145   }
146}