Parallel Identity Token | Parallel Developer Documentation
Parallel Developer Documentation Legacy – v1.x
This is documentation for Parallel Developer Documentation Legacy – v1.x, which is no longer actively maintained.
For up-to-date documentation, see the latest version (Current – v2.x).
Version: Legacy – v1.x
Overview
The Parallel Identity (PID) Token is a non-transferrable, non-fungible token (NFT) that links real world individual and business identities with Ethereum wallet addresses. The PID Token provides accreditation, Know Your Customer (KYC), and international sanctions information in the form of a ERC-721 compatible token.
Features
The PID Token has a number of features:
- Parallel Markets provides ongoing sanctions monitoring information on-chain for every PID Token holder for a year after minting
- Individuals (natural persons) and businesses (any form of corporate entity) can have a PID Token
- Tokens can contain additional traits, including accreditation status and other DeFi-related information
- While no PII is stored in the Token, every Token holder has gone through a rigorous KYC process, including for any business/corporate entity that owns the wallet
Getting Started
You can access PID Token information either directly on-chain on the Ethereum Mainnet or via one of the Web3 JavaScript libraries.
Ethereum Contract Access
Here's a quick example of usage on-chain to determine if a Token holder (individual or business) is currently accredited and free from sanctions. Just make sure to install the PID Token NPM package first to get easy access to the IParallelID interface.
import "@parallelmarkets/token/contracts/IParallelID.sol";
contract MyContract {
address public PID_CONTRACT = 0x9ec6232742b6068ce733645AF16BA277Fa412B0A;
function isSanctionsSafe(address subject) public view returns (bool) {
IParallelID pid = IParallelID(PID_CONTRACT);
for (uint256 i = 0; i < pid.balanceOf(subject); i++) {
uint256 tokenId = pid.tokenOfOwnerByIndex(subject, i);
if (pid.isSanctionsSafe(tokenId)) return true;
}
return false;
}
function currentlyAccredited(address subject) public view returns (bool) {
IParallelID pid = IParallelID(PID_CONTRACT);
for (uint256 i = 0; i < pid.balanceOf(subject); i++) {
uint256 tokenId = pid.tokenOfOwnerByIndex(subject, i);
bool recent = pid.mintedAt(tokenId) >= block.timestamp - 90 days;
bool accredited = pid.hasTrait(tokenId, "accredited");
if (recent && accredited) return true;
}
return false;
}
}
dApp JavaScript Access
This example uses the ethers.js library.
import { utils, Contract } from 'ethers'
const abi = [
'function tokenOfOwnerByIndex(address owner, uint256 index) view returns (uint256)',
'function balanceOf(address owner) view returns (uint256 balance)',
'function hasTrait(uint256 tokenId, string memory trait) view returns (bool)',
'function isSanctionsSafe(uint256 tokenId) view returns (bool)',
]
const PID_CONTRACT = '0x9ec6232742b6068ce733645AF16BA277Fa412B0A'
const contract = new Contract(PID_CONTRACT, abi, provider)
const isSanctionsSafe = (address) => {
for (let i = 0; i < contract.balanceOf(address); i++) {
const tokenId = contract.tokenOfOwnerByIndex(address, i)
if (contract.isSanctionsSafe(tokenId)) return true
}
return false
}
const currentlyAccredited = (address) => {
const ninetyDaysAgo = new Date().getTime() / 1000 - 90 * 86400
for (let i = 0; i < contract.balanceOf(address); i++) {
const tokenId = contract.tokenOfOwnerByIndex(address, i)
const recent = contract.mintedAt(tokenId) >= ninetyDaysAgo
const accredited = contract.hasTrait(tokenId, 'accredited')
if (recent && accredited) return true
}
return false
}
Contract Interface
In addition to the functions / events available as a part of the base ERC-721 description, the Parallel Identity Token also supports the Metadata and Enumerable extensions described in the specification. There are also custom functions to determine whether a subject, individual or business is sanctioned. The contract supports arbitrary string "traits" that provide an extensible way to indicate additional attributes for token holders. The list of available traits currently includes:
accredited: The subject was found to meet the regulatory requirements for accreditation based on an affirmative check of relevant source documentation.
Additional Functions
These functions exist on the contract in addition to those available via the base ERC-721 and Metadata / Enumerable extensions.
function isSanctionsMonitored(uint256 tokenId) public view returns (bool)
function isSanctionsSafe(uint256 tokenId) view returns (bool)
function mintedAt(uint256 tokenId) public view returns (uint256)
function isSanctionsSafeIn(uint256 tokenId, uint256 countryId) view returns (bool)
function subjectType(uint256 tokenId) view returns (uint16)
function hasTrait(uint256 tokenId, string memory trait) view returns (bool)
function traits(uint256 tokenId) view returns (string[] memory)
function burn(uint256 tokenId) external;
Events
Events will be emitted on trait addition/removal and sanctions matches.
event TraitAdded(uint256 indexed tokenId, string trait);
event TraitRemoved(uint256 indexed tokenId, string trait);
event SanctionsMatch(uint256 indexed tokenId, uint256 countryId);
Constants
uint16 public constant SUBJECT_INDIVIDUAL = 0;
uint16 public constant SUBJECT_BUSINESS = 1;
Sanctions Monitoring
Parallel Markets monitors PID Token holders for one year after minting and will actively update sanctions if any sanctions matches are found. Parallel actively monitors hundreds of sanctions lists, including:
- Office of Foreign Assets Control (OFAC) lists for the US Treasury Department
- Additional US Government Agencies like the Department of Justice and Customs and Border Protection
- International agencies, like Interpol, Europol, the World Bank, and the International Organization of Securities Commissions
- Hundreds of lists for individual countries across Europe, Central / South America, the Asia/Pacific region, the Middle East, Africa, and North America.
If you would like to restrict your consideration to specific countries or international agencies, you can use the isSanctionsSafeIn function to perform a specific lookup. If the token is still monitored (i.e., it's less than a year old) and the token holder is free from sanctions in the specified area, then the function will return true. Otherwise, it will return false.
The countryId parameter can be used to perform a lookup:
- In a specific country, using ISO 3166 country codes
- United Nations M49 statistical codes for international agencies:
1indicates sanctions for Interpol150indicates sanctions for either Europol or an EU regulatory body
Know Your Customer
Parallel Markets performs a US regulatorily compliant check for individuals and businesses to establish identity.
For individuals (natural persons), Parallel will:
- Request and verify government identification
- Collect tax id, date of birth, residency and other personal details
- Compare provided information against public and private datasets to determine if there is a high match against a known person
For businesses (corporations, trusts, and any other entities that are not natural persons), Parallel will:
- Request formation documentation (articles of incorporation, etc)
- Collect tax id, incorporation location, company addresses
- Compare provided information against public and private datasets to determine if there is a high match against a known entity
- Request information for all control persons, who must then each go through an individual KYC process
- Request information for all beneficial owners (at the 25% ownership level or higher), who much then each go through a KYC process
Any use of the PID Token by any person or business entity for any reason is subject to our Terms of Service, Privacy Policy and Web3-Specific Disclaimers.