Links

Supporting Documents

For compliance reasons, Swan needs to collect documents from users during onboarding and other processes. Here's how document collection works.

Supporting document collection

A supporting document collection is like a folder; each folder is dedicated to documents that serve a specific purpose. That purpose could be onboarding, compliance review of a transaction, etc.
Supporting document collection status
A collection is empty at first and you can add supporting documents to it later. Please find below the state diagram for the supporting document. We will explain each status later in this documentation.
Supporting document status

Get a list of required supporting documents

To get the list of minimum documents required by compliance to validate an account holder, (whetherCompany or Individual), check the onboarding mutation responses. In some cases, extra documents are required. Please find below an exhaustive list of supportingDocumentPurpose: otherwise, you'll no longer be able to modify the documents provided.
  • CompanyRegistration
  • SignedStatus
  • ProofOfAddress
  • ProofOfIdentity
  • ProofOfIncome
  • Other
Each supportingDocumentPurpose is associated to a list of supportingDocumentType also exposed in the onboarding payload.
Request
Response
mutation MyMutation {
onboardCompanyAccountHolder(
input: {
accountName: "Swan"
businessActivity: FinancialAndInsuranceOperations
businessActivityDescription: "test"
companyType: Company
email: "{{YOUR_EMAIL}}"
isRegistered: true
language: "fr"
monthlyPaymentVolume: Between50000And100000
name: "Swan"
residencyAddress: {
addressLine1: "1 rue gaillon"
city: "paris"
country: "FRA"
postalCode: "75002"
state: "idf"
}
registrationNumber: "123456789"
}
) {
... on OnboardCompanyAccountHolderSuccessPayload {
__typename
onboarding {
supportingDocumentCollection {
id
requiredSupportingDocumentPurposes {
acceptableSupportingDocumentTypes
name
}
statusInfo {
status
}
}
id
statusInfo {
status
}
}
}
}
}
{
"data": {
"onboardCompanyAccountHolder": {
"__typename": "OnboardCompanyAccountHolderSuccessPayload",
"onboarding": {
"supportingDocumentCollection": {
"id": "{{YOUR_SUPPORTING_DOCUMENT_COLLECTION_ID}}",
"requiredSupportingDocumentPurposes": [
{
"acceptableSupportingDocumentTypes": [
"RegisterExtract",
"ArticlesOfIncorporation",
"CapitalShareDepositCertificate",
"UBODeclaration"
],
"name": "CompanyRegistration"
},
{
"acceptableSupportingDocumentTypes": [
"ByLaws"
],
"name": "SignedStatus"
}
],
"statusInfo": {
"status": "WaitingForDocument"
}
},
"id": "{{YOUR_ONBOARDING_ID}}",
"statusInfo": {
"status": "Valid"
}
}
}
}
}

Add a supporting document to a collection

To add a supporting document, call the generateSupportingDocumentUploadUrl mutation. You have to mention both supportingDocumentPurpose and supportingDocumentType
Request
Reponse
mutation MyMutation {
generateSupportingDocumentUploadUrl(
input: {
supportingDocumentCollectionId: "{{YOUR_SUPPORTING_DOCUMENT_COLLECTION_ID}}"
filename: "KBisMyCompany.pdf"
supportingDocumentPurpose: CompanyRegistration
supportingDocumentType: RegisterExtract
}
) {
... on GenerateSupportingDocumentUploadUrlSuccessPayload {
__typename
upload {
fields {
key
value
}
url
}
}
}
}
{
"data": {
"generateSupportingDocumentUploadUrl": {
"__typename": "GenerateSupportingDocumentUploadUrlSuccessPayload",
"upload": {
"fields": [
{
"key": "Key",
"value": "INPUT/865ed98c-64aa-4288-a51a-e2f199287ab8"
},
{
"key": "X-Amz-Algorithm",
"value": "AWS4-HMAC-SHA256"
},
{
"key": "X-Amz-Credential",
"value": "ASIAWHEXXLUXL7AGJ4VK/20220705/eu-west-1/s3/aws4_request"
},
{
"key": "X-Amz-Date",
"value": "20220705T153359Z"
},
{
"key": "X-Amz-Security-Token",
"value": "FwoGZXIvYXdzEJH//////////wEaDCfPIY23o3yUfkdcBiKnBCMRiFV1ec3bQNAeD4yvIkMeVBuI3+XgizJ72OAseCffRFdhIIM9Bx80x6Mrb04IrtggYOm8GZZngpBwVJJwib06sXXYdAbkW59j2NKj7kE1FsiBs5MGq3lGpOgKHTWocr1et3vULY4Et2yLHkE1D+pwW4CExYqW6R2azviUhPJ2MACXLR2FvngTp5WdzkRKHc+AhDnue42JA0NUgJv+sQTJ5giYYMntrHdBBV8EWJfupgDEPNvqlyussVH5TT3uB2eatU1SwWgpaVTxyL7p0v4rWR6zDRRoMMmKi59R8TjHgfQcjEBIu0xnIjULLqmSYHRVhbQcFBnLtAzZdip0S7kpPIm2ZD7NajmTBffP+28GRmy2NgDX5wJ1yBqnXcJ7YGW2NKv2MN83WuHoEEDrYPYZTnPSIRL4gw/i4itcNBi1f54LxO3tsvlutiHk24UBh6HyJ2pzFpXjiKTpfz9LW92x0OqYlpX0XqxOsJMpC9e6aBlaMQymxlD2FsFoGm+zJ9iht7KjFOQZsYzDzzdDzMWK9NPFd5v9FH04ldER7Q9U90HOh7TsXz1ckAmTGF4QqrEFRjzD+080m90YU2P/zyJd8XIgIaN+HSsClbQfOv39uwQJ8tyud2TUdZg0KVCEKfPr7INZyWdoJayK2sNWdfoAglkEcG90pMx0caPH4Vot9oEpX93ej04Ep6lX2d6Spioy/8u9GqujUufWa94uCAgEXCreTe7sKOezkZYGMivr4PRAjuMb7fnDjGzSAXMqhy8xa7z9HSOmiViDgtv8WzKw1PsxoHMtNPET"
},
{
"key": "Policy",
"value": "eyJleHBpcmF0aW9uIjoiMjAyMi0wNy0xMlQxNTozMzo1OVoiLCJjb25kaXRpb25zIjpbWyJjb250ZW50LWxlbmd0aC1yYW5nZSIsMCwyMDk3MTUyMF0sWyJlcSIsIiR4LWFtei1tZXRhLXgtc3dhbi1zdXBwb3J0aW5nLWRvY3VtZW50LWlkIiwiODY1ZWQ5OGMtNjRhYS00Mjg4LWE1MWEtZTJmMTk5Mjg3YWI4Il0seyJrZXkiOiJJTlBVVC84NjVlZDk4Yy02NGFhLTQyODgtYTUxYS1lMmYxOTkyODdhYjgifSx7ImJ1Y2tldCI6InN3YW4tc3VwcG9ydGluZy1kb2N1bWVudC1tYXN0ZXItc2FuZGJveCJ9LHsiWC1BbXotQWxnb3JpdGhtIjoiQVdTNC1ITUFDLVNIQTI1NiJ9LHsiWC1BbXotQ3JlZGVudGlhbCI6IkFTSUFXSEVYWExVWEw3QUdKNFZLLzIwMjIwNzA1L2V1LXdlc3QtMS9zMy9hd3M0X3JlcXVlc3QifSx7IlgtQW16LURhdGUiOiIyMDIyMDcwNVQxNTMzNTlaIn0seyJYLUFtei1TZWN1cml0eS1Ub2tlbiI6IkZ3b0daWEl2WVhkekVKSC8vLy8vLy8vLy93RWFEQ2ZQSVkyM28zeVVma2RjQmlLbkJDTVJpRlYxZWMzYlFOQWVENHl2SWtNZVZCdUkzK1hnaXpKNzJPQXNlQ2ZmUkZkaElJTTlCeDgweDZNcmIwNElydGdnWU9tOEdaWm5ncEJ3VkpKd2liMDZzWFhZZEFia1c1OWoyTktqN2tFMUZzaUJzNU1HcTNsR3BPZ0tIVFdvY3IxZXQzdlVMWTRFdDJ5TEhrRTFEK3B3VzRDRXhZcVc2UjJhenZpVWhQSjJNQUNYTFIyRnZuZ1RwNVdkemtSS0hjK0FoRG51ZTQySkEwTlVnSnYrc1FUSjVnaVlZTW50ckhkQkJWOEVXSmZ1cGdERVBOdnFseXVzc1ZINVRUM3VCMmVhdFUxU3dXZ3BhVlR4eUw3cDB2NHJXUjZ6RFJSb01NbUtpNTlSOFRqSGdmUWNqRUJJdTB4bklqVUxMcW1TWUhSVmhiUWNGQm5MdEF6WmRpcDBTN2twUEltMlpEN05ham1UQmZmUCsyOEdSbXkyTmdEWDV3SjF5QnFuWGNKN1lHVzJOS3YyTU44M1d1SG9FRURyWVBZWlRuUFNJUkw0Z3cvaTRpdGNOQmkxZjU0THhPM3Rzdmx1dGlIazI0VUJoNkh5SjJwekZwWGppS1RwZno5TFc5MngwT3FZbHBYMFhxeE9zSk1wQzllNmFCbGFNUXlteGxEMkZzRm9HbSt6SjlpaHQ3S2pGT1Fac1l6RHp6ZER6TVdLOU5QRmQ1djlGSDA0bGRFUjdROVU5MEhPaDdUc1h6MWNrQW1UR0Y0UXFyRUZSanpEKzA4MG05MFlVMlAvenlKZDhYSWdJYU4rSFNzQ2xiUWZPdjM5dXdRSjh0eXVkMlRVZFpnMEtWQ0VLZlByN0lOWnlXZG9KYXlLMnNOV2Rmb0FnbGtFY0c5MHBNeDBjYVBINFZvdDlvRXBYOTNlajA0RXA2bFgyZDZTcGlveS84dTlHcXVqVXVmV2E5NHVDQWdFWENyZVRlN3NLT2V6a1pZR01pdnI0UFJBanVNYjdmbkRqR3pTQVhNcWh5OHhhN3o5SFNPbWlWaURndHY4V3pLdzFQc3hvSE10TlBFVCJ9XX0="
},
{
"key": "X-Amz-Signature",
"value": "994a3ba731d27a4606b90f4adc60b85af80ec8d2f048ffc37ebb97833c06657e"
},
{
"key": "X-Amz-Meta-X-Swan-Supporting-Document-Id",
"value": "865ed98c-64aa-4288-a51a-e2f199287ab8"
}
],
"url": "https://s3.eu-west-1.amazonaws.com/swan-supporting-document-master-sandbox"
}
}
}
}}
This provides you with an uploadUrl and the table key/value needed that you have to use to upload the document. This URL is valid for 7 days and generated on the fly.

Upload a supporting document

You then need to do an HTTP POST request on the URL without a Content-Type header. You can use this curl command to try the upload URL:
Request
curl --location --request POST '{{YOUR_URL}}' \
--form 'Key="INPUT/{{YOUR_ID}}"' \
--form 'X-Amz-Algorithm="AWS4-HMAC-SHA256"' \
--form 'X-Amz-Credential="{{YOUR_CREDENTIAL}}"' \
--form 'X-Amz-Date="20220705T135458Z"' \
--form 'X-Amz-Security-Token="{{YOUR_TOKEN}}"' \
--form 'Policy="{{YOUR_POLICY}}"' \
--form 'X-Amz-Signature="{{YOUR_SIGNATURE}}"' \
--form 'X-Amz-Meta-X-Swan-Supporting-Document-Id="{{YOUR_SUPPORTING_DOCUMENT_ID}}"' \
--form '[email protected]"{{YOUR_FILE_PATH}}"'
You can only upload if the supporting document is in WaitingForUpload.
These following document extensions are supported : .pdf, .png, .jpg
If the supporting document is not uploaded before finalizing the onboarding (i.e. supporting document status with the status ReviewPending), its status will be NotUploaded.
When you successfully upload a supporting document via the POST method, Amazon sends a "204: No content" but it was actually uploaded.

Delete a supporting document

As a partner or an end-user, a supporting document that was previously downloaded can be deleted. Usually what happens is your end customer uploaded the wrong file and wants to delete it so they can upload the right one.
The deleteSupportingDocument mutation can be called with a project access token or a user access token of the concerned user. This mutation is only possible when the document status is uploaded
Request
mutation MyMutation {
deleteSupportingDocument(input: { id: "{{DOCUMENT_ID}}" }) {
... on DeleteSupportingDocumentSuccessPayload {
id
}
}
}