Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions apps/desktop/package.json
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
{
"name": "@multica/desktop",
"productName": "Multica",
"productName": "Lunartica",
"version": "0.1.0",
"private": true,
"description": "Multica Desktop — native desktop client for the Multica platform.",
"description": "Lunartica Desktop — native desktop client for the Lunartica platform.",
"homepage": "https://multica.ai",
"repository": {
"type": "git",
Expand Down
2 changes: 1 addition & 1 deletion apps/desktop/src/renderer/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Multica</title>
<title>Lunartica</title>
</head>
<body class="h-full overflow-hidden antialiased font-sans">
<div id="root" class="h-full"></div>
Expand Down
6 changes: 3 additions & 3 deletions apps/web/app/auth/callback/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -148,9 +148,9 @@ function CallbackContent() {
<div className="flex min-h-screen items-center justify-center">
<Card className="w-full max-w-sm">
<CardHeader className="text-center">
<CardTitle className="text-2xl">Opening Multica</CardTitle>
<CardTitle className="text-2xl">Opening Lunartica</CardTitle>
<CardDescription>
You should see a prompt to open the Multica desktop app. If
You should see a prompt to open the Lunartica desktop app. If
nothing happens, click the button below.
</CardDescription>
</CardHeader>
Expand All @@ -161,7 +161,7 @@ function CallbackContent() {
window.location.href = `multica://auth/callback?token=${encodeURIComponent(desktopToken)}`;
}}
>
Open Multica Desktop
Open Lunartica Desktop
</Button>
</CardContent>
</Card>
Expand Down
4 changes: 2 additions & 2 deletions apps/web/app/custom.css
Original file line number Diff line number Diff line change
Expand Up @@ -34,8 +34,8 @@
--border: oklch(0.92 0.004 286.32);
--input: oklch(0.92 0.004 286.32);
--ring: oklch(0.705 0.015 286.067);
--brand: oklch(0.55 0.16 255);
--brand-foreground: oklch(0.985 0 0);
--brand: oklch(0.52 0.19 245);
--brand-foreground: oklch(0.985 0.004 245);
--success: oklch(0.55 0.16 145);
--warning: oklch(0.75 0.16 85);
--info: oklch(0.55 0.18 250);
Expand Down
8 changes: 4 additions & 4 deletions apps/web/app/layout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -55,15 +55,15 @@ export const viewport: Viewport = {
initialScale: 1,
themeColor: [
{ media: "(prefers-color-scheme: light)", color: "#ffffff" },
{ media: "(prefers-color-scheme: dark)", color: "#05070b" },
{ media: "(prefers-color-scheme: dark)", color: "#070d18" },
],
};

export const metadata: Metadata = {
metadataBase: new URL("https://www.multica.ai"),
title: {
default: "Multica — Project Management for Human + Agent Teams",
template: "%s | Multica",
default: "Lunartica — Project Management for Human + Agent Teams",
template: "%s | Lunartica",
},
description:
"Open-source platform that turns coding agents into real teammates. Assign tasks, track progress, compound skills.",
Expand All @@ -73,7 +73,7 @@ export const metadata: Metadata = {
},
openGraph: {
type: "website",
siteName: "Multica",
siteName: "Lunartica",
locale: "en_US",
},
twitter: {
Expand Down
2 changes: 1 addition & 1 deletion apps/web/app/not-found.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ export default function NotFound() {
The page you are looking for doesn&rsquo;t exist or has been moved.
</p>
<Link href="/" className={buttonVariants({ className: "mt-2" })}>
Back to Multica
Back to Lunartica
</Link>
</main>
);
Expand Down
9 changes: 3 additions & 6 deletions apps/web/public/favicon.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
118 changes: 118 additions & 0 deletions docs/LOCAL_DEV.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
# Local Development Setup

How to spin up Lunartica (Go API + PostgreSQL + Next.js web) on a fresh machine
for development and for testing the LunarWing `multica-bridge` interop.

> ⚠️ **Local dev only.** These instructions enable a passwordless login bypass
> (`MULTICA_DEV_VERIFICATION_CODE`) and use throwaway credentials. Never use this
> setup, the dev code, or `APP_ENV=development` on a public/production instance.

## Prerequisites

- **git**
- **Go ≥ 1.26** — or any Go; set `GOTOOLCHAIN=auto` and it auto-fetches the
version pinned in `server/go.mod`.
- **Node ≥ 20** (22 recommended). pnpm comes via corepack: `corepack enable pnpm`.
- **Docker** *or* **Podman** (for the PostgreSQL container).

## 1. Clone + configure

```bash
git clone https://github.com/LunarWingOrg/Lunartica.git
cd Lunartica
git checkout lunarpunk-reskin # the lunarpunk reskin branch

cp .env.example .env
sed -i "s/^JWT_SECRET=.*/JWT_SECRET=$(openssl rand -hex 32)/" .env
echo "MULTICA_DEV_VERIFICATION_CODE=424242" >> .env # passwordless dev login
corepack enable pnpm && pnpm install
```

Defaults in `.env` already point at Postgres `localhost:5432` (db/user/pass all
`multica`), the API on `:8080`, and the web app on `:3000`.

## 2a. Run it — Docker (simplest)

```bash
export GOTOOLCHAIN=auto # only needed if local Go < 1.26
make start # Postgres (compose) + migrate + API + web together
```

`make start` brings up the Postgres container via `docker compose`, applies
migrations, then runs the Go API (`:8080`) and the Next.js frontend (`:3000`).
Open <http://localhost:3000>.

(`make dev` does the same plus first-run env bootstrap; `make stop` stops the app
processes; `make db-down` stops the database container.)

## 2b. Run it — Podman / no Docker daemon

```bash
# Postgres (pgvector)
podman run -d --name lunartica-pg -p 127.0.0.1:5432:5432 \
-e POSTGRES_DB=multica -e POSTGRES_USER=multica -e POSTGRES_PASSWORD=multica \
docker.io/pgvector/pgvector:pg17

# migrate + run the API (loads .env; fetches Go 1.26 toolchain if needed)
set -a; . ./.env; set +a
( cd server && GOTOOLCHAIN=auto go run ./cmd/migrate up )
( cd server && GOTOOLCHAIN=auto APP_ENV=development go run ./cmd/server ) &

# run the web frontend
NEXT_PUBLIC_API_URL=http://localhost:8080 NEXT_PUBLIC_WS_URL=ws://localhost:8080/ws pnpm dev:web
```

Open <http://localhost:3000>.

## 3. Log in

Enter **any email** → on the code screen enter **`424242`**. The dev bypass is
active because `APP_ENV` ≠ `production` **and** `MULTICA_DEV_VERIFICATION_CODE` is
set. Without the dev code, read the real 6-digit code from the DB (Resend is unset
so no email is sent):

```bash
podman exec lunartica-pg psql -U multica -d multica -t \
-c "select code from verification_codes order by created_at desc limit 1;"
# (docker: docker exec <postgres-container> psql ... )
```

## 4. Accessing from another machine (headless/remote box)

The dev server is plain HTTP; browsing the box's LAN IP can trip HTTPS-Only mode
and the client JS may not hydrate. Tunnel instead, from your laptop:

```bash
ssh -L 3000:localhost:3000 -L 8080:localhost:8080 user@that-machine
```

Then browse <http://localhost:3000> — it's localhost on your side, so the JS
hydrates and the API (`:8080`) is reachable through the tunnel.

## 5. Optional — test the LunarWing bridge against this instance

The interop scripts live in the LunarWing repo:

```bash
git clone https://github.com/LunarWingOrg/lunarwing.git
cd lunarwing && git checkout 1.1.5-lunartica-1

# With Lunartica running on :8080, replay the bridge's daemon-protocol calls:
MULTICA_DEV_CODE=424242 ic/scripts/multica-bridge-smoke-test.sh
```

Or stand up Lunartica from scratch in one command:

```bash
LUNARTICA_DIR=/path/to/Lunartica ic/scripts/multica-local-test-server.sh up
# ... and tear it down:
ic/scripts/multica-local-test-server.sh down
```

## Notes

- **Ports:** API `8080`, web `3000`, Postgres `5432` (override via `.env`).
- **Go toolchain:** the repo pins Go 1.26.1 in `server/go.mod`; `GOTOOLCHAIN=auto`
lets an older local Go download it automatically.
- **Teardown (Podman path):** `podman rm -f lunartica-pg` and stop the `go run` /
`pnpm dev:web` processes (e.g. `kill` them or close the terminal).
39 changes: 19 additions & 20 deletions packages/ui/components/common/multica-icon.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -27,10 +27,24 @@ const borderedSizes = {
};

/**
* Pure CSS 8-pointed asterisk icon matching the Multica logo.
* Uses currentColor so it adapts to light/dark themes automatically.
* Clip-path polygon traced from the original SVG path coordinates.
* Crescent-moon brand mark (Lunartica / lunarpunk). Inline SVG filled with
* currentColor so it adapts to light/dark themes and inherits the violet brand
* colour wherever it is rendered. The entrance/hover spin animations from the
* original mark are preserved by the wrapper spans.
*/
function MoonGlyph() {
return (
<svg
viewBox="0 0 24 24"
fill="currentColor"
className="block size-full"
aria-hidden="true"
>
<path d="M21 12.79A9 9 0 1 1 11.21 3 7 7 0 0 0 21 12.79z" />
</svg>
);
}

export function MulticaIcon({
className,
animate = false,
Expand All @@ -47,15 +61,6 @@ export function MulticaIcon({
return () => clearTimeout(timer);
}, [animate]);

const clipPath = `polygon(
45% 62.1%, 45% 100%, 55% 100%, 55% 62.1%,
81.8% 88.9%, 88.9% 81.8%, 62.1% 55%, 100% 55%,
100% 45%, 62.1% 45%, 88.9% 18.2%, 81.8% 11.1%,
55% 37.9%, 55% 0%, 45% 0%, 45% 37.9%,
18.2% 11.1%, 11.1% 18.2%, 37.9% 45%, 0% 45%,
0% 55%, 37.9% 55%, 11.1% 81.8%, 18.2% 88.9%
)`;

if (bordered) {
const sizeConfig = borderedSizes[size];
return (
Expand All @@ -76,10 +81,7 @@ export function MulticaIcon({
entranceDone && !noSpin && "hover:animate-spin"
)}
>
<span
className="block size-full bg-current"
style={{ clipPath }}
/>
<MoonGlyph />
</span>
</span>
);
Expand All @@ -96,10 +98,7 @@ export function MulticaIcon({
aria-hidden="true"
{...props}
>
<span
className="block size-full bg-current"
style={{ clipPath }}
/>
<MoonGlyph />
</span>
);
}
Loading
Loading