URDAD

This document was generated from the URDAD model Online Auctioneer. It specifies what the business requires, independently of any technology.

It is written to be read without knowledge of URDAD or of its diagrams, as every diagram is followed by a description of what it shows, in words. The specification is organised by responsibility domain. For each, it describes the services the domain provides, i.e. what each requires and guarantees, the information exchanged with it, how the work is allocated to other domains and the business process which provides it. It then describes the entities the domain maintains, the services it depends on from other domains, and finally its lower-level responsibility domains, each in a part of its own. The first part is the model itself, specified as the responsibility domain which contains all the others. It gives the model’s scope and the top-level responsibility domains it decomposes into.

1. Online Auctioneer

This part specifies the model Online Auctioneer as a whole. The model is the responsibility domain which contains all the others. It decomposes into top-level responsibility domains, each of which provides services to others and may in turn rely on services of other domains.

An online auction platform: members list items, bid for them, and complete each sale.

An example model of an eBay-like auctioneer, built on StandardLib, FinanceLib and CommerceLib. Formal URDAD-OCL is written at the leaf services; each use case keeps its pre- and post-conditions in prose and delegates them whole to the service that meets them.

The scope diagram below shows what Online Auctioneer is responsible for, i.e. the top-level responsibility domains it decomposes into.

The scope of Online Auctioneer.
Figure 1. The scope of Online Auctioneer.

1.1. Lower-level responsibilities

Online Auctioneer decomposes into the following top-level responsibility domains, each specified in the same way:

  • Administrator: A person who sets the platform’s terms.

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

  • Bank: The bank that pays sellers.

  • Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

  • Payment Gateway: The card processor that charges buyers.

2. Administrator

This part specifies the Administrator responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

A person who sets the platform’s terms.

The scope diagram below shows what Administrator is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Administrator.
Figure 2. The scope of Administrator.

Nothing has been specified within this responsibility domain yet.

3. Auctioneer

This part specifies the Auctioneer responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

The online auctioneer: runs the auctions and completes each sale.

The organisation whose platform this is. Stakeholder of the platform's own rules: who may bid, when an auction closes, what the platform charges.

The scope diagram below shows what Auctioneer is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Auctioneer.
Figure 3. The scope of Auctioneer.

3.1. Dependencies

To provide its services, Auctioneer relies on services provided by other responsibility domains. The dependency diagram below shows which.

The responsibility domains Auctioneer depends on.
Figure 4. The responsibility domains Auctioneer depends on.

Auctioneer uses:

  • from Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

  • from Payment Gateway: The card processor that charges buyers.

  • from Bank: The bank that pays sellers.

    • the Pay seller service: Pays an amount into a seller’s account.

3.2. Lower-level responsibilities

Auctioneer delegates part of its responsibility to the following lower-level responsibility domains, each specified in the same way:

  • Listings: What is on offer and what was bid for it.

  • Membership: Who the members are.

  • Platform: The platform’s terms, the service fee among them.

  • Sales: Completing a sale: payment, payout, shipping and feedback.

4. Auctioneer / Listings

This part specifies the Listings responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

What is on offer and what was bid for it.

The scope diagram below shows what Listings is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Listings.
Figure 5. The scope of Listings.

4.1. Services

Listings is responsible for providing the following services. Each is described in its own section below: what it requires and what it guarantees (its service requirements), the information exchanged with it, how the work is allocated to the responsibility domains taking part, and the business process providing it.

  • Close listing: Closes a listing at its closing time and reports the highest bid, if any.

  • List item: A member offers an item for auction.

  • Place bid: A member bids for an item on offer.

  • Record bid: Records a bid for an open listing.

  • Record listing: Records an item offered for auction.

4.1.1. Service: Close listing

Listings provides the Close listing service.

Closes a listing at its closing time and reports the highest bid, if any.

Service requirements

The functional requirements diagram below shows who has an interest in the Close listing service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Close listing service.
Figure 6. Functional requirements of the Close listing service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-conditions Closing time reached and Listing still open.

  • Listings: What is on offer and what was bid for it.

    Listings requires the post-condition Listing closed.

  • Sales: Completing a sale: payment, payout, shipping and feedback.

    Sales requires the post-conditions Highest bid reported, Listing reported and Seller is a member.

It is provided only when:

  • Closing time reached: A listing is not closed early.

    Required by Auctioneer. Formally: Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies l.closesAt <= now())

  • Listing still open: A listing is closed once.

    Required by Auctioneer. Formally: Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.status = ListingStatus::open)

Once it has been provided:

  • Highest bid reported: The highest of the bids made is answered, and none where none was made.

    Required by Sales. Formally: response.winningBid = if Listing.allInstances()->any(l | l.listingNumber = request.listingNumber).bids->isEmpty() then null else Listing.allInstances()->any(l | l.listingNumber = request.listingNumber).bids->sortedBy(b | b.amount.amount)->last() endif

  • Listing closed: The listing takes no more bids.

    Required by Listings. Formally: Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.status = ListingStatus::closed)

  • Listing reported: What a sale needs of the listing is answered.

    Required by Sales. Formally: response.title = Listing.allInstances()->any(l | l.listingNumber = request.listingNumber).title and response.sellerLogin = Listing.allInstances()->any(l | l.listingNumber = request.listingNumber).seller.login and response.shippingCost = Listing.allInstances()->any(l | l.listingNumber = request.listingNumber).shippingCost

  • Seller is a member: The seller answered is a member, so a sale can ask Membership about them.

    Required by Sales. Formally: Member.allInstances()->collect(m | m.login)->includes(response.sellerLogin)

Exceptions

When a pre-condition does not hold, the Close listing service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Closing time reached not met, raised when Closing time reached does not hold: Raised when 'Close listing' is requested while 'Closing time reached' does not hold.

  • Listing still open not met, raised when Listing still open does not hold: Raised when 'Close listing' is requested while 'Listing still open' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Listings::Request.

What is supplied when requesting 'Close listing'.

The Auctioneer::Listings::Request data structure
Figure 7. The Auctioneer::Listings::Request data structure, fully expanded.

A Auctioneer::Listings::Request has:

  • one listingNumber (its type is not yet specified): The listing to close.

Response data structure

The information the service returns once provided is a Auctioneer::Listings::Response.

What 'Close listing' answers with.

The Auctioneer::Listings::Response data structure
Figure 8. The Auctioneer::Listings::Response data structure, fully expanded.

A Auctioneer::Listings::Response has:

  • one sellerLogin (its type is not yet specified): The seller, by their login.

  • one shippingCost (its type is not yet specified): What the buyer pays for shipping.

  • one title (its type is not yet specified): What the item is.

  • optionally one winningBid, a Auctioneer::Listings::Bid: The highest bid, where any was made.

Auctioneer::Listings::Bid: One bid made for a listing.

A Auctioneer::Listings::Bid has:

  • one amount (its type is not yet specified): What they bid.

  • one bidderLogin (its type is not yet specified): Who bid, by their login.

  • one placedAt (its type is not yet specified): When the bid was made.

Business process

No business process is needed. The service’s post-conditions say exactly what it records, i.e. it updates a Listing. It is thus provided by making that one change.

4.1.2. Service: List item

Listings provides the List item service.

A member offers an item for auction.

Service requirements

The functional requirements diagram below shows who has an interest in the List item service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the List item service.
Figure 9. Functional requirements of the List item service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-conditions Closes in the future and May sell.

  • Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

    Member requires the post-conditions Auction closed at its closing time and Item listed.

It is provided only when:

  • Closes in the future: An auction cannot close before it opens.

    Required by Auctioneer. Formally: request.closesAt > now()

  • May sell: The person listing is a member.

    Required by Auctioneer. Formally, as the services refining it state it: Member.allInstances()->exists(m | m.login = caller)

Once it has been provided:

  • Auction closed at its closing time: At its closing time the listing is closed, and sold to its highest bidder if anyone bid.

    Required by Member.

  • Item listed: The item is on offer in the seller’s name, open for bids.

    Required by Member. Formally, as the services refining it state it: Listing.allInstances@pre()->forAll(l | l.listingNumber <> response.listingNumber) and Listing.allInstances()->exists(l | l.listingNumber = response.listingNumber and l.seller.login = caller and l.title = request.title and l.description = request.description and l.photos = request.photos and l.documents = request.documents and l.condition = request.condition and l.startingBid = request.startingBid and l.shippingCost = request.shippingCost and l.closesAt = request.closesAt and l.status = ListingStatus::open and l.bids = Set{})

Exceptions

When a pre-condition does not hold, the List item service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Closes in the future not met, raised when Closes in the future does not hold: Raised when 'List item' is requested while 'Closes in the future' does not hold.

  • May sell not met, raised when May sell does not hold: Raised when 'List item' is requested while 'May sell' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Listings::Request.

What is supplied when requesting 'List item'.

The Auctioneer::Listings::Request data structure
Figure 10. The Auctioneer::Listings::Request data structure, fully expanded.

A Auctioneer::Listings::Request has:

  • one closesAt (its type is not yet specified): When bidding closes.

  • one condition (its type is not yet specified): The state the item is in.

  • one description (its type is not yet specified): The item described.

  • any number of documents (its type is not yet specified): Supporting documents, by URL.

  • between 1 and 12 photos (its type is not yet specified): Photos of the item, by URL.

  • one shippingCost (its type is not yet specified): What the buyer pays for shipping.

  • one startingBid (its type is not yet specified): The lowest bid to accept.

  • one title (its type is not yet specified): What the item is, in a line.

The following must always hold for a Auctioneer::Listings::Request:

  • Amounts in euro: self.startingBid.currency = Currency::EUR and self.shippingCost.currency = Currency::EUR

  • Shipping cost is not negative: self.shippingCost.amount >= 0

  • Starting bid is positive: self.startingBid.amount > 0

Response data structure

The information the service returns once provided is a Auctioneer::Listings::Response.

What 'List item' answers with.

The Auctioneer::Listings::Response data structure
Figure 11. The Auctioneer::Listings::Response data structure, fully expanded.

A Auctioneer::Listings::Response has:

  • one listingNumber (its type is not yet specified): The listing number issued.

Responsibility allocation

The responsibility allocation diagram below shows how the List item process takes care of each requirement of the List item service. It shows which of its steps addresses each pre- and post-condition, and which services it uses from other responsibility domains to do so.

Responsibility allocation for the List item process.
Figure 12. Responsibility allocation for the List item process.

Requirement by requirement:

  • Closes in the future (pre-condition) is addressed by checking it before anything else is done.

  • May sell (pre-condition) is addressed by requesting the Record listing service from Listings.

  • Auction closed at its closing time (post-condition) is addressed by requesting the Complete sale service from Sales.

  • Item listed (post-condition) is addressed by requesting the Record listing service from Listings.

To do so the process uses the following services:

Business process

Records the listing in the caller’s name, answers, and closes the auction at its closing time.

The List item business process provides the List item service. The diagram below shows its flow. The numbered steps after it describe the same flow in words, with each choice, loop and parallel flow holding its own steps beneath it.

The business process List item.
Figure 13. The business process List item.

Step by step:

  1. Check that Closes in the future holds. If it does not, stop and raise Closes in the future not met.

    Formally: request.closesAt > now()

  2. Request the Record listing service from Listings.

    This step addresses Item listed and May sell.

    The request is populated as follows:

    • closesAt: providerRequest.closesAt = request.closesAt

    • condition: providerRequest.condition = request.condition

    • description: providerRequest.description = request.description

    • documents: providerRequest.documents = request.documents

    • photos: providerRequest.photos = request.photos

    • sellerLogin: providerRequest.sellerLogin = caller

    • shippingCost: providerRequest.shippingCost = request.shippingCost

    • startingBid: providerRequest.startingBid = request.startingBid

    • title: providerRequest.title = request.title

      The answer is kept as listed, one Auctioneer::Listings::Response.

  3. Do the following at the same time, and carry on once all of them are done:

    • Flow 1:

      1. Populate the response.

        • listingNumber: response.listingNumber = listed.listingNumber

    • Flow 2:

      1. In the background, without the process waiting for it:

        1. Wait for whichever of the following happens first, and react to it:

          • When the time reaches request.closesAt:

            1. Request the Complete sale service from Sales.

              This step addresses Auction closed at its closing time.

              The request is populated as follows:

              • listingNumber: providerRequest.listingNumber = listed.listingNumber

              • If it raises Highest bidder can buy not met:

                the exception is ignored and the process carries on.

              • If it raises Listing ready to close not met:

                the exception is ignored and the process carries on.

4.1.3. Service: Place bid

Listings provides the Place bid service.

A member bids for an item on offer.

Service requirements

The functional requirements diagram below shows who has an interest in the Place bid service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Place bid service.
Figure 14. Functional requirements of the Place bid service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-condition Bid acceptable.

  • Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

    Member requires the post-condition Bid placed.

It is provided only when:

  • Bid acceptable: The bid is one the auction takes.

    Required by Auctioneer. Formally, as the services refining it state it: Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies if l.bids->isEmpty() then request.amount.amount >= l.startingBid.amount else request.amount.amount > l.bids->collect(b | b.amount.amount)->max() endif) and Member.allInstances()->exists(m | m.login = caller) and Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies l.seller.login <> caller) and Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies now() < l.closesAt) and Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.status = ListingStatus::open)

Once it has been provided:

  • Bid placed: The bid stands, in the bidder’s name.

    Required by Member. Formally, as the services refining it state it: Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.bids = l.bids@pre->including(Tuple{bidderLogin = caller, amount = request.amount, placedAt = now()}))

Exceptions

When a pre-condition does not hold, the Place bid service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Bid acceptable not met, raised when Bid acceptable does not hold: Raised when 'Place bid' is requested while 'Bid acceptable' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Listings::Request.

What is supplied when requesting 'Place bid'.

The Auctioneer::Listings::Request data structure
Figure 15. The Auctioneer::Listings::Request data structure, fully expanded.

A Auctioneer::Listings::Request has:

  • one amount (its type is not yet specified): What they bid.

  • one listingNumber (its type is not yet specified): The listing bid for.

The following must always hold for a Auctioneer::Listings::Request:

  • Bid in euro: self.amount.currency = Currency::EUR

Response data structure

The information the service returns once provided is a Auctioneer::Listings::Response.

What 'Place bid' answers with.

The Auctioneer::Listings::Response data structure
Figure 16. The Auctioneer::Listings::Response data structure, fully expanded.

A Auctioneer::Listings::Response carries no information of its own.

Responsibility allocation

The responsibility allocation diagram below shows how the Place bid process takes care of each requirement of the Place bid service. It shows which of its steps addresses each pre- and post-condition, and which services it uses from other responsibility domains to do so.

Responsibility allocation for the Place bid process.
Figure 17. Responsibility allocation for the Place bid process.

Requirement by requirement:

  • Bid acceptable (pre-condition) is addressed by requesting the Record bid service from Listings.

  • Bid placed (post-condition) is addressed by requesting the Record bid service from Listings.

To do so the process uses the following services:

Business process

Records the bid in the caller’s name.

The Place bid business process provides the Place bid service. The diagram below shows its flow. The numbered steps after it describe the same flow in words, with each choice, loop and parallel flow holding its own steps beneath it.

The business process Place bid.
Figure 18. The business process Place bid.

Step by step:

  1. Request the Record bid service from Listings.

    This step addresses Bid acceptable and Bid placed.

    The request is populated as follows:

    • amount: providerRequest.amount = request.amount

    • bidderLogin: providerRequest.bidderLogin = caller

    • listingNumber: providerRequest.listingNumber = request.listingNumber

4.1.4. Service: Record bid

Listings provides the Record bid service.

Records a bid for an open listing.

Service requirements

The functional requirements diagram below shows who has an interest in the Record bid service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Record bid service.
Figure 19. Functional requirements of the Record bid service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-conditions Bid above the current price, Bidder is a member, Bidder is not the seller, Bidding has not closed and Listing is open.

  • Listings: What is on offer and what was bid for it.

    Listings requires the post-condition Bid recorded.

It is provided only when:

  • Bid above the current price: A first bid is at least the starting bid; any later one beats the highest so far.

    Required by Auctioneer. Formally: Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies (if l.bids->isEmpty() then request.amount.amount >= l.startingBid.amount else request.amount.amount > l.bids->collect(b | b.amount.amount)->max() endif))

  • Bidder is a member: Only a member may bid.

    Required by Auctioneer. Formally: Member.allInstances()->exists(m | m.login = request.bidderLogin)

  • Bidder is not the seller: A seller may not bid for their own item.

    Required by Auctioneer. Formally: Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies l.seller.login <> request.bidderLogin)

  • Bidding has not closed: No bid is taken once the closing time has passed.

    Required by Auctioneer. Formally: Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies now() < l.closesAt)

  • Listing is open: Bids are taken only for a listing still open.

    Required by Auctioneer. Formally: Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.status = ListingStatus::open)

Once it has been provided:

  • Bid recorded: The bid is kept with the listing, as made now.

    Required by Listings. Formally: Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.bids = l.bids@pre->including(Tuple{bidderLogin = request.bidderLogin, amount = request.amount, placedAt = now()}))

Exceptions

When a pre-condition does not hold, the Record bid service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Bid above the current price not met, raised when Bid above the current price does not hold: Raised when 'Record bid' is requested while 'Bid above the current price' does not hold.

  • Bidder is a member not met, raised when Bidder is a member does not hold: Raised when 'Record bid' is requested while 'Bidder is a member' does not hold.

  • Bidder is not the seller not met, raised when Bidder is not the seller does not hold: Raised when 'Record bid' is requested while 'Bidder is not the seller' does not hold.

  • Bidding has not closed not met, raised when Bidding has not closed does not hold: Raised when 'Record bid' is requested while 'Bidding has not closed' does not hold.

  • Listing is open not met, raised when Listing is open does not hold: Raised when 'Record bid' is requested while 'Listing is open' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Listings::Request.

What is supplied when requesting 'Record bid'.

The Auctioneer::Listings::Request data structure
Figure 20. The Auctioneer::Listings::Request data structure, fully expanded.

A Auctioneer::Listings::Request has:

  • one amount (its type is not yet specified): What they bid.

  • one bidderLogin (its type is not yet specified): The bidder, by their login.

  • one listingNumber (its type is not yet specified): The listing bid for.

Response data structure

The information the service returns once provided is a Auctioneer::Listings::Response.

What 'Record bid' answers with.

The Auctioneer::Listings::Response data structure
Figure 21. The Auctioneer::Listings::Response data structure, fully expanded.

A Auctioneer::Listings::Response carries no information of its own.

Business process

No business process is needed. The service’s post-conditions say exactly what it records, i.e. it updates a Listing. It is thus provided by making that one change.

4.1.5. Service: Record listing

Listings provides the Record listing service.

Records an item offered for auction.

Service requirements

The functional requirements diagram below shows who has an interest in the Record listing service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Record listing service.
Figure 22. Functional requirements of the Record listing service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-condition Seller is a member.

  • Listings: What is on offer and what was bid for it.

    Listings requires the post-conditions Listing number is new and Listing recorded.

It is provided only when:

  • Seller is a member: Only a member may sell.

    Required by Auctioneer. Formally: Member.allInstances()->exists(m | m.login = request.sellerLogin)

Once it has been provided:

  • Listing number is new: The number issued belonged to no listing before.

    Required by Listings. Formally: Listing.allInstances@pre()->forAll(l | l.listingNumber <> response.listingNumber)

  • Listing recorded: The item is on offer, open for bids, with none made yet.

    Required by Listings. Formally: Listing.allInstances()->exists(l | l.listingNumber = response.listingNumber and l.seller.login = request.sellerLogin and l.title = request.title and l.description = request.description and l.photos = request.photos and l.documents = request.documents and l.condition = request.condition and l.startingBid = request.startingBid and l.shippingCost = request.shippingCost and l.closesAt = request.closesAt and l.status = ListingStatus::open and l.bids = Set{})

Exceptions

When a pre-condition does not hold, the Record listing service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Seller is a member not met, raised when Seller is a member does not hold: Raised when 'Record listing' is requested while 'Seller is a member' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Listings::Request.

What is supplied when requesting 'Record listing'.

The Auctioneer::Listings::Request data structure
Figure 23. The Auctioneer::Listings::Request data structure, fully expanded.

A Auctioneer::Listings::Request has:

  • one closesAt (its type is not yet specified): When bidding closes.

  • one condition (its type is not yet specified): The state the item is in.

  • one description (its type is not yet specified): The item described.

  • any number of documents (its type is not yet specified): Supporting documents, by URL.

  • between 1 and 12 photos (its type is not yet specified): Photos of the item, by URL.

  • one sellerLogin (its type is not yet specified): The seller, by their login.

  • one shippingCost (its type is not yet specified): What the buyer pays for shipping.

  • one startingBid (its type is not yet specified): The lowest bid to accept.

  • one title (its type is not yet specified): What the item is, in a line.

Response data structure

The information the service returns once provided is a Auctioneer::Listings::Response.

What 'Record listing' answers with.

The Auctioneer::Listings::Response data structure
Figure 24. The Auctioneer::Listings::Response data structure, fully expanded.

A Auctioneer::Listings::Response has:

  • one listingNumber (its type is not yet specified): The number issued.

Business process

No business process is needed. The service’s post-conditions say exactly what it records, i.e. it creates a Listing. It is thus provided by making that one change.

4.2. Entities

An entity is information which Listings keeps over time. It is a record which outlives any one request, and which its services create, change and read. Listings maintains the following entities:

  • Listing: An item offered for auction, with the bids made for it.

The entity map below shows each entity together with its facets, i.e. the data structures whose fields make up what it stores.

The entities maintained by Listings.
Figure 25. The entities maintained by Listings.

4.2.1. Entity: Listing

An item offered for auction, with the bids made for it.

How it is populated

Listing is populated as follows:

  • The Close listing service updates a Listing, identified by listingNumber.

  • The Record bid service updates a Listing, identified by listingNumber.

  • The Record listing service creates a Listing, identified by listingNumber.

  • The ListingRecord data structure describes part of what it holds: The auctioneer’s record of one item on offer.

Entity structure

The diagram below shows the Listing entity fully expanded, i.e. everything it holds, gathered from all of its facets, and the information it is related to. The same structure is described in words after it.

The Listing entity
Figure 26. The Listing entity, fully expanded.

A Listing has:

  • any number of bids, each a Auctioneer::Listings::Bid: The bids made, in the order made.

  • one closesAt (its type is not yet specified): When bidding closes.

  • one condition (its type is not yet specified): The state the item is in.

  • one description (its type is not yet specified): The item described.

  • any number of documents (its type is not yet specified): Supporting documents, by URL.

  • one listingNumber (its type is not yet specified), which identifies it: The listing’s number.

  • between 1 and 12 photos (its type is not yet specified): Photos of the item, by URL.

  • one shippingCost (its type is not yet specified): What the buyer pays for shipping.

  • one startingBid (its type is not yet specified): The lowest bid accepted.

  • one status, a Auctioneer::Listings::ListingStatus: Whether the listing still takes bids.

    One of closed and open.

  • one title (its type is not yet specified): What the item is, in a line.

  • one version (its type is not yet specified), the version of the instance read, which an update is decided on: The version of the listing read.

A Listing is associated with:

  • one seller, a Auctioneer::Membership::MemberRecord: The member selling the item.

Auctioneer::Listings::Bid: One bid made for a listing.

A Auctioneer::Listings::Bid has:

  • one amount (its type is not yet specified): What they bid.

  • one bidderLogin (its type is not yet specified): Who bid, by their login.

  • one placedAt (its type is not yet specified): When the bid was made.

Auctioneer::Membership::MemberRecord: The auctioneer’s record of one member.

A Auctioneer::Membership::MemberRecord has:

  • one email (its type is not yet specified): Where the member is written to.

  • one login (its type is not yet specified), unique: The login identity the member signs in with: what `caller` and `respondent` are compared with.

  • one memberNumber (its type is not yet specified), which identifies it: The member’s number.

  • one name (its type is not yet specified): The member’s name.

  • one payoutAccount (its type is not yet specified): The account the member is paid into when they sell.

  • one shippingAddress (its type is not yet specified): Where items bought are shipped.

The following must always hold for a Auctioneer::Membership::MemberRecord:

  • Member number format: self.memberNumber.matches('MB-[0-9]{4,}')

Data dictionary

This section lists what Listing stores, attribute by attribute. An attribute gathers every field of that name in the entity’s facets. Where it gathers more than one, each is listed, since fields of one name are stored as one attribute whatever each was meant to hold. The services listed write or read it as their specifications say.

Attribute Type Role Multiplicity Unique Personal data Merged from Written by Read by

bids

Auctioneer::Listings::Bid

states

0..*

no

—

—

closesAt

—

states

1

no

—

—

condition

—

states

1

no

—

—

—

description

—

states

1

no

—

—

—

documents

—

states

0..*

no

—

—

—

listingNumber

—

identifies

1

yes

—

—

photos

—

states

1..12

no

—

—

—

seller

Auctioneer::Membership::MemberRecord

states

1

no

—

—

shippingCost

—

states

1

no

—

—

startingBid

—

states

1

no

—

—

status

Auctioneer::Listings::ListingStatus

states

1

no

—

—

title

—

states

1

no

—

—

4.3. Dependencies

To provide its services, Listings relies on services provided by other responsibility domains. The dependency diagram below shows which.

The responsibility domains Listings depends on.
Figure 27. The responsibility domains Listings depends on.

Listings uses:

  • from Sales: Completing a sale: payment, payout, shipping and feedback.

    • the Complete sale service: Closes a listing and takes its sale, if any, from payment to the buyer’s feedback.

5. Auctioneer / Membership

This part specifies the Membership responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

Who the members are.

The scope diagram below shows what Membership is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Membership.
Figure 28. The scope of Membership.

5.1. Services

Membership is responsible for providing the following services. Each is described in its own section below: what it requires and what it guarantees (its service requirements), the information exchanged with it, how the work is allocated to the responsibility domains taking part, and the business process providing it.

  • Get member: Tells another part of the auctioneer what it needs of a member: where to ship to and where to pay.

  • Record member: Records a new member and issues their number.

  • Register member: A person becomes a member of the auctioneer.

5.1.1. Service: Get member

Membership provides the Get member service. It is a query, i.e. it answers from information already held and changes nothing.

Tells another part of the auctioneer what it needs of a member: where to ship to and where to pay.

A member's name, address and account are personal data, which Membership keeps and no other domain reads from its records: a sale asks for them here.

Service requirements

The functional requirements diagram below shows who has an interest in the Get member service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Get member service.
Figure 29. Functional requirements of the Get member service.

Its stakeholders, and what each requires of it, are:

  • Membership: Who the members are.

    Membership requires the pre-condition Member exists.

  • Sales: Completing a sale: payment, payout, shipping and feedback.

    Sales requires the post-condition Member reported.

It is provided only when:

  • Member exists: Only a member is told of.

    Required by Membership. Formally: Member.allInstances()->exists(m | m.login = request.login)

Once it has been provided:

  • Member reported: Their name, address and account are answered as recorded.

    Required by Sales. Formally: response.name = Member.allInstances()->any(m | m.login = request.login).name and response.shippingAddress = Member.allInstances()->any(m | m.login = request.login).shippingAddress and response.payoutAccount = Member.allInstances()->any(m | m.login = request.login).payoutAccount

Exceptions

When a pre-condition does not hold, the Get member service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Member exists not met, raised when Member exists does not hold: Raised when 'Get member' is requested while 'Member exists' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Membership::Request.

What is supplied when requesting 'Get member'.

The Auctioneer::Membership::Request data structure
Figure 30. The Auctioneer::Membership::Request data structure, fully expanded.

A Auctioneer::Membership::Request has:

  • one login (its type is not yet specified): The member, by their login.

Response data structure

The information the service returns once provided is a Auctioneer::Membership::Response.

What 'Get member' answers with.

The Auctioneer::Membership::Response data structure
Figure 31. The Auctioneer::Membership::Response data structure, fully expanded.

A Auctioneer::Membership::Response has:

  • one name (its type is not yet specified): Their name.

  • one payoutAccount (its type is not yet specified): The account they are paid into.

  • one shippingAddress (its type is not yet specified): Where items they buy are shipped.

Business process

No business process providing this service has been specified yet.

5.1.2. Service: Record member

Membership provides the Record member service.

Records a new member and issues their number.

Service requirements

The functional requirements diagram below shows who has an interest in the Record member service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Record member service.
Figure 32. Functional requirements of the Record member service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-condition Login not yet registered.

  • Membership: Who the members are.

    Membership requires the post-conditions Member number is new and Member recorded.

It is provided only when:

  • Login not yet registered: A login identity belongs to one member.

    Required by Auctioneer. Formally: Member.allInstances()->forAll(m | m.login <> request.login)

Once it has been provided:

  • Member number is new: The number issued belonged to no member before.

    Required by Membership. Formally: Member.allInstances@pre()->forAll(m | m.memberNumber <> response.memberNumber)

  • Member recorded: The member is on record with the details given.

    Required by Membership. Formally: Member.allInstances()->exists(m | m.memberNumber = response.memberNumber and m.login = request.login and m.name = request.name and m.email = request.email and m.shippingAddress = request.shippingAddress and m.payoutAccount = request.payoutAccount)

Exceptions

When a pre-condition does not hold, the Record member service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Login not yet registered not met, raised when Login not yet registered does not hold: Raised when 'Record member' is requested while 'Login not yet registered' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Membership::Request.

What is supplied when requesting 'Record member'.

The Auctioneer::Membership::Request data structure
Figure 33. The Auctioneer::Membership::Request data structure, fully expanded.

A Auctioneer::Membership::Request has:

  • one email (its type is not yet specified): Their e-mail address.

  • one login (its type is not yet specified): The login identity the member will use.

  • one name (its type is not yet specified): The member’s name.

  • one payoutAccount (its type is not yet specified): The account they are paid into when they sell.

  • one shippingAddress (its type is not yet specified): Where items they buy are shipped.

Response data structure

The information the service returns once provided is a Auctioneer::Membership::Response.

What 'Record member' answers with.

The Auctioneer::Membership::Response data structure
Figure 34. The Auctioneer::Membership::Response data structure, fully expanded.

A Auctioneer::Membership::Response has:

  • one memberNumber (its type is not yet specified): The number issued.

Business process

No business process is needed. The service’s post-conditions say exactly what it records, i.e. it creates a Member. It is thus provided by making that one change.

5.1.3. Service: Register member

Membership provides the Register member service.

A person becomes a member of the auctioneer.

Service requirements

The functional requirements diagram below shows who has an interest in the Register member service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Register member service.
Figure 35. Functional requirements of the Register member service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-condition May register.

  • Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

    Member requires the post-condition Member registered.

It is provided only when:

  • May register: The person asking is not a member yet.

    Required by Auctioneer. Formally, as the services refining it state it: Member.allInstances()->forAll(m | m.login <> caller)

Once it has been provided:

  • Member registered: The person is a member, under the login they asked with.

    Required by Member. Formally, as the services refining it state it: Member.allInstances@pre()->forAll(m | m.memberNumber <> response.memberNumber) and Member.allInstances()->exists(m | m.memberNumber = response.memberNumber and m.login = caller and m.name = request.name and m.email = request.email and m.shippingAddress = request.shippingAddress and m.payoutAccount = request.payoutAccount)

Exceptions

When a pre-condition does not hold, the Register member service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • May register not met, raised when May register does not hold: Raised when 'Register member' is requested while 'May register' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Membership::Request.

What is supplied when requesting 'Register member'.

The Auctioneer::Membership::Request data structure
Figure 36. The Auctioneer::Membership::Request data structure, fully expanded.

A Auctioneer::Membership::Request has:

  • one email (its type is not yet specified): Their e-mail address.

  • one name (its type is not yet specified): Their name.

  • one payoutAccount (its type is not yet specified): The account they are paid into when they sell.

  • one shippingAddress (its type is not yet specified): Where items they buy are shipped.

Response data structure

The information the service returns once provided is a Auctioneer::Membership::Response.

What 'Register member' answers with.

The Auctioneer::Membership::Response data structure
Figure 37. The Auctioneer::Membership::Response data structure, fully expanded.

A Auctioneer::Membership::Response has:

  • one memberNumber (its type is not yet specified): The member number issued.

Responsibility allocation

The responsibility allocation diagram below shows how the Register member process takes care of each requirement of the Register member service. It shows which of its steps addresses each pre- and post-condition, and which services it uses from other responsibility domains to do so.

Responsibility allocation for the Register member process.
Figure 38. Responsibility allocation for the Register member process.

Requirement by requirement:

To do so the process uses the following services:

Business process

Records the person as a member under the login they asked with.

The Register member business process provides the Register member service. The diagram below shows its flow. The numbered steps after it describe the same flow in words, with each choice, loop and parallel flow holding its own steps beneath it.

The business process Register member.
Figure 39. The business process Register member.

Step by step:

  1. Request the Record member service from Membership.

    This step addresses May register and Member registered.

    The request is populated as follows:

    • email: providerRequest.email = request.email

    • login: providerRequest.login = caller

    • name: providerRequest.name = request.name

    • payoutAccount: providerRequest.payoutAccount = request.payoutAccount

    • shippingAddress: providerRequest.shippingAddress = request.shippingAddress

      The answer is kept as recorded, one Auctioneer::Membership::Response.

  2. Populate the response.

    • memberNumber: response.memberNumber = recorded.memberNumber

5.2. Entities

An entity is information which Membership keeps over time. It is a record which outlives any one request, and which its services create, change and read. Membership maintains the following entities:

  • Member: A person registered to buy and sell.

The entity map below shows each entity together with its facets, i.e. the data structures whose fields make up what it stores.

The entities maintained by Membership.
Figure 40. The entities maintained by Membership.

5.2.1. Entity: Member

A person registered to buy and sell.

How it is populated

Member is populated as follows:

  • The Record member service creates a Member, identified by memberNumber.

  • The MemberRecord data structure describes part of what it holds: The auctioneer’s record of one member.

Entity structure

The diagram below shows the Member entity fully expanded, i.e. everything it holds, gathered from all of its facets, and the information it is related to. The same structure is described in words after it.

The Member entity
Figure 41. The Member entity, fully expanded.

A Member has:

  • one email (its type is not yet specified): Where the member is written to.

  • one login (its type is not yet specified), unique: The login identity the member signs in with: what `caller` and `respondent` are compared with.

  • one memberNumber (its type is not yet specified), which identifies it: The member’s number.

  • one name (its type is not yet specified): The member’s name.

  • one payoutAccount (its type is not yet specified): The account the member is paid into when they sell.

  • one shippingAddress (its type is not yet specified): Where items bought are shipped.

Data dictionary

This section lists what Member stores, attribute by attribute. An attribute gathers every field of that name in the entity’s facets. Where it gathers more than one, each is listed, since fields of one name are stored as one attribute whatever each was meant to hold. The services listed write or read it as their specifications say.

Attribute Type Role Multiplicity Unique Personal data Merged from Written by Read by

email

—

states

1

no

personal

—

—

login

—

states

1

yes

—

—

memberNumber

—

identifies

1

yes

—

—

—

name

—

states

1

no

personal

—

payoutAccount

—

states

1

no

personal

—

shippingAddress

—

states

1

no

personal

—

6. Auctioneer / Platform

This part specifies the Platform responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

The platform’s terms, the service fee among them.

The scope diagram below shows what Platform is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Platform.
Figure 42. The scope of Platform.

6.1. Services

Platform is responsible for providing the following services. Each is described in its own section below: what it requires and what it guarantees (its service requirements), the information exchanged with it, how the work is allocated to the responsibility domains taking part, and the business process providing it.

6.1.1. Service: Get service fee

Platform provides the Get service fee service. It is a query, i.e. it answers from information already held and changes nothing.

Tells the rate the platform charges now.

Service requirements

The functional requirements diagram below shows who has an interest in the Get service fee service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Get service fee service.
Figure 43. Functional requirements of the Get service fee service.

Its stakeholders, and what each requires of it, are:

  • Sales: Completing a sale: payment, payout, shipping and feedback.

    Sales requires the post-condition Current rate reported.

Once it has been provided:

  • Current rate reported: The rate on record is answered, or none where none was ever set.

    Required by Sales. Formally: response.serviceFeeRate = PlatformPolicy.allInstances()->collect(p | p.serviceFeeRate)->sum()

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Platform::Request.

What is supplied when requesting 'Get service fee'.

The Auctioneer::Platform::Request data structure
Figure 44. The Auctioneer::Platform::Request data structure, fully expanded.

A Auctioneer::Platform::Request carries no information of its own.

Response data structure

The information the service returns once provided is a Auctioneer::Platform::Response.

What 'Get service fee' answers with.

The Auctioneer::Platform::Response data structure
Figure 45. The Auctioneer::Platform::Response data structure, fully expanded.

A Auctioneer::Platform::Response has:

  • one serviceFeeRate (its type is not yet specified): The rate, in per cent.

Business process

No business process providing this service has been specified yet.

6.1.2. Service: Record service fee

Platform provides the Record service fee service.

Records the service fee the platform charges.

Service requirements

The functional requirements diagram below shows who has an interest in the Record service fee service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Record service fee service.
Figure 46. Functional requirements of the Record service fee service.

Its stakeholders, and what each requires of it, are:

  • Platform: The platform’s terms, the service fee among them.

    Platform requires the post-condition Service fee recorded.

Once it has been provided:

  • Service fee recorded: The platform’s one set of terms carries the new rate.

    Required by Platform. Formally: PlatformPolicy.allInstances()->size() = 1 and PlatformPolicy.allInstances()->forAll(p | p.policyName = 'service fee' and p.serviceFeeRate = request.serviceFeeRate)

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Platform::Request.

What is supplied when requesting 'Record service fee'.

The Auctioneer::Platform::Request data structure
Figure 47. The Auctioneer::Platform::Request data structure, fully expanded.

A Auctioneer::Platform::Request has:

  • one serviceFeeRate (its type is not yet specified): The new rate, in per cent.

The following must always hold for a Auctioneer::Platform::Request:

  • Fee rate within bounds: self.serviceFeeRate >= 0 and self.serviceFeeRate <= 50

Response data structure

The information the service returns once provided is a Auctioneer::Platform::Response.

What 'Record service fee' answers with.

The Auctioneer::Platform::Response data structure
Figure 48. The Auctioneer::Platform::Response data structure, fully expanded.

A Auctioneer::Platform::Response carries no information of its own.

Business process

No business process providing this service has been specified yet.

6.1.3. Service: Set service fee

Platform provides the Set service fee service.

An administrator sets the platform’s service fee.

Service requirements

The functional requirements diagram below shows who has an interest in the Set service fee service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Set service fee service.
Figure 49. Functional requirements of the Set service fee service.

Its stakeholders, and what each requires of it, are:

  • Administrator: A person who sets the platform’s terms.

    Administrator requires the post-condition Service fee set.

Once it has been provided:

  • Service fee set: Sales completed from now on are charged the new rate.

    Required by Administrator. Formally, as the services refining it state it: PlatformPolicy.allInstances()->size() = 1 and PlatformPolicy.allInstances()->forAll(p | p.policyName = 'service fee' and p.serviceFeeRate = request.serviceFeeRate)

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Platform::Request.

What is supplied when requesting 'Set service fee'.

The Auctioneer::Platform::Request data structure
Figure 50. The Auctioneer::Platform::Request data structure, fully expanded.

A Auctioneer::Platform::Request has:

  • one serviceFeeRate (its type is not yet specified): The new rate, in per cent.

The following must always hold for a Auctioneer::Platform::Request:

  • Fee rate within bounds: self.serviceFeeRate >= 0 and self.serviceFeeRate <= 50

Response data structure

The information the service returns once provided is a Auctioneer::Platform::Response.

What 'Set service fee' answers with.

The Auctioneer::Platform::Response data structure
Figure 51. The Auctioneer::Platform::Response data structure, fully expanded.

A Auctioneer::Platform::Response carries no information of its own.

Responsibility allocation

The responsibility allocation diagram below shows how the Set service fee process takes care of each requirement of the Set service fee service. It shows which of its steps addresses each pre- and post-condition, and which services it uses from other responsibility domains to do so.

Responsibility allocation for the Set service fee process.
Figure 52. Responsibility allocation for the Set service fee process.

Requirement by requirement:

To do so the process uses the following services:

Business process

Records the rate the administrator gave.

The Set service fee business process provides the Set service fee service. The diagram below shows its flow. The numbered steps after it describe the same flow in words, with each choice, loop and parallel flow holding its own steps beneath it.

The business process Set service fee.
Figure 53. The business process Set service fee.

Step by step:

  1. Request the Record service fee service from Platform.

    This step addresses Service fee set.

    The request is populated as follows:

    • serviceFeeRate: providerRequest.serviceFeeRate = request.serviceFeeRate

6.2. Entities

An entity is information which Platform keeps over time. It is a record which outlives any one request, and which its services create, change and read. Platform maintains the following entities:

The entity map below shows each entity together with its facets, i.e. the data structures whose fields make up what it stores.

The entities maintained by Platform.
Figure 54. The entities maintained by Platform.

6.2.1. Entity: PlatformPolicy

The platform’s terms, as one record.

How it is populated

PlatformPolicy is populated as follows:

  • The PlatformTerms data structure describes part of what it holds: The terms the platform trades on.

Entity structure

The diagram below shows the PlatformPolicy entity fully expanded, i.e. everything it holds, gathered from all of its facets, and the information it is related to. The same structure is described in words after it.

The PlatformPolicy entity
Figure 55. The PlatformPolicy entity, fully expanded.

A PlatformPolicy has:

  • one policyName (its type is not yet specified), which identifies it: Which terms these are. There is one record, `service fee`.

  • one serviceFeeRate (its type is not yet specified): The share of the price the auctioneer keeps, in per cent.

Data dictionary

This section lists what PlatformPolicy stores, attribute by attribute. An attribute gathers every field of that name in the entity’s facets. Where it gathers more than one, each is listed, since fields of one name are stored as one attribute whatever each was meant to hold. The services listed write or read it as their specifications say.

Attribute Type Role Multiplicity Unique Personal data Merged from Written by Read by

policyName

—

identifies

1

yes

—

—

—

—

serviceFeeRate

—

states

1

no

—

—

—

7. Auctioneer / Sales

This part specifies the Sales responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

Completing a sale: payment, payout, shipping and feedback.

The scope diagram below shows what Sales is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Sales.
Figure 56. The scope of Sales.

7.1. Services

Sales is responsible for providing the following services. Each is described in its own section below: what it requires and what it guarantees (its service requirements), the information exchanged with it, how the work is allocated to the responsibility domains taking part, and the business process providing it.

  • Collect payment: Has the buyer pay for what they won, by the payment deadline.

  • Complete sale: Closes a listing and takes its sale, if any, from payment to the buyer’s feedback.

  • Compute settlement: Works out the fee, what the buyer pays and what the seller is paid.

  • Record sale: Records the sale of a closed listing to its highest bidder.

  • Update sale: Records how far a sale has got.

7.1.1. Service: Collect payment

Sales provides the Collect payment service.

Has the buyer pay for what they won, by the payment deadline.

Service requirements

The functional requirements diagram below shows who has an interest in the Collect payment service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Collect payment service.
Figure 57. Functional requirements of the Collect payment service.

Its stakeholders, and what each requires of it, are:

  • Sales: Completing a sale: payment, payout, shipping and feedback.

    Sales requires the pre-condition Sale on record and the post-conditions Not paid and Paid.

It is provided only when:

  • Sale on record: Payment is collected only for a sale on record.

    Required by Sales. Formally: Sale.allInstances()->exists(s | s.saleNumber = request.saleNumber)

Once it has been provided:

  • Not paid: The sale is marked overdue or failed, and nothing was charged.

    Required by Sales. Applies only when response.paymentReference->isEmpty().

  • Paid: The buyer was charged the amount due, and the sale is marked paid.

    Required by Sales. Applies only when response.paymentReference->notEmpty().

Exceptions

When a pre-condition does not hold, the Collect payment service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Sale on record not met, raised when Sale on record does not hold: Raised when 'Collect payment' is requested while 'Sale on record' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Sales::Request.

What is supplied when requesting 'Collect payment'.

The Auctioneer::Sales::Request data structure
Figure 58. The Auctioneer::Sales::Request data structure, fully expanded.

A Auctioneer::Sales::Request has:

  • one amountDue (its type is not yet specified): What the buyer pays.

  • one buyerLogin (its type is not yet specified): The buyer, by their login.

  • one saleNumber (its type is not yet specified): The sale.

  • one title (its type is not yet specified): The item bought.

Response data structure

The information the service returns once provided is a Auctioneer::Sales::Response.

What 'Collect payment' answers with.

The Auctioneer::Sales::Response data structure
Figure 59. The Auctioneer::Sales::Response data structure, fully expanded.

A Auctioneer::Sales::Response has:

  • optionally one paymentReference (its type is not yet specified): The payment taken, where it was.

Responsibility allocation

The responsibility allocation diagram below shows how the Collect payment process takes care of each requirement of the Collect payment service. It shows which of its steps addresses each pre- and post-condition, and which services it uses from other responsibility domains to do so.

Responsibility allocation for the Collect payment process.
Figure 60. Responsibility allocation for the Collect payment process.

Requirement by requirement:

  • Sale on record (pre-condition) is addressed by checking it before anything else is done.

  • Not paid (post-condition) is addressed by the step Payment deadline.

  • Paid (post-condition) is addressed by requesting the Charge payment service from Payment Gateway.

To do so the process uses the following services:

Business process

The buyer pays within three days, or the sale says why not.

The Collect payment business process provides the Collect payment service. The diagram below shows its flow. The numbered steps after it describe the same flow in words, with each choice, loop and parallel flow holding its own steps beneath it.

The business process Collect payment.
Figure 61. The business process Collect payment.

Step by step:

  1. Check that Sale on record holds. If it does not, stop and raise Sale on record not met.

    Formally: Sale.allInstances()->exists(s | s.saleNumber = request.saleNumber)

  2. Do the following, watching for what is listed after it:

    This step addresses Not paid.

    1. Request the Pay for item service from Member.

      The request is populated as follows:

      • amountDue: providerRequest.amountDue = request.amountDue

      • buyerLogin: providerRequest.buyerLogin = request.buyerLogin

      • saleNumber: providerRequest.saleNumber = request.saleNumber

      • title: providerRequest.title = request.title

        The answer is kept as payment, one Member::Response.

      • If the service is provided:

        1. Request the Charge payment service from Payment Gateway.

          This step addresses Paid.

          The request is populated as follows:

          • amount: providerRequest.amount = request.amountDue

          • paymentToken: providerRequest.paymentToken = payment.paymentToken

          • reference: providerRequest.reference = request.saleNumber

            The answer is kept as charged, one Payment Gateway::Response.

          • If the service is provided:

            1. Request the Update sale service from Sales.

              The request is populated as follows:

              • paymentReference: providerRequest.paymentReference = charged.paymentReference

              • saleNumber: providerRequest.saleNumber = request.saleNumber

              • status: providerRequest.status = SaleStatus::paid

                It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

            2. Populate the response.

              • paymentReference: response.paymentReference = charged.paymentReference

          • If it raises Payment authorised not met:

            1. Request the Update sale service from Sales.

              The request is populated as follows:

              • saleNumber: providerRequest.saleNumber = request.saleNumber

              • status: providerRequest.status = SaleStatus::paymentFailed

                It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

            2. Populate the response.

              It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

              It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes. ** When P3D has passed: stop those steps, do the following instead, and carry on after them: …​ Request the Update sale service from Sales.

              + The request is populated as follows:

              • saleNumber: providerRequest.saleNumber = request.saleNumber

              • status: providerRequest.status = SaleStatus::paymentOverdue

                1. Populate the response.

7.1.2. Service: Complete sale

Sales provides the Complete sale service.

Closes a listing and takes its sale, if any, from payment to the buyer’s feedback.

Service requirements

The functional requirements diagram below shows who has an interest in the Complete sale service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Complete sale service.
Figure 62. Functional requirements of the Complete sale service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-conditions Highest bidder can buy and Listing ready to close.

  • Listings: What is on offer and what was bid for it.

    Listings requires the post-condition Auction closed.

  • Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

    Member requires the post-conditions Buyer kept informed, Paid and paid out, Sale completed and Sold to the highest bidder.

It is provided only when:

  • Highest bidder can buy: The listing is unsold, and its highest bidder still a member.

    Required by Auctioneer.

  • Listing ready to close: The listing is open and its closing time has come.

    Required by Auctioneer. Formally, as the services refining it state it: Listing.allInstances()->forAll(l | l.listingNumber = request.listingNumber implies l.closesAt <= now()) and Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.status = ListingStatus::open)

Once it has been provided:

  • Auction closed: The listing takes no more bids, and its highest bid is known.

    Required by Listings.

  • Buyer kept informed: The buyer is sent a receipt, and the tracking details once shipped.

    Required by Member.

    While meeting it, the service sends:

    • Receipt sent, carrying a Auctioneer::Sales::Receipt, to Member, as a notification which any number of parties may act on

    • Tracking details sent, carrying a Auctioneer::Sales::TrackingDetails, to Member, as a notification which any number of parties may act on

  • Paid and paid out: Where the buyer pays in time, the seller is paid the price and shipping less the fee.

    Required by Member.

  • Sale completed: Once the buyer confirms receipt, or two weeks pass, the sale is complete, with the buyer’s rating where they gave one.

    Required by Member.

  • Sold to the highest bidder: Where anyone bid, the highest bidder buys at their bid.

    Required by Member.

Exceptions

When a pre-condition does not hold, the Complete sale service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Highest bidder can buy not met, raised when Highest bidder can buy does not hold: Raised when 'Complete sale' is requested while 'Highest bidder can buy' does not hold.

  • Listing ready to close not met, raised when Listing ready to close does not hold: Raised when 'Complete sale' is requested while 'Listing ready to close' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Sales::Request.

What is supplied when requesting 'Complete sale'.

The Auctioneer::Sales::Request data structure
Figure 63. The Auctioneer::Sales::Request data structure, fully expanded.

A Auctioneer::Sales::Request has:

  • one listingNumber (its type is not yet specified): The listing whose auction has closed.

Response data structure

The information the service returns once provided is a Auctioneer::Sales::Response.

What 'Complete sale' answers with.

The Auctioneer::Sales::Response data structure
Figure 64. The Auctioneer::Sales::Response data structure, fully expanded.

A Auctioneer::Sales::Response has:

  • optionally one saleNumber (its type is not yet specified): The sale made, where there was a bid.

Responsibility allocation

The responsibility allocation diagram below shows how the Complete sale process takes care of each requirement of the Complete sale service. It shows which of its steps addresses each pre- and post-condition, and which services it uses from other responsibility domains to do so.

Responsibility allocation for the Complete sale process.
Figure 65. Responsibility allocation for the Complete sale process.

Requirement by requirement:

  • Highest bidder can buy (pre-condition) is addressed by requesting the Record sale service from Sales.

  • Listing ready to close (pre-condition) is addressed by requesting the Close listing service from Listings.

  • Auction closed (post-condition) is addressed by requesting the Close listing service from Listings.

  • Buyer kept informed (post-condition) is addressed by the step Was it paid.

  • Paid and paid out (post-condition) is addressed by requesting the Pay seller service from Bank.

  • Sale completed (post-condition) is addressed by the step Feedback window.

  • Sold to the highest bidder (post-condition) is addressed by requesting the Record sale service from Sales.

To do so the process uses the following services:

Business process

Closes the listing, then takes a sale to the highest bidder through payment, payout, shipping and feedback.

The Complete sale business process provides the Complete sale service. The diagram below shows its flow. The numbered steps after it describe the same flow in words, with each choice, loop and parallel flow holding its own steps beneath it.

The business process Complete sale.
Figure 66. The business process Complete sale.

Step by step:

  1. Request the Close listing service from Listings.

    This step addresses Auction closed and Listing ready to close.

    The request is populated as follows:

    • listingNumber: providerRequest.listingNumber = request.listingNumber

      The answer is kept as closed, one Auctioneer::Listings::Response.

      It needs no undoing: An auction closes at its closing time whether or not its highest bidder can buy: the listing stays closed when Record sale refuses, and the refusal says only that no sale could be made.

  2. Choose one way to continue, the first whose condition holds:

    • If closed.winningBid->notEmpty() (Has bids):

      1. Request the Get service fee service from Platform.

        The answer is kept as terms, one Auctioneer::Platform::Response.

      2. Request the Compute settlement service from Sales.

        The request is populated as follows:

        • price: providerRequest.price = closed.winningBid.amount

        • serviceFeeRate: providerRequest.serviceFeeRate = terms.serviceFeeRate

        • shippingCost: providerRequest.shippingCost = closed.shippingCost

          The answer is kept as settlement, one Auctioneer::Sales::Response.

      3. Request the Record sale service from Sales.

        This step addresses Highest bidder can buy and Sold to the highest bidder.

        The request is populated as follows:

        • amountDue: providerRequest.amountDue = settlement.amountDue

        • buyerLogin: providerRequest.buyerLogin = closed.winningBid.bidderLogin

        • fee: providerRequest.fee = settlement.fee

        • listingNumber: providerRequest.listingNumber = request.listingNumber

        • price: providerRequest.price = closed.winningBid.amount

        • sellerPayout: providerRequest.sellerPayout = settlement.sellerPayout

          The answer is kept as sale, one Auctioneer::Sales::Response.

          It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

      4. Request the Get member service from Membership.

        The request is populated as follows:

        • login: providerRequest.login = closed.winningBid.bidderLogin

          The answer is kept as buyer, one Auctioneer::Membership::Response.

      5. Request the Get member service from Membership.

        The request is populated as follows:

        • login: providerRequest.login = closed.sellerLogin

          The answer is kept as seller, one Auctioneer::Membership::Response.

      6. Request the Collect payment service from Sales.

        The request is populated as follows:

        • amountDue: providerRequest.amountDue = settlement.amountDue

        • buyerLogin: providerRequest.buyerLogin = closed.winningBid.bidderLogin

        • saleNumber: providerRequest.saleNumber = sale.saleNumber

        • title: providerRequest.title = closed.title

          The answer is kept as collected, one Auctioneer::Sales::Response.

          It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

      7. Choose one way to continue, the first whose condition holds:

        This step addresses Buyer kept informed.

        • If collected.paymentReference->notEmpty() (Paid):

          1. Request the Pay seller service from Bank.

            This step addresses Paid and paid out.

            The request is populated as follows:

            • amount: providerRequest.amount = settlement.sellerPayout

            • payee: providerRequest.payee = seller.payoutAccount

            • reference: providerRequest.reference = sale.saleNumber

              The answer is kept as payout, one Bank::Response.

              It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

          2. Request the Update sale service from Sales.

            The request is populated as follows:

            • payoutReference: providerRequest.payoutReference = payout.payoutReference

            • saleNumber: providerRequest.saleNumber = sale.saleNumber

            • status: providerRequest.status = SaleStatus::paid

              It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

          3. Send a Auctioneer::Sales::Receipt to Member (the one given by closed.winningBid.bidderLogin), as a notification which any number of parties may act on.

            • amountPaid: sent.amountPaid = settlement.amountDue

            • paymentReference: sent.paymentReference = collected.paymentReference

            • saleNumber: sent.saleNumber = sale.saleNumber

            • title: sent.title = closed.title

          4. Request the Provide shipping details service from Member.

            The request is populated as follows:

            • buyerName: providerRequest.buyerName = buyer.name

            • paymentReference: providerRequest.paymentReference = collected.paymentReference

            • saleNumber: providerRequest.saleNumber = sale.saleNumber

            • sellerLogin: providerRequest.sellerLogin = closed.sellerLogin

            • shippingAddress: providerRequest.shippingAddress = buyer.shippingAddress

            • title: providerRequest.title = closed.title

              The answer is kept as shipped, one Member::Response.

              It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

          5. Request the Update sale service from Sales.

            The request is populated as follows:

            • saleNumber: providerRequest.saleNumber = sale.saleNumber

            • shipment: providerRequest.shipment = shipped.shipment

            • status: providerRequest.status = SaleStatus::shipped

              It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

          6. Send a Auctioneer::Sales::TrackingDetails to Member (the one given by closed.winningBid.bidderLogin), as a notification which any number of parties may act on.

            • saleNumber: sent.saleNumber = sale.saleNumber

            • shipment: sent.shipment = shipped.shipment

            • title: sent.title = closed.title

          7. Do the following, watching for what is listed after it:

            This step addresses Sale completed.

            1. Request the Confirm receipt and rate service from Member.

              The request is populated as follows:

              • buyerLogin: providerRequest.buyerLogin = closed.winningBid.bidderLogin

              • saleNumber: providerRequest.saleNumber = sale.saleNumber

              • shipment: providerRequest.shipment = shipped.shipment

              • title: providerRequest.title = closed.title

                The answer is kept as confirmation, one Member::Response.

              • If the service is provided:

                1. Request the Update sale service from Sales.

                  The request is populated as follows:

                  • feedback: providerRequest.feedback = confirmation.feedback

                  • rating: providerRequest.rating = confirmation.rating

                  • saleNumber: providerRequest.saleNumber = sale.saleNumber

                  • status: providerRequest.status = SaleStatus::completed

                    It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes.

                    It needs no undoing: Nothing after this step can refuse: the only later refusal points are the steps updating the sale, whose one pre-condition, that the sale exists, Record sale established and nothing removes. When P14D has passed: stop those steps, do the following instead, and carry on after them: …​…​. Request the Update sale service from Sales.

                    + The request is populated as follows:

                    • saleNumber: providerRequest.saleNumber = sale.saleNumber

                    • status: providerRequest.status = SaleStatus::completed

        • Otherwise:

          Nothing is done.

      8. Populate the response.

        • saleNumber: response.saleNumber = sale.saleNumber

    • Otherwise:

      1. Populate the response.

7.1.3. Service: Compute settlement

Sales provides the Compute settlement service. It is a query, i.e. it answers from information already held and changes nothing.

Works out the fee, what the buyer pays and what the seller is paid.

Service requirements

The functional requirements diagram below shows who has an interest in the Compute settlement service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Compute settlement service.
Figure 67. Functional requirements of the Compute settlement service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the post-conditions Buyer pays price and shipping, Fee at the rate and Seller paid the rest.

Once it has been provided:

  • Buyer pays price and shipping: The buyer pays the price and the shipping cost.

    Required by Auctioneer. Formally: response.amountDue.amount = request.price.amount + request.shippingCost.amount and response.amountDue.currency = request.price.currency

  • Fee at the rate: The fee is the rate’s share of the price, to the cent.

    Required by Auctioneer. Formally: response.fee.amount = (request.price.amount * request.serviceFeeRate).divideHalfUp(100, 2) and response.fee.currency = request.price.currency

  • Seller paid the rest: The seller is paid what the buyer pays, less the fee.

    Required by Auctioneer. Formally: response.sellerPayout.amount = response.amountDue.amount - response.fee.amount and response.sellerPayout.currency = request.price.currency

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Sales::Request.

What is supplied when requesting 'Compute settlement'.

The Auctioneer::Sales::Request data structure
Figure 68. The Auctioneer::Sales::Request data structure, fully expanded.

A Auctioneer::Sales::Request has:

  • one price (its type is not yet specified): The winning bid.

  • one serviceFeeRate (its type is not yet specified): The rate charged, in per cent.

  • one shippingCost (its type is not yet specified): What the buyer pays for shipping.

Response data structure

The information the service returns once provided is a Auctioneer::Sales::Response.

What 'Compute settlement' answers with.

The Auctioneer::Sales::Response data structure
Figure 69. The Auctioneer::Sales::Response data structure, fully expanded.

A Auctioneer::Sales::Response has:

  • one amountDue (its type is not yet specified): What the buyer pays.

  • one fee (its type is not yet specified): What the auctioneer keeps.

  • one sellerPayout (its type is not yet specified): What the seller is paid.

Business process

No business process providing this service has been specified yet.

7.1.4. Service: Record sale

Sales provides the Record sale service.

Records the sale of a closed listing to its highest bidder.

Service requirements

The functional requirements diagram below shows who has an interest in the Record sale service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Record sale service.
Figure 70. Functional requirements of the Record sale service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-conditions Buyer is a member, Listing closed and Listing not yet sold.

  • Sales: Completing a sale: payment, payout, shipping and feedback.

    Sales requires the post-conditions Buyer still a member, Sale number is new and Sale recorded.

It is provided only when:

  • Buyer is a member: Only a member buys.

    Required by Auctioneer. Formally: Member.allInstances()->exists(m | m.login = request.buyerLogin)

  • Listing closed: Only a closed listing is sold.

    Required by Auctioneer. Formally: Listing.allInstances()->exists(l | l.listingNumber = request.listingNumber and l.status = ListingStatus::closed)

  • Listing not yet sold: A listing is sold once.

    Required by Auctioneer. Formally: Sale.allInstances()->forAll(s | s.listing.listingNumber <> request.listingNumber)

Once it has been provided:

  • Buyer still a member: The buyer the sale is recorded for is a member, so a sale can ask Membership about them.

    Required by Sales. Formally: Member.allInstances()->collect(m | m.login)->includes(request.buyerLogin)

  • Sale number is new: The number issued belonged to no sale before.

    Required by Sales. Formally: Sale.allInstances@pre()->forAll(s | s.saleNumber <> response.saleNumber)

  • Sale recorded: The sale is on record, awaiting the buyer’s payment.

    Required by Sales. Formally: Sale.allInstances()->exists(s | s.saleNumber = response.saleNumber and s.listing.listingNumber = request.listingNumber and s.buyer.login = request.buyerLogin and s.price = request.price and s.fee = request.fee and s.amountDue = request.amountDue and s.sellerPayout = request.sellerPayout and s.status = SaleStatus::awaitingPayment)

Exceptions

When a pre-condition does not hold, the Record sale service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Buyer is a member not met, raised when Buyer is a member does not hold: Raised when 'Record sale' is requested while 'Buyer is a member' does not hold.

  • Listing closed not met, raised when Listing closed does not hold: Raised when 'Record sale' is requested while 'Listing closed' does not hold.

  • Listing not yet sold not met, raised when Listing not yet sold does not hold: Raised when 'Record sale' is requested while 'Listing not yet sold' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Sales::Request.

What is supplied when requesting 'Record sale'.

The Auctioneer::Sales::Request data structure
Figure 71. The Auctioneer::Sales::Request data structure, fully expanded.

A Auctioneer::Sales::Request has:

  • one amountDue (its type is not yet specified): What the buyer pays.

  • one buyerLogin (its type is not yet specified): The highest bidder, by their login.

  • one fee (its type is not yet specified): What the auctioneer keeps.

  • one listingNumber (its type is not yet specified): The listing sold.

  • one price (its type is not yet specified): The winning bid.

  • one sellerPayout (its type is not yet specified): What the seller is paid.

Response data structure

The information the service returns once provided is a Auctioneer::Sales::Response.

What 'Record sale' answers with.

The Auctioneer::Sales::Response data structure
Figure 72. The Auctioneer::Sales::Response data structure, fully expanded.

A Auctioneer::Sales::Response has:

  • one saleNumber (its type is not yet specified): The number issued.

Business process

No business process is needed. The service’s post-conditions say exactly what it records, i.e. it creates a Sale. It is thus provided by making that one change.

7.1.5. Service: Update sale

Sales provides the Update sale service.

Records how far a sale has got.

Service requirements

The functional requirements diagram below shows who has an interest in the Update sale service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Update sale service.
Figure 73. Functional requirements of the Update sale service.

Its stakeholders, and what each requires of it, are:

  • Sales: Completing a sale: payment, payout, shipping and feedback.

    Sales requires the pre-condition Sale exists and the post-condition Sale updated.

It is provided only when:

  • Sale exists: Only a sale on record is updated.

    Required by Sales. Formally: Sale.allInstances()->exists(s | s.saleNumber = request.saleNumber)

Once it has been provided:

  • Sale updated: The sale carries the status and every detail given; what is not given is kept.

    Required by Sales. Formally: Sale.allInstances()->exists(s | s.saleNumber = request.saleNumber and s.status = request.status and s.paymentReference = if request.paymentReference->notEmpty() then request.paymentReference else Sale.allInstances@pre()->any(b | b.saleNumber = request.saleNumber).paymentReference endif and s.payoutReference = if request.payoutReference->notEmpty() then request.payoutReference else Sale.allInstances@pre()->any(b | b.saleNumber = request.saleNumber).payoutReference endif and s.shipment = if request.shipment->notEmpty() then request.shipment else Sale.allInstances@pre()->any(b | b.saleNumber = request.saleNumber).shipment endif and s.rating = if request.rating->notEmpty() then request.rating else Sale.allInstances@pre()->any(b | b.saleNumber = request.saleNumber).rating endif and s.feedback = if request.feedback->notEmpty() then request.feedback else Sale.allInstances@pre()->any(b | b.saleNumber = request.saleNumber).feedback endif)

Exceptions

When a pre-condition does not hold, the Update sale service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Sale exists not met, raised when Sale exists does not hold: Raised when 'Update sale' is requested while 'Sale exists' does not hold.

Request data structure

The information a requester provides when asking for the service is a Auctioneer::Sales::Request.

What is supplied when requesting 'Update sale'.

The Auctioneer::Sales::Request data structure
Figure 74. The Auctioneer::Sales::Request data structure, fully expanded.

A Auctioneer::Sales::Request has:

  • optionally one feedback (its type is not yet specified): The buyer’s words, once given.

  • optionally one paymentReference (its type is not yet specified): The buyer’s payment, once taken.

  • optionally one payoutReference (its type is not yet specified): The payout to the seller, once made.

  • optionally one rating (its type is not yet specified): The buyer’s rating, once given.

  • one saleNumber (its type is not yet specified): The sale.

  • optionally one shipment (its type is not yet specified): How the item was shipped, once it was.

  • one status, a Auctioneer::Sales::SaleStatus: How far it has got.

    One of awaitingPayment, completed, paid, paymentFailed, paymentOverdue and shipped.

Response data structure

The information the service returns once provided is a Auctioneer::Sales::Response.

What 'Update sale' answers with.

The Auctioneer::Sales::Response data structure
Figure 75. The Auctioneer::Sales::Response data structure, fully expanded.

A Auctioneer::Sales::Response carries no information of its own.

Business process

No business process is needed. The service’s post-conditions say exactly what it records, i.e. it updates a Sale. It is thus provided by making that one change.

7.2. Entities

An entity is information which Sales keeps over time. It is a record which outlives any one request, and which its services create, change and read. Sales maintains the following entities:

  • Sale: An item sold to its highest bidder, from payment to feedback.

The entity map below shows each entity together with its facets, i.e. the data structures whose fields make up what it stores.

The entities maintained by Sales.
Figure 76. The entities maintained by Sales.

7.2.1. Entity: Sale

An item sold to its highest bidder, from payment to feedback.

How it is populated

Sale is populated as follows:

  • The Record sale service creates a Sale, identified by saleNumber.

  • The Update sale service updates a Sale, identified by saleNumber.

  • The SaleRecord data structure describes part of what it holds: The auctioneer’s record of one sale.

Entity structure

The diagram below shows the Sale entity fully expanded, i.e. everything it holds, gathered from all of its facets, and the information it is related to. The same structure is described in words after it.

The Sale entity
Figure 77. The Sale entity, fully expanded.

A Sale has:

  • one amountDue (its type is not yet specified): What the buyer pays: the price and the shipping cost.

  • one fee (its type is not yet specified): What the auctioneer keeps.

  • optionally one feedback (its type is not yet specified): The buyer’s words about the sale.

  • optionally one paymentReference (its type is not yet specified): The payment gateway’s reference for the buyer’s payment.

  • optionally one payoutReference (its type is not yet specified): The bank’s reference for the payout to the seller.

  • one price (its type is not yet specified): The winning bid.

  • optionally one rating (its type is not yet specified): The buyer’s rating of the seller.

  • one saleNumber (its type is not yet specified), which identifies it: The sale’s number.

  • one sellerPayout (its type is not yet specified): What the seller is paid.

  • optionally one shipment (its type is not yet specified): How the item was shipped.

  • one status, a Auctioneer::Sales::SaleStatus: How far the sale has got.

    One of awaitingPayment, completed, paid, paymentFailed, paymentOverdue and shipped.

  • one version (its type is not yet specified), the version of the instance read, which an update is decided on: The version of the sale read.

A Sale is associated with:

  • one buyer, a Auctioneer::Membership::MemberRecord: The member who bought it.

  • one listing, a Auctioneer::Listings::ListingRecord: The listing sold.

Auctioneer::Membership::MemberRecord: The auctioneer’s record of one member.

A Auctioneer::Membership::MemberRecord has:

  • one email (its type is not yet specified): Where the member is written to.

  • one login (its type is not yet specified), unique: The login identity the member signs in with: what `caller` and `respondent` are compared with.

  • one memberNumber (its type is not yet specified), which identifies it: The member’s number.

  • one name (its type is not yet specified): The member’s name.

  • one payoutAccount (its type is not yet specified): The account the member is paid into when they sell.

  • one shippingAddress (its type is not yet specified): Where items bought are shipped.

The following must always hold for a Auctioneer::Membership::MemberRecord:

  • Member number format: self.memberNumber.matches('MB-[0-9]{4,}')

Auctioneer::Listings::ListingRecord: The auctioneer’s record of one item on offer.

A Auctioneer::Listings::ListingRecord has:

  • any number of bids, each a Auctioneer::Listings::Bid: The bids made, in the order made.

  • one closesAt (its type is not yet specified): When bidding closes.

  • one condition (its type is not yet specified): The state the item is in.

  • one description (its type is not yet specified): The item described.

  • any number of documents (its type is not yet specified): Supporting documents, by URL.

  • one listingNumber (its type is not yet specified), which identifies it: The listing’s number.

  • between 1 and 12 photos (its type is not yet specified): Photos of the item, by URL.

  • one shippingCost (its type is not yet specified): What the buyer pays for shipping.

  • one startingBid (its type is not yet specified): The lowest bid accepted.

  • one status, a Auctioneer::Listings::ListingStatus: Whether the listing still takes bids.

    One of closed and open.

  • one title (its type is not yet specified): What the item is, in a line.

  • one version (its type is not yet specified), the version of the instance read, which an update is decided on: The version of the listing read.

A Auctioneer::Listings::ListingRecord is associated with:

  • one seller, a Auctioneer::Membership::MemberRecord: The member selling the item.

The following must always hold for a Auctioneer::Listings::ListingRecord:

  • Amounts in euro: self.startingBid.currency = Currency::EUR and self.shippingCost.currency = Currency::EUR

  • Listing number format: self.listingNumber.matches('LI-[0-9]{4,}')

  • Shipping cost is not negative: self.shippingCost.amount >= 0

  • Starting bid is positive: self.startingBid.amount > 0

Auctioneer::Listings::Bid: One bid made for a listing.

A Auctioneer::Listings::Bid has:

  • one amount (its type is not yet specified): What they bid.

  • one bidderLogin (its type is not yet specified): Who bid, by their login.

  • one placedAt (its type is not yet specified): When the bid was made.

Data dictionary

This section lists what Sale stores, attribute by attribute. An attribute gathers every field of that name in the entity’s facets. Where it gathers more than one, each is listed, since fields of one name are stored as one attribute whatever each was meant to hold. The services listed write or read it as their specifications say.

Attribute Type Role Multiplicity Unique Personal data Merged from Written by Read by

amountDue

—

states

1

no

—

—

—

buyer

Auctioneer::Membership::MemberRecord

states

1

no

—

—

—

fee

—

states

1

no

—

—

—

feedback

—

states

0..1

no

—

—

—

listing

Auctioneer::Listings::ListingRecord

states

1

no

—

—

paymentReference

—

states

0..1

no

—

—

—

payoutReference

—

states

0..1

no

—

—

—

price

—

states

1

no

—

—

—

rating

—

states

0..1

no

—

—

—

saleNumber

—

identifies

1

yes

—

—

sellerPayout

—

states

1

no

—

—

—

shipment

—

states

0..1

no

—

—

—

status

Auctioneer::Sales::SaleStatus

states

1

no

—

—

—

7.3. Dependencies

To provide its services, Sales relies on services provided by other responsibility domains. The dependency diagram below shows which.

The responsibility domains Sales depends on.
Figure 78. The responsibility domains Sales depends on.

Sales uses:

  • from Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

  • from Payment Gateway: The card processor that charges buyers.

  • from Listings: What is on offer and what was bid for it.

    • the Close listing service: Closes a listing at its closing time and reports the highest bid, if any.

  • from Platform: The platform’s terms, the service fee among them.

  • from Membership: Who the members are.

    • the Get member service: Tells another part of the auctioneer what it needs of a member: where to ship to and where to pay.

  • from Bank: The bank that pays sellers.

    • the Pay seller service: Pays an amount into a seller’s account.

8. Bank

This part specifies the Bank responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

The bank that pays sellers.

An external system. Stubbed in the execution environment.

The scope diagram below shows what Bank is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Bank.
Figure 79. The scope of Bank.

8.1. Services

Bank is responsible for providing the following services. Each is described in its own section below: what it requires and what it guarantees (its service requirements), the information exchanged with it, how the work is allocated to the responsibility domains taking part, and the business process providing it.

  • Pay seller: Pays an amount into a seller’s account.

8.1.1. Service: Pay seller

Bank provides the Pay seller service.

Pays an amount into a seller’s account.

Service requirements

The functional requirements diagram below shows who has an interest in the Pay seller service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Pay seller service.
Figure 80. Functional requirements of the Pay seller service.

Its stakeholders, and what each requires of it, are:

  • Member: A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

    Member requires the post-condition Seller paid.

Once it has been provided:

  • Seller paid: The amount is paid into the payee’s account, under the reference answered.

    Required by Member.

Request data structure

The information a requester provides when asking for the service is a Bank::Request.

What is supplied when requesting 'Pay seller'.

The Bank::Request data structure
Figure 81. The Bank::Request data structure, fully expanded.

A Bank::Request has:

  • one amount (its type is not yet specified): What to pay.

  • one payee (its type is not yet specified): The seller’s account.

  • one reference (its type is not yet specified): The sale paid out for.

Response data structure

The information the service returns once provided is a Bank::Response.

What 'Pay seller' answers with.

The Bank::Response data structure
Figure 82. The Bank::Response data structure, fully expanded.

A Bank::Response has:

  • one payoutReference (its type is not yet specified): The bank’s reference for the payment.

The following must always hold for a Bank::Response:

  • Payout referenced: self.payoutReference.size() > 0

Business process

No business process providing this service has been specified yet.

9. Member

This part specifies the Member responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

A person registered with the auctioneer, who lists items, bids, pays, ships and confirms.

A role: anyone a member's login identifies plays it. The tasks of a sale are offered to the one member they are for, the buyer or the seller, by a respondent pre-condition.

The scope diagram below shows what Member is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Member.
Figure 83. The scope of Member.

9.1. Services

Member is responsible for providing the following services. Each is described in its own section below: what it requires and what it guarantees (its service requirements), the information exchanged with it, how the work is allocated to the responsibility domains taking part, and the business process providing it.

9.1.1. Service: Confirm receipt and rate

Member provides the Confirm receipt and rate service.

The buyer confirms the item arrived, and may rate the seller.

A task offered to the buyer alone.

Service requirements

The functional requirements diagram below shows who has an interest in the Confirm receipt and rate service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Confirm receipt and rate service.
Figure 84. Functional requirements of the Confirm receipt and rate service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-condition Answered by the buyer.

It is provided only when:

  • Answered by the buyer: Only the buyer confirms what they received.

    Required by Auctioneer. Formally: respondent = request.buyerLogin

It is answered only by the party which Answered by the buyer names as its respondent.

Exceptions

When a pre-condition does not hold, the Confirm receipt and rate service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Answered by the buyer not met, raised when Answered by the buyer does not hold: Raised when 'Confirm receipt and rate' is requested while 'Answered by the buyer' does not hold.

Request data structure

The information a requester provides when asking for the service is a Member::Request.

What is supplied when requesting 'Confirm receipt and rate'.

The Member::Request data structure
Figure 85. The Member::Request data structure, fully expanded.

A Member::Request has:

  • one buyerLogin (its type is not yet specified): Who confirms, by their login.

  • one saleNumber (its type is not yet specified): The sale.

  • one shipment (its type is not yet specified): How it was shipped.

  • one title (its type is not yet specified): The item bought.

Response data structure

The information the service returns once provided is a Member::Response.

What 'Confirm receipt and rate' answers with.

The Member::Response data structure
Figure 86. The Member::Response data structure, fully expanded.

A Member::Response has:

  • optionally one feedback (its type is not yet specified): Their words about the sale.

  • optionally one rating (its type is not yet specified): Their rating of the seller.

The following must always hold for a Member::Response:

  • Feedback comes with a rating: self.feedback->notEmpty() implies self.rating->notEmpty()

Business process

No business process providing this service has been specified yet.

9.1.2. Service: Pay for item

Member provides the Pay for item service.

The buyer pays for what they won.

A task offered to the buyer alone: respondent is compared with the buyer's login.

Service requirements

The functional requirements diagram below shows who has an interest in the Pay for item service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Pay for item service.
Figure 87. Functional requirements of the Pay for item service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-condition Answered by the buyer.

It is provided only when:

  • Answered by the buyer: Only the buyer pays.

    Required by Auctioneer. Formally: respondent = request.buyerLogin

It is answered only by the party which Answered by the buyer names as its respondent.

Exceptions

When a pre-condition does not hold, the Pay for item service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Answered by the buyer not met, raised when Answered by the buyer does not hold: Raised when 'Pay for item' is requested while 'Answered by the buyer' does not hold.

Request data structure

The information a requester provides when asking for the service is a Member::Request.

What is supplied when requesting 'Pay for item'.

The Member::Request data structure
Figure 88. The Member::Request data structure, fully expanded.

A Member::Request has:

  • one amountDue (its type is not yet specified): What to pay: the price and the shipping cost.

  • one buyerLogin (its type is not yet specified): Who is to pay, by their login.

  • one saleNumber (its type is not yet specified): The sale to pay for.

  • one title (its type is not yet specified): The item bought.

Response data structure

The information the service returns once provided is a Member::Response.

What 'Pay for item' answers with.

The Member::Response data structure
Figure 89. The Member::Response data structure, fully expanded.

A Member::Response has:

  • one paymentToken (its type is not yet specified): The payment gateway’s token for the buyer’s card or account.

The following must always hold for a Member::Response:

  • Payment details given: self.paymentToken.size() > 0

Business process

No business process providing this service has been specified yet.

9.1.3. Service: Provide shipping details

Member provides the Provide shipping details service.

The seller ships the item and says how.

A task offered to the seller, told the sale and that it has been paid for. A supervisor of the task's domain may answer on the seller's behalf.

Service requirements

The functional requirements diagram below shows who has an interest in the Provide shipping details service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Provide shipping details service.
Figure 90. Functional requirements of the Provide shipping details service.

Its stakeholders, and what each requires of it, are:

  • Auctioneer: The online auctioneer: runs the auctions and completes each sale.

    Auctioneer requires the pre-condition Answered by the seller.

It is provided only when:

  • Answered by the seller: Only the seller, or someone acting for them, says how the item was shipped.

    Required by Auctioneer. Formally: respondent = request.sellerLogin

It is answered only by the party which Answered by the seller names as its respondent. A supervisor may answer on behalf of that party.

Exceptions

When a pre-condition does not hold, the Provide shipping details service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Answered by the seller not met, raised when Answered by the seller does not hold: Raised when 'Provide shipping details' is requested while 'Answered by the seller' does not hold.

Request data structure

The information a requester provides when asking for the service is a Member::Request.

What is supplied when requesting 'Provide shipping details'.

The Member::Request data structure
Figure 91. The Member::Request data structure, fully expanded.

A Member::Request has:

  • one buyerName (its type is not yet specified): Who to ship to.

  • one paymentReference (its type is not yet specified): The buyer’s payment: the confirmation that it has been paid for.

  • one saleNumber (its type is not yet specified): The sale to ship.

  • one sellerLogin (its type is not yet specified): Who ships, by their login.

  • one shippingAddress (its type is not yet specified): Where to ship to.

  • one title (its type is not yet specified): The item sold.

Response data structure

The information the service returns once provided is a Member::Response.

What 'Provide shipping details' answers with.

The Member::Response data structure
Figure 92. The Member::Response data structure, fully expanded.

A Member::Response has:

  • one shipment (its type is not yet specified): The carrier and the tracking number.

The following must always hold for a Member::Response:

  • Tracking number given: self.shipment.trackingNumber.size() > 0

Business process

No business process providing this service has been specified yet.

10. Payment Gateway

This part specifies the Payment Gateway responsibility domain. A responsibility domain is an area of responsibility, e.g. a business unit, a role or a system, which provides services to others and may in turn rely on services of other domains.

The card processor that charges buyers.

An external system. Stubbed in the execution environment.

The scope diagram below shows what Payment Gateway is responsible for, i.e. the services it provides and the lower-level responsibility domains it contains.

The scope of Payment Gateway.
Figure 93. The scope of Payment Gateway.

10.1. Services

Payment Gateway is responsible for providing the following services. Each is described in its own section below: what it requires and what it guarantees (its service requirements), the information exchanged with it, how the work is allocated to the responsibility domains taking part, and the business process providing it.

10.1.1. Service: Charge payment

Payment Gateway provides the Charge payment service.

Charges the buyer’s card or account.

Service requirements

The functional requirements diagram below shows who has an interest in the Charge payment service, i.e. its stakeholders, and what each requires of it. A pre-condition is a condition which must hold for the service to be provided at all. When one does not, the request is refused with an exception. A post-condition is what must be true once the service has been provided, i.e. what it must have achieved.

Functional requirements of the Charge payment service.
Figure 94. Functional requirements of the Charge payment service.

Its stakeholders, and what each requires of it, are:

  • Payment Gateway: The card processor that charges buyers.

    Payment Gateway requires the pre-condition Payment authorised.

It is provided only when:

  • Payment authorised: The card or account behind the token covers the amount.

    Required by Payment Gateway.

Exceptions

When a pre-condition does not hold, the Charge payment service is not provided. Instead, it raises the exception belonging to that pre-condition, which the requester may handle. These are the ways in which the service can fail:

  • Payment authorised not met, raised when Payment authorised does not hold: Raised when 'Charge payment' is requested while 'Payment authorised' does not hold.

Request data structure

The information a requester provides when asking for the service is a Payment Gateway::Request.

What is supplied when requesting 'Charge payment'.

The Payment Gateway::Request data structure
Figure 95. The Payment Gateway::Request data structure, fully expanded.

A Payment Gateway::Request has:

  • one amount (its type is not yet specified): What to charge.

  • one paymentToken (its type is not yet specified): The buyer’s token.

  • one reference (its type is not yet specified): The sale charged for.

Response data structure

The information the service returns once provided is a Payment Gateway::Response.

What 'Charge payment' answers with.

The Payment Gateway::Response data structure
Figure 96. The Payment Gateway::Response data structure, fully expanded.

A Payment Gateway::Response has:

  • one paymentReference (its type is not yet specified): The gateway’s reference for the payment.

The following must always hold for a Payment Gateway::Response:

  • Payment referenced: self.paymentReference.size() > 0

Business process

No business process providing this service has been specified yet.