Frequently Asked Questions
Your Plivo Auth ID and Auth Token are found on your Plivo console dashboard after you log in. These credentials are essential for authenticating with the Plivo API.
Use the Plivo Node.js SDK with a web framework like Fastify. This allows you to create a server-side application that can handle MMS sending requests via the Plivo API. Make sure to set up your Plivo account and configure the necessary credentials in your project.
Fastify is a high-performance Node.js web framework known for its speed and plugin ecosystem. The tutorial uses it for its efficiency and features like built-in request validation and easy route handling.
Dotenv helps manage environment variables, allowing you to store sensitive information like API keys outside your codebase. This improves security and makes it easier to manage different environments (development, production).
Use npm or yarn. Install fastify, plivo, and dotenv as core dependencies. For development, pino-pretty is recommended for enhanced logging. Run npm install fastify plivo dotenv or yarn add fastify plivo dotenv, and similarly for dev dependencies.
The .env file securely stores your Plivo Auth ID, Auth Token, sender number, host, and port. This keeps sensitive credentials out of your codebase, enhancing security.
Create directories for source code (src), routes (src/routes), and place your main application file (app.js) in src. Routes are defined in files within src/routes. Also, include .env, .env.example, and .gitignore files in the root.
You need a Plivo phone number with MMS capabilities enabled, typically available for the US and Canada. Purchase one from the Plivo console and confirm MMS is enabled.
The provided code example uses try...catch blocks and checks for PlivoResponseError to handle errors. You can provide specific responses depending on the error code returned by the Plivo API.
The tutorial uses @fastify/rate-limit to implement rate limiting. The default example configuration limits to 100 requests per minute per IP, which is customizable.
Rate limiting helps prevent abuse and protects your Plivo account balance by controlling the number of MMS messages sent within a specific time window.
Use curl to send test requests to your local Fastify server. Provide valid JSON data with recipient number, media URLs, and message text in the request body.
A successful response will return a 200 OK status code with a JSON body including the message, messageUuid (an array of UUIDs), and apiId.
It means Plivo has accepted your request and queued the message for sending. It doesn't guarantee delivery; for that, implement status callbacks.
The tutorial provides troubleshooting for authentication errors, invalid numbers, media URL issues, rate limiting, and other potential Plivo API errors. Refer to the article for more details.
Send MMS with Plivo, Node.js & Fastify: Complete Tutorial
Learn how to build a production-ready service using Fastify and Node.js to send Multimedia Messaging Service (MMS) messages via the Plivo API. This comprehensive tutorial covers project setup, authentication, sending logic, error handling, rate limiting, and testing.
By the end of this guide, you'll have a robust Fastify application that sends MMS messages with media attachments (images, audio, video) using Plivo's reliable messaging infrastructure.
MMS vs SMS: When to Use Multimedia Messaging
MMS (Multimedia Messaging Service) allows you to send rich media content including images, audio files, videos, and longer text (up to 1600 characters), while SMS is limited to 160 characters of text only. Use MMS when you need to:
Note that MMS messages typically cost more than SMS and require cellular data connection on the recipient's device. Plivo supports MMS exclusively within the US and Canada.
Technologies Used:
.envfile, keeping sensitive credentials out of the codebase.<!-- EXPAND: Could benefit from version compatibility matrix (Type: Enhancement) -->
Prerequisites:
<!-- GAP: Missing cost breakdown and trial account limitations (Type: Critical, Priority: High) --> <!-- DEPTH: No information about MMS pricing or account balance requirements (Priority: High) -->
System Architecture:
(A diagram illustrating the flow from HTTP Client -> Fastify App -> Plivo API -> End User would typically be included here.)
This guide focuses on the "Fastify Application" component and its interaction with the Plivo API for sending MMS.
<!-- EXPAND: Missing actual architecture diagram or flowchart (Type: Enhancement, Priority: Medium) --> <!-- GAP: No explanation of webhook flow for delivery status (Type: Substantive) -->
Setting Up Your Plivo MMS Project
Let's initialize the project, install dependencies, and set up the basic structure.
Create Project Directory: Open your terminal and create a new directory for your project, then navigate into it.
Initialize Node.js Project: Initialize a
package.jsonfile. The-yflag accepts default settings.Install Dependencies: Install Fastify, the Plivo SDK, and
dotenv.<!-- DEPTH: No explanation of why these specific packages or alternatives (Priority: Low) -->
Install Development Dependencies (Optional): Install
pino-prettyfor better log readability during development.Create Project Structure: Set up a basic directory structure for better organization.
src/: Contains the main application source code.src/routes/: Will hold route definitions.src/app.js: The main Fastify application entry point.src/routes/mms.js: The route handler specifically for MMS sending..env: Stores sensitive environment variables (API keys, etc.). Never commit this file..env.example: An example file showing required environment variables (safe to commit)..gitignore: Specifies files and directories that Git should ignore.<!-- EXPAND: Could add testing directory structure and config files (Type: Enhancement) -->
Configure
.gitignore: Addnode_modulesand.envto your.gitignorefile to prevent committing them to version control.Configure
.env.example: Add the necessary environment variable placeholders to.env.example.Configure
.env: Copy.env.exampleto.envand fill in your actual Plivo credentials and phone number.Now, edit the
.envfile with your real values obtained from the Plivo console.Why
.env? Storing sensitive information like API keys directly in code is a major security risk..envfiles allow you to keep configuration separate from the codebase, making it easier to manage different environments (development, production) and preventing accidental exposure.<!-- DEPTH: Missing best practices for secret rotation and key management (Priority: Medium) -->
Implementing the Fastify Server for MMS
Let's set up the basic Fastify server and configure it to use the Plivo client.
Edit
src/app.js: This file will initialize Fastify, load environment variables, instantiate the Plivo client, register routes, and start the server.dotenv.config()loads variables from.env. We add basic checks to ensure critical variables are present.pino-prettyfor development for easier reading and standard JSON logging for production (better for log aggregation tools).plivo.Clientis instantiated using credentials fromprocess.env.app.decorate): This is a key Fastify pattern. We "decorate" the Fastifyappinstance with theplivoClientandplivoSenderNumber. This makes them easily accessible within route handlers viarequest.server.plivoorreply.server.plivo(and similarly forplivoSenderNumber), avoiding the need to pass them around manually or re-initialize them.src/routes/mms.jsunder the/api/mmsprefix./healthendpoint is added, which is standard practice for monitoring.app.listenfunction starts the server on the configured host and port.<!-- DEPTH: Missing graceful shutdown handling and signal management (Priority: High) --> <!-- GAP: No error recovery strategies or circuit breaker pattern (Type: Substantive) -->
Building the MMS Sending API Endpoint
Now, let's implement the route that will handle incoming requests to send an MMS.
<!-- EXPAND: Could add request/response examples with different scenarios (Type: Enhancement) -->
Edit
src/routes/mms.js: This file defines the API endpoint for sending MMS messages.sendMmsSchemausing JSON Schema. Fastify automatically validates incoming request bodies against this schema before the handler function runs. If validation fails, Fastify sends a400 Bad Requestresponse automatically. This simplifies the handler logic significantly. We specify required fields (to,media_urls,text), types, and formats (like E.164 pattern and URL format).additionalProperties: falseprevents extra, unexpected fields. Thetofield pattern was corrected, and its description enhanced. AddedmaxItems: 10to media_urls based on Plivo limits.fastify.post('/send', { schema: sendMmsSchema }, ...)defines a POST endpoint at/api/mms/send. The schema is attached directly to the route options.fastify.plivoandfastify.plivoSenderNumberprovide the initialized Plivo client and sender number.paramsobject required byplivoClient.messages.create. Note that Plivo usesdstfor the destination number. We explicitly settype: 'mms'.async/await: The route handler is anasyncfunction, allowing us to useawaitfor the Plivo API call, making the asynchronous code cleaner.200 OKresponse with details from the Plivo API. The response keys (messageUuid,apiId) are now consistently camelCase, matching the schema and common Node.js practice.try...catchblock handles errors during the API call. We log the error and attempt to provide a meaningful status code and message back to the client. We check if the error is a specificPlivoResponseErrorto potentially extract more details, adding a comment about common error codes. The response schema was updated to use camelCase for consistency.<!-- GAP: Missing retry logic for transient failures (Type: Substantive, Priority: High) --> <!-- DEPTH: No explanation of idempotency or duplicate request handling (Priority: Medium) --> <!-- EXPAND: Could add detailed error code mapping table (Type: Enhancement) -->
Adding Rate Limiting for Security
To prevent abuse and protect your Plivo account balance, implementing rate limiting is crucial.
<!-- DEPTH: Missing explanation of DDoS protection and additional security layers (Priority: Medium) -->
Install Rate Limiter Plugin:
Register and Configure in
src/app.js: Modifysrc/app.jsto include the rate limiter.app.registerto add the@fastify/rate-limitplugin. It's important to register this before the routes you want to limit.max: Sets the maximum number of requests allowed within thetimeWindow. Adjust this based on expected traffic and Plivo's own rate limits.timeWindow: Defines the duration over which requests are counted (e.g., '1 minute', '1 hour',60000ms).errorResponseBuilder: Customizes the429 Too Many Requestsresponse sent when the limit is hit.enableDraftSpec: Adds standardRateLimit-*headers to responses, which is good practice.<!-- GAP: Missing Redis configuration for distributed rate limiting (Type: Substantive, Priority: Medium) --> <!-- DEPTH: No guidance on tuning rate limits based on account tier (Priority: High) -->
Testing Your MMS Service
Now, let's run the server and test the MMS sending endpoint.
<!-- EXPAND: Could add automated testing examples with Jest or Mocha (Type: Enhancement) -->
Add Run Scripts to
package.json:start: Runs the application in production mode (default logger).dev: Runs in development mode, settingNODE_ENVand piping logs throughpino-pretty.Run the Server (Development Mode):
You should see output indicating the server is running, similar to:
Test with
curl: Open another terminal window. Replace placeholders with your verified destination number (for trial accounts) or any US/Canada number (for paid accounts), and a publicly accessible media URL.Success Case:
Expected Success Response (JSON - using camelCase):
You should also see corresponding logs in the server terminal and receive the MMS on the destination phone shortly.
<!-- DEPTH: No explanation of typical delivery times or latency expectations (Priority: Medium) -->
Validation Error Case (Missing
text):Expected Error Response (400 Bad Request - Handled by Fastify):
Plivo API Error Case (e.g., Invalid Auth Token in
.env):(Simulate by temporarily putting an incorrect token in
.envand restarting the server)Expected Error Response (Handled by our
catchblock):<!-- EXPAND: Could add Postman collection or OpenAPI spec for testing (Type: Enhancement) -->
Troubleshooting Common MMS Issues
PLIVO_AUTH_IDandPLIVO_AUTH_TOKENin your.envfile. Ensure they are copied correctly from the Plivo console.srcordstNumber (e.g., 400 Bad Request from Plivo):PLIVO_SENDER_NUMBERis an MMS-enabled number you own on Plivo.srcanddstnumbers are in E.164 format (e.g.,+14151234567). Thetofield validator checks the format (^\\+[1-9]\\d{1,14}$).dstnumber must be verified in the Sandbox Numbers section of the Plivo console.media_urlsmust point to publicly accessible URLs. Plivo's servers need to fetch the media from these URLs. Test the URL in your browser first. Supported file types include JPEG, GIF, PNG (images), MP3 (audio), and MP4 (video). For Canadian carriers, keep MMS attachments smaller than 1 MB to ensure broad compatibility across all networks.max: 100,timeWindow: '1 minute'by default in this guide) or Plivo's own API limits. Plivo enforces a default limit of 300 API requests per 5 seconds for non-call APIs, and supports up to 100 concurrent MMS requests. When limits are exceeded, Plivo responds with HTTP 429 Too Many Requests. The error response indicates when you can retry. Source: Plivo Rate Limits and Plivo MMS Account Rate Limitsapi.plivo.com). Firewalls or network configuration could block requests.200 OK,message: "message(s) queued") only means Plivo accepted the request. It doesn't guarantee delivery to the handset. For delivery confirmation, you need to implement webhook handlers for Plivo's status callbacks (using theurlandmethodparameters in themessages.createcall). This is a more advanced topic.<!-- GAP: Missing specific timeout values and timeout handling strategies (Type: Critical, Priority: High) --> <!-- DEPTH: No troubleshooting flowchart or decision tree (Priority: Medium) --> <!-- EXPAND: Could add logging best practices for debugging production issues (Type: Enhancement) -->
Production Deployment Best Practices
.envfile. Use your hosting provider's mechanism for setting environment variables (e.g., Heroku Config Vars, AWS Systems Manager Parameter Store, Docker environment variables).pm2or run your application within a container (Docker) to handle restarts, clustering (for multi-core utilization), and logging.pm2:npm install -g pm2, thenpm2 start src/app.js --name fastify-plivo-mms/healthendpoint. Monitor application performance (APM tools) and error rates.<!-- GAP: Missing Docker/Kubernetes deployment examples (Type: Substantive, Priority: Medium) --> <!-- DEPTH: No guidance on horizontal scaling or load balancing (Priority: High) --> <!-- EXPAND: Could add infrastructure as code examples (Terraform/CloudFormation) (Type: Enhancement) --> <!-- GAP: Missing backup/disaster recovery considerations (Type: Critical, Priority: Medium) -->
Plivo MMS Frequently Asked Questions
How do I send MMS with Plivo and Node.js?
To send MMS with Plivo and Node.js, install the Plivo SDK (
npm install plivo), initialize a Plivo client with your Auth ID and Auth Token, and callclient.messages.create()with parameters includingsrc(your Plivo number),dst(recipient in E.164 format),text,media_urls(array of public media URLs), andtype: 'mms'. Plivo supports MMS only within the US and Canada.What file formats does Plivo MMS support?
Plivo MMS supports JPEG, GIF, and PNG for images, MP3 for audio, and MP4 for video. Media files must be hosted on publicly accessible URLs that Plivo servers can fetch. For Canadian carriers, keep MMS attachments smaller than 1 MB to ensure broad compatibility across all networks. You can include up to 10 media URLs per MMS message.
<!-- DEPTH: Missing specific file size limits per format (Priority: Medium) -->
What is E.164 phone number format?
E.164 is the international phone number format standardized by ITU-T. It consists of a plus sign (+) followed by a country code (1-3 digits) and subscriber number, with a maximum of 15 digits total. Example: +14151234567 for a US number. Both source and destination numbers must use E.164 format for Plivo API calls.
Why use Fastify for MMS messaging?
Fastify is a high-performance, low-overhead Node.js web framework ideal for MMS messaging services. It provides built-in JSON schema validation, automatic request/response serialization, extensive plugin ecosystem (including @fastify/rate-limit), and superior performance compared to Express. Fastify's decorator pattern simplifies sharing the Plivo client across routes.
<!-- EXPAND: Could add performance benchmarks vs Express (Type: Enhancement) -->
What are Plivo API rate limits?
Plivo enforces a default limit of 300 API requests per 5 seconds for non-call APIs and supports up to 100 concurrent MMS requests. When limits are exceeded, Plivo responds with HTTP 429 Too Many Requests. Implement rate limiting in your Fastify application using @fastify/rate-limit to control costs and prevent abuse.
Can I send MMS to countries outside US and Canada with Plivo?
No. Plivo supports MMS messaging exclusively within the US and Canada. Attempts to send MMS to other countries may fail or be converted to SMS with a media link. You can only send and receive MMS using US or Canadian Plivo phone numbers (local long code, toll-free, or short code).
How do I handle Plivo MMS delivery status?
Plivo's
messages.create()returns a200 OKresponse when messages are queued, not delivered. For delivery confirmation, implement webhook handlers for Plivo's status callbacks by addingurlandmethodparameters to your API call. Plivo will POST delivery status updates (delivered, failed, undelivered) to your webhook endpoint.<!-- GAP: Missing webhook implementation example (Type: Substantive, Priority: High) --> <!-- DEPTH: No explanation of webhook security/verification (Priority: High) -->
What Node.js version should I use for Plivo MMS?
Use Node.js 22.x LTS for production applications. Node.js 22 is in Active LTS until October 2025 and Maintenance LTS until April 2027. This version provides full support for modern JavaScript features, security updates, and optimal performance for Fastify and Plivo SDK integration.
Related Resources and Next Steps
Now that you've built a Fastify MMS service with Plivo, consider exploring these related topics:
Wrapping Up
You have now successfully built a Fastify application capable of sending MMS messages using the Plivo Node.js SDK. We covered project setup, secure credential management, API route implementation with validation, error handling, rate limiting, and essential testing procedures.
This provides a solid foundation for integrating MMS capabilities into your Node.js applications. From here, you could expand the service to include status webhooks for delivery tracking, build a frontend interface, or integrate it into a larger communication workflow.
<!-- EXPAND: Could add next steps roadmap with advanced features (Type: Enhancement) -->