/* Copyright 2026 Marimo. All rights reserved. */
import { BoxIcon, CheckCircleIcon, XCircleIcon } from "lucide-react";
import React from "react";
import { Spinner } from "@/components/icons/spinner";
import { Button } from "@/components/ui/button";
import { Kbd } from "@/components/ui/kbd";
import {
Table,
TableBody,
TableCell,
TableHead,
TableHeader,
TableRow,
} from "@/components/ui/table";
import { toast } from "@/components/ui/use-toast";
import { useResolvedMarimoConfig } from "@/core/config/config";
import { useRequestClient } from "@/core/network/requests";
import { isWasm } from "@/core/wasm/utils";
import { useAsyncData } from "@/hooks/useAsyncData";
import { ErrorBanner } from "@/plugins/impl/common/error-banner";
import { cn } from "@/utils/cn";
import { SettingSubtitle } from "./common";
interface Package {
name: string;
minVersion?: string;
}
interface OptionalFeature {
id: string;
/**
* Required packages to install for the feature to work.
*/
packagesRequired: Package[];
/**
* Additional packages to install if installed through this UI.
*/
additionalPackageInstalls: Package[];
/**
* Description of the feature.
*/
description: string;
}
// Define the optional dependencies and their features
const OPTIONAL_DEPENDENCIES: OptionalFeature[] = [
{
id: "sql",
packagesRequired: [{ name: "duckdb" }, { name: "sqlglot" }],
additionalPackageInstalls: [{ name: "polars[pyarrow]" }],
description: "SQL cells",
},
{
id: "charts",
packagesRequired: [{ name: "altair" }],
additionalPackageInstalls: [],
description: "Charts in datasource viewer",
},
{
id: "fast-charts",
packagesRequired: [{ name: "vegafusion" }, { name: "vl-convert-python" }],
additionalPackageInstalls: [],
description: "Fast server-side charts",
},
{
id: "formatting",
packagesRequired: [isWasm() ? { name: "black" } : { name: "ruff" }],
additionalPackageInstalls: [],
description: "Formatting",
},
{
id: "ai",
packagesRequired: [{ name: "openai" }],
additionalPackageInstalls: [],
description: "AI features",
},
{
id: "mcp",
packagesRequired: [{ name: "mcp", minVersion: "1" }],
additionalPackageInstalls: [{ name: "pydantic", minVersion: "2" }],
description: "Connect to MCP servers",
},
{
id: "ipy-export",
packagesRequired: [{ name: "nbformat" }],
additionalPackageInstalls: [],
description: "Export as IPYNB",
},
{
id: "testing",
packagesRequired: [{ name: "pytest" }],
additionalPackageInstalls: [],
description: "Autorun unit tests",
},
];
// Only available outside wasm
if (!isWasm()) {
OPTIONAL_DEPENDENCIES.push({
id: "lsp",
packagesRequired: [{ name: "python-lsp-server" }, { name: "websockets" }],
additionalPackageInstalls: [{ name: "python-lsp-ruff" }],
description: "Language Server Protocol*",
});
}
export const OptionalFeatures: React.FC = () => {
const [config] = useResolvedMarimoConfig();
const packageManager = config.package_management.manager;
const { getPackageList } = useRequestClient();
const { data, error, refetch, isPending } = useAsyncData(
() => getPackageList(),
[packageManager],
);
if (isPending) {
return
marimo is lightweight, with few dependencies, to maximize compatibility
with your own environments.
To unlock additional features in the marimo editor, you can install
these optional dependencies:
*Requires server restart