diff --git a/abis/TalentLayerEscrow.json b/abis/TalentLayerEscrow.json index 3d58f5a4..a994a825 100644 --- a/abis/TalentLayerEscrow.json +++ b/abis/TalentLayerEscrow.json @@ -382,7 +382,7 @@ }, { "indexed": false, - "internalType": "enum TalentLayerEscrowV1.PaymentType", + "internalType": "enum TalentLayerEscrow.PaymentType", "name": "_paymentType", "type": "uint8" }, @@ -408,6 +408,25 @@ "name": "Payment", "type": "event" }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "_serviceId", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "_transactionId", + "type": "uint256" + } + ], + "name": "PaymentCompleted", + "type": "event" + }, { "anonymous": false, "inputs": [ diff --git a/schema.graphql b/schema.graphql index 335e4d9b..4995f8db 100644 --- a/schema.graphql +++ b/schema.graphql @@ -147,7 +147,7 @@ type Proposal @entity { status: ProposalStatus! # Proposal status seller: User # Proposal seller rateToken: Token! # Rate token entity - rateAmount: BigInt # Rate amount + rateAmount: BigInt! # Rate amount cid: String # cid of the description platform: Platform # Platform on which proposal was created description: ProposalDescription #Proposals that the description describes. @@ -190,6 +190,8 @@ type Transaction @entity { receiver: User # receiver of the transaction token: Token! # token entity amount: BigInt! # amount + releasedAmount: BigInt! # Total released amount + totalAmount: BigInt! # Total escrowed amount service: Service # service entity protocolEscrowFeeRate: Int! # fee paid to the protocol originServiceFeeRate: Int! # Fee asked by the platform which created the service diff --git a/src/getters.ts b/src/getters.ts index 697de375..a205a4c0 100644 --- a/src/getters.ts +++ b/src/getters.ts @@ -43,6 +43,7 @@ export function getOrCreateProposal(id: string, serviceId: BigInt): Proposal { proposal.updatedAt = ZERO proposal.service = getOrCreateService(serviceId).id proposal.rateToken = getOrCreateToken(ZERO_ADDRESS).id + proposal.rateAmount = ZERO proposal.expirationDate = ZERO proposal.save() } @@ -105,6 +106,8 @@ export function getOrCreateTransaction(id: BigInt, blockTimestamp: BigInt = ZERO transaction = new Transaction(id.toString()) transaction.token = '' transaction.amount = ZERO + transaction.releasedAmount = ZERO + transaction.totalAmount = ZERO transaction.protocolEscrowFeeRate = 0 transaction.originServiceFeeRate = 0 transaction.originValidatedProposalFeeRate = 0 diff --git a/src/mappings/talent-layer-escrow.ts b/src/mappings/talent-layer-escrow.ts index 64a439d2..21d9a606 100644 --- a/src/mappings/talent-layer-escrow.ts +++ b/src/mappings/talent-layer-escrow.ts @@ -1,4 +1,4 @@ -import { BigInt, DataSourceContext, log } from '@graphprotocol/graph-ts' +import { BigInt, DataSourceContext } from '@graphprotocol/graph-ts' import { Service, Transaction, User } from '../../generated/schema' import { getOrCreateService, @@ -19,7 +19,8 @@ import { import { Payment as PaymentCurrent, Payment1 as PaymentV1, - PaymentCompleted, + PaymentCompleted as PaymentCompleted, + PaymentCompleted1 as PaymentCompletedV1, FeesClaimed, ProtocolEscrowFeeRateUpdated, TransactionCreated, @@ -58,6 +59,7 @@ export function handleTransactionCreated(event: TransactionCreated): void { transaction.receiver = User.load(event.params._receiverId.toString())!.id transaction.token = getOrCreateToken(event.params._token).id transaction.amount = event.params._amount + transaction.totalAmount = event.params._amount transaction.service = Service.load(event.params._serviceId.toString())!.id transaction.protocolEscrowFeeRate = event.params._protocolEscrowFeeRate transaction.originServiceFeeRate = event.params._originServiceFeeRate @@ -81,8 +83,19 @@ export function handleTransactionCreated(event: TransactionCreated): void { } export function handlePaymentCompleted(event: PaymentCompleted): void { + const protocol = getOrCreateProtocol() const service = getOrCreateService(event.params._serviceId) service.status = 'Finished' + const transaction = getOrCreateTransaction(event.params._transactionId) + + const releasedAmount = transaction.totalAmount.minus(transaction.releasedAmount) + const releasedPercentage = releasedAmount.times(BigInt.fromString('100')).div(transaction.totalAmount) + if (releasedPercentage >= protocol.minServiceCompletionPercentage) { + service.status = 'Finished' + } else { + service.status = 'Uncompleted' + } + service.updatedAt = event.block.timestamp service.save() @@ -99,11 +112,12 @@ export function handlePayment(event: PaymentCurrent): void { const paymentId = generateUniqueId(event.transaction.hash.toHex(), event.logIndex.toString()) const payment = getOrCreatePayment(paymentId, event.params._serviceId, event.params._proposalId) const token = event.params._token + const transaction = getOrCreateTransaction(event.params._transactionId) payment.amount = event.params._amount payment.rateToken = getOrCreateToken(token).id payment.createdAt = event.block.timestamp - payment.transaction = Transaction.load(event.params._transactionId.toString())!.id + payment.transaction = transaction.id if (event.params._paymentType === PaymentType.Release) { payment.paymentType = 'Release' @@ -117,6 +131,8 @@ export function handlePayment(event: PaymentCurrent): void { userGain.totalGain = userGain.totalGain.plus(event.params._amount) userGain.save() } + // Update released amount in case of a release + transaction.releasedAmount = transaction.releasedAmount.plus(event.params._amount) } if (event.params._paymentType === PaymentType.Reimburse) { payment.paymentType = 'Reimburse' @@ -125,7 +141,6 @@ export function handlePayment(event: PaymentCurrent): void { payment.transactionHash = event.transaction.hash.toHex() payment.save() - const transaction = getOrCreateTransaction(event.params._transactionId) transaction.amount = transaction.amount.minus(event.params._amount) transaction.save() } @@ -307,3 +322,18 @@ export function handlePaymentV1(event: PaymentV1): void { transaction.amount = transaction.amount.minus(event.params._amount) transaction.save() } + +export function handlePaymentCompletedV1(event: PaymentCompletedV1): void { + const service = getOrCreateService(event.params._serviceId) + service.status = 'Finished' + service.updatedAt = event.block.timestamp + service.save() + + const buyerUserStats = getOrCreateUserStats(BigInt.fromString(service.buyer!)) + buyerUserStats.numFinishedServicesAsBuyer.plus(ONE) + buyerUserStats.save() + + const sellerUserStats = getOrCreateUserStats(BigInt.fromString(service.seller!)) + sellerUserStats.numFinishedServicesAsSeller.plus(ONE) + sellerUserStats.save() +} diff --git a/subgraph.yaml b/subgraph.yaml index 7b8cd804..75c4c7fc 100644 --- a/subgraph.yaml +++ b/subgraph.yaml @@ -129,10 +129,10 @@ dataSources: - name: ERC20 file: ./abis/ERC20.json eventHandlers: - - event: PaymentCompleted(uint256) - handler: handlePaymentCompleted - event: Payment(uint256,uint8,address,uint256,uint256,uint256) handler: handlePayment + - event: PaymentCompleted(uint256,uint256) + handler: handlePaymentCompleted - event: FeesClaimed(uint256,indexed address,uint256) handler: handleFeesClaimed - event: OriginServiceFeeRateReleased(uint256,uint256,indexed address,uint256) @@ -159,6 +159,8 @@ dataSources: # Legacy events - event: Payment(uint256,uint8,address,uint256,uint256) handler: handlePaymentV1 + - event: PaymentCompleted(uint256) + handler: handlePaymentCompletedV1 file: ./src/mappings/talent-layer-escrow.ts - kind: ethereum/contract name: TalentLayerPlatformID