| /* |
| * 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. |
| */ |
| |
| buildscript { |
| repositories { |
| mavenCentral() |
| jcenter() |
| } |
| |
| dependencies { |
| classpath "org.asciidoctor:asciidoctorj:1.6.2" |
| } |
| } |
| |
| plugins { |
| id 'java' |
| id 'com.github.jruby-gradle.base' version '2.0.0' |
| } |
| |
| // This project does not contribute anything to main dependencies. |
| versionsLock { |
| testProject() |
| } |
| |
| description = 'Solr reference guide' |
| |
| // Use an internal proxy to ruby gems. |
| repositories { |
| ruby.gems() |
| } |
| |
| configurations { |
| depVer |
| refGuide |
| } |
| |
| dependencies { |
| // Dependencies to compile internal tools. |
| implementation('org.asciidoctor:asciidoctorj') |
| implementation('com.vaadin.external.google:android-json') |
| implementation('org.jsoup:jsoup') |
| implementation('org.slf4j:jcl-over-slf4j') |
| implementation('org.slf4j:slf4j-simple') |
| implementation('org.apache.logging.log4j:log4j-core') |
| implementation('com.google.guava:guava') |
| implementation('commons-codec:commons-codec') |
| |
| // Dependencies referenced in the guide. |
| depVer('commons-codec:commons-codec') |
| depVer('io.dropwizard.metrics:metrics-core') |
| depVer('org.apache.logging.log4j:log4j-core') |
| depVer('org.apache.opennlp:opennlp-tools') |
| depVer('org.apache.tika:tika-core') |
| depVer('org.apache.zookeeper:zookeeper') |
| |
| // jekyll dependencies |
| gems 'rubygems:jekyll:3.5.2' |
| gems 'rubygems:jekyll-asciidoc:3.0.0' |
| |
| // don't know why we have to explicitly add these deps but it doesn't resolve them |
| // automatically. |
| gems 'rubygems:tilt:2.0.10' |
| gems 'rubygems:slim:4.0.1' |
| gems 'rubygems:concurrent-ruby:1.0.5' |
| } |
| |
| sourceSets { |
| refGuide { |
| java { |
| srcDirs = [] |
| } |
| resources { |
| srcDirs = ['src'] |
| } |
| } |
| |
| main { |
| java { |
| srcDirs = ['tools'] |
| } |
| } |
| |
| test { |
| java { |
| srcDirs = [] |
| } |
| } |
| } |
| |
| ext { |
| mainPage = "index" |
| |
| // the "MAJOR.MINOR" version of solr this guide is about (guides aren't specific to BUGFIX releases) |
| // So on 'branch_9_9' where 'version' may be 9.9.0, 9.9.1, 9.9.9, etc..; solrDocsVersion = 9.9 |
| solrDocsVersion = "${version}".replaceAll(/^(\d+\.\d+)(|\..*)$/, "\$1") |
| |
| // the "MAJOR_MINOR" version as a path for publishing the guide |
| // So on 'branch_9_9' where solrDocsVersion = 9.9; solrGuideVersionPath => 9_9 |
| solrGuideVersionPath = "${solrDocsVersion}".replaceAll(/^(\d+)\.(\d+)$/, "\$1_\$2") |
| |
| // these will be used to dynamically build up (nearly) identical tasks with consistent names |
| // for building & link checking the ref guide. One using absolute URLs to javadocs, the |
| // other using local paths that can be validated by the link checker. |
| htmlSiteDetails = |
| [name: 'Site', |
| path: 'html-site', |
| desc: 'HTML Site for publishing to the Solr website', |
| props: [ |
| htmlSolrJavadocs: "https://lucene.apache.org/solr/${solrGuideVersionPath}_0/", |
| htmlLuceneJavadocs: "https://lucene.apache.org/core/${solrGuideVersionPath}_0/" |
| ] |
| ] |
| linkCheckSiteDetails = |
| [name: 'LocalJavadocLinksSite', |
| path: 'local-jdoc-links-site', |
| desc: 'Local Site for checking javadoc links', |
| |
| // NOTE: extra '../' because we'll in a sub-dir of buildDir that will be built later... |
| props: [ |
| htmlSolrJavadocs : 'link:../' + buildDir.toPath().relativize(project(':solr:documentation').docroot.toPath()).toString().replace(File.separator, '/'), |
| htmlLuceneJavadocs : skipLucene ? 'link:../' : 'link:../' + buildDir.toPath().relativize(project(':lucene:documentation').docroot.toPath()).toString().replace(File.separator, '/') |
| ] |
| ] |
| } |
| |
| // dynamically define the 2 variations of each target that we need... |
| [ htmlSiteDetails, linkCheckSiteDetails ].each{ details -> |
| final def contentDir = file("${buildDir}/${details.path}-content") |
| final def htmlDir = file("${buildDir}/${details.path}") |
| final def extraProps = details.props.clone() |
| extraProps.htmlOutDir = "../${details.path}" |
| |
| task "prepare${details.name}Sources"(type: PrepareSources) { |
| outDir contentDir |
| props extraProps |
| } |
| |
| task "build${details.name}"(type: com.github.jrubygradle.JRubyExec) { |
| dependsOn "prepare${details.name}Sources" |
| group "Documentation" |
| description "Builds the ${details.desc}" |
| |
| inputs.dir contentDir |
| outputs.dir htmlDir |
| |
| script 'jekyll' |
| scriptArgs 'build' //, '--verbose' |
| workingDir contentDir |
| } |
| |
| task "check${details.name}"(type: JavaExec) { |
| dependsOn "build${details.name}" |
| |
| classpath = sourceSets.main.runtimeClasspath |
| main = 'CheckLinksAndAnchors' |
| workingDir = contentDir |
| |
| // NOTE: even for the 'real' site, we check all relative links |
| // (there will just be less of them, and this way any stray hardcoded |
| // '../../' paths can be caught more easily) |
| args([ htmlDir, "-check-all-relative-links" ]) |
| } |
| } |
| |
| // Hook in our dependency on all top level documentation in order to check local javadoc links |
| checkLocalJavadocLinksSite.dependsOn ':documentation' |
| |
| // Hook up custom tasks with standard tasks. |
| check.dependsOn checkLocalJavadocLinksSite, checkSite |
| |
| // Hook site building to assemble. |
| assemble.dependsOn buildSite |
| |
| abstract class PrepareSources extends DefaultTask { |
| |
| /** Original Source files we'll be syncing <b>FROM</b> */ |
| @InputDirectory |
| public File getSrcDir() { |
| return getProject().file("src") |
| } |
| |
| /** |
| * Where we sync the source files <b>TO</b> |
| */ |
| public void setOutDir(File outDir) { |
| this.outDir = outDir; |
| getOutputs().dir(outDir); |
| } |
| public File outDir; |
| |
| /** |
| * Task specific props |
| */ |
| @Input |
| public Map<String,String> getProps() { |
| return props; |
| } |
| public void setProps(Map<String,String> props) { |
| this.props = props; |
| } |
| private Map<String,String> props; |
| |
| /** |
| * Basic properties that should be the same for all tasks of this type |
| */ |
| @Input |
| public Map<String,String> getStandardProps() { |
| final Project p = getProject(); |
| return [ |
| javadocLink : "https://docs.oracle.com/en/java/javase/11/docs/api/", |
| solrGuideDraftStatus : p.propertyOrDefault('solrGuideDraft', "true").toBoolean() ? "DRAFT" : "", |
| solrRootPath : p.project(':solr').projectDir.toString() + File.separator, |
| solrDocsVersion : p.property('solrDocsVersion'), |
| solrGuideVersionPath : p.property('solrGuideVersionPath'), |
| buildDate : p.property('buildDate'), |
| buildYear : p.property('buildYear'), |
| ]; |
| } |
| |
| public PrepareSources() { |
| // setup 'dependsOn classes, configurations.depVer' here |
| // so that it's not neccessary for every task impl to declare redundently |
| final Project p = getProject(); |
| dependsOn(p.getConfigurations().getByName('depVer')) |
| dependsOn(p.getTasksByName('classes', false)) |
| |
| } |
| |
| @TaskAction |
| public void doCopy() { |
| final Project p = getProject(); |
| final Configuration depVer = p.getConfigurations().getByName('depVer'); |
| |
| // start with any task (instance) specific props. |
| final def props = getProps().clone(); |
| // then add/override with anystandard props that should alwasy be used |
| getStandardProps().each { k, v -> props[k] = v }; |
| |
| // These properties have to be resolved after the configuration phase is complete |
| // (palantir's constraint) so we can't use them as input for caches. But as this task |
| // depends on the configuration, it's used correctly |
| [ |
| ["ivyCommonsCodec", "commons-codec", "commons-codec"], |
| ["ivyDropwizardMetrics", "io.dropwizard.metrics", "metrics-core"], |
| ["ivyLog4j", "org.apache.logging.log4j", "log4j-core"], |
| ["ivyOpennlpTools", "org.apache.opennlp", "opennlp-tools"], |
| ["ivyTika", "org.apache.tika", "tika-core"], |
| ["ivyZookeeper", "org.apache.zookeeper", "zookeeper"], |
| ].each { prop, depGroup, depId -> |
| props[prop] = p.getVersion(depGroup, depId, depVer) |
| } |
| |
| final File intoDir = this.outDir; |
| |
| // Emit info about properties for clarity. |
| logger.lifecycle('Syncing source files to {} using props:\n{}', |
| intoDir, props.collect({ k, v -> " ${k} -> ${v}" }).join('\n')) |
| |
| // Escape all the properties, so they can be inserted into YAML templates. |
| final def escapedProps = props.collectEntries{k, v -> [k, v.replace("'","''")]} |
| |
| final WorkResult syncResult = p.sync({ copySpec -> |
| copySpec.setFilteringCharset('UTF-8'); |
| copySpec.from(getSrcDir(), { raw -> |
| raw.exclude('**/*.template') |
| }) |
| |
| copySpec.from(getSrcDir(), { templated -> |
| templated.include('**/*.template') |
| templated.rename('(.+)\\.template', '$1') |
| templated.expand(escapedProps) |
| }) |
| copySpec.into(intoDir); |
| }); |
| setDidWork(syncResult.getDidWork()); |
| if (syncResult.getDidWork()) { |
| // if sync did work, that means we need to rebuild the nav data files... |
| p.javaexec({ execSpec -> |
| execSpec.setClasspath( getProject().getConvention() |
| .getPlugin(JavaPluginConvention.class) |
| .getSourceSets().getByName("main").getRuntimeClasspath() ) |
| execSpec.setWorkingDir( intoDir ) |
| execSpec.setMain( 'BuildNavDataFiles' ) |
| execSpec.args([ intoDir, p.property('mainPage') ]) |
| }) |
| } |
| } |
| } |