1 /* 2 * Copyright (C) 2017 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.tools.metalava 18 19 const val COMPAT_MODE_BY_DEFAULT = true 20 21 /** 22 * The old API generator code had a number of quirks. Initially we want to simulate these 23 * quirks to produce compatible signature files and APIs, but we want to track what these quirks 24 * are and be able to turn them off eventually. This class offers more fine grained control 25 * of these compatibility behaviors such that we can enable/disable them selectively 26 */ 27 var compatibility: Compatibility = Compatibility() 28 29 class Compatibility( 30 /** Whether compatibility is generally on */ 31 val compat: Boolean = COMPAT_MODE_BY_DEFAULT 32 ) { 33 34 /** Whether to inline fields from implemented interfaces into concrete classes */ 35 var inlineInterfaceFields: Boolean = compat 36 37 /** In signature files, use "implements" instead of "extends" for the super class of 38 * an interface */ 39 var extendsForInterfaceSuperClass: Boolean = compat 40 41 /** In signature files, refer to annotations as an "abstract class" instead of an "@interface" 42 * and implementing this interface: java.lang.annotation.Annotation */ 43 var classForAnnotations: Boolean = compat 44 45 /** Add in explicit `valueOf` and `values` methods into annotation classes */ 46 var defaultAnnotationMethods: Boolean = compat 47 48 /** In signature files, refer to enums as "class" instead of "enum" */ 49 var classForEnums: Boolean = compat 50 51 /** Whether to use a nonstandard, compatibility modifier order instead of the Java canonical order. 52 * ("deprecated" isn't a real modifier, so in "standard" mode it's listed first, as if it was the 53 * `@Deprecated` annotation before the modifier list */ 54 var nonstandardModifierOrder: Boolean = compat 55 56 /** In signature files, skip the native modifier from the modifier lists */ 57 var skipNativeModifier: Boolean = nonstandardModifierOrder 58 59 /** In signature files, skip the strictfp modifier from the modifier lists */ 60 var skipStrictFpModifier: Boolean = nonstandardModifierOrder 61 62 /** Whether to include instance methods in annotation classes for the annotation properties */ 63 var skipAnnotationInstanceMethods: Boolean = compat 64 65 /** Include spaces after commas in type strings */ 66 var spacesAfterCommas: Boolean = compat 67 68 /** Use two spaces after type for package private elements in signature files */ 69 var doubleSpaceForPackagePrivate: Boolean = compat 70 71 /** 72 * In signature files, whether interfaces should also be described as "abstract" 73 */ 74 var abstractInInterfaces: Boolean = compat 75 76 /** 77 * In signature files, whether annotation types should also be described as "abstract" 78 */ 79 var abstractInAnnotations: Boolean = compat 80 81 /** 82 * In signature files, whether interfaces can be listed as final 83 */ 84 var finalInInterfaces: Boolean = compat 85 86 /** 87 * In this signature 88 * public <X extends Throwable> T orElseThrow(Supplier<? extends X> exceptionSupplier) throws X { 89 * doclava1 would treat this as "throws Throwable" instead of "throws X". This variable turns on 90 * this compat behavior. 91 * */ 92 var useErasureInThrows: Boolean = compat 93 94 /** 95 * Whether throws classes in methods should be filtered. This should definitely 96 * be the case, but doclava1 doesn't. Note that this only applies to signature 97 * files, not stub files. 98 */ 99 var filterThrowsClasses: Boolean = !compat 100 101 /** 102 * Include a single space in front of package private classes with no other modifiers 103 * (this doesn't align well, but is supported to make the output 100% identical to the 104 * doclava1 format 105 */ 106 var extraSpaceForEmptyModifiers: Boolean = compat 107 108 /** Format `Map<K,V>` as `Map<K, V>` */ 109 var spaceAfterCommaInTypes: Boolean = compat 110 111 /** 112 * Doclava1 sorts classes/interfaces by class name instead of qualified name 113 */ 114 var sortClassesBySimpleName: Boolean = compat 115 116 /** 117 * Doclava1 omits type parameters in interfaces (in signature files, not in stubs) 118 */ 119 var omitTypeParametersInInterfaces: Boolean = compat 120 121 /** 122 * Doclava1 sorted the methods like this: 123 * 124 * public final class RoundingMode extends java.lang.Enum { 125 * method public static java.math.RoundingMode valueOf(java.lang.String); 126 * method public static java.math.RoundingMode valueOf(int); 127 * ... 128 * 129 * Note how the two valueOf methods are out of order. With this compatibility mode, 130 * we try to perform the same sorting. 131 */ 132 var sortEnumValueOfMethodFirst: Boolean = compat 133 134 /** 135 * Whether packages should be treated as recursive for documentation. In other words, 136 * if a directory has a `packages.html` file containing a `@hide` comment, then 137 * all "sub" packages (directories below this one) will also inherit the same comment. 138 * Java packages aren't supposed to work that way, but doclava does. 139 */ 140 var inheritPackageDocs: Boolean = compat 141 142 /** Force methods named "values" in enums to be marked final. This was done by 143 * doclava1 with this comment: 144 * 145 * Explicitly coerce 'final' state of Java6-compiled enum values() method, 146 * to match the Java5-emitted base API description. 147 * 148 **/ 149 var forceFinalInEnumValueMethods: Boolean = compat 150 151 /** Whether signature files and stubs should contain annotations */ 152 var annotationsInSignatures: Boolean = !compat 153 154 /** Emit errors in the old API diff format */ 155 var oldErrorOutputFormat: Boolean = false 156 157 /** 158 * When a public class implementing a public interface inherits the implementation 159 * of a method in that interface from a hidden super class, the method must be 160 * included in the stubs etc (since otherwise subclasses would believe they need 161 * to implement that method and can't just inherit it). However, doclava1 does not 162 * list these methods. This flag controls this compatibility behavior. 163 * Not that this refers only to the signature files, not the stub file generation. 164 * 165 * An example is StringBuilder#setLength. 166 */ 167 var skipInheritedMethods: Boolean = compat 168 169 /** 170 * Whether to include parameter names in the signature file 171 */ 172 var parameterNames: Boolean = true 173 174 /** 175 * *Some* signatures for doclava1 wrote "<?>" as "<? extends java.lang.Object>", 176 * which is equivalent. Metalava does not do that. This flags ensures that the 177 * signature files look like the old ones for the specific methods which did this. 178 */ 179 var includeExtendsObjectInWildcard = compat 180 181 // Other examples: sometimes we sort by qualified name, sometimes by full name 182 }