# zksbt service payment spec
## Terminology
- **Service** Payment is now prior to **zksbt mint**, and bind to specific zksbt, but the dsign could be more general in this spec, so as to compatible with future demands
|params|type||
|---|---|---|
|category|bigint|zksbt mintID|
|attribute|string|zksbt attribute, such as, pomp range|
|serviceType|string|service for pay, like, **Using the value of mintId**|
|serviceData|string|a jason string of service metadata, like, <br> **{tokenId: 'tokenId'}**|
## Workflow
1. Frontend POST Request **salt** from backend
```json
POST /npo/aigc/salt
{
"address": "string",
"mintId": "string",
"tokenId": "string"
}
```
2. Frontend call SDK.generateServiceProof
```typescript=
const serviceData = "{tokenId: 'tokenId'}"
const serviceType = mintId
const zkp = await sdk.generateServiceProof(
category,
attribute,
serviceType,
serviceData,
salt
)
const nullifierHash = zkp.publicSignals.nullifierHash
const proof = zkp.proof
```
3. Frontend POST service request.
```json
POST /npo/aigc/servicePayment
{
"public_address": "string",
"address": "string"
"mintId": "string",
"attribute": "string",
"tokenId": "string",
"serviceData": "string",
"nullifierHash": "string",
"proof": {}
}
```
4. Backend Verify Proof with salt, update salt, signature service with fee.
```typescript=
const signalHash = service_signal_hash(
publicAddress,
category,
attribute,
serviceType,
serviceData
)
const valid = await verifyIdentitySignalProof(
publicAddress,
nullifierHash,
signalHash,
salt,
this.identity_zkey,
proof
)
assert(valid == true, "invalid proof")
// fee management
const fee = BigInt(Math.floor(Math.random() * 10000))
const msg = service_certi_msg(
publicAddress.toString(),
category,
attribute,
serviceType,
serviceData,
fee
)
const certificate_signature = await this.signer.signMessage(msg);
return {
eligible : true,
signature : certificate_signature,
fee : fee,
}
```
5. Frontend call SDK.payForService, metamask tx.
```typescript=
await sdk.payForService(
category,
attribute,
serviceType,
serviceData,
service_certificate.fee,
service_certificate.signature
)
```
6. Backend Monitor On-chain Event
```solidity=
struct ServiceInfo {
uint publicAddress;
uint category;
string attribute;
string serviceType;
string serviceData;
}
event PayForService(
ServiceInfo service,
uint fee
);
```
```mermaid
sequenceDiagram
participant F as User/Frontend
participant B as Backend
participant C as Contract/Blockchain
%% Proof Key generate
rect rgba(0, 220, 220, .3)
F -->> B : get salt[publicAddress][service]
B -->> F : salt[publicAddress][service]
F -->> B : proof = zkp(service, salt)
B -->> B : verify(service, salt)
B -->> B : upgrade salt[publicAddress][service]
B -->> F : signature(service, fee)
F -->> C : payForService(service, fee, signature)
end
```
## [DEMO](https://github.com/Manta-Network/zksbt/blob/integrate/packages/contracts/test/zksbt.test.ts#L87)
## JSSDK
@zksbt/jssdk 0.8.2
## TESTNET
0x74AAFfeB0eDd591b78BDb67Ff7cd054d4d0dA51E