<!--
  ~ Copyright 2010 the original author or authors.
  ~
  ~ Licensed 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.
  -->
<chapter id='gradle_wrapper'>
    <title>The Gradle Wrapper</title>
    <para>
        The Gradle Wrapper (henceforth referred to as the “wrapper) is the preferred way of starting a Gradle build. The wrapper
        is a batch script on Windows, and a shell script for other operating systems. When you start a Gradle build via the wrapper,
        Gradle will be automatically downloaded and used to run the build. 
    </para>
    <para>
        The wrapper is something you <emphasis>should</emphasis> check into version control. By distributing the wrapper with your project,
        anyone can work with it without needing to install Gradle beforehand. Even better, users of the build are guaranteed to use the 
        version of Gradle that the build was designed to work with. Of course, this is also great for 
        <ulink url="http://en.wikipedia.org/wiki/Continuous_integration">continuous integration</ulink> servers (i.e. servers that regularly
        build your project) as it requires no configuration on the server.
    </para>
    <para>
        You install the wrapper into your project by adding and configuring a <apilink class="org.gradle.api.tasks.wrapper.Wrapper"/> 
        task in your build script, and then executing it.
    </para>
    <sample id="wrapperSimple" dir="userguide/wrapper/simple" title="Wrapper task">
        <sourcefile file="build.gradle"/>
    </sample>
    <para>
        After such an execution you find the following new or updated files in your project directory 
        (in case the default configuration of the wrapper task is used).
    </para>
    <sample id="wrapperSimple" dir="userguide/wrapper/simple" title="Wrapper generated files">
        <layout after="wrapper">
            gradlew
            gradlew.bat
            gradle/wrapper/gradle-wrapper.jar
            gradle/wrapper/gradle-wrapper.properties
        </layout>
    </sample>
    <para>
        All of these files <emphasis>should</emphasis> be submitted to your version control system. This only needs to be done once. After
        these files have been added to the project, the project should then be built with the added <command>gradlew</command> command.
        The <command>gradlew</command> command can be used <emphasis>exactly</emphasis> the same way as the <command>gradle</command> command.
    </para>
    <para>If you want to switch to a new version of Gradle you don't need to rerun the wrapper task. It is good enough
        to change the respective entry in the <literal>gradle-wrapper.properties</literal> file. But if there is for
        example an improvement in the gradle-wrapper functionality you need to regenerate the wrapper files.
    </para>
    <section id='sec:configuration'>
        <title>Configuration</title>
        <para>If you run Gradle with <command>gradlew</command>, Gradle checks if a Gradle distribution for the wrapper
            is available. If not it tries to download it, otherwise it delegates to the <command>gradle</command>
            command of this distribution with all the arguments passed originally to the <command>gradlew</command>
            command.
        </para>
        <para>You can specify where the wrapper files should be stored (within your project directory):</para>
        <sample id="wrapperCustomized" dir="userguide/wrapper/customized" title="Configuration of wrapper task">
            <sourcefile file="build.gradle"/>
            <layout after="wrapper">
                gradlew
                gradlew.bat
                wrapper/wrapper.jar
                wrapper/wrapper.properties
            </layout>
        </sample>
        <para>
            You can specify the download URL of the wrapper distribution. You can also specify where the wrapper distribution
            should be stored and unpacked (either within the project or within the Gradle user home dir). If the wrapper
            is run and there is local archive of the wrapper distribution Gradle tries to download it and stores it at
            the specified place. If there is no unpacked wrapper distribution Gradle unpacks the local archive of the
            wrapper distribution at the specified place. All the configuration options have defaults except the version of the wrapper distribution.</para>
        <para>For the details on how to configure the wrapper, see <apilink class="org.gradle.api.tasks.wrapper.Wrapper"/>
        </para>
        <para>If you don't
            want any download to happen when your project is build via <command>gradlew</command>, simply add the Gradle
            distribution zip to your version control at the location specified by your wrapper configuration.
            Relative url is supported - you can specify a distribution file relative to the location of <literal>gradle-wrapper.properties</literal> file.
        </para>
        <para>If you build via the wrapper, any existing Gradle distribution installed on the machine is ignored.
        </para>
    </section>
    <section id='sec:unix_file_permissions'>
        <title>Unix file permissions</title>
        <para>The Wrapper task adds appropriate file permissions to allow the execution for the gradlew *NIX command.
            Subversion preserves this file permission. We are not sure how other version control systems deal with this.
            What should always work is to execute <literal>sh gradlew</literal>.
        </para>
    </section>
    <section id='sec:environment_variable'>
        <title>Environment variable</title>
        <para>Some rather exotic use cases might occur when working with the Gradle Wrapper. For example the continuous
            integration server goes down during unzipping the Gradle distribution. As the distribution directory exists
            <command>gradlew</command>
            delegates to it but the distribution is corrupt. Or the zip-distribution was not properly downloaded. When
            you have no admin right on the continuous integration server to remove the corrupt files, Gradle offers a
            solution via environment variables.
        </para>
        <table>
            <title>Gradle wrapper environment variables</title>
            <thead>
                <tr>
                    <td>Variable Name</td>
                    <td>Meaning</td>
                </tr>
            </thead>
            <tr>
                <td>GRADLE_WRAPPER_ALWAYS_UNPACK</td>
                <td>If set to <literal>true</literal>, the distribution directory gets always deleted when
                    <command>gradlew</command>
                    is run and the distribution zip is freshly unpacked. If the zip is not there, Gradle tries to
                    download it.
                </td>
            </tr>
            <tr>
                <td>GRADLE_WRAPPER_ALWAYS_DOWNLOAD</td>
                <td>If set to <literal>true</literal>, the distribution directory and the distribution zip gets always
                    deleted when <command>gradlew</command>
                    is run and the distribution zip is freshly downloaded.
                </td>
            </tr>

        </table>
    </section>
</chapter>
