001/*
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *      http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.apache.juneau.rest.annotation;
018
019import static java.lang.annotation.ElementType.*;
020import static java.lang.annotation.RetentionPolicy.*;
021
022import java.lang.annotation.*;
023import java.nio.charset.*;
024
025import org.apache.juneau.*;
026import org.apache.juneau.annotation.*;
027import org.apache.juneau.bean.swagger.*;
028import org.apache.juneau.commons.annotation.*;
029import org.apache.juneau.encoders.*;
030import org.apache.juneau.http.remote.*;
031import org.apache.juneau.parser.*;
032import org.apache.juneau.rest.*;
033import org.apache.juneau.rest.converter.*;
034import org.apache.juneau.rest.guard.*;
035import org.apache.juneau.rest.httppart.*;
036import org.apache.juneau.rest.matcher.*;
037import org.apache.juneau.rest.servlet.*;
038import org.apache.juneau.rest.swagger.*;
039import org.apache.juneau.serializer.*;
040
041/**
042 * Identifies a REST operation Java method on a {@link RestServlet} implementation class.
043 *
044 * <h5 class='section'>See Also:</h5><ul>
045 *    <li class='link'><a class="doclink" href="https://juneau.apache.org/docs/topics/RestOpAnnotatedMethodBasics">@RestOp-Annotated Method Basics</a>
046
047 * </ul>
048 */
049@Target(METHOD)
050@Retention(RUNTIME)
051@Inherited
052@ContextApply(RestOpAnnotation.RestOpContextApply.class)
053@AnnotationGroup(RestOp.class)
054public @interface RestOp {
055
056   /**
057    * Specifies whether this method can be called based on the client version.
058    *
059    * <p>
060    * The client version is identified via the HTTP request header identified by
061    * {@link Rest#clientVersionHeader() @Rest(clientVersionHeader)} which by default is <js>"Client-Version"</js>.
062    *
063    * <p>
064    * This is a specialized kind of {@link RestMatcher} that allows you to invoke different Java methods for the same
065    * method/path based on the client version.
066    *
067    * <p>
068    * The format of the client version range is similar to that of OSGi versions.
069    *
070    * <p>
071    * In the following example, the Java methods are mapped to the same HTTP method and URL <js>"/foobar"</js>.
072    * <p class='bjava'>
073    *    <jc>// Call this method if Client-Version is at least 2.0.
074    *    // Note that this also matches 2.0.1.</jc>
075    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/foobar"</js>, clientVersion=<js>"2.0"</js>)
076    *    <jk>public</jk> Object method1()  {...}
077    *
078    *    <jc>// Call this method if Client-Version is at least 1.1, but less than 2.0.</jc>
079    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/foobar"</js>, clientVersion=<js>"[1.1,2.0)"</js>)
080    *    <jk>public</jk> Object method2()  {...}
081    *
082    *    <jc>// Call this method if Client-Version is less than 1.1.</jc>
083    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/foobar"</js>, clientVersion=<js>"[0,1.1)"</js>)
084    *    <jk>public</jk> Object method3()  {...}
085    * </p>
086    *
087    * <p>
088    * It's common to combine the client version with transforms that will convert new POJOs into older POJOs for
089    * backwards compatibility.
090    * <p class='bjava'>
091    *    <jc>// Call this method if Client-Version is at least 2.0.</jc>
092    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/foobar"</js>, clientVersion=<js>"2.0"</js>)
093    *    <jk>public</jk> NewPojo newMethod()  {...}
094    *
095    *    <jc>// Call this method if X-Client-Version is at least 1.1, but less than 2.0.</jc>
096    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/foobar"</js>, clientVersion=<js>"[1.1,2.0)"</js>)
097    *    <ja>@BeanConfig(swaps=NewToOldSwap.<jk>class</jk>)
098    *    <jk>public</jk> NewPojo oldMethod() {
099    *       <jk>return</jk> newMethod();
100    *    }
101    *
102    * <p>
103    * Note that in the previous example, we're returning the exact same POJO, but using a transform to convert it into
104    * an older form.
105    * The old method could also just return back a completely different object.
106    * The range can be any of the following:
107    * <ul>
108    *    <li><js>"[0,1.0)"</js> = Less than 1.0.  1.0 and 1.0.0 does not match.
109    *    <li><js>"[0,1.0]"</js> = Less than or equal to 1.0.  Note that 1.0.1 will match.
110    *    <li><js>"1.0"</js> = At least 1.0.  1.0 and 2.0 will match.
111    * </ul>
112    *
113    * <h5 class='section'>See Also:</h5><ul>
114    *    <li class='jm'>{@link org.apache.juneau.rest.RestContext.Builder#clientVersionHeader(String)}
115    * </ul>
116    *
117    * @return The annotation value.
118    */
119   String clientVersion() default "";
120
121   /**
122    * Supported content media types.
123    *
124    * <p>
125    * Overrides the media types inferred from the parsers that identify what media types can be consumed by the resource.
126    *
127    * <h5 class='section'>Notes:</h5><ul>
128    *    <li class='note'>
129    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
130    *       (e.g. <js>"$S{mySystemProperty}"</js>).
131    * </ul>
132    *
133    * <h5 class='section'>See Also:</h5><ul>
134    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#consumes(MediaType...)}
135    * </ul>
136    *
137    * @return The annotation value.
138    */
139   String[] consumes() default {};
140
141   /**
142    * Class-level response converters.
143    *
144    * <p>
145    * Associates one or more {@link RestConverter converters} with this method.
146    *
147    * <h5 class='section'>See Also:</h5><ul>
148    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#converters()} - Registering converters with REST resources.
149    * </ul>
150    *
151    * @return The annotation value.
152    */
153   Class<? extends RestConverter>[] converters() default {};
154
155   /**
156    * Enable debug mode.
157    *
158    * <p>
159    * Enables the following:
160    * <ul class='spaced-list'>
161    *    <li>
162    *       HTTP request/response bodies are cached in memory for logging purposes.
163    *    <li>
164    *       Request/response messages are automatically logged.
165    * </ul>
166    *
167    * <ul class='values'>
168    *    <li><js>"true"</js> - Debug is enabled for all requests.
169    *    <li><js>"false"</js> - Debug is disabled for all requests.
170    *    <li><js>"conditional"</js> - Debug is enabled only for requests that have a <c class='snippet'>Debug: true</c> header.
171    *    <li><js>""</js> (or anything else) - Debug mode is inherited from class.
172    * </ul>
173    *
174    * <h5 class='section'>Notes:</h5><ul>
175    *    <li class='note'>
176    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
177    *       (e.g. <js>"$L{my.localized.variable}"</js>).
178    * </ul>
179    *
180    * <h5 class='section'>See Also:</h5><ul>
181    *    <li class='jm'>{@link org.apache.juneau.rest.RestContext.Builder#debugEnablement()}
182    * </ul>
183    *
184    * @return The annotation value.
185    */
186   String debug() default "";
187
188   /**
189    * Default <c>Accept</c> header.
190    *
191    * <p>
192    * The default value for the <c>Accept</c> header if not specified on a request.
193    *
194    * <p>
195    * This is a shortcut for using {@link #defaultRequestHeaders()} for just this specific header.
196    *
197    * @return The annotation value.
198    */
199   String defaultAccept() default "";
200
201   /**
202    * Default character encoding.
203    *
204    * <p>
205    * The default character encoding for the request and response if not specified on the request.
206    *
207    * <h5 class='section'>Notes:</h5><ul>
208    *    <li class='note'>
209    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
210    *       (e.g. <js>"$S{mySystemProperty}"</js>).
211    * </ul>
212    *
213    * <h5 class='section'>See Also:</h5><ul>
214    *    <li class='jm'>{@link org.apache.juneau.rest.RestContext.Builder#defaultCharset(Charset)}
215    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#defaultCharset(Charset)}
216    *    <li class='ja'>{@link Rest#defaultCharset}
217    * </ul>
218    *
219    * @return The annotation value.
220    */
221   String defaultCharset() default "";
222
223   /**
224    * Default <c>Content-Type</c> header.
225    *
226    * <p>
227    * The default value for the <c>Content-Type</c> header if not specified on a request.
228    *
229    * <p>
230    * This is a shortcut for using {@link #defaultRequestHeaders()} for just this specific header.
231    *
232    * @return The annotation value.
233    */
234   String defaultContentType() default "";
235
236   /**
237    * Default request attributes.
238    *
239    * <p>
240    * Specifies default values for request attributes if they're not already set on the request.
241    *
242    * <p>
243    * Affects values returned by the following methods:
244    *    <ul>
245    *       <li class='jm'>{@link RestRequest#getAttribute(String)}.
246    *       <li class='jm'>{@link RestRequest#getAttributes()}.
247    *    </ul>
248    *
249    * <h5 class='section'>Example:</h5>
250    * <p class='bjava'>
251    *    <jc>// Defined via annotation resolving to a config file setting with default value.</jc>
252    *    <ja>@Rest</ja>(defaultRequestAttributes={<js>"Foo=bar"</js>, <js>"Baz: $C{REST/myAttributeValue}"</js>})
253    *    <jk>public class</jk> MyResource {
254    *
255    *       <jc>// Override at the method level.</jc>
256    *       <ja>@RestGet</ja>(defaultRequestAttributes={<js>"Foo: bar"</js>})
257    *       <jk>public</jk> Object myMethod() {...}
258    *    }
259    * </p>
260    *
261    * </ul>
262    * <h5 class='section'>Notes:</h5><ul>
263    *    <li class='note'>
264    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
265    *       (e.g. <js>"$L{my.localized.variable}"</js>).
266    * </ul>
267    *
268    * <h5 class='section'>See Also:</h5><ul>
269    *    <li class='jm'>{@link org.apache.juneau.rest.RestContext.Builder#defaultRequestAttributes(NamedAttribute...)}
270    *    <li class='ja'>{@link Rest#defaultRequestAttributes()}
271    * </ul>
272    *
273    * @return The annotation value.
274    */
275   String[] defaultRequestAttributes() default {};
276
277   /**
278    * Specifies default values for form-data parameters.
279    *
280    * <p>
281    * Strings are of the format <js>"name=value"</js>.
282    *
283    * <p>
284    * Affects values returned by {@link RestRequest#getFormParam(String)} when the parameter is not present on the
285    * request.
286    *
287    * <h5 class='section'>Example:</h5>
288    * <p class='bjava'>
289    *    <ja>@RestOp</ja>(method=<jsf>POST</jsf>, path=<js>"/*"</js>, defaultRequestFormData={<js>"foo=bar"</js>})
290    *    <jk>public</jk> String doPost(<ja>@FormData</ja>(<js>"foo"</js>) String <jv>foo</jv>)  {...}
291    * </p>
292    *
293    * <h5 class='section'>Notes:</h5><ul>
294    *    <li class='note'>
295    *       You can use either <js>':'</js> or <js>'='</js> as the key/value delimiter.
296    *    <li class='note'>
297    *       Key and value is trimmed of whitespace.
298    *    <li class='note'>
299    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
300    *       (e.g. <js>"$S{mySystemProperty}"</js>).
301    * </ul>
302    *
303    * @return The annotation value.
304    */
305   String[] defaultRequestFormData() default {};
306
307   /**
308    * Default request headers.
309    *
310    * <p>
311    * Specifies default values for request headers if they're not passed in through the request.
312    *
313    * <h5 class='section'>Example:</h5>
314    * <p class='bjava'>
315    *    <jc>// Assume "text/json" Accept value when Accept not specified</jc>
316    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/*"</js>, defaultRequestHeaders={<js>"Accept: text/json"</js>})
317    *    <jk>public</jk> String doGet()  {...}
318    * </p>
319    *
320    * <h5 class='section'>Notes:</h5><ul>
321    *    <li class='note'>
322    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
323    *       (e.g. <js>"$S{mySystemProperty}"</js>).
324    * </ul>
325    *
326    * <h5 class='section'>See Also:</h5><ul>
327    *    <li class='jm'>{@link org.apache.juneau.rest.RestContext.Builder#defaultRequestHeaders(org.apache.http.Header...)}
328    * </ul>
329    *
330    * @return The annotation value.
331    */
332   String[] defaultRequestHeaders() default {};
333
334   /**
335    * Specifies default values for query parameters.
336    *
337    * <p>
338    * Strings are of the format <js>"name=value"</js>.
339    *
340    * <p>
341    * Affects values returned by {@link RestRequest#getQueryParam(String)} when the parameter is not present on the request.
342    *
343    * <h5 class='section'>Example:</h5>
344    * <p class='bjava'>
345    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/*"</js>, defaultRequestQueryData={<js>"foo=bar"</js>})
346    *    <jk>public</jk> String doGet(<ja>@Query</ja>(<js>"foo"</js>) String <jv>foo</jv>)  {...}
347    * </p>
348    *
349    * <h5 class='section'>Notes:</h5><ul>
350    *    <li class='note'>
351    *       You can use either <js>':'</js> or <js>'='</js> as the key/value delimiter.
352    *    <li class='note'>
353    *       Key and value is trimmed of whitespace.
354    *    <li class='note'>
355    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
356    *       (e.g. <js>"$S{mySystemProperty}"</js>).
357    * </ul>
358    *
359    * @return The annotation value.
360    */
361   String[] defaultRequestQueryData() default {};
362
363   /**
364    * Default response headers.
365    *
366    * <p>
367    * Specifies default values for response headers if they're not overwritten during the request.
368    *
369    * <h5 class='section'>Example:</h5>
370    * <p class='bjava'>
371    *    <jc>// Assume "text/json" Accept value when Accept not specified</jc>
372    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/*"</js>, defaultResponseHeaders={<js>"Content-Type: text/json"</js>})
373    *    <jk>public</jk> String doGet()  {...}
374    * </p>
375    *
376    * <h5 class='section'>Notes:</h5><ul>
377    *    <li class='note'>
378    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
379    *       (e.g. <js>"$S{mySystemProperty}"</js>).
380    * </ul>
381    *
382    * <h5 class='section'>See Also:</h5><ul>
383    *    <li class='jm'>{@link org.apache.juneau.rest.RestContext.Builder#defaultResponseHeaders(org.apache.http.Header...)}
384    * </ul>
385    *
386    * @return The annotation value.
387    */
388   String[] defaultResponseHeaders() default {};
389
390   /**
391    * Optional description for the exposed API.
392    *
393    * <p>
394    * This description is used in the following locations:
395    * <ul class='spaced-list'>
396    *    <li>
397    *       The value returned by {@link Operation#getDescription()} in the auto-generated swagger.
398    *    <li>
399    *       The <js>"$RS{operationDescription}"</js> variable.
400    *    <li>
401    *       The description of the method in the Swagger page.
402    * </ul>
403    *
404    * <h5 class='section'>Notes:</h5><ul>
405    *    <li class='note'>
406    *       Corresponds to the swagger field <c>/paths/{path}/{method}/description</c>.
407    *    <li class='note'>
408    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
409    *       (e.g. <js>"$L{my.localized.variable}"</js>).
410    * </ul>
411    *
412    * @return The annotation value.
413    */
414   String[] description() default {};
415
416   /**
417    * Specifies the compression encoders for this method.
418    *
419    * <p>
420    * Encoders are used to enable various kinds of compression (e.g. <js>"gzip"</js>) on requests and responses.
421    *
422    * <p>
423    * This value overrides encoders specified at the class level using {@link Rest#encoders()}.
424    * The {@link org.apache.juneau.encoders.EncoderSet.Inherit} class can be used to include values from the parent class.
425    *
426    * <h5 class='section'>Example:</h5>
427    * <p class='bjava'>
428    *    <jc>// Define a REST resource that handles GZIP compression.</jc>
429    *    <ja>@Rest</ja>(
430    *       encoders={
431    *          GzipEncoder.<jk>class</jk>
432    *       }
433    *    )
434    *    <jk>public class</jk> MyResource {
435    *
436    *       <jc>// Define a REST method that can also use a custom encoder.</jc>
437    *       <ja>@RestOp</ja>(
438    *          method=<jsf>GET</jsf>,
439    *          encoders={
440    *             EncoderSet.Inherit.<jk>class</jk>, MyEncoder.<jk>class</jk>
441    *          }
442    *       )
443    *       <jk>public</jk> MyBean doGet() {
444    *          ...
445    *       }
446    *    }
447    * </p>
448    *
449    * <p>
450    * The programmatic equivalent to this annotation is:
451    * <p class='bjava'>
452    *    RestOpContext.Builder <jv>builder</jv> = RestOpContext.<jsm>create</jsm>(<jv>method</jv>,<jv>restContext</jv>);
453    *    <jv>builder</jv>.getEncoders().set(<jv>classes</jv>);
454    * </p>
455    *
456    * <h5 class='section'>See Also:</h5><ul>
457    *    <li class='link'><a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerEncoders">Encoders</a>
458    * </ul>
459    *
460    * @return The annotation value.
461    */
462   Class<? extends Encoder>[] encoders() default {};
463
464   /**
465    * Method-level guards.
466    *
467    * <p>
468    * Associates one or more {@link RestGuard RestGuards} with this method.
469    *
470    * <h5 class='section'>See Also:</h5><ul>
471    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#guards()}
472    * </ul>
473    *
474    * @return The annotation value.
475    */
476   Class<? extends RestGuard>[] guards() default {};
477
478   /**
479    * Method matchers.
480    *
481    * <p>
482    * Associates one more more {@link RestMatcher RestMatchers} with this method.
483    *
484    * <p>
485    * Matchers are used to allow multiple Java methods to handle requests assigned to the same URL path pattern, but
486    * differing based on some request attribute, such as a specific header value.
487    *
488    * <h5 class='section'>See Also:</h5><ul>
489    *    <li class='jac'>{@link RestMatcher}
490    * </ul>
491    *
492    * @return The annotation value.
493    */
494   Class<? extends RestMatcher>[] matchers() default {};
495
496   /**
497    * The maximum allowed input size (in bytes) on HTTP requests.
498    *
499    * <p>
500    * Useful for alleviating DoS attacks by throwing an exception when too much input is received instead of resulting
501    * in out-of-memory errors which could affect system stability.
502    *
503    * <h5 class='section'>Example:</h5>
504    * <p class='bjava'>
505    *    <ja>@RestOp</ja>(
506    *       maxInput=<js>"100M"</js>
507    *    )
508    * </p>
509    *
510    * <h5 class='section'>Notes:</h5><ul>
511    *    <li>
512    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
513    *       (e.g. <js>"$S{mySystemProperty}"</js>).
514    * </ul>
515    *
516    * <h5 class='section'>See Also:</h5><ul>
517    *    <li class='jm'>{@link org.apache.juneau.rest.RestContext.Builder#maxInput(String)}
518    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#maxInput(String)}
519    *    <li class='ja'>{@link Rest#maxInput}
520    * </ul>
521    *
522    * @return The annotation value.
523    */
524   String maxInput() default "";
525
526   /**
527    * REST method name.
528    *
529    * <p>
530    * Typically <js>"GET"</js>, <js>"PUT"</js>, <js>"POST"</js>, <js>"DELETE"</js>, or <js>"OPTIONS"</js>.
531    *
532    * <p>
533    * Method names are case-insensitive (always folded to upper-case).
534    *
535    * <p>
536    * Note that you can use {@link org.apache.juneau.http.HttpMethod} for constant values.
537    *
538    * <p>
539    * Note that you can also use {@link #value()} to specify the method name and path in shortened form.
540    *
541    * <p>
542    * Besides the standard HTTP method names, the following can also be specified:
543    * <ul class='spaced-list'>
544    *    <li>
545    *       <js>"*"</js>
546    *       - Denotes any method.
547    *       <br>Use this if you want to capture any HTTP methods in a single Java method.
548    *       <br>The {@link Method @Method} annotation and/or {@link RestRequest#getMethod()} method can be used to
549    *       distinguish the actual HTTP method name.
550    *    <li>
551    *       <js>""</js>
552    *       - Auto-detect.
553    *       <br>The method name is determined based on the Java method name.
554    *       <br>For example, if the method is <c>doPost(...)</c>, then the method name is automatically detected
555    *       as <js>"POST"</js>.
556    *       <br>Otherwise, defaults to <js>"GET"</js>.
557    *    <li>
558    *       <js>"RRPC"</js>
559    *       - Remote-proxy interface.
560    *       <br>This denotes a Java method that returns an object (usually an interface, often annotated with the
561    *       {@link Remote @Remote} annotation) to be used as a remote proxy using
562    *       <c>RestClient.getRemoteInterface(Class&lt;T&gt; interfaceClass, String url)</c>.
563    *       <br>This allows you to construct client-side interface proxies using REST as a transport medium.
564    *       <br>Conceptually, this is simply a fancy <c>POST</c> against the url <js>"/{path}/{javaMethodName}"</js>
565    *       where the arguments are marshalled from the client to the server as an HTTP content containing an array of
566    *       objects, passed to the method as arguments, and then the resulting object is marshalled back to the client.
567    *    <li>
568    *       Anything else
569    *       - Overloaded non-HTTP-standard names that are passed in through a <c>&amp;method=methodName</c> URL
570    *       parameter.
571    * </ul>
572    *
573    * @return The annotation value.
574    */
575   String method() default "";
576
577   /**
578    * Dynamically apply this annotation to the specified methods.
579    *
580    * <h5 class='section'>See Also:</h5><ul>
581    *    <li class='link'><a class="doclink" href="https://juneau.apache.org/docs/topics/DynamicallyAppliedAnnotations">Dynamically Applied Annotations</a>
582    * </ul>
583    *
584    * @return The annotation value.
585    */
586   String[] on() default {};
587
588   /**
589    * Specifies the parsers for converting HTTP request bodies into POJOs for this method.
590    *
591    * <p>
592    * Parsers are used to convert the content of HTTP requests into POJOs.
593    * <br>Any of the Juneau framework parsers can be used in this setting.
594    * <br>The parser selected is based on the request <c>Content-Type</c> header matched against the values returned by the following method
595    * using a best-match algorithm:
596    * <ul class='javatree'>
597    *    <li class='jm'>{@link Parser#getMediaTypes()}
598    * </ul>
599    *
600    * <p>
601    * This value overrides parsers specified at the class level using {@link Rest#parsers()}.
602    * The {@link org.apache.juneau.parser.ParserSet.Inherit} class can be used to include values from the parent class.
603    *
604    * <h5 class='section'>Example:</h5>
605    * <p class='bjava'>
606    *    <jc>// Define a REST resource that can consume JSON and HTML.</jc>
607    *    <ja>@Rest</ja>(
608    *       parsers={
609    *          JsonParser.<jk>class</jk>,
610    *          HtmlParser.<jk>class</jk>
611    *       }
612    *    )
613    *    <jk>public class</jk> MyResource {
614    *
615    *       <jc>// Define a REST method that can also consume XML.</jc>
616    *       <ja>@RestOp</ja>(
617    *          method=<jsf>POST</jsf>,
618    *          parsers={
619    *             ParserSet.Inherit.<jk>class</jk>, XmlParser.<jk>class</jk>
620    *          }
621    *       )
622    *       <jk>public void</jk> doPost(MyBean <jv>bean</jv>) {
623    *          ...
624    *       }
625    *    }
626    * </p>
627    *
628    * <p>
629    * The programmatic equivalent to this annotation is:
630    * <p class='bjava'>
631    *    RestOpContext.Builder <jv>builder</jv> = RestOpContext.<jsm>create</jsm>(<jv>method</jv>,<jv>restContext</jv>);
632    *    <jv>builder</jv>.getParsers().set(<jv>classes</jv>);
633    * </p>
634    *
635    * <h5 class='section'>See Also:</h5><ul>
636    *    <li class='link'><a class="doclink" href="https://juneau.apache.org/docs/topics/Marshalling">Marshalling</a>
637    * </ul>
638    *
639    * @return The annotation value.
640    */
641   Class<?>[] parsers() default {};
642
643   /**
644    * Optional path pattern for the specified method.
645    *
646    * <p>
647    * Appending <js>"/*"</js> to the end of the path pattern will make it match any remainder too.
648    * <br>Not appending <js>"/*"</js> to the end of the pattern will cause a 404 (Not found) error to occur if the exact
649    * pattern is not found.
650    *
651    * <p>
652    * The path can contain variables that get resolved to {@link org.apache.juneau.http.annotation.Path @Path} parameters.
653    *
654    * <h5 class='figure'>Examples:</h5>
655    * <p class='bjava'>
656    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/myurl/{foo}/{bar}/{baz}/*"</js>)
657    * </p>
658    * <p class='bjava'>
659    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>, path=<js>"/myurl/{0}/{1}/{2}/*"</js>)
660    * </p>
661    *
662    * <p>
663    * If you do not specify a path name, then the path name is inferred from the Java method name.
664    *
665    * <h5 class='figure'>Example:</h5>
666    * <p class='bjava'>
667    *    <jc>// Path is assumed to be "/foo".</jc>
668    *    <ja>@RestOp</ja>(method=<jsf>GET</jsf>)
669    *    <jk>public void</jk> foo() {...}
670    * </p>
671    *
672    * <p>
673    * If you also do not specify the {@link #method()} and the Java method name starts with <js>"get"</js>, <js>"put"</js>, <js>"post"</js>, or <js>"deleted"</js>,
674    * then the HTTP method name is stripped from the inferred path.
675    *
676    * <h5 class='figure'>Examples:</h5>
677    * <p class='bjava'>
678    *    <jc>// Method is GET, path is "/foo".</jc>
679    *    <ja>@RestOp</ja>
680    *    <jk>public void</jk> getFoo() {...}
681    * </p>
682    * <p class='bjava'>
683    *    <jc>// Method is DELETE, path is "/bar".</jc>
684    *    <ja>@RestOp</ja>
685    *    <jk>public void</jk> deleteBar() {...}
686    * </p>
687    * <p class='bjava'>
688    *    <jc>// Method is GET, path is "/foobar".</jc>
689    *    <ja>@RestOp</ja>
690    *    <jk>public void</jk> foobar() {...}
691    * </p>
692    * <p class='bjava'>
693    *    <jc>// Method is GET, path is "/".</jc>
694    *    <ja>@RestOp</ja>
695    *    <jk>public void</jk> get() {...}
696    * </p>
697    *
698    * <p>
699    * Note that you can also use {@link #value()} to specify the method name and path in shortened form.
700    *
701    * <h5 class='section'>See Also:</h5><ul>
702    *    <li class='ja'>{@link org.apache.juneau.http.annotation.Path}
703    * </ul>
704    *
705    * @return The annotation value.
706    */
707   String[] path() default {};
708
709   /**
710    * Supported accept media types.
711    *
712    * <p>
713    * Overrides the media types inferred from the serializers that identify what media types can be produced by the resource.
714    *
715    * <h5 class='section'>Notes:</h5><ul>
716    *    <li class='note'>
717    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
718    *       (e.g. <js>"$S{mySystemProperty}"</js>).
719    * </ul>
720    *
721    * <h5 class='section'>See Also:</h5><ul>
722    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#produces(MediaType...)}
723    * </ul>
724    *
725    * @return The annotation value.
726    */
727   String[] produces() default {};
728
729   /**
730    * Role guard.
731    *
732    * <p>
733    * An expression defining if a user with the specified roles are allowed to access this method.
734    *
735    * <h5 class='section'>Example:</h5>
736    * <p class='bjava'>
737    *    <jk>public class</jk> MyResource <jk>extends</jk> BasicRestServlet {
738    *
739    *       <ja>@RestOp</ja>(
740    *          method=<jsf>GET</jsf>,
741    *          path=<js>"/foo"</js>,
742    *          roleGuard=<js>"ROLE_ADMIN || (ROLE_READ_WRITE &amp;&amp; ROLE_SPECIAL)"</js>
743    *       )
744    *       <jk>public</jk> Object doGet() {
745    *       }
746    *    }
747    * </p>
748    *
749    * <h5 class='section'>Notes:</h5><ul>
750    *    <li class='note'>
751    *       Supports any of the following expression constructs:
752    *       <ul>
753    *          <li><js>"foo"</js> - Single arguments.
754    *          <li><js>"foo,bar,baz"</js> - Multiple OR'ed arguments.
755    *          <li><js>"foo | bar | baz"</js> - Multiple OR'ed arguments, pipe syntax.
756    *          <li><js>"foo || bar || baz"</js> - Multiple OR'ed arguments, Java-OR syntax.
757    *          <li><js>"fo*"</js> - Patterns including <js>'*'</js> and <js>'?'</js>.
758    *          <li><js>"fo* &amp; *oo"</js> - Multiple AND'ed arguments, ampersand syntax.
759    *          <li><js>"fo* &amp;&amp; *oo"</js> - Multiple AND'ed arguments, Java-AND syntax.
760    *          <li><js>"fo* || (*oo || bar)"</js> - Parenthesis.
761    *       </ul>
762    *    <li class='note'>
763    *       AND operations take precedence over OR operations (as expected).
764    *    <li class='note'>
765    *       Whitespace is ignored.
766    *    <li class='note'>
767    *       <jk>null</jk> or empty expressions always match as <jk>false</jk>.
768    *    <li class='note'>
769    *       If patterns are used, you must specify the list of declared roles using {@link #rolesDeclared()} or {@link org.apache.juneau.rest.RestOpContext.Builder#rolesDeclared(String...)}.
770    *    <li class='note'>
771    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
772    *       (e.g. <js>"$L{my.localized.variable}"</js>).
773    *    <li class='note'>
774    *       When defined on parent/child classes and methods, ALL guards within the hierarchy must pass.
775    * </ul>
776    *
777    * <h5 class='section'>See Also:</h5><ul>
778    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#roleGuard(String)}
779    * </ul>
780    *
781    * @return The annotation value.
782    */
783   String roleGuard() default "";
784
785   /**
786    * Declared roles.
787    *
788    * <p>
789    * A comma-delimited list of all possible user roles.
790    *
791    * <p>
792    * Used in conjunction with {@link #roleGuard()} is used with patterns.
793    *
794    * <h5 class='section'>Example:</h5>
795    * <p class='bjava'>
796    *    <jk>public class</jk> MyResource <jk>extends</jk> BasicRestServlet {
797    *
798    *       <ja>@RestOp</ja>(
799    *          method=<jsf>GET</jsf>,
800    *          path=<js>"/foo"</js>,
801    *          rolesDeclared=<js>"ROLE_ADMIN,ROLE_READ_WRITE,ROLE_READ_ONLY,ROLE_SPECIAL"</js>,
802    *          roleGuard=<js>"ROLE_ADMIN || (ROLE_READ_WRITE &amp;&amp; ROLE_SPECIAL)"</js>
803    *       )
804    *       <jk>public</jk> Object doGet() {
805    *       }
806    *    }
807    * </p>
808    *
809    * <h5 class='section'>See Also:</h5><ul>
810    *    <li class='jm'>{@link org.apache.juneau.rest.RestOpContext.Builder#rolesDeclared(String...)}
811    * </ul>
812    *
813    * @return The annotation value.
814    */
815   String rolesDeclared() default "";
816
817   /**
818    * Specifies the serializers for marshalling POJOs into response bodies for this method.
819    *
820    * <p>
821    * Serializer are used to convert POJOs to HTTP response bodies.
822    * <br>Any of the Juneau framework serializers can be used in this setting.
823    * <br>The serializer selected is based on the request <c>Accept</c> header matched against the values returned by the following method
824    * using a best-match algorithm:
825    * <ul class='javatree'>
826    *    <li class='jm'>{@link Serializer#getMediaTypeRanges()}
827    * </ul>
828    *
829    * <p>
830    * This value overrides serializers specified at the class level using {@link Rest#serializers()}.
831    * The {@link org.apache.juneau.serializer.SerializerSet.Inherit} class can be used to include values from the parent class.
832    *
833    * <h5 class='section'>Example:</h5>
834    * <p class='bjava'>
835    *    <jc>// Define a REST resource that can produce JSON and HTML.</jc>
836    *    <ja>@Rest</ja>(
837    *       serializers={
838    *          JsonParser.<jk>class</jk>,
839    *          HtmlParser.<jk>class</jk>
840    *       }
841    *    )
842    *    <jk>public class</jk> MyResource {
843    *
844    *       <jc>// Define a REST method that can also produce XML.</jc>
845    *       <ja>@RestOp</ja>(
846    *          method=<jsf>POST</jsf>,
847    *          parsers={
848    *             SerializerSet.Inherit.<jk>class</jk>, XmlParser.<jk>class</jk>
849    *          }
850    *       )
851    *       <jk>public void</jk> doPost(MyBean <jv>bean</jv>) {
852    *          ...
853    *       }
854    *    }
855    * </p>
856    *
857    * <p>
858    * The programmatic equivalent to this annotation is:
859    * <p class='bjava'>
860    *    RestOpContext.Builder <jv>builder</jv> = RestOpContext.<jsm>create</jsm>(<jv>method</jv>,<jv>restContext</jv>);
861    *    <jv>builder</jv>.getSerializers().set(<jv>classes</jv>);
862    * </p>
863    *
864    * <h5 class='section'>See Also:</h5><ul>
865    *    <li class='link'><a class="doclink" href="https://juneau.apache.org/docs/topics/Marshalling">Marshalling</a>
866    * </ul>
867    *
868    * @return The annotation value.
869    */
870   Class<? extends Serializer>[] serializers() default {};
871
872   /**
873    * Optional summary for the exposed API.
874    *
875    * <p>
876    * This summary is used in the following locations:
877    * <ul class='spaced-list'>
878    *    <li>
879    *       The value returned by {@link Operation#getSummary()} in the auto-generated swagger.
880    *    <li>
881    *       The <js>"$RS{operationSummary}"</js> variable.
882    *    <li>
883    *       The summary of the method in the Swagger page.
884    * </ul>
885    *
886    * <h5 class='section'>Notes:</h5><ul>
887    *    <li class='note'>
888    *       Corresponds to the swagger field <c>/paths/{path}/{method}/summary</c>.
889    *    <li class='note'>
890    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
891    *       (e.g. <js>"$L{my.localized.variable}"</js>).
892    * </ul>
893    *
894    * @return The annotation value.
895    */
896   String summary() default "";
897
898   /**
899    * Provides swagger-specific metadata on this method.
900    *
901    * <p>
902    * Used to populate the auto-generated OPTIONS swagger documentation.
903    *
904    * <p>
905    * The format of this annotation is JSON when all individual parts are concatenated.
906    * <br>The starting and ending <js>'{'</js>/<js>'}'</js> characters around the entire value are optional.
907    *
908    * <h5 class='section'>Example:</h5>
909    * <p class='bjava'>
910    *    <ja>@RestOp</ja>(
911    *       method=<jsf>PUT</jsf>,
912    *       path=<js>"/{propertyName}"</js>,
913    *
914    *       <jc>// Swagger info.</jc>
915    *       swagger={
916    *          <js>"parameters:["</js>,
917    *             <js>"{name:'propertyName',in:'path',description:'The system property name.'},"</js>,
918    *             <js>"{in:'body',description:'The new system property value.'}"</js>,
919    *          <js>"],"</js>,
920    *          <js>"responses:{"</js>,
921    *             <js>"302: {headers:{Location:{description:'The root URL of this resource.'}}},"</js>,
922    *             <js>"403: {description:'User is not an admin.'}"</js>,
923    *          <js>"}"</js>
924    *       }
925    *    )
926    * </p>
927    *
928    * <h5 class='section'>Notes:</h5><ul>
929    *    <li class='note'>
930    *       The format is <a class="doclink" href="https://juneau.apache.org/docs/topics/JuneauBeanSwagger2">juneau-bean-swagger-v2</a>.
931    *       <br>Multiple lines are concatenated with newlines.
932    *    <li class='note'>
933    *       The starting and ending <js>'{'</js>/<js>'}'</js> characters around the entire value are optional.
934    *    <li class='note'>
935    *       These values are superimposed on top of any Swagger JSON file present for the resource in the classpath.
936    *    <li class='note'>
937    *       Supports <a class="doclink" href="https://juneau.apache.org/docs/topics/RestServerSvlVariables">SVL Variables</a>
938    *       (e.g. <js>"$L{my.localized.variable}"</js>).
939    * </ul>
940    *
941    * <h5 class='section'>See Also:</h5><ul>
942    *    <li class='ja'>{@link OpSwagger}
943    *    <li class='jc'>{@link SwaggerProvider}
944    * </ul>
945    *
946    * @return The annotation value.
947    */
948   OpSwagger swagger() default @OpSwagger;
949
950   /**
951    * REST method name and path.
952    *
953    * <p>
954    * Can be used to provide a shortened combined form for the {@link #method()} and {@link #path()} values.
955    *
956    * <p>
957    * The following examples are considered equivalent.
958    * <p class='bjava'>
959    *    <jc>// Normal form</jc>
960    *    <ja>@RestOp</ja>(method=<jsf>PUT</jsf>, path=<js>"/{propertyName}"</js>)
961    *
962    *    <jc>// Shortened form</jc>
963    *    <ja>@RestOp</ja>(<js>"PUT /{propertyName}"</js>)
964    * </p>
965    *
966    * <h5 class='section'>Notes:</h5><ul>
967    *    <li class='note'>
968    *       The path portion is optional.
969    * </ul>
970    *
971    * @return The annotation value.
972    */
973   String value() default "";
974}