Upgrade docs
2
docs/.prettierignore
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
.next
|
||||||
|
.node_modules
|
||||||
@@ -1,3 +0,0 @@
|
|||||||
{
|
|
||||||
"plugins": ["prettier-plugin-tailwindcss"]
|
|
||||||
}
|
|
||||||
@@ -1 +0,0 @@
|
|||||||
nodejs 22.8.0
|
|
||||||
@@ -1 +1,37 @@
|
|||||||
This is where Cup's documentation lives. It's created with [Nextra](https://nextra.site).
|
# Cup Documentation
|
||||||
|
|
||||||
|
## Architecture
|
||||||
|
|
||||||
|
The docs are built with [Nextra](https://nextra.site). We use [Bun](https://bun.sh) as a package manager and Node.js as a runtime (Next.js and Bun don't play well together at the moment). Docs pages are written in [MDX](https://mdxjs.com) and any custom components are written in TypeScript with TSX.
|
||||||
|
|
||||||
|
## Development
|
||||||
|
|
||||||
|
Prerequisites:
|
||||||
|
|
||||||
|
- A recent Node.js version (22 recommended)
|
||||||
|
- [Bun](https://bun.sh)
|
||||||
|
|
||||||
|
```bash
|
||||||
|
git clone https://github.com/sergi0g/cup
|
||||||
|
cd cup/docs
|
||||||
|
bun install
|
||||||
|
```
|
||||||
|
|
||||||
|
You're ready to go!
|
||||||
|
|
||||||
|
## Scripts
|
||||||
|
|
||||||
|
The available scripts are:
|
||||||
|
|
||||||
|
- `bun dev` starts the development server. Note that making changes to MDX pages will probably require a full reload.
|
||||||
|
- `bun run build` creates a static production build, ready to be deployed.
|
||||||
|
- `bun lint` checks for errors in your code.
|
||||||
|
- `bun fmt` formats your code with Prettier, so it becomes... prettier.
|
||||||
|
|
||||||
|
## Contributing
|
||||||
|
|
||||||
|
Our documentation is always evolving, so, we constantly need to update this repository with new guides and configuration options. If you have any ideas of a guide or suggestions on how to improve them, feel free to open a pull request or create an issue. All contributions are welcome!
|
||||||
|
|
||||||
|
## License
|
||||||
|
|
||||||
|
The documentation is licensed under the MIT License. TL;DR — You are free to use, copy, modify, merge, publish, distribute, sublicense, and sell copies of the software. However, the software is provided "as is," without warranty of any kind. You must include the original license in all copies or substantial portions of the software.
|
||||||
|
|||||||
|
Before Width: | Height: | Size: 83 KiB |
|
Before Width: | Height: | Size: 87 KiB |
|
Before Width: | Height: | Size: 136 KiB |
BIN
docs/bun.lockb
Executable file
@@ -1,23 +0,0 @@
|
|||||||
import React, { ReactNode } from "react";
|
|
||||||
|
|
||||||
export function Step({
|
|
||||||
children,
|
|
||||||
title,
|
|
||||||
number,
|
|
||||||
}: {
|
|
||||||
children: ReactNode;
|
|
||||||
title: string;
|
|
||||||
number: number;
|
|
||||||
}) {
|
|
||||||
return (
|
|
||||||
<div className="mb-2 flex grow-0 items-baseline">
|
|
||||||
<p className="m-2 flex size-10 items-center justify-center rounded-full bg-neutral-100 dark:bg-neutral-900">
|
|
||||||
{number}
|
|
||||||
</p>
|
|
||||||
<div>
|
|
||||||
<p className="text-xl font-bold">{title}</p>
|
|
||||||
<div className="my-6">{children}</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
@@ -1,174 +0,0 @@
|
|||||||
import React, { useState, useEffect } from "react";
|
|
||||||
import {
|
|
||||||
IconAdjustments,
|
|
||||||
IconArrowRight,
|
|
||||||
IconBolt,
|
|
||||||
IconBraces,
|
|
||||||
IconCheck,
|
|
||||||
IconClipboard,
|
|
||||||
IconDevices,
|
|
||||||
IconFeather,
|
|
||||||
IconLockCheck,
|
|
||||||
} from "@tabler/icons-react";
|
|
||||||
import { GitHubIcon } from "../../assets/GitHubIcon";
|
|
||||||
import { GridPattern } from "../GridPattern";
|
|
||||||
import { Section } from "../Section";
|
|
||||||
import { GradientText } from "../GradientText";
|
|
||||||
import Image from "next/image";
|
|
||||||
import screenshot_light from "../../assets/screenshot_light.png";
|
|
||||||
import screenshot_dark from "../../assets/screenshot_dark.png";
|
|
||||||
import { Step } from "../Step";
|
|
||||||
import { Card } from "../Card";
|
|
||||||
|
|
||||||
export function Home() {
|
|
||||||
const [copySuccess, setCopySuccess] = useState(false);
|
|
||||||
const [isBrowser, setIsBrowser] = useState(false); // To prevent hydration mismatch
|
|
||||||
useEffect(() => setIsBrowser(true));
|
|
||||||
const handleCopy = (text: string) => {
|
|
||||||
return () => {
|
|
||||||
navigator.clipboard.writeText(text).then(() => {
|
|
||||||
setCopySuccess(true);
|
|
||||||
setTimeout(() => {
|
|
||||||
setCopySuccess(false);
|
|
||||||
}, 3000);
|
|
||||||
});
|
|
||||||
};
|
|
||||||
};
|
|
||||||
return (
|
|
||||||
<div className="home-animation" style={{ opacity: 0 }}>
|
|
||||||
<div className="relative h-full overflow-x-hidden p-4 pt-10 lg:pt-20">
|
|
||||||
<GridPattern />
|
|
||||||
<div className="mx-auto h-full min-h-svh w-full max-w-screen-xl md:h-[46rem] md:min-h-0">
|
|
||||||
<div className="grid gap-8 lg:grid-cols-2">
|
|
||||||
<div className="flex max-w-3xl flex-col gap-8">
|
|
||||||
<div className="text-6xl font-extrabold leading-none tracking-tighter sm:text-7xl">
|
|
||||||
The easiest way to manage your
|
|
||||||
<GradientText
|
|
||||||
text="container updates."
|
|
||||||
innerClassName="bg-gradient-to-r from-blue-500 to-green-500"
|
|
||||||
blur={30}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<h3 className="text-xl text-neutral-600 dark:text-neutral-400">
|
|
||||||
Cup is a small utility with a big impact. Simplify your
|
|
||||||
container management workflow with fast and efficient update
|
|
||||||
checking, a full-featured CLI and web inteface, and more.
|
|
||||||
</h3>
|
|
||||||
<div className="*:-0 mt-auto grid w-fit grid-cols-2 gap-4 *:flex *:items-center *:gap-2 *:rounded-lg *:px-3 *:py-2">
|
|
||||||
<a
|
|
||||||
href="/docs"
|
|
||||||
className="hide-focus group h-full bg-black text-white dark:bg-white dark:text-black"
|
|
||||||
>
|
|
||||||
Get started
|
|
||||||
<IconArrowRight className="ml-auto mr-1 transition-transform duration-300 ease-out group-hover:translate-x-1 group-focus:translate-x-1 dark:!text-black" />
|
|
||||||
</a>
|
|
||||||
<a
|
|
||||||
href="https://github.com/sergi0g/cup"
|
|
||||||
target="_blank"
|
|
||||||
className="hide-focus h-full text-nowrap border border-neutral-400 transition-colors duration-200 ease-in-out hover:border-neutral-600 focus:border-neutral-600 dark:border-neutral-600 hover:dark:border-neutral-400 hover:dark:shadow-sm hover:dark:shadow-neutral-600 focus:dark:border-neutral-400"
|
|
||||||
>
|
|
||||||
Star on GitHub
|
|
||||||
<GitHubIcon className="ml-auto size-4 md:size-5" />
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div className="h-full">
|
|
||||||
<div className="max-h-[33.75rem] max-w-full overflow-hidden rounded-xl border border-neutral-200 dark:border-neutral-800">
|
|
||||||
<Image
|
|
||||||
src={screenshot_light}
|
|
||||||
alt="Screenshot of Cup's web interface"
|
|
||||||
className="dark:hidden"
|
|
||||||
/>
|
|
||||||
<Image
|
|
||||||
src={screenshot_dark}
|
|
||||||
alt="Screenshot of Cup's web interface"
|
|
||||||
className="hidden dark:block"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<Section
|
|
||||||
title="Powerful at its core."
|
|
||||||
className="bg-gradient-to-r from-red-500 to-amber-500"
|
|
||||||
>
|
|
||||||
<Card
|
|
||||||
name="100% Safe Code"
|
|
||||||
icon={IconLockCheck}
|
|
||||||
description="Built with safe Rust and Typescript to ensure security and reliability."
|
|
||||||
/>
|
|
||||||
<Card
|
|
||||||
name="Lightning Fast Performance"
|
|
||||||
icon={IconBolt}
|
|
||||||
description="Heavily optimized to squeeze out every last drop of performance. Each release is extensively benchmarked and profiled so that you'll never have to stare at a loading spinner for long."
|
|
||||||
/>
|
|
||||||
<Card
|
|
||||||
name="Lightweight"
|
|
||||||
icon={IconFeather}
|
|
||||||
description="No runtimes or libraries are needed. All you need is the 5.1 MB static binary that works out of the box on any system."
|
|
||||||
/>
|
|
||||||
</Section>
|
|
||||||
<Section
|
|
||||||
title="Efficient, yet flexible."
|
|
||||||
className="bg-gradient-to-r from-blue-500 to-indigo-500"
|
|
||||||
>
|
|
||||||
<Card
|
|
||||||
name="JSON output"
|
|
||||||
description="Connect Cup to your favorite intergrations with JSON output for the CLI and an API for the server. Now go make that cool dashboard you've been dreaming of!"
|
|
||||||
icon={IconBraces}
|
|
||||||
/>
|
|
||||||
<Card
|
|
||||||
name="Both CLI and web interface"
|
|
||||||
description="Whether you prefer the command line, or the web, Cup runs wherever you choose."
|
|
||||||
icon={IconDevices}
|
|
||||||
/>
|
|
||||||
<Card
|
|
||||||
name="Configurable"
|
|
||||||
description="The simple configuration file provides you with all the tools you need to specify a custom Docker socket, manage registry connection options, choose a theme for the web interface and more."
|
|
||||||
icon={IconAdjustments}
|
|
||||||
/>
|
|
||||||
</Section>
|
|
||||||
<div className="relative py-24">
|
|
||||||
<GridPattern />
|
|
||||||
<div className="mx-auto flex w-full max-w-screen-xl flex-col items-center">
|
|
||||||
<p className="mb-8 text-center text-3xl font-bold">
|
|
||||||
Still not convinced? Try it out now!
|
|
||||||
</p>
|
|
||||||
<div>
|
|
||||||
<Step title="Open a terminal and run" number={1}>
|
|
||||||
<div className="group relative mx-auto flex max-w-screen-xl items-center rounded-lg bg-neutral-100 px-3 py-2 font-mono text-neutral-700 dark:bg-neutral-950 dark:text-neutral-300">
|
|
||||||
<p className="overflow-scroll">
|
|
||||||
docker run --rm -t -v /var/run/docker.sock:/var/run/docker.sock -p 8000:8000 ghcr.io/sergi0g/cup serve
|
|
||||||
</p>
|
|
||||||
{isBrowser &&
|
|
||||||
navigator.clipboard &&
|
|
||||||
(copySuccess ? (
|
|
||||||
<IconCheck className="absolute right-3 size-7 bg-neutral-100 pl-2 dark:bg-neutral-950" />
|
|
||||||
) : (
|
|
||||||
<button
|
|
||||||
className="duration-50 absolute right-3 bg-neutral-100 pl-2 opacity-0 transition-opacity group-hover:opacity-100 dark:bg-neutral-950"
|
|
||||||
onClick={handleCopy(
|
|
||||||
"docker run --rm -t -v /var/run/docker.sock:/var/run/docker.sock -p 8000:8000 ghcr.io/sergi0g/cup serve",
|
|
||||||
)}
|
|
||||||
>
|
|
||||||
<IconClipboard className="size-5" />
|
|
||||||
</button>
|
|
||||||
))}
|
|
||||||
</div>
|
|
||||||
</Step>
|
|
||||||
<Step number={2} title="Open the dashboard in your browser">
|
|
||||||
<p>
|
|
||||||
Visit{" "}
|
|
||||||
<a href="http://localhost:8000" className="underline">
|
|
||||||
http://localhost:8000
|
|
||||||
</a>{" "}
|
|
||||||
in your browser to try it out!
|
|
||||||
</p>
|
|
||||||
</Step>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
21
docs/eslint.config.mjs
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
import { dirname } from "path";
|
||||||
|
import { fileURLToPath } from "url";
|
||||||
|
import { FlatCompat } from "@eslint/eslintrc";
|
||||||
|
|
||||||
|
const __filename = fileURLToPath(import.meta.url);
|
||||||
|
const __dirname = dirname(__filename);
|
||||||
|
|
||||||
|
const compat = new FlatCompat({
|
||||||
|
baseDirectory: __dirname,
|
||||||
|
});
|
||||||
|
|
||||||
|
const eslintConfig = [
|
||||||
|
...compat.extends("next/core-web-vitals", "next/typescript"),
|
||||||
|
{
|
||||||
|
rules: {
|
||||||
|
"import/no-anonymous-default-export": "off",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
export default eslintConfig;
|
||||||
2
docs/next-env.d.ts
vendored
@@ -2,4 +2,4 @@
|
|||||||
/// <reference types="next/image-types/global" />
|
/// <reference types="next/image-types/global" />
|
||||||
|
|
||||||
// NOTE: This file should not be edited
|
// NOTE: This file should not be edited
|
||||||
// see https://nextjs.org/docs/pages/building-your-application/configuring/typescript for more information.
|
// see https://nextjs.org/docs/app/api-reference/config/typescript for more information.
|
||||||
|
|||||||
@@ -1,16 +0,0 @@
|
|||||||
const withNextra = require("nextra")({
|
|
||||||
theme: "nextra-theme-docs",
|
|
||||||
themeConfig: "./theme.config.jsx",
|
|
||||||
});
|
|
||||||
|
|
||||||
module.exports = withNextra({
|
|
||||||
output: "export",
|
|
||||||
images: {
|
|
||||||
unoptimized: true,
|
|
||||||
},
|
|
||||||
transpilePackages: ["geist", "framer-motion"],
|
|
||||||
basePath: process.env.NODE_ENV == "production" ? "/cup" : "",
|
|
||||||
});
|
|
||||||
|
|
||||||
// If you have other Next.js configurations, you can pass them as the parameter:
|
|
||||||
// module.exports = withNextra({ /* other next.js config */ })
|
|
||||||
19
docs/next.config.ts
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
import nextra from "nextra";
|
||||||
|
|
||||||
|
const withNextra = nextra({
|
||||||
|
defaultShowCopyCode: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
export default withNextra({
|
||||||
|
output: "export",
|
||||||
|
transpilePackages: ["geist"],
|
||||||
|
images: {
|
||||||
|
unoptimized: true,
|
||||||
|
remotePatterns: [
|
||||||
|
{
|
||||||
|
protocol: "https",
|
||||||
|
hostname: "raw.githubusercontent.com",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
});
|
||||||
@@ -1,28 +1,38 @@
|
|||||||
{
|
{
|
||||||
|
"name": "cup-docs",
|
||||||
|
"version": "0.1.0",
|
||||||
|
"private": true,
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"dev": "next",
|
"dev": "next dev",
|
||||||
"build": "next build",
|
"build": "next build",
|
||||||
"start": "next start",
|
"start": "next start",
|
||||||
"fmt": "prettier --ignore-path ../.gitignore --write ."
|
"lint": "next lint",
|
||||||
|
"fmt": "bun prettier --write ."
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@tabler/icons-react": "^3.11.0",
|
"@heroicons/react": "^2.2.0",
|
||||||
"clsx": "^2.1.1",
|
"@tabler/icons-react": "^3.29.0",
|
||||||
"geist": "^1.3.1",
|
"geist": "^1.3.1",
|
||||||
"next": "^14.2.10",
|
"next": "15.1.5",
|
||||||
"nextra": "^2.13.4",
|
"nextra": "^4.1.0",
|
||||||
"nextra-theme-docs": "^2.13.4",
|
"nextra-theme-docs": "^4.1.0",
|
||||||
"react": "^18.3.1",
|
"react": "^19.0.0",
|
||||||
"react-dom": "^18.3.1"
|
"react-dom": "^19.0.0",
|
||||||
|
"tailwind-merge": "^2.6.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@types/node": "22.10.2",
|
"@eslint/eslintrc": "^3.2.0",
|
||||||
"autoprefixer": "^10.4.19",
|
"@tailwindcss/postcss": "^4.0.1",
|
||||||
"postcss": "^8.4.39",
|
"@types/node": "^22.10.7",
|
||||||
|
"@types/react": "^19.0.7",
|
||||||
|
"@types/react-dom": "^19.0.3",
|
||||||
|
"eslint": "^9.18.0",
|
||||||
|
"eslint-config-next": "15.1.5",
|
||||||
|
"postcss": "^8.5.1",
|
||||||
"prettier": "^3.4.2",
|
"prettier": "^3.4.2",
|
||||||
"prettier-plugin-tailwindcss": "^0.6.9",
|
"prettier-plugin-tailwindcss": "^0.6.11",
|
||||||
"tailwindcss": "^3.4.5",
|
"tailwindcss": "^4.0.1",
|
||||||
"typescript": "5.7.2"
|
"typescript": "^5.7.3"
|
||||||
},
|
},
|
||||||
"packageManager": "pnpm@9.10.0+sha512.73a29afa36a0d092ece5271de5177ecbf8318d454ecd701343131b8ebc0c1a91c487da46ab77c8e596d6acf1461e3594ced4becedf8921b074fbd8653ed7051c"
|
"packageManager": "yarn@1.22.22+sha512.a6b2f7906b721bba3d67d4aff083df04dad64c399707841b7acf00f6b133b7ac24255f2652fa22ae3534329dc6180534e98d17432037ff6fd140556e2bb3137e"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,12 +0,0 @@
|
|||||||
import "../styles.css";
|
|
||||||
import "nextra-theme-docs/style.css";
|
|
||||||
import { GeistSans } from "geist/font/sans";
|
|
||||||
|
|
||||||
export default function App({ Component, pageProps }) {
|
|
||||||
return (
|
|
||||||
<main className={GeistSans.className}>
|
|
||||||
<Component {...pageProps} />
|
|
||||||
</main>
|
|
||||||
);
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,45 +0,0 @@
|
|||||||
import React from "react";
|
|
||||||
import Document, { Html, Head, Main, NextScript } from "next/document";
|
|
||||||
import type { DocumentInitialProps, DocumentContext } from "next/document";
|
|
||||||
|
|
||||||
class DocumentProMax extends Document {
|
|
||||||
static async getInitialProps(
|
|
||||||
ctx: DocumentContext,
|
|
||||||
): Promise<DocumentInitialProps> {
|
|
||||||
const initialProps = await Document.getInitialProps(ctx);
|
|
||||||
|
|
||||||
return initialProps;
|
|
||||||
}
|
|
||||||
|
|
||||||
render() {
|
|
||||||
return (
|
|
||||||
<Html lang="en">
|
|
||||||
<Head>
|
|
||||||
<link
|
|
||||||
rel="apple-touch-icon"
|
|
||||||
sizes="180x180"
|
|
||||||
href="/apple-touch-icon.png"
|
|
||||||
/>
|
|
||||||
<link rel="icon" type="image/svg+xml" href="/favicon.svg" />
|
|
||||||
<link rel="icon" type="image/x-icon" href="/favicon.ico" />
|
|
||||||
<meta
|
|
||||||
name="theme-color"
|
|
||||||
media="(prefers-color-scheme: light)"
|
|
||||||
content="#ffffff"
|
|
||||||
/>
|
|
||||||
<meta
|
|
||||||
name="theme-color"
|
|
||||||
media="(prefers-color-scheme: dark)"
|
|
||||||
content="#111111"
|
|
||||||
/>
|
|
||||||
</Head>
|
|
||||||
<body>
|
|
||||||
<Main />
|
|
||||||
<NextScript />
|
|
||||||
</body>
|
|
||||||
</Html>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export default DocumentProMax;
|
|
||||||
@@ -1,14 +0,0 @@
|
|||||||
{
|
|
||||||
"docs": {
|
|
||||||
"title": "Documentation",
|
|
||||||
"type": "page"
|
|
||||||
},
|
|
||||||
"index": {
|
|
||||||
"type": "page",
|
|
||||||
"title": "Cup - The easiest way to manage your container updates",
|
|
||||||
"display": "hidden",
|
|
||||||
"theme": {
|
|
||||||
"layout": "raw"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,23 +0,0 @@
|
|||||||
{
|
|
||||||
"index": {
|
|
||||||
"title": "Introduction"
|
|
||||||
},
|
|
||||||
"installation": {
|
|
||||||
"title": "Installation"
|
|
||||||
},
|
|
||||||
"configuration": {
|
|
||||||
"title": "Configuration"
|
|
||||||
},
|
|
||||||
"usage": {
|
|
||||||
"title": "Usage"
|
|
||||||
},
|
|
||||||
"community-resources": {
|
|
||||||
"title": "Community Resources"
|
|
||||||
},
|
|
||||||
"nightly": {
|
|
||||||
"title": "Using the latest version"
|
|
||||||
},
|
|
||||||
"contributing": {
|
|
||||||
"title": "Contributing"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,8 +0,0 @@
|
|||||||
{
|
|
||||||
"docker": {
|
|
||||||
"title": "With Docker"
|
|
||||||
},
|
|
||||||
"binary": {
|
|
||||||
"title": "As a binary"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,11 +0,0 @@
|
|||||||
import { IconServer, IconTerminal } from "@tabler/icons-react";
|
|
||||||
import { Cards, Card } from "nextra-theme-docs";
|
|
||||||
|
|
||||||
# Usage
|
|
||||||
|
|
||||||
You can use Cup in 2 different ways. As a CLI or as a server. You can learn more about each mode in its corresponding page
|
|
||||||
|
|
||||||
<Cards>
|
|
||||||
<Card icon={<IconTerminal />} title="CLI" href="/docs/usage/cli" />
|
|
||||||
<Card icon={<IconServer />} title="Server" href="/docs/usage/server" />
|
|
||||||
</Cards>
|
|
||||||
@@ -1,57 +0,0 @@
|
|||||||
import { Callout } from "nextra-theme-docs";
|
|
||||||
|
|
||||||
# Server
|
|
||||||
|
|
||||||
The server provides the `cup serve` command.
|
|
||||||
|
|
||||||
## Basic usage
|
|
||||||
|
|
||||||
```ansi
|
|
||||||
$ cup serve
|
|
||||||
[2m2024-07-17T09:08:38.724922Z [0m [32m INFO [0m [2mxitca_server::net [0m [2m: [0m Started Tcp listening on: Some(0.0.0.0:8000)
|
|
||||||
[2m2024-07-17T09:08:38.725076Z [0m [33m WARN [0m [2mxitca_server::server::future [0m [2m: [0m ServerFuture::wait is called from within tokio context. It would block current thread from handling async tasks
|
|
||||||
[2m2024-07-17T09:08:38.725248Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-0
|
|
||||||
[2m2024-07-17T09:08:38.725343Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-1
|
|
||||||
[2m2024-07-17T09:08:38.725580Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-2
|
|
||||||
[2m2024-07-17T09:08:38.725607Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-3
|
|
||||||
[2m2024-07-17T09:08:41.390783Z [0m [32m INFO [0m [1mrequest [0m [1m{ [0m [3mmethod [0m [2m= [0mGET [3muri [0m [2m= [0m/ [1m} [0m [2m: [0m [2mon_request [0m [2m: [0m serving request
|
|
||||||
[2m2024-07-17T09:08:41.390905Z [0m [32m INFO [0m [1mrequest [0m [1m{ [0m [3mmethod [0m [2m= [0mGET [3muri [0m [2m= [0m/ [1m} [0m [2m: [0m [2mon_response [0m [2m: [0m sending response
|
|
||||||
```
|
|
||||||
|
|
||||||
This will launch the server on port `8000`. To access it, visit `http://<YOUR_IP>:8000` (replace `<YOUR_IP>` with the IP address of the machine running Cup.)
|
|
||||||
|
|
||||||
<Callout>
|
|
||||||
The URL `http://<YOUR_IP>:8000/api/v3/json` is also available for usage with integrations.
|
|
||||||
</Callout>
|
|
||||||
|
|
||||||
## Use a different port
|
|
||||||
|
|
||||||
Pass the `-p` argument with the port you want to use
|
|
||||||
|
|
||||||
```ansi
|
|
||||||
$ cup serve -p 9000
|
|
||||||
[2m2024-07-17T09:08:38.724922Z [0m [32m INFO [0m [2mxitca_server::net [0m [2m: [0m Started Tcp listening on: Some(0.0.0.0:9000)
|
|
||||||
[2m2024-07-17T09:08:38.725076Z [0m [33m WARN [0m [2mxitca_server::server::future [0m [2m: [0m ServerFuture::wait is called from within tokio context. It would block current thread from handling async tasks
|
|
||||||
[2m2024-07-17T09:08:38.725248Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-0
|
|
||||||
[2m2024-07-17T09:08:38.725343Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-1
|
|
||||||
[2m2024-07-17T09:08:38.725580Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-2
|
|
||||||
[2m2024-07-17T09:08:38.725607Z [0m [32m INFO [0m [2mxitca_server::worker [0m [2m: [0m Started xitca-server-worker-3
|
|
||||||
[2m2024-07-17T09:08:41.390783Z [0m [32m INFO [0m [1mrequest [0m [1m{ [0m [3mmethod [0m [2m= [0mGET [3muri [0m [2m= [0m/ [1m} [0m [2m: [0m [2mon_request [0m [2m: [0m serving request
|
|
||||||
[2m2024-07-17T09:08:41.390905Z [0m [32m INFO [0m [1mrequest [0m [1m{ [0m [3mmethod [0m [2m= [0mGET [3muri [0m [2m= [0m/ [1m} [0m [2m: [0m [2mon_response [0m [2m: [0m sending response
|
|
||||||
```
|
|
||||||
|
|
||||||
## Usage with Docker
|
|
||||||
|
|
||||||
If you're using the Docker image, just replace all occurences of `cup` in the examples with `docker run -tv /var/run/docker.sock:/var/run/docker.sock -p <PORT>:<PORT> ghcr.io/sergi0g/cup`, where `<PORT>` is the port Cup will be using.
|
|
||||||
|
|
||||||
For example, this:
|
|
||||||
|
|
||||||
```bash /serve -p 9000/
|
|
||||||
$ cup serve -p 9000
|
|
||||||
```
|
|
||||||
|
|
||||||
becomes:
|
|
||||||
|
|
||||||
```bash /serve -p 9000/
|
|
||||||
$ docker run -tv /var/run/docker.sock:/var/run/docker.sock -p 9000:9000 ghcr.io/sergi0g/cup serve -p 9000
|
|
||||||
```
|
|
||||||
5680
docs/pnpm-lock.yaml
generated
@@ -1,6 +0,0 @@
|
|||||||
module.exports = {
|
|
||||||
plugins: {
|
|
||||||
tailwindcss: {},
|
|
||||||
autoprefixer: {},
|
|
||||||
},
|
|
||||||
};
|
|
||||||
8
docs/postcss.config.mjs
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
/** @type {import('postcss-load-config').Config} */
|
||||||
|
const config = {
|
||||||
|
plugins: {
|
||||||
|
"@tailwindcss/postcss": {},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
export default config;
|
||||||
|
Before Width: | Height: | Size: 136 KiB After Width: | Height: | Size: 136 KiB |
27
docs/src/app/[...mdxPath]/page.tsx
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
import { generateStaticParamsFor, importPage } from "nextra/pages";
|
||||||
|
import { useMDXComponents } from "@/mdx-components";
|
||||||
|
|
||||||
|
export const generateStaticParams = generateStaticParamsFor("mdxPath");
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
params: { mdxPath: string[] };
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function generateMetadata(props: Props) {
|
||||||
|
const params = await props.params;
|
||||||
|
const { metadata } = await importPage(params.mdxPath);
|
||||||
|
return metadata;
|
||||||
|
}
|
||||||
|
/* eslint-disable-next-line */
|
||||||
|
const Wrapper = useMDXComponents({}).wrapper;
|
||||||
|
|
||||||
|
export default async function Page(props: Props) {
|
||||||
|
const params = await props.params;
|
||||||
|
const result = await importPage(params.mdxPath);
|
||||||
|
const { default: MDXContent, toc, metadata } = result;
|
||||||
|
return (
|
||||||
|
<Wrapper toc={toc} metadata={metadata}>
|
||||||
|
<MDXContent {...props} params={params} />
|
||||||
|
</Wrapper>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
Before Width: | Height: | Size: 5.7 KiB After Width: | Height: | Size: 5.7 KiB |
|
Before Width: | Height: | Size: 176 KiB After Width: | Height: | Size: 176 KiB |
|
Before Width: | Height: | Size: 107 KiB After Width: | Height: | Size: 107 KiB |
BIN
docs/src/app/assets/blue_theme.png
Normal file
|
After Width: | Height: | Size: 242 KiB |
|
Before Width: | Height: | Size: 136 KiB After Width: | Height: | Size: 136 KiB |
BIN
docs/src/app/assets/hero-dark.png
Normal file
|
After Width: | Height: | Size: 232 KiB |
BIN
docs/src/app/assets/hero-mobile-dark.png
Normal file
|
After Width: | Height: | Size: 240 KiB |
BIN
docs/src/app/assets/hero-mobile.png
Normal file
|
After Width: | Height: | Size: 242 KiB |
BIN
docs/src/app/assets/hero.png
Normal file
|
After Width: | Height: | Size: 233 KiB |
252
docs/src/app/components/Browser.tsx
Normal file
23
docs/src/app/components/Button.tsx
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
import Link from "next/link";
|
||||||
|
import { ReactNode } from "react";
|
||||||
|
import { twMerge } from "tailwind-merge";
|
||||||
|
|
||||||
|
interface ButtonProps {
|
||||||
|
href: string;
|
||||||
|
className?: string;
|
||||||
|
children: ReactNode;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default function Button({ href, className, children }: ButtonProps) {
|
||||||
|
return (
|
||||||
|
<Link
|
||||||
|
href={href}
|
||||||
|
className={twMerge(
|
||||||
|
"flex items-center justify-center rounded-md border border-transparent px-8 py-3 text-base font-medium no-underline transition-colors duration-200 md:text-lg md:leading-6",
|
||||||
|
className,
|
||||||
|
)}
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
</Link>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -1,20 +1,17 @@
|
|||||||
import { ReactNode, createElement } from "react";
|
import { Icon as IconType } from "@tabler/icons-react";
|
||||||
|
|
||||||
export function Card({
|
export function Card({
|
||||||
name,
|
name,
|
||||||
icon,
|
icon: Icon,
|
||||||
description,
|
description,
|
||||||
}: {
|
}: {
|
||||||
name: string;
|
name: string;
|
||||||
icon: ReactNode;
|
icon: IconType;
|
||||||
description: string;
|
description: string;
|
||||||
}) {
|
}) {
|
||||||
const iconElement = createElement(icon, {
|
|
||||||
className: "text-black size-7 dark:text-white inline mr-2",
|
|
||||||
});
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
{iconElement}
|
<Icon className="text-black size-7 dark:text-white inline mr-2" />
|
||||||
<span className="align-middle text-2xl font-bold text-black dark:text-white">
|
<span className="align-middle text-2xl font-bold text-black dark:text-white">
|
||||||
{name}
|
{name}
|
||||||
</span>
|
</span>
|
||||||
28
docs/src/app/components/CopyableCode.tsx
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
"use client";
|
||||||
|
|
||||||
|
import { IconCopy, IconCopyCheck } from "@tabler/icons-react";
|
||||||
|
import { useState } from "react";
|
||||||
|
|
||||||
|
export default function CopyableCode({ children }: { children: string }) {
|
||||||
|
const [success, setSuccess] = useState(false);
|
||||||
|
const handleClick = () => {
|
||||||
|
navigator.clipboard.writeText(children);
|
||||||
|
setSuccess(true);
|
||||||
|
setTimeout(() => setSuccess(false), 3000);
|
||||||
|
};
|
||||||
|
return (
|
||||||
|
<div className="relative rounded-md xl:w-auto">
|
||||||
|
<button
|
||||||
|
className="hover:bg-black/10 dark:hover:bg-black/60 flex w-full items-center justify-center gap-4 rounded-md border border-black/10 bg-black/5 px-8 py-3 font-mono text-sm font-medium text-black/70 transition-colors duration-200 md:px-10 md:py-3 md:text-base md:leading-6 dark:border-white/15 dark:bg-black dark:text-gray-300 backdrop-blur-md"
|
||||||
|
onClick={handleClick}
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
{success ? (
|
||||||
|
<IconCopyCheck className="stroke-black/40 dark:stroke-white/50" />
|
||||||
|
) : (
|
||||||
|
<IconCopy className="stroke-black/40 dark:stroke-white/50" />
|
||||||
|
)}
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -14,7 +14,9 @@ export function GradientText({
|
|||||||
}) {
|
}) {
|
||||||
return (
|
return (
|
||||||
<div className={clsx("relative", className)}>
|
<div className={clsx("relative", className)}>
|
||||||
<p className={clsx("bg-clip-text text-transparent", innerClassName)}>
|
<p
|
||||||
|
className={clsx("bg-clip-text text-transparent w-fit", innerClassName)}
|
||||||
|
>
|
||||||
{text}
|
{text}
|
||||||
</p>
|
</p>
|
||||||
<p
|
<p
|
||||||
@@ -16,8 +16,8 @@ export function GridPattern() {
|
|||||||
width={SIZE}
|
width={SIZE}
|
||||||
height={SIZE}
|
height={SIZE}
|
||||||
patternUnits="userSpaceOnUse"
|
patternUnits="userSpaceOnUse"
|
||||||
x={0}
|
x={-1}
|
||||||
y={0}
|
y={-1}
|
||||||
>
|
>
|
||||||
<path
|
<path
|
||||||
d={`M.5 ${SIZE}V.5H${SIZE}`}
|
d={`M.5 ${SIZE}V.5H${SIZE}`}
|
||||||
29
docs/src/app/components/Head.tsx
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
"use client";
|
||||||
|
|
||||||
|
import { Head as NextraHead } from "nextra/components";
|
||||||
|
|
||||||
|
export function Head() {
|
||||||
|
return (
|
||||||
|
<NextraHead>
|
||||||
|
<link rel="icon" type="image/svg+xml" href="/favicon.svg" />
|
||||||
|
<link rel="icon" type="image/x-icon" href="/favicon.ico" />
|
||||||
|
<meta
|
||||||
|
name="theme-color"
|
||||||
|
media="(prefers-color-scheme: light)"
|
||||||
|
content="#ffffff"
|
||||||
|
/>
|
||||||
|
<meta
|
||||||
|
name="theme-color"
|
||||||
|
media="(prefers-color-scheme: dark)"
|
||||||
|
content="#111111"
|
||||||
|
/>
|
||||||
|
<meta
|
||||||
|
name="og:image"
|
||||||
|
content="https://raw.githubusercontent.com/sergi0g/cup/main/docs/public/cup-og.png"
|
||||||
|
/>
|
||||||
|
<meta name="twitter:card" content="summary_large_image" />
|
||||||
|
<meta name="twitter:site" content="https://cup.sergi0g.dev" />
|
||||||
|
<meta name="apple-mobile-web-app-title" content="Cup" />
|
||||||
|
</NextraHead>
|
||||||
|
);
|
||||||
|
}
|
||||||
57
docs/src/app/components/Logo.tsx
Normal file
@@ -0,0 +1,57 @@
|
|||||||
|
export default function Logo() {
|
||||||
|
return (
|
||||||
|
<svg
|
||||||
|
viewBox="0 0 128 128"
|
||||||
|
style={{ height: "calc(var(--nextra-navbar-height) * 0.6)" }}
|
||||||
|
>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#A6CFD6" }}
|
||||||
|
d="M65.12,17.55c-17.6-0.53-34.75,5.6-34.83,14.36c-0.04,5.2,1.37,18.6,3.62,48.68s2.25,33.58,3.5,34.95
|
||||||
|
c1.25,1.37,10.02,8.8,25.75,8.8s25.93-6.43,26.93-8.05c0.48-0.78,1.83-17.89,3.5-37.07c1.81-20.84,3.91-43.9,3.99-45.06
|
||||||
|
C97.82,30.66,94.2,18.43,65.12,17.55z"
|
||||||
|
/>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#DCEDF6" }}
|
||||||
|
d="M41.4,45.29c-0.12,0.62,1.23,24.16,2.32,27.94c1.99,6.92,9.29,7.38,10.23,4.16
|
||||||
|
c0.9-3.07-0.38-29.29-0.38-29.29s-3.66-0.3-6.43-0.84C44,46.63,41.4,45.29,41.4,45.29z"
|
||||||
|
/>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#6CA4AE" }}
|
||||||
|
d="M33.74,32.61c-0.26,8.83,20.02,12.28,30.19,12.22c13.56-0.09,29.48-4.29,29.8-11.7
|
||||||
|
S79.53,21.1,63.35,21.1C49.6,21.1,33.96,25.19,33.74,32.61z"
|
||||||
|
/>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#DC0D27" }}
|
||||||
|
d="M84.85,13.1c-0.58,0.64-9.67,30.75-9.67,30.75s2.01-0.33,4-0.79c2.63-0.61,3.76-1.06,3.76-1.06
|
||||||
|
s7.19-22.19,7.64-23.09c0.45-0.9,21.61-7.61,22.31-7.93c0.7-0.32,1.39-0.4,1.46-0.78c0.06-0.38-2.34-6.73-3.11-6.73
|
||||||
|
C110.47,3.47,86.08,11.74,84.85,13.1z"
|
||||||
|
/>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#8A1F0F" }}
|
||||||
|
d="M110.55,7.79c1.04,2.73,2.8,3.09,3.55,2.77c0.45-0.19,1.25-1.84,0.01-4.47
|
||||||
|
c-0.99-2.09-2.17-2.74-2.93-2.61C110.42,3.6,109.69,5.53,110.55,7.79z"
|
||||||
|
/>
|
||||||
|
<g>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#8A1F0F" }}
|
||||||
|
d="M91.94,18.34c-0.22,0-0.44-0.11-0.58-0.3l-3.99-5.77c-0.22-0.32-0.14-0.75,0.18-0.97
|
||||||
|
c0.32-0.22,0.76-0.14,0.97,0.18l3.99,5.77c0.22,0.32,0.14,0.75-0.18,0.97C92.21,18.3,92.07,18.34,91.94,18.34z"
|
||||||
|
/>
|
||||||
|
</g>
|
||||||
|
<g>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#8A1F0F" }}
|
||||||
|
d="M90.28,19.43c-0.18,0-0.35-0.07-0.49-0.2l-5.26-5.12c-0.28-0.27-0.28-0.71-0.01-0.99
|
||||||
|
c0.27-0.28,0.71-0.28,0.99-0.01l5.26,5.12c0.28,0.27,0.28,0.71,0.01,0.99C90.64,19.36,90.46,19.43,90.28,19.43z"
|
||||||
|
/>
|
||||||
|
</g>
|
||||||
|
<g>
|
||||||
|
<path
|
||||||
|
style={{ fill: "#8A1F0F" }}
|
||||||
|
d="M89.35,21.22c-0.12,0-0.25-0.03-0.36-0.1l-5.6-3.39c-0.33-0.2-0.44-0.63-0.24-0.96
|
||||||
|
c0.2-0.33,0.63-0.44,0.96-0.24l5.6,3.39c0.33,0.2,0.44,0.63,0.24,0.96C89.82,21.1,89.59,21.22,89.35,21.22z"
|
||||||
|
/>
|
||||||
|
</g>
|
||||||
|
</svg>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -11,7 +11,7 @@ export function Section({
|
|||||||
children: ReactNode;
|
children: ReactNode;
|
||||||
}) {
|
}) {
|
||||||
return (
|
return (
|
||||||
<div className="border-t bg-neutral-50 py-32 dark:border-t-neutral-600/30 dark:bg-neutral-950">
|
<div className="border-t border-t-neutral-300 bg-neutral-50 py-32 dark:border-t-neutral-600/30 dark:bg-neutral-950">
|
||||||
<div className="mx-auto w-full max-w-screen-xl">
|
<div className="mx-auto w-full max-w-screen-xl">
|
||||||
<GradientText
|
<GradientText
|
||||||
text={title}
|
text={title}
|
||||||
136
docs/src/app/components/pages/home.tsx
Normal file
@@ -0,0 +1,136 @@
|
|||||||
|
import React from "react";
|
||||||
|
import "./styles.css";
|
||||||
|
|
||||||
|
import CopyableCode from "../CopyableCode";
|
||||||
|
import { Browser } from "../Browser";
|
||||||
|
import { Card } from "../Card";
|
||||||
|
import {
|
||||||
|
IconAdjustments,
|
||||||
|
IconArrowRight,
|
||||||
|
IconBolt,
|
||||||
|
IconBraces,
|
||||||
|
IconDevices,
|
||||||
|
IconFeather,
|
||||||
|
IconLockCheck,
|
||||||
|
} from "@tabler/icons-react";
|
||||||
|
import { GitHubIcon } from "nextra/icons";
|
||||||
|
import { GridPattern } from "../GridPattern";
|
||||||
|
import { GradientText } from "../GradientText";
|
||||||
|
import { Section } from "../Section";
|
||||||
|
import { Steps } from "nextra/components";
|
||||||
|
import Link from "next/link";
|
||||||
|
|
||||||
|
export default async function Home() {
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<div className="relative">
|
||||||
|
<GridPattern />
|
||||||
|
<div className="px-4 pt-16 pb-8 sm:pt-24 lg:px-8">
|
||||||
|
<div className="flex w-full flex-col items-center justify-between">
|
||||||
|
<div>
|
||||||
|
<h1 className="mx-auto max-w-2xl text-center text-6xl leading-none font-extrabold tracking-tighter text-black sm:text-7xl dark:text-white">
|
||||||
|
The easiest way to manage your
|
||||||
|
<GradientText
|
||||||
|
text="container updates."
|
||||||
|
className="mx-auto w-fit"
|
||||||
|
innerClassName="bg-linear-to-r/oklch from-blue-500 to-green-500"
|
||||||
|
blur={30}
|
||||||
|
/>
|
||||||
|
</h1>
|
||||||
|
<h3 className="mx-auto mt-6 max-w-3xl text-center text-xl leading-tight font-medium text-gray-400">
|
||||||
|
Cup is a small utility with a big impact. Simplify your
|
||||||
|
container management workflow with fast and efficient update
|
||||||
|
checking, a full-featured CLI and web inteface, and more.
|
||||||
|
</h3>
|
||||||
|
</div>
|
||||||
|
<div className="mt-8 grid w-fit grid-cols-2 gap-4 *:flex *:items-center *:gap-2 *:rounded-lg *:px-3 *:py-2">
|
||||||
|
<Link
|
||||||
|
href="/docs"
|
||||||
|
className="hide-focus group h-full bg-black text-white dark:bg-white dark:text-black"
|
||||||
|
>
|
||||||
|
Get started
|
||||||
|
<IconArrowRight className="ml-auto mr-1 transition-transform duration-300 ease-out group-hover:translate-x-1 group-focus:translate-x-1 dark:!text-black" />
|
||||||
|
</Link>
|
||||||
|
<a
|
||||||
|
href="https://github.com/sergi0g/cup"
|
||||||
|
target="_blank"
|
||||||
|
className="hide-focus h-full text-nowrap border border-neutral-400 transition-colors duration-200 ease-in-out hover:border-neutral-600 focus:border-neutral-600 dark:border-neutral-600 hover:dark:border-neutral-400 hover:dark:shadow-sm hover:dark:shadow-neutral-600 focus:dark:border-neutral-400"
|
||||||
|
>
|
||||||
|
Star on GitHub
|
||||||
|
<GitHubIcon className="ml-auto size-4 md:size-5" />
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div className="py-10 flex translate-y-32 justify-center" id="hero">
|
||||||
|
<Browser />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<Section
|
||||||
|
title="Powerful at its core."
|
||||||
|
className="bg-gradient-to-r from-red-500 to-amber-500"
|
||||||
|
>
|
||||||
|
<Card
|
||||||
|
name="100% Safe Code"
|
||||||
|
icon={IconLockCheck}
|
||||||
|
description="Built with safe Rust and Typescript to ensure security and reliability."
|
||||||
|
/>
|
||||||
|
<Card
|
||||||
|
name="Lightning Fast Performance"
|
||||||
|
icon={IconBolt}
|
||||||
|
description="Heavily optimized to squeeze out every last drop of performance. Each release is extensively benchmarked and profiled so that you'll never have to stare at a loading spinner for long."
|
||||||
|
/>
|
||||||
|
<Card
|
||||||
|
name="Lightweight"
|
||||||
|
icon={IconFeather}
|
||||||
|
description="No runtimes or libraries are needed. All you need is the 5.1 MB static binary that works out of the box on any system."
|
||||||
|
/>
|
||||||
|
</Section>
|
||||||
|
<Section
|
||||||
|
title="Efficient, yet flexible."
|
||||||
|
className="bg-gradient-to-r from-blue-500 to-indigo-500"
|
||||||
|
>
|
||||||
|
<Card
|
||||||
|
name="JSON output"
|
||||||
|
description="Connect Cup to your favorite intergrations with JSON output for the CLI and an API for the server. Now go make that cool dashboard you've been dreaming of!"
|
||||||
|
icon={IconBraces}
|
||||||
|
/>
|
||||||
|
<Card
|
||||||
|
name="Both CLI and web interface"
|
||||||
|
description="Whether you prefer the command line, or the web, Cup runs wherever you choose."
|
||||||
|
icon={IconDevices}
|
||||||
|
/>
|
||||||
|
<Card
|
||||||
|
name="Configurable"
|
||||||
|
description="The simple configuration file provides you with all the tools you need to specify a custom Docker socket, manage registry connection options, choose a theme for the web interface and more."
|
||||||
|
icon={IconAdjustments}
|
||||||
|
/>
|
||||||
|
</Section>
|
||||||
|
<div className="relative py-24 border-t border-t-neutral-300 dark:border-t-neutral-600/30 text-black dark:text-white">
|
||||||
|
<GridPattern />
|
||||||
|
<div className="mx-auto flex w-full max-w-screen-xl flex-col items-center">
|
||||||
|
<p className="mb-8 text-center text-3xl font-bold">
|
||||||
|
Still not convinced? Try it out now!
|
||||||
|
</p>
|
||||||
|
<div>
|
||||||
|
<Steps>
|
||||||
|
<h3 className="mb-2">Open a terminal and run</h3>
|
||||||
|
<CopyableCode>
|
||||||
|
docker run --rm -t -v /var/run/docker.sock:/var/run/docker.sock
|
||||||
|
-p 8000:8000 ghcr.io/sergi0g/cup serve
|
||||||
|
</CopyableCode>
|
||||||
|
<h3 className="mb-2">Open the dashboard in your browser</h3>
|
||||||
|
<p>
|
||||||
|
Visit{" "}
|
||||||
|
<a href="http://localhost:8000" className="underline">
|
||||||
|
http://localhost:8000
|
||||||
|
</a>{" "}
|
||||||
|
in your browser to try it out!
|
||||||
|
</p>
|
||||||
|
</Steps>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
36
docs/src/app/components/pages/styles.css
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
/* Override nextra styles restricting width */
|
||||||
|
|
||||||
|
:root {
|
||||||
|
--nextra-content-width: unset !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
header.nextra-navbar {
|
||||||
|
--nextra-content-width: 90rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
article {
|
||||||
|
padding-inline: 0 !important;
|
||||||
|
padding-top: 0 !important;
|
||||||
|
padding-bottom: 0 !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
article div.x\:mt-16:last-child:empty {
|
||||||
|
margin-top: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#hero {
|
||||||
|
animation-name: hero;
|
||||||
|
animation-duration: 1500ms;
|
||||||
|
animation-delay: 500ms;
|
||||||
|
animation-timing-function: ease-in-out;
|
||||||
|
animation-fill-mode: forwards;
|
||||||
|
}
|
||||||
|
|
||||||
|
@keyframes hero {
|
||||||
|
from {
|
||||||
|
translate: 0 8rem;
|
||||||
|
}
|
||||||
|
to {
|
||||||
|
translate: 0 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Before Width: | Height: | Size: 1.0 KiB After Width: | Height: | Size: 1.0 KiB |
17
docs/src/app/globals.css
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
@import "tailwindcss";
|
||||||
|
|
||||||
|
@variant dark (&:where(.dark, .dark *));
|
||||||
|
|
||||||
|
.nextra-card .tabler-icon:hover {
|
||||||
|
color: rgb(17 24 39 / var(--tw-text-opacity));
|
||||||
|
}
|
||||||
|
.nextra-card .tabler-icon {
|
||||||
|
color: rgb(55 65 81 / var(--tw-text-opacity));
|
||||||
|
}
|
||||||
|
.nextra-card .tabler-icon:is(.dark *) {
|
||||||
|
color: rgb(229 229 229 / var(--tw-text-opacity));
|
||||||
|
}
|
||||||
|
|
||||||
|
.nextra-card .tabler-icon:is(.dark *):hover {
|
||||||
|
color: rgb(250 250 250 / var(--tw-text-opacity));
|
||||||
|
}
|
||||||
55
docs/src/app/layout.tsx
Normal file
@@ -0,0 +1,55 @@
|
|||||||
|
import type { Metadata } from "next";
|
||||||
|
import { Footer, Layout, Navbar, ThemeSwitch } from "nextra-theme-docs";
|
||||||
|
import { getPageMap } from "nextra/page-map";
|
||||||
|
import { GeistSans } from "geist/font/sans";
|
||||||
|
import "nextra-theme-docs/style.css";
|
||||||
|
import "./globals.css";
|
||||||
|
import { Head } from "./components/Head";
|
||||||
|
import Logo from "./components/Logo";
|
||||||
|
|
||||||
|
export const metadata: Metadata = {
|
||||||
|
title: "Cup",
|
||||||
|
description: "The easiest way to manage your container updates",
|
||||||
|
};
|
||||||
|
|
||||||
|
const logo = (
|
||||||
|
<div className="flex items-center">
|
||||||
|
<Logo />
|
||||||
|
<h1 className="ml-2 font-bold">Cup</h1>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
|
||||||
|
const navbar = (
|
||||||
|
<Navbar logo={logo} projectLink="https://github.com/sergi0g/cup">
|
||||||
|
<ThemeSwitch lite className="cursor-pointer" />
|
||||||
|
</Navbar>
|
||||||
|
);
|
||||||
|
|
||||||
|
const footer = <Footer> </Footer>;
|
||||||
|
|
||||||
|
export default async function RootLayout({
|
||||||
|
children,
|
||||||
|
}: Readonly<{
|
||||||
|
children: React.ReactNode;
|
||||||
|
}>) {
|
||||||
|
return (
|
||||||
|
<html
|
||||||
|
lang="en"
|
||||||
|
dir="ltr"
|
||||||
|
suppressHydrationWarning
|
||||||
|
className={`${GeistSans.className} antialiased`}
|
||||||
|
>
|
||||||
|
<Head />
|
||||||
|
<body>
|
||||||
|
<Layout
|
||||||
|
navbar={navbar}
|
||||||
|
pageMap={await getPageMap()}
|
||||||
|
footer={footer}
|
||||||
|
docsRepositoryBase="https://github.com/sergi0g/cup"
|
||||||
|
>
|
||||||
|
<div>{children}</div>
|
||||||
|
</Layout>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -3,6 +3,6 @@ title: Cup - The easiest way to manage your container updates
|
|||||||
description: Simple, fast, efficient Docker image update checking
|
description: Simple, fast, efficient Docker image update checking
|
||||||
---
|
---
|
||||||
|
|
||||||
import { Home } from "../components/pages/Home";
|
import Home from "@/app/components/pages/home";
|
||||||
|
|
||||||
<Home />
|
<Home />
|
||||||
17
docs/src/content/_meta.ts
Normal file
@@ -0,0 +1,17 @@
|
|||||||
|
export default {
|
||||||
|
index: {
|
||||||
|
theme: {
|
||||||
|
sidebar: false,
|
||||||
|
toc: false,
|
||||||
|
breadcrumb: false,
|
||||||
|
pagination: false,
|
||||||
|
timestamp: false,
|
||||||
|
layout: "full",
|
||||||
|
},
|
||||||
|
display: "hidden",
|
||||||
|
},
|
||||||
|
docs: {
|
||||||
|
type: "page",
|
||||||
|
title: "Documentation",
|
||||||
|
},
|
||||||
|
};
|
||||||
5
docs/src/content/docs/_meta.ts
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
export default {
|
||||||
|
installation: {},
|
||||||
|
usage: {},
|
||||||
|
configuration: {},
|
||||||
|
};
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
import Image from "next/image";
|
import Image from "next/image";
|
||||||
import widget1 from "../../../assets/350767810-42eccc89-bdfd-426a-a113-653abe7483d8.png";
|
import widget1 from "@/app/assets/350767810-42eccc89-bdfd-426a-a113-653abe7483d8.png";
|
||||||
import widget2 from "../../../assets/358304960-e9f26767-51f7-4b5a-8b74-a5811019497b.jpeg";
|
import widget2 from "@/app/assets/358304960-e9f26767-51f7-4b5a-8b74-a5811019497b.jpeg";
|
||||||
|
|
||||||
# Homepage Widget
|
# Homepage Widget
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
import { Callout } from "nextra-theme-docs";
|
import { Callout } from "nextra/components";
|
||||||
|
|
||||||
# Authentication
|
# Authentication
|
||||||
|
|
||||||
@@ -1,4 +1,8 @@
|
|||||||
import { Steps, Callout, Card, Cards } from "nextra-theme-docs";
|
---
|
||||||
|
asIndexPage: true
|
||||||
|
---
|
||||||
|
|
||||||
|
import { Steps, Callout, Cards } from "nextra/components";
|
||||||
import {
|
import {
|
||||||
IconPaint,
|
IconPaint,
|
||||||
IconLockOpen,
|
IconLockOpen,
|
||||||
@@ -14,13 +18,13 @@ Sometimes, there may be a need to specify a custom docker socket. Cup provides t
|
|||||||
|
|
||||||
For example, if using Podman, you might do
|
For example, if using Podman, you might do
|
||||||
|
|
||||||
```
|
```bash
|
||||||
$ cup -s /run/user/1000/podman/podman.sock check
|
$ cup -s /run/user/1000/podman/podman.sock check
|
||||||
```
|
```
|
||||||
|
|
||||||
This option is also available in the configuration file and it's best to put it there.
|
This option is also available in the configuration file and it's best to put it there.
|
||||||
|
|
||||||
<Card
|
<Cards.Card
|
||||||
icon={<IconPlug />}
|
icon={<IconPlug />}
|
||||||
title="Custom Docker socket"
|
title="Custom Docker socket"
|
||||||
href="/docs/configuration/socket"
|
href="/docs/configuration/socket"
|
||||||
@@ -40,17 +44,21 @@ If you're running with Docker, you can create a `cup.json` in the directory you'
|
|||||||
Follow the guides below to customize your `cup.json`
|
Follow the guides below to customize your `cup.json`
|
||||||
|
|
||||||
<Cards>
|
<Cards>
|
||||||
<Card
|
<Cards.Card
|
||||||
icon={<IconKey />}
|
icon={<IconKey />}
|
||||||
title="Authentication"
|
title="Authentication"
|
||||||
href="/docs/configuration/authentication"
|
href="/docs/configuration/authentication"
|
||||||
/>
|
/>
|
||||||
<Card
|
<Cards.Card
|
||||||
icon={<IconLockOpen />}
|
icon={<IconLockOpen />}
|
||||||
title="Insecure registries"
|
title="Insecure registries"
|
||||||
href="/docs/configuration/insecure-registries"
|
href="/docs/configuration/insecure-registries"
|
||||||
/>
|
/>
|
||||||
<Card icon={<IconPaint />} title="Theme" href="/docs/configuration/theme" />
|
<Cards.Card
|
||||||
|
icon={<IconPaint />}
|
||||||
|
title="Theme"
|
||||||
|
href="/docs/configuration/theme"
|
||||||
|
/>
|
||||||
</Cards>
|
</Cards>
|
||||||
|
|
||||||
Here's a full example:
|
Here's a full example:
|
||||||
@@ -67,8 +75,10 @@ Here's a full example:
|
|||||||
```
|
```
|
||||||
|
|
||||||
<Callout>
|
<Callout>
|
||||||
If you want autocompletions and error checking for your editor, there is a JSON schema available.
|
If you want autocompletions and error checking for your editor, there is a
|
||||||
Use it by adding a `"$schema": "https://raw.githubusercontent.com/sergi0g/cup/main/cup.schema.json"` entry in your `cup.json` file.
|
JSON schema available. Use it by adding a `"$schema":
|
||||||
|
"https://raw.githubusercontent.com/sergi0g/cup/main/cup.schema.json"` entry in
|
||||||
|
your `cup.json` file.
|
||||||
</Callout>
|
</Callout>
|
||||||
|
|
||||||
### Run Cup with the new configuration file
|
### Run Cup with the new configuration file
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
import { Callout } from "nextra-theme-docs";
|
import { Callout } from "nextra/components";
|
||||||
|
|
||||||
# Insecure registries
|
# Insecure registries
|
||||||
|
|
||||||
@@ -27,6 +27,6 @@ Here's what it looks like:
|
|||||||
|
|
||||||
<Callout emoji="⚠️">
|
<Callout emoji="⚠️">
|
||||||
When configuring an insecure registry that doesn't run on port 80, don't
|
When configuring an insecure registry that doesn't run on port 80, don't
|
||||||
forget to specify the port (i.e. use `localhost:5000` instead of `localhost` if your
|
forget to specify the port (i.e. use `localhost:5000` instead of `localhost`
|
||||||
registry is running on port `5000`)
|
if your registry is running on port `5000`)
|
||||||
</Callout>
|
</Callout>
|
||||||
@@ -1,8 +1,8 @@
|
|||||||
import { Callout } from "nextra-theme-docs";
|
import { Callout } from "nextra/components";
|
||||||
import Image from "next/image";
|
import Image from "next/image";
|
||||||
|
|
||||||
import blue from "../../../assets/blue_theme.png";
|
import blue from "@/app/assets/blue_theme.png";
|
||||||
import neutral from "../../../assets/neutral_theme.png";
|
import neutral from "@/app/assets/hero-dark.png";
|
||||||
|
|
||||||
# Theme
|
# Theme
|
||||||
|
|
||||||
@@ -27,3 +27,5 @@ Here's an example:
|
|||||||
// Other options
|
// Other options
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
Note that the difference between the 2 themes is almost impossible to perceive when your system is in light mode.
|
||||||
@@ -1,3 +1,5 @@
|
|||||||
|
import { Steps } from "nextra/components";
|
||||||
|
|
||||||
# Contributing
|
# Contributing
|
||||||
|
|
||||||
First of all, thanks for taking time to contribute to Cup! This guide will help you set up a development environment and make your first contribution.
|
First of all, thanks for taking time to contribute to Cup! This guide will help you set up a development environment and make your first contribution.
|
||||||
@@ -10,10 +12,26 @@ Requirements:
|
|||||||
- Rust (usually installed from https://rustup.rs/)
|
- Rust (usually installed from https://rustup.rs/)
|
||||||
- Node.js 22+ and Bun 1+
|
- Node.js 22+ and Bun 1+
|
||||||
|
|
||||||
1. Fork the repository. This is where you'll be pushing your changes before you create a pull request. Make sure to _create a new branch_ for your changes.
|
<Steps>
|
||||||
2. Clone your fork with `git clone https://github.com/<YOUR_USERNAME>/cup` (if you use SSH, `git clone git@github.com:<YOUR_USERNAME>/cup`) and open your editor
|
### Fork the repository
|
||||||
3. Switch to your newly created branch (e.g. if your branch is called `improve-logging`, run `git checkout improve-logging`)
|
This is where you'll be pushing your changes before you create a pull request. Make sure to _create a new branch_ for your changes.
|
||||||
4. Run `bun install` in `web/` and `./build.sh` to set up the frontend
|
### Clone your fork
|
||||||
|
```bash
|
||||||
|
git clone https://github.com/<YOUR_USERNAME>/cup
|
||||||
|
```
|
||||||
|
If you use SSH:
|
||||||
|
```bash
|
||||||
|
git clone git@github.com:<YOUR_USERNAME>/cup`)
|
||||||
|
```
|
||||||
|
### Switch to your newly created branch (e.g. if your branch is called `improve-logging`, run `git checkout improve-logging`)
|
||||||
|
### Set up the frontend
|
||||||
|
```bash
|
||||||
|
$ cd web
|
||||||
|
$ bun install
|
||||||
|
$ cd ..
|
||||||
|
$ ./build.sh
|
||||||
|
```
|
||||||
|
</Steps>
|
||||||
|
|
||||||
You're ready to go!
|
You're ready to go!
|
||||||
|
|
||||||
@@ -1,11 +1,11 @@
|
|||||||
import Image from "next/image";
|
import Image from "next/image";
|
||||||
import cup from "../../assets/cup.gif";
|
import cup from "@/app/assets/cup.gif";
|
||||||
import { Cards, Card } from "nextra-theme-docs";
|
import { Cards } from "nextra/components";
|
||||||
import { IconBrandDocker, IconPackage } from "@tabler/icons-react";
|
import { IconBrandDocker, IconPackage } from "@tabler/icons-react";
|
||||||
|
|
||||||
# Introduction
|
# Introduction
|
||||||
|
|
||||||
<Image src={cup} unoptimized />
|
<Image src={cup} alt="Animated GIF of Cup's CLI in action" unoptimized />
|
||||||
|
|
||||||
Cup is a lightweight alternative to [What's up Docker?](https://github.com/getwud/wud) written in Rust.
|
Cup is a lightweight alternative to [What's up Docker?](https://github.com/getwud/wud) written in Rust.
|
||||||
|
|
||||||
@@ -21,12 +21,12 @@ Cup is a lightweight alternative to [What's up Docker?](https://github.com/getwu
|
|||||||
# Installation
|
# Installation
|
||||||
|
|
||||||
<Cards>
|
<Cards>
|
||||||
<Card
|
<Cards.Card
|
||||||
icon={<IconBrandDocker />}
|
icon={<IconBrandDocker />}
|
||||||
title="With Docker"
|
title="With Docker"
|
||||||
href="/docs/installation/docker"
|
href="/docs/installation/docker"
|
||||||
/>
|
/>
|
||||||
<Card
|
<Cards.Card
|
||||||
icon={<IconPackage />}
|
icon={<IconPackage />}
|
||||||
title="As a binary"
|
title="As a binary"
|
||||||
href="/docs/installation/binary"
|
href="/docs/installation/binary"
|
||||||
8
docs/src/content/docs/installation/_meta.ts
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
export default {
|
||||||
|
docker: {
|
||||||
|
title: "With Docker",
|
||||||
|
},
|
||||||
|
binary: {
|
||||||
|
title: "As a binary",
|
||||||
|
},
|
||||||
|
};
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
import { Callout, Card, Steps } from "nextra-theme-docs";
|
import { Callout, Cards, Steps } from "nextra/components";
|
||||||
import { IconFileDescription } from "@tabler/icons-react";
|
import { IconFileDescription } from "@tabler/icons-react";
|
||||||
|
|
||||||
# As a binary
|
# As a binary
|
||||||
@@ -25,4 +25,4 @@ Move the binary you downloaded to a directory in your path. You can usually get
|
|||||||
That's it! Cup is ready to be used. Head over to the Usage page to get started.
|
That's it! Cup is ready to be used. Head over to the Usage page to get started.
|
||||||
|
|
||||||
<br />
|
<br />
|
||||||
<Card icon={<IconFileDescription />} title="Usage" href="/docs/usage" />
|
<Cards.Card icon={<IconFileDescription />} title="Usage" href="/docs/usage" />
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
import { Callout, Card } from "nextra-theme-docs";
|
import { Callout, Cards } from "nextra/components";
|
||||||
import { IconFileDescription } from "@tabler/icons-react";
|
import { IconFileDescription } from "@tabler/icons-react";
|
||||||
|
|
||||||
# With Docker
|
# With Docker
|
||||||
@@ -16,12 +16,12 @@ $ docker pull ghcr.io/sergi0g/cup
|
|||||||
```
|
```
|
||||||
|
|
||||||
<Callout emoji="⚠️">
|
<Callout emoji="⚠️">
|
||||||
If you aren't in the `docker` group, please ensure you run all commands as a
|
If you aren't a member of the `docker` group, please ensure you run all
|
||||||
user who does. In most cases, you'll just need to prefix the `docker` commands
|
commands as a user who is. In most cases, you'll just need to prefix the
|
||||||
with `sudo`
|
`docker` commands with `sudo`
|
||||||
</Callout>
|
</Callout>
|
||||||
|
|
||||||
That's it! Cup is ready to be used. Head over to the Usage page to get started.
|
That's it! Cup is ready to be used. Head over to the Usage page to get started.
|
||||||
|
|
||||||
<br />
|
<br />
|
||||||
<Card icon={<IconFileDescription />} title="Usage" href="/docs/usage" />
|
<Cards.Card icon={<IconFileDescription />} title="Usage" href="/docs/usage" />
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
import { Callout } from "nextra-theme-docs";
|
import { Callout } from "nextra/components";
|
||||||
|
|
||||||
# Using the latest version
|
# Using the latest version
|
||||||
|
|
||||||
@@ -13,7 +13,7 @@ Cup's nightly version always contains the latest changes in the main branch.
|
|||||||
breaking changes or a bad commit and it may not work properly. Install nightly
|
breaking changes or a bad commit and it may not work properly. Install nightly
|
||||||
only if you know what you are doing. These instructions will assume you have
|
only if you know what you are doing. These instructions will assume you have
|
||||||
the technical know-how to follow them. If you do not, please use the stable
|
the technical know-how to follow them. If you do not, please use the stable
|
||||||
release
|
release!
|
||||||
</Callout>
|
</Callout>
|
||||||
|
|
||||||
## With Docker
|
## With Docker
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
import Image from "next/image";
|
import Image from "next/image";
|
||||||
import cup from "../../../assets/cup.gif";
|
import cup from "@/app/assets/cup.gif";
|
||||||
|
|
||||||
# CLI
|
# CLI
|
||||||
|
|
||||||
15
docs/src/content/docs/usage/index.mdx
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
---
|
||||||
|
asIndexPage: true
|
||||||
|
---
|
||||||
|
|
||||||
|
import { IconServer, IconTerminal } from "@tabler/icons-react";
|
||||||
|
import { Cards } from "nextra/components";
|
||||||
|
|
||||||
|
# Usage
|
||||||
|
|
||||||
|
You can use Cup in 2 different ways. As a CLI or as a server. You can learn more about each mode in its corresponding page
|
||||||
|
|
||||||
|
<Cards>
|
||||||
|
<Cards.Card icon={<IconTerminal />} title="CLI" href="/docs/usage/cli" />
|
||||||
|
<Cards.Card icon={<IconServer />} title="Server" href="/docs/usage/server" />
|
||||||
|
</Cards>
|
||||||
55
docs/src/content/docs/usage/server.mdx
Normal file
@@ -0,0 +1,55 @@
|
|||||||
|
import { Callout } from "nextra/components";
|
||||||
|
|
||||||
|
# Server
|
||||||
|
|
||||||
|
The server provides the `cup serve` command.
|
||||||
|
|
||||||
|
## Basic usage
|
||||||
|
|
||||||
|
```ansi
|
||||||
|
$ cup serve
|
||||||
|
[36;1mINFO [0mStarting server, please wait...
|
||||||
|
[36;1mINFO [0m✨ Checked 8 images in 8862ms
|
||||||
|
[36;1mINFO [0mReady to start!
|
||||||
|
[94;1mHTTP [0m[32mGET[0m / [32m200[0m in 0ms
|
||||||
|
[94;1mHTTP [0m[32mGET[0m /assets/index.js [32m200[0m in 3ms
|
||||||
|
[94;1mHTTP [0m[32mGET[0m /assets/index.css [32m200[0m in 0ms
|
||||||
|
[94;1mHTTP [0m[32mGET[0m /api/v3/json [32m200[0m in 0ms
|
||||||
|
```
|
||||||
|
|
||||||
|
This will launch the server on port `8000`. To access it, visit `http://<YOUR_IP>:8000` (replace `<YOUR_IP>` with the IP address of the machine running Cup.)
|
||||||
|
|
||||||
|
<Callout>
|
||||||
|
The URL `http://<YOUR_IP>:8000/api/v3/json` is also available for usage with integrations.
|
||||||
|
</Callout>
|
||||||
|
|
||||||
|
## Use a different port
|
||||||
|
|
||||||
|
Pass the `-p` argument with the port you want to use
|
||||||
|
|
||||||
|
```ansi
|
||||||
|
$ cup serve -p 9000
|
||||||
|
[36;1mINFO [0mStarting server, please wait...
|
||||||
|
[36;1mINFO [0m✨ Checked 8 images in 8862ms
|
||||||
|
[36;1mINFO [0mReady to start!
|
||||||
|
[94;1mHTTP [0m[32mGET[0m / [32m200[0m in 0ms
|
||||||
|
[94;1mHTTP [0m[32mGET[0m /assets/index.js [32m200[0m in 3ms
|
||||||
|
[94;1mHTTP [0m[32mGET[0m /assets/index.css [32m200[0m in 0ms
|
||||||
|
[94;1mHTTP [0m[32mGET[0m /api/v3/json [32m200[0m in 0ms
|
||||||
|
```
|
||||||
|
|
||||||
|
## Usage with Docker
|
||||||
|
|
||||||
|
If you're using the Docker image, just replace all occurences of `cup` in the examples with `docker run -tv /var/run/docker.sock:/var/run/docker.sock -p <PORT>:<PORT> ghcr.io/sergi0g/cup`, where `<PORT>` is the port Cup will be using.
|
||||||
|
|
||||||
|
For example, this:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
$ cup serve -p 9000
|
||||||
|
```
|
||||||
|
|
||||||
|
becomes:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
$ docker run -tv /var/run/docker.sock:/var/run/docker.sock -p 9000:9000 ghcr.io/sergi0g/cup serve -p 9000
|
||||||
|
```
|
||||||
13
docs/src/mdx-components.ts
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
import { useMDXComponents as getThemeComponents } from "nextra-theme-docs";
|
||||||
|
import { MDXComponents } from "nextra/mdx-components";
|
||||||
|
|
||||||
|
// Get the default MDX components
|
||||||
|
const themeComponents = getThemeComponents();
|
||||||
|
|
||||||
|
// Merge components
|
||||||
|
export function useMDXComponents(components: MDXComponents) {
|
||||||
|
return {
|
||||||
|
...themeComponents,
|
||||||
|
...components,
|
||||||
|
};
|
||||||
|
}
|
||||||
@@ -1,54 +0,0 @@
|
|||||||
@tailwind base;
|
|
||||||
@tailwind components;
|
|
||||||
@tailwind utilities;
|
|
||||||
|
|
||||||
.nextra-card .tabler-icon:hover {
|
|
||||||
color: rgb(17 24 39 / var(--tw-text-opacity));
|
|
||||||
}
|
|
||||||
.nextra-card .tabler-icon {
|
|
||||||
color: rgb(55 65 81 / var(--tw-text-opacity));
|
|
||||||
}
|
|
||||||
.nextra-card .tabler-icon:is(.dark *) {
|
|
||||||
color: rgb(229 229 229 / var(--tw-text-opacity));
|
|
||||||
}
|
|
||||||
|
|
||||||
.nextra-card .tabler-icon:is(.dark *):hover {
|
|
||||||
color: rgb(250 250 250 / var(--tw-text-opacity));
|
|
||||||
}
|
|
||||||
|
|
||||||
.home-animation {
|
|
||||||
animation-name: fade-in;
|
|
||||||
animation-delay: 300ms;
|
|
||||||
animation-duration: 500ms;
|
|
||||||
animation-fill-mode: forwards;
|
|
||||||
animation-timing-function: ease-in;
|
|
||||||
}
|
|
||||||
|
|
||||||
@keyframes fade-in {
|
|
||||||
from {
|
|
||||||
opacity: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
to {
|
|
||||||
opacity: 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
.hide-focus:focus {
|
|
||||||
outline: none;
|
|
||||||
box-shadow: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.home-pattern {
|
|
||||||
background-color: white;
|
|
||||||
background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='40' height='40' viewBox='0 0 40 40'%3E%3Cg fill-rule='evenodd'%3E%3Cg fill='%23000000' fill-opacity='0.15'%3E%3Cpath d='M0 38.59l2.83-2.83 1.41 1.41L1.41 40H0v-1.41zM0 1.4l2.83 2.83 1.41-1.41L1.41 0H0v1.41zM38.59 40l-2.83-2.83 1.41-1.41L40 38.59V40h-1.41zM40 1.41l-2.83 2.83-1.41-1.41L38.59 0H40v1.41zM20 18.6l2.83-2.83 1.41 1.41L21.41 20l2.83 2.83-1.41 1.41L20 21.41l-2.83 2.83-1.41-1.41L18.59 20l-2.83-2.83 1.41-1.41L20 18.59z'/%3E%3C/g%3E%3C/g%3E%3C/svg%3E");
|
|
||||||
mask-image: radial-gradient(ellipse at top, white, transparent);
|
|
||||||
translate: 0 -0.5rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
.home-pattern:is(.dark *) {
|
|
||||||
background-color: #111111;
|
|
||||||
background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='40' height='40' viewBox='0 0 40 40'%3E%3Cg fill-rule='evenodd'%3E%3Cg fill='%23ffffff' fill-opacity='0.1'%3E%3Cpath d='M0 38.59l2.83-2.83 1.41 1.41L1.41 40H0v-1.41zM0 1.4l2.83 2.83 1.41-1.41L1.41 0H0v1.41zM38.59 40l-2.83-2.83 1.41-1.41L40 38.59V40h-1.41zM40 1.41l-2.83 2.83-1.41-1.41L38.59 0H40v1.41zM20 18.6l2.83-2.83 1.41 1.41L21.41 20l2.83 2.83-1.41 1.41L20 21.41l-2.83 2.83-1.41-1.41L18.59 20l-2.83-2.83 1.41-1.41L20 18.59z'/%3E%3C/g%3E%3C/g%3E%3C/svg%3E");
|
|
||||||
mask-image: radial-gradient(ellipse at top, #111111, transparent);
|
|
||||||
translate: 0 -0.5rem;
|
|
||||||
}
|
|
||||||
@@ -1,9 +0,0 @@
|
|||||||
/** @type {import('tailwindcss').Config} */
|
|
||||||
module.exports = {
|
|
||||||
darkMode: "class",
|
|
||||||
content: ["theme.config.jsx", "components/**/*.tsx"],
|
|
||||||
theme: {
|
|
||||||
extend: {},
|
|
||||||
},
|
|
||||||
plugins: [],
|
|
||||||
};
|
|
||||||
@@ -1,116 +0,0 @@
|
|||||||
import { ThemeSwitch } from "nextra-theme-docs";
|
|
||||||
import { useRouter } from "next/router";
|
|
||||||
import { useConfig } from "nextra-theme-docs";
|
|
||||||
|
|
||||||
export default {
|
|
||||||
docsRepositoryBase: "https://github.com/sergi0g/cup/tree/main/docs",
|
|
||||||
useNextSeoProps() {
|
|
||||||
const { asPath } = useRouter();
|
|
||||||
if (asPath !== "/") {
|
|
||||||
return {
|
|
||||||
titleTemplate: "Cup – %s",
|
|
||||||
};
|
|
||||||
} else {
|
|
||||||
return {
|
|
||||||
titleTemplate: "%s"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
head: () => {
|
|
||||||
const { asPath } = useRouter();
|
|
||||||
const { frontMatter } = useConfig();
|
|
||||||
const url = "https://sergi0g.github.io/cup/docs/" + `/${asPath}`;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<>
|
|
||||||
<meta property="og:url" content={url} />
|
|
||||||
<meta property="og:title" content={frontMatter.title || "Cup"} />
|
|
||||||
<meta
|
|
||||||
property="og:description"
|
|
||||||
content={
|
|
||||||
frontMatter.description ||
|
|
||||||
"The easiest way to manage your container updates"
|
|
||||||
}
|
|
||||||
/>
|
|
||||||
</>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
logo: (
|
|
||||||
<div className="flex items-center">
|
|
||||||
<Logo />
|
|
||||||
<h1 className="ml-2 font-bold">Cup</h1>
|
|
||||||
</div>
|
|
||||||
),
|
|
||||||
logoLink: "/",
|
|
||||||
project: {
|
|
||||||
link: "https://github.com/sergi0g/cup/",
|
|
||||||
},
|
|
||||||
navbar: {
|
|
||||||
extraContent: <ThemeSwitch lite className="[&_span]:hidden" />,
|
|
||||||
},
|
|
||||||
toc: {
|
|
||||||
backToTop: true,
|
|
||||||
},
|
|
||||||
footer: {
|
|
||||||
text: null,
|
|
||||||
},
|
|
||||||
navigation: false,
|
|
||||||
};
|
|
||||||
|
|
||||||
function Logo() {
|
|
||||||
return (
|
|
||||||
<svg
|
|
||||||
viewBox="0 0 128 128"
|
|
||||||
style={{ height: "calc(var(--nextra-navbar-height) * 0.6)" }}
|
|
||||||
>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#A6CFD6" }}
|
|
||||||
d="M65.12,17.55c-17.6-0.53-34.75,5.6-34.83,14.36c-0.04,5.2,1.37,18.6,3.62,48.68s2.25,33.58,3.5,34.95
|
|
||||||
c1.25,1.37,10.02,8.8,25.75,8.8s25.93-6.43,26.93-8.05c0.48-0.78,1.83-17.89,3.5-37.07c1.81-20.84,3.91-43.9,3.99-45.06
|
|
||||||
C97.82,30.66,94.2,18.43,65.12,17.55z"
|
|
||||||
/>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#DCEDF6" }}
|
|
||||||
d="M41.4,45.29c-0.12,0.62,1.23,24.16,2.32,27.94c1.99,6.92,9.29,7.38,10.23,4.16
|
|
||||||
c0.9-3.07-0.38-29.29-0.38-29.29s-3.66-0.3-6.43-0.84C44,46.63,41.4,45.29,41.4,45.29z"
|
|
||||||
/>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#6CA4AE" }}
|
|
||||||
d="M33.74,32.61c-0.26,8.83,20.02,12.28,30.19,12.22c13.56-0.09,29.48-4.29,29.8-11.7
|
|
||||||
S79.53,21.1,63.35,21.1C49.6,21.1,33.96,25.19,33.74,32.61z"
|
|
||||||
/>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#DC0D27" }}
|
|
||||||
d="M84.85,13.1c-0.58,0.64-9.67,30.75-9.67,30.75s2.01-0.33,4-0.79c2.63-0.61,3.76-1.06,3.76-1.06
|
|
||||||
s7.19-22.19,7.64-23.09c0.45-0.9,21.61-7.61,22.31-7.93c0.7-0.32,1.39-0.4,1.46-0.78c0.06-0.38-2.34-6.73-3.11-6.73
|
|
||||||
C110.47,3.47,86.08,11.74,84.85,13.1z"
|
|
||||||
/>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#8A1F0F" }}
|
|
||||||
d="M110.55,7.79c1.04,2.73,2.8,3.09,3.55,2.77c0.45-0.19,1.25-1.84,0.01-4.47
|
|
||||||
c-0.99-2.09-2.17-2.74-2.93-2.61C110.42,3.6,109.69,5.53,110.55,7.79z"
|
|
||||||
/>
|
|
||||||
<g>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#8A1F0F" }}
|
|
||||||
d="M91.94,18.34c-0.22,0-0.44-0.11-0.58-0.3l-3.99-5.77c-0.22-0.32-0.14-0.75,0.18-0.97
|
|
||||||
c0.32-0.22,0.76-0.14,0.97,0.18l3.99,5.77c0.22,0.32,0.14,0.75-0.18,0.97C92.21,18.3,92.07,18.34,91.94,18.34z"
|
|
||||||
/>
|
|
||||||
</g>
|
|
||||||
<g>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#8A1F0F" }}
|
|
||||||
d="M90.28,19.43c-0.18,0-0.35-0.07-0.49-0.2l-5.26-5.12c-0.28-0.27-0.28-0.71-0.01-0.99
|
|
||||||
c0.27-0.28,0.71-0.28,0.99-0.01l5.26,5.12c0.28,0.27,0.28,0.71,0.01,0.99C90.64,19.36,90.46,19.43,90.28,19.43z"
|
|
||||||
/>
|
|
||||||
</g>
|
|
||||||
<g>
|
|
||||||
<path
|
|
||||||
style={{ fill: "#8A1F0F" }}
|
|
||||||
d="M89.35,21.22c-0.12,0-0.25-0.03-0.36-0.1l-5.6-3.39c-0.33-0.2-0.44-0.63-0.24-0.96
|
|
||||||
c0.2-0.33,0.63-0.44,0.96-0.24l5.6,3.39c0.33,0.2,0.44,0.63,0.24,0.96C89.82,21.1,89.59,21.22,89.35,21.22z"
|
|
||||||
/>
|
|
||||||
</g>
|
|
||||||
</svg>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
@@ -1,18 +1,27 @@
|
|||||||
{
|
{
|
||||||
"compilerOptions": {
|
"compilerOptions": {
|
||||||
|
"target": "ES2017",
|
||||||
"lib": ["dom", "dom.iterable", "esnext"],
|
"lib": ["dom", "dom.iterable", "esnext"],
|
||||||
"allowJs": true,
|
"allowJs": true,
|
||||||
"skipLibCheck": true,
|
"skipLibCheck": true,
|
||||||
"strict": false,
|
"strict": true,
|
||||||
"noEmit": true,
|
"noEmit": true,
|
||||||
"incremental": true,
|
|
||||||
"module": "esnext",
|
|
||||||
"esModuleInterop": true,
|
"esModuleInterop": true,
|
||||||
"moduleResolution": "node",
|
"module": "esnext",
|
||||||
|
"moduleResolution": "bundler",
|
||||||
"resolveJsonModule": true,
|
"resolveJsonModule": true,
|
||||||
"isolatedModules": true,
|
"isolatedModules": true,
|
||||||
"jsx": "preserve"
|
"jsx": "preserve",
|
||||||
|
"incremental": true,
|
||||||
|
"plugins": [
|
||||||
|
{
|
||||||
|
"name": "next"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"paths": {
|
||||||
|
"@/*": ["./src/*"]
|
||||||
|
}
|
||||||
},
|
},
|
||||||
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
|
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
|
||||||
"exclude": ["node_modules"]
|
"exclude": ["node_modules"]
|
||||||
}
|
}
|
||||||
|
|||||||