Skip to content

Commit 0440e73

Browse files
committed
Squashed 'spaces/space-demo-template/' content from commit cc0a411
git-subtree-dir: spaces/space-demo-template git-subtree-split: cc0a411b48a7848c2706249fd0cd6769ad6a0b32
0 parents  commit 0440e73

23 files changed

+6530
-0
lines changed

.eslintrc.json

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"extends": "next/core-web-vitals"
3+
}

.gitattributes

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
*.7z filter=lfs diff=lfs merge=lfs -text
2+
*.arrow filter=lfs diff=lfs merge=lfs -text
3+
*.bin filter=lfs diff=lfs merge=lfs -text
4+
*.bz2 filter=lfs diff=lfs merge=lfs -text
5+
*.ckpt filter=lfs diff=lfs merge=lfs -text
6+
*.ftz filter=lfs diff=lfs merge=lfs -text
7+
*.gz filter=lfs diff=lfs merge=lfs -text
8+
*.h5 filter=lfs diff=lfs merge=lfs -text
9+
*.joblib filter=lfs diff=lfs merge=lfs -text
10+
*.lfs.* filter=lfs diff=lfs merge=lfs -text
11+
*.mlmodel filter=lfs diff=lfs merge=lfs -text
12+
*.model filter=lfs diff=lfs merge=lfs -text
13+
*.msgpack filter=lfs diff=lfs merge=lfs -text
14+
*.npy filter=lfs diff=lfs merge=lfs -text
15+
*.npz filter=lfs diff=lfs merge=lfs -text
16+
*.onnx filter=lfs diff=lfs merge=lfs -text
17+
*.ot filter=lfs diff=lfs merge=lfs -text
18+
*.parquet filter=lfs diff=lfs merge=lfs -text
19+
*.pb filter=lfs diff=lfs merge=lfs -text
20+
*.pickle filter=lfs diff=lfs merge=lfs -text
21+
*.pkl filter=lfs diff=lfs merge=lfs -text
22+
*.pt filter=lfs diff=lfs merge=lfs -text
23+
*.pth filter=lfs diff=lfs merge=lfs -text
24+
*.rar filter=lfs diff=lfs merge=lfs -text
25+
*.safetensors filter=lfs diff=lfs merge=lfs -text
26+
saved_model/**/* filter=lfs diff=lfs merge=lfs -text
27+
*.tar.* filter=lfs diff=lfs merge=lfs -text
28+
*.tar filter=lfs diff=lfs merge=lfs -text
29+
*.tflite filter=lfs diff=lfs merge=lfs -text
30+
*.tgz filter=lfs diff=lfs merge=lfs -text
31+
*.wasm filter=lfs diff=lfs merge=lfs -text
32+
*.xz filter=lfs diff=lfs merge=lfs -text
33+
*.zip filter=lfs diff=lfs merge=lfs -text
34+
*.zst filter=lfs diff=lfs merge=lfs -text
35+
*tfevents* filter=lfs diff=lfs merge=lfs -text

.gitignore

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
2+
3+
# dependencies
4+
/node_modules
5+
/.pnp
6+
.pnp.*
7+
.yarn/*
8+
!.yarn/patches
9+
!.yarn/plugins
10+
!.yarn/releases
11+
!.yarn/versions
12+
13+
# testing
14+
/coverage
15+
16+
# next.js
17+
/.next/
18+
/out/
19+
20+
# production
21+
/build
22+
23+
# misc
24+
.DS_Store
25+
*.pem
26+
27+
# debug
28+
npm-debug.log*
29+
yarn-debug.log*
30+
yarn-error.log*
31+
32+
# env files (can opt-in for commiting if needed)
33+
.env*
34+
35+
# vercel
36+
.vercel
37+
38+
# typescript
39+
*.tsbuildinfo
40+
next-env.d.ts

Dockerfile

Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
# Adapted from https://github.com/vercel/next.js/blob/canary/examples/with-docker/Dockerfile
2+
# For more information, see https://nextjs.org/docs/pages/building-your-application/deploying#docker-image
3+
4+
# Use a base image for building
5+
FROM node:18-slim AS base
6+
7+
# Install git
8+
RUN apt-get update && apt-get install -y git
9+
10+
# Clone the repository and navigate to the next-server folder
11+
WORKDIR /app
12+
RUN git clone https://github.com/huggingface/transformers.js-examples .
13+
14+
# Set the working directory to the next-server folder
15+
WORKDIR /app/next-server
16+
17+
# Install dependencies only when needed
18+
FROM base AS deps
19+
20+
# Install dependencies based on the preferred package manager
21+
RUN \
22+
if [ -f yarn.lock ]; then yarn --frozen-lockfile; \
23+
elif [ -f package-lock.json ]; then npm ci; \
24+
elif [ -f pnpm-lock.yaml ]; then corepack enable pnpm && pnpm i --frozen-lockfile; \
25+
else echo "Lockfile not found." && exit 1; \
26+
fi
27+
28+
# Rebuild the source code only when needed
29+
FROM base AS builder
30+
WORKDIR /app/next-server
31+
COPY --from=deps /app/next-server/node_modules ./node_modules
32+
COPY . .
33+
34+
RUN \
35+
if [ -f yarn.lock ]; then yarn run build; \
36+
elif [ -f package-lock.json ]; then npm run build; \
37+
elif [ -f pnpm-lock.yaml ]; then corepack enable pnpm && pnpm run build; \
38+
else echo "Lockfile not found." && exit 1; \
39+
fi
40+
41+
# Production image, copy all the files and run next
42+
FROM base AS runner
43+
WORKDIR /app/next-server
44+
45+
ENV NODE_ENV=production
46+
47+
RUN addgroup --system --gid 1001 nodejs
48+
RUN adduser --system --uid 1001 nextjs
49+
50+
COPY --from=builder /app/next-server/public ./public
51+
52+
# Set the correct permission for prerender cache
53+
RUN mkdir .next
54+
RUN chown nextjs:nodejs .next
55+
56+
# Automatically leverage output traces to reduce image size
57+
COPY --from=builder --chown=nextjs:nodejs /app/next-server/.next/standalone ./
58+
COPY --from=builder --chown=nextjs:nodejs /app/next-server/.next/static ./.next/static
59+
60+
USER nextjs
61+
62+
# Allow the running process to write model files to the cache folder.
63+
RUN mkdir -p /app/next-server/node_modules/@huggingface/transformers/.cache
64+
RUN chmod 777 -R /app/next-server/node_modules/@huggingface/transformers/.cache
65+
66+
EXPOSE 3000
67+
68+
ENV PORT=3000
69+
ENV HOSTNAME="0.0.0.0"
70+
CMD ["node", "server.js"]

README.md

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
---
2+
title: Topcoder Hugging Face Space Template with Docker + Next.js
3+
emoji: 🗄️
4+
colorFrom: blue
5+
colorTo: purple
6+
sdk: docker
7+
pinned: false
8+
app_port: 3000
9+
---
10+
11+
# Topcoder Hugging Face Space Template with Docker + Next.js
12+
13+
This project, bootstrapped using [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app), demonstrates how to use `@huggingface/transformers` in [Next.js](https://nextjs.org) in the Topcoder Huggig Face organization.
14+
15+
Original repo source: https://github.com/huggingface/transformers.js-examples/tree/main/next-server
16+
17+
## Instructions
18+
19+
1. Clone the repository:
20+
21+
```sh
22+
git clone https://github.com/topcoder-platform/tc-huggingface-spaces.git
23+
```
24+
25+
2. Change directory to the `spaces/space-demo-template` project:
26+
27+
```sh
28+
cd tc-huggingface-spaces/spaces/space-demo-template
29+
```
30+
31+
3. Install the dependencies:
32+
33+
```sh
34+
npm install
35+
```
36+
37+
4. Run the development server:
38+
39+
```sh
40+
npm run dev
41+
```
42+
43+
5. Open [http://localhost:3000](http://localhost:3000) with your browser to see the result.
44+
6. You can start editing the page by modifying `app/page.js` (Next.js) and `app/api/classify/route.js` (Transformers.js). The page auto-updates as you edit the file.
45+
7. Enjoy developing at Topcoder with Hugging Face.

app/api/classify/route.js

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
// https://nextjs.org/docs/app/building-your-application/routing/route-handlers
2+
3+
import { pipeline } from "@huggingface/transformers";
4+
5+
// NOTE: We attach the classifier to the global object to avoid unnecessary reloads during development
6+
const classifier = (globalThis.classifier ??= await pipeline(
7+
"text-classification",
8+
"Xenova/distilbert-base-uncased-finetuned-sst-2-english",
9+
));
10+
11+
export async function GET(request) {
12+
const text = request.nextUrl.searchParams.get("text");
13+
14+
if (!text) {
15+
return Response.json({ message: "No text provided" }, { status: 400 });
16+
}
17+
18+
const result = await classifier(text);
19+
return Response.json(result[0]);
20+
}

app/classifier.js

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
"use client";
2+
3+
import { useEffect, useState } from "react";
4+
5+
export default function Classifier() {
6+
const [text, setText] = useState("I love Topcoder!");
7+
const [result, setResult] = useState(null);
8+
9+
useEffect(() => {
10+
const params = new URLSearchParams();
11+
params.append("text", text);
12+
const url = "/api/classify?" + params.toString();
13+
14+
fetch(url)
15+
.then((res) => res.json())
16+
.then((o) => setResult(o));
17+
}, [text]);
18+
19+
return (
20+
<>
21+
<input
22+
value={text}
23+
onChange={(e) => setText(e.target.value)}
24+
className="border border-gray-300 rounded p-2 dark:bg-black dark:text-white w-full"
25+
></input>
26+
27+
<pre className="border border-gray-300 rounded p-2 dark:bg-black dark:text-white w-full min-h-[120px]">
28+
{result ? JSON.stringify(result, null, 2) : "Loading…"}
29+
</pre>
30+
</>
31+
);
32+
}

app/favicon.ico

46.8 KB
Binary file not shown.

app/fonts/GeistMonoVF.woff

66.3 KB
Binary file not shown.

app/fonts/GeistVF.woff

64.7 KB
Binary file not shown.

app/globals.css

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
@tailwind base;
2+
@tailwind components;
3+
@tailwind utilities;
4+
5+
:root {
6+
--background: #ffffff;
7+
--foreground: #171717;
8+
}
9+
10+
@media (prefers-color-scheme: dark) {
11+
:root {
12+
--background: #0a0a0a;
13+
--foreground: #ededed;
14+
}
15+
}
16+
17+
body {
18+
color: var(--foreground);
19+
background: var(--background);
20+
font-family: Arial, Helvetica, sans-serif;
21+
}

app/layout.js

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
import localFont from "next/font/local";
2+
import "./globals.css";
3+
4+
const geistSans = localFont({
5+
src: "./fonts/GeistVF.woff",
6+
variable: "--font-geist-sans",
7+
weight: "100 900",
8+
});
9+
const geistMono = localFont({
10+
src: "./fonts/GeistMonoVF.woff",
11+
variable: "--font-geist-mono",
12+
weight: "100 900",
13+
});
14+
15+
export const metadata = {
16+
title: "Topcoder Hugging Face Space Template with Docker + Next.js",
17+
description: "Generated by create next app",
18+
};
19+
20+
export default function RootLayout({ children }) {
21+
return (
22+
<html lang="en">
23+
<body
24+
className={`${geistSans.variable} ${geistMono.variable} antialiased`}
25+
>
26+
{children}
27+
</body>
28+
</html>
29+
);
30+
}

app/page.js

Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
import Image from "next/image";
2+
import Classifier from "./classifier";
3+
4+
export default function Home() {
5+
return (
6+
<div className="grid grid-rows-[20px_1fr_20px] items-center justify-items-center min-h-screen p-8 pb-20 gap-16 sm:p-8 font-[family-name:var(--font-geist-sans)]">
7+
<main className="flex flex-col gap-8 row-start-2 items-center sm:items-start">
8+
<div className="flex items-center">
9+
<Image
10+
src="/topcoder-logo.svg"
11+
alt="Topcoder logo"
12+
width={201}
13+
height={31}
14+
priority
15+
/>
16+
<span className="text-4xl font-light mx-5">&#xd7;</span>
17+
<Image
18+
src="/hf-logo.svg"
19+
alt="Hugging Face logo"
20+
width={50}
21+
height={50}
22+
priority
23+
/>
24+
<span className="text-4xl font-light mx-5">&#xd7;</span>
25+
<Image
26+
className="dark:invert"
27+
src="/next.svg"
28+
alt="Next.js logo"
29+
width={180}
30+
height={38}
31+
priority
32+
/>
33+
</div>
34+
<ol className="list-inside list-decimal text-sm text-center sm:text-left font-[family-name:var(--font-geist-mono)]">
35+
<li className="mb-2">
36+
Get started by editing{" "}
37+
<code className="bg-black/[.05] dark:bg-white/[.06] px-1 py-0.5 rounded font-semibold">
38+
app/page.js
39+
</code>
40+
.
41+
</li>
42+
<li className="mb-2">
43+
Update Transformers.js code in{" "}
44+
<code className="bg-black/[.05] dark:bg-white/[.06] px-1 py-0.5 rounded font-semibold">
45+
app/api/classify/route.js
46+
</code>
47+
.
48+
</li>
49+
<li>Save and see your changes instantly.</li>
50+
</ol>
51+
52+
<div className="flex gap-4 items-center flex-col sm:flex-row">
53+
<a
54+
className="rounded-full border border-solid border-transparent transition-colors flex items-center justify-center bg-foreground text-background gap-2 hover:bg-[#383838] dark:hover:bg-[#ccc] text-sm sm:text-base h-10 sm:h-12 px-4 sm:px-5"
55+
href="https://github.com/topcoder-platform/tc-huggingface-spaces.git"
56+
target="_blank"
57+
rel="noopener noreferrer"
58+
>
59+
Source code
60+
</a>
61+
62+
{/* <a
63+
className="rounded-full border border-solid border-black/[.08] dark:border-white/[.145] transition-colors flex items-center justify-center hover:bg-[#f2f2f2] dark:hover:bg-[#1a1a1a] hover:border-transparent text-sm sm:text-base h-10 sm:h-12 px-4 sm:px-5"
64+
href="https://huggingface.co/docs/transformers.js/index"
65+
target="_blank"
66+
rel="noopener noreferrer"
67+
>
68+
Read our docs
69+
</a> */}
70+
</div>
71+
<Classifier />
72+
</main>
73+
<footer className="row-start-3 flex gap-6 flex-wrap items-center justify-center">
74+
<a
75+
className="flex items-center gap-2 hover:underline hover:underline-offset-4"
76+
href="https://www.topcoder.com/ai-hub/competitions?utm_campaign=huggingface&utm_source=huggingface&utm_medium=Topcoder"
77+
target="_blank"
78+
rel="noopener noreferrer"
79+
>
80+
<Image
81+
aria-hidden
82+
src="/globe.svg"
83+
alt="Globe icon"
84+
width={16}
85+
height={16}
86+
/>
87+
Go to Topcoder AI Hub Competitions →
88+
</a>
89+
</footer>
90+
</div>
91+
);
92+
}

0 commit comments

Comments
 (0)