@worldcoin/minikit-js
Version:
minikit-js is our SDK for building mini-apps.
1,435 lines (1,402 loc) • 48.9 kB
JavaScript
import {
generateSiweMessage
} from "./chunk-YPZEODWL.js";
import {
COMMAND_VERSIONS,
CommandUnavailableError,
executeWithFallback,
getFallbackAdapter,
isCommandAvailable,
sendMiniKitEvent
} from "./chunk-DZ2YRSIU.js";
// src/commands/attestation/types.ts
var AttestationErrorCodes = /* @__PURE__ */ ((AttestationErrorCodes2) => {
AttestationErrorCodes2["Unauthorized"] = "unauthorized";
AttestationErrorCodes2["AttestationFailed"] = "attestation_failed";
AttestationErrorCodes2["IntegrityFailed"] = "integrity_failed";
AttestationErrorCodes2["InvalidInput"] = "invalid_input";
AttestationErrorCodes2["UnsupportedVersion"] = "unsupported_version";
return AttestationErrorCodes2;
})(AttestationErrorCodes || {});
var AttestationError = class extends Error {
constructor(error_code) {
super(`Attestation failed: ${error_code}`);
this.error_code = error_code;
this.name = "AttestationError";
}
};
// src/events.ts
var EventManager = class {
constructor() {
this.listeners = {
["miniapp-attestation" /* MiniAppAttestation */]: () => {
},
["miniapp-payment" /* MiniAppPayment */]: () => {
},
["miniapp-wallet-auth" /* MiniAppWalletAuth */]: () => {
},
["miniapp-send-transaction" /* MiniAppSendTransaction */]: () => {
},
["miniapp-sign-message" /* MiniAppSignMessage */]: () => {
},
["miniapp-sign-typed-data" /* MiniAppSignTypedData */]: () => {
},
["miniapp-share-contacts" /* MiniAppShareContacts */]: () => {
},
["miniapp-request-permission" /* MiniAppRequestPermission */]: () => {
},
["miniapp-get-permissions" /* MiniAppGetPermissions */]: () => {
},
["miniapp-send-haptic-feedback" /* MiniAppSendHapticFeedback */]: () => {
},
["miniapp-share" /* MiniAppShare */]: () => {
},
["miniapp-microphone" /* MiniAppMicrophone */]: () => {
},
["miniapp-chat" /* MiniAppChat */]: () => {
}
};
}
subscribe(event, handler) {
this.listeners[event] = handler;
}
unsubscribe(event) {
delete this.listeners[event];
}
trigger(event, payload) {
if (!this.listeners[event]) {
console.error(
`No handler for event ${event}, payload: ${JSON.stringify(payload)}`
);
return;
}
this.listeners[event](payload);
}
};
// src/commands/attestation/index.ts
async function attestation(options, ctx) {
const result = await executeWithFallback({
command: "attestation" /* Attestation */,
nativeExecutor: () => nativeAttestation(options, ctx),
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeAttestation(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("attestation" /* Attestation */)) {
throw new Error(
"'attestation' command is unavailable. Check MiniKit.install() or update the app version"
);
}
if (!options.requestHash || options.requestHash.length === 0) {
throw new Error("'attestation' command requires a non-empty requestHash");
}
const payload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-attestation" /* MiniAppAttestation */, (response) => {
ctx.events.unsubscribe("miniapp-attestation" /* MiniAppAttestation */);
resolve(response);
});
sendMiniKitEvent({
command: "attestation" /* Attestation */,
version: COMMAND_VERSIONS["attestation" /* Attestation */],
payload: {
request_hash: options.requestHash
}
});
} catch (error) {
reject(error);
}
}
);
if (payload.status === "error") {
throw new AttestationError(payload.error_code);
}
return payload;
}
// src/commands/chat/types.ts
var ChatErrorCodes = /* @__PURE__ */ ((ChatErrorCodes2) => {
ChatErrorCodes2["UserRejected"] = "user_rejected";
ChatErrorCodes2["SendFailed"] = "send_failed";
ChatErrorCodes2["GenericError"] = "generic_error";
return ChatErrorCodes2;
})(ChatErrorCodes || {});
var ChatError = class extends Error {
constructor(error_code) {
super(`Chat failed: ${error_code}`);
this.error_code = error_code;
this.name = "ChatError";
}
};
// src/commands/chat/index.ts
async function chat(options, ctx) {
const result = await executeWithFallback({
command: "chat" /* Chat */,
nativeExecutor: () => nativeChat(options, ctx),
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeChat(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("chat" /* Chat */)) {
throw new Error(
"'chat' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payloadInput = {
message: options.message,
to: options.to
};
if (payloadInput.message.length === 0) {
throw new Error("'chat' command requires a non-empty message");
}
const payload = await new Promise((resolve, reject) => {
try {
ctx.events.subscribe("miniapp-chat" /* MiniAppChat */, (response) => {
ctx.events.unsubscribe("miniapp-chat" /* MiniAppChat */);
resolve(response);
});
sendMiniKitEvent({
command: "chat" /* Chat */,
version: COMMAND_VERSIONS["chat" /* Chat */],
payload: payloadInput
});
} catch (error) {
reject(error);
}
});
if (payload.status === "error") {
throw new ChatError(payload.error_code);
}
return payload;
}
// src/commands/close-miniapp/index.ts
async function closeMiniApp(options = {}, _ctx) {
const result = await executeWithFallback({
command: "close-miniapp" /* CloseMiniApp */,
nativeExecutor: () => nativeCloseMiniApp(),
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeCloseMiniApp() {
if (typeof window === "undefined" || !isCommandAvailable("close-miniapp" /* CloseMiniApp */)) {
throw new Error(
"'closeMiniApp' command is unavailable. Check MiniKit.install() or update the app version"
);
}
sendMiniKitEvent({
command: "close-miniapp" /* CloseMiniApp */,
version: COMMAND_VERSIONS["close-miniapp" /* CloseMiniApp */],
payload: {}
});
return {
status: "success",
version: COMMAND_VERSIONS["close-miniapp" /* CloseMiniApp */]
};
}
// src/commands/get-permissions/types.ts
var GetPermissionsErrorCodes = /* @__PURE__ */ ((GetPermissionsErrorCodes2) => {
GetPermissionsErrorCodes2["GenericError"] = "generic_error";
return GetPermissionsErrorCodes2;
})(GetPermissionsErrorCodes || {});
var Permission = /* @__PURE__ */ ((Permission2) => {
Permission2["Notifications"] = "notifications";
Permission2["Contacts"] = "contacts";
Permission2["Microphone"] = "microphone";
return Permission2;
})(Permission || {});
var GetPermissionsError = class extends Error {
constructor(error_code) {
super(`Get permissions failed: ${error_code}`);
this.error_code = error_code;
this.name = "GetPermissionsError";
}
};
// src/commands/get-permissions/index.ts
async function getPermissions(options, ctx) {
const resolvedOptions = options ?? {};
const result = await executeWithFallback({
command: "get-permissions" /* GetPermissions */,
nativeExecutor: () => nativeGetPermissions(ctx),
customFallback: resolvedOptions.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeGetPermissions(ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("get-permissions" /* GetPermissions */)) {
throw new Error(
"'getPermissions' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-get-permissions" /* MiniAppGetPermissions */, (response) => {
ctx.events.unsubscribe("miniapp-get-permissions" /* MiniAppGetPermissions */);
resolve(response);
});
sendMiniKitEvent({
command: "get-permissions" /* GetPermissions */,
version: COMMAND_VERSIONS["get-permissions" /* GetPermissions */],
payload: {}
});
} catch (error) {
reject(error);
}
}
);
if (payload.status === "error") {
throw new GetPermissionsError(payload.error_code);
}
return payload;
}
// src/commands/pay/types.ts
var Tokens = /* @__PURE__ */ ((Tokens2) => {
Tokens2["USDC"] = "USDCE";
Tokens2["WLD"] = "WLD";
Tokens2["WARS"] = "WARS";
Tokens2["WCOP"] = "WCOP";
Tokens2["WMXN"] = "WMXN";
Tokens2["WBRL"] = "WBRL";
Tokens2["WPEN"] = "WPEN";
Tokens2["WCLP"] = "WCLP";
Tokens2["EURC"] = "EURC";
return Tokens2;
})(Tokens || {});
var TokenDecimals = {
["USDCE" /* USDC */]: 6,
["WLD" /* WLD */]: 18,
["WARS" /* WARS */]: 18,
["WCOP" /* WCOP */]: 18,
["WMXN" /* WMXN */]: 18,
["WBRL" /* WBRL */]: 18,
["WPEN" /* WPEN */]: 18,
["WCLP" /* WCLP */]: 18,
["EURC" /* EURC */]: 6
};
var Network = /* @__PURE__ */ ((Network2) => {
Network2["WorldChain"] = "worldchain";
return Network2;
})(Network || {});
var PaymentErrorCodes = /* @__PURE__ */ ((PaymentErrorCodes2) => {
PaymentErrorCodes2["InputError"] = "input_error";
PaymentErrorCodes2["UserRejected"] = "user_rejected";
PaymentErrorCodes2["PaymentRejected"] = "payment_rejected";
PaymentErrorCodes2["InvalidReceiver"] = "invalid_receiver";
PaymentErrorCodes2["InsufficientBalance"] = "insufficient_balance";
PaymentErrorCodes2["TransactionFailed"] = "transaction_failed";
PaymentErrorCodes2["GenericError"] = "generic_error";
PaymentErrorCodes2["UserBlocked"] = "user_blocked";
return PaymentErrorCodes2;
})(PaymentErrorCodes || {});
var PaymentErrorMessage = {
["input_error" /* InputError */]: "There was a problem with this request. Please try again or contact the app owner.",
["user_rejected" /* UserRejected */]: "You have cancelled the payment in World App.",
["payment_rejected" /* PaymentRejected */]: "You've cancelled the payment in World App.",
["invalid_receiver" /* InvalidReceiver */]: "The receiver address is invalid. Please contact the app owner.",
["insufficient_balance" /* InsufficientBalance */]: "You do not have enough balance to complete this transaction.",
["transaction_failed" /* TransactionFailed */]: "The transaction failed. Please try again.",
["generic_error" /* GenericError */]: "Something unexpected went wrong. Please try again.",
["user_blocked" /* UserBlocked */]: "User's region is blocked from making payments."
};
var PayError = class extends Error {
constructor(code) {
super(`Payment failed: ${code}`);
this.name = "PayError";
this.code = code;
}
};
// src/commands/pay/validate.ts
var tokenToDecimals = (amount, token) => {
const decimals = TokenDecimals[token];
if (decimals === void 0) {
throw new Error(`Invalid token: ${token}`);
}
const factor = 10 ** decimals;
const result = amount * factor;
if (!Number.isInteger(result)) {
throw new Error(`The resulting amount is not a whole number: ${result}`);
}
return result;
};
var validatePaymentPayload = (payload) => {
if (payload.tokens.some(
(token) => token.symbol == "USDCE" /* USDC */ && parseFloat(token.token_amount) < 0.1
)) {
console.error("USDC amount should be greater than $0.1");
return false;
}
if (payload.reference.length > 36) {
console.error("Reference must not exceed 36 characters");
return false;
}
if (typeof payload.reference !== "string") {
throw new Error("Reference must be a string");
}
return true;
};
// src/commands/pay/index.ts
async function pay(options, ctx) {
const result = await executeWithFallback({
command: "pay" /* Pay */,
nativeExecutor: () => nativePay(options, ctx),
// No Wagmi fallback - pay is native only
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return { executedWith: "minikit", data: result.data };
}
async function nativePay(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("pay" /* Pay */)) {
throw new Error(
"'pay' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const input = {
reference: options.reference,
to: options.to,
tokens: options.tokens,
description: options.description,
network: options.network
};
if (!validatePaymentPayload(input)) {
throw new Error("Invalid payment payload");
}
const eventPayload = {
...input,
network: "worldchain" /* WorldChain */
};
const finalPayload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-payment" /* MiniAppPayment */, (response) => {
ctx.events.unsubscribe("miniapp-payment" /* MiniAppPayment */);
resolve(response);
});
sendMiniKitEvent({
command: "pay" /* Pay */,
version: COMMAND_VERSIONS["pay" /* Pay */],
payload: eventPayload
});
} catch (error) {
reject(error);
}
}
);
if (finalPayload.status === "error") {
throw new PayError(finalPayload.error_code);
}
return {
transactionId: finalPayload.transaction_id,
reference: finalPayload.reference,
from: finalPayload.from,
chain: finalPayload.chain,
timestamp: finalPayload.timestamp
};
}
// src/commands/request-permission/types.ts
var RequestPermissionErrorCodes = /* @__PURE__ */ ((RequestPermissionErrorCodes2) => {
RequestPermissionErrorCodes2["UserRejected"] = "user_rejected";
RequestPermissionErrorCodes2["GenericError"] = "generic_error";
RequestPermissionErrorCodes2["AlreadyRequested"] = "already_requested";
RequestPermissionErrorCodes2["PermissionDisabled"] = "permission_disabled";
RequestPermissionErrorCodes2["AlreadyGranted"] = "already_granted";
RequestPermissionErrorCodes2["UnsupportedPermission"] = "unsupported_permission";
return RequestPermissionErrorCodes2;
})(RequestPermissionErrorCodes || {});
var RequestPermissionError = class extends Error {
constructor(error_code) {
super(`Request permission failed: ${error_code}`);
this.error_code = error_code;
this.name = "RequestPermissionError";
}
};
// src/commands/request-permission/index.ts
async function requestPermission(options, ctx) {
const result = await executeWithFallback({
command: "request-permission" /* RequestPermission */,
nativeExecutor: () => nativeRequestPermission(options, ctx),
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeRequestPermission(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("request-permission" /* RequestPermission */)) {
throw new Error(
"'requestPermission' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-request-permission" /* MiniAppRequestPermission */, (response) => {
ctx.events.unsubscribe("miniapp-request-permission" /* MiniAppRequestPermission */);
resolve(response);
});
sendMiniKitEvent({
command: "request-permission" /* RequestPermission */,
version: COMMAND_VERSIONS["request-permission" /* RequestPermission */],
payload: { permission: options.permission }
});
} catch (error) {
reject(error);
}
}
);
if (payload.status === "error") {
throw new RequestPermissionError(payload.error_code);
}
return payload;
}
// src/commands/send-haptic-feedback/types.ts
var SendHapticFeedbackErrorCodes = /* @__PURE__ */ ((SendHapticFeedbackErrorCodes2) => {
SendHapticFeedbackErrorCodes2["GenericError"] = "generic_error";
SendHapticFeedbackErrorCodes2["UserRejected"] = "user_rejected";
return SendHapticFeedbackErrorCodes2;
})(SendHapticFeedbackErrorCodes || {});
var SendHapticFeedbackError = class extends Error {
constructor(error_code) {
super(`Send haptic feedback failed: ${error_code}`);
this.error_code = error_code;
this.name = "SendHapticFeedbackError";
}
};
// src/commands/send-haptic-feedback/index.ts
async function sendHapticFeedback(options, ctx) {
const result = await executeWithFallback({
command: "send-haptic-feedback" /* SendHapticFeedback */,
nativeExecutor: () => nativeSendHapticFeedback(options, ctx),
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeSendHapticFeedback(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("send-haptic-feedback" /* SendHapticFeedback */)) {
throw new Error(
"'sendHapticFeedback' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payloadInput = options.hapticsType === "selection-changed" ? { hapticsType: "selection-changed" } : options.hapticsType === "impact" ? {
hapticsType: "impact",
style: options.style
} : {
hapticsType: "notification",
style: options.style
};
const payload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-send-haptic-feedback" /* MiniAppSendHapticFeedback */, (response) => {
ctx.events.unsubscribe("miniapp-send-haptic-feedback" /* MiniAppSendHapticFeedback */);
resolve(response);
});
sendMiniKitEvent({
command: "send-haptic-feedback" /* SendHapticFeedback */,
version: COMMAND_VERSIONS["send-haptic-feedback" /* SendHapticFeedback */],
payload: payloadInput
});
} catch (error) {
reject(error);
}
}
);
if (payload.status === "error") {
throw new SendHapticFeedbackError(payload.error_code);
}
return payload;
}
// src/commands/send-transaction/types.ts
var SendTransactionErrorCodes = /* @__PURE__ */ ((SendTransactionErrorCodes2) => {
SendTransactionErrorCodes2["InvalidOperation"] = "invalid_operation";
SendTransactionErrorCodes2["UserRejected"] = "user_rejected";
SendTransactionErrorCodes2["InputError"] = "input_error";
SendTransactionErrorCodes2["SimulationFailed"] = "simulation_failed";
SendTransactionErrorCodes2["TransactionFailed"] = "transaction_failed";
SendTransactionErrorCodes2["GenericError"] = "generic_error";
SendTransactionErrorCodes2["DisallowedOperation"] = "disallowed_operation";
SendTransactionErrorCodes2["ValidationError"] = "validation_error";
SendTransactionErrorCodes2["InvalidContract"] = "invalid_contract";
SendTransactionErrorCodes2["MaliciousOperation"] = "malicious_operation";
SendTransactionErrorCodes2["DailyTxLimitReached"] = "daily_tx_limit_reached";
SendTransactionErrorCodes2["PermittedAmountExceedsSlippage"] = "permitted_amount_exceeds_slippage";
SendTransactionErrorCodes2["PermittedAmountNotFound"] = "permitted_amount_not_found";
return SendTransactionErrorCodes2;
})(SendTransactionErrorCodes || {});
var SendTransactionErrorMessage = {
["invalid_operation" /* InvalidOperation */]: "Transaction included an operation that was invalid",
["user_rejected" /* UserRejected */]: "User rejected the request.",
["input_error" /* InputError */]: "Invalid payload.",
["simulation_failed" /* SimulationFailed */]: "The transaction simulation failed.",
["validation_error" /* ValidationError */]: "The transaction validation failed. Please try again.",
["transaction_failed" /* TransactionFailed */]: "The transaction failed. Please try again later.",
["generic_error" /* GenericError */]: "Something unexpected went wrong. Please try again.",
["disallowed_operation" /* DisallowedOperation */]: "The operation requested is not allowed. Please refer to the docs.",
["invalid_contract" /* InvalidContract */]: "The contract address is not allowed for your application. Please check your developer portal configurations",
["malicious_operation" /* MaliciousOperation */]: "The operation requested is considered malicious.",
["daily_tx_limit_reached" /* DailyTxLimitReached */]: "Daily transaction limit reached. Max 100 transactions per day. Wait until the next day.",
["permitted_amount_exceeds_slippage" /* PermittedAmountExceedsSlippage */]: "Permitted amount exceeds slippage. You must spend at least 90% of the permitted amount.",
["permitted_amount_not_found" /* PermittedAmountNotFound */]: "Permitted amount not found in permit2 payload."
};
var WORLD_APP_FEATURES = {
batch: true,
permit2: true,
gasSponsorship: true
};
var WEB_FEATURES = {
batch: false,
permit2: false,
gasSponsorship: false
};
var SendTransactionError = class extends Error {
constructor(code, details) {
super(`Transaction failed: ${code}`);
this.name = "SendTransactionError";
this.code = code;
this.details = details;
}
};
// src/commands/send-transaction/validate.ts
var isValidHex = (str) => {
return /^0x[0-9A-Fa-f]+$/.test(str);
};
var processPayload = (payload) => {
if (typeof payload === "boolean" || typeof payload === "string" || payload === null || payload === void 0) {
return payload;
}
if (typeof payload === "number" || typeof payload === "bigint") {
return String(payload);
}
if (Array.isArray(payload)) {
return payload.map((value) => processPayload(value));
}
if (typeof payload === "object") {
const result = { ...payload };
if ("chainId" in result && result.chainId !== void 0) {
if (typeof result.chainId === "string") {
const parsed = Number(result.chainId);
if (Number.isFinite(parsed)) {
result.chainId = parsed;
}
} else if (typeof result.chainId === "bigint") {
const parsed = Number(result.chainId);
if (!Number.isSafeInteger(parsed)) {
throw new Error(`Invalid chainId: ${String(result.chainId)}`);
}
result.chainId = parsed;
}
}
if ("value" in result && result.value !== void 0) {
if (typeof result.value !== "string") {
result.value = String(result.value);
}
if (!isValidHex(result.value)) {
console.error(
"Transaction value must be a valid hex string",
result.value
);
throw new Error(
`Transaction value must be a valid hex string: ${result.value}`
);
}
}
for (const key in result) {
if (Object.prototype.hasOwnProperty.call(result, key)) {
if (key === "chainId") continue;
result[key] = processPayload(result[key]);
}
}
return result;
}
return payload;
};
var validateSendTransactionPayload = (payload) => {
return processPayload(payload);
};
// src/commands/send-transaction/index.ts
var WORLD_CHAIN_ID = 480;
function resolveChainId(options) {
return options.chainId;
}
function resolveTransactions(options) {
if (options.transactions.length === 0) {
throw new SendTransactionError("input_error" /* InputError */, {
reason: "At least one transaction is required. Use `transactions: [{ to, data, value }]`."
});
}
return options.transactions;
}
function normalizeSendTransactionOptions(options) {
const chainId = resolveChainId(options);
if (chainId !== WORLD_CHAIN_ID) {
throw new SendTransactionError("invalid_operation" /* InvalidOperation */, {
reason: `World App only supports World Chain (chainId: ${WORLD_CHAIN_ID})`
});
}
return {
transactions: resolveTransactions(options),
chainId
};
}
async function sendTransaction(options, ctx) {
const normalizedOptions = normalizeSendTransactionOptions(options);
const fallbackAdapter = getFallbackAdapter();
const result = await executeWithFallback({
command: "send-transaction" /* SendTransaction */,
nativeExecutor: () => nativeSendTransaction(normalizedOptions, ctx),
wagmiFallback: fallbackAdapter?.sendTransaction ? () => adapterSendTransactionFallback(normalizedOptions) : void 0,
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
if (result.executedWith === "wagmi") {
return {
executedWith: "wagmi",
data: result.data
};
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeSendTransaction(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("send-transaction" /* SendTransaction */)) {
throw new Error(
"'sendTransaction' command is unavailable. Check MiniKit.install() or update the app version"
);
}
if (options.chainId !== WORLD_CHAIN_ID) {
throw new Error(
`World App only supports World Chain (chainId: ${WORLD_CHAIN_ID})`
);
}
const commandInput = window.WorldApp?.supported_commands.find(
(command) => command.name === "send-transaction" /* SendTransaction */
);
if (commandInput && !commandInput.supported_versions.includes(
COMMAND_VERSIONS["send-transaction" /* SendTransaction */]
)) {
throw new CommandUnavailableError("send-transaction" /* SendTransaction */, "oldAppVersion");
}
const input = {
transactions: options.transactions,
chainId: options.chainId
};
const validatedPayload = validateSendTransactionPayload(input);
const finalPayload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-send-transaction" /* MiniAppSendTransaction */, (response) => {
ctx.events.unsubscribe("miniapp-send-transaction" /* MiniAppSendTransaction */);
resolve(response);
});
sendMiniKitEvent({
command: "send-transaction" /* SendTransaction */,
version: COMMAND_VERSIONS["send-transaction" /* SendTransaction */],
payload: validatedPayload
});
} catch (error) {
reject(error);
}
}
);
if (finalPayload.status === "error") {
throw new SendTransactionError(
finalPayload.error_code,
finalPayload.details
);
}
const successPayload = finalPayload;
return {
userOpHash: String(successPayload.userOpHash ?? ""),
status: finalPayload.status,
version: finalPayload.version,
from: String(successPayload.from ?? ""),
timestamp: String(successPayload.timestamp ?? (/* @__PURE__ */ new Date()).toISOString())
};
}
async function adapterSendTransactionFallback(options) {
const fallbackAdapter = getFallbackAdapter();
if (!fallbackAdapter?.sendTransaction) {
throw new Error("Fallback adapter is not registered.");
}
const result = await fallbackAdapter.sendTransaction({
transactions: options.transactions.map((tx) => ({
address: tx.to,
data: tx.data,
value: tx.value
})),
chainId: options.chainId
});
return {
userOpHash: result.transactionHash,
status: "success",
version: COMMAND_VERSIONS["send-transaction" /* SendTransaction */],
from: "",
timestamp: (/* @__PURE__ */ new Date()).toISOString()
};
}
// src/commands/share/types.ts
var ShareFilesErrorCodes = /* @__PURE__ */ ((ShareFilesErrorCodes2) => {
ShareFilesErrorCodes2["UserRejected"] = "user_rejected";
ShareFilesErrorCodes2["GenericError"] = "generic_error";
ShareFilesErrorCodes2["InvalidFileName"] = "invalid_file_name";
return ShareFilesErrorCodes2;
})(ShareFilesErrorCodes || {});
var ShareError = class extends Error {
constructor(error_code) {
super(`Share failed: ${error_code}`);
this.error_code = error_code;
this.name = "ShareError";
}
};
// src/commands/share/format.ts
var MAX_FILES = 10;
var MAX_TOTAL_SIZE_MB = 50;
var MAX_TOTAL_SIZE_BYTES = MAX_TOTAL_SIZE_MB * 1024 * 1024;
var processFile = async (file) => {
const buffer = await file.arrayBuffer();
const uint8Array = new Uint8Array(buffer);
let binaryString = "";
const K_CHUNK_SIZE = 32768;
for (let i = 0; i < uint8Array.length; i += K_CHUNK_SIZE) {
const chunk = uint8Array.subarray(
i,
Math.min(i + K_CHUNK_SIZE, uint8Array.length)
);
binaryString += String.fromCharCode.apply(
null,
Array.from(chunk)
// Convert Uint8Array chunk to number[]
);
}
const base64Data = btoa(binaryString);
return {
name: file.name,
type: file.type,
data: base64Data
};
};
var formatShareInput = async (input) => {
if (!input.files) {
return {
title: input.title,
text: input.text,
url: input.url
};
}
if (!Array.isArray(input.files)) {
throw new Error('The "files" property must be an array.');
}
if (input.files.length === 0) {
} else {
if (input.files.length > MAX_FILES) {
throw new Error(`Cannot share more than ${MAX_FILES} files.`);
}
let totalSize = 0;
for (const file of input.files) {
if (!(file instanceof File)) {
throw new Error(
`Each item in the 'files' array must be a File object. Received: ${typeof file}`
);
}
totalSize += file.size;
}
if (totalSize > MAX_TOTAL_SIZE_BYTES) {
throw new Error(`Total file size cannot exceed ${MAX_TOTAL_SIZE_MB}MB.`);
}
}
const fileProcessingPromises = input.files.map((file) => processFile(file));
const processedFiles = await Promise.all(fileProcessingPromises);
return {
files: processedFiles,
title: input.title,
text: input.text,
url: input.url
};
};
// src/commands/share/index.ts
async function share(options, ctx) {
const result = await executeWithFallback({
command: "share" /* Share */,
nativeExecutor: () => nativeShare(options, ctx),
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return {
executedWith: "fallback",
data: result.data
};
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeShare(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("share" /* Share */)) {
throw new Error(
"'share' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payloadInput = {
files: options.files,
title: options.title,
text: options.text,
url: options.url
};
if (ctx.state.deviceProperties.deviceOS === "ios" && typeof navigator !== "undefined") {
sendMiniKitEvent({
command: "share" /* Share */,
version: COMMAND_VERSIONS["share" /* Share */],
payload: payloadInput
});
await navigator.share(payloadInput);
return {
status: "success",
version: COMMAND_VERSIONS["share" /* Share */],
shared_files_count: payloadInput.files?.length ?? 0,
timestamp: (/* @__PURE__ */ new Date()).toISOString()
};
}
const formattedPayload = await formatShareInput(payloadInput);
const payload = await new Promise((resolve, reject) => {
try {
ctx.events.subscribe("miniapp-share" /* MiniAppShare */, (response) => {
ctx.events.unsubscribe("miniapp-share" /* MiniAppShare */);
resolve(response);
});
sendMiniKitEvent({
command: "share" /* Share */,
version: COMMAND_VERSIONS["share" /* Share */],
payload: formattedPayload
});
} catch (error) {
reject(error);
}
});
if (payload.status === "error") {
throw new ShareError(payload.error_code);
}
return payload;
}
// src/commands/share-contacts/types.ts
var ShareContactsErrorCodes = /* @__PURE__ */ ((ShareContactsErrorCodes2) => {
ShareContactsErrorCodes2["UserRejected"] = "user_rejected";
ShareContactsErrorCodes2["GenericError"] = "generic_error";
return ShareContactsErrorCodes2;
})(ShareContactsErrorCodes || {});
var ShareContactsErrorMessage = {
["user_rejected" /* UserRejected */]: "User rejected the request.",
["generic_error" /* GenericError */]: "Something unexpected went wrong."
};
var ShareContactsError = class extends Error {
constructor(code) {
super(`Share contacts failed: ${code}`);
this.name = "ShareContactsError";
this.code = code;
}
};
// src/commands/share-contacts/index.ts
async function shareContacts(options, ctx) {
const resolvedOptions = options ?? {};
const result = await executeWithFallback({
command: "share-contacts" /* ShareContacts */,
nativeExecutor: () => nativeShareContacts(resolvedOptions, ctx),
// No Wagmi fallback - contacts is native only
customFallback: resolvedOptions.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
return { executedWith: "minikit", data: result.data };
}
var getContacts = shareContacts;
async function nativeShareContacts(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("share-contacts" /* ShareContacts */)) {
throw new Error(
"'shareContacts' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payload = {
isMultiSelectEnabled: options.isMultiSelectEnabled ?? false,
inviteMessage: options.inviteMessage
};
const finalPayload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-share-contacts" /* MiniAppShareContacts */, (response) => {
ctx.events.unsubscribe("miniapp-share-contacts" /* MiniAppShareContacts */);
resolve(response);
});
sendMiniKitEvent({
command: "share-contacts" /* ShareContacts */,
version: COMMAND_VERSIONS["share-contacts" /* ShareContacts */],
payload
});
} catch (error) {
reject(error);
}
}
);
if (finalPayload.status === "error") {
throw new ShareContactsError(finalPayload.error_code);
}
return {
contacts: finalPayload.contacts,
timestamp: finalPayload.timestamp
};
}
// src/commands/sign-message/types.ts
var SignMessageErrorCodes = /* @__PURE__ */ ((SignMessageErrorCodes2) => {
SignMessageErrorCodes2["InvalidMessage"] = "invalid_message";
SignMessageErrorCodes2["UserRejected"] = "user_rejected";
SignMessageErrorCodes2["GenericError"] = "generic_error";
return SignMessageErrorCodes2;
})(SignMessageErrorCodes || {});
var SignMessageError = class extends Error {
constructor(error_code) {
super(`Sign message failed: ${error_code}`);
this.error_code = error_code;
this.name = "SignMessageError";
}
};
// src/commands/sign-message/index.ts
async function signMessage(options, ctx) {
const fallbackAdapter = getFallbackAdapter();
const result = await executeWithFallback({
command: "sign-message" /* SignMessage */,
nativeExecutor: () => nativeSignMessage(options, ctx),
wagmiFallback: fallbackAdapter?.signMessage ? () => fallbackAdapter.signMessage({
message: options.message
}) : void 0,
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
if (result.executedWith === "wagmi") {
return {
executedWith: "wagmi",
data: result.data
};
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeSignMessage(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("sign-message" /* SignMessage */)) {
throw new Error(
"'signMessage' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-sign-message" /* MiniAppSignMessage */, (response) => {
ctx.events.unsubscribe("miniapp-sign-message" /* MiniAppSignMessage */);
resolve(response);
});
sendMiniKitEvent({
command: "sign-message" /* SignMessage */,
version: COMMAND_VERSIONS["sign-message" /* SignMessage */],
payload: { message: options.message }
});
} catch (error) {
reject(error);
}
}
);
if (payload.status === "error") {
throw new SignMessageError(payload.error_code);
}
return payload;
}
// src/commands/sign-typed-data/types.ts
var SignTypedDataErrorCodes = /* @__PURE__ */ ((SignTypedDataErrorCodes2) => {
SignTypedDataErrorCodes2["InvalidOperation"] = "invalid_operation";
SignTypedDataErrorCodes2["UserRejected"] = "user_rejected";
SignTypedDataErrorCodes2["InputError"] = "input_error";
SignTypedDataErrorCodes2["SimulationFailed"] = "simulation_failed";
SignTypedDataErrorCodes2["GenericError"] = "generic_error";
SignTypedDataErrorCodes2["DisallowedOperation"] = "disallowed_operation";
SignTypedDataErrorCodes2["InvalidContract"] = "invalid_contract";
SignTypedDataErrorCodes2["MaliciousOperation"] = "malicious_operation";
return SignTypedDataErrorCodes2;
})(SignTypedDataErrorCodes || {});
var SignTypedDataError = class extends Error {
constructor(error_code) {
super(`Sign typed data failed: ${error_code}`);
this.error_code = error_code;
this.name = "SignTypedDataError";
}
};
// src/commands/sign-typed-data/index.ts
async function signTypedData(options, ctx) {
const fallbackAdapter = getFallbackAdapter();
const result = await executeWithFallback({
command: "sign-typed-data" /* SignTypedData */,
nativeExecutor: () => nativeSignTypedData(options, ctx),
wagmiFallback: fallbackAdapter?.signTypedData ? () => fallbackAdapter.signTypedData({
types: options.types,
primaryType: options.primaryType,
message: options.message,
domain: options.domain,
chainId: options.chainId
}) : void 0,
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
if (result.executedWith === "wagmi") {
return {
executedWith: "wagmi",
data: result.data
};
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeSignTypedData(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("sign-typed-data" /* SignTypedData */)) {
throw new Error(
"'signTypedData' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const payloadInput = {
types: options.types,
primaryType: options.primaryType,
message: options.message,
domain: options.domain,
chainId: options.chainId ?? 480
};
const payload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-sign-typed-data" /* MiniAppSignTypedData */, (response) => {
ctx.events.unsubscribe("miniapp-sign-typed-data" /* MiniAppSignTypedData */);
resolve(response);
});
sendMiniKitEvent({
command: "sign-typed-data" /* SignTypedData */,
version: COMMAND_VERSIONS["sign-typed-data" /* SignTypedData */],
payload: payloadInput
});
} catch (error) {
reject(error);
}
}
);
if (payload.status === "error") {
throw new SignTypedDataError(payload.error_code);
}
return payload;
}
// src/commands/wallet-auth/types.ts
var WalletAuthErrorCodes = /* @__PURE__ */ ((WalletAuthErrorCodes2) => {
WalletAuthErrorCodes2["MalformedRequest"] = "malformed_request";
WalletAuthErrorCodes2["UserRejected"] = "user_rejected";
WalletAuthErrorCodes2["GenericError"] = "generic_error";
return WalletAuthErrorCodes2;
})(WalletAuthErrorCodes || {});
var WalletAuthErrorMessage = {
["malformed_request" /* MalformedRequest */]: "Provided parameters in the request are invalid.",
["user_rejected" /* UserRejected */]: "User rejected the request.",
["generic_error" /* GenericError */]: "Something unexpected went wrong."
};
var WalletAuthError = class extends Error {
constructor(code, details) {
super(details || `Wallet auth failed: ${code}`);
this.name = "WalletAuthError";
this.code = code;
this.details = details;
}
};
// src/commands/wallet-auth/validate.ts
var SIWE_NONCE_REGEX = /^[a-zA-Z0-9]+$/;
var validateWalletAuthCommandInput = (params) => {
if (!params.nonce) {
return { valid: false, message: "'nonce' is required" };
}
if (params.nonce.length < 8) {
return { valid: false, message: "'nonce' must be at least 8 characters" };
}
if (!SIWE_NONCE_REGEX.test(params.nonce)) {
return {
valid: false,
message: "'nonce' must be alphanumeric (letters and numbers only)"
};
}
if (params.statement && params.statement.includes("\n")) {
return { valid: false, message: "'statement' must not contain newlines" };
}
if (params.expirationTime && new Date(params.expirationTime) < /* @__PURE__ */ new Date()) {
return { valid: false, message: "'expirationTime' must be in the future" };
}
if (params.expirationTime && new Date(params.expirationTime) > new Date(Date.now() + 7 * 24 * 60 * 60 * 1e3)) {
return { valid: false, message: "'expirationTime' must be within 7 days" };
}
if (params.notBefore && new Date(params.notBefore) > new Date(Date.now() + 7 * 24 * 60 * 60 * 1e3)) {
return { valid: false, message: "'notBefore' must be within 7 days" };
}
return { valid: true };
};
// src/commands/wallet-auth/index.ts
async function walletAuth(options, ctx) {
const fallbackAdapter = getFallbackAdapter();
const result = await executeWithFallback({
command: "wallet-auth" /* WalletAuth */,
nativeExecutor: () => nativeWalletAuth(options, ctx),
wagmiFallback: fallbackAdapter?.walletAuth ? () => fallbackAdapter.walletAuth({
nonce: options.nonce,
statement: options.statement,
expirationTime: options.expirationTime
}) : void 0,
customFallback: options.fallback
});
if (result.executedWith === "fallback") {
return { executedWith: "fallback", data: result.data };
}
if (result.executedWith === "wagmi") {
return {
executedWith: "wagmi",
data: result.data
};
}
return {
executedWith: "minikit",
data: result.data
};
}
async function nativeWalletAuth(options, ctx) {
if (!ctx) {
ctx = { events: new EventManager(), state: { deviceProperties: {} } };
}
if (typeof window === "undefined" || !isCommandAvailable("wallet-auth" /* WalletAuth */)) {
throw new Error(
"'walletAuth' command is unavailable. Check MiniKit.install() or update the app version"
);
}
const input = {
nonce: options.nonce,
statement: options.statement,
requestId: options.requestId,
expirationTime: options.expirationTime,
notBefore: options.notBefore
};
const validationResult = validateWalletAuthCommandInput(input);
if (!validationResult.valid) {
throw new Error(`Invalid wallet auth input: ${validationResult.message}`);
}
let protocol;
try {
const currentUrl = new URL(window.location.href);
protocol = currentUrl.protocol.split(":")[0];
} catch (error) {
throw new Error("Failed to get current URL");
}
const siweMessage = generateSiweMessage({
scheme: protocol,
domain: window.location.host,
statement: input.statement ?? void 0,
uri: window.location.href,
version: "1",
chain_id: 480,
nonce: input.nonce,
issued_at: (/* @__PURE__ */ new Date()).toISOString(),
expiration_time: input.expirationTime?.toISOString() ?? void 0,
not_before: input.notBefore?.toISOString() ?? void 0,
request_id: input.requestId ?? void 0
});
const walletAuthPayload = { siweMessage };
const worldAppVersion = ctx.state.deviceProperties.worldAppVersion;
if (worldAppVersion && worldAppVersion <= 2087900) {
throw new Error(
"Wallet auth v1 is no longer supported. Please update World App to the latest version."
);
}
const finalPayload = await new Promise(
(resolve, reject) => {
try {
ctx.events.subscribe("miniapp-wallet-auth" /* MiniAppWalletAuth */, (response) => {
ctx.events.unsubscribe("miniapp-wallet-auth" /* MiniAppWalletAuth */);
resolve(response);
});
sendMiniKitEvent({
command: "wallet-auth" /* WalletAuth */,
version: COMMAND_VERSIONS["wallet-auth" /* WalletAuth */],
payload: walletAuthPayload
});
} catch (error) {
reject(error);
}
}
);
if (finalPayload.status === "error") {
throw new WalletAuthError(finalPayload.error_code, finalPayload.details);
}
return {
address: finalPayload.address,
message: finalPayload.message,
signature: finalPayload.signature,
version: finalPayload.version
};
}
// src/types.ts
var MiniAppLaunchLocation = /* @__PURE__ */ ((MiniAppLaunchLocation2) => {
MiniAppLaunchLocation2["Chat"] = "chat";
MiniAppLaunchLocation2["Home"] = "home";
MiniAppLaunchLocation2["AppStore"] = "app-store";
MiniAppLaunchLocation2["DeepLink"] = "deep-link";
MiniAppLaunchLocation2["WalletTab"] = "wallet-tab";
return MiniAppLaunchLocation2;
})(MiniAppLaunchLocation || {});
var MiniKitInstallErrorCodes = /* @__PURE__ */ ((MiniKitInstallErrorCodes2) => {
MiniKitInstallErrorCodes2["Unknown"] = "unknown";
MiniKitInstallErrorCodes2["AlreadyInstalled"] = "already_installed";
MiniKitInstallErrorCodes2["OutsideOfWorldApp"] = "outside_of_worldapp";
MiniKitInstallErrorCodes2["NotOnClient"] = "not_on_client";
MiniKitInstallErrorCodes2["AppOutOfDate"] = "app_out_of_date";
return MiniKitInstallErrorCodes2;
})(MiniKitInstallErrorCodes || {});
var MiniKitInstallErrorMessage = {
["unknown" /* Unknown */]: "Failed to install MiniKit.",
["already_installed" /* AlreadyInstalled */]: "MiniKit is already installed.",
["outside_of_worldapp" /* OutsideOfWorldApp */]: "MiniApp launched outside of WorldApp.",
["not_on_client" /* NotOnClient */]: "Window object is not available.",
["app_out_of_date" /* AppOutOfDate */]: "WorldApp is out of date. Please update the app."
};
export {
EventManager,
AttestationErrorCodes,
AttestationError,
attestation,
ChatErrorCodes,
ChatError,
chat,
closeMiniApp,
GetPermissionsErrorCodes,
Permission,
GetPermissionsError,
getPermissions,
Tokens,
TokenDecimals,
Network,
PaymentErrorCodes,
PaymentErrorMessage,
PayError,
tokenToDecimals,
pay,
RequestPermissionErrorCodes,
RequestPermissionError,
requestPermission,
SendHapticFeedbackErrorCodes,
SendHapticFeedbackError,
sendHapticFeedback,
SendTransactionErrorCodes,
SendTransactionErrorMessage,
WORLD_APP_FEATURES,
WEB_FEATURES,
SendTransactionError,
sendTransaction,
ShareFilesErrorCodes,
ShareError,
share,
ShareContactsErrorCodes,
ShareContactsErrorMessage,
ShareContactsError,
shareContacts,
getContacts,
SignMessageErrorCodes,
SignMessageError,
signMessage,
SignTypedDataErrorCodes,
SignTypedDataError,
signTypedData,
WalletAuthErrorCodes,
WalletAuthErrorMessage,
WalletAuthError,
walletAuth,
MiniAppLaunchLocation,
MiniKitInstallErrorCodes,
MiniKitInstallErrorMessage
};