Frequently Asked Questions
Create a new RedwoodJS project, install required dependencies like MessageBird and Prisma, define the database schema for appointments, and implement the API logic to handle bookings and scheduling. Then, build a frontend form for users to book appointments and connect it to the backend API. Finally, configure the SMS integration with MessageBird to send automated reminders.
RedwoodJS is the core framework for building the web application. It provides a full-stack, serverless-first environment based on React, GraphQL, and Prisma, enabling rapid development of both frontend and backend components.
MessageBird is a communications platform offering a reliable SMS API and phone number lookup capabilities. This integration allows for automated SMS reminders to be sent to users, minimizing no-shows and improving appointment management.
While this tutorial uses Moment.js for date/time manipulation, it's in maintenance mode. For new projects or significant updates, consider modern alternatives like date-fns, Luxon, or native JavaScript Date/Intl methods for better performance and maintainability. This is especially crucial for production-level applications
Yes, RedwoodJS supports authentication features. You can use Redwood's built-in authentication generators to easily add user accounts, enabling users to manage their own appointments and access personalized features. After generating authentication you can add the @requireAuth
directive to the relevant services.
The guide provides examples for PostgreSQL and SQLite. PostgreSQL is generally recommended for production environments, while SQLite is suitable for simpler development and testing purposes. The Prisma ORM handles database interactions.
The application uses the MessageBird Lookup API to validate phone numbers. This API verifies the number's format and identifies the number type (e.g., mobile, landline), ensuring only valid mobile numbers are used for SMS reminders.
The application enforces a minimum booking time of 3 hours and 5 minutes in the future. This time constraint is implemented in the backend service logic, ensuring adequate time for reminder scheduling.
The tutorial implementation uses date-time parsing that depends on the server's time zone, which can be problematic. Ideally, you should implement robust timezone handling using specialized libraries like date-fns-tz
or Luxon, storing all dates and times in UTC format.
While not covered in the initial setup, implementing MessageBird webhooks allows receiving real-time status updates for SMS messages. This provides feedback on delivery success or failure and enables more advanced features like retry mechanisms or notifications.
Appointment data is stored in a relational database (PostgreSQL or SQLite). The application uses Prisma, a next-generation ORM, to define the database schema, manage migrations, and interact with the database seamlessly from the API side.
RedwoodJS utilizes GraphQL for communication between the frontend and the backend API. The frontend uses GraphQL queries and mutations to request and modify data, while the backend defines the GraphQL schema and resolvers that handle these requests.
The optional messageBirdId
field stores the unique identifier assigned to the scheduled SMS message by MessageBird. This allows for tracking the message status and potentially canceling or rescheduling it later.
RedwoodJS offers deployment options for various platforms like Vercel, Netlify, and Render. Consult the RedwoodJS deployment documentation for specific instructions. Make sure to properly configure your environment variables (DATABASE_URL, MESSAGEBIRD_API_KEY, etc.) in your production environment.
Build a production-ready appointment booking system with automated SMS reminders using RedwoodJS and MessageBird. This comprehensive tutorial covers everything from project setup and database design to phone validation and deployment – perfect for developers creating appointment-based applications with SMS notifications.
Modern appointment booking systems require reliable SMS notifications to reduce no-shows and improve customer experience. This guide shows you how to leverage RedwoodJS's full-stack capabilities with MessageBird's SMS API to create an automated reminder system that validates phone numbers, schedules messages, and manages appointments efficiently.
How to Build an SMS Appointment Reminder System with RedwoodJS and MessageBird
Create a complete appointment booking application with automated SMS notifications using these production-ready features:
Note: This tutorial focuses on core booking and reminder functionality. Appointment updates and cancellations (including MessageBird message management) require additional implementation for production systems.
Why Build This Appointment Reminder System:
Automated SMS reminders reduce appointment no-shows significantly, with studies showing reductions between 5-38% depending on implementation. Healthcare and service-based businesses worldwide report baseline no-show rates of 15-30% in outpatient clinics, representing substantial lost revenue and inefficient resource utilization. SMS reminders provide a cost-effective solution that requires minimal staff intervention while improving patient attendance and allowing better schedule management through increased cancellation and rescheduling rates.
Technology Stack:
date-fns
or Luxon for new projects due to better bundle size and maintenance)System Architecture Overview:
Prerequisites for This Tutorial:
What You'll Have at the End:
A fully functional appointment booking system with automated SMS reminder capabilities. You'll understand how to integrate MessageBird for phone validation and message scheduling, use Prisma for database management, and leverage RedwoodJS conventions for rapid full-stack development. This foundation enables extensions like user authentication, cancellation workflows, and administrative dashboards.
1. Set Up Your RedwoodJS Project for SMS Scheduling
Create a new RedwoodJS application and configure dependencies for SMS messaging. Use TypeScript for enhanced type safety and better developer experience.
Create Your RedwoodJS App: Open your terminal and run the RedwoodJS create command:
This scaffolds a new RedwoodJS project with TypeScript configured in a directory named
redwood-messagebird-reminders
.Navigate to Your Project Directory:
Install Your Initial Dependencies: RedwoodJS automatically runs
yarn install
after creation. To run it manually:Configure Your Environment Variables: RedwoodJS uses a
.env
file for environment variables. Create this file in your project root:Open
.env
and add these variables. Get the values in subsequent steps.Why Use
.env
? Store sensitive information like API keys and database URLs separate from code – this prevents accidental exposure. Environment variables provide a standard, secure way to manage configuration across different environments (development, staging, production). Redwood automatically loads variables from.env
intoprocess.env
.Install Your Additional API Dependencies: Install the MessageBird Node.js SDK and Moment.js for date manipulation within your API service. Navigate to the
api
workspace:Why Use
yarn workspace api add
? Redwood uses Yarn Workspaces to manage dependencies for theweb
andapi
sides separately. This command ensures these packages are added only to theapi
side where you need them.Make Your Initial Git Commit (Recommended): Initialize a Git repository and make your first commit:
You now have a basic RedwoodJS project structure with the necessary configurations and dependencies ready for development.
2. Build Your Core Functionality (API & Database)
Design your database schema, implement booking logic with phone validation, and set up GraphQL endpoints for appointment management.
Define Your Database Schema (Prisma): Open the Prisma schema file at
api/db/schema.prisma
. Replace the default example model with yourAppointment
model:Why This Schema? This captures essential appointment details, including separate fields for the appointment time (
appointmentDt
) and the scheduled reminder time (reminderDt
). Storing themessageBirdId
lets you track the scheduled message status later if needed. Phone numbers are stored in E.164 format (international standard with country code, up to 15 digits). Store dates in UTC to avoid timezone issues.Apply Your Database Migrations: Use Prisma Migrate to create the
Appointment
table in your database based on the schema changes.create appointment model
works wellmigrate dev
? This command compares yourschema.prisma
with the database state, generates SQL migration files, applies them to your development database, and regenerates the Prisma Client. This keeps your database schema in sync with your application modelGenerate Your GraphQL SDL and Service: Redwood's generators can scaffold the basic GraphQL schema definition language (SDL) files and service implementations for CRUD operations.
This command creates/updates:
api/src/graphql/appointments.sdl.ts
: Defines the GraphQL types (Appointment
,CreateAppointmentInput
,UpdateAppointmentInput
) and operations (queries/mutations)api/src/services/appointments/appointments.ts
: Contains the business logic (resolvers) for interacting with theAppointment
modelapi/src/services/appointments/appointments.scenarios.ts
: For defining seed data for testsapi/src/services/appointments/appointments.test.ts
: Basic test file structureCustomize Your GraphQL SDL: Open
api/src/graphql/appointments.sdl.ts
. Adjust theCreateAppointmentInput
to match the fields you'll collect from the user form (excluding fields generated by the backend likereminderDt
,messageBirdId
,createdAt
).Key Changes:
CreateAppointmentInput
to acceptnumber
,date
, andtime
as strings – reflects typical HTML form input. Added comment suggesting ISO 8601@skipAuth
tocreateAppointment
mutation to allow unauthenticated users to book. Keep@requireAuth
for other operationsImplement Your Service Logic: This is where your core booking and scheduling logic lives. Open
api/src/services/appointments/appointments.ts
and modify thecreateAppointment
function significantly.validateAppointmentDateTime
warning about server-local time zone parsing and recommending UTC/ISO 8601.messagebird.lookup.read
asynchronously using Promises. Handles errors and checks if the number is mobile. Throws specific, user-friendly errors. Stores the E.164 formattednormalizedPhoneNumber
.messagebird.messages.create
, ensuringscheduledDatetime
is formatted as ISO 8601 (UTC recommended). Uses Promises for async handling.try...catch
blocks. Logs detailed errors using Redwood's logger and throws user-friendly error messages.You've now implemented your core backend logic. Your API can accept booking requests, validate data and phone numbers, schedule SMS reminders via MessageBird, and save appointments to your database.
3. Build Your Frontend Interface
Create the React components and page for users to interact with your booking system.
Generate Your Page and Component: Use Redwood generators to create the page and a reusable form component.
This creates:
web/src/pages/BookingPage/BookingPage.tsx
(and related files) accessible at the/booking
routeweb/src/components/BookingForm/BookingForm.tsx
(and related files)Implement Your Booking Form Component: Open
web/src/components/BookingForm/BookingForm.tsx
. Use Redwood's form helpers for easier state management and validation handling.@redwoodjs/forms
,@redwoodjs/router
,@redwoodjs/web
, and@redwoodjs/web/toast
. Added logger import. Commented outdate-fns
import but noted its recommendation.CREATE_APPOINTMENT_MUTATION
matching the backend SDL.useMutation
Hook: Sets up the mutation call, includingonCompleted
(for success toast, logging, navigation, form reset) andonError
(for error toast and logging) handlers.useForm
Hook: Initializes Redwood's form handling, setting validation mode toonBlur
.onSubmit
Handler:datetime-local
input string (data.appointmentDateTime
) into aDate
object. Includes a warning about potential nativeDate
parsing issues and recommends a library.Date
object intoYYYY-MM-DD
andHH:mm
strings as required by the backend mutation input. Includes a note about the fragility of string manipulation and preference for date library functions.input
object for the mutation.create
function fromuseMutation
.try...catch
block for errors during date/time processing before the mutation is sent.getMinDateTime
Helper: Calculates the earliest selectable date/time for theDatetimeLocalField
based on the backend rule (3 hours) plus a buffer (15 minutes) to prevent validation failures due to timing differences. Formats the date correctly for themin
attribute ofdatetime-local
.<Form>
,<FormError>
,<Label>
,<TextField>
,<DatetimeLocalField>
,<FieldError>
, and<Submit>
components.DatetimeLocalField
for combined date and time input, simplifying the UI.required
validation. Commented out a basic phone number pattern, emphasizing backend validation is primary.min
attribute onDatetimeLocalField
usinggetMinDateTime
.<Submit>
button is disabled during loading.Implement Your Booking Page: Open
web/src/pages/BookingPage/BookingPage.tsx
. This page simply renders theBookingForm
component.What This Does: Imports
MetaTags
for SEO and theBookingForm
. Renders a heading, descriptive text, and the form component.Add Your Routes: Ensure your routes are defined in
web/src/Routes.tsx
. Thegenerate page
command should have added the/booking
route. You might also want a success page route.bookingSuccess
which theBookingForm
attempts to navigate to. Generate and implementBookingSuccessPage
for this to work fully.Add Your Toaster: To display success/error messages from
toast
, add the<Toaster />
component, typically in your main layout file (e.g.,web/src/layouts/MainLayout/MainLayout.tsx
).Your frontend is now set up. Users can navigate to
/booking
, fill out the form, and submit it to trigger your backend logic. Feedback is provided via toasts.4. Run and Test Your Application
Start Your Development Server: Run the Redwood development server – starts both the API and web sides with hot-reloading.
Access Your Application: Open your browser and navigate to
http://localhost:8910/booking
(or the port specified in yourredwood.toml
).Test Your Booking:
yarn rw prisma studio
)Test Your Validation:
Next Steps: Enhance Your Appointment System
You've successfully built a RedwoodJS appointment booking system with automated SMS reminders powered by MessageBird. This implementation demonstrates full-stack development with phone validation, scheduled messaging, and database persistence.
Production Enhancements:
BookingSuccessPage
component with appointment summary and next stepsmessageBirdId
yarn rw generate auth ...
) for personalized appointment historydate-fns-tz
or Luxon for accurate scheduling across regions. Store all timestamps in UTCDATABASE_URL
,MESSAGEBIRD_API_KEY
, and other secretsRelated Resources: