killbill-memoizeit

Changes

Details

diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountEmailJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountEmailJson.java
index a0447c5..5d91029 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountEmailJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountEmailJson.java
@@ -19,15 +19,17 @@ package org.killbill.billing.jaxrs.json;
 import java.util.UUID;
 
 import org.joda.time.DateTime;
-
 import org.killbill.billing.account.api.AccountEmail;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class AccountEmailJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
+    @ApiModelProperty(required = true)
     private final String email;
 
     @JsonCreator
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountJson.java
index 7e6ceef..3ea7daf 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AccountJson.java
@@ -32,9 +32,12 @@ import org.killbill.billing.util.audit.AccountAuditLogs;
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
 import com.google.common.base.Objects;
+import com.google.common.base.Strings;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class AccountJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
     private final String externalKey;
     private final BigDecimal accountCBA;
@@ -44,6 +47,7 @@ public class AccountJson extends JsonBase {
     private final String email;
     private final Integer billCycleDayLocal;
     private final String currency;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String paymentMethodId;
     private final String timeZone;
     private final String address1;
@@ -137,7 +141,7 @@ public class AccountJson extends JsonBase {
         return new AccountData() {
             @Override
             public DateTimeZone getTimeZone() {
-                return (timeZone != null) ? DateTimeZone.forID(timeZone) : null;
+                return (Strings.emptyToNull(timeZone) != null) ? DateTimeZone.forID(timeZone) : null;
             }
 
             @Override
@@ -203,7 +207,7 @@ public class AccountJson extends JsonBase {
 
             @Override
             public Currency getCurrency() {
-                if (currency == null) {
+                if (Strings.emptyToNull(currency) == null) {
                     return null;
                 } else {
                     return Currency.valueOf(currency);
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AuditLogJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AuditLogJson.java
index 9db5376..951e271 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AuditLogJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/AuditLogJson.java
@@ -22,10 +22,12 @@ import org.killbill.billing.util.audit.AuditLog;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class AuditLogJson {
 
     private final String changeType;
+    @ApiModelProperty(dataType = "org.joda.time.DateTime")
     private final DateTime changeDate;
     private final String changedBy;
     private final String reasonCode;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BillingExceptionJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BillingExceptionJson.java
index a009eb5..181fa6d 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BillingExceptionJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BillingExceptionJson.java
@@ -54,12 +54,13 @@ public class BillingExceptionJson {
         this.stackTrace = stackTrace;
     }
 
-    public BillingExceptionJson(final Exception exception) {
+    public BillingExceptionJson(final Exception exception, final boolean withStackTrace) {
         this(exception.getClass().getName(),
              exception instanceof BillingExceptionBase ? ((BillingExceptionBase) exception).getCode() : null,
              exception.getLocalizedMessage(),
              exception.getCause() == null ? null : exception.getCause().getClass().getName(),
              exception.getCause() == null ? null : exception.getCause().getLocalizedMessage(),
+             !withStackTrace ? ImmutableList.<StackTraceElementJson>of() :
              Lists.<StackTraceElement, StackTraceElementJson>transform(ImmutableList.<StackTraceElement>copyOf(exception.getStackTrace()),
                                                                        new Function<StackTraceElement, StackTraceElementJson>() {
                                                                            @Override
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BundleJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BundleJson.java
index 249e149..9c3a1f0 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BundleJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/BundleJson.java
@@ -31,10 +31,13 @@ import com.fasterxml.jackson.annotation.JsonProperty;
 import com.google.common.base.Predicate;
 import com.google.common.collect.Collections2;
 import com.google.common.collect.ImmutableList;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class BundleJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID", required = true)
     protected final String accountId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     protected final String bundleId;
     protected final String externalKey;
     private final List<SubscriptionJson> subscriptions;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CreditJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CreditJson.java
index ab5112d..5819a22 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CreditJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CreditJson.java
@@ -21,23 +21,24 @@ import java.util.List;
 
 import javax.annotation.Nullable;
 
-import org.joda.time.DateTime;
-import org.joda.time.DateTimeZone;
 import org.joda.time.LocalDate;
-
 import org.killbill.billing.invoice.api.Invoice;
 import org.killbill.billing.invoice.api.InvoiceItem;
 import org.killbill.billing.util.audit.AuditLog;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class CreditJson extends JsonBase {
 
+    @ApiModelProperty(required = true)
     private final BigDecimal creditAmount;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String invoiceId;
     private final String invoiceNumber;
     private final LocalDate effectiveDate;
+    @ApiModelProperty(dataType = "java.util.UUID", required = true)
     private final String accountId;
 
     @JsonCreator
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CustomFieldJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CustomFieldJson.java
index c0abc8a..9013d28 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CustomFieldJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/CustomFieldJson.java
@@ -26,13 +26,18 @@ import org.killbill.billing.util.customfield.CustomField;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class CustomFieldJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String customFieldId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String objectId;
     private final ObjectType objectType;
+    @ApiModelProperty(required = true)
     private final String name;
+    @ApiModelProperty(required = true)
     private final String value;
 
     @JsonCreator
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/GatewayNotificationJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/GatewayNotificationJson.java
index 923258c..bfc1b85 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/GatewayNotificationJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/GatewayNotificationJson.java
@@ -28,9 +28,11 @@ import org.killbill.billing.payment.plugin.api.GatewayNotification;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class GatewayNotificationJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String kbPaymentId;
     private final Integer status;
     private final String entity;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/HostedPaymentPageFormDescriptorJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/HostedPaymentPageFormDescriptorJson.java
index 2753e70..623cdca 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/HostedPaymentPageFormDescriptorJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/HostedPaymentPageFormDescriptorJson.java
@@ -23,9 +23,11 @@ import org.killbill.billing.payment.plugin.api.HostedPaymentPageFormDescriptor;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class HostedPaymentPageFormDescriptorJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String kbAccountId;
     private final String formMethod;
     private final String formUrl;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceEmailJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceEmailJson.java
index 0a4f024..a0e5d9e 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceEmailJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceEmailJson.java
@@ -19,9 +19,11 @@ package org.killbill.billing.jaxrs.json;
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonGetter;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class InvoiceEmailJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
     private final boolean isNotifiedForInvoices;
 
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceItemJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceItemJson.java
index 0d87f23..a476a22 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceItemJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceItemJson.java
@@ -31,14 +31,21 @@ import org.killbill.billing.util.audit.AuditLog;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class InvoiceItemJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID", required = true)
     private final String invoiceItemId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String invoiceId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String linkedInvoiceItemId;
+    @ApiModelProperty(dataType = "java.util.UUID", required = true)
     private final String accountId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String bundleId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String subscriptionId;
     private final String planName;
     private final String phaseName;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceJson.java
index b45e4c4..639d2c9 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoiceJson.java
@@ -31,11 +31,13 @@ import org.killbill.billing.util.audit.AuditLog;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class InvoiceJson extends JsonBase {
 
     private final BigDecimal amount;
     private final String currency;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String invoiceId;
     private final LocalDate invoiceDate;
     private final LocalDate targetDate;
@@ -43,6 +45,7 @@ public class InvoiceJson extends JsonBase {
     private final BigDecimal balance;
     private final BigDecimal creditAdj;
     private final BigDecimal refundAdj;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
     private final List<InvoiceItemJson> items;
     private final String bundleKeys;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoicePaymentJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoicePaymentJson.java
index f7c366d..f37d2e4 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoicePaymentJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/InvoicePaymentJson.java
@@ -29,9 +29,11 @@ import org.killbill.billing.util.audit.AccountAuditLogs;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class InvoicePaymentJson extends PaymentJson {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String targetInvoiceId;
 
 
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/NotificationJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/NotificationJson.java
index e8fcd14..469e2c4 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/NotificationJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/NotificationJson.java
@@ -20,6 +20,7 @@ import org.killbill.billing.notification.plugin.api.ExtBusEvent;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 /*
  * Use to communicate back with client after they registered a callback
@@ -27,8 +28,10 @@ import com.fasterxml.jackson.annotation.JsonProperty;
 public class NotificationJson {
 
     private final String eventType;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
     private final String objectType;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String objectId;
 
     @JsonCreator
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentJson.java
index 4bf0f5d..3a85882 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentJson.java
@@ -31,10 +31,13 @@ import com.fasterxml.jackson.annotation.JsonProperty;
 import com.google.common.base.Function;
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.Iterables;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class PaymentJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String paymentId;
     private final String paymentNumber;
     private final String paymentExternalKey;
@@ -44,6 +47,7 @@ public class PaymentJson extends JsonBase {
     private final BigDecimal refundedAmount;
     private final BigDecimal creditedAmount;
     private final String currency;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String paymentMethodId;
     private final List<? extends PaymentTransactionJson> transactions;
 
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentMethodJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentMethodJson.java
index 0482484..2cc6720 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentMethodJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentMethodJson.java
@@ -36,11 +36,14 @@ import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
 import com.google.common.base.Function;
 import com.google.common.collect.Collections2;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class PaymentMethodJson extends JsonBase {
 
     private final String externalKey;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String paymentMethodId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
     private final Boolean isDefault;
     private final String pluginName;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentTransactionJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentTransactionJson.java
index 28489f2..82a40dd 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentTransactionJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/PaymentTransactionJson.java
@@ -36,7 +36,7 @@ public class PaymentTransactionJson extends JsonBase {
     @ApiModelProperty(dataType = "java.util.UUID")
     private final String transactionId;
     private final String transactionExternalKey;
-    @ApiModelProperty(dataType = "java.util.UUID")
+    @ApiModelProperty(value = "Associated payment id, required when notifying state transitions", dataType = "java.util.UUID")
     private final String paymentId;
     private final String paymentExternalKey;
     @ApiModelProperty(dataType = "org.killbill.billing.payment.api.TransactionType")
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/RolledUpUsageJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/RolledUpUsageJson.java
index 0cc9bc6..c8185b2 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/RolledUpUsageJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/RolledUpUsageJson.java
@@ -27,9 +27,11 @@ import com.fasterxml.jackson.annotation.JsonProperty;
 import com.google.common.base.Function;
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.Iterables;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class RolledUpUsageJson {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String subscriptionId;
     private final LocalDate startDate;
     private final LocalDate endDate;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SessionJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SessionJson.java
index fbd5eca..03f7395 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SessionJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SessionJson.java
@@ -22,11 +22,14 @@ import org.joda.time.DateTimeZone;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class SessionJson {
 
     private final String id;
+    @ApiModelProperty(dataType = "org.joda.time.DateTime")
     private final DateTime startDate;
+    @ApiModelProperty(dataType = "org.joda.time.DateTime")
     private final DateTime lastAccessDate;
     private final Long timeout;
     private final String host;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionJson.java
index ffecd4a..4296784 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionJson.java
@@ -33,17 +33,25 @@ import org.killbill.billing.util.audit.AccountAuditLogs;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class SubscriptionJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String accountId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String bundleId;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String subscriptionId;
     private final String externalKey;
     private final LocalDate startDate;
+    @ApiModelProperty(required = true)
     private final String productName;
+    @ApiModelProperty(dataType = "org.killbill.billing.catalog.api.ProductCategory", required = true)
     private final String productCategory;
+    @ApiModelProperty(dataType = "org.killbill.billing.catalog.api.BillingPeriod", required = true)
     private final String billingPeriod;
+    @ApiModelProperty(required = true)
     private final String priceList;
     private final LocalDate cancelledDate;
     private final LocalDate chargedThroughDate;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionUsageRecordJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionUsageRecordJson.java
index 06caa2d..9e961a6 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionUsageRecordJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/SubscriptionUsageRecordJson.java
@@ -30,10 +30,13 @@ import com.fasterxml.jackson.annotation.JsonProperty;
 import com.google.common.base.Function;
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.Iterables;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class SubscriptionUsageRecordJson {
 
+    @ApiModelProperty(dataType = "java.util.UUID", required = true)
     private final String subscriptionId;
+    @ApiModelProperty(required = true)
     private final List<UnitUsageRecordJson> unitUsageRecords;
 
     @JsonCreator
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagDefinitionJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagDefinitionJson.java
index fd1c5cb..fedac1c 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagDefinitionJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagDefinitionJson.java
@@ -29,12 +29,16 @@ import com.fasterxml.jackson.annotation.JsonProperty;
 import com.google.common.base.Function;
 import com.google.common.collect.Collections2;
 import com.google.common.collect.ImmutableList;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class TagDefinitionJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String id;
     private final Boolean isControlTag;
+    @ApiModelProperty(required = true)
     private final String name;
+    @ApiModelProperty(required = true)
     private final String description;
     private final List<String> applicableObjectTypes;
 
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagJson.java
index 6307410..0e8233d 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TagJson.java
@@ -27,11 +27,15 @@ import org.killbill.billing.util.tag.TagDefinition;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class TagJson extends JsonBase {
 
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String tagId;
+    @ApiModelProperty(dataType = "org.killbill.billing.ObjectType")
     private final ObjectType objectType;
+    @ApiModelProperty(dataType = "java.util.UUID")
     private final String tagDefinitionId;
     private final String tagDefinitionName;
 
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantJson.java
index 6670881..76fe844 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantJson.java
@@ -21,13 +21,17 @@ import org.killbill.billing.tenant.api.TenantData;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonProperty;
+import com.wordnik.swagger.annotations.ApiModelProperty;
 
 public class TenantJson extends JsonBase {
 
-    protected final String tenantId;
-    protected final String externalKey;
-    protected final String apiKey;
-    protected final String apiSecret;
+    @ApiModelProperty(dataType = "java.util.UUID")
+    private final String tenantId;
+    private final String externalKey;
+    @ApiModelProperty(required = true)
+    private final String apiKey;
+    @ApiModelProperty(required = true)
+    private final String apiSecret;
 
     @JsonCreator
     public TenantJson(@JsonProperty("tenantId") final String tenantId,
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantKeyJson.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantKeyJson.java
index 51d4bdf..f3d3b3d 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantKeyJson.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/json/TenantKeyJson.java
@@ -26,7 +26,6 @@ public class TenantKeyJson {
     private final String key;
     private final List<String> values;
 
-
     @JsonCreator
     public TenantKeyJson(@JsonProperty("key") final String key,
                          @JsonProperty("values") final List<String> values) {
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/ExceptionMapperBase.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/ExceptionMapperBase.java
index 7e32c1d..047d76e 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/ExceptionMapperBase.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/ExceptionMapperBase.java
@@ -48,6 +48,8 @@ public abstract class ExceptionMapperBase {
     private static final Logger log = LoggerFactory.getLogger(ExceptionMapperBase.class);
     private static final ObjectMapper mapper = new ObjectMapper();
 
+    private static final String QUERY_WITH_STACK_TRACE = "withStackTrace";
+
     protected Response fallback(final Exception exception, final UriInfo uriInfo) {
         if (exception.getCause() == null) {
             return buildBadRequestResponse(exception, uriInfo);
@@ -114,7 +116,7 @@ public abstract class ExceptionMapperBase {
         log.warn("Conflicting request", e);
 
         final Response.ResponseBuilder responseBuilder = Response.status(Status.CONFLICT);
-        serializeException(e, responseBuilder);
+        serializeException(e, uriInfo, responseBuilder);
         return responseBuilder.build();
     }
 
@@ -123,7 +125,7 @@ public abstract class ExceptionMapperBase {
         log.info("Not found", e);
 
         final Response.ResponseBuilder responseBuilder = Response.status(Status.NOT_FOUND);
-        serializeException(e, responseBuilder);
+        serializeException(e, uriInfo, responseBuilder);
         return responseBuilder.build();
     }
 
@@ -132,7 +134,7 @@ public abstract class ExceptionMapperBase {
         log.warn("Bad request", e);
 
         final Response.ResponseBuilder responseBuilder = Response.status(Status.BAD_REQUEST);
-        serializeException(e, responseBuilder);
+        serializeException(e, uriInfo, responseBuilder);
         return responseBuilder.build();
     }
 
@@ -142,7 +144,7 @@ public abstract class ExceptionMapperBase {
 
         // TODO Forbidden?
         final Response.ResponseBuilder responseBuilder = Response.status(Status.UNAUTHORIZED);
-        serializeException(e, responseBuilder);
+        serializeException(e, uriInfo, responseBuilder);
         return responseBuilder.build();
     }
 
@@ -151,23 +153,24 @@ public abstract class ExceptionMapperBase {
         log.warn("Internal error", e);
 
         final Response.ResponseBuilder responseBuilder = Response.status(Status.INTERNAL_SERVER_ERROR);
-        serializeException(e, responseBuilder);
+        serializeException(e, uriInfo, responseBuilder);
         return responseBuilder.build();
     }
 
     protected Response buildPluginTimeoutResponse(final Exception e, final UriInfo uriInfo) {
         final Response.ResponseBuilder responseBuilder = Response.status(Status.ACCEPTED);
-        serializeException(e, responseBuilder);
+        serializeException(e, uriInfo, responseBuilder);
         return responseBuilder.build();
     }
 
-    private void serializeException(final Exception e, final Response.ResponseBuilder responseBuilder) {
-        final BillingExceptionJson billingExceptionJson = new BillingExceptionJson(e);
+    private void serializeException(final Exception e, final UriInfo uriInfo, final Response.ResponseBuilder responseBuilder) {
+        final boolean withStackTrace = uriInfo.getQueryParameters() != null && "true".equals(uriInfo.getQueryParameters().getFirst(QUERY_WITH_STACK_TRACE));
+        final BillingExceptionJson billingExceptionJson = new BillingExceptionJson(e, withStackTrace);
 
         try {
             final String billingExceptionJsonAsString = mapper.writeValueAsString(billingExceptionJson);
             responseBuilder.entity(billingExceptionJsonAsString).type(MediaType.APPLICATION_JSON);
-        } catch (JsonProcessingException jsonException) {
+        } catch (final JsonProcessingException jsonException) {
             log.warn("Unable to serialize exception", jsonException);
             responseBuilder.entity(e.toString()).type(MediaType.TEXT_PLAIN_TYPE);
         }
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/JsonMappingExceptionMapper.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/JsonMappingExceptionMapper.java
new file mode 100644
index 0000000..d13b523
--- /dev/null
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/JsonMappingExceptionMapper.java
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2014 Groupon, Inc
+ * Copyright 2014 The Billing Project, LLC
+ *
+ * The Billing Project 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.
+ */
+
+package org.killbill.billing.jaxrs.mappers;
+
+import javax.inject.Singleton;
+import javax.ws.rs.core.Context;
+import javax.ws.rs.core.Response;
+import javax.ws.rs.core.UriInfo;
+import javax.ws.rs.ext.ExceptionMapper;
+import javax.ws.rs.ext.Provider;
+
+import com.fasterxml.jackson.databind.JsonMappingException;
+
+@Singleton
+@Provider
+public class JsonMappingExceptionMapper extends ExceptionMapperBase implements ExceptionMapper<JsonMappingException> {
+
+    private final UriInfo uriInfo;
+
+    public JsonMappingExceptionMapper(@Context final UriInfo uriInfo) {
+        this.uriInfo = uriInfo;
+    }
+
+    @Override
+    public Response toResponse(final JsonMappingException exception) {
+        // Likely bad arguments
+        return buildBadRequestResponse(exception, uriInfo);
+    }
+}
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/TenantApiExceptionMapper.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/TenantApiExceptionMapper.java
new file mode 100644
index 0000000..820ba2a
--- /dev/null
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/mappers/TenantApiExceptionMapper.java
@@ -0,0 +1,60 @@
+/*
+ * Copyright 2014 Groupon, Inc
+ * Copyright 2014 The Billing Project, LLC
+ *
+ * The Billing Project 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.
+ */
+
+package org.killbill.billing.jaxrs.mappers;
+
+import javax.inject.Singleton;
+import javax.ws.rs.core.Context;
+import javax.ws.rs.core.Response;
+import javax.ws.rs.core.UriInfo;
+import javax.ws.rs.ext.ExceptionMapper;
+import javax.ws.rs.ext.Provider;
+
+import org.killbill.billing.ErrorCode;
+import org.killbill.billing.tenant.api.TenantApiException;
+
+@Singleton
+@Provider
+public class TenantApiExceptionMapper extends ExceptionMapperBase implements ExceptionMapper<TenantApiException> {
+
+    private final UriInfo uriInfo;
+
+    public TenantApiExceptionMapper(@Context final UriInfo uriInfo) {
+        this.uriInfo = uriInfo;
+    }
+
+    @Override
+    public Response toResponse(final TenantApiException exception) {
+        if (exception.getCode() == ErrorCode.TENANT_ALREADY_EXISTS.getCode()) {
+            return buildConflictingRequestResponse(exception, uriInfo);
+        } else if (exception.getCode() == ErrorCode.TENANT_DOES_NOT_EXIST_FOR_ID.getCode()) {
+            return buildNotFoundResponse(exception, uriInfo);
+        } else if (exception.getCode() == ErrorCode.TENANT_DOES_NOT_EXIST_FOR_KEY.getCode()) {
+            return buildNotFoundResponse(exception, uriInfo);
+        } else if (exception.getCode() == ErrorCode.TENANT_DOES_NOT_EXIST_FOR_API_KEY.getCode()) {
+            return buildNotFoundResponse(exception, uriInfo);
+        } else if (exception.getCode() == ErrorCode.TENANT_CREATION_FAILED.getCode()) {
+            return buildInternalErrorResponse(exception, uriInfo);
+        } else if (exception.getCode() == ErrorCode.TENANT_UPDATE_FAILED.getCode()) {
+            return buildInternalErrorResponse(exception, uriInfo);
+        } else if (exception.getCode() == ErrorCode.TENANT_NO_SUCH_KEY.getCode()) {
+            return buildNotFoundResponse(exception, uriInfo);
+        } else {
+            return fallback(exception, uriInfo);
+        }
+    }
+}
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/AccountResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/AccountResource.java
index 66438a3..6ffc71a 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/AccountResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/AccountResource.java
@@ -297,6 +297,8 @@ public class AccountResource extends JaxRsResourceBase {
                                   @HeaderParam(HDR_COMMENT) final String comment,
                                   @javax.ws.rs.core.Context final HttpServletRequest request,
                                   @javax.ws.rs.core.Context final UriInfo uriInfo) throws AccountApiException {
+        verifyNonNullOrEmpty(json, "AccountJson body should be specified");
+
         final AccountData data = json.toAccountData();
         final Account account = accountUserApi.createAccount(data, context.createContext(createdBy, reason, comment, request));
         return uriBuilder.buildResponse(uriInfo, AccountResource.class, "getAccount", account.getId());
@@ -315,6 +317,8 @@ public class AccountResource extends JaxRsResourceBase {
                                   @HeaderParam(HDR_REASON) final String reason,
                                   @HeaderParam(HDR_COMMENT) final String comment,
                                   @javax.ws.rs.core.Context final HttpServletRequest request) throws AccountApiException {
+        verifyNonNullOrEmpty(json, "AccountJson body should be specified");
+
         final AccountData data = json.toAccountData();
         final UUID uuid = UUID.fromString(accountId);
         accountUserApi.updateAccount(uuid, data, context.createContext(createdBy, reason, comment, request));
@@ -408,6 +412,8 @@ public class AccountResource extends JaxRsResourceBase {
                                                     @HeaderParam(HDR_REASON) final String reason,
                                                     @HeaderParam(HDR_COMMENT) final String comment,
                                                     @javax.ws.rs.core.Context final HttpServletRequest request) throws AccountApiException {
+        verifyNonNullOrEmpty(json, "InvoiceEmailJson body should be specified");
+
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
         final UUID accountId = UUID.fromString(accountIdString);
@@ -581,6 +587,9 @@ public class AccountResource extends JaxRsResourceBase {
                                         @HeaderParam(HDR_COMMENT) final String comment,
                                         @javax.ws.rs.core.Context final UriInfo uriInfo,
                                         @javax.ws.rs.core.Context final HttpServletRequest request) throws AccountApiException, PaymentApiException {
+        verifyNonNullOrEmpty(json, "PaymentMethodJson body should be specified");
+        verifyNonNullOrEmpty(json.getPluginName(), "PaymentMethodJson pluginName should be specified");
+
         final Iterable<PluginProperty> pluginProperties = extractPluginProperties(pluginPropertiesString);
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
@@ -699,14 +708,18 @@ public class AccountResource extends JaxRsResourceBase {
     @ApiResponses(value = {@ApiResponse(code = 400, message = "Invalid account id supplied"),
                            @ApiResponse(code = 404, message = "Account not found")})
     public Response processPayment(final PaymentTransactionJson json,
-                                         @PathParam("accountId") final String accountIdStr,
-                                         @QueryParam("paymentMethodId") final String paymentMethodIdStr,
-                                         @QueryParam(QUERY_PLUGIN_PROPERTY) final List<String> pluginPropertiesString,
-                                         @HeaderParam(HDR_CREATED_BY) final String createdBy,
-                                         @HeaderParam(HDR_REASON) final String reason,
-                                         @HeaderParam(HDR_COMMENT) final String comment,
-                                         @javax.ws.rs.core.Context final UriInfo uriInfo,
-                                         @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+                                   @PathParam("accountId") final String accountIdStr,
+                                   @QueryParam("paymentMethodId") final String paymentMethodIdStr,
+                                   @QueryParam(QUERY_PLUGIN_PROPERTY) final List<String> pluginPropertiesString,
+                                   @HeaderParam(HDR_CREATED_BY) final String createdBy,
+                                   @HeaderParam(HDR_REASON) final String reason,
+                                   @HeaderParam(HDR_COMMENT) final String comment,
+                                   @javax.ws.rs.core.Context final UriInfo uriInfo,
+                                   @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "PaymentTransactionJson body should be specified");
+        verifyNonNullOrEmpty(json.getTransactionType(), "PaymentTransactionJson transactionType needs to be set",
+                             json.getAmount(), "PaymentTransactionJson amount needs to be set");
+
         final Iterable<PluginProperty> pluginProperties = extractPluginProperties(pluginPropertiesString);
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
         final UUID accountId = UUID.fromString(accountIdStr);
@@ -919,6 +932,9 @@ public class AccountResource extends JaxRsResourceBase {
                              @HeaderParam(HDR_COMMENT) final String comment,
                              @javax.ws.rs.core.Context final HttpServletRequest request,
                              @javax.ws.rs.core.Context final UriInfo uriInfo) throws AccountApiException {
+        verifyNonNullOrEmpty(json, "AccountEmailJson body should be specified");
+        verifyNonNullOrEmpty(json.getEmail(), "AccountEmailJson email needs to be set");
+
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
         final UUID accountId = UUID.fromString(id);
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/BundleResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/BundleResource.java
index cba108e..a0481e4 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/BundleResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/BundleResource.java
@@ -315,6 +315,8 @@ public class BundleResource extends JaxRsResourceBase {
                                    @HeaderParam(HDR_COMMENT) final String comment,
                                    @javax.ws.rs.core.Context final UriInfo uriInfo,
                                    @javax.ws.rs.core.Context final HttpServletRequest request) throws EntitlementApiException, SubscriptionApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "BundleJson body should be specified");
+        verifyNonNullOrEmpty(json.getAccountId(), "BundleJson accountId needs to be set");
 
         final BillingActionPolicy policy = BillingActionPolicy.valueOf(policyString.toUpperCase());
 
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/CreditResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/CreditResource.java
index d292613..bfad1b1 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/CreditResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/CreditResource.java
@@ -108,6 +108,10 @@ public class CreditResource extends JaxRsResourceBase {
                                  @HeaderParam(HDR_COMMENT) final String comment,
                                  @javax.ws.rs.core.Context final HttpServletRequest request,
                                  @javax.ws.rs.core.Context final UriInfo uriInfo) throws AccountApiException, InvoiceApiException {
+        verifyNonNullOrEmpty(json, "CreditJson body should be specified");
+        verifyNonNullOrEmpty(json.getAccountId(), "CreditJson accountId needs to be set",
+                             json.getCreditAmount(), "CreditJson creditAmount needs to be set");
+
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
         final Account account = accountUserApi.getAccountById(UUID.fromString(json.getAccountId()), callContext);
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoicePaymentResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoicePaymentResource.java
index 263b537..3a68362 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoicePaymentResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoicePaymentResource.java
@@ -149,6 +149,7 @@ public class InvoicePaymentResource extends JaxRsResourceBase {
                                                 @HeaderParam(HDR_COMMENT) final String comment,
                                                 @javax.ws.rs.core.Context final UriInfo uriInfo,
                                                 @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "InvoicePaymentTransactionJson body should be specified");
 
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
         final UUID paymentUuid = UUID.fromString(paymentId);
@@ -194,6 +195,8 @@ public class InvoicePaymentResource extends JaxRsResourceBase {
                                      @HeaderParam(HDR_COMMENT) final String comment,
                                      @javax.ws.rs.core.Context final UriInfo uriInfo,
                                      @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "InvoicePaymentTransactionJson body should be specified");
+        verifyNonNullOrEmpty(json.getAmount(), "InvoicePaymentTransactionJson amount needs to be set");
 
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
         final UUID paymentUuid = UUID.fromString(paymentId);
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoiceResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoiceResource.java
index c79c048..9399f63 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoiceResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/InvoiceResource.java
@@ -312,6 +312,10 @@ public class InvoiceResource extends JaxRsResourceBase {
                                       @HeaderParam(HDR_COMMENT) final String comment,
                                       @javax.ws.rs.core.Context final HttpServletRequest request,
                                       @javax.ws.rs.core.Context final UriInfo uriInfo) throws AccountApiException, InvoiceApiException {
+        verifyNonNullOrEmpty(json, "InvoiceItemJson body should be specified");
+        verifyNonNullOrEmpty(json.getAccountId(), "InvoiceItemJson accountId needs to be set",
+                             json.getInvoiceItemId(), "InvoiceItemJson invoiceItemId needs to be set");
+
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
         final UUID accountId = UUID.fromString(json.getAccountId());
@@ -341,7 +345,7 @@ public class InvoiceResource extends JaxRsResourceBase {
     @Produces(APPLICATION_JSON)
     @Consumes(APPLICATION_JSON)
     @Path("/" + CHARGES + "/{accountId:" + UUID_PATTERN + "}")
-    @ApiOperation(value = "Create external charge(s)",response = InvoiceItemJson.class, responseContainer = "List")
+    @ApiOperation(value = "Create external charge(s)", response = InvoiceItemJson.class, responseContainer = "List")
     @ApiResponses(value = {@ApiResponse(code = 400, message = "Invalid account id supplied"),
                            @ApiResponse(code = 404, message = "Account not found")})
     public Response createExternalCharges(final Iterable<InvoiceItemJson> externalChargesJson,
@@ -453,6 +457,11 @@ public class InvoiceResource extends JaxRsResourceBase {
                                          @HeaderParam(HDR_COMMENT) final String comment,
                                          @javax.ws.rs.core.Context final HttpServletRequest request,
                                          @javax.ws.rs.core.Context final UriInfo uriInfo) throws AccountApiException, PaymentApiException {
+        verifyNonNullOrEmpty(payment, "InvoicePaymentJson body should be specified");
+        verifyNonNullOrEmpty(payment.getAccountId(), "InvoicePaymentJson accountId needs to be set",
+                             payment.getTargetInvoiceId(), "InvoicePaymentJson targetInvoiceId needs to be set",
+                             payment.getPurchasedAmount(), "InvoicePaymentJson purchasedAmount needs to be set");
+
         final Iterable<PluginProperty> pluginProperties = extractPluginProperties(pluginPropertiesString);
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/JaxRsResourceBase.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/JaxRsResourceBase.java
index b95fa5b..e2ede5d 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/JaxRsResourceBase.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/JaxRsResourceBase.java
@@ -23,6 +23,7 @@ import java.io.OutputStream;
 import java.math.BigDecimal;
 import java.net.URI;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collection;
 import java.util.HashMap;
 import java.util.LinkedList;
@@ -85,7 +86,9 @@ import org.slf4j.LoggerFactory;
 import com.fasterxml.jackson.core.JsonGenerator;
 import com.google.common.base.Function;
 import com.google.common.base.Joiner;
+import com.google.common.base.Preconditions;
 import com.google.common.base.Predicate;
+import com.google.common.base.Strings;
 import com.google.common.collect.Collections2;
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.Iterables;
@@ -197,6 +200,8 @@ public abstract class JaxRsResourceBase implements JaxrsResource {
                                           final UriInfo uriInfo) throws CustomFieldApiException {
         final LinkedList<CustomField> input = new LinkedList<CustomField>();
         for (final CustomFieldJson cur : customFields) {
+            verifyNonNullOrEmpty(cur.getName(), "CustomFieldJson name needs to be set");
+            verifyNonNullOrEmpty(cur.getValue(), "CustomFieldJson value needs to be set");
             input.add(new StringCustomField(cur.getName(), cur.getValue(), getObjectType(), id, context.getCreatedDate()));
         }
 
@@ -399,4 +404,13 @@ public abstract class JaxRsResourceBase implements JaxrsResource {
         return invoicePayment != null ? invoicePayment.getInvoiceId() : null;
     }
 
+    protected void verifyNonNullOrEmpty(final Object... elements) {
+        Preconditions.checkArgument(elements.length % 2 == 0, "%s should have an even number of elements", Arrays.toString(elements));
+        for (int i = 0; i < elements.length; i += 2) {
+            final Object argument = elements[i];
+            final Object errorMessage = elements[i + 1];
+            final boolean expression = argument instanceof String ? Strings.emptyToNull((String) argument) != null : argument != null;
+            Preconditions.checkArgument(expression, errorMessage);
+        }
+    }
 }
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/PaymentResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/PaymentResource.java
index cb8b4b5..43b3464 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/PaymentResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/PaymentResource.java
@@ -215,6 +215,9 @@ public class PaymentResource extends JaxRsResourceBase {
                                          @HeaderParam(HDR_COMMENT) final String comment,
                                          @javax.ws.rs.core.Context final UriInfo uriInfo,
                                          @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "PaymentTransactionJson body should be specified");
+        verifyNonNullOrEmpty(json.getAmount(), "PaymentTransactionJson amount needs to be set");
+
         final Iterable<PluginProperty> pluginProperties = extractPluginProperties(pluginPropertiesString);
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
         final UUID paymentId = UUID.fromString(paymentIdStr);
@@ -244,6 +247,9 @@ public class PaymentResource extends JaxRsResourceBase {
                                   @HeaderParam(HDR_COMMENT) final String comment,
                                   @javax.ws.rs.core.Context final UriInfo uriInfo,
                                   @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "PaymentTransactionJson body should be specified");
+        verifyNonNullOrEmpty(json.getAmount(), "PaymentTransactionJson amount needs to be set");
+
         final Iterable<PluginProperty> pluginProperties = extractPluginProperties(pluginPropertiesString);
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
         final UUID paymentId = UUID.fromString(paymentIdStr);
@@ -301,6 +307,9 @@ public class PaymentResource extends JaxRsResourceBase {
                                       @HeaderParam(HDR_COMMENT) final String comment,
                                       @javax.ws.rs.core.Context final UriInfo uriInfo,
                                       @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "PaymentTransactionJson body should be specified");
+        verifyNonNullOrEmpty(json.getAmount(), "PaymentTransactionJson amount needs to be set");
+
         final Iterable<PluginProperty> pluginProperties = extractPluginProperties(pluginPropertiesString);
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
         final UUID paymentId = UUID.fromString(paymentIdStr);
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/SubscriptionResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/SubscriptionResource.java
index db47697..e83a503 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/SubscriptionResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/SubscriptionResource.java
@@ -146,6 +146,18 @@ public class SubscriptionResource extends JaxRsResourceBase {
                                       @HeaderParam(HDR_COMMENT) final String comment,
                                       @javax.ws.rs.core.Context final HttpServletRequest request,
                                       @javax.ws.rs.core.Context final UriInfo uriInfo) throws EntitlementApiException, AccountApiException, SubscriptionApiException {
+        verifyNonNullOrEmpty(entitlement, "SubscriptionJson body should be specified");
+        verifyNonNullOrEmpty(entitlement.getProductName(), "SubscriptionJson productName needs to be set",
+                             entitlement.getProductCategory(), "SubscriptionJson productCategory needs to be set",
+                             entitlement.getBillingPeriod(), "SubscriptionJson billingPeriod needs to be set",
+                             entitlement.getPriceList(), "SubscriptionJson priceList needs to be set");
+        final boolean createAddOnEntitlement = ProductCategory.ADD_ON.toString().equals(entitlement.getProductCategory());
+        if (createAddOnEntitlement) {
+            verifyNonNullOrEmpty(entitlement.getBundleId(), "SubscriptionJson bundleId should be specified");
+        } else {
+            verifyNonNullOrEmpty(entitlement.getAccountId(), "SubscriptionJson accountId should be specified");
+        }
+
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
         final EntitlementCallCompletionCallback<Entitlement> callback = new EntitlementCallCompletionCallback<Entitlement>() {
             @Override
@@ -158,7 +170,7 @@ public class SubscriptionResource extends JaxRsResourceBase {
                 final UUID accountId = entitlement.getAccountId() != null ? UUID.fromString(entitlement.getAccountId()) : null;
                 final LocalDate inputLocalDate = toLocalDate(accountId, requestedDate, callContext);
                 final UUID bundleId = entitlement.getBundleId() != null ? UUID.fromString(entitlement.getBundleId()) : null;
-                return (entitlement.getProductCategory().equals(ProductCategory.ADD_ON.toString())) ?
+                return createAddOnEntitlement ?
                        entitlementApi.addEntitlement(bundleId, spec, inputLocalDate, callContext) :
                        entitlementApi.createBaseEntitlement(accountId, spec, entitlement.getExternalKey(), inputLocalDate, callContext);
             }
@@ -214,6 +226,11 @@ public class SubscriptionResource extends JaxRsResourceBase {
                                           @HeaderParam(HDR_REASON) final String reason,
                                           @HeaderParam(HDR_COMMENT) final String comment,
                                           @javax.ws.rs.core.Context final HttpServletRequest request) throws EntitlementApiException, AccountApiException, SubscriptionApiException {
+        verifyNonNullOrEmpty(entitlement, "SubscriptionJson body should be specified");
+        verifyNonNullOrEmpty(entitlement.getProductName(), "SubscriptionJson productName needs to be set",
+                             entitlement.getBillingPeriod(), "SubscriptionJson billingPeriod needs to be set",
+                             entitlement.getPriceList(), "SubscriptionJson priceList needs to be set");
+
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
         final EntitlementCallCompletionCallback<Response> callback = new EntitlementCallCompletionCallback<Response>() {
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TagDefinitionResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TagDefinitionResource.java
index e2a1ce8..0afb793 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TagDefinitionResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TagDefinitionResource.java
@@ -38,11 +38,10 @@ import javax.ws.rs.core.UriInfo;
 
 import org.killbill.billing.ObjectType;
 import org.killbill.billing.account.api.AccountUserApi;
-import org.killbill.billing.payment.api.PaymentApi;
-import org.killbill.clock.Clock;
 import org.killbill.billing.jaxrs.json.TagDefinitionJson;
 import org.killbill.billing.jaxrs.util.Context;
 import org.killbill.billing.jaxrs.util.JaxrsUriBuilder;
+import org.killbill.billing.payment.api.PaymentApi;
 import org.killbill.billing.util.api.AuditUserApi;
 import org.killbill.billing.util.api.CustomFieldUserApi;
 import org.killbill.billing.util.api.TagDefinitionApiException;
@@ -50,9 +49,9 @@ import org.killbill.billing.util.api.TagUserApi;
 import org.killbill.billing.util.audit.AuditLog;
 import org.killbill.billing.util.callcontext.TenantContext;
 import org.killbill.billing.util.tag.TagDefinition;
+import org.killbill.clock.Clock;
 
 import com.codahale.metrics.annotation.Timed;
-import com.google.common.base.Preconditions;
 import com.google.inject.Inject;
 import com.google.inject.Singleton;
 import com.wordnik.swagger.annotations.Api;
@@ -127,8 +126,9 @@ public class TagDefinitionResource extends JaxRsResourceBase {
                                         @javax.ws.rs.core.Context final HttpServletRequest request,
                                         @javax.ws.rs.core.Context final UriInfo uriInfo) throws TagDefinitionApiException {
         // Checked as the database layer as well, but bail early and return 400 instead of 500
-        Preconditions.checkNotNull(json.getName(), String.format("TagDefinition name needs to be set"));
-        Preconditions.checkNotNull(json.getDescription(), String.format("TagDefinition description needs to be set"));
+        verifyNonNullOrEmpty(json, "TagDefinitionJson body should be specified");
+        verifyNonNullOrEmpty(json.getName(), "TagDefinition name needs to be set",
+                             json.getDescription(), "TagDefinition description needs to be set");
 
         final TagDefinition createdTagDef = tagUserApi.createTagDefinition(json.getName(), json.getDescription(), context.createContext(createdBy, reason, comment, request));
         return uriBuilder.buildResponse(uriInfo, TagDefinitionResource.class, "getTagDefinition", createdTagDef.getId());
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TenantResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TenantResource.java
index 50f8625..045eb04 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TenantResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TenantResource.java
@@ -119,6 +119,10 @@ public class TenantResource extends JaxRsResourceBase {
                                  @HeaderParam(HDR_COMMENT) final String comment,
                                  @javax.ws.rs.core.Context final HttpServletRequest request,
                                  @javax.ws.rs.core.Context final UriInfo uriInfo) throws TenantApiException {
+        verifyNonNullOrEmpty(json, "TenantJson body should be specified");
+        verifyNonNullOrEmpty(json.getApiKey(), "TenantJson apiKey needs to be set",
+                             json.getApiSecret(), "TenantJson apiSecret needs to be set");
+
         final TenantData data = json.toTenantData();
         final Tenant tenant = tenantApi.createTenant(data, context.createContext(createdBy, reason, comment, request));
         return uriBuilder.buildResponse(uriInfo, TenantResource.class, "getTenant", tenant.getId());
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TransactionResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TransactionResource.java
index 41c1ae5..68d9060 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TransactionResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/TransactionResource.java
@@ -17,25 +17,16 @@
 
 package org.killbill.billing.jaxrs.resources;
 
-import java.net.URI;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
 import java.util.UUID;
-import java.util.concurrent.atomic.AtomicReference;
 
 import javax.inject.Inject;
 import javax.servlet.http.HttpServletRequest;
 import javax.ws.rs.Consumes;
-import javax.ws.rs.DELETE;
-import javax.ws.rs.DefaultValue;
-import javax.ws.rs.GET;
 import javax.ws.rs.HeaderParam;
 import javax.ws.rs.POST;
 import javax.ws.rs.Path;
 import javax.ws.rs.PathParam;
 import javax.ws.rs.Produces;
-import javax.ws.rs.QueryParam;
 import javax.ws.rs.core.Response;
 import javax.ws.rs.core.UriInfo;
 
@@ -43,8 +34,6 @@ import org.killbill.billing.ObjectType;
 import org.killbill.billing.account.api.Account;
 import org.killbill.billing.account.api.AccountApiException;
 import org.killbill.billing.account.api.AccountUserApi;
-import org.killbill.billing.catalog.api.Currency;
-import org.killbill.billing.jaxrs.json.PaymentJson;
 import org.killbill.billing.jaxrs.json.PaymentTransactionJson;
 import org.killbill.billing.jaxrs.util.Context;
 import org.killbill.billing.jaxrs.util.JaxrsUriBuilder;
@@ -56,17 +45,11 @@ import org.killbill.billing.payment.api.TransactionStatus;
 import org.killbill.billing.util.api.AuditUserApi;
 import org.killbill.billing.util.api.CustomFieldUserApi;
 import org.killbill.billing.util.api.TagUserApi;
-import org.killbill.billing.util.audit.AccountAuditLogs;
 import org.killbill.billing.util.callcontext.CallContext;
-import org.killbill.billing.util.callcontext.TenantContext;
-import org.killbill.billing.util.entity.Pagination;
 import org.killbill.clock.Clock;
 
 import com.codahale.metrics.annotation.Timed;
-import com.google.common.base.Function;
-import com.google.common.base.Strings;
 import com.google.common.collect.ImmutableList;
-import com.google.common.collect.ImmutableMap;
 import com.wordnik.swagger.annotations.Api;
 import com.wordnik.swagger.annotations.ApiOperation;
 import com.wordnik.swagger.annotations.ApiResponse;
@@ -99,12 +82,15 @@ public class TransactionResource extends JaxRsResourceBase {
     @ApiResponses(value = {@ApiResponse(code = 400, message = "Invalid paymentId supplied"),
                            @ApiResponse(code = 404, message = "Account or Payment not found")})
     public Response notifyStateChanged(final PaymentTransactionJson json,
-                                         @PathParam("transactionId") final String transactionIdStr,
-                                         @HeaderParam(HDR_CREATED_BY) final String createdBy,
-                                         @HeaderParam(HDR_REASON) final String reason,
-                                         @HeaderParam(HDR_COMMENT) final String comment,
-                                         @javax.ws.rs.core.Context final UriInfo uriInfo,
-                                         @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+                                       @PathParam("transactionId") final String transactionIdStr,
+                                       @HeaderParam(HDR_CREATED_BY) final String createdBy,
+                                       @HeaderParam(HDR_REASON) final String reason,
+                                       @HeaderParam(HDR_COMMENT) final String comment,
+                                       @javax.ws.rs.core.Context final UriInfo uriInfo,
+                                       @javax.ws.rs.core.Context final HttpServletRequest request) throws PaymentApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "PaymentTransactionJson body should be specified");
+        verifyNonNullOrEmpty(json.getPaymentId(), "PaymentTransactionJson paymentId needs to be set",
+                             json.getStatus(), "PaymentTransactionJson status needs to be set");
 
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
 
@@ -112,13 +98,11 @@ public class TransactionResource extends JaxRsResourceBase {
         final Payment payment = paymentApi.getPayment(paymentId, false, ImmutableList.<PluginProperty>of(), callContext);
         final Account account = accountUserApi.getAccountById(payment.getAccountId(), callContext);
 
-        final boolean success = json.getStatus().equals(TransactionStatus.SUCCESS.name());
+        final boolean success = TransactionStatus.SUCCESS.name().equals(json.getStatus());
         final Payment result = paymentApi.notifyPendingTransactionOfStateChanged(account, UUID.fromString(transactionIdStr), success, callContext);
         return uriBuilder.buildResponse(uriInfo, PaymentResource.class, "getPayment", result.getId());
     }
 
-
-
     @Override
     protected ObjectType getObjectType() {
         return ObjectType.TRANSACTION;
diff --git a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/UsageResource.java b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/UsageResource.java
index 9df0f4c..f961ac2 100644
--- a/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/UsageResource.java
+++ b/jaxrs/src/main/java/org/killbill/billing/jaxrs/resources/UsageResource.java
@@ -19,7 +19,6 @@ package org.killbill.billing.jaxrs.resources;
 import java.util.List;
 import java.util.UUID;
 
-import javax.annotation.concurrent.Immutable;
 import javax.inject.Inject;
 import javax.servlet.http.HttpServletRequest;
 import javax.ws.rs.Consumes;
@@ -98,14 +97,14 @@ public class UsageResource extends JaxRsResourceBase {
     @ApiOperation(value = "Record usage for a subscription")
     @ApiResponses(value = {@ApiResponse(code = 400, message = "Invalid subscription (e.g. inactive)")})
     public Response recordUsage(final SubscriptionUsageRecordJson json,
-                                  @HeaderParam(HDR_CREATED_BY) final String createdBy,
-                                  @HeaderParam(HDR_REASON) final String reason,
-                                  @HeaderParam(HDR_COMMENT) final String comment,
-                                  @javax.ws.rs.core.Context final HttpServletRequest request,
-                                  @javax.ws.rs.core.Context final UriInfo uriInfo) throws EntitlementApiException, AccountApiException {
-
-        Preconditions.checkNotNull(json.getSubscriptionId());
-        Preconditions.checkNotNull(json.getUnitUsageRecords());
+                                @HeaderParam(HDR_CREATED_BY) final String createdBy,
+                                @HeaderParam(HDR_REASON) final String reason,
+                                @HeaderParam(HDR_COMMENT) final String comment,
+                                @javax.ws.rs.core.Context final HttpServletRequest request,
+                                @javax.ws.rs.core.Context final UriInfo uriInfo) throws EntitlementApiException, AccountApiException {
+        verifyNonNullOrEmpty(json, "SubscriptionUsageRecordJson body should be specified");
+        verifyNonNullOrEmpty(json.getSubscriptionId(), "SubscriptionUsageRecordJson subscriptionId needs to be set",
+                             json.getUnitUsageRecords(), "SubscriptionUsageRecordJson unitUsageRecords needs to be set");
         Preconditions.checkArgument(!json.getUnitUsageRecords().isEmpty());
 
         final CallContext callContext = context.createContext(createdBy, reason, comment, request);
@@ -130,7 +129,7 @@ public class UsageResource extends JaxRsResourceBase {
                              @PathParam("unitType") final String unitType,
                              @QueryParam(QUERY_START_DATE) final String startDate,
                              @QueryParam(QUERY_END_DATE) final String endDate,
-                             @javax.ws.rs.core.Context final HttpServletRequest request)  {
+                             @javax.ws.rs.core.Context final HttpServletRequest request) {
 
         if (startDate == null || endDate == null) {
             return Response.status(Status.BAD_REQUEST).build();
@@ -152,9 +151,9 @@ public class UsageResource extends JaxRsResourceBase {
     @ApiOperation(value = "Retrieve usage for a subscription", response = RolledUpUsageJson.class)
     @ApiResponses(value = {@ApiResponse(code = 400, message = "Missing start date or end date")})
     public Response getAllUsage(@PathParam("subscriptionId") final String subscriptionId,
-                             @QueryParam(QUERY_START_DATE) final String startDate,
-                             @QueryParam(QUERY_END_DATE) final String endDate,
-                             @javax.ws.rs.core.Context final HttpServletRequest request)  {
+                                @QueryParam(QUERY_START_DATE) final String startDate,
+                                @QueryParam(QUERY_END_DATE) final String endDate,
+                                @javax.ws.rs.core.Context final HttpServletRequest request) {
 
         if (startDate == null || endDate == null) {
             return Response.status(Status.BAD_REQUEST).build();
diff --git a/jaxrs/src/test/java/org/killbill/billing/jaxrs/json/TestBillingExceptionJson.java b/jaxrs/src/test/java/org/killbill/billing/jaxrs/json/TestBillingExceptionJson.java
index 86b605c..626df42 100644
--- a/jaxrs/src/test/java/org/killbill/billing/jaxrs/json/TestBillingExceptionJson.java
+++ b/jaxrs/src/test/java/org/killbill/billing/jaxrs/json/TestBillingExceptionJson.java
@@ -56,7 +56,7 @@ public class TestBillingExceptionJson extends JaxrsTestSuiteNoDB {
             nil.toString();
             Assert.fail();
         } catch (final NullPointerException e) {
-            final BillingExceptionJson exceptionJson = new BillingExceptionJson(e);
+            final BillingExceptionJson exceptionJson = new BillingExceptionJson(e, true);
             Assert.assertEquals(exceptionJson.getClassName(), e.getClass().getName());
             Assert.assertNull(exceptionJson.getCode());
             Assert.assertNull(exceptionJson.getMessage());
@@ -66,6 +66,14 @@ public class TestBillingExceptionJson extends JaxrsTestSuiteNoDB {
             Assert.assertEquals(exceptionJson.getStackTrace().get(0).getClassName(), TestBillingExceptionJson.class.getName());
             Assert.assertEquals(exceptionJson.getStackTrace().get(0).getMethodName(), "testFromException");
             Assert.assertFalse(exceptionJson.getStackTrace().get(0).getNativeMethod());
+
+            final BillingExceptionJson exceptionJsonNoStackTrace = new BillingExceptionJson(e, false);
+            Assert.assertEquals(exceptionJsonNoStackTrace.getClassName(), e.getClass().getName());
+            Assert.assertNull(exceptionJsonNoStackTrace.getCode());
+            Assert.assertNull(exceptionJsonNoStackTrace.getMessage());
+            Assert.assertNull(exceptionJsonNoStackTrace.getCauseClassName());
+            Assert.assertNull(exceptionJsonNoStackTrace.getCauseMessage());
+            Assert.assertTrue(exceptionJsonNoStackTrace.getStackTrace().isEmpty());
         }
     }
 }
diff --git a/profiles/killbill/src/main/webapp/api.html b/profiles/killbill/src/main/webapp/api.html
index b271f3d..dce3c00 100644
--- a/profiles/killbill/src/main/webapp/api.html
+++ b/profiles/killbill/src/main/webapp/api.html
@@ -3,6 +3,7 @@
 <head>
   <title>Kill Bill APIs</title>
   <link href='//fonts.googleapis.com/css?family=Droid+Sans:400,700' rel='stylesheet' type='text/css'/>
+  <link href='//fonts.googleapis.com/css?family=Roboto:400,700' rel='stylesheet' type='text/css'/>
   <link href='css/reset.css' media='screen' rel='stylesheet' type='text/css'/>
   <link href='css/screen.css' media='screen' rel='stylesheet' type='text/css'/>
   <link href='css/reset.css' media='print' rel='stylesheet' type='text/css'/>
@@ -108,6 +109,11 @@
 <body class="swagger-section">
 <div id='header'>
   <div class="swagger-ui-wrap">
+    <div id="kb-logo-container">
+      <a href="http://kill-bill.org">
+        <img id="kb-logo" title="Kill Bill" border="0" alt="Kill Bill" src="../images/killbill_logo.png">
+      </a>
+    </div>
     <form id='api_selector'>
       <div class='input'><input placeholder="http://127.0.0.1:8080/api-docs" id="input_baseUrl" name="baseUrl" type="text" size="38"/></div>
       <div class='input'><input placeholder="api_key" id="input_kb_apiKey" name="apiKey" type="text" size="8"/></div>
diff --git a/profiles/killbill/src/main/webapp/css/killbill-swagger.css b/profiles/killbill/src/main/webapp/css/killbill-swagger.css
index b3b0210..ded906d 100644
--- a/profiles/killbill/src/main/webapp/css/killbill-swagger.css
+++ b/profiles/killbill/src/main/webapp/css/killbill-swagger.css
@@ -12,10 +12,39 @@
 }
 */
 
+#kb-logo-container {
+  max-width: 175px;
+  margin-left: -220px;
+  margin-top: -10px;
+  float: left;
+}
+
+img#kb-logo {
+  max-width: 100%;
+  height: auto;
+  width: auto\9; /* ie8 */
+}
+
 .swagger-section .swagger-ui-wrap {
   height: 24px;
 }
 
+.swagger-section .swagger-ui-wrap {
+  font-family: "Roboto Light";
+}
+
+.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 {
+  font-family: "Roboto Light";
+}
+
+.swagger-section #header {
+  background-color: transparent;
+}
+
 .swagger-section #header form#api_selector {
   float: left;
 }
+
+.swagger-section #header form#api_selector .input a#explore {
+  background-color: #e44c3a;
+}
\ No newline at end of file
diff --git a/profiles/killbill/src/main/webapp/images/killbill_logo.png b/profiles/killbill/src/main/webapp/images/killbill_logo.png
new file mode 100644
index 0000000..feb37eb
Binary files /dev/null and b/profiles/killbill/src/main/webapp/images/killbill_logo.png differ
diff --git a/profiles/killpay/src/main/webapp/api.html b/profiles/killpay/src/main/webapp/api.html
index b271f3d..dce3c00 100644
--- a/profiles/killpay/src/main/webapp/api.html
+++ b/profiles/killpay/src/main/webapp/api.html
@@ -3,6 +3,7 @@
 <head>
   <title>Kill Bill APIs</title>
   <link href='//fonts.googleapis.com/css?family=Droid+Sans:400,700' rel='stylesheet' type='text/css'/>
+  <link href='//fonts.googleapis.com/css?family=Roboto:400,700' rel='stylesheet' type='text/css'/>
   <link href='css/reset.css' media='screen' rel='stylesheet' type='text/css'/>
   <link href='css/screen.css' media='screen' rel='stylesheet' type='text/css'/>
   <link href='css/reset.css' media='print' rel='stylesheet' type='text/css'/>
@@ -108,6 +109,11 @@
 <body class="swagger-section">
 <div id='header'>
   <div class="swagger-ui-wrap">
+    <div id="kb-logo-container">
+      <a href="http://kill-bill.org">
+        <img id="kb-logo" title="Kill Bill" border="0" alt="Kill Bill" src="../images/killbill_logo.png">
+      </a>
+    </div>
     <form id='api_selector'>
       <div class='input'><input placeholder="http://127.0.0.1:8080/api-docs" id="input_baseUrl" name="baseUrl" type="text" size="38"/></div>
       <div class='input'><input placeholder="api_key" id="input_kb_apiKey" name="apiKey" type="text" size="8"/></div>
diff --git a/profiles/killpay/src/main/webapp/css/killbill-swagger.css b/profiles/killpay/src/main/webapp/css/killbill-swagger.css
index b3b0210..ded906d 100644
--- a/profiles/killpay/src/main/webapp/css/killbill-swagger.css
+++ b/profiles/killpay/src/main/webapp/css/killbill-swagger.css
@@ -12,10 +12,39 @@
 }
 */
 
+#kb-logo-container {
+  max-width: 175px;
+  margin-left: -220px;
+  margin-top: -10px;
+  float: left;
+}
+
+img#kb-logo {
+  max-width: 100%;
+  height: auto;
+  width: auto\9; /* ie8 */
+}
+
 .swagger-section .swagger-ui-wrap {
   height: 24px;
 }
 
+.swagger-section .swagger-ui-wrap {
+  font-family: "Roboto Light";
+}
+
+.swagger-section .swagger-ui-wrap ul#resources li.resource div.heading h2 {
+  font-family: "Roboto Light";
+}
+
+.swagger-section #header {
+  background-color: transparent;
+}
+
 .swagger-section #header form#api_selector {
   float: left;
 }
+
+.swagger-section #header form#api_selector .input a#explore {
+  background-color: #e44c3a;
+}
\ No newline at end of file
diff --git a/profiles/killpay/src/main/webapp/images/killbill_logo.png b/profiles/killpay/src/main/webapp/images/killbill_logo.png
new file mode 100644
index 0000000..feb37eb
Binary files /dev/null and b/profiles/killpay/src/main/webapp/images/killbill_logo.png differ