npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

wlj-cloud-api

v1.0.1

Published

Node.js SDK for WLJ Cloud Reseller API - Manage VPS servers, orders, and VM operations programmatically

Readme

WLJ Cloud API - Node.js SDK

npm version License: MIT

Official Node.js SDK for WLJ Cloud Reseller API. Manage VPS servers, orders, and VM operations programmatically with full async/await support.

Features

Complete API Coverage - All endpoints implemented
Async/Await - Full promise-based API
Auto Retry - Built-in retry logic for failed requests
Rate Limiting - Automatic rate limit handling
Webhook Verification - Helper utilities for webhook signatures
Clean & Simple - Easy to use, well-documented API
TypeScript Ready - JSDoc comments for better IDE support

Installation

npm install wlj-cloud-api

Quick Start

const WLJCloud = require('wlj-cloud-api');

// Initialize client
const client = new WLJCloud({
  apiKey: 'wlj_live_your_api_key_here'
});

// Get account info
const account = await client.account.getInfo();
console.log(`Balance: Rp ${account.data.balance}`);

// List available packages
const packages = await client.packages.list({ type: 'linux' });
console.log('Available packages:', packages.data);

// Create a new VPS order
const order = await client.orders.create({
  vm_name: 'my-server',
  serverid: 'jakarta-1',
  osid: '3cd7fdd4-802c-4af6-8efd-a8935d4a031f',
  package_id: 'f1117f8f-85c3-49f7-8aa0-3b9b531788d0',
  billing_cycle: 'monthly'
});
console.log('Order created:', order.data.orderid);

Configuration

const client = new WLJCloud({
  apiKey: 'wlj_live_your_api_key_here',  // Required
  baseURL: 'https://api.wlj-cloud.id/api/v1',  // Optional
  timeout: 30000,        // Optional, request timeout in ms (default: 30000)
  maxRetries: 3,         // Optional, max retry attempts (default: 3)
  retryDelay: 1000       // Optional, initial retry delay in ms (default: 1000)
});

API Reference

Account

// Get account information
const info = await client.account.getInfo();

// Get transaction history
const transactions = await client.account.getTransactions({
  limit: 20,
  offset: 0,
  type: 'order'  // order, renewal, deposit, refund
});

Servers

// List all servers
const servers = await client.servers.list();

// Get OS templates for a server
const templates = await client.servers.getOSTemplates('jakarta-1');

Packages

// List all packages
const packages = await client.packages.list({
  serverid: 'jakarta-1',  // Optional filter
  type: 'linux'           // Optional: linux or windows
});

// Get package details
const pkg = await client.packages.get('package-uuid');

Orders

// Create new order
const order = await client.orders.create({
  vm_name: 'my-vps-server',
  serverid: 'jakarta-1',
  osid: 'os-template-uuid',
  package_id: 'package-uuid',
  billing_cycle: 'monthly'  // daily, weekly, or monthly
});

// List orders
const orders = await client.orders.list({
  limit: 10,
  offset: 0,
  status: 'active'  // pending, active, suspended, expired, cancelled
});

// Get order details
const orderDetails = await client.orders.get('order-uuid');
console.log('VM IP:', orderDetails.data.ipvm);
console.log('Password:', orderDetails.data.passwordvm);

// Extend/renew order
const renewed = await client.orders.extend('order-uuid', {
  billing_cycle: 'monthly'
});

// Reinstall VM with new OS
const job = await client.orders.reinstall('order-uuid', {
  osid: 'new-os-template-uuid'
});
console.log('Reinstall job:', job.data.jobId);

VM Power Control

// Start VM
await client.vmPower.start('order-uuid');

// Stop VM (force stop)
await client.vmPower.stop('order-uuid');

// Graceful shutdown
await client.vmPower.shutdown('order-uuid');

// Restart VM
await client.vmPower.restart('order-uuid');

Port Forwarding (NAT VMs)

// Add port forwarding
const portForward = await client.portForwarding.create({
  orderid: 'order-uuid',
  public_port: 50062,
  private_port: 80,
  protocol: 'tcp',  // tcp or udp
  description: 'Web Server'
});

// List port forwards
const rules = await client.portForwarding.list('order-uuid');

// Update port forwarding
await client.portForwarding.update(portForwardId, {
  private_port: 8080,
  description: 'Updated description'
});

Job Status Tracking

// Get job status
const job = await client.jobs.get('job-uuid');
console.log('Status:', job.data.status); // pending, processing, completed, failed

// Wait for job completion
const completed = await client.jobs.waitForCompletion('job-uuid', {
  interval: 3000,   // Poll every 3 seconds
  timeout: 600000   // Timeout after 10 minutes
});

if (completed.data.status === 'completed') {
  console.log('Job finished successfully!');
}

VNC Console Access

// HTTP method - direct browser access
const ticket = await client.console.createTicket({
  orderid: 'order-uuid',
  method: 'http'
});
console.log('Console URL:', ticket.data.http_url);

// WebSocket method - for custom integration (noVNC)
const wsTicket = await client.console.createTicket({
  orderid: 'order-uuid',
  method: 'websocket'
});
console.log('WebSocket URL:', wsTicket.data.websocket_url);

Webhook Verification

Verify webhook signatures to ensure they came from WLJ Cloud:

const { WebhookHelper } = require('wlj-cloud-api');

// Manual verification
const isValid = WebhookHelper.verifySignature(
  'your-api-key',
  req.headers['x-webhook-signature'],
  req.body
);

// Complete verification (signature + timestamp)
const verification = WebhookHelper.verify({
  apiKey: 'your-api-key',
  signature: req.headers['x-webhook-signature'],
  timestamp: req.headers['x-webhook-timestamp'],
  payload: req.body,
  maxAge: 300  // 5 minutes
});

if (verification.valid) {
  // Process webhook
  const { event_type, data } = req.body;
  console.log('Event:', event_type);
}

// Express middleware
const express = require('express');
const app = express();

app.post('/webhook',
  express.json(),
  WebhookHelper.middleware('your-api-key'),
  (req, res) => {
    // Webhook is verified, process it
    const { event_type, data } = req.body;
    console.log('Webhook event:', event_type);
    res.json({ received: true });
  }
);

Error Handling

const { errors } = require('wlj-cloud-api');

try {
  await client.orders.create({ /* ... */ });
} catch (error) {
  if (error instanceof errors.AuthenticationError) {
    console.error('Invalid API key');
  } else if (error instanceof errors.InsufficientBalanceError) {
    console.error('Not enough balance');
  } else if (error instanceof errors.RateLimitError) {
    console.error('Rate limit exceeded, retry after:', error.retryAfter);
  } else if (error instanceof errors.ValidationError) {
    console.error('Invalid parameters:', error.message);
  } else {
    console.error('Error:', error.message);
  }
}

Rate Limiting

The SDK automatically handles rate limiting with exponential backoff. Rate limit information is available in responses:

const info = await client.account.getInfo();
console.log('Rate limit:', info._rateLimit);
// {
//   limit: '2000',
//   remaining: '1999',
//   reset: '900',
//   policy: '2000;w=900'
// }

Advanced Examples

Complete Order Flow

async function createAndConfigureVPS() {
  // 1. Check balance
  const account = await client.account.getInfo();
  console.log('Balance:', account.data.balance);

  // 2. List available packages
  const packages = await client.packages.list({ type: 'linux' });
  const selectedPackage = packages.data[0];

  // 3. Get OS templates
  const templates = await client.servers.getOSTemplates(selectedPackage.serverid);
  const ubuntuOS = templates.data.find(os => os.os_name === 'Ubuntu');

  // 4. Create order
  const order = await client.orders.create({
    vm_name: 'production-web-server',
    serverid: selectedPackage.serverid,
    osid: ubuntuOS.osid,
    package_id: selectedPackage.package_id,
    billing_cycle: 'monthly'
  });

  console.log('Order created:', order.data.orderid);

  // 5. Wait for VM to be ready (webhook recommended for production)
  // In production, use webhooks instead of polling
  await new Promise(resolve => setTimeout(resolve, 60000)); // Wait 1 minute

  // 6. Get VM details
  const vmDetails = await client.orders.get(order.data.orderid);
  console.log('VM IP:', vmDetails.data.ipvm);
  console.log('VM Password:', vmDetails.data.passwordvm);

  return vmDetails;
}

Webhook Handler (Express)

const express = require('express');
const WLJCloud = require('wlj-cloud-api');

const app = express();
const client = new WLJCloud({ apiKey: process.env.WLJ_API_KEY });

app.post('/webhook',
  express.json(),
  WLJCloud.WebhookHelper.middleware(process.env.WLJ_API_KEY),
  async (req, res) => {
    // Respond quickly
    res.json({ received: true });

    // Process webhook asynchronously
    const { event_type, data } = req.body;

    try {
      switch (event_type) {
        case 'vm_created':
          console.log('VM created:', data.order_id);
          console.log('IP:', data.ip_address);
          console.log('Password:', data.password);
          // Send email to customer, update database, etc.
          break;

        case 'vm_suspended':
          console.log('VM suspended:', data.order_id);
          // Notify customer
          break;

        case 'package_stock_updated':
          console.log('Package stock updated:', data.package_name);
          console.log('New stock:', data.new_stock);
          // Update your website's package availability
          break;

        default:
          console.log('Unhandled event:', event_type);
      }
    } catch (error) {
      console.error('Webhook processing error:', error);
    }
  }
);

app.listen(3000, () => {
  console.log('Webhook server listening on port 3000');
});

API Limits

| Endpoint Type | Limit | Window | |--------------|-------|--------| | General (Account, Orders, etc) | 2000 requests | 15 minutes | | Packages | 500 requests | 15 minutes | | Create Order | 100 requests | 1 hour |

The SDK automatically handles rate limiting and retries requests when necessary.

Requirements

  • Node.js >= 14.0.0
  • Valid WLJ Cloud API key

Getting Your API Key

  1. Login to WLJ Cloud Dashboard
  2. Navigate to Profile/Settings
  3. Generate a new API key in the "API Access" section
  4. Save your API key securely

Support

License

MIT License - see LICENSE file for details

Contributing

Contributions are welcome! Please feel free to submit a Pull Request.


Made with ❤️ for WLJ Cloud resellers