/*
 * Copyright 2020 Google LLC.
 *
 * 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.
 */

package com.google.cloud.tools.jib.gradle.extension.ownership;

import java.util.List;
import javax.inject.Inject;
import org.gradle.api.Action;
import org.gradle.api.Project;
import org.gradle.api.provider.ListProperty;
import org.gradle.api.tasks.Input;
import org.gradle.api.tasks.Optional;

/**
 * Extension-specific Gradle configuration.
 *
 * <p>Example usage in {@code build.gradle}:
 *
 * <pre>{@code
 * configuration {
 *   rules {
 *     // sets UID 300 for all files under /app/classes/
 *     rule {
 *       glob = '/app/classes/**'
 *       ownership = '300'
 *     }
 *     // sets UID 300 and GID 500 for all files under /static/
 *     rule {
 *       glob = '/static/**'
 *       ownership = '300:500'
 *     }
 *   }
 * }
 * }</pre>
 */
public class Configuration {

  public static class Rule {
    private String glob = "";
    private String ownership = "";

    @Input
    public String getGlob() {
      return glob;
    }

    @Input
    @Optional
    public String getOwnership() {
      return ownership;
    }
  }

  public class RuleSpec {

    /**
     * Adds a new rule configuration to the rules list.
     *
     * @param action closure representing a rule configuration
     */
    public void rule(Action<? super Rule> action) {
      Rule filter = project.getObjects().newInstance(Rule.class);
      action.execute(filter);
      rules.add(filter);
    }
  }

  private final Project project;
  private final RuleSpec ruleSpec;
  private final ListProperty<Rule> rules;

  /**
   * Constructor used to inject a Gradle project.
   *
   * @param project the injected Gradle project
   */
  @Inject
  public Configuration(Project project) {
    this.project = project;
    ruleSpec = project.getObjects().newInstance(RuleSpec.class);
    rules = project.getObjects().listProperty(Rule.class).empty();
  }

  public List<Rule> getRules() {
    return rules.get();
  }

  public void filters(Action<? super RuleSpec> action) {
    action.execute(ruleSpec);
  }
}

@@ -1538,16 +1538,86 @@
 %0A    %7D%0A%0A
+    public void setGlob(String glob) %7B%0A      this.glob = glob;%0A    %7D%0A%0A
     @Inp
@@ -1693,24 +1693,114 @@
 rship;%0A    %7D
+%0A%0A    public void setOwnership(String ownership) %7B%0A      this.ownership = ownership;%0A    %7D
 %0A  %7D%0A%0A  publ
@@ -1798,24 +1798,31 @@
 %7D%0A%0A  public 
+static 
 class RuleSp
@@ -1823,16 +1823,17 @@
 Rule
+s
 Spec %7B%0A%0A
     
@@ -1828,16 +1828,325 @@
 Spec %7B%0A%0A
+    private final Project project;%0A    private final ListProperty%3CRule%3E rules;%0A%0A    @Inject%0A    public RulesSpec(Project project) %7B%0A      this.project = project;%0A      rules = project.getObjects().listProperty(Rule.class).empty();%0A    %7D%0A%0A    private ListProperty%3CRule%3E getRules() %7B%0A      return rules;%0A    %7D%0A%0A
     /**%0A
@@ -2467,41 +2467,8 @@
  %7D%0A%0A
-  private final Project project;%0A
   pr
@@ -2479,24 +2479,25 @@
 e final Rule
+s
 Spec ruleSpe
@@ -2497,55 +2497,14 @@
 rule
+s
 Spec;
-%0A  private final ListProperty%3CRule%3E rules;
 %0A%0A  
@@ -2672,44 +2672,16 @@
 ) %7B%0A
-    this.project = project;%0A
     rule
 Spec
@@ -2672,24 +2672,25 @@
 ) %7B%0A    rule
+s
 Spec = proje
@@ -2717,24 +2717,25 @@
 nstance(Rule
+s
 Spec.class);
@@ -2736,75 +2736,17 @@
 lass
-);%0A    rules = project.getObjects().listProperty(Rule.class).empty(
+, project
 );%0A 
@@ -2798,16 +2798,31 @@
 rn rules
+Spec.getRules()
 .get();%0A
@@ -2840,22 +2840,20 @@
 ic void 
-filter
+rule
 s(Action
@@ -2865,16 +2865,17 @@
 per Rule
+s
 Spec%3E ac
@@ -2905,16 +2905,17 @@
 ute(rule
+s
 Spec);%0A 

Fix Gradle configuration setup