├── .eslintrc.json ├── .gitignore ├── README.md ├── next.config.js ├── package-lock.json ├── package.json ├── pages ├── _app.js ├── api │ └── diffusion.js └── index.js ├── public ├── banana.svg └── favicon.ico └── styles ├── Home.module.css └── globals.css /.eslintrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "next/core-web-vitals" 3 | } 4 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # next.js 12 | /.next/ 13 | /out/ 14 | 15 | # production 16 | /build 17 | 18 | # misc 19 | .DS_Store 20 | *.pem 21 | 22 | # debug 23 | npm-debug.log* 24 | yarn-debug.log* 25 | yarn-error.log* 26 | .pnpm-debug.log* 27 | 28 | # local env files 29 | .env*.local 30 | 31 | # vercel 32 | .vercel 33 | 34 | # typescript 35 | *.tsbuildinfo 36 | next-env.d.ts 37 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Next.js Template for Stable Diffusion 2 | 3 | This is a [Next.js](https://nextjs.org/) template for 🍌 [Banana](https://www.banana.dev/) deployments of Stable Diffusion on serverless GPUs. Feel free to customize this frontend and make it your own! Enter your API keys in .env.local and go bananas! 🎉 4 | 5 | ## Getting Started 6 | 7 | 1. Clone this repo. 8 | 9 | 2. Create a `.env.local` file with `BANANA_API_KEY=your_api_key` and `BANANA_MODEL_KEY=your_model_key`. 10 | 11 | 3. Install dependencies: 12 | 13 | ```bash 14 | npm i 15 | ``` 16 | 17 | 4. Run the development server: 18 | 19 | ```bash 20 | npm run dev 21 | ``` 22 | 23 | 5. Open [http://localhost:3000](http://localhost:3000) with your browser to see your project! 24 | 25 | You can start editing the page by modifying `pages/index.js`. The page auto-updates as you edit the file. 26 | 27 | An [API route](https://nextjs.org/docs/api-routes/introduction) has already been created [http://localhost:3000/api/diffusion](http://localhost:3000/api/diffusion). This endpoint uses the Banana API keys you provide and can be edited at `pages/api/diffusion.js`. 28 | 29 | The `pages/api` directory is mapped to `/api/*`. Files in this directory are treated as [API routes](https://nextjs.org/docs/api-routes/introduction) instead of React pages. 30 | 31 | ## 🍌 Banana Docs 32 | 33 | To learn more about Banana, take a look at the following resources: 34 | 35 | - [Banana Documentation](https://www.banana.dev/docs) - learn about Banana's API. 36 | - [1-Click Stable Diffusion model on Banana](https://www.banana.dev/stable-diffusion) - the world's easiest way to deploy Stable Diffusion on serverless GPUs. 37 | 38 | To customize the model beyond the one-click template, see [Banana's GitHub repository](https://github.com/bananaml/serverless-template-stable-diffusion) - full credit goes to Banana for making this project possible! 39 | 40 | ## Deploy on Vercel 41 | 42 | The easiest way to deploy your Next.js app is to use the [Vercel Platform](https://vercel.com/new?utm_medium=default-template&filter=next.js&utm_source=create-next-app&utm_campaign=create-next-app-readme) from the creators of Next.js. 43 | 44 | Check out our [Next.js deployment documentation](https://nextjs.org/docs/deployment) for more details. 45 | 46 | Important note: Vercel's "free" plan has a serverless function execution timeout of 10 seconds. You may need a "pro" plan (which has a 60 second timeout) to run this in production without issues. This limitation does not affect local development. 47 | 48 | ## Use 🍌 Banana for scale. 49 | -------------------------------------------------------------------------------- /next.config.js: -------------------------------------------------------------------------------- 1 | /** @type {import('next').NextConfig} */ 2 | const nextConfig = { 3 | reactStrictMode: true, 4 | swcMinify: true, 5 | } 6 | 7 | module.exports = nextConfig 8 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "stable-diffusion-nextjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "scripts": { 6 | "dev": "next dev", 7 | "build": "next build", 8 | "start": "next start", 9 | "lint": "next lint" 10 | }, 11 | "dependencies": { 12 | "@banana-dev/banana-dev": "^4.0.0", 13 | "next": "12.3.0", 14 | "react": "18.2.0", 15 | "react-dom": "18.2.0" 16 | }, 17 | "devDependencies": { 18 | "eslint": "8.23.1", 19 | "eslint-config-next": "12.3.0" 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /pages/_app.js: -------------------------------------------------------------------------------- 1 | import '../styles/globals.css' 2 | 3 | function MyApp({ Component, pageProps }) { 4 | return 5 | } 6 | 7 | export default MyApp 8 | -------------------------------------------------------------------------------- /pages/api/diffusion.js: -------------------------------------------------------------------------------- 1 | import * as banana from "@banana-dev/banana-dev"; 2 | 3 | // Enter your Banana API keys in .env.local 4 | const apiKey = process.env.BANANA_API_KEY 5 | const modelKey = process.env.BANANA_MODEL_KEY 6 | 7 | export default async function (req, res) { 8 | 9 | const modelParameters = { 10 | "prompt": req.body.prompt 11 | } 12 | 13 | const output = await banana.run(apiKey, modelKey, modelParameters); 14 | 15 | res.status(200).json(output); 16 | 17 | } -------------------------------------------------------------------------------- /pages/index.js: -------------------------------------------------------------------------------- 1 | import Head from 'next/head' 2 | import Image from "next/image"; 3 | import styles from '../styles/Home.module.css' 4 | import { useState } from 'react'; 5 | 6 | const Home = () => { 7 | 8 | const [prompt, setPrompt] = useState(""); 9 | const [image, setImage] = useState(); 10 | const [loading, setLoading] = useState(false); 11 | 12 | const handleSubmit = async(e) => { 13 | e.preventDefault(); 14 | setLoading(true); 15 | 16 | const response = await fetch("/api/diffusion", { 17 | method: "POST", 18 | headers: { 19 | "Content-Type": "application/json", 20 | }, 21 | body: JSON.stringify({ prompt: prompt }), 22 | }); 23 | 24 | const data = await response.json(); 25 | setLoading(false); 26 | setImage(data.modelOutputs[0].image_base64); 27 | }; 28 | 29 | 30 | 31 | return ( 32 |
33 | 34 | Stable Diffusion 35 | 36 | 37 | 38 | 39 |
40 |

Next.js template available on GitHub

41 |
42 | 43 |
44 |

45 | Stable Diffusion 46 |

47 | 48 | {image ?
Generated image
49 | :

Enter a prompt to generate an image.

} 50 | 51 | {loading ?

Loading... please wait up to a minute.

: null} 52 | 53 |
54 |
55 | 56 |