// Path: src/main/java/org/killbill/billing/plugin/simpletax/internal/TaxCode.java
// public class TaxCode {
// 
//     private String name;
//     private String taxItemDescription;
//     private BigDecimal rate;
//     private LocalDate startingOn;
//     private LocalDate stoppingOn;
//     private Country country;
// 
//     /**
//      * constructs a new tax code definition.
//      *
//      * @param name
//      *            The unique name for the tax code.
//      * @param taxItemDescription
//      *            The description for tax items that will be generated by the
//      *            tax code.
//      * @param rate
//      *            The tax rate to apply when computing tax amounts.
//      * @param startingOn
//      *            The first day on which the tax code will <em>start</em> being
//      *            applicable, or {@code null} if the tax code has no sunrise
//      *            date.
//      * @param stoppingOn
//      *            The first day on which this tax code will <em>cease</em> to be
//      *            applicable, or {@code null} if the tax code has no sunset
//      *            date.
//      * @param country
//      *            The country on which this tax code applies.
//      */
//     public TaxCode(String name, String taxItemDescription, BigDecimal rate, LocalDate startingOn, LocalDate stoppingOn,
//             Country country) {
//         super();
//         this.name = name;
//         this.taxItemDescription = taxItemDescription;
//         this.rate = rate;
//         this.startingOn = startingOn;
//         this.stoppingOn = stoppingOn;
//         this.country = country;
//     }
// 
//     @Override
//     public boolean equals(Object obj) {
//         if (obj == null) {
//             return false;
//         }
//         if (obj == this) {
//             return true;
//         }
//         if (obj.getClass() != getClass()) {
//             return false;
//         }
//         TaxCode rhs = (TaxCode) obj;
//         if (!new EqualsBuilder()//
//                 .append(name, rhs.name)//
//                 .append(taxItemDescription, rhs.taxItemDescription)//
//                 .append(startingOn, rhs.startingOn)//
//                 .append(stoppingOn, rhs.stoppingOn)//
//                 .append(country, rhs.country)//
//                 .isEquals()) {
//             return false;
//         }
//         // Custom processing BigDecimal equality ignoring scale
//         if (rate == null) {
//             return rhs.rate == null;
//         }
//         return rate.compareTo(rhs.rate) == 0;
//     }
// 
//     @Override
//     public int hashCode() {
//         return new HashCodeBuilder()//
//                 .append(name)//
//                 .append(taxItemDescription)//
//                 // Custom processing BigDecimal hash ignoring scale
//                 .append(rate == null ? 0 : rate.toString())//
//                 .append(startingOn)//
//                 .append(stoppingOn)//
//                 .append(country)//
//                 .toHashCode();
//     }
// 
//     @Override
//     public String toString() {
//         return new ToStringBuilder(this, SHORT_STYLE)//
//                 .append("name", name)//
//                 .append("taxItemDescription", taxItemDescription)//
//                 .append("rate", rate)//
//                 .append("startingOn", startingOn)//
//                 .append("stoppingOn", stoppingOn)//
//                 .append("country", country)//
//                 .toString();
//     }
// 
//     /**
//      * @return The unique name of this tax code.
//      */
//     public String getName() {
//         return name;
//     }
// 
//     /**
//      * @return The description for tax items that are generated by this tax
//      *         code.
//      */
//     public String getTaxItemDescription() {
//         return taxItemDescription;
//     }
// 
//     /**
//      * @return The tax rate to apply when computing tax amounts.
//      */
//     public BigDecimal getRate() {
//         return rate;
//     }
// 
//     /**
//      * @return The first day on which this tax code <em>starts</em> being
//      *         applicable.
//      */
//     public LocalDate getStartingOn() {
//         return startingOn;
//     }
// 
//     /**
//      * @return The first day on which this tax code <em>ceases</em> to be
//      *         applicable.
//      */
//     public LocalDate getStoppingOn() {
//         return stoppingOn;
//     }
// 
//     /**
//      * @return The country on which this tax code applies.
//      */
//     public Country getCountry() {
//         return country;
//     }
// }


import javax.annotation.Nullable;
import org.killbill.billing.invoice.api.InvoiceItem;
import org.killbill.billing.plugin.simpletax.internal.TaxCode;
/*
 * Copyright 2015 Benjamin Gandon
 *
 * 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 org.killbill.billing.plugin.simpletax.resolving;



/**
 * Tax resolvers are meant to apply regulation specific rules when determining
 * which tax code actually applies, in a set of potential candidates.
 * <p>
 * Constructors of implementing classes must accept one single argument of type
 * {@link org.killbill.billing.plugin.simpletax.TaxComputationContext}.
 *
 * @author Benjamin Gandon
 */
public interface TaxResolver {

    /**
     * Retain only one applicable tax code, so that taxation of invoice item can
     * be done, based on the returned tax code.
     *
     * @param taxCodes
     *            The candidate tax codes for this invoice item.
     * @param item
     *            The invoice item to tax.
     * @return The tax code to apply to this item, or {@code null} if none
     *         applies.
     */
    @Nullable
// Path: src/main/java/org/killbill/billing/plugin/simpletax/internal/TaxCode.java
// public class TaxCode {
// 
//     private String name;
//     private String taxItemDescription;
//     private BigDecimal rate;
//     private LocalDate startingOn;
//     private LocalDate stoppingOn;
//     private Country country;
// 
//     /**
//      * constructs a new tax code definition.
//      *
//      * @param name
//      *            The unique name for the tax code.
//      * @param taxItemDescription
//      *            The description for tax items that will be generated by the
//      *            tax code.
//      * @param rate
//      *            The tax rate to apply when computing tax amounts.
//      * @param startingOn
//      *            The first day on which the tax code will <em>start</em> being
//      *            applicable, or {@code null} if the tax code has no sunrise
//      *            date.
//      * @param stoppingOn
//      *            The first day on which this tax code will <em>cease</em> to be
//      *            applicable, or {@code null} if the tax code has no sunset
//      *            date.
//      * @param country
//      *            The country on which this tax code applies.
//      */
//     public TaxCode(String name, String taxItemDescription, BigDecimal rate, LocalDate startingOn, LocalDate stoppingOn,
//             Country country) {
//         super();
//         this.name = name;
//         this.taxItemDescription = taxItemDescription;
//         this.rate = rate;
//         this.startingOn = startingOn;
//         this.stoppingOn = stoppingOn;
//         this.country = country;
//     }
// 
//     @Override
//     public boolean equals(Object obj) {
//         if (obj == null) {
//             return false;
//         }
//         if (obj == this) {
//             return true;
//         }
//         if (obj.getClass() != getClass()) {
//             return false;
//         }
//         TaxCode rhs = (TaxCode) obj;
//         if (!new EqualsBuilder()//
//                 .append(name, rhs.name)//
//                 .append(taxItemDescription, rhs.taxItemDescription)//
//                 .append(startingOn, rhs.startingOn)//
//                 .append(stoppingOn, rhs.stoppingOn)//
//                 .append(country, rhs.country)//
//                 .isEquals()) {
//             return false;
//         }
//         // Custom processing BigDecimal equality ignoring scale
//         if (rate == null) {
//             return rhs.rate == null;
//         }
//         return rate.compareTo(rhs.rate) == 0;
//     }
// 
//     @Override
//     public int hashCode() {
//         return new HashCodeBuilder()//
//                 .append(name)//
//                 .append(taxItemDescription)//
//                 // Custom processing BigDecimal hash ignoring scale
//                 .append(rate == null ? 0 : rate.toString())//
//                 .append(startingOn)//
//                 .append(stoppingOn)//
//                 .append(country)//
//                 .toHashCode();
//     }
// 
//     @Override
//     public String toString() {
//         return new ToStringBuilder(this, SHORT_STYLE)//
//                 .append("name", name)//
//                 .append("taxItemDescription", taxItemDescription)//
//                 .append("rate", rate)//
//                 .append("startingOn", startingOn)//
//                 .append("stoppingOn", stoppingOn)//
//                 .append("country", country)//
//                 .toString();
//     }
// 
//     /**
//      * @return The unique name of this tax code.
//      */
//     public String getName() {
//         return name;
//     }
// 
//     /**
//      * @return The description for tax items that are generated by this tax
//      *         code.
//      */
//     public String getTaxItemDescription() {
//         return taxItemDescription;
//     }
// 
//     /**
//      * @return The tax rate to apply when computing tax amounts.
//      */
//     public BigDecimal getRate() {
//         return rate;
//     }
// 
//     /**
//      * @return The first day on which this tax code <em>starts</em> being
//      *         applicable.
//      */
//     public LocalDate getStartingOn() {
//         return startingOn;
//     }
// 
//     /**
//      * @return The first day on which this tax code <em>ceases</em> to be
//      *         applicable.
//      */
//     public LocalDate getStoppingOn() {
//         return stoppingOn;
//     }
// 
//     /**
//      * @return The country on which this tax code applies.
//      */
//     public Country getCountry() {
//         return country;
//     }
// }


// Path: src/main/java/org/killbill/billing/plugin/simpletax/resolving/TaxResolver.java
import javax.annotation.Nullable;
import org.killbill.billing.invoice.api.InvoiceItem;
import org.killbill.billing.plugin.simpletax.internal.TaxCode;

/*
 * Copyright 2015 Benjamin Gandon
 *
 * 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 org.killbill.billing.plugin.simpletax.resolving;



/**
 * Tax resolvers are meant to apply regulation specific rules when determining
 * which tax code actually applies, in a set of potential candidates.
 * <p>
 * Constructors of implementing classes must accept one single argument of type
 * {@link org.killbill.billing.plugin.simpletax.TaxComputationContext}.
 *
 * @author Benjamin Gandon
 */
public interface TaxResolver {

    /**
     * Retain only one applicable tax code, so that taxation of invoice item can
     * be done, based on the returned tax code.
     *
     * @param taxCodes
     *            The candidate tax codes for this invoice item.
     * @param item
     *            The invoice item to tax.
     * @return The tax code to apply to this item, or {@code null} if none
     *         applies.
     */
    @Nullable
    public abstract TaxCode applicableCodeForItem(Iterable<TaxCode> taxCodes, InvoiceItem item);