Download - Adopt JSR 354

Transcript
Page 1: Adopt JSR 354

Go for the Money

Adopt JSR 354

Slideshare 2014

March 2014

Go for the money – Adopt JSR 354 -

http://java.net/projects/javamoney

Page 2: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Bio

Anatole Tresch

Consultant, Coach

Credit Suisse

Technical Coordinator & Architect

Specification Lead JSR 354

Regular Conference Speaker

Driving Java EE Config

Twitter/Google+: @atsticks

[email protected]

[email protected]

Java Config Discussion https://groups.google.com/forum/#!forum/java-config

Java Config Blog: http://javaeeconfig.blogspot.ch

Zurich Java Community (Google Community)

Zurich Hackergarten

2

Page 3: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Agenda

3

Overview

Setup

Adoption Areas

API Challenge: Moneymachine

Helping out with the TCK

Adding functonalities to the RI,

e.g. Cash Roundings

Stabilizing JavaMoney Library

Other ?

Page 4: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Overview

4

Page 5: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Money Machine

5

Page 6: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Overview of JSR 354 and Javamoney

API (javax.money):

CurrencyUnit, MonetaryAmount, MonetaryOperator,

MonetaryQuery, CurrencyConversion, ExchangeRate,

MonetaryAmountFormat, MonetaryException;

MonetaryCurrencies, MonetaryAmounts, MonetaryRoundings,

MonetaryConversions, MonetaryFormats

RI (org.javamoney.moneta): BuildableCurrencyUnit, Money, FastMoney, MonetaryFunctions

TCK (org.javamoney.tck):

Javamoney (GitHub OSS project): org.javamoney…

format (extended API)

currencies (mapping)

Regions

Validity

calc

6

Page 7: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Currencies and Monetary Amounts

javax.money

7

Page 8: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Currencies (continued)

API

8

Allow currencies with arbitrary other currency codes

Register additional Currency Units using an flexible SPI Fluent API using a Builder (RI only)

Historic Validity of currencies related to regions/countries and vice

versa (not part of JSR, but javamoney OSS project)

public interface CurrencyUnit{

public String getCurrencyCode();

public int getNumericCode();

public int getDefaultFractionDigits();

}

public final class MonetaryCurrencies{

public CurrencyUnit getCurrency(String currencyCode);

public CurrencyUnit getCurrency(Locale locale);

public boolean isCurrencyAvailable(String currencyCode);

public boolean isCurrencyAvailable(String locale);

}

Page 9: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Currencies (continued)

API Samples

CurrencyUnit currency1 = MonetaryCurrencies.getCurrency("USD");

CurrencyUnit currency2 = MonetaryCurrencies.getCurrency(

Locale.GERMANY);

CurrencyUnit bitcoin = new BuildableCurrencyUnit.Builder("BTC")

.setNumericCode(123456)

.setDefaultFractionDigits(8)

.create();

9

Access a CurrencyUnit

Build a CurrencyUnit (RI only)

Register a CurrencyUnit

CurrencyUnit bitcoin = ….create(true);

Page 10: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Monetary Amounts

General Aspects

10

Amount = Currency + Numeric Value

+ Capabilities

Arithmetic Functions, Comparison

Fluent API

Page 11: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Monetary Amounts (continued)

Key Decisions

11

Support Several Numeric Representations (instead of one

single fixed value type)

Use functional design for extendible functionality (MonetaryOperator, MonetaryQuery)

Define Implementation Recommendations

• Rounding should to be modelled as separate concern (a MonetaryOperator)

• Ensure Interoperability by the MonetaryAmount

interface

• Precision/scale capabilities should be inherited to its

operational results.

Page 12: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Monetary Amounts (continued)

The API public interface MonetaryAmount{

public CurrencyUnit getCurrency();

public NumberValue getNumber();

public MonetaryContext getMonetaryContext();

public MonetaryAmount with(MonetaryOperator operator);

public <R> R query(MonetaryQuery<R> query);

public MonetaryAmountFactory<? extends MonetaryAmount> getFactory();

public boolean isLessThanOrEqualTo(MonetaryAmount amt);

public boolean isLessThan(MonetaryAmount amt);

public boolean isEqualTo(MonetaryAmount amt);

public int signum();

public MonetaryAmount add(MonetaryAmount amount);

public MonetaryAmount subtract(MonetaryAmount amount);

public MonetaryAmount divide(long number);

public MonetaryAmount multiply(Number number);

public MonetaryAmount remainder(double number);

public MonetaryAmount stripTrailingZeros();

}

12

Page 13: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Monetary Context

Model Amount Capabilities

13

Describes the capabilities of a MonetaryAmount.

Accessible from each MonetaryAmount instance.

Allows querying a feasible implementation type from

MonetaryAmounts.

Contains

common aspects

Max precision, max scale, amount flavor

Arbitrary attributes

E.g. RoundingMode, MathContext, …

Page 14: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Monetary Context (continued)

The API

public final class MonetaryContext extends AbstractContext

implements Serializable {

public static enum AmountFlavor{ PRECISION, PERFORMANCE, UNDEFINED }

public int getPrecision();

public int getMaxScale();

public AmountFlavor getAmountFlavor();

public Class<? extends MonetaryAmount> getAmountType();

public static final class Builder{…}

}

public abstract class AbstractContext implements Serializable{

public <T> T getNamedAttribute(Class<T> type, Object key,

T defaultValue);

public <T> T getNamedAttribute(Class<T> type, Object key);

public <T> T getAttribute(Class<T> type, T defaultValue);

public <T> T getAttribute(Class<T> type);

public Set<Class<?>> getAttributeTypes();

}

14

Page 15: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Creating Monetary Amounts

Monetary Amount Factory

15

Creates new instances of MonetaryAmount.

Declares

The concrete MonetaryAmount implementation type

returned.

The min/max MonetaryContext supported.

Can be configured with a target

CurrencyUnit

A numeric value

MonetaryContext.

Page 16: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Creating Monetary Amounts (continued)

Monetary Amount Factory

public interface MonetaryAmountFactory<T extends MonetaryAmount> {

Class<? extends MonetaryAmount> getAmountType();

MonetaryAmountFactory<T> setCurrency(String currencyCode);

MonetaryAmountFactory<T> setCurrency(CurrencyUnit currency);

MonetaryAmountFactory<T> setNumber(double number);

MonetaryAmountFactory<T> setNumber(long number);

MonetaryAmountFactory<T> setNumber(Number number);

MonetaryAmountFactory<T> setContext(MonetaryContext monetaryContext);

MonetaryAmountFactory<T> setAmount(MonetaryAmount amount);

T create();

MonetaryContext getDefaultMonetaryContext();

MonetaryContext getMaximalMonetaryContext();

}

16

Page 17: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Creating Monetary Amounts

Usage Samples

// Using the default type

MonetaryAmount amount1 = MonetaryAmounts.getAmountFactory()

.setCurrency("USD“)

.setNumber(1234566.15)

.create();

// Using an explicit type

Money amount2 = MonetaryAmounts.getAmountFactory(Money.class)

.setCurrency("USD“)

.setNumber(1234566.15)

.create();

// Query a matching implementation type

Class<? extends MonetaryAmount> type = MonetaryAmounts.queryAmontType(

new MonetaryContext.Builder()

.setAmountFlavor(

AmountFlavor.PERFORMANT)

.create());

MonetaryAmount amount3 = MonetaryAmounts.getAmountFactory(type)

.setCurrency("USD“)

.setNumber(1234566.15)

.create();

17

Page 18: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Extension Points

javax.money

18

cmp Components

Component1

ProvidedInterface1

RequiredInterface

Component2

RequiredInterface

Page 19: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Extension Points

MonetaryOperator

Takes an amount and procudes some other amount.

• With different value

• With different currency

• Or both // @FunctionalInterface

public interface MonetaryOperator {

public MonetaryAmount apply(MonetaryAmount amount);

}

• Operators then can be applied on every MonetaryAmount:

public interface MonetaryAmount{

public MonetaryAmount with (MonetaryOperator operator);

}

19

Page 20: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Extension Points (continued)

MonetaryOperator: Use Cases

Extend the algorithmic capabilities

• Percentages

• Permil

• Different Minor Units

• Different Major Units

• Rounding

• Currency Conversion

• Financial Calculations

• …

20

Page 21: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Extension Points (continued)

MonetaryOperator Example: Rounding and Percentage

21

// round an amount

MonetaryOperator rounding =

MoneyRoundings.getRounding(

MonetaryCurrencies.getCurrency(“USD”));

Money amount = Money.of(“USD”, 12.345567);

Money rounded = amount.with(rounding); // USD 12.35

// MonetaryFunctions, e.g. calculate 3% of it

Money threePercent = rounded.with(

MonetaryFunctions.getPercent(3));

// USD 0.3705

Page 22: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Extension Points (continued)

MonetaryQuery

A MonetaryQuery takes an amount and procuces an arbitrary

result:

// @FunctionalInterface

public interface MonetaryQuery<T> {

public T queryFrom(MonetaryAmount amount);

}

Queries then can be applied on every MonetaryAmount:

public interface MonetaryAmount {

public <T> T query (MonetaryQuary<T> query);

}

22

Page 23: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Currency Conversion

javax.money.convert.*

23

Page 24: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Currency Conversion

ExchangeRate

A ExchangeRate models a conversion between two currencies:

• Base CurrencyUnit

• Terminating/target CurrencyUnit

• Provider

• Conversion Factor, where M(term) = M(base) * f

• Additional attributes (ConversionContext)

• Rate chain (composite rates)

Rates may be direct or derived (composite rates)

24

Page 25: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Currency Conversion

ExchangeRateProvider

// access default provider (chain)

ExchangeRateProvider prov =

MonetaryConversions.getExchangeRateProvider();

// access a provider explicitly

prov = MonetaryConversions.getExchangeRateProvider("IMF");

// access explicit provider chain

prov = MonetaryConversions.getExchangeRateProvider("ECB", "IMF");

// access Exchange rates

ExchangeRate rate = provider.getExchangeRate("EUR", "CHF");

// Passing additional parameters

ExchangeRate rate = provider.getExchangeRate("EUR", "CHF",

ConversionContext.of(

System.currentTimeMillis() + 2000L) );

25 Go for the money - JSR 354 - http://java.net/projects/javamoney

Page 26: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Currency Conversion (continued)

Performing Conversion

Accessing a CurrencyConversion (always targeted to a terminating CurrencyUnit):

// access from a ExchangeRateProvider

ExchangeRateProvider prov = …;

CurrencyConversion conv = prov.getCurrencyConversion("INR");

// access it directly (using default rate chain)

conv = MonetaryConversions.getConversion("INR");

// access it, using explicit provider chain

conv = MonetaryConversions.getConversion("INR", "ECB", "IMF");

Performing conversion:

MonetaryAmount chfAmount = MonetaryAmounts.of("CHF",10.50);

MonetaryAmount inrAmount = chfAmount.with(conv); // around EUR 8.75

26

Page 27: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Formatting and Parsing

javax.money.format.*

27

Page 28: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Formatting and Parsing

MonetaryAmountFormat

Similar to java.text.DecimalFormat, but also ME

compatible

Configured by AmountStyle, CurrencyStyle,

AmountFormatSymbols

Supports also custom formats

Building AmountStyle using a fluent API

Preconfigured format access is also possible

28 Go for the money - JSR 354 - http://java.net/projects/javamoney

Page 29: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Formatting and Parsing (continued)

MonetaryAmountFormat: Usage Example

// Access a provided format

MonetaryAmountFormat format = MonetaryFormats.getAmountFormat(

new Locale(“”, “in”));

System.out.println(format.format(

Money.of("INR", 39101112.123456))));

output> INR 3,91,01,112.10

29 Go for the money - JSR 354 - http://java.net/projects/javamoney

Page 30: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

JavaMoney OSS Project

org.javamoney.*

30

Page 31: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

JavaMoney OSS Project

Extended Currency Services

Currency namespaces (e.g. ISO, VIRTUAL, …)

Currency namespace mapping

Validity Services (Historization API)

• access of historic currency data related to regions

Region Services

Region Forest

• Unicode CLDR region tree

• ISO 2-, 3-letter countries

• Custom Trees

Extendible token-based Formatting API

Financial Calculations & Formulas

31

Page 32: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Links

Current Spec (work in progress, comments allowed): https://docs.google.com/document/d/1FfihURoCYrbkDcSf1W

XM6fHoU3d3tKooMnZLCpmpyV8/edit GitHub Project (JSR and JavaMoney):

https://github.com/JavaMoney/javamoney Umbrella Page: http://javamoney.org JSR 354: http://jcp.org

Java.net Project: http://java.net/projects/javamoney JUG Chennai Adoption (TrakStok):

https://github.com/jugchennaiadoptjava/TrakStok

Twitter: @jsr354 Cash Rounding: http://en.wikipedia.org/wiki/Swedish_rounding

32

Page 33: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Setup

33

Page 34: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Setup

34

• Install VirtualBox, if not yet done, download from https://www.virtualbox.org

• Download the prepared image and start it • Login with debian/debian • Open the IDE of your choice (Eclipse, IntelliJ and

Netbeans are preinstalled and setup) • Update the projects/repositories

• For Contributors:

• Ensure you have a GitHub user account • Create your own Branch of the corresponding repositories

• Switch your local repositories on your VM, on which you want to commit, to your branched repos

Page 35: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Adoption Areas JSR 354

API Challenge: MoneyMachine

35

Objective: Test the API for usability, make proposals to improve

How:

Checkout/update the MoneyMachine project from https://github.com/atsticks/moneymachine.git

Implement the classes in the src/main/java to make the tests

green (skeletons are already there) The challenge will guide you throughout the whole JSR Overall 34 test cases of different complexity, you may also selct

only a subset ;-) Tell me about improvements

Email [email protected] (please add [moneymachine] in your subject header)

Issues on java.net or gitub Blog your (hopefully positive) experience, twitter, …

Page 36: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Adoption Areas JSR 354

API Challenge: MoneyMachine Example

36

/**

* This class has to be implemented and helps us giving feedback on the JSR's API. This

* part of the

* project deals with basic aspects such as getting currencies and amounts.

* Created by Anatole on 07.03.14.

*/

public class Basics{

/**

* Get a CurrencyUnit using a currency code.

*

* @param currencyCode the currency code

* @return the corresponding CurrencyUnit instance.

*/

public CurrencyUnit getProvidedCurrency(String currencyCode){

throw new UnsupportedOperationException();

}

/**

* Get a CurrencyUnit using a Locale, modeling a country.

*

* @param locale The country locale.

* @return the corresponding CurrencyUnit instance.

*/

public CurrencyUnit getProvidedCurrency(Locale locale){

throw new UnsupportedOperationException();

}

...

}

Describes

the task to

be done

(incl. Some

hints)

Replace this

with the

code

Page 37: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Adoption Areas JSR 354

API Challenge: MoneyMachine Testing

37

To check your

implementation is correct,

simply execute the test suite

Correct ;-)

Page 38: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Adoption Areas JSR 354

Helping on the TCK

38

Objective: Help writing the JSRs TCK

How:

If the JSR is completely new: Checkout the slides, read the spec, so you have a basic idea

Branch TCK and RI (sometimes you may also find an issue in the RI)

Update/checkout the JSR’s API, RI, JavaMoney parent and TCK Look for the test classes present in the TCK Select tests you want to contribute and coordinate with me Write the tests, if not sure how, you may ask me ;-) If it is the first time working on a TCK, you may do pair

programming with a more experienced person Commit your code to your branch Create a Git Pull Request

Page 39: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Adoption Areas JSR 354

Helping on the TCK (continued)

39

/**

* Test successful conversion for possible currency pairs.<br/>

* Hint: you may only check for rate factory, when using a hardcoded

* ExchangeRateProvider, such a provider

* must be also implemented and registered as an SPI.

*/

@Test @SpecAssertion(id = "432-A1", section="4.3.2")

public void testConversion(){

Assert.fail();

}

Describes the test

very briefly

References the according

section in the spec

Add your test code here.

Hint 1: if you are unsure first write a story line

Hint 2: some aspects may require to implement multiple

tests, just ensure the annotations are on all tests

Page 40: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Adoption Areas JSR 354

Extending the Reference Implementation

40

Objective: Adding functonalities to the RI

How:

If the JSR is completely new: Talk with me first

Discuss your ideas with me to see where your idea fits best

Branch RI (and/or JavaMoney Library)

Adding functonalities/tests to the RI (and/or JavaMoney Lib)

Write/enhance documentation Commit your changes Create a Pull Request

Page 41: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Adoption Areas JSR 354

Stabilizing JavaMoney Library

41

Objective: Help stabilizing the functionality of JavaMoney

How:

If the JSR is completely new: Talk with me first

Branch JavaMoney Library Write tests, e.g. for financial calculations

Write/enhance documentation

New functionalities: discuss with me first Commit your changes

Create a Pull Request

Page 42: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

Q & A

42

Page 43: Adopt JSR 354

Go for the money - JSR 354 - http://java.net/projects/javamoney March 2014

The End

43


Top Related