{"owner":"aipotheosis-labs","repo":"aci","hasSkills":true,"totalSkillsCount":2,"totalTokensCount":3631,"categories":["claude-rule","plugin-manifest"],"hasMcp":false,"mcpConfig":null,"found":["CLAUDE.md","frontend/src/components/ui-extensions/enhanced-data-table/README.md"],"skills":{"CLAUDE.md":"# CLAUDE.md\n\nThis file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.\n\n## Project Overview\n\nACI.dev is an open-source tool-calling platform providing 600+ integrations for AI agents. It serves as infrastructure for Unified MCP (Model Context Protocol) servers and VibeOps automated DevOps workflows. The platform handles multi-tenant authentication, granular permissions, and dynamic tool discovery.\n\n## Repository Structure\n\nThis is a **monorepo** with two main components:\n\n- `backend/` - FastAPI server with 600+ integrations (Python 3.12+, PostgreSQL, uv package manager)\n- `frontend/` - Next.js 15 developer portal (React 19, TypeScript, Tailwind CSS, shadcn/ui)\n\n## Essential Development Commands\n\n### Backend Commands\n\n```bash\ncd backend\nuv sync                                          # Install dependencies\nsource .venv/bin/activate                       # Activate virtual environment\ndocker compose up --build                       # Start all services (includes PostgreSQL with pgvector)\ndocker compose exec runner ./scripts/seed_db.sh # Seed database\n\n# Database management\ndocker compose exec runner alembic upgrade head                    # Apply migrations\ndocker compose exec runner alembic revision --autogenerate -m \"description\" # Create migration\n\n# Testing and quality\ndocker compose exec test-runner pytest         # Run tests\nruff format .                                   # Format code\nruff check .                                    # Lint code\nmypy .                                          # Type checking\n\n# Admin CLI\ndocker compose exec runner python -m aci.cli --help\ndocker compose exec runner python -m aci.cli upsert-app --app-file ./apps/gmail/app.json\n```\n\n### Frontend Commands\n\n```bash\ncd frontend\nnpm install --legacy-peer-deps                 # Install dependencies (React 19 compatibility required)\ncp .env.example .env                           # Setup environment\nnpm run dev                                    # Start development server\n\n# Code quality\nnpm run format                                 # Prettier formatting\nnpm run lint                                   # ESLint\nnpm run test                                   # Vitest in watch mode\nnpm run build                                  # Production build\n```\n\n## Core Architecture\n\n### Database Models (`backend/aci/common/db/sql_models.py`)\n\n- **Project**: Multi-tenant container for API keys, apps, and agents\n- **Agent**: Logical actors that access the platform (tied to API keys)\n- **App**: Third-party service integrations (Gmail, Slack, etc.)\n- **Function**: Individual API endpoints within apps\n- **LinkedAccount**: User authentication credentials for OAuth/API keys\n- **AppConfiguration**: User-specific app settings and permissions\n\n### Backend Structure (`backend/aci/`)\n\n- `server/` - FastAPI application with routes, middleware, app_connectors\n- `common/db/` - SQLAlchemy models and CRUD operations\n- `common/schemas/` - Pydantic models for validation\n- `cli/` - Admin command-line interface\n- `apps/` - 600+ integration definitions as JSON configs\n\n### Frontend Structure (`frontend/src/`)\n\n- `app/` - Next.js App Router pages (apps/, playground/, settings/)\n- `components/` - Reusable UI components with shadcn/ui\n- `lib/` - API clients and utilities\n- `hooks/` - Custom React hooks\n\n## Integration System\n\nEach integration requires two JSON files in `backend/apps/{app_name}/`:\n\n- `app.json` - Metadata, authentication schemes, categories, visibility\n- `functions.json` - API endpoints and their schemas\n\nApps support OAuth2, API keys, and no-auth patterns with encrypted credential storage.\n\n## Key Services (Docker Compose)\n\n- **server**: FastAPI backend (port 8000)\n- **db**: PostgreSQL with pgvector extension (port 5432)\n- **aws**: LocalStack for AWS services (port 4566)\n- **runner**: Utility container for CLI commands and database operations\n- **test-runner**: Isolated testing environment\n\n## Authentication & API Structure\n\n### Authentication Methods\n\n1. **PropelAuth**: Web portal authentication for developers\n2. **API Keys**: Agent/programmatic access via `X-API-KEY` header\n3. **OAuth2/API Keys**: End-user service authentication stored as LinkedAccounts\n\n### Core API Endpoints (`/v1/`)\n\n- `/apps` - Browse and configure integrations\n- `/functions` - Execute tool calls with semantic search using pgvector\n- `/linked-accounts` - Manage user authentication\n- `/projects` - Project and agent management\n- `/playground` - Interactive agent testing\n\n## Function Execution Flow\n\n1. **Discovery**: Semantic search finds relevant functions using OpenAI embeddings\n2. **Authentication**: Validates API key and linked account permissions\n3. **Execution**: Routes calls through appropriate connectors\n4. **Logging**: Comprehensive request/response tracking with Sentry/Logfire\n\n## Local Development Setup\n\n1. **Backend**: Copy `.env.example` to `.env.local`, set OpenAI API keys, run `docker compose up --build`\n2. **Frontend**: Copy `.env.example` to `.env`, run `npm install --legacy-peer-deps`\n3. **Database**: Run `docker compose exec runner ./scripts/seed_db.sh` to populate with sample data\n\n## Package Managers\n\n- **Backend**: Uses `uv` (modern Python package manager) - do not use pip/poetry\n- **Frontend**: Uses npm with `--legacy-peer-deps` flag required for React 19 compatibility\n\n## Testing\n\n- **Backend**: `docker compose exec test-runner pytest` (isolated test environment)\n- **Frontend**: `npm run test` (Vitest in watch mode)\n\n## Code Quality Tools\n\n- **Backend**: ruff (formatting/linting), mypy (type checking), pre-commit hooks\n- **Frontend**: Prettier (formatting), ESLint (linting), TypeScript compiler\n","frontend/src/components/ui-extensions/enhanced-data-table/README.md":"# EnhancedDataTable Component Documentation\n\nThe EnhancedDataTable is a data table component built on TanStack Table (React Table), providing advanced features such as sorting, filtering, searching, and row selection. This documentation will help you quickly understand and effectively use this component.\n\n## Table of Contents\n\n- [Basic Usage](#basic-usage)\n- [Column Definitions](#column-definitions)\n- [Search and Filtering](#search-and-filtering)\n- [Sorting Functionality](#sorting-functionality)\n- [Row Selection](#row-selection)\n- [Custom Column Styling and Actions](#custom-column-styling-and-actions)\n- [Practical Application Examples](#practical-application-examples)\n\n## Basic Usage\n\nTo use the EnhancedDataTable, you need to provide two basic parameters: `columns` (column definitions) and `data` (data source).\n\n```tsx\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useMyTableColumns } from \"./useMyTableColumns\";\n\nexport function MyTable({ data }) {\n  // Use custom hook to get column definitions\n  const columns = useMyTableColumns();\n\n  return (\n    <EnhancedDataTable\n      columns={columns}\n      data={data}\n      searchBarProps={{ placeholder: \"Search...\" }}\n    />\n  );\n}\n```\n\n## Column Definitions\n\nIt's recommended to create column definition hooks in separate files using `createColumnHelper` to get better type support.\n\n### Creating Basic Column Definition Files\n\n```tsx\n// useMyTableColumns.tsx\nimport { useMemo } from \"react\";\nimport { createColumnHelper, type ColumnDef } from \"@tanstack/react-table\";\nimport { MyDataType } from \"@/lib/types/myDataType\";\n\nconst columnHelper = createColumnHelper<MyDataType>();\n\nexport const useMyTableColumns = (): ColumnDef<MyDataType>[] => {\n  return useMemo(\n    () => [\n      columnHelper.accessor(\"name\", {\n        header: \"Name\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n      columnHelper.accessor(\"description\", {\n        header: \"Description\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n    ],\n    [],\n  );\n};\n```\n\n### Column Properties Explained\n\n- `header`: Column title, can be a string or React component\n- `cell`: Cell rendering function\n- `enableGlobalFilter`: Whether to include this column in global search\n- `enableColumnFilter`: Whether to enable column filtering\n- `filterFn`: Filter function type, e.g., \"arrIncludes\" for array fields\n- `id`: Custom column ID, required when using accessor function\n- `meta`: Used to set default sorting and other metadata\n\n### Creating Sortable Columns\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: ({ column }) => (\n    <Button\n      variant=\"ghost\"\n      onClick={() => column.toggleSorting(column.getIsSorted() === \"asc\")}\n      className=\"w-full justify-start px-0\"\n    >\n      Name\n      <ArrowUpDown className=\"h-4 w-4\" />\n    </Button>\n  ),\n  cell: (info) => info.getValue(),\n  enableGlobalFilter: true,\n  // Set as default sort column\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: false,\n  },\n});\n```\n\n## Search and Filtering\n\n### Enabling Global Search\n\nProvide the `searchBarProps` parameter and ensure relevant columns have `enableGlobalFilter: true`:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  searchBarProps={{ placeholder: \"Search...\" }}\n/>\n```\n\n### Column Filtering Functionality\n\nEnhancedDataTable provides single‑value dropdown filtering for array‑type columns. :\n\n1. Set `enableColumnFilter: true`\n2. Set `filterFn: \"arrIncludes\"`\n\n#### Enabling Dropdown Filtering for Array Type Columns\n\n```tsx\n// Using dropdown filtering for tag arrays\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2\">\n      {info.getValue().map((tag) => (\n        <span key={tag} className=\"px-2 py-1 bg-gray-100 rounded-md\">\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true, // Enable column filtering\n  filterFn: \"arrIncludes\", // Specify array filtering function\n});\n```\n\n#### Handling Arrays from Non-Standard Data Sources\n\nFor array data not in default fields, you can use custom accessors:\n\n```tsx\n// Handling nested objects or transforming data\ncolumnHelper.accessor(\n  (row) => row.metadata?.categories || [], // Extract array from nested object\n  {\n    id: \"categoriesDisplay\", // Must provide unique ID\n    header: \"Categories\",\n    cell: (info) => (\n      <div className=\"flex flex-wrap gap-2\">\n        {info.getValue().map((category) => (\n          <span key={category} className=\"badge\">\n            {category}\n          </span>\n        ))}\n      </div>\n    ),\n    enableColumnFilter: true,\n    filterFn: \"arrIncludes\",\n  },\n);\n```\n\n#### Automatic Filter UI Generation\n\nWhen the following conditions are met, the table will automatically generate dropdown filter menus for columns:\n\n1. Column has `enableColumnFilter: true`\n2. Column uses `filterFn: \"arrIncludes\"`\n\nFilters will be displayed in the top toolbar of the table, allowing users to select multiple values for filtering.\n\n## Sorting Functionality\n\n### Setting Default Sorting\n\nYou can set default sorting in two ways:\n\n1. Using the `meta` property in column definition:\n\n```tsx\ncolumnHelper.accessor(\"createdAt\", {\n  header: \"Created At\",\n  cell: (info) => new Date(info.getValue()).toLocaleString(),\n  id: \"createdAt\",\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: true, // Default descending order\n  },\n});\n```\n\n2. Through the component's `defaultSorting` property:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  defaultSorting={[\n    {\n      id: \"createdAt\",\n      desc: true,\n    },\n  ]}\n/>\n```\n\n## Row Selection\n\nTo enable row selection functionality, you need to provide `rowSelectionProps`:\n\n```tsx\nconst [rowSelection, setRowSelection] = useState({});\n\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  rowSelectionProps={{\n    rowSelection,\n    onRowSelectionChange: setRowSelection,\n    getRowId: (row) => row.id,\n  }}\n/>;\n```\n\nThis will add a selection checkbox column to the left of the table, allowing users to select multiple rows of data.\n\n## Custom Column Styling and Actions\n\n### Image and Text Combination Column\n\n```tsx\ncolumnHelper.accessor(\"app_name\", {\n  header: \"App Name\",\n  cell: (info) => {\n    const appName = info.getValue();\n    return (\n      <div className=\"flex items-center gap-3\">\n        <div className=\"relative h-5 w-5 shrink-0 overflow-hidden\">\n          {appsMap[appName]?.logo && (\n            <Image\n              src={appsMap[appName]?.logo || \"\"}\n              alt={`${appName} logo`}\n              fill\n              className=\"object-contain\"\n            />\n          )}\n        </div>\n        <IdDisplay id={appName} dim={false} />\n      </div>\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n### Tag Rendering\n\n```tsx\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2 overflow-hidden\">\n      {(info.getValue() || []).map((tag) => (\n        <span\n          key={tag}\n          className=\"rounded-md bg-gray-100 px-3 py-1 text-sm font-medium text-gray-600 border border-gray-200\"\n        >\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true,\n  filterFn: \"arrIncludes\",\n});\n```\n\n### Custom Action Buttons Column\n\n```tsx\ncolumnHelper.accessor(\n  (row) => row, // Get entire row data\n  {\n    id: \"actions\",\n    header: \"\",\n    cell: (info) => {\n      const item = info.getValue();\n      return (\n        <div className=\"space-x-2 flex\">\n          <Link href={`/items/${item.id}`}>\n            <Button variant=\"outline\" size=\"sm\">\n              Open\n            </Button>\n          </Link>\n          <Button variant=\"ghost\" size=\"sm\" className=\"text-red-600\">\n            <GoTrash />\n          </Button>\n        </div>\n      );\n    },\n    enableGlobalFilter: false,\n  },\n);\n```\n\n### Editable Cells\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: \"Name\",\n  cell: (ctx) => {\n    const item = ctx.row.original;\n    return (\n      <EditableCell\n        initialValue={item.name}\n        fieldName=\"name\"\n        itemId={item.id}\n        onUpdate={handleUpdate}\n      />\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n## Pagination\n\nEnhancedDataTable supports client-side pagination using TanStack Table’s built-in `getPaginationRowModel()`.\n\nTo enable pagination, pass the `paginationOptions` prop:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  paginationOptions={{\n    initialPageIndex: 0, // Default to first page (0-based)\n    initialPageSize: 10, // Number of entries per page\n  }}\n/>\n```\n\n## Practical Application Examples\n\n### App Configuration Table (with Icons, Category Filtering, and Toggle Switch)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAppConfigsTableColumns } from \"./useAppConfigsTableColumns\";\n\nexport function AppConfigsPage() {\n  const [appConfigs, setAppConfigs] = useState<AppConfig[]>([]);\n  // ...other states and logic\n\n  const appConfigsColumns = useAppConfigsTableColumns({\n    linkedAccountsCountMap,\n    appsMap,\n    updateAppConfigs: loadAllData,\n  });\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={appConfigs}\n        columns={appConfigsColumns}\n        searchBarProps={{ placeholder: \"Search apps...\" }}\n      />\n    </div>\n  );\n}\n```\n\n### Agents Table (with Editable Cells and Custom Actions)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAgentsTableColumns } from \"./useAgentsTableColumns\";\n\nexport function AgentsPage() {\n  const [agents, setAgents] = useState<Agent[]>([]);\n  // ...other states and logic\n\n  const columns = useAgentsTableColumns(\n    projectId,\n    handleDeleteAgent,\n    reloadAgents,\n    handleInstructionsSave,\n  );\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={agents}\n        columns={columns}\n        searchBarProps={{ placeholder: \"Search agents...\" }}\n      />\n    </div>\n  );\n}\n```\n"},"files":{"CLAUDE.md":"# CLAUDE.md\n\nThis file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.\n\n## Project Overview\n\nACI.dev is an open-source tool-calling platform providing 600+ integrations for AI agents. It serves as infrastructure for Unified MCP (Model Context Protocol) servers and VibeOps automated DevOps workflows. The platform handles multi-tenant authentication, granular permissions, and dynamic tool discovery.\n\n## Repository Structure\n\nThis is a **monorepo** with two main components:\n\n- `backend/` - FastAPI server with 600+ integrations (Python 3.12+, PostgreSQL, uv package manager)\n- `frontend/` - Next.js 15 developer portal (React 19, TypeScript, Tailwind CSS, shadcn/ui)\n\n## Essential Development Commands\n\n### Backend Commands\n\n```bash\ncd backend\nuv sync                                          # Install dependencies\nsource .venv/bin/activate                       # Activate virtual environment\ndocker compose up --build                       # Start all services (includes PostgreSQL with pgvector)\ndocker compose exec runner ./scripts/seed_db.sh # Seed database\n\n# Database management\ndocker compose exec runner alembic upgrade head                    # Apply migrations\ndocker compose exec runner alembic revision --autogenerate -m \"description\" # Create migration\n\n# Testing and quality\ndocker compose exec test-runner pytest         # Run tests\nruff format .                                   # Format code\nruff check .                                    # Lint code\nmypy .                                          # Type checking\n\n# Admin CLI\ndocker compose exec runner python -m aci.cli --help\ndocker compose exec runner python -m aci.cli upsert-app --app-file ./apps/gmail/app.json\n```\n\n### Frontend Commands\n\n```bash\ncd frontend\nnpm install --legacy-peer-deps                 # Install dependencies (React 19 compatibility required)\ncp .env.example .env                           # Setup environment\nnpm run dev                                    # Start development server\n\n# Code quality\nnpm run format                                 # Prettier formatting\nnpm run lint                                   # ESLint\nnpm run test                                   # Vitest in watch mode\nnpm run build                                  # Production build\n```\n\n## Core Architecture\n\n### Database Models (`backend/aci/common/db/sql_models.py`)\n\n- **Project**: Multi-tenant container for API keys, apps, and agents\n- **Agent**: Logical actors that access the platform (tied to API keys)\n- **App**: Third-party service integrations (Gmail, Slack, etc.)\n- **Function**: Individual API endpoints within apps\n- **LinkedAccount**: User authentication credentials for OAuth/API keys\n- **AppConfiguration**: User-specific app settings and permissions\n\n### Backend Structure (`backend/aci/`)\n\n- `server/` - FastAPI application with routes, middleware, app_connectors\n- `common/db/` - SQLAlchemy models and CRUD operations\n- `common/schemas/` - Pydantic models for validation\n- `cli/` - Admin command-line interface\n- `apps/` - 600+ integration definitions as JSON configs\n\n### Frontend Structure (`frontend/src/`)\n\n- `app/` - Next.js App Router pages (apps/, playground/, settings/)\n- `components/` - Reusable UI components with shadcn/ui\n- `lib/` - API clients and utilities\n- `hooks/` - Custom React hooks\n\n## Integration System\n\nEach integration requires two JSON files in `backend/apps/{app_name}/`:\n\n- `app.json` - Metadata, authentication schemes, categories, visibility\n- `functions.json` - API endpoints and their schemas\n\nApps support OAuth2, API keys, and no-auth patterns with encrypted credential storage.\n\n## Key Services (Docker Compose)\n\n- **server**: FastAPI backend (port 8000)\n- **db**: PostgreSQL with pgvector extension (port 5432)\n- **aws**: LocalStack for AWS services (port 4566)\n- **runner**: Utility container for CLI commands and database operations\n- **test-runner**: Isolated testing environment\n\n## Authentication & API Structure\n\n### Authentication Methods\n\n1. **PropelAuth**: Web portal authentication for developers\n2. **API Keys**: Agent/programmatic access via `X-API-KEY` header\n3. **OAuth2/API Keys**: End-user service authentication stored as LinkedAccounts\n\n### Core API Endpoints (`/v1/`)\n\n- `/apps` - Browse and configure integrations\n- `/functions` - Execute tool calls with semantic search using pgvector\n- `/linked-accounts` - Manage user authentication\n- `/projects` - Project and agent management\n- `/playground` - Interactive agent testing\n\n## Function Execution Flow\n\n1. **Discovery**: Semantic search finds relevant functions using OpenAI embeddings\n2. **Authentication**: Validates API key and linked account permissions\n3. **Execution**: Routes calls through appropriate connectors\n4. **Logging**: Comprehensive request/response tracking with Sentry/Logfire\n\n## Local Development Setup\n\n1. **Backend**: Copy `.env.example` to `.env.local`, set OpenAI API keys, run `docker compose up --build`\n2. **Frontend**: Copy `.env.example` to `.env`, run `npm install --legacy-peer-deps`\n3. **Database**: Run `docker compose exec runner ./scripts/seed_db.sh` to populate with sample data\n\n## Package Managers\n\n- **Backend**: Uses `uv` (modern Python package manager) - do not use pip/poetry\n- **Frontend**: Uses npm with `--legacy-peer-deps` flag required for React 19 compatibility\n\n## Testing\n\n- **Backend**: `docker compose exec test-runner pytest` (isolated test environment)\n- **Frontend**: `npm run test` (Vitest in watch mode)\n\n## Code Quality Tools\n\n- **Backend**: ruff (formatting/linting), mypy (type checking), pre-commit hooks\n- **Frontend**: Prettier (formatting), ESLint (linting), TypeScript compiler\n","frontend/src/components/ui-extensions/enhanced-data-table/README.md":"# EnhancedDataTable Component Documentation\n\nThe EnhancedDataTable is a data table component built on TanStack Table (React Table), providing advanced features such as sorting, filtering, searching, and row selection. This documentation will help you quickly understand and effectively use this component.\n\n## Table of Contents\n\n- [Basic Usage](#basic-usage)\n- [Column Definitions](#column-definitions)\n- [Search and Filtering](#search-and-filtering)\n- [Sorting Functionality](#sorting-functionality)\n- [Row Selection](#row-selection)\n- [Custom Column Styling and Actions](#custom-column-styling-and-actions)\n- [Practical Application Examples](#practical-application-examples)\n\n## Basic Usage\n\nTo use the EnhancedDataTable, you need to provide two basic parameters: `columns` (column definitions) and `data` (data source).\n\n```tsx\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useMyTableColumns } from \"./useMyTableColumns\";\n\nexport function MyTable({ data }) {\n  // Use custom hook to get column definitions\n  const columns = useMyTableColumns();\n\n  return (\n    <EnhancedDataTable\n      columns={columns}\n      data={data}\n      searchBarProps={{ placeholder: \"Search...\" }}\n    />\n  );\n}\n```\n\n## Column Definitions\n\nIt's recommended to create column definition hooks in separate files using `createColumnHelper` to get better type support.\n\n### Creating Basic Column Definition Files\n\n```tsx\n// useMyTableColumns.tsx\nimport { useMemo } from \"react\";\nimport { createColumnHelper, type ColumnDef } from \"@tanstack/react-table\";\nimport { MyDataType } from \"@/lib/types/myDataType\";\n\nconst columnHelper = createColumnHelper<MyDataType>();\n\nexport const useMyTableColumns = (): ColumnDef<MyDataType>[] => {\n  return useMemo(\n    () => [\n      columnHelper.accessor(\"name\", {\n        header: \"Name\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n      columnHelper.accessor(\"description\", {\n        header: \"Description\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n    ],\n    [],\n  );\n};\n```\n\n### Column Properties Explained\n\n- `header`: Column title, can be a string or React component\n- `cell`: Cell rendering function\n- `enableGlobalFilter`: Whether to include this column in global search\n- `enableColumnFilter`: Whether to enable column filtering\n- `filterFn`: Filter function type, e.g., \"arrIncludes\" for array fields\n- `id`: Custom column ID, required when using accessor function\n- `meta`: Used to set default sorting and other metadata\n\n### Creating Sortable Columns\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: ({ column }) => (\n    <Button\n      variant=\"ghost\"\n      onClick={() => column.toggleSorting(column.getIsSorted() === \"asc\")}\n      className=\"w-full justify-start px-0\"\n    >\n      Name\n      <ArrowUpDown className=\"h-4 w-4\" />\n    </Button>\n  ),\n  cell: (info) => info.getValue(),\n  enableGlobalFilter: true,\n  // Set as default sort column\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: false,\n  },\n});\n```\n\n## Search and Filtering\n\n### Enabling Global Search\n\nProvide the `searchBarProps` parameter and ensure relevant columns have `enableGlobalFilter: true`:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  searchBarProps={{ placeholder: \"Search...\" }}\n/>\n```\n\n### Column Filtering Functionality\n\nEnhancedDataTable provides single‑value dropdown filtering for array‑type columns. :\n\n1. Set `enableColumnFilter: true`\n2. Set `filterFn: \"arrIncludes\"`\n\n#### Enabling Dropdown Filtering for Array Type Columns\n\n```tsx\n// Using dropdown filtering for tag arrays\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2\">\n      {info.getValue().map((tag) => (\n        <span key={tag} className=\"px-2 py-1 bg-gray-100 rounded-md\">\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true, // Enable column filtering\n  filterFn: \"arrIncludes\", // Specify array filtering function\n});\n```\n\n#### Handling Arrays from Non-Standard Data Sources\n\nFor array data not in default fields, you can use custom accessors:\n\n```tsx\n// Handling nested objects or transforming data\ncolumnHelper.accessor(\n  (row) => row.metadata?.categories || [], // Extract array from nested object\n  {\n    id: \"categoriesDisplay\", // Must provide unique ID\n    header: \"Categories\",\n    cell: (info) => (\n      <div className=\"flex flex-wrap gap-2\">\n        {info.getValue().map((category) => (\n          <span key={category} className=\"badge\">\n            {category}\n          </span>\n        ))}\n      </div>\n    ),\n    enableColumnFilter: true,\n    filterFn: \"arrIncludes\",\n  },\n);\n```\n\n#### Automatic Filter UI Generation\n\nWhen the following conditions are met, the table will automatically generate dropdown filter menus for columns:\n\n1. Column has `enableColumnFilter: true`\n2. Column uses `filterFn: \"arrIncludes\"`\n\nFilters will be displayed in the top toolbar of the table, allowing users to select multiple values for filtering.\n\n## Sorting Functionality\n\n### Setting Default Sorting\n\nYou can set default sorting in two ways:\n\n1. Using the `meta` property in column definition:\n\n```tsx\ncolumnHelper.accessor(\"createdAt\", {\n  header: \"Created At\",\n  cell: (info) => new Date(info.getValue()).toLocaleString(),\n  id: \"createdAt\",\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: true, // Default descending order\n  },\n});\n```\n\n2. Through the component's `defaultSorting` property:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  defaultSorting={[\n    {\n      id: \"createdAt\",\n      desc: true,\n    },\n  ]}\n/>\n```\n\n## Row Selection\n\nTo enable row selection functionality, you need to provide `rowSelectionProps`:\n\n```tsx\nconst [rowSelection, setRowSelection] = useState({});\n\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  rowSelectionProps={{\n    rowSelection,\n    onRowSelectionChange: setRowSelection,\n    getRowId: (row) => row.id,\n  }}\n/>;\n```\n\nThis will add a selection checkbox column to the left of the table, allowing users to select multiple rows of data.\n\n## Custom Column Styling and Actions\n\n### Image and Text Combination Column\n\n```tsx\ncolumnHelper.accessor(\"app_name\", {\n  header: \"App Name\",\n  cell: (info) => {\n    const appName = info.getValue();\n    return (\n      <div className=\"flex items-center gap-3\">\n        <div className=\"relative h-5 w-5 shrink-0 overflow-hidden\">\n          {appsMap[appName]?.logo && (\n            <Image\n              src={appsMap[appName]?.logo || \"\"}\n              alt={`${appName} logo`}\n              fill\n              className=\"object-contain\"\n            />\n          )}\n        </div>\n        <IdDisplay id={appName} dim={false} />\n      </div>\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n### Tag Rendering\n\n```tsx\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2 overflow-hidden\">\n      {(info.getValue() || []).map((tag) => (\n        <span\n          key={tag}\n          className=\"rounded-md bg-gray-100 px-3 py-1 text-sm font-medium text-gray-600 border border-gray-200\"\n        >\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true,\n  filterFn: \"arrIncludes\",\n});\n```\n\n### Custom Action Buttons Column\n\n```tsx\ncolumnHelper.accessor(\n  (row) => row, // Get entire row data\n  {\n    id: \"actions\",\n    header: \"\",\n    cell: (info) => {\n      const item = info.getValue();\n      return (\n        <div className=\"space-x-2 flex\">\n          <Link href={`/items/${item.id}`}>\n            <Button variant=\"outline\" size=\"sm\">\n              Open\n            </Button>\n          </Link>\n          <Button variant=\"ghost\" size=\"sm\" className=\"text-red-600\">\n            <GoTrash />\n          </Button>\n        </div>\n      );\n    },\n    enableGlobalFilter: false,\n  },\n);\n```\n\n### Editable Cells\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: \"Name\",\n  cell: (ctx) => {\n    const item = ctx.row.original;\n    return (\n      <EditableCell\n        initialValue={item.name}\n        fieldName=\"name\"\n        itemId={item.id}\n        onUpdate={handleUpdate}\n      />\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n## Pagination\n\nEnhancedDataTable supports client-side pagination using TanStack Table’s built-in `getPaginationRowModel()`.\n\nTo enable pagination, pass the `paginationOptions` prop:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  paginationOptions={{\n    initialPageIndex: 0, // Default to first page (0-based)\n    initialPageSize: 10, // Number of entries per page\n  }}\n/>\n```\n\n## Practical Application Examples\n\n### App Configuration Table (with Icons, Category Filtering, and Toggle Switch)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAppConfigsTableColumns } from \"./useAppConfigsTableColumns\";\n\nexport function AppConfigsPage() {\n  const [appConfigs, setAppConfigs] = useState<AppConfig[]>([]);\n  // ...other states and logic\n\n  const appConfigsColumns = useAppConfigsTableColumns({\n    linkedAccountsCountMap,\n    appsMap,\n    updateAppConfigs: loadAllData,\n  });\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={appConfigs}\n        columns={appConfigsColumns}\n        searchBarProps={{ placeholder: \"Search apps...\" }}\n      />\n    </div>\n  );\n}\n```\n\n### Agents Table (with Editable Cells and Custom Actions)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAgentsTableColumns } from \"./useAgentsTableColumns\";\n\nexport function AgentsPage() {\n  const [agents, setAgents] = useState<Agent[]>([]);\n  // ...other states and logic\n\n  const columns = useAgentsTableColumns(\n    projectId,\n    handleDeleteAgent,\n    reloadAgents,\n    handleInstructionsSave,\n  );\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={agents}\n        columns={columns}\n        searchBarProps={{ placeholder: \"Search agents...\" }}\n      />\n    </div>\n  );\n}\n```\n"},"items":[{"name":"CLAUDE.md","path":"CLAUDE.md","rawUrl":"https://raw.githubusercontent.com/aipotheosis-labs/aci/HEAD/CLAUDE.md","title":"Claude Agent Guidelines & System Prompt","category":"claude-rule","format":"markdown","content":"# CLAUDE.md\n\nThis file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.\n\n## Project Overview\n\nACI.dev is an open-source tool-calling platform providing 600+ integrations for AI agents. It serves as infrastructure for Unified MCP (Model Context Protocol) servers and VibeOps automated DevOps workflows. The platform handles multi-tenant authentication, granular permissions, and dynamic tool discovery.\n\n## Repository Structure\n\nThis is a **monorepo** with two main components:\n\n- `backend/` - FastAPI server with 600+ integrations (Python 3.12+, PostgreSQL, uv package manager)\n- `frontend/` - Next.js 15 developer portal (React 19, TypeScript, Tailwind CSS, shadcn/ui)\n\n## Essential Development Commands\n\n### Backend Commands\n\n```bash\ncd backend\nuv sync                                          # Install dependencies\nsource .venv/bin/activate                       # Activate virtual environment\ndocker compose up --build                       # Start all services (includes PostgreSQL with pgvector)\ndocker compose exec runner ./scripts/seed_db.sh # Seed database\n\n# Database management\ndocker compose exec runner alembic upgrade head                    # Apply migrations\ndocker compose exec runner alembic revision --autogenerate -m \"description\" # Create migration\n\n# Testing and quality\ndocker compose exec test-runner pytest         # Run tests\nruff format .                                   # Format code\nruff check .                                    # Lint code\nmypy .                                          # Type checking\n\n# Admin CLI\ndocker compose exec runner python -m aci.cli --help\ndocker compose exec runner python -m aci.cli upsert-app --app-file ./apps/gmail/app.json\n```\n\n### Frontend Commands\n\n```bash\ncd frontend\nnpm install --legacy-peer-deps                 # Install dependencies (React 19 compatibility required)\ncp .env.example .env                           # Setup environment\nnpm run dev                                    # Start development server\n\n# Code quality\nnpm run format                                 # Prettier formatting\nnpm run lint                                   # ESLint\nnpm run test                                   # Vitest in watch mode\nnpm run build                                  # Production build\n```\n\n## Core Architecture\n\n### Database Models (`backend/aci/common/db/sql_models.py`)\n\n- **Project**: Multi-tenant container for API keys, apps, and agents\n- **Agent**: Logical actors that access the platform (tied to API keys)\n- **App**: Third-party service integrations (Gmail, Slack, etc.)\n- **Function**: Individual API endpoints within apps\n- **LinkedAccount**: User authentication credentials for OAuth/API keys\n- **AppConfiguration**: User-specific app settings and permissions\n\n### Backend Structure (`backend/aci/`)\n\n- `server/` - FastAPI application with routes, middleware, app_connectors\n- `common/db/` - SQLAlchemy models and CRUD operations\n- `common/schemas/` - Pydantic models for validation\n- `cli/` - Admin command-line interface\n- `apps/` - 600+ integration definitions as JSON configs\n\n### Frontend Structure (`frontend/src/`)\n\n- `app/` - Next.js App Router pages (apps/, playground/, settings/)\n- `components/` - Reusable UI components with shadcn/ui\n- `lib/` - API clients and utilities\n- `hooks/` - Custom React hooks\n\n## Integration System\n\nEach integration requires two JSON files in `backend/apps/{app_name}/`:\n\n- `app.json` - Metadata, authentication schemes, categories, visibility\n- `functions.json` - API endpoints and their schemas\n\nApps support OAuth2, API keys, and no-auth patterns with encrypted credential storage.\n\n## Key Services (Docker Compose)\n\n- **server**: FastAPI backend (port 8000)\n- **db**: PostgreSQL with pgvector extension (port 5432)\n- **aws**: LocalStack for AWS services (port 4566)\n- **runner**: Utility container for CLI commands and database operations\n- **test-runner**: Isolated testing environment\n\n## Authentication & API Structure\n\n### Authentication Methods\n\n1. **PropelAuth**: Web portal authentication for developers\n2. **API Keys**: Agent/programmatic access via `X-API-KEY` header\n3. **OAuth2/API Keys**: End-user service authentication stored as LinkedAccounts\n\n### Core API Endpoints (`/v1/`)\n\n- `/apps` - Browse and configure integrations\n- `/functions` - Execute tool calls with semantic search using pgvector\n- `/linked-accounts` - Manage user authentication\n- `/projects` - Project and agent management\n- `/playground` - Interactive agent testing\n\n## Function Execution Flow\n\n1. **Discovery**: Semantic search finds relevant functions using OpenAI embeddings\n2. **Authentication**: Validates API key and linked account permissions\n3. **Execution**: Routes calls through appropriate connectors\n4. **Logging**: Comprehensive request/response tracking with Sentry/Logfire\n\n## Local Development Setup\n\n1. **Backend**: Copy `.env.example` to `.env.local`, set OpenAI API keys, run `docker compose up --build`\n2. **Frontend**: Copy `.env.example` to `.env`, run `npm install --legacy-peer-deps`\n3. **Database**: Run `docker compose exec runner ./scripts/seed_db.sh` to populate with sample data\n\n## Package Managers\n\n- **Backend**: Uses `uv` (modern Python package manager) - do not use pip/poetry\n- **Frontend**: Uses npm with `--legacy-peer-deps` flag required for React 19 compatibility\n\n## Testing\n\n- **Backend**: `docker compose exec test-runner pytest` (isolated test environment)\n- **Frontend**: `npm run test` (Vitest in watch mode)\n\n## Code Quality Tools\n\n- **Backend**: ruff (formatting/linting), mypy (type checking), pre-commit hooks\n- **Frontend**: Prettier (formatting), ESLint (linting), TypeScript compiler\n","isInternal":false,"tokens":1244,"sizeBytes":5697},{"name":"README.md","path":"frontend/src/components/ui-extensions/enhanced-data-table/README.md","rawUrl":"https://raw.githubusercontent.com/aipotheosis-labs/aci/HEAD/frontend/src/components/ui-extensions/enhanced-data-table/README.md","title":"enhanced-data-table Documentation","category":"plugin-manifest","format":"markdown","content":"# EnhancedDataTable Component Documentation\n\nThe EnhancedDataTable is a data table component built on TanStack Table (React Table), providing advanced features such as sorting, filtering, searching, and row selection. This documentation will help you quickly understand and effectively use this component.\n\n## Table of Contents\n\n- [Basic Usage](#basic-usage)\n- [Column Definitions](#column-definitions)\n- [Search and Filtering](#search-and-filtering)\n- [Sorting Functionality](#sorting-functionality)\n- [Row Selection](#row-selection)\n- [Custom Column Styling and Actions](#custom-column-styling-and-actions)\n- [Practical Application Examples](#practical-application-examples)\n\n## Basic Usage\n\nTo use the EnhancedDataTable, you need to provide two basic parameters: `columns` (column definitions) and `data` (data source).\n\n```tsx\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useMyTableColumns } from \"./useMyTableColumns\";\n\nexport function MyTable({ data }) {\n  // Use custom hook to get column definitions\n  const columns = useMyTableColumns();\n\n  return (\n    <EnhancedDataTable\n      columns={columns}\n      data={data}\n      searchBarProps={{ placeholder: \"Search...\" }}\n    />\n  );\n}\n```\n\n## Column Definitions\n\nIt's recommended to create column definition hooks in separate files using `createColumnHelper` to get better type support.\n\n### Creating Basic Column Definition Files\n\n```tsx\n// useMyTableColumns.tsx\nimport { useMemo } from \"react\";\nimport { createColumnHelper, type ColumnDef } from \"@tanstack/react-table\";\nimport { MyDataType } from \"@/lib/types/myDataType\";\n\nconst columnHelper = createColumnHelper<MyDataType>();\n\nexport const useMyTableColumns = (): ColumnDef<MyDataType>[] => {\n  return useMemo(\n    () => [\n      columnHelper.accessor(\"name\", {\n        header: \"Name\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n      columnHelper.accessor(\"description\", {\n        header: \"Description\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n    ],\n    [],\n  );\n};\n```\n\n### Column Properties Explained\n\n- `header`: Column title, can be a string or React component\n- `cell`: Cell rendering function\n- `enableGlobalFilter`: Whether to include this column in global search\n- `enableColumnFilter`: Whether to enable column filtering\n- `filterFn`: Filter function type, e.g., \"arrIncludes\" for array fields\n- `id`: Custom column ID, required when using accessor function\n- `meta`: Used to set default sorting and other metadata\n\n### Creating Sortable Columns\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: ({ column }) => (\n    <Button\n      variant=\"ghost\"\n      onClick={() => column.toggleSorting(column.getIsSorted() === \"asc\")}\n      className=\"w-full justify-start px-0\"\n    >\n      Name\n      <ArrowUpDown className=\"h-4 w-4\" />\n    </Button>\n  ),\n  cell: (info) => info.getValue(),\n  enableGlobalFilter: true,\n  // Set as default sort column\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: false,\n  },\n});\n```\n\n## Search and Filtering\n\n### Enabling Global Search\n\nProvide the `searchBarProps` parameter and ensure relevant columns have `enableGlobalFilter: true`:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  searchBarProps={{ placeholder: \"Search...\" }}\n/>\n```\n\n### Column Filtering Functionality\n\nEnhancedDataTable provides single‑value dropdown filtering for array‑type columns. :\n\n1. Set `enableColumnFilter: true`\n2. Set `filterFn: \"arrIncludes\"`\n\n#### Enabling Dropdown Filtering for Array Type Columns\n\n```tsx\n// Using dropdown filtering for tag arrays\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2\">\n      {info.getValue().map((tag) => (\n        <span key={tag} className=\"px-2 py-1 bg-gray-100 rounded-md\">\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true, // Enable column filtering\n  filterFn: \"arrIncludes\", // Specify array filtering function\n});\n```\n\n#### Handling Arrays from Non-Standard Data Sources\n\nFor array data not in default fields, you can use custom accessors:\n\n```tsx\n// Handling nested objects or transforming data\ncolumnHelper.accessor(\n  (row) => row.metadata?.categories || [], // Extract array from nested object\n  {\n    id: \"categoriesDisplay\", // Must provide unique ID\n    header: \"Categories\",\n    cell: (info) => (\n      <div className=\"flex flex-wrap gap-2\">\n        {info.getValue().map((category) => (\n          <span key={category} className=\"badge\">\n            {category}\n          </span>\n        ))}\n      </div>\n    ),\n    enableColumnFilter: true,\n    filterFn: \"arrIncludes\",\n  },\n);\n```\n\n#### Automatic Filter UI Generation\n\nWhen the following conditions are met, the table will automatically generate dropdown filter menus for columns:\n\n1. Column has `enableColumnFilter: true`\n2. Column uses `filterFn: \"arrIncludes\"`\n\nFilters will be displayed in the top toolbar of the table, allowing users to select multiple values for filtering.\n\n## Sorting Functionality\n\n### Setting Default Sorting\n\nYou can set default sorting in two ways:\n\n1. Using the `meta` property in column definition:\n\n```tsx\ncolumnHelper.accessor(\"createdAt\", {\n  header: \"Created At\",\n  cell: (info) => new Date(info.getValue()).toLocaleString(),\n  id: \"createdAt\",\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: true, // Default descending order\n  },\n});\n```\n\n2. Through the component's `defaultSorting` property:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  defaultSorting={[\n    {\n      id: \"createdAt\",\n      desc: true,\n    },\n  ]}\n/>\n```\n\n## Row Selection\n\nTo enable row selection functionality, you need to provide `rowSelectionProps`:\n\n```tsx\nconst [rowSelection, setRowSelection] = useState({});\n\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  rowSelectionProps={{\n    rowSelection,\n    onRowSelectionChange: setRowSelection,\n    getRowId: (row) => row.id,\n  }}\n/>;\n```\n\nThis will add a selection checkbox column to the left of the table, allowing users to select multiple rows of data.\n\n## Custom Column Styling and Actions\n\n### Image and Text Combination Column\n\n```tsx\ncolumnHelper.accessor(\"app_name\", {\n  header: \"App Name\",\n  cell: (info) => {\n    const appName = info.getValue();\n    return (\n      <div className=\"flex items-center gap-3\">\n        <div className=\"relative h-5 w-5 shrink-0 overflow-hidden\">\n          {appsMap[appName]?.logo && (\n            <Image\n              src={appsMap[appName]?.logo || \"\"}\n              alt={`${appName} logo`}\n              fill\n              className=\"object-contain\"\n            />\n          )}\n        </div>\n        <IdDisplay id={appName} dim={false} />\n      </div>\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n### Tag Rendering\n\n```tsx\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2 overflow-hidden\">\n      {(info.getValue() || []).map((tag) => (\n        <span\n          key={tag}\n          className=\"rounded-md bg-gray-100 px-3 py-1 text-sm font-medium text-gray-600 border border-gray-200\"\n        >\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true,\n  filterFn: \"arrIncludes\",\n});\n```\n\n### Custom Action Buttons Column\n\n```tsx\ncolumnHelper.accessor(\n  (row) => row, // Get entire row data\n  {\n    id: \"actions\",\n    header: \"\",\n    cell: (info) => {\n      const item = info.getValue();\n      return (\n        <div className=\"space-x-2 flex\">\n          <Link href={`/items/${item.id}`}>\n            <Button variant=\"outline\" size=\"sm\">\n              Open\n            </Button>\n          </Link>\n          <Button variant=\"ghost\" size=\"sm\" className=\"text-red-600\">\n            <GoTrash />\n          </Button>\n        </div>\n      );\n    },\n    enableGlobalFilter: false,\n  },\n);\n```\n\n### Editable Cells\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: \"Name\",\n  cell: (ctx) => {\n    const item = ctx.row.original;\n    return (\n      <EditableCell\n        initialValue={item.name}\n        fieldName=\"name\"\n        itemId={item.id}\n        onUpdate={handleUpdate}\n      />\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n## Pagination\n\nEnhancedDataTable supports client-side pagination using TanStack Table’s built-in `getPaginationRowModel()`.\n\nTo enable pagination, pass the `paginationOptions` prop:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  paginationOptions={{\n    initialPageIndex: 0, // Default to first page (0-based)\n    initialPageSize: 10, // Number of entries per page\n  }}\n/>\n```\n\n## Practical Application Examples\n\n### App Configuration Table (with Icons, Category Filtering, and Toggle Switch)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAppConfigsTableColumns } from \"./useAppConfigsTableColumns\";\n\nexport function AppConfigsPage() {\n  const [appConfigs, setAppConfigs] = useState<AppConfig[]>([]);\n  // ...other states and logic\n\n  const appConfigsColumns = useAppConfigsTableColumns({\n    linkedAccountsCountMap,\n    appsMap,\n    updateAppConfigs: loadAllData,\n  });\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={appConfigs}\n        columns={appConfigsColumns}\n        searchBarProps={{ placeholder: \"Search apps...\" }}\n      />\n    </div>\n  );\n}\n```\n\n### Agents Table (with Editable Cells and Custom Actions)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAgentsTableColumns } from \"./useAgentsTableColumns\";\n\nexport function AgentsPage() {\n  const [agents, setAgents] = useState<Agent[]>([]);\n  // ...other states and logic\n\n  const columns = useAgentsTableColumns(\n    projectId,\n    handleDeleteAgent,\n    reloadAgents,\n    handleInstructionsSave,\n  );\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={agents}\n        columns={columns}\n        searchBarProps={{ placeholder: \"Search agents...\" }}\n      />\n    </div>\n  );\n}\n```\n","isInternal":false,"tokens":2387,"sizeBytes":10155}],"systemPromptSnippet":"<yakaai_skills repo=\"aipotheosis-labs/aci\">\n<!-- File: CLAUDE.md (Tokens: ~1244 | Category: claude-rule) -->\n# CLAUDE.md\n\nThis file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.\n\n## Project Overview\n\nACI.dev is an open-source tool-calling platform providing 600+ integrations for AI agents. It serves as infrastructure for Unified MCP (Model Context Protocol) servers and VibeOps automated DevOps workflows. The platform handles multi-tenant authentication, granular permissions, and dynamic tool discovery.\n\n## Repository Structure\n\nThis is a **monorepo** with two main components:\n\n- `backend/` - FastAPI server with 600+ integrations (Python 3.12+, PostgreSQL, uv package manager)\n- `frontend/` - Next.js 15 developer portal (React 19, TypeScript, Tailwind CSS, shadcn/ui)\n\n## Essential Development Commands\n\n### Backend Commands\n\n```bash\ncd backend\nuv sync                                          # Install dependencies\nsource .venv/bin/activate                       # Activate virtual environment\ndocker compose up --build                       # Start all services (includes PostgreSQL with pgvector)\ndocker compose exec runner ./scripts/seed_db.sh # Seed database\n\n# Database management\ndocker compose exec runner alembic upgrade head                    # Apply migrations\ndocker compose exec runner alembic revision --autogenerate -m \"description\" # Create migration\n\n# Testing and quality\ndocker compose exec test-runner pytest         # Run tests\nruff format .                                   # Format code\nruff check .                                    # Lint code\nmypy .                                          # Type checking\n\n# Admin CLI\ndocker compose exec runner python -m aci.cli --help\ndocker compose exec runner python -m aci.cli upsert-app --app-file ./apps/gmail/app.json\n```\n\n### Frontend Commands\n\n```bash\ncd frontend\nnpm install --legacy-peer-deps                 # Install dependencies (React 19 compatibility required)\ncp .env.example .env                           # Setup environment\nnpm run dev                                    # Start development server\n\n# Code quality\nnpm run format                                 # Prettier formatting\nnpm run lint                                   # ESLint\nnpm run test                                   # Vitest in watch mode\nnpm run build                                  # Production build\n```\n\n## Core Architecture\n\n### Database Models (`backend/aci/common/db/sql_models.py`)\n\n- **Project**: Multi-tenant container for API keys, apps, and agents\n- **Agent**: Logical actors that access the platform (tied to API keys)\n- **App**: Third-party service integrations (Gmail, Slack, etc.)\n- **Function**: Individual API endpoints within apps\n- **LinkedAccount**: User authentication credentials for OAuth/API keys\n- **AppConfiguration**: User-specific app settings and permissions\n\n### Backend Structure (`backend/aci/`)\n\n- `server/` - FastAPI application with routes, middleware, app_connectors\n- `common/db/` - SQLAlchemy models and CRUD operations\n- `common/schemas/` - Pydantic models for validation\n- `cli/` - Admin command-line interface\n- `apps/` - 600+ integration definitions as JSON configs\n\n### Frontend Structure (`frontend/src/`)\n\n- `app/` - Next.js App Router pages (apps/, playground/, settings/)\n- `components/` - Reusable UI components with shadcn/ui\n- `lib/` - API clients and utilities\n- `hooks/` - Custom React hooks\n\n## Integration System\n\nEach integration requires two JSON files in `backend/apps/{app_name}/`:\n\n- `app.json` - Metadata, authentication schemes, categories, visibility\n- `functions.json` - API endpoints and their schemas\n\nApps support OAuth2, API keys, and no-auth patterns with encrypted credential storage.\n\n## Key Services (Docker Compose)\n\n- **server**: FastAPI backend (port 8000)\n- **db**: PostgreSQL with pgvector extension (port 5432)\n- **aws**: LocalStack for AWS services (port 4566)\n- **runner**: Utility container for CLI commands and database operations\n- **test-runner**: Isolated testing environment\n\n## Authentication & API Structure\n\n### Authentication Methods\n\n1. **PropelAuth**: Web portal authentication for developers\n2. **API Keys**: Agent/programmatic access via `X-API-KEY` header\n3. **OAuth2/API Keys**: End-user service authentication stored as LinkedAccounts\n\n### Core API Endpoints (`/v1/`)\n\n- `/apps` - Browse and configure integrations\n- `/functions` - Execute tool calls with semantic search using pgvector\n- `/linked-accounts` - Manage user authentication\n- `/projects` - Project and agent management\n- `/playground` - Interactive agent testing\n\n## Function Execution Flow\n\n1. **Discovery**: Semantic search finds relevant functions using OpenAI embeddings\n2. **Authentication**: Validates API key and linked account permissions\n3. **Execution**: Routes calls through appropriate connectors\n4. **Logging**: Comprehensive request/response tracking with Sentry/Logfire\n\n## Local Development Setup\n\n1. **Backend**: Copy `.env.example` to `.env.local`, set OpenAI API keys, run `docker compose up --build`\n2. **Frontend**: Copy `.env.example` to `.env`, run `npm install --legacy-peer-deps`\n3. **Database**: Run `docker compose exec runner ./scripts/seed_db.sh` to populate with sample data\n\n## Package Managers\n\n- **Backend**: Uses `uv` (modern Python package manager) - do not use pip/poetry\n- **Frontend**: Uses npm with `--legacy-peer-deps` flag required for React 19 compatibility\n\n## Testing\n\n- **Backend**: `docker compose exec test-runner pytest` (isolated test environment)\n- **Frontend**: `npm run test` (Vitest in watch mode)\n\n## Code Quality Tools\n\n- **Backend**: ruff (formatting/linting), mypy (type checking), pre-commit hooks\n- **Frontend**: Prettier (formatting), ESLint (linting), TypeScript compiler\n\n<!-- File: frontend/src/components/ui-extensions/enhanced-data-table/README.md (Tokens: ~2387 | Category: plugin-manifest) -->\n# EnhancedDataTable Component Documentation\n\nThe EnhancedDataTable is a data table component built on TanStack Table (React Table), providing advanced features such as sorting, filtering, searching, and row selection. This documentation will help you quickly understand and effectively use this component.\n\n## Table of Contents\n\n- [Basic Usage](#basic-usage)\n- [Column Definitions](#column-definitions)\n- [Search and Filtering](#search-and-filtering)\n- [Sorting Functionality](#sorting-functionality)\n- [Row Selection](#row-selection)\n- [Custom Column Styling and Actions](#custom-column-styling-and-actions)\n- [Practical Application Examples](#practical-application-examples)\n\n## Basic Usage\n\nTo use the EnhancedDataTable, you need to provide two basic parameters: `columns` (column definitions) and `data` (data source).\n\n```tsx\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useMyTableColumns } from \"./useMyTableColumns\";\n\nexport function MyTable({ data }) {\n  // Use custom hook to get column definitions\n  const columns = useMyTableColumns();\n\n  return (\n    <EnhancedDataTable\n      columns={columns}\n      data={data}\n      searchBarProps={{ placeholder: \"Search...\" }}\n    />\n  );\n}\n```\n\n## Column Definitions\n\nIt's recommended to create column definition hooks in separate files using `createColumnHelper` to get better type support.\n\n### Creating Basic Column Definition Files\n\n```tsx\n// useMyTableColumns.tsx\nimport { useMemo } from \"react\";\nimport { createColumnHelper, type ColumnDef } from \"@tanstack/react-table\";\nimport { MyDataType } from \"@/lib/types/myDataType\";\n\nconst columnHelper = createColumnHelper<MyDataType>();\n\nexport const useMyTableColumns = (): ColumnDef<MyDataType>[] => {\n  return useMemo(\n    () => [\n      columnHelper.accessor(\"name\", {\n        header: \"Name\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n      columnHelper.accessor(\"description\", {\n        header: \"Description\",\n        cell: (info) => info.getValue(),\n        enableGlobalFilter: true,\n      }),\n    ],\n    [],\n  );\n};\n```\n\n### Column Properties Explained\n\n- `header`: Column title, can be a string or React component\n- `cell`: Cell rendering function\n- `enableGlobalFilter`: Whether to include this column in global search\n- `enableColumnFilter`: Whether to enable column filtering\n- `filterFn`: Filter function type, e.g., \"arrIncludes\" for array fields\n- `id`: Custom column ID, required when using accessor function\n- `meta`: Used to set default sorting and other metadata\n\n### Creating Sortable Columns\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: ({ column }) => (\n    <Button\n      variant=\"ghost\"\n      onClick={() => column.toggleSorting(column.getIsSorted() === \"asc\")}\n      className=\"w-full justify-start px-0\"\n    >\n      Name\n      <ArrowUpDown className=\"h-4 w-4\" />\n    </Button>\n  ),\n  cell: (info) => info.getValue(),\n  enableGlobalFilter: true,\n  // Set as default sort column\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: false,\n  },\n});\n```\n\n## Search and Filtering\n\n### Enabling Global Search\n\nProvide the `searchBarProps` parameter and ensure relevant columns have `enableGlobalFilter: true`:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  searchBarProps={{ placeholder: \"Search...\" }}\n/>\n```\n\n### Column Filtering Functionality\n\nEnhancedDataTable provides single‑value dropdown filtering for array‑type columns. :\n\n1. Set `enableColumnFilter: true`\n2. Set `filterFn: \"arrIncludes\"`\n\n#### Enabling Dropdown Filtering for Array Type Columns\n\n```tsx\n// Using dropdown filtering for tag arrays\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2\">\n      {info.getValue().map((tag) => (\n        <span key={tag} className=\"px-2 py-1 bg-gray-100 rounded-md\">\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true, // Enable column filtering\n  filterFn: \"arrIncludes\", // Specify array filtering function\n});\n```\n\n#### Handling Arrays from Non-Standard Data Sources\n\nFor array data not in default fields, you can use custom accessors:\n\n```tsx\n// Handling nested objects or transforming data\ncolumnHelper.accessor(\n  (row) => row.metadata?.categories || [], // Extract array from nested object\n  {\n    id: \"categoriesDisplay\", // Must provide unique ID\n    header: \"Categories\",\n    cell: (info) => (\n      <div className=\"flex flex-wrap gap-2\">\n        {info.getValue().map((category) => (\n          <span key={category} className=\"badge\">\n            {category}\n          </span>\n        ))}\n      </div>\n    ),\n    enableColumnFilter: true,\n    filterFn: \"arrIncludes\",\n  },\n);\n```\n\n#### Automatic Filter UI Generation\n\nWhen the following conditions are met, the table will automatically generate dropdown filter menus for columns:\n\n1. Column has `enableColumnFilter: true`\n2. Column uses `filterFn: \"arrIncludes\"`\n\nFilters will be displayed in the top toolbar of the table, allowing users to select multiple values for filtering.\n\n## Sorting Functionality\n\n### Setting Default Sorting\n\nYou can set default sorting in two ways:\n\n1. Using the `meta` property in column definition:\n\n```tsx\ncolumnHelper.accessor(\"createdAt\", {\n  header: \"Created At\",\n  cell: (info) => new Date(info.getValue()).toLocaleString(),\n  id: \"createdAt\",\n  meta: {\n    defaultSort: true,\n    defaultSortDesc: true, // Default descending order\n  },\n});\n```\n\n2. Through the component's `defaultSorting` property:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  defaultSorting={[\n    {\n      id: \"createdAt\",\n      desc: true,\n    },\n  ]}\n/>\n```\n\n## Row Selection\n\nTo enable row selection functionality, you need to provide `rowSelectionProps`:\n\n```tsx\nconst [rowSelection, setRowSelection] = useState({});\n\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  rowSelectionProps={{\n    rowSelection,\n    onRowSelectionChange: setRowSelection,\n    getRowId: (row) => row.id,\n  }}\n/>;\n```\n\nThis will add a selection checkbox column to the left of the table, allowing users to select multiple rows of data.\n\n## Custom Column Styling and Actions\n\n### Image and Text Combination Column\n\n```tsx\ncolumnHelper.accessor(\"app_name\", {\n  header: \"App Name\",\n  cell: (info) => {\n    const appName = info.getValue();\n    return (\n      <div className=\"flex items-center gap-3\">\n        <div className=\"relative h-5 w-5 shrink-0 overflow-hidden\">\n          {appsMap[appName]?.logo && (\n            <Image\n              src={appsMap[appName]?.logo || \"\"}\n              alt={`${appName} logo`}\n              fill\n              className=\"object-contain\"\n            />\n          )}\n        </div>\n        <IdDisplay id={appName} dim={false} />\n      </div>\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n### Tag Rendering\n\n```tsx\ncolumnHelper.accessor(\"tags\", {\n  header: \"Tags\",\n  cell: (info) => (\n    <div className=\"flex flex-wrap gap-2 overflow-hidden\">\n      {(info.getValue() || []).map((tag) => (\n        <span\n          key={tag}\n          className=\"rounded-md bg-gray-100 px-3 py-1 text-sm font-medium text-gray-600 border border-gray-200\"\n        >\n          {tag}\n        </span>\n      ))}\n    </div>\n  ),\n  enableGlobalFilter: true,\n  enableColumnFilter: true,\n  filterFn: \"arrIncludes\",\n});\n```\n\n### Custom Action Buttons Column\n\n```tsx\ncolumnHelper.accessor(\n  (row) => row, // Get entire row data\n  {\n    id: \"actions\",\n    header: \"\",\n    cell: (info) => {\n      const item = info.getValue();\n      return (\n        <div className=\"space-x-2 flex\">\n          <Link href={`/items/${item.id}`}>\n            <Button variant=\"outline\" size=\"sm\">\n              Open\n            </Button>\n          </Link>\n          <Button variant=\"ghost\" size=\"sm\" className=\"text-red-600\">\n            <GoTrash />\n          </Button>\n        </div>\n      );\n    },\n    enableGlobalFilter: false,\n  },\n);\n```\n\n### Editable Cells\n\n```tsx\ncolumnHelper.accessor(\"name\", {\n  header: \"Name\",\n  cell: (ctx) => {\n    const item = ctx.row.original;\n    return (\n      <EditableCell\n        initialValue={item.name}\n        fieldName=\"name\"\n        itemId={item.id}\n        onUpdate={handleUpdate}\n      />\n    );\n  },\n  enableGlobalFilter: true,\n});\n```\n\n## Pagination\n\nEnhancedDataTable supports client-side pagination using TanStack Table’s built-in `getPaginationRowModel()`.\n\nTo enable pagination, pass the `paginationOptions` prop:\n\n```tsx\n<EnhancedDataTable\n  columns={columns}\n  data={data}\n  paginationOptions={{\n    initialPageIndex: 0, // Default to first page (0-based)\n    initialPageSize: 10, // Number of entries per page\n  }}\n/>\n```\n\n## Practical Application Examples\n\n### App Configuration Table (with Icons, Category Filtering, and Toggle Switch)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAppConfigsTableColumns } from \"./useAppConfigsTableColumns\";\n\nexport function AppConfigsPage() {\n  const [appConfigs, setAppConfigs] = useState<AppConfig[]>([]);\n  // ...other states and logic\n\n  const appConfigsColumns = useAppConfigsTableColumns({\n    linkedAccountsCountMap,\n    appsMap,\n    updateAppConfigs: loadAllData,\n  });\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={appConfigs}\n        columns={appConfigsColumns}\n        searchBarProps={{ placeholder: \"Search apps...\" }}\n      />\n    </div>\n  );\n}\n```\n\n### Agents Table (with Editable Cells and Custom Actions)\n\n```tsx\n// In page component\nimport { EnhancedDataTable } from \"@/components/ui-extensions/enhanced-data-table/data-table\";\nimport { useAgentsTableColumns } from \"./useAgentsTableColumns\";\n\nexport function AgentsPage() {\n  const [agents, setAgents] = useState<Agent[]>([]);\n  // ...other states and logic\n\n  const columns = useAgentsTableColumns(\n    projectId,\n    handleDeleteAgent,\n    reloadAgents,\n    handleInstructionsSave,\n  );\n\n  return (\n    <div>\n      <EnhancedDataTable\n        data={agents}\n        columns={columns}\n        searchBarProps={{ placeholder: \"Search agents...\" }}\n      />\n    </div>\n  );\n}\n```\n</yakaai_skills>"}