マイクロサービスアーキテクチャでサービス分割の指針としてドメイン駆動設計が再び注目されています。このLTではLambda函数でドメインモデルを実装しユニットテストを実施する方法について15分で紹介することにチャレンジします。 詳細は以下の記事をご覧ください。 https://qiita.com/afukui/items/c705aca2cb46e182c5e4
© 2021, Amazon Web Services, Inc. or its Affiliates.
View Slide
© 2021, Amazon Web Services, Inc. or its Affiliates.Atsushi FukuiSenior Solutions ArchitectServerless SpecialistAmazon Web Services JapanDDD on AWS LambdaHow to implement your domain models on your AWS Lambda functionJAWS PANKLATION 20212021/11/20
© 2021, Amazon Web Services, Inc. or its Affiliates.Who am Iv Namev Atsushi Fukui / twitter: [email protected]v Role and companyv Senior Solutions Architect Serverless Specialistv Amazon Web Services Japanv Interestsv Software Architecture, Object Oriented Design and programming,Agile Development processv My favorite AWS Servicesv AWS Lambda, AWS Step SQS and other all serverless services
© 2021, Amazon Web Services, Inc. or its Affiliates.Agendao Domain Driven Design (DDD)o Hexagonal Architectureo Domain models for sample applicationo How to implement unit testing codeo Demoo Conclusion
© 2021, Amazon Web Services, Inc. or its Affiliates.Domain-driven designo Provides a broad framework formaking design decisions anddeveloping a technicalvocabulary for discussingdomain designo Ubiquitous language - modelingthe language of the businesso Provides guidance abouttactical design - model domainswith entities, value objects,repositories and services, andstrategic design…
© 2021, Amazon Web Services, Inc. or its Affiliates.Hexagonal architectureDomainModelPortsAdaptersPrimaryActorSecondaryActorHTTP RequestEvent MessageQueue…File StorageDatabaseQueue…
© 2021, Amazon Web Services, Inc. or its Affiliates.Sample Senarioo Vaccination reservation systemo Use cases:o A recipient can search for some vacant slots and register a reservation slot forvaccination reservation.o A recipient cannot register her reservation if there is no vacant slot.o A recipient cannot reserve her reservations more than two slots.o A recipient cannot reserve two reservations if there are same date time.There are pure business logics you need to implement on your domain model.
© 2021, Amazon Web Services, Inc. or its Affiliates.Class diagram: register vaccination reservation
© 2021, Amazon Web Services, Inc. or its Affiliates.Sequence diagram: register vaccination reservation
© 2021, Amazon Web Services, Inc. or its Affiliates.Hexagonal architecture with the Lambda functionDomainModelPortsAdaptersAmazon API Gateway Amazon DynamoDBAWS Lambda function
© 2021, Amazon Web Services, Inc. or its Affiliates.Implement domain models
© 2021, Amazon Web Services, Inc. or its Affiliates.Domain modelsfrom slot import Slotclass Recipient:def __init__(self, recipient_id:str, email:str, first_name:str, last_name:str, age:int):self.__recipient_id = recipient_id….@propertydef recipient_id(self):return self.__recipient_id…def add_reserve_slot(self, slot:Slot) -> bool:if self.are_slots_same_date(slot):return Falseif self.is_slot_counts_equal_or_over_two():return Falseself.__slots.append(slot)slot.use_slot()
© 2021, Amazon Web Services, Inc. or its Affiliates.Unit testing for functions
© 2021, Amazon Web Services, Inc. or its Affiliates.Unit test for Domain Modeldef test_cannot_append_slot_more_than_two(fixture_recipient, fixture_slot, fixture_slot_2, fixture_slot_3):slot = fixture_slotslot2 = fixture_slot_2slot3 = fixture_slot_3target = fixture_recipienttarget.add_reserve_slot(slot)target.add_reserve_slot(slot2)ret = target.add_reserve_slot(slot3)assert False == retassert 2 == len(target.slots)def test_cannot_append_same_date_slot(fixture_recipient, fixture_slot):slot = fixture_slottarget = fixture_recipienttarget.add_reserve_slot(slot)ret = target.add_reserve_slot(slot)assert False == retassert 1 == len(target.slots)
© 2021, Amazon Web Services, Inc. or its Affiliates.Unit test for Ports and Adapters classesclass DummyRecipientAdapter(IRecipientAdapter):def load(self, recipient_id:str) -> Recipient:return Recipient(recipient_id, email, first_name, last_name, age)def save(self, recipient:Recipient) -> bool:return Trueclass DummyModule(Module):def configure(self, binder):binder.bind(RecipientPort, to=RecipientPort(DummyRecipientAdapter()))@pytest.fixture()def fixture_recipient_port():injector = Injector([DummyModule])recipient_port = injector.get(RecipientPort)return recipient_port
© 2021, Amazon Web Services, Inc. or its Affiliates.Unit test for Ports and Adapters classesdef test_recipient_port_recipient_by_id(fixture_recipient_port):target = fixture_recipient_portrecipient_id = "dummy_number"recipient = target.recipient_by_id(recipient_id)assert recipient != Noneassert recipient_id == recipient.recipient_idassert email == recipient.emailassert first_name == recipient.first_nameassert last_name == recipient.last_nameassert age == recipient.age
© 2021, Amazon Web Services, Inc. or its Affiliates.app.py calls concrate class instancesclass RequestPortModule(Module):def configure(self, binder):binder.bind(ReservationService, to=ReservationService(RecipientPort(DDBRecipientAdapter()), SlotPort(DDBSlotAdapter())))def lambda_handler(event, context):body = json.loads(event['body'])recipient_id = body['recipient_id']slot_id = body['slot_id']injector = Injector([RequestPortModule])request_port = injector.get(RequestPort)status = request_port.make_reservation(recipient_id, slot_id)
© 2021, Amazon Web Services, Inc. or its Affiliates.Demo
© 2021, Amazon Web Services, Inc. or its Affiliates.Summaryo Loosely coupling and strong encapsulation are key concept.o Hexagonal architecture is an architecture pattern used for encapslatingdomain logic, and decoupling it from other implementaion details, such asinfrastructure or client requests.o This approach can help create separetion of concerns and sepalate thedomain logic from the infrastructure.o Inversion of control (IoC) or injecting object instances is useful for unittesting with mock or fake objects.
© 2021, Amazon Web Services, Inc. or its Affiliates.Please see my sample project on GitHubo https://github.com/afukui/jaws-pankration-ddd-lambda
© 2021, Amazon Web Services, Inc. or its Affiliates.Thank you!