mirror of https://github.com/apache/lucene.git
LUCENE-9375: some build file cleanups. (#10)
This commit is contained in:
parent
2892ef4ca0
commit
7f5e660395
|
@ -146,7 +146,6 @@ apply from: file('gradle/validation/rat-sources.gradle')
|
|||
apply from: file('gradle/validation/owasp-dependency-check.gradle')
|
||||
apply from: file('gradle/validation/ecj-lint.gradle')
|
||||
apply from: file('gradle/validation/gradlew-scripts-tweaked.gradle')
|
||||
apply from: file('gradle/validation/validate-log-calls.gradle')
|
||||
apply from: file('gradle/validation/check-broken-links.gradle')
|
||||
|
||||
if (!skipLucene) {
|
||||
|
|
|
@ -1,21 +0,0 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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
|
||||
*
|
||||
* http://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.
|
||||
*/
|
||||
|
||||
// Stick to previous artifact names (not identical to path/ folders).
|
||||
configure(subprojects.findAll { it.path.contains(':solr:contrib:') }) {
|
||||
project.archivesBaseName = project.archivesBaseName.replace("-contrib-", "-")
|
||||
}
|
|
@ -1,37 +0,0 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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
|
||||
*
|
||||
* http://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.
|
||||
*/
|
||||
|
||||
|
||||
// Force versions of certain components to align them with ant build.
|
||||
|
||||
project(":solr").subprojects {
|
||||
plugins.withType(JavaPlugin) {
|
||||
dependencies {
|
||||
implementation enforcedPlatform('org.slf4j:slf4j-api:1.7.24')
|
||||
implementation enforcedPlatform('commons-logging:commons-logging:1.1.3')
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
configure(project(":solr:server")) {
|
||||
afterEvaluate {
|
||||
dependencies {
|
||||
libExt enforcedPlatform('org.slf4j:slf4j-api:1.7.24')
|
||||
libExt enforcedPlatform('commons-logging:commons-logging:1.1.3')
|
||||
}
|
||||
}
|
||||
}
|
|
@ -55,19 +55,7 @@ configure(rootProject) {
|
|||
":lucene:spatial-extras",
|
||||
":lucene:spatial3d",
|
||||
":lucene:suggest",
|
||||
":lucene:test-framework",
|
||||
|
||||
":solr:core",
|
||||
":solr:solrj",
|
||||
":solr:contrib:analysis-extras",
|
||||
":solr:contrib:analytics",
|
||||
":solr:contrib:clustering",
|
||||
":solr:contrib:extraction",
|
||||
":solr:contrib:langid",
|
||||
":solr:contrib:jaegertracer-configurator",
|
||||
":solr:contrib:prometheus-exporter",
|
||||
":solr:contrib:scripting",
|
||||
":solr:test-framework",
|
||||
":lucene:test-framework"
|
||||
]
|
||||
|
||||
apacheNexusSnapshots = "https://repository.apache.org/content/repositories/snapshots"
|
||||
|
@ -123,9 +111,7 @@ configure(subprojects.findAll { it.path in rootProject.published }) { prj ->
|
|||
// in gradle or just complex relationships between lazy collection hooks.
|
||||
gradle.projectsEvaluated {
|
||||
publishing {
|
||||
def configurePom;
|
||||
if (project.path.startsWith(":lucene")) {
|
||||
configurePom = {
|
||||
def configurePom = {
|
||||
name = "Apache Lucene (module: ${project.name})"
|
||||
description = name
|
||||
url = 'https://lucene.apache.org/'
|
||||
|
@ -150,13 +136,6 @@ configure(subprojects.findAll { it.path in rootProject.published }) { prj ->
|
|||
}
|
||||
|
||||
mailingLists {
|
||||
mailingList {
|
||||
name = "General List"
|
||||
subscribe = "general-subscribe@lucene.apache.org"
|
||||
unsubscribe = "general-unsubscribe@lucene.apache.org"
|
||||
archive = "https://mail-archives.apache.org/mod_mbox/lucene-general/"
|
||||
}
|
||||
|
||||
mailingList {
|
||||
name = "Java User List"
|
||||
subscribe = "java-user-subscribe@lucene.apache.org"
|
||||
|
@ -180,65 +159,10 @@ configure(subprojects.findAll { it.path in rootProject.published }) { prj ->
|
|||
}
|
||||
|
||||
scm {
|
||||
connection = 'scm:git:https://gitbox.apache.org/repos/asf/lucene-solr.git'
|
||||
developerConnection = 'scm:git:https://gitbox.apache.org/repos/asf/lucene-solr.git'
|
||||
url = 'https://gitbox.apache.org/repos/asf?p=lucene-solr.git'
|
||||
connection = 'scm:git:https://gitbox.apache.org/repos/asf/lucene.git'
|
||||
developerConnection = 'scm:git:https://gitbox.apache.org/repos/asf/lucene.git'
|
||||
url = 'https://gitbox.apache.org/repos/asf?p=lucene.git'
|
||||
}
|
||||
}
|
||||
} else {
|
||||
configurePom = {
|
||||
name = "Apache Solr (module: ${project.name})"
|
||||
description = name
|
||||
url = 'https://lucene.apache.org/solr/'
|
||||
|
||||
licenses {
|
||||
license {
|
||||
name = 'Apache 2'
|
||||
url = 'http://www.apache.org/licenses/LICENSE-2.0.txt'
|
||||
}
|
||||
}
|
||||
|
||||
inceptionYear = "2006"
|
||||
|
||||
issueManagement {
|
||||
system = "JIRA"
|
||||
url = "https://issues.apache.org/jira/browse/SOLR"
|
||||
}
|
||||
|
||||
ciManagement {
|
||||
system = "Jenkins"
|
||||
url = "https://builds.apache.org/job/Lucene/"
|
||||
}
|
||||
|
||||
mailingLists {
|
||||
mailingList {
|
||||
name = "Solr User List"
|
||||
subscribe = "solr-user-subscribe@lucene.apache.org"
|
||||
unsubscribe = "solr-user-unsubscribe@lucene.apache.org"
|
||||
archive = "https://mail-archives.apache.org/mod_mbox/solr-user/"
|
||||
}
|
||||
|
||||
mailingList {
|
||||
name = "Java Developer List"
|
||||
subscribe = "dev-subscribe@lucene.apache.org"
|
||||
unsubscribe = "dev-unsubscribe@lucene.apache.org"
|
||||
archive = "https://mail-archives.apache.org/mod_mbox/lucene-dev/"
|
||||
}
|
||||
|
||||
mailingList {
|
||||
name = "Java Commits List"
|
||||
subscribe = "commits-subscribe@lucene.apache.org"
|
||||
unsubscribe = "commits-unsubscribe@lucene.apache.org"
|
||||
archive = "https://mail-archives.apache.org/mod_mbox/lucene-java-commits/"
|
||||
}
|
||||
}
|
||||
|
||||
scm {
|
||||
connection = 'scm:git:https://gitbox.apache.org/repos/asf/lucene-solr.git'
|
||||
developerConnection = 'scm:git:https://gitbox.apache.org/repos/asf/lucene-solr.git'
|
||||
url = 'https://gitbox.apache.org/repos/asf?p=lucene-solr.git'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
publications {
|
||||
|
|
|
@ -189,15 +189,9 @@ allprojects {
|
|||
} else if (project.path.startsWith(":lucene")) {
|
||||
systemProperty 'java.security.manager', "org.apache.lucene.util.TestSecurityManager"
|
||||
systemProperty 'java.security.policy', file("${resources}/policies/tests.policy")
|
||||
} else {
|
||||
systemProperty 'common-solr.dir', commonSolrDir
|
||||
systemProperty 'java.security.manager', "org.apache.lucene.util.TestSecurityManager"
|
||||
systemProperty 'java.security.policy', file("${resources}/policies/solr-tests.policy")
|
||||
}
|
||||
|
||||
if (!skipLucene) {
|
||||
systemProperty 'common.dir', commonDir
|
||||
}
|
||||
systemProperty 'common.dir', commonDir
|
||||
|
||||
def gradleUserHome = project.gradle.getGradleUserHomeDir()
|
||||
systemProperty 'gradle.lib.dir', Paths.get(project.class.location.toURI()).parent.toAbsolutePath().toString().replace('\\', '/')
|
||||
|
|
|
@ -1,217 +0,0 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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
|
||||
*
|
||||
* http://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.
|
||||
*/
|
||||
|
||||
// Policy file for solr. Please keep minimal and avoid wildcards.
|
||||
|
||||
// permissions needed for tests to pass, based on properties set by the build system
|
||||
// NOTE: if the property is not set, the permission entry is ignored.
|
||||
grant {
|
||||
// 3rd party jar resources (where symlinks are not supported), test-files/ resources
|
||||
permission java.io.FilePermission "${common.dir}${/}-", "read";
|
||||
permission java.io.FilePermission "${common-solr.dir}${/}-", "read";
|
||||
|
||||
// system jar resources
|
||||
permission java.io.FilePermission "${java.home}${/}-", "read";
|
||||
|
||||
// Test launchers (randomizedtesting, etc.)
|
||||
permission java.io.FilePermission "${java.io.tmpdir}", "read,write";
|
||||
permission java.io.FilePermission "${java.io.tmpdir}${/}-", "read,write,delete";
|
||||
|
||||
permission java.io.FilePermission "${tests.linedocsfile}", "read";
|
||||
// DirectoryFactoryTest messes with these (wtf?)
|
||||
permission java.io.FilePermission "/tmp/inst1/conf/solrcore.properties", "read";
|
||||
permission java.io.FilePermission "/path/to/myinst/conf/solrcore.properties", "read";
|
||||
// TestConfigSets messes with these (wtf?)
|
||||
permission java.io.FilePermission "/path/to/solr/home/lib", "read";
|
||||
|
||||
permission java.nio.file.LinkPermission "hard";
|
||||
|
||||
// all possibilities of accepting/binding/connections on localhost with ports >=1024:
|
||||
permission java.net.SocketPermission "localhost:1024-", "accept,listen,connect,resolve";
|
||||
permission java.net.SocketPermission "127.0.0.1:1024-", "accept,listen,connect,resolve";
|
||||
permission java.net.SocketPermission "[::1]:1024-", "accept,listen,connect,resolve";
|
||||
// "dead hosts", we try to keep it fast
|
||||
permission java.net.SocketPermission "[::1]:4", "connect,resolve";
|
||||
permission java.net.SocketPermission "[::1]:6", "connect,resolve";
|
||||
permission java.net.SocketPermission "[::1]:8", "connect,resolve";
|
||||
|
||||
// Basic permissions needed for Lucene to work:
|
||||
permission java.util.PropertyPermission "*", "read,write";
|
||||
|
||||
// needed by randomizedtesting runner to identify test methods.
|
||||
permission java.lang.reflect.ReflectPermission "suppressAccessChecks";
|
||||
permission java.lang.RuntimePermission "accessDeclaredMembers";
|
||||
// needed by certain tests to redirect sysout/syserr:
|
||||
permission java.lang.RuntimePermission "setIO";
|
||||
// needed by randomized runner to catch failures from other threads:
|
||||
permission java.lang.RuntimePermission "setDefaultUncaughtExceptionHandler";
|
||||
// needed by randomized runner getTopThreadGroup:
|
||||
permission java.lang.RuntimePermission "modifyThreadGroup";
|
||||
// needed by tests e.g. shutting down executors:
|
||||
permission java.lang.RuntimePermission "modifyThread";
|
||||
// needed for tons of test hacks etc
|
||||
permission java.lang.RuntimePermission "getStackTrace";
|
||||
// needed for mock filesystems in tests
|
||||
permission java.lang.RuntimePermission "fileSystemProvider";
|
||||
// needed by IndexFetcher
|
||||
permission java.lang.RuntimePermission "getFileStoreAttributes";
|
||||
// analyzers/uima: needed by lucene expressions' JavascriptCompiler
|
||||
permission java.lang.RuntimePermission "createClassLoader";
|
||||
// needed to test unmap hack on platforms that support it
|
||||
permission java.lang.RuntimePermission "accessClassInPackage.sun.misc";
|
||||
// needed by jacoco to dump coverage
|
||||
permission java.lang.RuntimePermission "shutdownHooks";
|
||||
// needed by org.apache.logging.log4j
|
||||
permission java.lang.RuntimePermission "getenv.*";
|
||||
permission java.lang.RuntimePermission "getClassLoader";
|
||||
permission java.lang.RuntimePermission "setContextClassLoader";
|
||||
permission java.lang.RuntimePermission "getStackWalkerWithClassReference";
|
||||
// needed by bytebuddy
|
||||
permission java.lang.RuntimePermission "defineClass";
|
||||
// needed by mockito
|
||||
permission java.lang.RuntimePermission "accessClassInPackage.sun.reflect";
|
||||
permission java.lang.RuntimePermission "reflectionFactoryAccess";
|
||||
// needed by SolrResourceLoader
|
||||
permission java.lang.RuntimePermission "closeClassLoader";
|
||||
// needed by HttpSolrClient
|
||||
permission java.lang.RuntimePermission "getFileSystemAttributes";
|
||||
// needed by hadoop auth (TODO: there is a cleaner way to handle this)
|
||||
permission java.lang.RuntimePermission "loadLibrary.jaas";
|
||||
permission java.lang.RuntimePermission "loadLibrary.jaas_unix";
|
||||
permission java.lang.RuntimePermission "loadLibrary.jaas_nt";
|
||||
// needed by hadoop common RawLocalFileSystem for java nio getOwner
|
||||
permission java.lang.RuntimePermission "accessUserInformation";
|
||||
// needed by hadoop hdfs
|
||||
permission java.lang.RuntimePermission "readFileDescriptor";
|
||||
permission java.lang.RuntimePermission "writeFileDescriptor";
|
||||
// needed by hadoop http
|
||||
permission java.lang.RuntimePermission "getProtectionDomain";
|
||||
|
||||
// These two *have* to be spelled out a separate
|
||||
permission java.lang.management.ManagementPermission "control";
|
||||
permission java.lang.management.ManagementPermission "monitor";
|
||||
|
||||
// needed by hadoop htrace
|
||||
permission java.net.NetPermission "getNetworkInformation";
|
||||
|
||||
// needed by DIH - possibly even after DIH is a package
|
||||
permission java.sql.SQLPermission "deregisterDriver";
|
||||
|
||||
permission java.util.logging.LoggingPermission "control";
|
||||
|
||||
// needed by solr mbeans feature/tests
|
||||
// TODO: can we remove wildcard for class names/members?
|
||||
permission javax.management.MBeanPermission "*", "getAttribute";
|
||||
permission javax.management.MBeanPermission "*", "getMBeanInfo";
|
||||
permission javax.management.MBeanPermission "*", "queryMBeans";
|
||||
permission javax.management.MBeanPermission "*", "queryNames";
|
||||
permission javax.management.MBeanPermission "*", "registerMBean";
|
||||
permission javax.management.MBeanPermission "*", "unregisterMBean";
|
||||
permission javax.management.MBeanServerPermission "createMBeanServer";
|
||||
permission javax.management.MBeanServerPermission "findMBeanServer";
|
||||
permission javax.management.MBeanServerPermission "releaseMBeanServer";
|
||||
permission javax.management.MBeanTrustPermission "register";
|
||||
|
||||
// needed by hadoop auth
|
||||
permission javax.security.auth.AuthPermission "getSubject";
|
||||
permission javax.security.auth.AuthPermission "modifyPrincipals";
|
||||
permission javax.security.auth.AuthPermission "doAs";
|
||||
permission javax.security.auth.AuthPermission "getLoginConfiguration";
|
||||
permission javax.security.auth.AuthPermission "setLoginConfiguration";
|
||||
permission javax.security.auth.AuthPermission "modifyPrivateCredentials";
|
||||
permission javax.security.auth.AuthPermission "modifyPublicCredentials";
|
||||
permission javax.security.auth.PrivateCredentialPermission "org.apache.hadoop.security.Credentials * \"*\"", "read";
|
||||
|
||||
// needed by hadoop security
|
||||
permission java.security.SecurityPermission "putProviderProperty.SaslPlainServer";
|
||||
permission java.security.SecurityPermission "insertProvider";
|
||||
|
||||
permission javax.xml.bind.JAXBPermission "setDatatypeConverter";
|
||||
|
||||
// SSL related properties for Solr tests
|
||||
permission javax.net.ssl.SSLPermission "setDefaultSSLContext";
|
||||
|
||||
// SASL/Kerberos related properties for Solr tests
|
||||
permission javax.security.auth.PrivateCredentialPermission "javax.security.auth.kerberos.KerberosTicket * \"*\"", "read";
|
||||
|
||||
// may only be necessary with Java 7?
|
||||
permission javax.security.auth.PrivateCredentialPermission "javax.security.auth.kerberos.KeyTab * \"*\"", "read";
|
||||
permission javax.security.auth.PrivateCredentialPermission "sun.security.jgss.krb5.Krb5Util$KeysFromKeyTab * \"*\"", "read";
|
||||
|
||||
permission javax.security.auth.kerberos.ServicePermission "*", "initiate";
|
||||
permission javax.security.auth.kerberos.ServicePermission "*", "accept";
|
||||
permission javax.security.auth.kerberos.DelegationPermission "\"*\" \"krbtgt/EXAMPLE.COM@EXAMPLE.COM\"";
|
||||
|
||||
// java 8 accessibility requires this perm - should not after 8 I believe (rrd4j is the root reason we hit an accessibility code path)
|
||||
permission java.awt.AWTPermission "*";
|
||||
|
||||
// used by solr to create sandboxes (e.g. script execution)
|
||||
permission java.security.SecurityPermission "createAccessControlContext";
|
||||
};
|
||||
|
||||
// additional permissions based on system properties set by /bin/solr
|
||||
// NOTE: if the property is not set, the permission entry is ignored.
|
||||
grant {
|
||||
permission java.io.FilePermission "${hadoop.security.credential.provider.path}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${hadoop.security.credential.provider.path}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${solr.jetty.keystore}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${solr.jetty.keystore}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${solr.jetty.truststore}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${solr.jetty.truststore}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${solr.install.dir}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${solr.install.dir}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${jetty.home}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${jetty.home}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${solr.solr.home}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${solr.solr.home}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${solr.data.home}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${solr.data.home}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${solr.default.confdir}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${solr.default.confdir}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${solr.log.dir}", "read,write,delete,readlink";
|
||||
permission java.io.FilePermission "${solr.log.dir}${/}-", "read,write,delete,readlink";
|
||||
|
||||
permission java.io.FilePermission "${log4j.configurationFile}", "read,write,delete,readlink";
|
||||
|
||||
// expanded to a wildcard if set, allows all networking everywhere
|
||||
permission java.net.SocketPermission "${solr.internal.network.permission}", "accept,listen,connect,resolve";
|
||||
};
|
||||
|
||||
// Grant all permissions to Gradle test runner classes.
|
||||
|
||||
grant codeBase "file:${gradle.lib.dir}${/}-" {
|
||||
permission java.security.AllPermission;
|
||||
};
|
||||
|
||||
grant codeBase "file:${gradle.worker.jar}" {
|
||||
permission java.security.AllPermission;
|
||||
};
|
||||
|
||||
grant {
|
||||
// Allow reading gradle worker JAR.
|
||||
permission java.io.FilePermission "${gradle.worker.jar}", "read";
|
||||
// Allow reading from classpath JARs (resources).
|
||||
permission java.io.FilePermission "${gradle.user.home}${/}-", "read";
|
||||
};
|
|
@ -36,7 +36,6 @@ configure(rootProject) {
|
|||
"javadoc",
|
||||
"rat",
|
||||
"ecjLint",
|
||||
"validateLogCalls",
|
||||
"validateSourcePatterns",
|
||||
"spotlessCheck"
|
||||
]}
|
||||
|
|
|
@ -1,235 +0,0 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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
|
||||
*
|
||||
* http://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.
|
||||
*/
|
||||
|
||||
import org.apache.tools.ant.BuildException
|
||||
|
||||
// Checks logging calls to keep from using patterns that might be expensive
|
||||
// either in CPU or unnecessary object creation. Some of the checks are a little
|
||||
// over-zealous, but it's worth a bit of aggravation to catch the egregious
|
||||
// mistakes before they accrue.
|
||||
|
||||
// This all started with Java Flight Recorder showing a massive number of
|
||||
// objects allocated and garbage collected. Tracing a bunch of them down showed
|
||||
// that we have a number of calls like:
|
||||
// log.debug("some string" + very_expensive_object_to_make_a_string).
|
||||
// which _always_ constructed the very expensive ojbect even if the log level
|
||||
// was INFO or more severe. Rather than leave lots of confusing formats laying
|
||||
// about or expecting people to remember the rules, we opted to make this
|
||||
// check part of Gradle precommit. It will be included by default in Solr
|
||||
// 9.0.
|
||||
|
||||
// See the associated help task "gradlew helpValidateLogCalls"
|
||||
|
||||
configure(subprojects.findAll { it.path.startsWith(':solr') }) {
|
||||
plugins.withType(JavaPlugin) {
|
||||
task validateLogCalls(type: ValidateLogCallsTask) { task ->
|
||||
description "Checks that log calls are either validated or conform to efficient patterns."
|
||||
group "verification"
|
||||
|
||||
// This task has no proper outputs.
|
||||
setupDummyOutputs(task)
|
||||
|
||||
sourceFiles = files(sourceSets*.java)
|
||||
}
|
||||
|
||||
// Add log validation to per-project checks as well.
|
||||
check.dependsOn validateLogCalls
|
||||
}
|
||||
}
|
||||
|
||||
class ValidateLogCallsTask extends DefaultTask {
|
||||
def logLevels = ["log.trace", "log.debug", "log.info", "log.warn", "log.error", "log.fatal"]
|
||||
|
||||
def errsFound = 0;
|
||||
def violations = new ArrayList();
|
||||
|
||||
def reportViolation(String msg) {
|
||||
violations.add(System.lineSeparator + msg);
|
||||
errsFound++;
|
||||
}
|
||||
|
||||
// We have a log.something line, check for patterns we're not fond of.
|
||||
def checkLine(File file, String line, int lineNumber, String previous) {
|
||||
boolean violation = false
|
||||
|
||||
// If the line has been explicitly OK'd, then it's OK!
|
||||
if (line.replaceAll("\\s", "").toLowerCase().contains("//nowarn")) {
|
||||
return
|
||||
}
|
||||
// Strip all of the comments, things in quotes and the like.
|
||||
def stripped =
|
||||
line.replaceFirst("//.*", " ") // remove comment to EOL. May be fragile due to the possibility of embedded double slashes
|
||||
.replaceFirst(/.*?\(/, " ") // Get rid of "log.whatever("
|
||||
.replaceFirst(/\);/, " ") // get rid of the closing ");"
|
||||
.replaceFirst("/\\*.*?\\*/", " ") // replace embedded comments "/*....*/"
|
||||
.replaceAll(/".*?"/, '""') // remove anything between quotes. This is a bit fragile if there are embedded double quotes.
|
||||
.replaceAll(/timeLeft\(.*?\)/, " ") // used all over tests, it's benign
|
||||
.replaceAll(/TimeUnit\..*?\.convert\(.*?\)/, " ") // again, a pattern that's efficient
|
||||
.replaceAll("\\s", "")
|
||||
|
||||
// The compiler will pre-assemble patterns like 'log.info("string const1 {}" + " string const2 {}", obj1, obj2)'
|
||||
// to log.info("string const1 {} string const2 {}", obj1, obj2)', so don't worry about any plus preceded and
|
||||
// followed by double quotes, otherwise flag it.
|
||||
def hasPlus = false
|
||||
for (int idx = 0; idx < stripped.length(); ++idx) {
|
||||
if (stripped.charAt(idx) == '+') {
|
||||
if (idx == 0 || idx == stripped.length() - 1
|
||||
|| stripped.charAt(idx - 1) != '"' || stripped.charAt(idx + 1) != '"') {
|
||||
hasPlus = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
//TODO remove me
|
||||
String cause = ""
|
||||
// Get the level of this log message.
|
||||
// We don't really care about checking for method calls for WARN and more severe, the presumption
|
||||
// is that they _should_ always be reported.
|
||||
|
||||
def level = ""
|
||||
def lev = (line =~ "log\\.(.*?)\\(")
|
||||
if (lev.find()) {
|
||||
level = lev.group(1).toLowerCase().trim()
|
||||
}
|
||||
if (logLevels.contains("log." + level) == false) {
|
||||
reportViolation(String.format("Found an unexpected log level: %s, file: %s:%d"
|
||||
, level, file.getAbsolutePath(), lineNumber))
|
||||
}
|
||||
boolean persnicketyLevel = !(level.equals("fatal") || level.equals("error") || level.equals("warn"))
|
||||
|
||||
// Check that previous line isn't an if statement for always-reported log levels.
|
||||
// There's a convention to declare a member variable for whether a level is enabled and check that rather than
|
||||
// isDebugEnabled so we need to check both.
|
||||
String prevLine = previous.replaceAll("\\s+", "").toLowerCase()
|
||||
boolean prevLineNotIf = ((prevLine.contains("if(log.is" + level + "enabled") == false
|
||||
&& prevLine.contains("if(" + level + ")") == false))
|
||||
|
||||
if (hasPlus) {
|
||||
cause = "hasPlus: " + hasPlus
|
||||
violation = true
|
||||
}
|
||||
if (violation == false) {
|
||||
def m = stripped =~ "\\(.*?\\)"
|
||||
def hasParens = m.find()
|
||||
|
||||
if (hasParens && prevLineNotIf && persnicketyLevel) {
|
||||
cause = "hasParens " + hasParens + " prevLineNotIf " + prevLineNotIf + " pernicketyLevel " + persnicketyLevel
|
||||
violation = true
|
||||
}
|
||||
}
|
||||
|
||||
// Always report toString(). Note, this over-reports some constructs
|
||||
// but just add //nowarn if it's really OK.
|
||||
if (violation == false) {
|
||||
if (line.contains("toString(") == true && prevLineNotIf) {
|
||||
cause = "Line contains toString"
|
||||
violation = true
|
||||
}
|
||||
}
|
||||
if (stripped.contains("getMessage()") || stripped.contains("getCause()")) {
|
||||
cause = "getMessage or getCause in log line";
|
||||
violation = true;
|
||||
}
|
||||
if (violation) {
|
||||
reportViolation(String.format("cause: '%s' Suspicious logging call, Parameterize and possibly surround with 'if (log.is*Enabled) {..}'. Help at: 'gradlew helpValidateLogCalls' %s %s:%d"
|
||||
, cause , System.lineSeparator, file.getAbsolutePath(), lineNumber))
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// Require all our logger definitions lower case "log", except if they have //nowarn
|
||||
def checkLogName(File file, String line) {
|
||||
// It's many times faster to do check this way than use a regex
|
||||
if (line.contains("static ") && line.contains("getLogger") && line.contains(" log ") == false) {
|
||||
if (line.replaceAll("\\s", "").toLowerCase().contains("//nowarn")) {
|
||||
return
|
||||
}
|
||||
reportViolation("Change the logger name to lower-case 'log' in " + file.name + " " + line + " project" + project)
|
||||
}
|
||||
}
|
||||
|
||||
def checkFile(File file) {
|
||||
int state = 0
|
||||
int lineNumber = 0
|
||||
StringBuilder sb = new StringBuilder();
|
||||
|
||||
// We have to assemble line-by-line to get the full log statement. We require that all loggers (except requestLog
|
||||
// and slowLog) be exactly "log". That will be checked as well.
|
||||
String prevLine = ""
|
||||
file.eachLine { String line ->
|
||||
lineNumber++
|
||||
checkLogName(file, line)
|
||||
switch (state) {
|
||||
case 0: // Not collecting a logging line.
|
||||
logLevels.each {
|
||||
if (line.contains(it)) {
|
||||
if (line.contains(");")) {
|
||||
state = 2
|
||||
} else {
|
||||
state = 1
|
||||
}
|
||||
sb.setLength(0)
|
||||
sb.append(line)
|
||||
}
|
||||
}
|
||||
break
|
||||
|
||||
case 1: // collecting a log line
|
||||
if (line.replaceFirst("//.*", " ")
|
||||
.replaceFirst("/\\*.*?\\*/", " ") // replace embedded comments "/*....*/"
|
||||
.replaceAll(/".*?"/, '""') // remove anything between quotes. This is a bit fragile if there are embedded double quotes.
|
||||
.trim().endsWith(");")) {
|
||||
state = 2
|
||||
}
|
||||
sb.append(line)
|
||||
break
|
||||
|
||||
default:
|
||||
reportViolation("Bad state, should be 0-1 in the switch statement") // make people aware the code sucks
|
||||
break
|
||||
}
|
||||
|
||||
// It's just easier to do this here rather than read another line in the switch above.
|
||||
if (state == 0) {
|
||||
// Not collecting a log line
|
||||
prevLine = line.toLowerCase();
|
||||
} else if (state == 1) {
|
||||
// collecting a logging line.
|
||||
} else if (state == 2) {
|
||||
// We've collected the complete log line.
|
||||
checkLine(file, sb.toString(), lineNumber, prevLine)
|
||||
state = 0
|
||||
} else {
|
||||
assert false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@InputFiles
|
||||
FileCollection sourceFiles
|
||||
|
||||
@TaskAction
|
||||
def checkLogLines() {
|
||||
sourceFiles.each { checkFile(it) }
|
||||
logger.info("Checked: ${sourceFiles.files.size()}")
|
||||
|
||||
if (errsFound > 0) {
|
||||
throw new BuildException(String.format(Locale.ENGLISH, 'Found %d violations in source files (%s).',
|
||||
errsFound, violations.join(', ')));
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue