/join
POST ASYNCConsolidates coins to a higher denomination.
Description
This endpoint initiates an operation to consolidate coins within a given wallet. The system automatically finds a suitable denomination and exchanges ten coins for a single coin of the next higher denomination (e.g., ten 1-CloudCoin notes become one 10-CloudCoin note). This is useful for optimizing a wallet, especially before transferring coins to a locker.
Asynchronous Operation
This is a long-running, asynchronous operation because it requires communication with the RAIDA to perform the exchange. The API responds immediately with a task ID, and the process runs in the background. You must poll the /tasks/{id}
endpoint to get the final result.
Request Body
The request must be a JSON object specifying the wallet to process.
Request Body Parameters
Parameter | Type | Required | Description |
---|---|---|---|
name |
string | Yes | The name of the wallet in which to consolidate coins. |
Example Request Body
{
"name": "Default"
}
Response
The initial response is a `200 OK` containing a `TaskResponse` object with the ID for the background job.
Initial Response from POST /join
{
"status": "success",
"payload": {
"id": "d1e2f3a4-b5c6-7890-1234-567890abcdef",
"status": "running",
"progress": 0,
"message": "Command Started",
"data": null
}
}
Final Result from Polling /tasks/{id}
After the task completes, polling the task status endpoint will show a `completed` status. On success, the `data` field will contain the string "OK".
{
"status": "success",
"payload": {
"id": "d1e2f3a4-b5c6-7890-1234-567890abcdef",
"status": "completed",
"progress": 100,
"message": "Command Completed",
"data": "OK"
}
}
Examples
JavaScript Example
const apiHost = 'http://localhost:8006';
// Function to poll the task status
async function pollTask(taskId) {
const taskResponse = await fetch(`${apiHost}/api/v1/tasks/${taskId}`);
const taskData = await taskResponse.json();
const task = taskData.payload;
console.log(`Task ${taskId} progress: ${task.progress}% - ${task.message}`);
if (task.status === 'completed') {
console.log(' Coin consolidation finished successfully:', task.data);
return true; // Stop polling
} else if (task.status === 'error') {
console.error('Task failed:', task.message);
return true; // Stop polling
}
return false; // Continue polling
}
// Main function to start the join process
async function startJoinProcess(walletName) {
try {
// Step 1: Call the /join endpoint to start consolidation
const initialResponse = await fetch(`${apiHost}/api/v1/join`, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ name: walletName })
});
if (!initialResponse.ok) {
throw new Error(`HTTP error! status: ${initialResponse.status}`);
}
const taskInfo = await initialResponse.json();
const taskId = taskInfo.payload.id;
console.log(`Consolidation task created with ID: ${taskId}`);
// Step 2: Poll for the result
const pollInterval = setInterval(async () => {
const isDone = await pollTask(taskId);
if (isDone) {
clearInterval(pollInterval);
}
}, 3000); // Check every 3 seconds
} catch (error) {
console.error('Error initiating join task:', error);
}
}
// Start the process for the "Default" wallet
startJoinProcess('Default');
cURL Example
# Step 1: Initiate the join task
TASK_ID=$(curl -s -X POST "http://localhost:8006/api/v1/join" \
-H "Content-Type: application/json" \
-d '{"name":"Default"}' | jq -r '.payload.id')
echo "Join task started with ID: $TASK_ID"
# Step 2: Poll the task endpoint until finished
while true; do
RESPONSE=$(curl -s "http://localhost:8006/api/v1/tasks/$TASK_ID")
STATUS=$(echo $RESPONSE | jq -r '.payload.status')
echo "Polling task.. Status: $STATUS"
if [[ "$STATUS" == "completed" ]] || [[ "$STATUS" == "error" ]]; then
echo "Final Response:"
echo $RESPONSE | jq
break
fi
sleep 2
done
Go Example
package main
import (
"bytes"
"encoding/json"
"fmt"
"net/http"
"time"
)
type Task struct {
ID string `json:"id"`
Status string `json:"status"`
Progress int `json:"progress"`
Message string `json:"message"`
Data interface{} `json:"data"`
}
type TaskResponse struct {
Status string `json:"status"`
Payload Task `json:"payload"`
}
// startJoinProcess initiates the coin consolidation operation.
func startJoinProcess(walletName string) (string, error) {
apiHost := "http://localhost:8006"
payload, _ := json.Marshal(map[string]string{"name": walletName})
resp, err := http.Post(fmt.Sprintf("%s/api/v1/join", apiHost), "application/json", bytes.NewBuffer(payload))
if err != nil {
return "", err
}
defer resp.Body.Close()
var taskResp TaskResponse
if err := json.NewDecoder(resp.Body).Decode(&taskResp); err != nil {
return "", err
}
if taskResp.Status != "success" {
return "", fmt.Errorf("API error: %s", taskResp.Payload.Message)
}
fmt.Printf("Coin consolidation task started with ID: %s\n", taskResp.Payload.ID)
return taskResp.Payload.ID, nil
}
// pollTaskStatus checks the status of a task until it completes or fails.
func pollTaskStatus(taskId string) {
apiHost := "http://localhost:8006"
for {
resp, err := http.Get(fmt.Sprintf("%s/api/v1/tasks/%s", apiHost, taskId))
if err != nil {
fmt.Printf("Error polling task: %v\n", err)
return
}
var taskResp TaskResponse
json.NewDecoder(resp.Body).Decode(&taskResp)
resp.Body.Close()
fmt.Printf("Polling... Status: %s, Progress: %d%%\n", taskResp.Payload.Status, taskResp.Payload.Progress)
if taskResp.Payload.Status == "completed" {
fmt.Printf("Task completed successfully. Result: %v\n", taskResp.Payload.Data)
return
} else if taskResp.Payload.Status == "error" {
fmt.Printf("Task failed: %s\n", taskResp.Payload.Message)
return
}
time.Sleep(3 * time.Second)
}
}
func main() {
// Step 1: Start the join process
taskId, err := startJoinProcess("Default")
if err != nil {
panic(err)
}
// Step 2: Poll for the result
if taskId != "" {
pollTaskStatus(taskId)
}
}