Skip to main content

Distribution Functions

After the audit window is completed, a node is selected and tasked with the responsibility of generating and submitting a distribution list on-chain.

What is a Distribution List?

A distribution list is a JSON object that contains a key-value pair, where the key is the node's public key and the value is the number of KOII tokens to be awarded to the node.

Distribution list example:

const distributionList = {
"29SSj6EQARvATESSQbBcmSE3A1iaWwqXFunzAEDoV7Xj": 100,
"3KUfsjpjCSCjwCBm4TraM5cGx6YzEUo9rrq2hrSsJw3x": 200,
Avxvdc2efsPqysBZt4VKDSgiP4iuJ8GaAWhsNVUAi5CZ: 300,
};

generateDistributionList()

As the name suggests, this function generates the distribution list.

For the example on the template:

  • An empty distribution list is initialized
  • The task's data is retrieved using the getTaskState helper function
  • All valid submissions are fetched from the task's data
  • The submissions_audit_trigger is also retrieved from the task's data; this object contains information about the audited submissions
  • If submissions is null, an empty distribution list is returned. Otherwise, the keys and values of the submissions are grouped separately and in a loop, it calculates the audits on each submission and how many votes on the audit, and based on that it makes a decision.
/**
* @description Generates a distribution list that contains the key:value pair
* of participating nodes' public keys and amount of KOII to be rewarded.
* Introduce preferred rules when generating a distribution list
* @param {number} round Current round of the task
*/
async function generateDistributionList(round) {
let distributionList = {}; // init distribution list
const taskAccountDataJSON = await namespaceWrapper.getTaskState(); // retrieve task data
const submissions = taskAccountDataJSON.submissions[round]; // retrieve submissions
const submissions_audit_trigger =
taskAccountDataJSON.submissions_audit_trigger[round];

if (submissions == null) {
return distributionList;
} else {
const keys = Object.keys(submissions);
const values = Object.values(submissions);
const size = values.length;
console.log("Submissions from last round: ", keys, values, size);

for (let i = 0; i < size; i++) {
const candidatePublicKey = keys[i];
if (
submissions_audit_trigger &&
submissions_audit_trigger[candidatePublicKey]
) {
console.log(
submissions_audit_trigger[candidatePublicKey].votes,
"distributions_audit_trigger votes"
);
const votes = submissions_audit_trigger[candidatePublicKey].votes;
let numOfVotes = 0;
for (let index = 0; index < votes.length; index++) {
if (votes[i].is_valid) numOfVotes++;
else numOfVotes--;
}
if (numOfVotes < 0) continue;
}
distributionList[candidatePublicKey] = 1;
}
}
}

When writing this function for your task, you can use logic to determine how many KOII tokens to award to each node based on priority. You can award more KOII tokens to the node that worked the hardest to complete the task or to the node that staked the most KOII tokens.

info

Click here to find out the full task data retrieved from getTaskState()

submitDistributionList()

This function submits the distribution list generated by generateDistributionList() to K2.

For the example on the template:

  • The generateDistributionList() is called to retrieve the distribution list
  • The distribution list is submitted on-chain
/**
* @description Submits distribution list to K2 including the current round
*
* @param {number} round Current round of the task
*/
async function submitDistributionList(round) {
console.log("SubmitDistributionList called");

const distributionList = await generateDistributionList(round); // get distribution list

const decider = await namespaceWrapper.uploadDistributionList(
distributionList,
round
);
console.log("DECIDER", decider);

if (decider) {
const response = await namespaceWrapper.distributionListSubmissionOnChain(
round
);
console.log("RESPONSE FROM DISTRIBUTION LIST", response);
}
}

Click the link below to learn about auditing the distribution list.

Audit Distribution List