Skip to content

Latest commit

 

History

15 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 

Repository files navigation

VidFlow

VidFlow is a full-stack video-sharing platform built with React, Vite, Node.js, Express, MongoDB, JWT authentication, Cloudinary uploads, and Multer.

Architecture

User -> Vercel React frontend -> Render Docker/Express API -> MongoDB Atlas / Cloudinary

The repository is split into:

  • Frontend/: Vite 5 and React 18. The production build is npm run build, and Vite writes to dist/.
  • Backend/: Express 5 with the entry point src/index.js. It starts with npm start and listens on process.env.PORT || 8000.

Node.js 22 is used by both package manifests, .nvmrc, Docker, and GitHub Actions.

Configuration

Copy the example files before running locally:

cp Backend/.env.example Backend/.env
cp Frontend/.env.example Frontend/.env

On Windows Command Prompt, use copy instead of cp.

Backend variables

Variable Purpose
PORT HTTP port. Render supplies this automatically.
NODE_ENV Use development locally and production on Render.
MONGODB_URI Complete MongoDB/Atlas connection URI. The application selects the youtube database.
CORS_ORIGIN Comma-separated allowed frontend origins, without path components.
COOKIE_SAME_SITE Usually lax locally and none for the cross-site Vercel/Render deployment.
ACCESS_TOKEN_SECRET Secret used to sign access tokens.
ACCESS_TOKEN_EXPIRY Access-token lifetime, such as 1d.
REFRESH_TOKEN_SECRET Separate secret used to sign refresh tokens.
REFRESH_TOKEN_EXPIRY Refresh-token lifetime, such as 10d.
CLOUDINARY_CLOUD_NAME Cloudinary cloud name.
CLOUDINARY_API_KEY Cloudinary API key.
CLOUDINARY_API_SECRET Cloudinary API secret.

Generate independent, long random values for both JWT secrets. Never commit a populated .env file.

Frontend variable

VITE_API_BASE_URL must contain the complete API prefix:

# Local direct connection
VITE_API_BASE_URL=http://localhost:8000/api/v1

# Vercel production
VITE_API_BASE_URL=https://YOUR-RENDER-SERVICE.onrender.com/api/v1

If the variable is omitted locally, the frontend uses /api/v1, which the Vite development proxy forwards to http://localhost:8000. The localhost proxy is development-only and is not included in the production bundle.

Local development

Backend:

cd Backend
npm ci
npm run dev

Frontend, in a second terminal:

cd Frontend
npm ci
npm run dev

Useful validation commands:

cd Backend
npm test

cd ../Frontend
npm run build
npm run preview

npm test performs a syntax check of every backend JavaScript file. There is no automated application test suite yet.

Docker

Build the backend image from the repository root:

docker build -t vidflow-backend ./Backend

Run it with secrets supplied at runtime:

docker run --name vidflow-api --env-file Backend/.env -p 8000:8000 vidflow-backend

Test the running container:

curl http://localhost:8000/api/v1/health
curl http://localhost:8000/api/v1/videos

The second request also exercises MongoDB-backed API behavior. It can fail if the Atlas network allowlist or database credentials do not permit the container's connection.

Stop and remove the local container when finished:

docker stop vidflow-api
docker rm vidflow-api

The image contains the application and production dependencies. A container is a running instance of that image. The Dockerfile describes how the image is built; .dockerignore keeps local dependencies, temporary uploads, archives, and secrets out of the build context. EXPOSE 8000 documents the intended container port but does not publish it—the -p 8000:8000 option does that. Runtime environment variables keep secrets out of immutable image layers and allow the same image to run with different configurations.

The flow is:

docker build -> execute Dockerfile layers -> create vidflow-backend image
docker run   -> create a container -> inject environment -> npm start -> Express listens

Docker Compose is intentionally omitted because the application uses hosted MongoDB Atlas and Cloudinary services.

Deploy the frontend to Vercel

  1. Push this repository to GitHub and import it in the Vercel dashboard.
  2. Set Root Directory to Frontend.
  3. Select Vite as the framework preset.
  4. Use Build Command npm run build.
  5. Use Output Directory dist.
  6. Leave the install command at npm install or set it to npm ci.
  7. Add VITE_API_BASE_URL=https://YOUR-RENDER-SERVICE.onrender.com/api/v1 for Production (and Preview if desired).
  8. Deploy, then copy the assigned https://YOUR-PROJECT.vercel.app URL from the deployment overview.

Frontend/vercel.json sends non-file routes to index.html, so refreshing React Router URLs such as /trending or /watch/:videoId does not return a Vercel 404. Changing a Vercel environment variable requires a new deployment because Vite embeds it during the build.

Deploy the backend to Render

Deploy Render first so its URL is available for the Vercel build:

  1. In Render, choose New > Web Service and connect the GitHub repository.
  2. Choose the main branch and set Root Directory to Backend.
  3. Select Docker as the language/runtime.
  4. Set Dockerfile Path to ./Dockerfile and Docker Build Context Directory to ..
  5. Do not enter a separate build command. Render builds the Dockerfile.
  6. Leave Docker Command empty so Render uses the Dockerfile's CMD ["npm", "start"].
  7. Set Health Check Path to /api/v1/health.
  8. Add the environment variables below. Do not manually set PORT; Render injects it.
  9. Deploy and copy the assigned https://YOUR-SERVICE.onrender.com URL from the service page.

Render environment variables:

NODE_ENV=production
MONGODB_URI=<complete Atlas connection URI>
CORS_ORIGIN=http://localhost:5173
COOKIE_SAME_SITE=none
ACCESS_TOKEN_SECRET=<long random secret>
ACCESS_TOKEN_EXPIRY=1d
REFRESH_TOKEN_SECRET=<different long random secret>
REFRESH_TOKEN_EXPIRY=10d
CLOUDINARY_CLOUD_NAME=<cloud name>
CLOUDINARY_API_KEY=<API key>
CLOUDINARY_API_SECRET=<API secret>

Ensure MongoDB Atlas permits connections from Render and that the database user has only the permissions VidFlow needs.

After Render provides its URL:

  1. Set Vercel's VITE_API_BASE_URL to the Render URL plus /api/v1, then deploy Vercel.
  2. Copy the final Vercel origin, for example https://vidflow.vercel.app.
  3. Replace Render's temporary CORS_ORIGIN with that exact origin and redeploy Render.
  4. If local frontend access is also needed against the hosted API, use a comma-separated value such as https://vidflow.vercel.app,http://localhost:5173.
  5. Verify the health endpoint, sign-up/login, an authenticated request, and an upload from the deployed frontend.

The API allows credentials only for configured origins. Production cookies use Secure and default to SameSite=None. The frontend also sends the access token as a Bearer token, preserving the existing authentication design. For stronger cross-browser cookie reliability in a larger production deployment, place the frontend and API on related custom domains.

GitHub Actions CI

.github/workflows/ci.yml runs on every pull request and every push to main. It creates two independent jobs:

  • Backend: restore the npm download cache, run npm ci, syntax-check all backend JavaScript, and build the Docker image.
  • Frontend: restore the npm download cache, run npm ci, and create the Vite production build.

CI means automatically integrating and validating changes in a shared repository. GitHub Actions was chosen because it is hosted alongside the GitHub code and makes the checks visible on commits and pull requests. When a pull request is opened or updated, both jobs run on clean Linux runners. If the frontend build or any other step fails, the workflow fails and should be required before merging.

npm ci installs the exact dependency versions in package-lock.json, removes any pre-existing install tree, and fails if the manifest and lockfile disagree. That makes it more deterministic than npm install for CI.

This workflow is CI, not a GitHub Actions CD pipeline. It does not deploy or receive production secrets. Vercel and Render independently watch the GitHub repository and deploy after their account-level integrations are configured. A larger system could add unit/integration tests, dependency and image scanning, immutable image publishing, protected environments, staged promotion, smoke tests, observability, and rollback automation.

Deployment verification checklist

  • https://YOUR-RENDER-SERVICE.onrender.com/api/v1/health returns HTTP 200.
  • The Vercel home page loads and direct navigation to a nested route works.
  • Browser network requests target Render, not localhost.
  • Render's CORS_ORIGIN exactly contains the Vercel origin without a trailing path.
  • Login and an authenticated API request work.
  • A media upload reaches Cloudinary and leaves no permanent local upload file.
  • GitHub Actions passes on the committed revision.
  • No populated .env file or credential is tracked.

Infrastructure files

Created:

  • .nvmrc
  • .github/workflows/ci.yml
  • Backend/.dockerignore
  • Backend/.env.example
  • Backend/Dockerfile
  • Backend/scripts/check-syntax.js
  • Frontend/.env.example
  • Frontend/vercel.json

Modified:

  • Backend/src/index.js: hosted port and interface binding.
  • Backend/src/app.js: public health endpoint.
  • Backend/src/db/index.js: safe Atlas URI handling and non-secret logging.
  • Both package.json and lockfiles: Node 22 metadata and backend validation command.
  • Both application .gitignore files: environment and archive protection.
  • README.md: local, Docker, CI, deployment, and interview documentation.

Resume wording

Before the external services are created, the accurate statement is:

Containerized the backend with Docker, configured GitHub Actions CI, and prepared the React and Express applications for Vercel and Render deployment.

After Vercel and Render have both deployed the GitHub revision and the checklist above passes, it is truthful to write:

Containerized with Docker, configured GitHub Actions CI, and deployed on Vercel and Render.

About

A full-stack video sharing platform built with React, Node.js, Express, MongoDB, JWT authentication, Cloudinary uploads, likes, comments, playlists, subscriptions, and a modern responsive UI.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages