killbill-aplcache
Changes
account/src/main/java/com/ning/billing/account/api/user/DefaultAccountChangeNotification.java 19(+10 -9)
util/pom.xml 16(+15 -1)
Details
diff --git a/account/src/main/java/com/ning/billing/account/api/DefaultAccount.java b/account/src/main/java/com/ning/billing/account/api/DefaultAccount.java
index 5c32c00..2de266c 100644
--- a/account/src/main/java/com/ning/billing/account/api/DefaultAccount.java
+++ b/account/src/main/java/com/ning/billing/account/api/DefaultAccount.java
@@ -16,76 +16,79 @@
package com.ning.billing.account.api;
-import java.math.BigDecimal;
import java.util.List;
import java.util.UUID;
import org.joda.time.DateTime;
import org.joda.time.DateTimeZone;
import com.ning.billing.catalog.api.Currency;
import com.ning.billing.util.customfield.CustomizableEntityBase;
-import com.ning.billing.util.tag.DefaultTag;
+import com.ning.billing.util.tag.DescriptiveTag;
import com.ning.billing.util.tag.DefaultTagStore;
import com.ning.billing.util.tag.Tag;
-import com.ning.billing.util.tag.TagDescription;
+import com.ning.billing.util.tag.TagDefinition;
public class DefaultAccount extends CustomizableEntityBase implements Account {
- public final static String OBJECT_TYPE = "Account";
+ //public final static String OBJECT_TYPE = "Account";
private final String externalKey;
private final String email;
private final String name;
private final int firstNameLength;
- private final String phone;
private final Currency currency;
private final int billCycleDay;
private final String paymentProviderName;
- private final BigDecimal balance;
private final DefaultTagStore tags;
private final DateTimeZone timeZone;
private final String locale;
- private final DateTime nextBillingDate;
+ private final String address1;
+ private final String address2;
+ private final String city;
+ private final String stateOrProvince;
+ private final String country;
+ private final String postalCode;
+ private final String phone;
public DefaultAccount(final AccountData data) {
this(UUID.randomUUID(), data);
}
public DefaultAccount(final UUID id, final AccountData data) {
- this(id, data.getExternalKey(), data.getEmail(), data.getName(),
- data.getFirstNameLength(), data.getPhone(), data.getCurrency(), data.getBillCycleDay(),
- data.getPaymentProviderName(), BigDecimal.ZERO, data.getTimeZone(), data.getLocale(),
- data.getNextBillingDate());
+ this(id, data.getExternalKey(), data.getEmail(), data.getName(), data.getFirstNameLength(),
+ data.getCurrency(), data.getBillCycleDay(), data.getPaymentProviderName(),
+ data.getTimeZone(), data.getLocale(),
+ data.getAddress1(), data.getAddress2(), data.getCity(), data.getStateOrProvince(), data.getCountry(),
+ data.getPostalCode(), data.getPhone());
}
public DefaultAccount(final UUID id, final String externalKey, final String email, final String name, final int firstNameLength,
- final String phone, final Currency currency, final int billCycleDay, final String paymentProviderName,
- final BigDecimal balance, final DateTimeZone timeZone, final String locale,
- final DateTime nextBillingDate) {
+ final Currency currency, final int billCycleDay, final String paymentProviderName,
+ final DateTimeZone timeZone, final String locale,
+ final String address1, final String address2, final String city,
+ final String stateOrProvince, final String country, final String postalCode, final String phone) {
super(id);
this.externalKey = externalKey;
this.email = email;
this.name = name;
this.firstNameLength = firstNameLength;
- this.phone = phone;
this.currency = currency;
this.billCycleDay = billCycleDay;
this.paymentProviderName = paymentProviderName;
-
- if (balance == null) {
- this.balance = BigDecimal.ZERO;
- } else {
- this.balance = balance;
- }
-
this.timeZone = timeZone;
this.locale = locale;
- this.nextBillingDate = nextBillingDate;
+ this.address1 = address1;
+ this.address2 = address2;
+ this.city = city;
+ this.stateOrProvince = stateOrProvince;
+ this.postalCode = postalCode;
+ this.country = country;
+ this.phone = phone;
this.tags = new DefaultTagStore(id, getObjectName());
}
@Override
public String getObjectName() {
- return OBJECT_TYPE;
+ return "Account";
}
@Override
@@ -109,11 +112,6 @@ public class DefaultAccount extends CustomizableEntityBase implements Account {
}
@Override
- public String getPhone() {
- return phone;
- }
-
- @Override
public Currency getCurrency() {
return currency;
}
@@ -129,11 +127,6 @@ public class DefaultAccount extends CustomizableEntityBase implements Account {
}
@Override
- public BigDecimal getBalance() {
- return balance;
- }
-
- @Override
public DateTimeZone getTimeZone() {
return timeZone;
}
@@ -144,8 +137,38 @@ public class DefaultAccount extends CustomizableEntityBase implements Account {
}
@Override
- public DateTime getNextBillingDate() {
- return nextBillingDate;
+ public String getAddress1() {
+ return address1;
+ }
+
+ @Override
+ public String getAddress2() {
+ return address2;
+ }
+
+ @Override
+ public String getCity() {
+ return city;
+ }
+
+ @Override
+ public String getStateOrProvince() {
+ return stateOrProvince;
+ }
+
+ @Override
+ public String getPostalCode() {
+ return postalCode;
+ }
+
+ @Override
+ public String getCountry() {
+ return country;
+ }
+
+ @Override
+ public String getPhone() {
+ return phone;
}
@Override
@@ -159,8 +182,8 @@ public class DefaultAccount extends CustomizableEntityBase implements Account {
}
@Override
- public void addTag(TagDescription description, String addedBy, DateTime dateAdded) {
- Tag tag = new DefaultTag(description, addedBy, dateAdded);
+ public void addTag(TagDefinition description, String addedBy, DateTime dateAdded) {
+ Tag tag = new DescriptiveTag(description, addedBy, dateAdded);
tags.add(tag) ;
}
@@ -177,7 +200,7 @@ public class DefaultAccount extends CustomizableEntityBase implements Account {
}
@Override
- public void removeTag(TagDescription description) {
+ public void removeTag(TagDefinition description) {
tags.remove(description.getName());
}
diff --git a/account/src/main/java/com/ning/billing/account/api/user/AccountBuilder.java b/account/src/main/java/com/ning/billing/account/api/user/AccountBuilder.java
index 6a86605..c229fcc 100644
--- a/account/src/main/java/com/ning/billing/account/api/user/AccountBuilder.java
+++ b/account/src/main/java/com/ning/billing/account/api/user/AccountBuilder.java
@@ -30,14 +30,19 @@ public class AccountBuilder {
private String email;
private String name;
private int firstNameLength;
- private String phone;
private Currency currency;
private int billingCycleDay;
private String paymentProviderName;
- private BigDecimal balance = BigDecimal.ZERO;
private DateTimeZone timeZone;
private String locale;
- private DateTime nextBillingDate;
+ private String address1;
+ private String address2;
+ private String city;
+ private String stateOrProvince;
+ private String country;
+ private String postalCode;
+ private String phone;
+
public AccountBuilder() {
this(UUID.randomUUID());
@@ -67,11 +72,6 @@ public class AccountBuilder {
return this;
}
- public AccountBuilder phone(String phone) {
- this.phone = phone;
- return this;
- }
-
public AccountBuilder billingCycleDay(final int billingCycleDay) {
this.billingCycleDay = billingCycleDay;
return this;
@@ -87,11 +87,6 @@ public class AccountBuilder {
return this;
}
- public AccountBuilder balance(final BigDecimal balance) {
- this.balance = balance;
- return this;
- }
-
public AccountBuilder timeZone(final DateTimeZone timeZone) {
this.timeZone = timeZone;
return this;
@@ -102,14 +97,46 @@ public class AccountBuilder {
return this;
}
- public AccountBuilder nextBillingDate(final DateTime nextBillingDate) {
- this.nextBillingDate = nextBillingDate;
+ public AccountBuilder address1(final String address1) {
+ this.address1 = address1;
+ return this;
+ }
+
+ public AccountBuilder address2(final String address2) {
+ this.address2 = address2;
+ return this;
+ }
+
+ public AccountBuilder city(final String city) {
+ this.city = city;
+ return this;
+ }
+
+ public AccountBuilder stateOrProvince(final String stateOrProvince) {
+ this.stateOrProvince = stateOrProvince;
+ return this;
+ }
+
+ public AccountBuilder postalCode(final String postalCode) {
+ this.postalCode = postalCode;
+ return this;
+ }
+
+ public AccountBuilder country(final String country) {
+ this.country = country;
+ return this;
+ }
+
+ public AccountBuilder phone(final String phone) {
+ this.phone = phone;
return this;
}
public DefaultAccount build() {
return new DefaultAccount(id, externalKey, email, name, firstNameLength,
- phone, currency, billingCycleDay, paymentProviderName,
- balance, timeZone, locale, nextBillingDate);
+ currency, billingCycleDay, paymentProviderName,
+ timeZone, locale,
+ address1, address2, city, stateOrProvince, country,
+ postalCode, phone);
}
}
diff --git a/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountChangeNotification.java b/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountChangeNotification.java
index 297b16d..11a5a39 100644
--- a/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountChangeNotification.java
+++ b/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountChangeNotification.java
@@ -62,9 +62,6 @@ public class DefaultAccountChangeNotification implements AccountChangeNotificati
addIfValueChanged(tmpChangedFields, "firstName",
oldData.getName(), newData.getName());
- addIfValueChanged(tmpChangedFields, "phone",
- oldData.getPhone(), newData.getPhone());
-
addIfValueChanged(tmpChangedFields, "currency",
(oldData.getCurrency() != null) ? oldData.getCurrency().toString() : null,
(newData.getCurrency() != null) ? newData.getCurrency().toString() : null);
@@ -79,12 +76,16 @@ public class DefaultAccountChangeNotification implements AccountChangeNotificati
addIfValueChanged(tmpChangedFields, "locale", oldData.getLocale(), newData.getLocale());
addIfValueChanged(tmpChangedFields, "timeZone",
- oldData.getTimeZone().toString(),
- newData.getTimeZone().toString());
-
- addIfValueChanged(tmpChangedFields, "nextBillingDate",
- oldData.getNextBillingDate().toString(),
- newData.getNextBillingDate().toString());
+ (oldData.getTimeZone() == null) ? null : oldData.getTimeZone().toString(),
+ (newData.getTimeZone() == null) ? null : newData.getTimeZone().toString());
+
+ addIfValueChanged(tmpChangedFields, "address1", oldData.getAddress1(), newData.getAddress1());
+ addIfValueChanged(tmpChangedFields, "address2", oldData.getAddress2(), newData.getAddress2());
+ addIfValueChanged(tmpChangedFields, "city", oldData.getCity(), newData.getCity());
+ addIfValueChanged(tmpChangedFields, "stateOrProvince", oldData.getStateOrProvince(), newData.getStateOrProvince());
+ addIfValueChanged(tmpChangedFields, "country", oldData.getCountry(), newData.getCountry());
+ addIfValueChanged(tmpChangedFields, "postalCode", oldData.getPostalCode(), newData.getPostalCode());
+ addIfValueChanged(tmpChangedFields, "phone", oldData.getPhone(), newData.getPhone());
return tmpChangedFields;
}
diff --git a/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountUserApi.java b/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountUserApi.java
index 08080b4..d9372d1 100644
--- a/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountUserApi.java
+++ b/account/src/main/java/com/ning/billing/account/api/user/DefaultAccountUserApi.java
@@ -26,6 +26,7 @@ import com.ning.billing.account.api.AccountData;
import com.ning.billing.account.api.DefaultAccount;
import com.ning.billing.account.dao.AccountDao;
import com.ning.billing.util.customfield.CustomField;
+import com.ning.billing.util.eventbus.EventBus;
import com.ning.billing.util.tag.Tag;
public class DefaultAccountUserApi implements com.ning.billing.account.api.AccountUserApi {
@@ -62,12 +63,12 @@ public class DefaultAccountUserApi implements com.ning.billing.account.api.Accou
}
@Override
- public UUID getIdFromKey(final String externalKey) {
+ public UUID getIdFromKey(final String externalKey) throws AccountApiException {
return dao.getIdFromKey(externalKey);
}
@Override
- public void updateAccount(final Account account) {
+ public void updateAccount(final Account account) throws AccountApiException, EventBus.EventBusException {
dao.update(account);
}
}
diff --git a/account/src/main/java/com/ning/billing/account/dao/AccountDao.java b/account/src/main/java/com/ning/billing/account/dao/AccountDao.java
index 04b50e3..9d4b2ac 100644
--- a/account/src/main/java/com/ning/billing/account/dao/AccountDao.java
+++ b/account/src/main/java/com/ning/billing/account/dao/AccountDao.java
@@ -18,10 +18,17 @@ package com.ning.billing.account.dao;
import java.util.UUID;
import com.ning.billing.account.api.Account;
+import com.ning.billing.account.api.AccountApiException;
import com.ning.billing.util.entity.EntityDao;
public interface AccountDao extends EntityDao<Account> {
public Account getAccountByKey(String key);
- public UUID getIdFromKey(String externalKey);
-}
+ /***
+ *
+ * @param externalKey
+ * @return
+ * @throws AccountApiException when externalKey is null
+ */
+ public UUID getIdFromKey(String externalKey) throws AccountApiException;
+}
\ No newline at end of file
diff --git a/account/src/main/java/com/ning/billing/account/dao/AccountSqlDao.java b/account/src/main/java/com/ning/billing/account/dao/AccountSqlDao.java
index c57362d..ecfa6b9 100644
--- a/account/src/main/java/com/ning/billing/account/dao/AccountSqlDao.java
+++ b/account/src/main/java/com/ning/billing/account/dao/AccountSqlDao.java
@@ -17,7 +17,6 @@
package com.ning.billing.account.dao;
import com.ning.billing.account.api.Account;
-import com.ning.billing.account.api.AccountApiException;
import com.ning.billing.account.api.user.AccountBuilder;
import com.ning.billing.catalog.api.Currency;
import com.ning.billing.util.UuidMapper;
@@ -43,7 +42,6 @@ import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
-import java.math.BigDecimal;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
@@ -74,7 +72,6 @@ public interface AccountSqlDao extends EntityDao<Account>, Transactional<Account
String email = result.getString("email");
String name = result.getString("name");
int firstNameLength = result.getInt("first_name_length");
- String phone = result.getString("phone");
int billingCycleDay = result.getInt("billing_cycle_day");
String currencyString = result.getString("currency");
@@ -87,17 +84,23 @@ public interface AccountSqlDao extends EntityDao<Account>, Transactional<Account
String locale = result.getString("locale");
- Timestamp nextBillingDateTimestamp = result.getTimestamp("next_billing_date");
- DateTime nextBillingDate = nextBillingDateTimestamp == null ? null : new DateTime(nextBillingDateTimestamp);
+ String address1 = result.getString("address1");
+ String address2 = result.getString("address2");
+ String city = result.getString("city");
+ String stateOrProvince = result.getString("state_or_province");
+ String postalCode = result.getString("postal_code");
+ String country = result.getString("country");
+ String phone = result.getString("phone");
return new AccountBuilder(id).externalKey(externalKey).email(email)
.name(name).firstNameLength(firstNameLength)
.phone(phone).currency(currency)
.billingCycleDay(billingCycleDay)
.paymentProviderName(paymentProviderName)
- .timeZone(timeZone)
- .locale(locale)
- .nextBillingDate(nextBillingDate)
+ .timeZone(timeZone).locale(locale)
+ .address1(address1).address2(address2)
+ .city(city).stateOrProvince(stateOrProvince)
+ .postalCode(postalCode).country(country)
.build();
}
}
@@ -115,7 +118,6 @@ public interface AccountSqlDao extends EntityDao<Account>, Transactional<Account
q.bind("email", account.getEmail());
q.bind("name", account.getName());
q.bind("firstNameLength", account.getFirstNameLength());
- q.bind("phone", account.getPhone());
Currency currency = account.getCurrency();
q.bind("currency", (currency == null) ? null : currency.toString());
@@ -125,11 +127,15 @@ public interface AccountSqlDao extends EntityDao<Account>, Transactional<Account
DateTimeZone timeZone = account.getTimeZone();
q.bind("timeZone", (timeZone == null) ? null : timeZone.toString());
-
q.bind("locale", account.getLocale());
- DateTime nextBillingDate = account.getNextBillingDate();
- q.bind("nextBillingDate", (nextBillingDate == null) ? null : nextBillingDate.toDate());
+ q.bind("address1", account.getAddress1());
+ q.bind("address2", account.getAddress2());
+ q.bind("city", account.getCity());
+ q.bind("stateOrProvince", account.getStateOrProvince());
+ q.bind("country", account.getCountry());
+ q.bind("postalCode", account.getPostalCode());
+ q.bind("phone", account.getPhone());
}
};
}
diff --git a/account/src/main/java/com/ning/billing/account/dao/DefaultAccountDao.java b/account/src/main/java/com/ning/billing/account/dao/DefaultAccountDao.java
index 1724095..5072f90 100644
--- a/account/src/main/java/com/ning/billing/account/dao/DefaultAccountDao.java
+++ b/account/src/main/java/com/ning/billing/account/dao/DefaultAccountDao.java
@@ -21,27 +21,27 @@ import java.util.UUID;
import org.skife.jdbi.v2.IDBI;
import org.skife.jdbi.v2.Transaction;
import org.skife.jdbi.v2.TransactionStatus;
+import org.skife.jdbi.v2.exceptions.TransactionFailedException;
import com.google.inject.Inject;
import com.ning.billing.ErrorCode;
import com.ning.billing.account.api.Account;
import com.ning.billing.account.api.AccountApiException;
import com.ning.billing.account.api.AccountChangeNotification;
import com.ning.billing.account.api.AccountCreationNotification;
-import com.ning.billing.account.api.DefaultAccount;
import com.ning.billing.account.api.user.DefaultAccountChangeNotification;
import com.ning.billing.account.api.user.DefaultAccountCreationEvent;
import com.ning.billing.util.customfield.CustomField;
import com.ning.billing.util.customfield.dao.FieldStoreDao;
import com.ning.billing.util.eventbus.EventBus;
import com.ning.billing.util.tag.Tag;
-import com.ning.billing.util.tag.dao.TagStoreDao;
+import com.ning.billing.util.tag.dao.TagStoreSqlDao;
public class DefaultAccountDao implements AccountDao {
private final AccountSqlDao accountDao;
private final EventBus eventBus;
@Inject
- public DefaultAccountDao(IDBI dbi, EventBus eventBus) {
+ public DefaultAccountDao(final IDBI dbi, final EventBus eventBus) {
this.eventBus = eventBus;
this.accountDao = dbi.onDemand(AccountSqlDao.class);
}
@@ -50,36 +50,22 @@ public class DefaultAccountDao implements AccountDao {
public Account getAccountByKey(final String key) {
return accountDao.inTransaction(new Transaction<Account, AccountSqlDao>() {
@Override
- public Account inTransaction(AccountSqlDao accountSqlDao, TransactionStatus status) throws Exception {
+ public Account inTransaction(final AccountSqlDao accountSqlDao, final TransactionStatus status) throws Exception {
Account account = accountSqlDao.getAccountByKey(key);
-
if (account != null) {
- FieldStoreDao fieldStoreDao = accountSqlDao.become(FieldStoreDao.class);
- List<CustomField> fields = fieldStoreDao.load(account.getId().toString(), account.getObjectName());
-
- account.clearFields();
- if (fields != null) {
- for (CustomField field : fields) {
- account.setFieldValue(field.getName(), field.getValue());
- }
- }
-
- TagStoreDao tagStoreDao = fieldStoreDao.become(TagStoreDao.class);
- List<Tag> tags = tagStoreDao.load(account.getId().toString(), account.getObjectName());
- account.clearTags();
-
- if (tags != null) {
- account.addTags(tags);
- }
+ setCustomFieldsFromWithinTransaction(account, accountSqlDao);
+ setTagsFromWithinTransaction(account, accountSqlDao);
}
-
return account;
}
});
}
@Override
- public UUID getIdFromKey(final String externalKey) {
+ public UUID getIdFromKey(final String externalKey) throws AccountApiException {
+ if (externalKey == null) {
+ throw new AccountApiException(ErrorCode.ACCOUNT_CANNOT_MAP_NULL_KEY, "");
+ }
return accountDao.getIdFromKey(externalKey);
}
@@ -87,122 +73,136 @@ public class DefaultAccountDao implements AccountDao {
public Account getById(final String id) {
return accountDao.inTransaction(new Transaction<Account, AccountSqlDao>() {
@Override
- public Account inTransaction(AccountSqlDao accountSqlDao, TransactionStatus status) throws Exception {
+ public Account inTransaction(final AccountSqlDao accountSqlDao, final TransactionStatus status) throws Exception {
Account account = accountSqlDao.getById(id);
-
if (account != null) {
- FieldStoreDao fieldStoreDao = accountSqlDao.become(FieldStoreDao.class);
- List<CustomField> fields = fieldStoreDao.load(account.getId().toString(), account.getObjectName());
-
- account.clearFields();
- if (fields != null) {
- for (CustomField field : fields) {
- account.setFieldValue(field.getName(), field.getValue());
- }
- }
-
- TagStoreDao tagStoreDao = fieldStoreDao.become(TagStoreDao.class);
- List<Tag> tags = tagStoreDao.load(account.getId().toString(), account.getObjectName());
- account.clearTags();
-
- if (tags != null) {
- account.addTags(tags);
- }
+ setCustomFieldsFromWithinTransaction(account, accountSqlDao);
+ setTagsFromWithinTransaction(account, accountSqlDao);
}
-
return account;
}
});
}
+
@Override
public List<Account> get() {
return accountDao.get();
}
@Override
- public void test() {
- accountDao.test();
- }
-
- @Override
public void create(final Account account) {
final String key = account.getExternalKey();
- final String objectType = DefaultAccount.OBJECT_TYPE;
accountDao.inTransaction(new Transaction<Void, AccountSqlDao>() {
@Override
- public Void inTransaction(AccountSqlDao accountDao, TransactionStatus status) throws Exception {
- Account currentAccount = accountDao.getAccountByKey(key);
+ public Void inTransaction(final AccountSqlDao accountSqlDao, final TransactionStatus status) throws Exception {
+ Account currentAccount = accountSqlDao.getAccountByKey(key);
if (currentAccount != null) {
- throw new AccountApiException(ErrorCode.ACCOUNT_ALREADY_EXISTS, account.getExternalKey());
+ throw new AccountApiException(ErrorCode.ACCOUNT_ALREADY_EXISTS, key);
}
+ accountSqlDao.create(account);
- accountDao.create(account);
-
- String accountId = account.getId().toString();
- FieldStoreDao fieldStoreDao = accountDao.become(FieldStoreDao.class);
-
- List<CustomField> fieldList = account.getFieldList();
- if (fieldList != null) {
- fieldStoreDao.save(accountId, objectType, account.getFieldList());
- }
-
- TagStoreDao tagStoreDao = fieldStoreDao.become(TagStoreDao.class);
-
- List<Tag> tagList = account.getTagList();
- if (tagList != null) {
- tagStoreDao.save(accountId, objectType, account.getTagList());
- }
+ saveTagsFromWithinTransaction(account, accountSqlDao, true);
+ saveCustomFieldsFromWithinTransaction(account, accountSqlDao, true);
AccountCreationNotification creationEvent = new DefaultAccountCreationEvent(account);
eventBus.post(creationEvent);
-
return null;
}
});
}
@Override
- public void update(final Account account) {
- final String key = account.getExternalKey();
- final String objectType = DefaultAccount.OBJECT_TYPE;
+ public void update(final Account account) throws AccountApiException {
+ try {
+ accountDao.inTransaction(new Transaction<Void, AccountSqlDao>() {
+ @Override
+ public Void inTransaction(final AccountSqlDao accountSqlDao, final TransactionStatus status) throws AccountApiException, EventBus.EventBusException {
+ String accountId = account.getId().toString();
+ Account currentAccount = accountSqlDao.getById(accountId);
+ if (currentAccount == null) {
+ throw new AccountApiException(ErrorCode.ACCOUNT_DOES_NOT_EXIST_FOR_ID, accountId);
+ }
- accountDao.inTransaction(new Transaction<Void, AccountSqlDao>() {
- @Override
- public Void inTransaction(AccountSqlDao accountDao, TransactionStatus status) throws Exception {
- Account currentAccount = accountDao.getAccountByKey(key);
+ String currentKey = currentAccount.getExternalKey();
+ if (!currentKey.equals(account.getExternalKey())) {
+ throw new AccountApiException(ErrorCode.ACCOUNT_CANNOT_CHANGE_EXTERNAL_KEY, currentKey);
+ }
- if (currentAccount == null) {
- throw new AccountApiException(ErrorCode.ACCOUNT_DOES_NOT_EXIST, key);
+ accountSqlDao.update(account);
+
+ saveTagsFromWithinTransaction(account, accountSqlDao, false);
+ saveCustomFieldsFromWithinTransaction(account, accountSqlDao, false);
+
+ AccountChangeNotification changeEvent = new DefaultAccountChangeNotification(account.getId(), currentAccount, account);
+ if (changeEvent.hasChanges()) {
+ eventBus.post(changeEvent);
+ }
+ return null;
}
+ });
+ } catch (RuntimeException t) {
+ if (t.getCause() instanceof AccountApiException) {
+ throw (AccountApiException) t.getCause();
+ } else {
+ throw t;
+ }
+ }
+ }
+
+ @Override
+ public void test() {
+ accountDao.test();
+ }
- accountDao.update(account);
+ private void setCustomFieldsFromWithinTransaction(final Account account, final AccountSqlDao transactionalDao) {
+ FieldStoreDao fieldStoreDao = transactionalDao.become(FieldStoreDao.class);
+ List<CustomField> fields = fieldStoreDao.load(account.getId().toString(), account.getObjectName());
- String accountId = account.getId().toString();
- FieldStoreDao fieldStoreDao = accountDao.become(FieldStoreDao.class);
- fieldStoreDao.clear(accountId, objectType);
+ account.clearFields();
+ if (fields != null) {
+ account.addFields(fields);
+ }
+ }
- List<CustomField> fieldList = account.getFieldList();
- if (fieldList != null) {
- fieldStoreDao.save(accountId, objectType, account.getFieldList());
- }
+ private void setTagsFromWithinTransaction(final Account account, final AccountSqlDao transactionalDao) {
+ TagStoreSqlDao tagStoreDao = transactionalDao.become(TagStoreSqlDao.class);
+ List<Tag> tags = tagStoreDao.load(account.getId().toString(), account.getObjectName());
+ account.clearTags();
- TagStoreDao tagStoreDao = fieldStoreDao.become(TagStoreDao.class);
- tagStoreDao.clear(accountId, objectType);
+ if (tags != null) {
+ account.addTags(tags);
+ }
+ }
- List<Tag> tagList = account.getTagList();
- if (tagList != null) {
- tagStoreDao.save(accountId, objectType, tagList);
- }
+ private void saveCustomFieldsFromWithinTransaction(final Account account, final AccountSqlDao transactionalDao, final boolean isCreation) {
+ String accountId = account.getId().toString();
+ String objectType = account.getObjectName();
- AccountChangeNotification changeEvent = new DefaultAccountChangeNotification(account.getId(), currentAccount, account);
- if (changeEvent.hasChanges()) {
- eventBus.post(changeEvent);
- }
+ TagStoreSqlDao tagStoreDao = transactionalDao.become(TagStoreSqlDao.class);
+ if (!isCreation) {
+ tagStoreDao.clear(accountId, objectType);
+ }
- return null;
- }
- });
+ List<Tag> tagList = account.getTagList();
+ if (tagList != null) {
+ tagStoreDao.save(accountId, objectType, tagList);
+ }
+ }
+
+ private void saveTagsFromWithinTransaction(final Account account, final AccountSqlDao transactionalDao, final boolean isCreation) {
+ String accountId = account.getId().toString();
+ String objectType = account.getObjectName();
+
+ FieldStoreDao fieldStoreDao = transactionalDao.become(FieldStoreDao.class);
+ if (!isCreation) {
+ fieldStoreDao.clear(accountId, objectType);
+ }
+
+ List<CustomField> fieldList = account.getFieldList();
+ if (fieldList != null) {
+ fieldStoreDao.save(accountId, objectType, fieldList);
+ }
}
}
diff --git a/account/src/main/resources/com/ning/billing/account/dao/AccountSqlDao.sql.stg b/account/src/main/resources/com/ning/billing/account/dao/AccountSqlDao.sql.stg
index 097a0b6..e684869 100644
--- a/account/src/main/resources/com/ning/billing/account/dao/AccountSqlDao.sql.stg
+++ b/account/src/main/resources/com/ning/billing/account/dao/AccountSqlDao.sql.stg
@@ -2,38 +2,45 @@ group AccountDaoSql;
create() ::= <<
INSERT INTO accounts
- (id, external_key, email, name, first_name_length, phone, currency, billing_cycle_day,
- payment_provider_name, time_zone, locale, next_billing_date)
+ (id, external_key, email, name, first_name_length, currency, billing_cycle_day,
+ payment_provider_name, time_zone, locale,
+ address1, address2, city, state_or_province, country, postal_code, phone)
VALUES
- (:id, :externalKey, :email, :name, :firstNameLength, :phone, :currency, :billingCycleDay,
- :paymentProviderName, :timeZone, :locale, :nextBillingDate);
+ (:id, :externalKey, :email, :name, :firstNameLength, :currency, :billingCycleDay,
+ :paymentProviderName, :timeZone, :locale,
+ :address1, :address2, :city, :stateOrProvince, :country, :postalCode, :phone);
>>
update() ::= <<
UPDATE accounts
- SET email = :email, name = :name, first_name_length = :firstNameLength, phone = :phone,
+ SET external_key = :externalKey, email = :email, name = :name, first_name_length = :firstNameLength,
currency = :currency, billing_cycle_day = :billingCycleDay, payment_provider_name = :paymentProviderName,
- time_zone = :timeZone, locale = :locale, next_billing_date = :nextBillingDate
- WHERE id = :id AND external_key = :externalKey;
+ time_zone = :timeZone, locale = :locale,
+ address1 = :address1, address2 = :address2, city = :city, state_or_province = :stateOrProvince,
+ country = :country, postal_code = :postalCode, phone = :phone
+ WHERE id = :id;
>>
getAccountByKey() ::= <<
- select id, external_key, email, name, first_name_length, phone, currency, billing_cycle_day,
- payment_provider_name, time_zone, locale, next_billing_date
+ select id, external_key, email, name, first_name_length, currency, billing_cycle_day,
+ payment_provider_name, time_zone, locale,
+ address1, address2, city, state_or_province, country, postal_code, phone
from accounts
where external_key = :externalKey;
>>
getById() ::= <<
- select id, external_key, email, name, first_name_length, phone, currency, billing_cycle_day,
- payment_provider_name, time_zone, locale, next_billing_date
+ select id, external_key, email, name, first_name_length, currency, billing_cycle_day,
+ payment_provider_name, time_zone, locale,
+ address1, address2, city, state_or_province, country, postal_code, phone
from accounts
where id = :id;
>>
get() ::= <<
- select id, external_key, email, name, first_name_length, phone, currency, billing_cycle_day,
- payment_provider_name, time_zone, locale, next_billing_date
+ select id, external_key, email, name, first_name_length, currency, billing_cycle_day,
+ payment_provider_name, time_zone, locale,
+ address1, address2, city, state_or_province, country, postal_code, phone
from accounts;
>>
diff --git a/account/src/main/resources/com/ning/billing/account/ddl.sql b/account/src/main/resources/com/ning/billing/account/ddl.sql
index e8b0bcc..2458ab0 100644
--- a/account/src/main/resources/com/ning/billing/account/ddl.sql
+++ b/account/src/main/resources/com/ning/billing/account/ddl.sql
@@ -5,13 +5,18 @@ CREATE TABLE accounts (
email varchar(50) NOT NULL,
name varchar(100) NOT NULL,
first_name_length int NOT NULL,
- phone varchar(13) DEFAULT NULL,
currency char(3) DEFAULT NULL,
billing_cycle_day int DEFAULT NULL,
payment_provider_name varchar(20) DEFAULT NULL,
time_zone varchar(50) DEFAULT NULL,
locale varchar(5) DEFAULT NULL,
- next_billing_date datetime DEFAULT NULL,
+ address1 varchar(100) DEFAULT NULL,
+ address2 varchar(100) DEFAULT NULL,
+ city varchar(50) DEFAULT NULL,
+ state_or_province varchar(50) DEFAULT NULL,
+ country varchar(50) DEFAULT NULL,
+ postal_code varchar(11) DEFAULT NULL,
+ phone varchar(13) DEFAULT NULL,
PRIMARY KEY(id)
) ENGINE=innodb;
CREATE UNIQUE INDEX accounts_external_key ON accounts(external_key);
diff --git a/account/src/test/java/com/ning/billing/account/dao/TestSimpleAccountDao.java b/account/src/test/java/com/ning/billing/account/dao/TestSimpleAccountDao.java
index 2ecbe48..649aa35 100644
--- a/account/src/test/java/com/ning/billing/account/dao/TestSimpleAccountDao.java
+++ b/account/src/test/java/com/ning/billing/account/dao/TestSimpleAccountDao.java
@@ -25,28 +25,26 @@ import com.ning.billing.account.api.Account;
import com.ning.billing.account.api.AccountApiException;
import com.ning.billing.account.api.AccountData;
import com.ning.billing.account.api.DefaultAccount;
-import com.ning.billing.util.tag.DefaultTagDescription;
+import com.ning.billing.util.tag.DefaultTagDefinition;
import com.ning.billing.util.tag.Tag;
-import com.ning.billing.util.tag.TagDescription;
+import com.ning.billing.util.tag.TagDefinition;
import com.ning.billing.account.api.user.AccountBuilder;
import com.ning.billing.catalog.api.Currency;
import com.ning.billing.util.clock.DefaultClock;
-import com.ning.billing.util.tag.dao.TagDescriptionDao;
+import com.ning.billing.util.tag.dao.TagDefinitionSqlDao;
import static org.testng.Assert.assertEquals;
import static org.testng.Assert.assertNotNull;
import static org.testng.Assert.assertTrue;
+import static org.testng.Assert.fail;
@Test(groups = {"account-dao"})
public class TestSimpleAccountDao extends AccountDaoTestBase {
- private final String key = "test1234";
- private final String firstName = "Wesley";
- private final String email = "me@me.com";
-
private DefaultAccount createTestAccount() {
- String thisKey = key + UUID.randomUUID().toString();
+ String thisKey = "test" + UUID.randomUUID().toString();
String lastName = UUID.randomUUID().toString();
- String thisEmail = email + " " + UUID.randomUUID();
+ String thisEmail = "me@me.com" + " " + UUID.randomUUID();
+ String firstName = "Bob";
String name = firstName + " " + lastName;
String phone = "123-456-7890";
String locale = "EN-US";
@@ -114,13 +112,13 @@ public class TestSimpleAccountDao extends AccountDaoTestBase {
@Test
public void testTags() {
Account account = createTestAccount();
- TagDescription description = new DefaultTagDescription("Test Tag", "For testing only", true, true, "Test System", new DateTime());
- TagDescriptionDao tagDescriptionDao = dbi.onDemand(TagDescriptionDao.class);
- tagDescriptionDao.create(description);
+ TagDefinition definition = new DefaultTagDefinition("Test Tag", "For testing only", "Test System", new DateTime());
+ TagDefinitionSqlDao tagDescriptionDao = dbi.onDemand(TagDefinitionSqlDao.class);
+ tagDescriptionDao.create(definition);
String addedBy = "testTags()";
DateTime dateAdded = new DefaultClock().getUTCNow();
- account.addTag(description, addedBy, dateAdded);
+ account.addTag(definition, addedBy, dateAdded);
assertEquals(account.getTagList().size(), 1);
accountDao.create(account);
@@ -128,12 +126,9 @@ public class TestSimpleAccountDao extends AccountDaoTestBase {
List<Tag> tagList = thisAccount.getTagList();
assertEquals(tagList.size(), 1);
Tag tag = tagList.get(0);
- assertEquals(tag.getName(), description.getName());
- assertEquals(tag.getGenerateInvoice(), description.getGenerateInvoice());
- assertEquals(tag.getProcessPayment(), description.getProcessPayment());
- assertEquals(tag.getTagDescriptionId(), description.getId());
+ assertEquals(tag.getTagDefinitionName(), definition.getName());
assertEquals(tag.getAddedBy(), addedBy);
- assertEquals(tag.getDateAdded().compareTo(dateAdded), 0);
+ assertEquals(tag.getAddedDate().compareTo(dateAdded), 0);
}
@Test
@@ -141,12 +136,21 @@ public class TestSimpleAccountDao extends AccountDaoTestBase {
Account account = createTestAccount();
accountDao.create(account);
- UUID accountId = accountDao.getIdFromKey(account.getExternalKey());
- assertEquals(accountId, account.getId());
+ try {
+ UUID accountId = accountDao.getIdFromKey(account.getExternalKey());
+ assertEquals(accountId, account.getId());
+ } catch (AccountApiException a) {
+ fail("Retrieving account failed.");
+ }
+ }
+
+ @Test(expectedExceptions = AccountApiException.class)
+ public void testGetIdFromKeyForNullKey() throws AccountApiException {
+ accountDao.getIdFromKey(null);
}
@Test
- public void testUpdate() throws AccountApiException {
+ public void testUpdate() throws Exception {
final Account account = createTestAccount();
accountDao.create(account);
@@ -192,9 +196,33 @@ public class TestSimpleAccountDao extends AccountDaoTestBase {
public String getLocale() {
return "FR-CA";
}
+ @Override
+ public String getAddress1() {
+ return null;
+ }
+
+ @Override
+ public String getAddress2() {
+ return null;
+ }
+
+ @Override
+ public String getCity() {
+ return null;
+ }
@Override
- public DateTime getNextBillingDate() {
+ public String getStateOrProvince() {
+ return null;
+ }
+
+ @Override
+ public String getPostalCode() {
+ return null;
+ }
+
+ @Override
+ public String getCountry() {
return null;
}
};
@@ -207,11 +235,102 @@ public class TestSimpleAccountDao extends AccountDaoTestBase {
assertNotNull(savedAccount);
assertEquals(savedAccount.getName(), updatedAccount.getName());
assertEquals(savedAccount.getEmail(), updatedAccount.getEmail());
- assertEquals(savedAccount.getPhone(), updatedAccount.getPhone());
assertEquals(savedAccount.getPaymentProviderName(), updatedAccount.getPaymentProviderName());
assertEquals(savedAccount.getBillCycleDay(), updatedAccount.getBillCycleDay());
assertEquals(savedAccount.getFirstNameLength(), updatedAccount.getFirstNameLength());
assertEquals(savedAccount.getTimeZone(), updatedAccount.getTimeZone());
assertEquals(savedAccount.getLocale(), updatedAccount.getLocale());
+ assertEquals(savedAccount.getAddress1(), updatedAccount.getAddress1());
+ assertEquals(savedAccount.getAddress2(), updatedAccount.getAddress2());
+ assertEquals(savedAccount.getCity(), updatedAccount.getCity());
+ assertEquals(savedAccount.getStateOrProvince(), updatedAccount.getStateOrProvince());
+ assertEquals(savedAccount.getCountry(), updatedAccount.getCountry());
+ assertEquals(savedAccount.getPostalCode(), updatedAccount.getPostalCode());
+ assertEquals(savedAccount.getPhone(), updatedAccount.getPhone());
+ }
+
+ @Test
+ public void testAddingContactInformation() throws Exception {
+ UUID accountId = UUID.randomUUID();
+ DefaultAccount account = new DefaultAccount(accountId, "extKey123456", "myemail123456@glam.com",
+ "John Smith", 4, Currency.USD, 15, null,
+ DateTimeZone.forID("America/Cambridge_Bay"), "EN-CA",
+ null, null, null, null, null, null, null);
+ accountDao.create(account);
+
+ String address1 = "123 address 1";
+ String address2 = "456 address 2";
+ String city = "Cambridge Bay";
+ String stateOrProvince = "Nunavut";
+ String country = "Canada";
+ String postalCode = "X0B 0C0";
+ String phone = "18001112222";
+
+ DefaultAccount updatedAccount = new DefaultAccount(accountId, "extKey123456", "myemail123456@glam.com",
+ "John Smith", 4, Currency.USD, 15, null,
+ DateTimeZone.forID("America/Cambridge_Bay"), "EN-CA",
+ address1, address2, city, stateOrProvince, country,
+ postalCode, phone);
+
+ accountDao.update(updatedAccount);
+
+ Account savedAccount = accountDao.getById(accountId.toString());
+
+ assertNotNull(savedAccount);
+ assertEquals(savedAccount.getId(), accountId);
+ assertEquals(savedAccount.getAddress1(), address1);
+ assertEquals(savedAccount.getAddress2(), address2);
+ assertEquals(savedAccount.getCity(), city);
+ assertEquals(savedAccount.getStateOrProvince(), stateOrProvince);
+ assertEquals(savedAccount.getCity(), city);
+ assertEquals(savedAccount.getPostalCode(), postalCode);
+ assertEquals(savedAccount.getPhone(), phone);
+ }
+
+ @Test
+ public void testRemovingContactInformation() throws Exception {
+ UUID accountId = UUID.randomUUID();
+
+ DefaultAccount account = new DefaultAccount(accountId, "extKey654321", "myemail654321@glam.com",
+ "John Smith", 4, Currency.USD, 15, null,
+ DateTimeZone.forID("America/Cambridge_Bay"), "EN-CA",
+ "123 address 1", "456 address 2", "Cambridge Bay",
+ "Nunavut", "Canada", "X0B 0C0", "18001112222");
+ accountDao.create(account);
+
+ DefaultAccount updatedAccount = new DefaultAccount(accountId, "extKey654321", "myemail654321@glam.com",
+ "John Smith", 4, Currency.USD, 15, null,
+ DateTimeZone.forID("America/Cambridge_Bay"), "EN-CA",
+ null, null, null, null, null, null, null);
+
+ accountDao.update(updatedAccount);
+
+ Account savedAccount = accountDao.getById(accountId.toString());
+
+ assertNotNull(savedAccount);
+ assertEquals(savedAccount.getId(), accountId);
+ assertEquals(savedAccount.getAddress1(), null);
+ assertEquals(savedAccount.getAddress2(), null);
+ assertEquals(savedAccount.getCity(), null);
+ assertEquals(savedAccount.getStateOrProvince(), null);
+ assertEquals(savedAccount.getCity(), null);
+ assertEquals(savedAccount.getPostalCode(), null);
+ assertEquals(savedAccount.getPhone(), null);
+ }
+
+ @Test(expectedExceptions = AccountApiException.class)
+ public void testExternalKeyCannotBeUpdated() throws Exception {
+ UUID accountId = UUID.randomUUID();
+ String originalExternalKey = "extKey1337";
+
+ DefaultAccount account = new DefaultAccount(accountId, originalExternalKey, "myemail1337@glam.com",
+ "John Smith", 4, Currency.USD, 15, null,
+ null, null, null, null, null, null, null, null, null);
+ accountDao.create(account);
+
+ DefaultAccount updatedAccount = new DefaultAccount(accountId, "extKey1338", "myemail1337@glam.com",
+ "John Smith", 4, Currency.USD, 15, null,
+ null, null, null, null, null, null, null, null, null);
+ accountDao.update(updatedAccount);
}
}
diff --git a/analytics/src/main/java/com/ning/billing/analytics/BusinessAccountRecorder.java b/analytics/src/main/java/com/ning/billing/analytics/BusinessAccountRecorder.java
index 23fbcf4..f7081c7 100644
--- a/analytics/src/main/java/com/ning/billing/analytics/BusinessAccountRecorder.java
+++ b/analytics/src/main/java/com/ning/billing/analytics/BusinessAccountRecorder.java
@@ -50,7 +50,7 @@ public class BusinessAccountRecorder
final List<String> tags = new ArrayList<String>();
for (final Tag tag : account.getTagList()) {
- tags.add(tag.getName());
+ tags.add(tag.getTagDefinitionName());
}
// TODO Need payment and invoice api to fill most fields
diff --git a/analytics/src/test/java/com/ning/billing/analytics/api/TestAnalyticsService.java b/analytics/src/test/java/com/ning/billing/analytics/api/TestAnalyticsService.java
index c146de7..621243f 100644
--- a/analytics/src/test/java/com/ning/billing/analytics/api/TestAnalyticsService.java
+++ b/analytics/src/test/java/com/ning/billing/analytics/api/TestAnalyticsService.java
@@ -48,10 +48,10 @@ import com.ning.billing.entitlement.api.user.SubscriptionTransitionData;
import com.ning.billing.entitlement.events.EntitlementEvent;
import com.ning.billing.entitlement.events.user.ApiEventType;
import com.ning.billing.util.eventbus.EventBus;
-import com.ning.billing.util.tag.DefaultTag;
-import com.ning.billing.util.tag.DefaultTagDescription;
+import com.ning.billing.util.tag.DescriptiveTag;
+import com.ning.billing.util.tag.DefaultTagDefinition;
import com.ning.billing.util.tag.Tag;
-import com.ning.billing.util.tag.dao.TagDescriptionDao;
+import com.ning.billing.util.tag.dao.TagDefinitionSqlDao;
import org.apache.commons.io.IOUtils;
import org.joda.time.DateTime;
import org.joda.time.DateTimeZone;
@@ -74,8 +74,8 @@ public class TestAnalyticsService
{
private static final String KEY = "12345";
private static final String ACCOUNT_KEY = "pierre-12345";
- private static final DefaultTagDescription TAG_ONE = new DefaultTagDescription("batch20", "something", false, false, "pierre", new DateTime(DateTimeZone.UTC));
- private static final DefaultTagDescription TAG_TWO = new DefaultTagDescription("awesome", "something", false, false, "pierre", new DateTime(DateTimeZone.UTC));
+ private static final DefaultTagDefinition TAG_ONE = new DefaultTagDefinition("batch20", "something", "pierre", new DateTime(DateTimeZone.UTC));
+ private static final DefaultTagDefinition TAG_TWO = new DefaultTagDefinition("awesome", "something", "pierre", new DateTime(DateTimeZone.UTC));
@Inject
private AccountUserApi accountApi;
@@ -84,7 +84,7 @@ public class TestAnalyticsService
private EntitlementUserApi entitlementApi;
@Inject
- private TagDescriptionDao tagDao;
+ private TagDefinitionSqlDao tagDao;
@Inject
private AnalyticsService service;
@@ -118,8 +118,8 @@ public class TestAnalyticsService
final MockAccount account = new MockAccount(UUID.randomUUID(), ACCOUNT_KEY, Currency.USD);
try {
List<Tag> tags = new ArrayList<Tag>();
- tags.add(new DefaultTag(TAG_ONE, "pierre", new DateTime(DateTimeZone.UTC)));
- tags.add(new DefaultTag(TAG_TWO, "pierre", new DateTime(DateTimeZone.UTC)));
+ tags.add(new DescriptiveTag(TAG_ONE, "pierre", new DateTime(DateTimeZone.UTC)));
+ tags.add(new DescriptiveTag(TAG_TWO, "pierre", new DateTime(DateTimeZone.UTC)));
final Account storedAccount = accountApi.createAccount(account, null, tags);
diff --git a/analytics/src/test/java/com/ning/billing/analytics/MockAccount.java b/analytics/src/test/java/com/ning/billing/analytics/MockAccount.java
index 7488d5b..029be49 100644
--- a/analytics/src/test/java/com/ning/billing/analytics/MockAccount.java
+++ b/analytics/src/test/java/com/ning/billing/analytics/MockAccount.java
@@ -18,17 +18,15 @@ package com.ning.billing.analytics;
import sun.reflect.generics.reflectiveObjects.NotImplementedException;
-import java.math.BigDecimal;
import java.util.List;
import java.util.UUID;
import org.joda.time.DateTime;
import org.joda.time.DateTimeZone;
import com.ning.billing.account.api.Account;
-import com.ning.billing.account.api.AccountData;
import com.ning.billing.catalog.api.Currency;
import com.ning.billing.util.customfield.CustomField;
import com.ning.billing.util.tag.Tag;
-import com.ning.billing.util.tag.TagDescription;
+import com.ning.billing.util.tag.TagDefinition;
public class MockAccount implements Account
{
@@ -99,7 +97,32 @@ public class MockAccount implements Account
}
@Override
- public DateTime getNextBillingDate() {
+ public String getAddress1() {
+ return null;
+ }
+
+ @Override
+ public String getAddress2() {
+ return null;
+ }
+
+ @Override
+ public String getCity() {
+ return null;
+ }
+
+ @Override
+ public String getStateOrProvince() {
+ return null;
+ }
+
+ @Override
+ public String getPostalCode() {
+ return null;
+ }
+
+ @Override
+ public String getCountry() {
return null;
}
@@ -150,7 +173,7 @@ public class MockAccount implements Account
}
@Override
- public void addTag(TagDescription description, String addedBy, DateTime dateAdded) {
+ public void addTag(TagDefinition description, String addedBy, DateTime dateAdded) {
throw new NotImplementedException();
}
@@ -165,7 +188,7 @@ public class MockAccount implements Account
}
@Override
- public void removeTag(TagDescription description) {
+ public void removeTag(TagDefinition description) {
throw new NotImplementedException();
}
@@ -178,9 +201,4 @@ public class MockAccount implements Account
public boolean processPayment() {
throw new NotImplementedException();
}
-
- @Override
- public BigDecimal getBalance() {
- return BigDecimal.ZERO;
- }
}
diff --git a/api/src/main/java/com/ning/billing/account/api/Account.java b/api/src/main/java/com/ning/billing/account/api/Account.java
index 543f280..065ed3c 100644
--- a/api/src/main/java/com/ning/billing/account/api/Account.java
+++ b/api/src/main/java/com/ning/billing/account/api/Account.java
@@ -21,5 +21,4 @@ import com.ning.billing.util.customfield.CustomizableEntity;
import com.ning.billing.util.tag.Taggable;
public interface Account extends AccountData, CustomizableEntity, Taggable {
- public BigDecimal getBalance();
}
diff --git a/api/src/main/java/com/ning/billing/account/api/AccountData.java b/api/src/main/java/com/ning/billing/account/api/AccountData.java
index 62195e5..82f1845 100644
--- a/api/src/main/java/com/ning/billing/account/api/AccountData.java
+++ b/api/src/main/java/com/ning/billing/account/api/AccountData.java
@@ -31,8 +31,6 @@ public interface AccountData {
public String getEmail();
- public String getPhone();
-
public int getBillCycleDay();
public Currency getCurrency();
@@ -43,5 +41,17 @@ public interface AccountData {
public String getLocale();
- public DateTime getNextBillingDate();
+ public String getAddress1();
+
+ public String getAddress2();
+
+ public String getCity();
+
+ public String getStateOrProvince();
+
+ public String getPostalCode();
+
+ public String getCountry();
+
+ public String getPhone();
}
diff --git a/api/src/main/java/com/ning/billing/account/api/AccountUserApi.java b/api/src/main/java/com/ning/billing/account/api/AccountUserApi.java
index a535ada..ef86f38 100644
--- a/api/src/main/java/com/ning/billing/account/api/AccountUserApi.java
+++ b/api/src/main/java/com/ning/billing/account/api/AccountUserApi.java
@@ -25,7 +25,12 @@ public interface AccountUserApi {
public Account createAccount(AccountData data, List<CustomField> fields, List<Tag> tags) throws AccountApiException;
- public void updateAccount(Account account);
+ /***
+ *
+ * Note: does not update the external key
+ * @param account
+ */
+ public void updateAccount(Account account) throws Exception;
public Account getAccountByKey(String key);
@@ -33,5 +38,5 @@ public interface AccountUserApi {
public List<Account> getAccounts();
- public UUID getIdFromKey(String externalKey);
+ public UUID getIdFromKey(String externalKey) throws AccountApiException;
}
diff --git a/api/src/main/java/com/ning/billing/account/api/ControlTagType.java b/api/src/main/java/com/ning/billing/account/api/ControlTagType.java
new file mode 100644
index 0000000..a801c6d
--- /dev/null
+++ b/api/src/main/java/com/ning/billing/account/api/ControlTagType.java
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.account.api;
+
+public enum ControlTagType {
+ AUTO_BILLING_OFF(true, false),
+ AUTO_INVOICING_OFF(false, true);
+
+ private final boolean autoPaymentOff;
+ private final boolean autoInvoicingOff;
+
+ ControlTagType(final boolean autoPaymentOff, final boolean autoInvoicingOff) {
+ this.autoPaymentOff = autoPaymentOff;
+ this.autoInvoicingOff = autoInvoicingOff;
+ }
+
+ public boolean autoPaymentOff() {
+ return this.autoPaymentOff;
+ }
+
+ public boolean autoInvoicingOff() {
+ return this.autoInvoicingOff;
+ }
+}
diff --git a/api/src/main/java/com/ning/billing/ErrorCode.java b/api/src/main/java/com/ning/billing/ErrorCode.java
index cfff7a7..b1c93d2 100644
--- a/api/src/main/java/com/ning/billing/ErrorCode.java
+++ b/api/src/main/java/com/ning/billing/ErrorCode.java
@@ -91,7 +91,21 @@ public enum ErrorCode {
*/
ACCOUNT_ALREADY_EXISTS(3000, "Account already exists for key %s"),
ACCOUNT_INVALID_NAME(3001, "An invalid name was specified when creating or updating an account."),
- ACCOUNT_DOES_NOT_EXIST(3002, "Account does not exist for key %s")
+ ACCOUNT_DOES_NOT_EXIST_FOR_ID(3002, "Account does not exist for id %s"),
+ ACCOUNT_DOES_NOT_EXIST_FOR_KEY(3003, "Account does not exist for key %s"),
+ ACCOUNT_CANNOT_MAP_NULL_KEY(3004, "An attempt was made to get the id for a <null> external key."),
+ ACCOUNT_CANNOT_CHANGE_EXTERNAL_KEY(3005, "External keys cannot be updated. Original key remains: %s"),
+
+ /*
+ *
+ * Range 3900: Tag definitions
+ *
+ */
+ TAG_DEFINITION_CONFLICTS_WITH_CONTROL_TAG(3900, "The tag definition name conflicts with a reserved name (name %s)"),
+ TAG_DEFINITION_ALREADY_EXISTS(3901, "The tag definition name already exists (name: %s)"),
+ TAG_DEFINITION_DOES_NOT_EXIST(3902, "The tag definition name does not exist (name: %s)"),
+ TAG_DEFINITION_IN_USE(3903, "The tag definition name is currently in use (name: %s)")
+
;
private int code;
diff --git a/api/src/main/java/com/ning/billing/util/api/TagDefinitionApiException.java b/api/src/main/java/com/ning/billing/util/api/TagDefinitionApiException.java
new file mode 100644
index 0000000..81750cb
--- /dev/null
+++ b/api/src/main/java/com/ning/billing/util/api/TagDefinitionApiException.java
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.api;
+
+import com.ning.billing.BillingExceptionBase;
+import com.ning.billing.ErrorCode;
+
+public class TagDefinitionApiException extends BillingExceptionBase {
+ public TagDefinitionApiException(Throwable cause, int code, final String msg) {
+ super(cause, code, msg);
+ }
+
+ public TagDefinitionApiException(Throwable cause, ErrorCode code, final Object... args) {
+ super(cause, code, args);
+ }
+
+ public TagDefinitionApiException(ErrorCode code, final Object... args) {
+ super(code, args);
+ }
+}
\ No newline at end of file
diff --git a/api/src/main/java/com/ning/billing/util/api/TagDefinitionUserApi.java b/api/src/main/java/com/ning/billing/util/api/TagDefinitionUserApi.java
new file mode 100644
index 0000000..c38a7b3
--- /dev/null
+++ b/api/src/main/java/com/ning/billing/util/api/TagDefinitionUserApi.java
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.api;
+
+import java.util.UUID;
+import com.ning.billing.util.tag.TagDefinition;
+
+public interface TagDefinitionUserApi {
+ public TagDefinition create(String name, String description, String createdBy) throws TagDefinitionApiException;
+
+ public void deleteAllTagsForDefinition(String definitionName) throws TagDefinitionApiException;
+
+ public void deleteTagDefinition(String definitionName) throws TagDefinitionApiException;
+}
diff --git a/api/src/main/java/com/ning/billing/util/tag/ControlTag.java b/api/src/main/java/com/ning/billing/util/tag/ControlTag.java
new file mode 100644
index 0000000..a933cff
--- /dev/null
+++ b/api/src/main/java/com/ning/billing/util/tag/ControlTag.java
@@ -0,0 +1,23 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag;
+
+import com.ning.billing.account.api.ControlTagType;
+
+public interface ControlTag extends Tag {
+ public ControlTagType getControlTagType();
+}
diff --git a/api/src/main/java/com/ning/billing/util/tag/Tag.java b/api/src/main/java/com/ning/billing/util/tag/Tag.java
index 9fb15ed..5e9008b 100644
--- a/api/src/main/java/com/ning/billing/util/tag/Tag.java
+++ b/api/src/main/java/com/ning/billing/util/tag/Tag.java
@@ -21,15 +21,9 @@ import org.joda.time.DateTime;
import com.ning.billing.util.entity.Entity;
public interface Tag extends Entity {
- UUID getTagDescriptionId();
-
- String getName();
-
- boolean getProcessPayment();
-
- boolean getGenerateInvoice();
+ String getTagDefinitionName();
String getAddedBy();
- DateTime getDateAdded();
+ DateTime getAddedDate();
}
diff --git a/api/src/main/java/com/ning/billing/util/tag/Taggable.java b/api/src/main/java/com/ning/billing/util/tag/Taggable.java
index f274294..ce6a380 100644
--- a/api/src/main/java/com/ning/billing/util/tag/Taggable.java
+++ b/api/src/main/java/com/ning/billing/util/tag/Taggable.java
@@ -22,10 +22,10 @@ import org.joda.time.DateTime;
public interface Taggable {
public List<Tag> getTagList();
public boolean hasTag(String tagName);
- public void addTag(TagDescription description, String addedBy, DateTime dateAdded);
+ public void addTag(TagDefinition description, String addedBy, DateTime dateAdded);
public void addTags(List<Tag> tags);
public void clearTags();
- public void removeTag(TagDescription description);
+ public void removeTag(TagDefinition description);
public boolean generateInvoice();
public boolean processPayment();
}
diff --git a/entitlement/src/test/java/com/ning/billing/entitlement/api/TestApiBase.java b/entitlement/src/test/java/com/ning/billing/entitlement/api/TestApiBase.java
index 9e06be2..78607e6 100644
--- a/entitlement/src/test/java/com/ning/billing/entitlement/api/TestApiBase.java
+++ b/entitlement/src/test/java/com/ning/billing/entitlement/api/TestApiBase.java
@@ -322,8 +322,33 @@ public abstract class TestApiBase {
}
@Override
- public DateTime getNextBillingDate() {
- return null;
+ public String getAddress1() {
+ return null;
+ }
+
+ @Override
+ public String getAddress2() {
+ return null;
+ }
+
+ @Override
+ public String getCity() {
+ return null;
+ }
+
+ @Override
+ public String getStateOrProvince() {
+ return null;
+ }
+
+ @Override
+ public String getPostalCode() {
+ return null;
+ }
+
+ @Override
+ public String getCountry() {
+ return null;
}
};
return accountData;
diff --git a/invoice/src/test/java/com/ning/billing/invoice/dao/InvoiceDaoTestBase.java b/invoice/src/test/java/com/ning/billing/invoice/dao/InvoiceDaoTestBase.java
index 268aaf5..2e3a3ef 100644
--- a/invoice/src/test/java/com/ning/billing/invoice/dao/InvoiceDaoTestBase.java
+++ b/invoice/src/test/java/com/ning/billing/invoice/dao/InvoiceDaoTestBase.java
@@ -18,6 +18,7 @@ package com.ning.billing.invoice.dao;
import java.io.IOException;
import org.apache.commons.io.IOUtils;
+import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeClass;
import com.google.inject.Guice;
import com.google.inject.Injector;
@@ -31,12 +32,13 @@ import static org.testng.Assert.fail;
public abstract class InvoiceDaoTestBase {
protected InvoiceDao invoiceDao;
protected InvoiceItemSqlDao invoiceItemDao;
+ private InvoiceModuleMock module;
@BeforeClass()
protected void setup() throws IOException {
// Health check test to make sure MySQL is setup properly
try {
- InvoiceModuleMock module = new InvoiceModuleMock();
+ module = new InvoiceModuleMock();
final String ddl = IOUtils.toString(DefaultInvoiceDao.class.getResourceAsStream("/com/ning/billing/invoice/ddl.sql"));
module.createDb(ddl);
@@ -54,4 +56,10 @@ public abstract class InvoiceDaoTestBase {
fail(t.toString());
}
}
+
+ @AfterClass(alwaysRun = true)
+ public void stopMysql()
+ {
+ module.stopDb();
+ }
}
diff --git a/invoice/src/test/java/com/ning/billing/invoice/glue/InvoiceModuleMock.java b/invoice/src/test/java/com/ning/billing/invoice/glue/InvoiceModuleMock.java
index c2f7585..c1af617 100644
--- a/invoice/src/test/java/com/ning/billing/invoice/glue/InvoiceModuleMock.java
+++ b/invoice/src/test/java/com/ning/billing/invoice/glue/InvoiceModuleMock.java
@@ -32,6 +32,10 @@ public class InvoiceModuleMock extends InvoiceModule {
helper.initDb(ddl);
}
+ public void stopDb() {
+ helper.stopMysql();
+ }
+
public InvoiceItemSqlDao getInvoiceItemDao() {
return dbi.onDemand(InvoiceItemSqlDao.class);
}
util/pom.xml 16(+15 -1)
diff --git a/util/pom.xml b/util/pom.xml
index 5152ab7..9bf807a 100644
--- a/util/pom.xml
+++ b/util/pom.xml
@@ -51,6 +51,15 @@
<scope>test</scope>
</dependency>
<dependency>
+ <groupId>mysql</groupId>
+ <artifactId>mysql-connector-java</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.antlr</groupId>
+ <artifactId>stringtemplate</artifactId>
+ <scope>runtime</scope>
+ </dependency>
+ <dependency>
<groupId>org.testng</groupId>
<artifactId>testng</artifactId>
<scope>test</scope>
@@ -58,7 +67,12 @@
<dependency>
<groupId>com.mysql</groupId>
<artifactId>management</artifactId>
- <version>5.0.11</version>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
+ <groupId>com.mysql</groupId>
+ <artifactId>management-dbfiles</artifactId>
+ <scope>test</scope>
</dependency>
<dependency>
<groupId>commons-io</groupId>
diff --git a/util/src/main/java/com/ning/billing/util/entity/EntityDao.java b/util/src/main/java/com/ning/billing/util/entity/EntityDao.java
index 3b5dd46..cc8b45d 100644
--- a/util/src/main/java/com/ning/billing/util/entity/EntityDao.java
+++ b/util/src/main/java/com/ning/billing/util/entity/EntityDao.java
@@ -23,13 +23,15 @@ import org.skife.jdbi.v2.sqlobject.SqlQuery;
import org.skife.jdbi.v2.sqlobject.SqlUpdate;
import java.util.List;
+import com.ning.billing.account.api.AccountApiException;
+import com.ning.billing.util.eventbus.EventBus;
public interface EntityDao<T extends Entity> {
@SqlUpdate
- public void create(@BindBean T entity);
+ public void create(@BindBean final T entity);
@SqlUpdate
- public void update(@BindBean T entity);
+ public void update(@BindBean final T entity) throws AccountApiException, EventBus.EventBusException;
@SqlQuery
public T getById(@Bind("id") final String id);
diff --git a/util/src/main/java/com/ning/billing/util/glue/TagDescriptionDaoProvider.java b/util/src/main/java/com/ning/billing/util/glue/TagDescriptionDaoProvider.java
index 31fb306..560a09f 100644
--- a/util/src/main/java/com/ning/billing/util/glue/TagDescriptionDaoProvider.java
+++ b/util/src/main/java/com/ning/billing/util/glue/TagDescriptionDaoProvider.java
@@ -18,10 +18,10 @@ package com.ning.billing.util.glue;
import com.google.inject.Inject;
import com.google.inject.Provider;
-import com.ning.billing.util.tag.dao.TagDescriptionDao;
+import com.ning.billing.util.tag.dao.TagDefinitionSqlDao;
import org.skife.jdbi.v2.IDBI;
-public class TagDescriptionDaoProvider implements Provider<TagDescriptionDao>
+public class TagDescriptionDaoProvider implements Provider<TagDefinitionSqlDao>
{
private final IDBI dbi;
@@ -32,8 +32,8 @@ public class TagDescriptionDaoProvider implements Provider<TagDescriptionDao>
}
@Override
- public TagDescriptionDao get()
+ public TagDefinitionSqlDao get()
{
- return dbi.onDemand(TagDescriptionDao.class);
+ return dbi.onDemand(TagDefinitionSqlDao.class);
}
}
diff --git a/util/src/main/java/com/ning/billing/util/glue/TagStoreDaoProvider.java b/util/src/main/java/com/ning/billing/util/glue/TagStoreDaoProvider.java
index 2c612e6..aa0f080 100644
--- a/util/src/main/java/com/ning/billing/util/glue/TagStoreDaoProvider.java
+++ b/util/src/main/java/com/ning/billing/util/glue/TagStoreDaoProvider.java
@@ -18,10 +18,10 @@ package com.ning.billing.util.glue;
import com.google.inject.Inject;
import com.google.inject.Provider;
-import com.ning.billing.util.tag.dao.TagStoreDao;
+import com.ning.billing.util.tag.dao.TagStoreSqlDao;
import org.skife.jdbi.v2.IDBI;
-public class TagStoreDaoProvider implements Provider<TagStoreDao>
+public class TagStoreDaoProvider implements Provider<TagStoreSqlDao>
{
private final IDBI dbi;
@@ -32,8 +32,8 @@ public class TagStoreDaoProvider implements Provider<TagStoreDao>
}
@Override
- public TagStoreDao get()
+ public TagStoreSqlDao get()
{
- return dbi.onDemand(TagStoreDao.class);
+ return dbi.onDemand(TagStoreSqlDao.class);
}
}
diff --git a/util/src/main/java/com/ning/billing/util/glue/TagStoreModule.java b/util/src/main/java/com/ning/billing/util/glue/TagStoreModule.java
index ae14782..86f42ad 100644
--- a/util/src/main/java/com/ning/billing/util/glue/TagStoreModule.java
+++ b/util/src/main/java/com/ning/billing/util/glue/TagStoreModule.java
@@ -17,15 +17,21 @@
package com.ning.billing.util.glue;
import com.google.inject.AbstractModule;
-import com.ning.billing.util.tag.dao.TagDescriptionDao;
-import com.ning.billing.util.tag.dao.TagStoreDao;
+import com.ning.billing.util.clock.Clock;
+import com.ning.billing.util.clock.DefaultClock;
+import com.ning.billing.util.tag.dao.DefaultTagDefinitionDao;
+import com.ning.billing.util.tag.dao.TagDefinitionDao;
+import com.ning.billing.util.tag.dao.TagDefinitionSqlDao;
+import com.ning.billing.util.tag.dao.TagStoreSqlDao;
public class TagStoreModule extends AbstractModule
{
@Override
protected void configure()
{
- bind(TagDescriptionDao.class).toProvider(TagDescriptionDaoProvider.class).asEagerSingleton();
- bind(TagStoreDao.class).toProvider(TagStoreDaoProvider.class).asEagerSingleton();
+ bind(Clock.class).to(DefaultClock.class).asEagerSingleton();
+ bind(TagDefinitionSqlDao.class).toProvider(TagDescriptionDaoProvider.class).asEagerSingleton();
+ bind(TagDefinitionDao.class).to(DefaultTagDefinitionDao.class).asEagerSingleton();
+ bind(TagStoreSqlDao.class).toProvider(TagStoreDaoProvider.class).asEagerSingleton();
}
}
diff --git a/util/src/main/java/com/ning/billing/util/tag/api/DefaultTagDefinitionUserApi.java b/util/src/main/java/com/ning/billing/util/tag/api/DefaultTagDefinitionUserApi.java
new file mode 100644
index 0000000..fa387cb
--- /dev/null
+++ b/util/src/main/java/com/ning/billing/util/tag/api/DefaultTagDefinitionUserApi.java
@@ -0,0 +1,47 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag.api;
+
+import com.google.inject.Inject;
+import com.ning.billing.util.api.TagDefinitionApiException;
+import com.ning.billing.util.api.TagDefinitionUserApi;
+import com.ning.billing.util.tag.TagDefinition;
+import com.ning.billing.util.tag.dao.TagDefinitionDao;
+
+public class DefaultTagDefinitionUserApi implements TagDefinitionUserApi {
+ private TagDefinitionDao dao;
+
+ @Inject
+ public DefaultTagDefinitionUserApi(TagDefinitionDao dao) {
+ this.dao = dao;
+ }
+
+ @Override
+ public TagDefinition create(final String name, final String description, final String createdBy) throws TagDefinitionApiException {
+ return dao.create(name, description, createdBy);
+ }
+
+ @Override
+ public void deleteAllTagsForDefinition(final String definitionName) throws TagDefinitionApiException {
+ dao.deleteAllTagsForDefinition(definitionName);
+ }
+
+ @Override
+ public void deleteTagDefinition(final String definitionName) throws TagDefinitionApiException {
+ dao.deleteAllTagsForDefinition(definitionName);
+ }
+}
diff --git a/util/src/main/java/com/ning/billing/util/tag/dao/DefaultTagDefinitionDao.java b/util/src/main/java/com/ning/billing/util/tag/dao/DefaultTagDefinitionDao.java
new file mode 100644
index 0000000..8c0bd97
--- /dev/null
+++ b/util/src/main/java/com/ning/billing/util/tag/dao/DefaultTagDefinitionDao.java
@@ -0,0 +1,94 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag.dao;
+
+import org.skife.jdbi.v2.IDBI;
+import com.google.inject.Inject;
+import com.ning.billing.ErrorCode;
+import com.ning.billing.account.api.ControlTagType;
+import com.ning.billing.util.api.TagDefinitionApiException;
+import com.ning.billing.util.clock.Clock;
+import com.ning.billing.util.tag.DefaultTagDefinition;
+import com.ning.billing.util.tag.TagDefinition;
+
+public class DefaultTagDefinitionDao implements TagDefinitionDao {
+ private final TagDefinitionSqlDao dao;
+ private final Clock clock;
+
+ @Inject
+ public DefaultTagDefinitionDao(IDBI dbi, Clock clock) {
+ this.dao = dbi.onDemand(TagDefinitionSqlDao.class);
+ this.clock = clock;
+ }
+
+ @Override
+ public TagDefinition getByName(final String definitionName) {
+ return dao.getByName(definitionName);
+ }
+
+ @Override
+ public TagDefinition create(final String definitionName, final String description, final String createdBy) throws TagDefinitionApiException {
+ if (isControlTagName(definitionName)) {
+ throw new TagDefinitionApiException(ErrorCode.TAG_DEFINITION_CONFLICTS_WITH_CONTROL_TAG, definitionName);
+ }
+
+ TagDefinition existingDefinition = dao.getByName(definitionName);
+
+ if (existingDefinition != null) {
+ throw new TagDefinitionApiException(ErrorCode.TAG_DEFINITION_ALREADY_EXISTS, definitionName);
+ }
+
+ TagDefinition definition = new DefaultTagDefinition(definitionName, description, createdBy, clock.getUTCNow());
+ dao.create(definition);
+ return definition;
+ }
+
+ private boolean isControlTagName(final String definitionName) {
+ for (ControlTagType controlTagName : ControlTagType.values()) {
+ if (controlTagName.toString().equals(definitionName)) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ @Override
+ public void deleteAllTagsForDefinition(final String definitionName) throws TagDefinitionApiException {
+ TagDefinition existingDefinition = dao.getByName(definitionName);
+ if (existingDefinition == null) {
+ throw new TagDefinitionApiException(ErrorCode.TAG_DEFINITION_DOES_NOT_EXIST, definitionName);
+ }
+
+ dao.deleteAllTagsForDefinition(definitionName);
+ }
+
+ @Override
+ public void deleteTagDefinition(final String definitionName) throws TagDefinitionApiException {
+ if (dao.tagDefinitionUsageCount(definitionName) > 0) {
+ throw new TagDefinitionApiException(ErrorCode.TAG_DEFINITION_IN_USE, definitionName);
+ }
+
+ TagDefinition existingDefinition = dao.getByName(definitionName);
+
+ if (existingDefinition == null) {
+ throw new TagDefinitionApiException(ErrorCode.TAG_DEFINITION_DOES_NOT_EXIST, definitionName);
+ }
+
+ dao.deleteTagDefinition(definitionName);
+ }
+}
diff --git a/util/src/main/java/com/ning/billing/util/tag/dao/TagBinder.java b/util/src/main/java/com/ning/billing/util/tag/dao/TagBinder.java
new file mode 100644
index 0000000..d56257d
--- /dev/null
+++ b/util/src/main/java/com/ning/billing/util/tag/dao/TagBinder.java
@@ -0,0 +1,46 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag.dao;
+
+import java.lang.annotation.Annotation;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+import org.skife.jdbi.v2.SQLStatement;
+import org.skife.jdbi.v2.sqlobject.Binder;
+import org.skife.jdbi.v2.sqlobject.BinderFactory;
+import org.skife.jdbi.v2.sqlobject.BindingAnnotation;
+import com.ning.billing.util.tag.Tag;
+
+@BindingAnnotation(TagBinder.TagBinderFactory.class)
+@Retention(RetentionPolicy.RUNTIME)
+@Target({ElementType.PARAMETER})
+public @interface TagBinder {
+ public static class TagBinderFactory implements BinderFactory {
+ public Binder build(Annotation annotation) {
+ return new Binder<TagBinder, Tag>() {
+ public void bind(SQLStatement q, TagBinder bind, Tag tag) {
+ q.bind("id", tag.getId().toString());
+ q.bind("tagDefinitionName", tag.getTagDefinitionName());
+ q.bind("addedDate", tag.getAddedDate().toDate());
+ q.bind("addedBy", tag.getAddedBy());
+ }
+ };
+ }
+ }
+}
diff --git a/util/src/main/java/com/ning/billing/util/tag/dao/TagDefinitionDao.java b/util/src/main/java/com/ning/billing/util/tag/dao/TagDefinitionDao.java
new file mode 100644
index 0000000..eaf8224
--- /dev/null
+++ b/util/src/main/java/com/ning/billing/util/tag/dao/TagDefinitionDao.java
@@ -0,0 +1,30 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag.dao;
+
+import com.ning.billing.util.api.TagDefinitionApiException;
+import com.ning.billing.util.tag.TagDefinition;
+
+public interface TagDefinitionDao {
+ public TagDefinition getByName(String definitionName);
+
+ public TagDefinition create(String definitionName, String description, String createdBy) throws TagDefinitionApiException;
+
+ public void deleteAllTagsForDefinition(String definitionName) throws TagDefinitionApiException;
+
+ public void deleteTagDefinition(String definitionName) throws TagDefinitionApiException;
+}
diff --git a/util/src/main/java/com/ning/billing/util/tag/dao/TagMapper.java b/util/src/main/java/com/ning/billing/util/tag/dao/TagMapper.java
new file mode 100644
index 0000000..1296083
--- /dev/null
+++ b/util/src/main/java/com/ning/billing/util/tag/dao/TagMapper.java
@@ -0,0 +1,57 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag.dao;
+
+import java.sql.ResultSet;
+import java.sql.SQLException;
+import java.util.UUID;
+import org.joda.time.DateTime;
+import org.skife.jdbi.v2.StatementContext;
+import org.skife.jdbi.v2.tweak.ResultSetMapper;
+import com.ning.billing.account.api.ControlTagType;
+import com.ning.billing.util.tag.DefaultControlTag;
+import com.ning.billing.util.tag.DefaultTagDefinition;
+import com.ning.billing.util.tag.DescriptiveTag;
+import com.ning.billing.util.tag.Tag;
+import com.ning.billing.util.tag.TagDefinition;
+
+public class TagMapper implements ResultSetMapper<Tag> {
+ @Override
+ public Tag map(final int index, final ResultSet result, final StatementContext context) throws SQLException {
+ String name = result.getString("tag_definition_name");
+
+ UUID id = UUID.fromString(result.getString("id"));
+ String addedBy = result.getString("added_by");
+ DateTime addedDate = new DateTime(result.getTimestamp("added_date"));
+
+ Tag tag;
+ try {
+ ControlTagType controlTagType = ControlTagType.valueOf(name);
+ tag = new DefaultControlTag(id, addedBy, addedDate, controlTagType);
+ } catch (Throwable t) {
+ String description = result.getString("tag_description");
+ String createdBy = result.getString("created_by");
+ DateTime creationDate = new DateTime(result.getDate("creation_date"));
+
+ UUID tagDefinitionId = UUID.fromString(result.getString("tag_definition_id"));
+ TagDefinition tagDefinition = new DefaultTagDefinition(tagDefinitionId, name, description, createdBy, creationDate);
+ tag = new DescriptiveTag(id, tagDefinition, addedBy, addedDate);
+ }
+
+ return tag;
+ }
+}
diff --git a/util/src/main/java/com/ning/billing/util/tag/DefaultControlTag.java b/util/src/main/java/com/ning/billing/util/tag/DefaultControlTag.java
new file mode 100644
index 0000000..707526d
--- /dev/null
+++ b/util/src/main/java/com/ning/billing/util/tag/DefaultControlTag.java
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag;
+
+import java.util.UUID;
+import org.joda.time.DateTime;
+import com.ning.billing.account.api.ControlTagType;
+
+public class DefaultControlTag extends DescriptiveTag implements ControlTag {
+ private final ControlTagType controlTagType;
+
+ public DefaultControlTag(final String addedBy,
+ final DateTime addedDate, final ControlTagType controlTagType) {
+ this(UUID.randomUUID(), addedBy, addedDate, controlTagType);
+ }
+
+ public DefaultControlTag(final UUID id, final String addedBy,
+ final DateTime addedDate, final ControlTagType controlTagType) {
+
+ super(id, controlTagType.toString(), addedBy, addedDate);
+ this.controlTagType = controlTagType;
+ }
+
+ @Override
+ public ControlTagType getControlTagType() {
+ return controlTagType;
+ }
+}
diff --git a/util/src/main/java/com/ning/billing/util/tag/DefaultTagStore.java b/util/src/main/java/com/ning/billing/util/tag/DefaultTagStore.java
index 5d49fb2..2fd8144 100644
--- a/util/src/main/java/com/ning/billing/util/tag/DefaultTagStore.java
+++ b/util/src/main/java/com/ning/billing/util/tag/DefaultTagStore.java
@@ -17,6 +17,7 @@
package com.ning.billing.util.tag;
import java.util.UUID;
+import com.ning.billing.account.api.ControlTagType;
import com.ning.billing.util.entity.EntityCollectionBase;
public class DefaultTagStore extends EntityCollectionBase<Tag> implements TagStore {
@@ -26,7 +27,7 @@ public class DefaultTagStore extends EntityCollectionBase<Tag> implements TagSto
@Override
public String getEntityKey(final Tag entity) {
- return entity.getName();
+ return entity.getTagDefinitionName();
}
@Override
@@ -36,10 +37,14 @@ public class DefaultTagStore extends EntityCollectionBase<Tag> implements TagSto
*/
public boolean processPayment() {
for (Tag tag : entities.values()) {
- if (!tag.getProcessPayment()) {
- return false;
+ if (tag instanceof ControlTag) {
+ ControlTag controlTag = (ControlTag) tag;
+ if (controlTag.getControlTagType() == ControlTagType.AUTO_BILLING_OFF) {
+ return false;
+ }
}
}
+
return true;
}
@@ -50,10 +55,14 @@ public class DefaultTagStore extends EntityCollectionBase<Tag> implements TagSto
@Override
public boolean generateInvoice() {
for (Tag tag : entities.values()) {
- if (!tag.getGenerateInvoice()) {
- return false;
+ if (tag instanceof ControlTag) {
+ ControlTag controlTag = (ControlTag) tag;
+ if (controlTag.getControlTagType() == ControlTagType.AUTO_INVOICING_OFF) {
+ return false;
+ }
}
}
+
return true;
}
@@ -65,7 +74,7 @@ public class DefaultTagStore extends EntityCollectionBase<Tag> implements TagSto
@Override
public boolean containsTag(final String tagName) {
for (Tag tag : entities.values()) {
- if (tag.getName().equals(tagName)) {
+ if (tag.getTagDefinitionName().equals(tagName)) {
return true;
}
}
diff --git a/util/src/main/java/com/ning/billing/util/tag/TagBuilder.java b/util/src/main/java/com/ning/billing/util/tag/TagBuilder.java
index cd4247f..626acd3 100644
--- a/util/src/main/java/com/ning/billing/util/tag/TagBuilder.java
+++ b/util/src/main/java/com/ning/billing/util/tag/TagBuilder.java
@@ -21,10 +21,7 @@ import org.joda.time.DateTime;
public class TagBuilder {
private UUID id = UUID.randomUUID();
- private UUID tagDescriptionId;
private String name;
- private boolean processPayment;
- private boolean generateInvoice;
private String addedBy;
private DateTime dateAdded;
@@ -33,23 +30,8 @@ public class TagBuilder {
return this;
}
- public TagBuilder tagDescriptionId(UUID tagDescriptionId) {
- this.tagDescriptionId = tagDescriptionId;
- return this;
- }
-
- public TagBuilder name(String name) {
- this.name = name;
- return this;
- }
-
- public TagBuilder processPayment(boolean processPayment) {
- this.processPayment = processPayment;
- return this;
- }
-
- public TagBuilder generateInvoice(boolean generateInvoice) {
- this.generateInvoice = generateInvoice;
+ public TagBuilder tagDescriptionName(String tagDescriptionName) {
+ this.name = tagDescriptionName;
return this;
}
@@ -64,6 +46,6 @@ public class TagBuilder {
}
public Tag build() {
- return new DefaultTag(id, tagDescriptionId, name, processPayment, generateInvoice, addedBy, dateAdded);
+ return new DescriptiveTag(id, name, addedBy, dateAdded);
}
}
diff --git a/util/src/main/resources/com/ning/billing/util/customfield/dao/FieldStoreDao.sql.stg b/util/src/main/resources/com/ning/billing/util/customfield/dao/FieldStoreDao.sql.stg
index 57163a9..883f61b 100644
--- a/util/src/main/resources/com/ning/billing/util/customfield/dao/FieldStoreDao.sql.stg
+++ b/util/src/main/resources/com/ning/billing/util/customfield/dao/FieldStoreDao.sql.stg
@@ -1,4 +1,4 @@
-group IFieldStoreDao;
+group FieldStoreDao;
save() ::= <<
INSERT INTO custom_fields(id, object_id, object_type, field_name, field_value)
diff --git a/util/src/main/resources/com/ning/billing/util/ddl.sql b/util/src/main/resources/com/ning/billing/util/ddl.sql
index c68b18b..c0bff95 100644
--- a/util/src/main/resources/com/ning/billing/util/ddl.sql
+++ b/util/src/main/resources/com/ning/billing/util/ddl.sql
@@ -10,28 +10,26 @@ CREATE TABLE custom_fields (
CREATE INDEX custom_fields_object_id_object_type ON custom_fields(object_id, object_type);
CREATE UNIQUE INDEX custom_fields_unique ON custom_fields(object_id, object_type, field_name);
-DROP TABLE IF EXISTS tag_descriptions;
-CREATE TABLE tag_descriptions (
+DROP TABLE IF EXISTS tag_definitions;
+CREATE TABLE tag_definitions (
id char(36) NOT NULL,
name varchar(20) NOT NULL,
created_by varchar(50) NOT NULL,
creation_date datetime NOT NULL,
description varchar(200) NOT NULL,
- generate_invoice boolean DEFAULT false,
- process_payment boolean DEFAULT false,
PRIMARY KEY(id)
) ENGINE=innodb;
-CREATE UNIQUE INDEX tag_descriptions_name ON tag_descriptions(name);
+CREATE UNIQUE INDEX tag_definitions_name ON tag_definitions(name);
DROP TABLE IF EXISTS tags;
CREATE TABLE tags (
id char(36) NOT NULL,
- tag_description_id char(36) NOT NULL,
+ tag_definition_name varchar(20) NOT NULL,
object_id char(36) NOT NULL,
object_type varchar(30) NOT NULL,
- date_added datetime NOT NULL,
+ added_date datetime NOT NULL,
added_by varchar(50) NOT NULL,
PRIMARY KEY(id)
) ENGINE = innodb;
CREATE INDEX tags_by_object ON tags(object_id);
-CREATE UNIQUE INDEX tags_unique ON tags(tag_description_id, object_id);
\ No newline at end of file
+CREATE UNIQUE INDEX tags_unique ON tags(tag_definition_name, object_id);
\ No newline at end of file
diff --git a/util/src/main/resources/com/ning/billing/util/tag/dao/TagDefinitionSqlDao.sql.stg b/util/src/main/resources/com/ning/billing/util/tag/dao/TagDefinitionSqlDao.sql.stg
new file mode 100644
index 0000000..6e4904d
--- /dev/null
+++ b/util/src/main/resources/com/ning/billing/util/tag/dao/TagDefinitionSqlDao.sql.stg
@@ -0,0 +1,44 @@
+group TagDefinitionDao;
+
+create() ::= <<
+ INSERT INTO tag_definitions(id, name, created_by, creation_date, description)
+ VALUES(:id, :name, :createdBy, :creationDate, :description);
+>>
+
+update() ::= <<
+ UPDATE tag_definitions
+ SET name = :name, created_by = :createdBy, creation_date = :creationDate,
+ description = :description)
+ WHERE id = :id;
+>>
+
+load() ::= <<
+ SELECT id, name, created_by, creation_date, description
+ FROM tag_definitions
+ WHERE id = :id;
+>>
+
+deleteAllTagsForDefinition() ::= <<
+ DELETE FROM tags
+ WHERE tag_definition_name = :name;
+>>
+
+deleteTagDefinition() ::= <<
+ DELETE FROM tag_definitions
+ WHERE name = :name;
+>>
+
+tagDefinitionUsageCount() ::= <<
+ SELECT COUNT(id)
+ FROM tags
+ WHERE tag_definition_name = :name
+>>
+
+getByName() ::= <<
+ SELECT id, name, created_by, creation_date, description
+ FROM tag_definitions
+ WHERE name = :name;
+>>
+;
+
+
diff --git a/util/src/test/java/com/ning/billing/util/customfield/TestFieldStore.java b/util/src/test/java/com/ning/billing/util/customfield/TestFieldStore.java
index 32c70f8..3b8016f 100644
--- a/util/src/test/java/com/ning/billing/util/customfield/TestFieldStore.java
+++ b/util/src/test/java/com/ning/billing/util/customfield/TestFieldStore.java
@@ -20,6 +20,8 @@ import java.io.IOException;
import java.util.UUID;
import org.apache.commons.io.IOUtils;
import org.skife.jdbi.v2.IDBI;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Test;
@@ -39,6 +41,7 @@ import static org.testng.Assert.fail;
@Test(groups={"util"})
public class TestFieldStore {
+ Logger log = LoggerFactory.getLogger(TestFieldStore.class);
private final MysqlTestingHelper helper = new MysqlTestingHelper();
private IDBI dbi;
@@ -54,6 +57,7 @@ public class TestFieldStore {
dbi = helper.getDBI();
}
catch (Throwable t) {
+ log.error("Setup failed", t);
fail(t.toString());
}
}
diff --git a/util/src/test/java/com/ning/billing/util/tag/TagStoreModuleMock.java b/util/src/test/java/com/ning/billing/util/tag/TagStoreModuleMock.java
new file mode 100644
index 0000000..9fc4c78
--- /dev/null
+++ b/util/src/test/java/com/ning/billing/util/tag/TagStoreModuleMock.java
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2010-2011 Ning, Inc.
+ *
+ * Ning 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 com.ning.billing.util.tag;
+
+import java.io.IOException;
+import org.skife.jdbi.v2.IDBI;
+import com.ning.billing.dbi.MysqlTestingHelper;
+import com.ning.billing.util.glue.TagStoreModule;
+
+public class TagStoreModuleMock extends TagStoreModule {
+ private final MysqlTestingHelper helper = new MysqlTestingHelper();
+
+ public void startDb() throws IOException {
+ helper.startMysql();
+ }
+
+ public void initDb(String ddl) throws IOException {
+ helper.initDb(ddl);
+ }
+
+ public void stopDb() {
+ helper.stopMysql();
+ }
+
+ @Override
+ protected void configure() {
+ bind(IDBI.class).toInstance(helper.getDBI());
+ super.configure();
+ }
+}
diff --git a/util/src/test/java/com/ning/billing/util/tag/TestTagStore.java b/util/src/test/java/com/ning/billing/util/tag/TestTagStore.java
index d2c44a4..d1d696c 100644
--- a/util/src/test/java/com/ning/billing/util/tag/TestTagStore.java
+++ b/util/src/test/java/com/ning/billing/util/tag/TestTagStore.java
@@ -20,48 +20,61 @@ import java.io.IOException;
import java.util.List;
import java.util.UUID;
import org.apache.commons.io.IOUtils;
-import org.joda.time.DateTime;
import org.skife.jdbi.v2.IDBI;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Test;
-import com.ning.billing.dbi.MysqlTestingHelper;
+import com.google.inject.Guice;
+import com.google.inject.Injector;
+import com.google.inject.Stage;
+import com.ning.billing.account.api.ControlTagType;
+import com.ning.billing.util.api.TagDefinitionApiException;
import com.ning.billing.util.clock.Clock;
import com.ning.billing.util.clock.DefaultClock;
-import com.ning.billing.util.tag.dao.TagDescriptionDao;
-import com.ning.billing.util.tag.dao.TagStoreDao;
+import com.ning.billing.util.tag.dao.TagDefinitionDao;
+import com.ning.billing.util.tag.dao.TagStoreSqlDao;
import static org.testng.Assert.assertEquals;
+import static org.testng.Assert.assertNotNull;
+import static org.testng.Assert.assertNull;
import static org.testng.Assert.fail;
@Test(groups={"util"})
public class TestTagStore {
private final static String ACCOUNT_TYPE = "ACCOUNT";
private final Clock clock = new DefaultClock();
- private final MysqlTestingHelper helper = new MysqlTestingHelper();
private IDBI dbi;
- private TagDescription tag1;
- private TagDescription tag2;
+ private TagDefinition tag1;
+ private TagDefinition tag2;
+ private TagStoreModuleMock module;
+ private TagStoreSqlDao tagStoreSqlDao;
+ private TagDefinitionDao tagDefinitionDao;
+ private Logger log = LoggerFactory.getLogger(TestTagStore.class);
@BeforeClass(alwaysRun = true)
protected void setup() throws IOException {
// Health check test to make sure MySQL is setup properly
try {
+ module = new TagStoreModuleMock();
final String utilDdl = IOUtils.toString(TestTagStore.class.getResourceAsStream("/com/ning/billing/util/ddl.sql"));
- helper.startMysql();
- helper.initDb(utilDdl);
+ module.startDb();
+ module.initDb(utilDdl);
- dbi = helper.getDBI();
+ final Injector injector = Guice.createInjector(Stage.DEVELOPMENT, module);
+ dbi = injector.getInstance(IDBI.class);
- tag1 = new DefaultTagDescription("tag1", "First tag", true, true, "test", clock.getUTCNow());
- tag2 = new DefaultTagDescription("tag2", "Second tag", false, false, "test", clock.getUTCNow());
+ tagStoreSqlDao = injector.getInstance(TagStoreSqlDao.class);
+ tagStoreSqlDao.test();
- TagDescriptionDao dao = dbi.onDemand(TagDescriptionDao.class);
- dao.create(tag1);
- dao.create(tag2);
+ tagDefinitionDao = injector.getInstance(TagDefinitionDao.class);
+ tag1 = tagDefinitionDao.create("tag1", "First tag", "test");
+ tag2 = tagDefinitionDao.create("tag2", "Second tag", "test");
}
catch (Throwable t) {
+ log.error("Failed to start tag store tests", t);
fail(t.toString());
}
}
@@ -69,7 +82,7 @@ public class TestTagStore {
@AfterClass(alwaysRun = true)
public void stopMysql()
{
- helper.stopMysql();
+ module.stopDb();
}
@Test
@@ -77,22 +90,245 @@ public class TestTagStore {
UUID accountId = UUID.randomUUID();
TagStore tagStore = new DefaultTagStore(accountId, ACCOUNT_TYPE);
- Tag tag = new DefaultTag(tag2, "test", clock.getUTCNow());
+ Tag tag = new DescriptiveTag(tag2, "test", clock.getUTCNow());
tagStore.add(tag);
- TagStoreDao dao = dbi.onDemand(TagStoreDao.class);
+ TagStoreSqlDao dao = dbi.onDemand(TagStoreSqlDao.class);
dao.save(accountId.toString(), ACCOUNT_TYPE, tagStore.getEntityList());
List<Tag> savedTags = dao.load(accountId.toString(), ACCOUNT_TYPE);
assertEquals(savedTags.size(), 1);
Tag savedTag = savedTags.get(0);
- assertEquals(savedTag.getTagDescriptionId(), tag.getTagDescriptionId());
assertEquals(savedTag.getAddedBy(), tag.getAddedBy());
- assertEquals(savedTag.getDateAdded().compareTo(tag.getDateAdded()), 0);
- assertEquals(savedTag.getGenerateInvoice(), tag.getGenerateInvoice());
- assertEquals(savedTag.getName(), tag.getName());
- assertEquals(savedTag.getProcessPayment(), tag.getProcessPayment());
+ assertEquals(savedTag.getAddedDate().compareTo(tag.getAddedDate()), 0);
+ assertEquals(savedTag.getTagDefinitionName(), tag.getTagDefinitionName());
assertEquals(savedTag.getId(), tag.getId());
}
+
+ @Test
+ public void testControlTagCreation() {
+ UUID accountId = UUID.randomUUID();
+ TagStore tagStore = new DefaultTagStore(accountId, ACCOUNT_TYPE);
+
+ ControlTag tag = new DefaultControlTag("testUser", clock.getUTCNow(), ControlTagType.AUTO_INVOICING_OFF);
+ tagStore.add(tag);
+ assertEquals(tagStore.generateInvoice(), false);
+
+ List<Tag> tagList = tagStore.getEntityList();
+ tagStoreSqlDao.save(accountId.toString(), ACCOUNT_TYPE, tagList);
+
+ tagStore.clear();
+ assertEquals(tagStore.getEntityList().size(), 0);
+
+ tagList = tagStoreSqlDao.load(accountId.toString(), ACCOUNT_TYPE);
+ tagStore.add(tagList);
+ assertEquals(tagList.size(), 1);
+
+ assertEquals(tagStore.generateInvoice(), false);
+ }
+
+ @Test
+ public void testDescriptiveTagCreation() {
+ UUID accountId = UUID.randomUUID();
+ TagStore tagStore = new DefaultTagStore(accountId, ACCOUNT_TYPE);
+
+ String definitionName = "SomeTestTag";
+ TagDefinition tagDefinition = null;
+ try {
+ tagDefinition = tagDefinitionDao.create(definitionName, "Test tag for some test purpose", "testUser");
+ } catch (TagDefinitionApiException e) {
+ fail("Tag definition creation failed.", e);
+ }
+
+ DescriptiveTag tag = new DescriptiveTag(tagDefinition, "testUser", clock.getUTCNow());
+ tagStore.add(tag);
+ assertEquals(tagStore.generateInvoice(), true);
+
+ List<Tag> tagList = tagStore.getEntityList();
+ tagStoreSqlDao.save(accountId.toString(), ACCOUNT_TYPE, tagList);
+
+ tagStore.clear();
+ assertEquals(tagStore.getEntityList().size(), 0);
+
+ tagList = tagStoreSqlDao.load(accountId.toString(), ACCOUNT_TYPE);
+ tagStore.add(tagList);
+ assertEquals(tagList.size(), 1);
+
+ assertEquals(tagStore.generateInvoice(), true);
+ }
+
+ @Test
+ public void testMixedTagCreation() {
+ UUID accountId = UUID.randomUUID();
+ TagStore tagStore = new DefaultTagStore(accountId, ACCOUNT_TYPE);
+
+ String definitionName = "MixedTagTest";
+ TagDefinition tagDefinition = null;
+ try {
+ tagDefinition = tagDefinitionDao.create(definitionName, "Test tag for some test purpose", "testUser");
+ } catch (TagDefinitionApiException e) {
+ fail("Tag definition creation failed.", e);
+ }
+
+ DescriptiveTag descriptiveTag = new DescriptiveTag(tagDefinition, "testUser", clock.getUTCNow());
+ tagStore.add(descriptiveTag);
+ assertEquals(tagStore.generateInvoice(), true);
+
+ ControlTag controlTag = new DefaultControlTag("testUser", clock.getUTCNow(), ControlTagType.AUTO_INVOICING_OFF);
+ tagStore.add(controlTag);
+ assertEquals(tagStore.generateInvoice(), false);
+
+ List<Tag> tagList = tagStore.getEntityList();
+ tagStoreSqlDao.save(accountId.toString(), ACCOUNT_TYPE, tagList);
+
+ tagStore.clear();
+ assertEquals(tagStore.getEntityList().size(), 0);
+
+ tagList = tagStoreSqlDao.load(accountId.toString(), ACCOUNT_TYPE);
+ tagStore.add(tagList);
+ assertEquals(tagList.size(), 2);
+
+ assertEquals(tagStore.generateInvoice(), false);
+ }
+
+ @Test
+ public void testControlTags() {
+ UUID accountId = UUID.randomUUID();
+ TagStore tagStore = new DefaultTagStore(accountId, ACCOUNT_TYPE);
+ assertEquals(tagStore.generateInvoice(), true);
+ assertEquals(tagStore.processPayment(), true);
+
+ ControlTag invoiceTag = new DefaultControlTag("testUser", clock.getUTCNow(), ControlTagType.AUTO_INVOICING_OFF);
+ tagStore.add(invoiceTag);
+ assertEquals(tagStore.generateInvoice(), false);
+ assertEquals(tagStore.processPayment(), true);
+
+ ControlTag paymentTag = new DefaultControlTag("testUser", clock.getUTCNow(), ControlTagType.AUTO_BILLING_OFF);
+ tagStore.add(paymentTag);
+ assertEquals(tagStore.generateInvoice(), false);
+ assertEquals(tagStore.processPayment(), false);
+ }
+
+ @Test(expectedExceptions = TagDefinitionApiException.class)
+ public void testTagDefinitionCreationWithControlTagName() throws TagDefinitionApiException {
+ String definitionName = ControlTagType.AUTO_BILLING_OFF.toString();
+ tagDefinitionDao.create(definitionName, "This should break", "test");
+ }
+
+ @Test
+ public void testTagDefinitionDeletionForUnusedDefinition() throws TagDefinitionApiException {
+ String definitionName = "TestTag1234";
+ tagDefinitionDao.create(definitionName, "Some test tag", "test");
+
+ TagDefinition tagDefinition = tagDefinitionDao.getByName(definitionName);
+ assertNotNull(tagDefinition);
+
+ tagDefinitionDao.deleteTagDefinition(definitionName);
+ tagDefinition = tagDefinitionDao.getByName(definitionName);
+ assertNull(tagDefinition);
+ }
+
+ @Test(expectedExceptions = TagDefinitionApiException.class)
+ public void testTagDefinitionDeletionForDefinitionInUse() throws TagDefinitionApiException {
+ String definitionName = "TestTag12345";
+ tagDefinitionDao.create(definitionName, "Some test tag", "test");
+
+ TagDefinition tagDefinition = tagDefinitionDao.getByName(definitionName);
+ assertNotNull(tagDefinition);
+
+ UUID objectId = UUID.randomUUID();
+ String objectType = "TestType";
+ TagStore tagStore = new DefaultTagStore(objectId, objectType);
+ Tag tag = new DescriptiveTag(tagDefinition, "test", clock.getUTCNow());
+ tagStore.add(tag);
+
+ tagStoreSqlDao.save(objectId.toString(), objectType, tagStore.getEntityList());
+ List<Tag> tags = tagStoreSqlDao.load(objectId.toString(), objectType);
+ assertEquals(tags.size(), 1);
+
+ tagDefinitionDao.deleteTagDefinition(definitionName);
+ }
+
+ @Test
+ public void testDeleteAllTagsForDefinitionInUse() {
+ String definitionName = "TestTag1234567";
+ try {
+ tagDefinitionDao.create(definitionName, "Some test tag", "test");
+ } catch (TagDefinitionApiException e) {
+ fail("Could not create tag definition", e);
+ }
+
+ TagDefinition tagDefinition = tagDefinitionDao.getByName(definitionName);
+ assertNotNull(tagDefinition);
+
+ UUID objectId = UUID.randomUUID();
+ String objectType = "TestType";
+ TagStore tagStore = new DefaultTagStore(objectId, objectType);
+ Tag tag = new DescriptiveTag(tagDefinition, "test", clock.getUTCNow());
+ tagStore.add(tag);
+
+ tagStoreSqlDao.save(objectId.toString(), objectType, tagStore.getEntityList());
+ List<Tag> tags = tagStoreSqlDao.load(objectId.toString(), objectType);
+ assertEquals(tags.size(), 1);
+
+ try {
+ tagDefinitionDao.deleteAllTagsForDefinition(definitionName);
+ } catch (TagDefinitionApiException e) {
+ fail("Could not delete tags for tag definition", e);
+ }
+
+ try {
+ tagDefinitionDao.deleteTagDefinition(definitionName);
+ } catch (TagDefinitionApiException e) {
+ fail("Could not delete tag definition", e);
+ }
+ }
+
+ @Test
+ public void testDeleteAllTagsForDefinitionNotInUse() {
+ String definitionName = "TestTag4321";
+ try {
+ tagDefinitionDao.create(definitionName, "Some test tag", "test");
+ } catch (TagDefinitionApiException e) {
+ fail("Could not create tag definition", e);
+ }
+
+ TagDefinition tagDefinition = tagDefinitionDao.getByName(definitionName);
+ assertNotNull(tagDefinition);
+
+ try {
+ tagDefinitionDao.deleteAllTagsForDefinition(definitionName);
+ } catch (TagDefinitionApiException e) {
+ fail("Could not delete tags for tag definition", e);
+ }
+
+ try {
+ tagDefinitionDao.deleteTagDefinition(definitionName);
+ } catch (TagDefinitionApiException e) {
+ fail("Could not delete tag definition", e);
+ }
+ }
+
+ @Test(expectedExceptions = TagDefinitionApiException.class)
+ public void testDeleteAllTagsForDefinitionWithWrongName() throws TagDefinitionApiException {
+ String definitionName = "TestTag654321";
+ String wrongDefinitionName = "TestTag564321";
+ try {
+ tagDefinitionDao.create(definitionName, "Some test tag", "test");
+ } catch (TagDefinitionApiException e) {
+ fail("Could not create tag definition", e);
+ }
+
+ TagDefinition tagDefinition = tagDefinitionDao.getByName(definitionName);
+ assertNotNull(tagDefinition);
+
+ tagDefinitionDao.deleteAllTagsForDefinition(wrongDefinitionName);
+
+ try {
+ tagDefinitionDao.deleteTagDefinition(definitionName);
+ } catch (TagDefinitionApiException e) {
+ fail("Could not delete tag definition", e);
+ }
+ }
}