domain specific languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... ·...
TRANSCRIPT
![Page 1: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/1.jpg)
Domain Specific Languages
-a user view and an
implementation view
does expressiveness imply a compromise on the
underlying domain model ?
![Page 2: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/2.jpg)
Debasish Ghosh
@debasishg on twitter
Code @ http://github.com/debasishg
Blog @ Ruminations of a Programmer
http://debasishg.blogspot.com
![Page 3: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/3.jpg)
Open Source Footprints
Committer in Akka (http://akka.io)
Owner/Founder of :! sjson (JSON serializati on library for Scala objects !
http://github.com/debasishg/sjson )
! scala-redis (Redis client for Scala !http://github.com/debasishg/scala -redis)
! scouchdb (Scala driver for Couchdb !http://github.com/debasishg/scouchdb )
![Page 4: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/4.jpg)
model-view architecture of a DSL
how abstractions shape a DSL structure
choosing proper abstractions for compositionality
using proper language idioms
composing DSLs
![Page 5: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/5.jpg)
model-view architecture of a DSL
how abstractions shape a DSL structure
choosing proper abstractions for compositionality
using proper language idioms
composing DSLs
![Page 6: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/6.jpg)
ViewOr
Syntax
new_trade 'T-12435'for account 'acc-123'to buy 100 shares of 'IBM', at UnitPrice = 100,
Principal = 12000, Tax = 500
DSL
Model"
Semantic modelof the domain
![Page 7: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/7.jpg)
view / syntax
is derived from
model
![Page 8: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/8.jpg)
view / syntax
is a veneer of abstraction over
model
![Page 9: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/9.jpg)
view / syntax
is decoupled thru an interpreter from
model
![Page 10: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/10.jpg)
view / syntax
can be multiple over the same
model
![Page 11: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/11.jpg)
# create instrumentinstrument = Instrument.new('Google')
instrument.quantity = 100
#create tradeTrade.new('T-12435','acc-123', :buy, instrument, 'unitprice' => 200, 'principal' => 120000, 'tax' => 5000
)
idiomatic Ruby API
![Page 12: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/12.jpg)
new_trade 'T-12435'for account 'acc-123'to buy 100 shares of 'IBM', at UnitPrice = 100,
Principal = 12000, Tax = 500
add domain syntax
![Page 13: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/13.jpg)
new_trade 'T-12435'for account 'acc-123'to buy 100 shares of'IBM', at UnitPrice = 100,
Principal = 12000, Tax = 500
add domain syntax
![Page 14: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/14.jpg)
domain syntax
idiomatic Ruby model
interpreter
isolation layer between the model and the view of the DSL
![Page 15: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/15.jpg)
def parse(dsl_string)dsl = dsl_string.clonedsl.gsub!(/=/, '=>')dsl.sub!(/and /, '')dsl.sub!(/at /, '')dsl.sub!(/for account /, ',')dsl.sub!(/to buy /, ', :buy, ')dsl.sub!(/(\d+) shares of ('.*?')/,'\1.shares.of(\2)')
puts dsldsl
end
![Page 16: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/16.jpg)
Not all transformations can be done using simple regular expression
based string processing
![Page 17: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/17.jpg)
model-view architecture of a DSL
how abstractions shape a DSL structure
choosing proper abstractions for compositionality
using proper language idioms
composing DSLs
![Page 18: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/18.jpg)
" "
abstractions of the core domainmodel
layers of abstractions
![Page 19: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/19.jpg)
" "abstractions of the core domainmodel
abstractions thatglue modelelements
layers of abstractions
combinators, façade objects, bridges & adapters
![Page 20: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/20.jpg)
" "abstractions of the core domainmodel
abstractions thatglue modelelements
layers of abstractions
combinators, façade objects, bridges & adapters
domain specific embedded language
![Page 21: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/21.jpg)
" "abstractions of the core domainmodel
abstractions thatglue modelelements
layers of abstractions
combinators, façade objects, bridges & adapters
domain specific embedded language
mo
del
vie
w
![Page 22: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/22.jpg)
layers of abstractions ..
keep the underlying domain model cleanensure separation of concerns between the model and the view of the DSLyou can also implement the glue layer using a different programming language (polyglot programming)
![Page 23: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/23.jpg)
withAccount(trade) { account => {settle(trade usingaccount.getClient
.getStandingRules
.filter(_.account == account)
.first)andThen journalize
}}
DSL in Scala over a Java domain model
![Page 24: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/24.jpg)
withAccount(trade) { account => {
settle(trade usingaccount.getClient
.getStandingRules
.filter(_.account == account)
.first)andThen journalize
}}
DSL in Scala over a Java domain model
Java abstractions
![Page 25: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/25.jpg)
withAccount(trade) { account => {
settle(trade usingaccount.getClient
.getStandingRules
.filter(_.account == account)
.first)andThen journalize
}}
DSL in Scala over a Java domain model
Java abstractions
Wired throughScala control structures
![Page 26: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/26.jpg)
We need abstractions that generalize over computations ..
![Page 27: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/27.jpg)
Our domain stocks, trades, bulls, bears ..
Security tradeExchange of securities and currencies (also known as Instruments)In the stock exchange (market)On a specified "trade date"Between counter partiesIn defined quantitiesAt market ratesResulting in a net cash value for the sellerOn the "value date"
![Page 28: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/28.jpg)
Our domain stocks, trades, bulls, bears ..
Security tradeExchange of securities and currencies (also known as Instruments)In the stock exchange (market)On a specified "trade date"Between counter parties' accountsIn defined quantitiesAt market ratesResulting in a net cash value for the sellerOn the "value date"
![Page 29: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/29.jpg)
// The Trade modelcase class Trade(account: Account, instrument: Instrument, referenceNo: String, market: Market,unitPrice: BigDecimal, quantity: BigDecimal, tradeDate: Date = Calendar.getInstance.getTime, valueDate: Option[Date] = None, taxFees: Option[List[(TaxFeeId, BigDecimal)]] =
None, netAmount: Option[BigDecimal] = None)
![Page 30: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/30.jpg)
// various tax/fees to be paid when u do a tradesealed trait TaxFeeIdcase object TradeTax extends TaxFeeIdcase object Commission extends TaxFeeIdcase object VAT extends TaxFeeIdcase object Surcharge extends TaxFeeId
![Page 31: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/31.jpg)
// computes value date of a tradeval valueDateProcessor: Trade => Trade = //.. impl
// computes tax/fee of a tradeval taxFeeProcessor: Trade => Trade = //.. Impl
// computes the net cash value of a tradeval netAmountProcessor: Trade => Trade = //.. impl
![Page 32: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/32.jpg)
val trades = //.. list of security trades
// get a list of value dates for all tradesval valueDates = trades map (_.valueDate)
// enrich a trade passing it thru multiple processorsval richTrade = (valueDateProcessor map
taxFeeProcessor map netAmountProcessor) apply
trade
// pass a trade thru one specific processorval t = some(trade) map valueDateProcessor
![Page 33: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/33.jpg)
val trades = //.. list of security trades
// get a list of value dates for all trades
val valueDates = trades map (_.valueDate)// enrich a trade passing it thru multiple processors
val richTrade = (valueDateProcessor map
taxFeeProcessor map
netAmountProcessor) apply trade
// pass a trade thru one specific processor
val t = some(trade) mapvalueDateProcessor
![Page 34: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/34.jpg)
val trades = //.. list of security trades
// get a list of value dates for all trades
val valueDates = trades map (_.valueDate)
// enrich a trade passing it thru multiple processors
val richTrade = (valueDateProcessor maptaxFeeProcessor mapnetAmountProcessor) apply
trade
// pass a trade thru one specific processor
val t = some(trade) map valueDateProcessor
![Page 35: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/35.jpg)
val trades = //.. list of security trades
// map across the list functorval valueDates = trades map (_.valueDate)
// map across the Function1 functorval richTrade = (valueDateProcessor map
taxFeeProcessor map netAmountProcessor) apply
trade
// map across an Option functorval t = some(trade) map valueDateProcessor
![Page 37: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/37.jpg)
a map ..pimps abstractions to give us an ad hoc
polymorphism implementation on top of OO
![Page 38: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/38.jpg)
a map is ..fundamentally powered by type classes
![Page 39: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/39.jpg)
sealed trait MA[M[_], A] extends PimpedType[M[A]] {def map[B](f: A => B)(implicit t: Functor[M]): M[B] =t.fmap(value, f)
source: scalaz : https://github.com/scalaz/scalaz
a type class
a pimp
![Page 40: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/40.jpg)
trait Functor[F[_]] extends InvariantFunctor[F] {def fmap[A, B](r: F[A], f: A => B): F[B]
}
source: scalaz : https://github.com/scalaz/scalaz
![Page 41: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/41.jpg)
a functor is ..a type class for all things that can be mapped over
![Page 42: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/42.jpg)
// map across the Function1 functorval richTrade = (valueDateProcessor map
taxFeeProcessor map netAmountProcessor) apply
trade
Function1[]implicit def Function1Functor[R] =
new Functor //..
![Page 43: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/43.jpg)
the idea is to generalize abstractions ..
.. and by generalizing map over functors we get a combinator that can glue a large set of our domainabstractions
.. and this gives a feeling of uniformity in the DSL syntax
![Page 44: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/44.jpg)
semantic model+
combinators=
DSL
![Page 45: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/45.jpg)
model-view architecture of a DSL
how abstractions shape a DSL structure
choosing proper abstractions for compositionality
using proper language idioms
composing DSLs
![Page 46: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/46.jpg)
a DSL ..
evolves from the model non-invasivelyusing combinatorsthat compose model elementsinterprets them into computations of the domain
![Page 47: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/47.jpg)
so, a domain model also has to be ..
designed for compositionality
Image source: Mathematic al art of M. C. Escher (http://im-possible.info/english/articles/escher_math/escher_math.html)
![Page 48: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/48.jpg)
domain rule ..
enrichment of trade is done in steps:
1.get the tax/fee ids for a trade2.calculate tax/fee values3.enrich trade with net cash amount
![Page 49: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/49.jpg)
the DSL ..val enrich = for {
// get the tax/fee ids for a tradetaxFeeIds <- forTrade
// calculate tax fee valuestaxFeeValues <- taxFeeCalculate
// enrich trade with net cash amountnetAmount <- enrichTradeWith
}yield((taxFeeIds map taxFeeValues) map netAmount)
// enriching a tradetrade map enrich should equal( )
![Page 50: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/50.jpg)
the DSL ..val enrich = for {
// get the tax/fee ids for a tradetaxFeeIds <- forTrade
// calculate tax fee valuestaxFeeValues <- taxFeeCalculate
// enrich trade with net cash amountnetAmount <- enrichTradeWith
}yield((taxFeeIds map taxFeeValues) map netAmount)
// enriching a tradetrade map enrich should equal( )
Model elementsthat can be composedusing the for-comprehension
![Page 51: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/51.jpg)
reiterating ..
a combinator acts ..as a glue combining model elements
But ..
![Page 52: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/52.jpg)
there is a prerequisite ..
model elements should be composable
we call this the compositionality of the model
![Page 53: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/53.jpg)
Q: How to design your model
so that it's compositional ?
A: choose the right abstractions ..
depending on the programming paradigm(FP, OO ..) and the implementation
language used
![Page 54: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/54.jpg)
domain rule ..
net cash value calculation of trade:
1.use strategy for specific markets, if available2.otherwise use default strategy3.we can supply specific strategy inline as well
![Page 55: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/55.jpg)
the DSL ..// type alias for domain vocabularytype NetAmount = BigDecimaltype CashValueCalculationStrategy =PartialFunction[Market, Trade => NetAmount]
// declarative business logicval cashValueComputation: Trade => NetAmount = { trade => (forHongKong orElseforSingapore orElseforDefault)(trade.market)(trade)
}
![Page 56: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/56.jpg)
the DSL ..val cashValue: Trade => CashValueCalculationStrategy => NetAmount{ trade => pf =>if (pf.isDefinedAt(trade.market))pf(trade.market)(trade)
else cashValueComputation(trade)}
![Page 57: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/57.jpg)
PartialFunction is ..the secret sauce
all functions for specific and default computation
return PartialFunction
that offer combinators for chaining of abstractions ..
![Page 58: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/58.jpg)
val forHongKong: CashValueCalculationStrategy = {case HongKong => { trade => //.. }
}
val forSingapore: CashValueCalculationStrategy = {case Singapore => { trade => //.. }
}
val forDefault: CashValueCalculationStrategy = {case _ => { trade => //.. }
}
![Page 59: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/59.jpg)
model-view architecture of a DSL
how abstractions shape a DSL structure
choosing proper abstractions for compositionality
using proper language idioms
composing DSLs
![Page 60: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/60.jpg)
choice of abstractions depends
on the programming language chosen for implementation of your DSL
always keep an eye on the paradigms that yourimplementation language supports and play to
the idioms of the language
![Page 61: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/61.jpg)
domain rule ..
A trade needs to be enriched with a set of tax and feesbefore we calculate its net cash value
![Page 62: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/62.jpg)
the Java way ..
// use the decorator patternnew CommissionDecorator(new TaxFeeDecorator(new Trade(..)));
public class Trade { //..
public class TaxFeeDecorator extends Trade {private Trade trade;//..
}public class CommissionDecorator extends Trade {private Trade trade;//..
}
![Page 63: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/63.jpg)
the Java way ..
decorators and the decoratee share a common interfacestatically coupled through inheritancethe decorator usage syntax is outside-in
![Page 64: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/64.jpg)
the Ruby way ..
## decorator patternTrade.new(..).with TaxFee, Commission
class Tradeattr_accessor ..def initialize ..def with(*args)args.inject(self) {|memo, val| memo.extend val
enddef value@principal
endend
![Page 65: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/65.jpg)
the Ruby way ..
## mixinsmodule TaxFee## calculate taxfeedef valuesuper + ..
endend
## mixinsmodule Commission## calculate commissiondef valuesuper + ..
endend
![Page 66: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/66.jpg)
the Ruby way ..
more dynamic compared to Javauses Ruby idioms of runtime meta-programmingdecorators don t statically extend the core abstraction
![Page 67: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/67.jpg)
if we were to do the same in Clojure ..
## decorator pattern(with-tax-fee trade(with-values :tax 12)(with-values :commission 23))
(defmacro with-tax-fee"wrap a function in one or more decorators"[func & decorators]`(redef ~func (-> ~func ~@decorators)))
![Page 68: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/68.jpg)
the Clojure way ..
more functional uses HOFfunction threading makes the decorator implementation almost trivialcontrol structure uses macros, which are compile time meta-programming artifacts (unlike Ruby) no run time overhead
![Page 69: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/69.jpg)
model-view architecture of a DSL
how abstractions shape a DSL structure
choosing proper abstractions for compositionality
using proper language idioms
composing DSLs
![Page 70: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/70.jpg)
if you thought DSLs grow through composition of abstractions ..
.. then the final DSL is the whole formed from the composition of its parts ..
![Page 71: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/71.jpg)
and if the final DSL is also an abstraction ..
.. there's no reason we can compose it with another abstraction (aka another DSL) to form a bigger whole ..
![Page 72: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/72.jpg)
trait TradeDsl {type T <: Tradedef enrich: PartialFunction[T,
T]
//.. other methods}
constrained abstract type
abstract method
![Page 73: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/73.jpg)
trait FixedIncomeTradeDsl extends TradeDsl {type T = FixedIncomeTrade
import FixedIncomeTradingService._override def enrich: PartialFunction[T, T] = {
case t =>t.cashValue = cashValue(t)t.taxes = taxes(t)t.accruedInterest = accruedInterest(t)t
}}
object FixedIncomeTradeDslextends FixedIncomeTradeDsl
concrete type for fixed income trade
concrete definition forenrichment of fixed income trade
![Page 74: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/74.jpg)
trait EquityTradeDsl extends TradeDsl {type T = EquityTrade
import EquityTradingService._override def enrich: PartialFunction[T, T] = {
case t =>t.cashValue = cashValue(t)t.taxes = taxes(t)t
}}
object EquityTradeDslextends EquityTradeDsl
concrete type for equity trade
concrete definition forenrichment of equity trade
![Page 75: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/75.jpg)
.. and now a new market rule comes up that needs to be applied to all types of trades
.. you don t want to affect the core logic, since the rule is a temporary and promotional one and is likely to be discontinued after a few days ..
![Page 76: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/76.jpg)
.. design the DSL for the new rule in such a way that you can plug in the semantics of all types of trade within it ..
![Page 77: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/77.jpg)
and now the rule itself ..
Any trade on the New York Stock Exchange of principal value > 10,000 USD must have a discount of 10% of the principal on the net cash value.
![Page 78: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/78.jpg)
trait MarketRuleDsl extends TradeDsl {val semantics: TradeDsltype T = semantics.Toverride def enrich: PartialFunction[T, T] = {
case t =>val tr = semantics.enrich(t)tr match {
case x if x.market == NYSE && x.principal > 1000 =>
tr.cashValue = tr.cashValue - tr.principal * 0.1
trcase x => x
}}
}
![Page 79: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/79.jpg)
trait MarketRuleDsl extends TradeDsl {val semantics: TradeDsltype T = semantics.Toverride def enrich: PartialFunction[T, T] = {
case t =>val tr = semantics.enrich(t)tr match {
case x if x.market == NYSE && x.principal > 1000 =>
tr.cashValue = tr.cashValue - tr.principal * 0.1
trcase x => x
}}
}
polymorphic embedding
new business rule that actson top of the enriched trade
![Page 80: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/80.jpg)
object EquityTradeMarketRuleDsl extends MarketRuleDsl {val semantics = EquityTradeDsl
}
object FixedIncomeTradeMarketRuleDsl extendsMarketRuleDsl {
val semantics = FixedIncomeTradeDsl}
pluggable composition of DSLs
plug-in the concrete semantics
![Page 81: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/81.jpg)
import FixedIncomeTradeMarketRuleDsl._
withTrade(200 discount_bonds IBM
for_client NOMURAon NYSEat 72.ccy(USD)) {trade =>
Mailer(user) mail tradeLogger log trade
} cashValue
a sneak peek at the
fully composed DSL ..
![Page 82: Domain Specific Languageschariotsolutions.com/wp-content/uploads/presentations/archive/579/... · Domain Specific Languages-a user view and an implementation view does expressiveness](https://reader035.vdocument.in/reader035/viewer/2022071218/6053648adea3863c48672908/html5/thumbnails/82.jpg)
Summary
A DSL has a syntax (for the user) and a model (for the implementer)
The syntax is the view designed on top of the model
The model needs to be clean and extensible to support seamless development of domain syntax
The model needs to be compositional so that various model elements can be glued together using combinators to make an expressive syntax