Smart contracts in plain JavaScript.
No Solidity. No Rust. No new language to learn. Write contracts in JavaScript, test them in your browser, deploy to a chain with 5-second blocks and post-quantum signatures from block zero.
It looks like the code you already write.
// A subscription that fires itself.
// Customer signs once. Cron does the rest.
function subscribe(amountPerWeek) {
storage.set('sub:' + msg.sender, {
amount: amountPerWeek,
nextCharge: chain.timestamp + 7 * 86400,
});
cron.schedule(this.address, 'chargeAll', '@daily');
emit('Subscribed', { user: msg.sender, amount: amountPerWeek });
}
// Auto-called every day by the chain itself.
function chargeAll() {
for (const [addr, sub] of storage.entries('sub:')) {
if (chain.timestamp >= sub.nextCharge) {
E(AEV).transferFrom(addr, storage.merchant, sub.amount);
sub.nextCharge += 7 * 86400;
}
}
}
Deployed as plain source. Readable on-chain. Verifiable in a single hash compare. Reentrancy structurally impossible.
Write
Write your contract in JavaScript. Use storage, emit, msg, assert — familiar globals injected by the VM. ES module syntax. No compiler, no ABI generation, no build step.
Test
Test it live in your browser. The contract playground at testnet.aevumlabs.dev/playground lets you write, deploy, and interact with contracts without installing anything.
Deploy
Deploy to testnet in seconds. One click from the playground, or use the SDK and CLI. Your contract is live within a 5-second block, post-quantum signed from the first block.
The same contract. In both languages.
A weekly subscription that charges itself.
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;
import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
import "@chainlink/contracts/src/v0.8/AutomationCompatible.sol";
contract Subscriptions is AutomationCompatibleInterface {
IERC20 public immutable token;
address public immutable merchant;
struct Sub { uint256 amount; uint256 nextCharge; }
mapping(address => Sub) public subs;
address[] public subscribers;
mapping(address => bool) private known;
event Subscribed(address indexed user, uint256 amount);
event Charged(address indexed user, uint256 amount);
constructor(IERC20 _token, address _merchant) {
token = _token; merchant = _merchant;
}
function subscribe(uint256 amountPerWeek) external {
subs[msg.sender] = Sub(amountPerWeek, block.timestamp + 7 days);
if (!known[msg.sender]) {
known[msg.sender] = true;
subscribers.push(msg.sender);
}
emit Subscribed(msg.sender, amountPerWeek);
}
function checkUpkeep(bytes calldata) external view
returns (bool upkeepNeeded, bytes memory)
{
for (uint i = 0; i < subscribers.length; i++) {
if (block.timestamp >= subs[subscribers[i]].nextCharge)
return (true, "");
}
return (false, "");
}
function performUpkeep(bytes calldata) external {
for (uint i = 0; i < subscribers.length; i++) {
address u = subscribers[i];
Sub storage s = subs[u];
if (block.timestamp >= s.nextCharge) {
token.transferFrom(u, merchant, s.amount);
s.nextCharge += 7 days;
emit Charged(u, s.amount);
}
}
}
}
// + register with Chainlink Automation (fund LINK)
// A subscription that fires itself.
// Customer signs once. Cron does the rest.
function subscribe(amountPerWeek) {
storage.set('sub:' + msg.sender, {
amount: amountPerWeek,
nextCharge: chain.timestamp + 7 * 86400,
});
cron.schedule(this.address, 'chargeAll', '@daily');
emit('Subscribed', { user: msg.sender, amount: amountPerWeek });
}
// Auto-called every day by the chain itself.
function chargeAll() {
for (const [addr, sub] of storage.entries('sub:')) {
if (chain.timestamp >= sub.nextCharge) {
E(AEV).transferFrom(addr, storage.merchant, sub.amount);
sub.nextCharge += 7 * 86400;
}
}
}
vs. registering with Chainlink Automation and keeping it funded with LINK just to make time pass on-chain.
vs. hand-maintaining a parallel array of subscriber addresses just so you have something to loop over.
No constructor, no ABI to generate, no compiler in the loop. What you deploy is what you wrote.
Everything you need. Nothing you don't.
Contract Playground
In-browser IDE with templates, deploy, and interact — no install.
@aevumlabs/sdk
AevumClient, AevumWallet, AevumContract. ~14 KB. Node + browser. On npm.
@aevumlabs/pay
Stripe-shaped payments SDK. Charges, customers, checkout sessions, webhooks.
AEV-20 + AEV-21
Fungible token + scheduled-execution standards. The vocabulary the ecosystem speaks.
JSON-RPC API
Ethereum-compatible. Works with ethers.js, viem, and existing Web3 tools.
Block Explorer
Browse blocks, transactions, contract source, validator activity, faucet.
What your contract has access to.
Contracts run inside SES (Secure ECMAScript) — a hardened JavaScript sandbox. No filesystem, no network, no eval. These are the globals the VM injects:
storagePersistent key-value store
emitNamed events with data
msgTransaction context
chainBlock context
cronSchedule future calls
E(addr)Cross-contract calls
transferSend AEV tokens
assertRevert with message
Learning resources
Build a token in 10 minutes
Step-by-step: write a token contract, deploy it, transfer tokens, query balances.
Token tutorial →Hardened JavaScript, explained
How SES protects contracts from prototype pollution, eval injection, and supply-chain attacks.
Read the guide →Network parameters
Chain ID, block time, gas limits, contract size limits, and every protocol constant.
Parameters →Build for these
Six categories of dapp you couldn't cleanly build elsewhere. Each one has a working demo and a use-case page with the architecture, the code shape, and the primitives.
Revenue splits
That auto-distribute.
02 · AI AGENTSAutonomous agents
That schedule themselves on-chain.
03 · SUBSCRIPTIONSRecurring billing
Stripe Recurring, settled in one block.
04 · PAYROLLScheduled payouts
Monthly payday, fired by the protocol.
05 · TREASURYDCA + rebalance
Scheduled buys, rebalance, sweep — on autopilot.
06 · SOCIALProfiles + posts
On-chain profiles, posts, comments, likes.