{"id":20004201,"url":"https://github.com/brunostjohn/perplexideez","last_synced_at":"2025-04-08T14:03:57.240Z","repository":{"id":261065993,"uuid":"883152473","full_name":"brunostjohn/perplexideez","owner":"brunostjohn","description":"Search the web and your self-hosted apps using local AI agents.","archived":false,"fork":false,"pushed_at":"2024-11-17T21:26:34.000Z","size":52697,"stargazers_count":430,"open_issues_count":12,"forks_count":30,"subscribers_count":6,"default_branch":"main","last_synced_at":"2025-04-01T12:06:52.790Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"Svelte","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"agpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/brunostjohn.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-11-04T13:20:14.000Z","updated_at":"2025-03-30T18:44:12.000Z","dependencies_parsed_at":"2024-11-04T14:38:07.679Z","dependency_job_id":null,"html_url":"https://github.com/brunostjohn/perplexideez","commit_stats":null,"previous_names":["brunostjohn/perplexideez"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/brunostjohn%2Fperplexideez","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/brunostjohn%2Fperplexideez/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/brunostjohn%2Fperplexideez/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/brunostjohn%2Fperplexideez/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/brunostjohn","download_url":"https://codeload.github.com/brunostjohn/perplexideez/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247856541,"owners_count":21007620,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-13T05:28:54.383Z","updated_at":"2025-04-08T14:03:57.213Z","avatar_url":"https://github.com/brunostjohn.png","language":"Svelte","funding_links":[],"categories":["Svelte","A01_文本生成_文本对话"],"sub_categories":["大语言对话模型及数据"],"readme":"\u003cbr/\u003e\n\u003cdiv align=\"center\"\u003e\n\u003ca href=\"assets/icon-frameless.png\"\u003e\n\u003cimg src=\"assets/icon-frameless.png\" alt=\"Logo\" width=\"100\" height=\"100\"\u003e\n\u003c/a\u003e\n\u003ch3 align=\"center\"\u003ePerplexideez\u003c/h3\u003e\n\u003cp align=\"center\"\u003e\nSelf-hosted AI-powered search.\n\u003cbr/\u003e\n\u003cbr/\u003e\n\u003ca href=\"https://github.com/brunostjohn/perplexideez/issues/new?labels=bug\u0026template=bug_report.md\"\u003eReport Bug\u003c/a\u003e ·\n\u003ca href=\"https://github.com/brunostjohn/perplexideez/issues/new?labels=enhancement\u0026template=feature_request.md\"\u003eRequest Feature\u003c/a\u003e\n\u003c/p\u003e\n\u003c/div\u003e\n\n\u003ch3 id=\"aboutTheProject\"\u003eAbout The Project\u003c/h3\u003e\n\n![Screenshot](/assets/browser.png)\n\nThere are many self-hosted Perplexity clones out there. I chose to make my own as I was dissatisfied with their non-existent integration with other self-hosted services and lack of multi-user support. Perplexideez is backed by a Postgres database \u0026 either Ollama or OpenAI compatible endpoints. It searches the web using a SearXNG instance.\n\n### Table of Contents\n\n1. [About The Project](#aboutTheProject)\n2. [Features](#features)\n   1. [Search the web](#features-searchTheWeb)\n   2. [Know where conclusions come from](#features-knowWhere)\n      1. [Learn even more](#features-knowWhere-learnMore)\n   3. [Keep track of your most interesting searches](#features-keepTrack)\n   4. [Customise your experience](#features-customise)\n   5. [Multi-user support \u0026 SSO](#features-multiUser)\n   6. [Sharing searches](#features-sharing)\n      1. [Simple UI](#features-sharing-simple)\n      2. [Access control](#features-sharing-accessControl)\n      3. [Good looking embeds](#features-sharing-embeds)\n   7. [Deployment](#features-deployment)\n      1. [Security](#features-deployment-security)\n      2. [Statelessness](#features-deployment-statelessness)\n3. [Deploying](#deploying)\n   1. [Container images](#deploying-images)\n   2. [Docker](#deploying-docker)\n   3. [Kubernetes](#deploying-kube)\n   4. [Bare metal](#deploying-metal)\n   5. [General notes about dependencies](#deploying-notes)\n      1. [SearXNG](#deploying-notes-searxng)\n   6. [Environment variables](#deploying-env)\n      1. [Data storage](#deploying-env-data)\n      2. [App setup](#deploying-env-app)\n      3. [SSO](#deploying-env-sso)\n         1. [Notes](#deploying-env-sso-notes)\n      4. [SearXNG](#deploying-env-searxng)\n      5. [AI setup](#deploying-env-ai)\n         1. [OpenAI](#deploying-env-ai-openai)\n         2. [Ollama](#deploying-env-ai-ollama)\n4. [Built with](#builtWith)\n5. [Developing locally](#developingLocally)\n   1. [Prerequisites](#developingLocally-pre)\n   2. [Installation](#developingLocally-install)\n6. [Roadmap](#roadmap)\n7. [Contributing](#contributing)\n8. [License](#license)\n9. [Contact](#contact)\n10. [Acknowledgments](#acknowledgments)\n\n\u003ch3 id=\"features\"\u003eFeatures\u003c/h3\u003e\n\n\u003ch4 id=\"features-searchTheWeb\"\u003e Search the web \u003c/h4\u003e\n\n![Screenshot](/assets/search.png)\n\nLet AI do the hard work of sifting through search results for you.\n\n\u003ch4 id=\"features-knowWhere\"\u003e Know where conclusions come from \u003c/h4\u003e\n\n![Screenshot](/assets/sources.png)\n\nDon't worry about hallucinations ruining your research. Just hover over the source annotation your LLM inserted and see the source it used. Click on it, and view the source directly.\n\n\u003ch5 id=\"features-knowWhere-learnMore\"\u003e Learn even more \u003c/h5\u003e\n\n![Screenshot](/assets/follow-up.png)\n\nYour LLM will generate great follow-up questions for you. This way, you can ask about what interested you in the response without typing a single second.\n\n\u003ch4 id=\"features-keepTrack\"\u003e Keep track of your most interesting searches \u003c/h4\u003e\n\n![Screenshot](/assets/favourites.png)\n\nStash your favourite searches as favourites. This way, you'll never lose them.\n\n\u003ch4 id=\"features-customise\"\u003e Customise your experience \u003c/h4\u003e\n\n![Screenshot](/assets/model-picker.png)\n\nPerplexideez lets you use different models for different tasks, as appropriate. The robust environment variables and UI configuration allow you to make sure your self hosted resources are not overused.\n\n\u003ch4 id=\"features-multiUser\"\u003e Multi-user support \u0026 SSO \u003c/h4\u003e\n\n![Screenshot](/assets/multiuser.png)\n\nPerplexideez supports many user accounts, with separated data, and using OIDC SSO. You can disable either sign up, password login, or both.\n\n\u003ch4 id=\"features-sharing\"\u003e Sharing searches \u003c/h4\u003e\n\n\u003ch5 id=\"featuers-sharing-simple\"\u003e Simple UI \u003c/h5\u003e\n\n![Screenshot](/assets/sharing.png)\n\nPerplexideez allows you to share links to others with the results of your searches. This way, you can send the interesting stuff to your friends easily.\n\n\u003ch5 id=\"features-sharing-accessControl\"\u003e Access control \u003c/h5\u003e\n\n![Screenshot](/assets/access-control.png)\n\nWhen sharing a link, you can make sure only the people you want have access to it. Reroll the link's ID, require authentication to view, or disable it altogether.\n\n\u003ch5 id=\"features-sharing-embeds\"\u003e Good looking embeds \u003c/h5\u003e\n\n![Screenshot](/assets/embed.png)\n\nPerplexideez creates beautiful embeds for all the links you share publicly. This way, the people you send it to know what they'll be looking at.\n\n\u003ch4 id=\"features-deployment\"\u003e Deployment \u003c/h4\u003e\n\n\u003ch5 id=\"features-deployment-security\"\u003e Security \u003c/h5\u003e\n\nAll of the containers provided by this project run as non-root by default. They're ready to be deployed in rootless environments.\n\n\u003ch5 id=\"features-deployment-statelessness\"\u003e Statelessness \u003c/h5\u003e\n\nSave for an in-progress generation, the containers are fully stateless. The feature that blocks exiting while a response is generated is still a work in progress, but they're ready to run in a Kubernetes environment without concern about rolling updates or higher numbers of replicas screwing things up.\n\n\u003ch2 id=\"deploying\"\u003e Deploying \u003c/h2\u003e\n\n\u003ch3 id=\"deploying-images\"\u003e Container images \u003c/h3\u003e\n\n- [`ghcr.io/brunostjohn/perplexideez/migrate`](https://github.com/brunostjohn/perplexideez/pkgs/container/perplexideez%2Fmigrate) performs required database migrations and prepares your Postgres instance to be used with Perplexideez. The only environment variable it requires is `DATABASE_URL`.\n- [`ghcr.io/brunostjohn/perplexideez/app`](https://github.com/brunostjohn/perplexideez/pkgs/container/perplexideez%2Fapp) is the app itself. It requires the full environment variables mentioned below.\n\n\u003ch3 id=\"deploying-docker\"\u003e Docker \u003c/h3\u003e\n\nUse the example Compose files in [`deploy/docker`](https://github.com/brunostjohn/perplexideez/tree/main/deploy/docker) to configure your own stack. These include the app, SearXNG, and a database. Use the `.env.example` to get started, before running rename to `.env` and make sure all the required values from the table below are filled out. The example stack **does not** provide neither Ollama nor OpenAI compatible endpoints. Setting that up is up to you.\n\n\u003ch3 id=\"deploying-kube\"\u003e Kubernetes \u003c/h3\u003e\n\nI am still working on the Helm chart for this app. Writing Helm charts is quite the process so I'm procrastinating it. For now, please use [my homelab Kubernetes manifests as an example for how to write your own to deploy this on your cluster](https://github.com/brunostjohn/homelab/tree/main/k8s/productivity/perplexideez).\n\n\u003ch3 id=\"deploying-metal\"\u003e Bare Metal \u003c/h3\u003e\n\nDue to a lack of control over these environments and high variance between them, deploying without using container images is unsupported and such issues will go closed due to being out of scope.\n\n\u003ch3 id=\"deploying-notes\"\u003e General notes about dependencies \u003c/h3\u003e\n\n\u003ch4 id=\"deploying-notes-searxng\"\u003e SearXNG \u003c/h4\u003e\n\n- In my testing, it's very likely that Perplexideez will trigger SearXNG's limiter. Therefore, unless someone finds a better solution, it's better left disabled.\n- All requests to SearXNG _will_ fail unless **JSON output is enabled**. This is important, so please remember to adjust your configuration.\n\n\u003ch3 id=\"deploying-env\"\u003e Environment Variables \u003c/h3\u003e\n\n\u003ch4 id=\"deploying-env-data\"\u003e Data Storage \u003c/h4\u003e\n\n| Name | Required | Value | Example |\n| ---- | -------- | ----- | ------- |\n| `DATABASE_URL` | ✅ | An URL to a Postgres database. | `postgresql://postgres:postgres@localhost:5432/postgres?schema=public` |\n\n\u003ch4 id=\"deploying-env-app\"\u003e App Setup \u003c/h4\u003e\n\n| Name | Required | Value | Example |\n| ---- | -------- | ----- | ------- |\n| `PUBLIC_BASE_URL` | ✅ | The public-facing URL to your instance. | `https://perplexideez.domain.com` \n| `RATE_LIMIT_SECRET` | ✅ | A secret generated with `openssl rand -base64 32` to be used for securing your sign in page. | N/A |\n| `AUTH_SECRET` | ✅ | A secret generated with `openssl rand -base64 32` to be used for securing your instance. | N/A |\n| `DISABLE_SIGN_UP` | ❌ (default: `false`) | Whether or not to disable signing up to your instance. | `true`/`false`\n| `LOG_LEVEL` | ❌ (default: `info`) | Which log level the app should use. | `trace`/`debug`/`info`/`warn`/`error` |\n| `LOG_MODE` | ❌ (default: `json`) | Whether to pretty print logs or use JSON logging. | `pretty`/`json` |\n| `METRICS_PORT` | ❌ (default: `9001`) | The port on which Prometheus metrics will be exposed. | `9001` |\n| `SKIP_CSRF_CHECK` | ❌ (default: `false`) | Makes the app skip CSRF checks. You most likely don't need this. Only set this if you know what you're doing. | `true`/`false` |\n| `USE_SECURE_COOKIES` | ❌ (default: `true`) | Make the app use secure cookies (only transferred over https). Only set this if you're not exposing your app. | `true`/`false` |\n\n\u003ch4 id=\"deploying-env-sso\"\u003e SSO \u003c/h4\u003e\n\n| Name | Required | Value | Example |\n| ---- | -------- | ----- | ------- |\n| `OIDC_CLIENT_ID` | ❌ | The client ID for your IDP. | N/A |\n| `OIDC_CLIENT_SECRET` | ❌ | The client secret for your IDP. | N/A |\n| `OIDC_ISSUER` | ❌ | The `.well-known` URL for you IDP. | `https://auth.authentik.com/application/o/perplexideez/.well-known/openid-configuration` |\n| `OIDC_SCOPES` | ❌ (default: `openid email profile`) | The OIDC scopes to request from your IDP. | `openid email profile` |\n| `PUBLIC_OIDC_NAME` | ❌ | The identity provider name to show in the app's UI. | `Zefir's Cloud` |\n| `DISABLE_PASSWORD_LOGIN` | ❌ (default: false) | Whether or not to disable password authentication and hide it from the UI. | `true`/`false` |\n\n\u003ch4 id=\"deploying-env-sso-notes\"\u003e SSO notes \u003c/h4\u003e\n\n- The redirect URL for this app is `https://perplexideez.yourdomain.com/auth/callback/generic-oauth`.\n\n\u003ch4 id=\"deploying-env-searxng\"\u003e SearXNG \u003c/h4\u003e\n\n| Name | Required | Value | Example |\n| ---- | -------- | ----- | ------- |\n| `SEARXNG_URL` | ✅ | The URL for your SearXNG instance. | `http://searxng:8080` |\n\n\u003ch4 id=\"deploying-env-ai\"\u003e AI Setup \u003c/h4\u003e\n\n| Name | Required | Value | Example |\n| ---- | -------- | ----- | ------- |\n| `LLM_MODE` | ✅ | `ollama` | Which LLM provider to use. | `ollama`/`openai` |\n| `LLM_SPEED_MODEL` | ✅ | The LLM to use for generating responses in \"Speed\" mode. | `gemma2:2b` |\n| `LLM_BALANCED_MODEL` | ✅ | The LLM to use for generating responses in \"Balanced\" mode. | `llama3.1:latest` |\n| `LLM_QUALITY_MODEL` | ✅ | The LLM to use for generating responses in \"Quality\" mode. | `qwen2.5:32b` |\n| `LLM_EMBEDDINGS_MODEL` | ✅ | The LLM to use for text embeddings. | `nomic-embed-text:latest` |\n| `LLM_TITLE_MODEL` | ✅ | The LLM to use for generating chat titles. | `llama3.1:latest` |\n| `LLM_EMOJI_MODEL` | ✅ | The LLM to use for generating chat emojis. | `llama3.1:latest` |\n| `LLM_IMAGE_SEARCH_MODEL` | ✅ | The LLM to use for image searching. | `llama3.1:latest` |\n| `LLM_VIDEO_SEARCH_MODEL` | ✅ | The LLM to use for video searching. | `llama3.1:latest` |\n\n\u003ch5 id=\"deploying-env-ai-openai\"\u003e OpenAI \u003c/h5\u003e\n\nRequired only if `LLM_MODE` is set to `openai`.\n\n| Name | Required | Value | Example |\n| ---- | -------- | ----- | ------- |\n| `OPENAI_BASE_URL` | ✅ | The base URL to your OpenAI compatible endpoints. | `https://chat.domain.com/v1` |\n| `OPENAI_API_KEY` | ✅ | The API key to use for requests. | `sk-1234` |\n\n\u003ch5 id=\"deploying-env-ai-ollama\"\u003e Ollama \u003c/h5\u003e\n\nRequired only if `LLM_MODE` is set to `ollama`.\n\n| Name | Required | Value | Example |\n| ---- | -------- | ----- | ------- |\n| `OLLAMA_URL` | ✅ | The URL for your Ollama instance. | `http://ollama:11434` |\n\n\n\u003ch2 id=\"builtWith\"\u003e Built With \u003c/h2\u003e\n\n- [SvelteKit](https://svelte.dev)\n- [TailwindCSS](https://tailwindcss.com/)\n- [Shadcn Svelte](https://www.shadcn-svelte.com/)\n- [tRPC](https://trpc.io/)\n- [Prisma](https://www.prisma.io/)\n- [AuthJS](https://authjs.dev/)\n- [TanStack Query](https://tanstack.com/query)\n- [Docker](https://docker.com/)\n- [Kubernetes](https://kubernetes.io)\n- [Langchain](https://langchain.com)\n\n\u003ch2 id=\"developingLocally\"\u003e Developing Locally \u003c/h2\u003e\n\nTo get a local copy up and running follow these simple example steps.\n\n\u003ch3 id=\"developingLocally-pre\"\u003e Prerequisites \u003c/h3\u003e\n\nYou need either an OpenAI API token/OpenAI compatible API or an Ollama instance running somewhere. The development container setup only provides Postgres and SearXNG.\n\n- pnpm\n  ```sh\n  corepack install pnpm\n  ```\n\n\u003ch3 id=\"developingLocally-install\"\u003e Installation \u003c/h3\u003e\n\n1. Clone the repo\n   ```sh\n   git clone https://github.com/brunostjohn/perplexideez.git\n   ```\n2. Install packages\n   ```sh\n   pnpm install\n   ```\n3. Create a `.env` file using the `.env.example`\n4. Start the development environment\n   ```sh\n   pnpm dev:up\n   ```\n5. Update the database schema\n   ```sh\n   pnpm db:push\n   ```\n6. Run the app\n   ```sh\n   pnpm dev\n   ```\n\n\u003ch2 id=\"roadmap\"\u003e Roadmap \u003c/h2\u003e\n\n- [x] Fully support web searching\n- [x] Shareable no-authentication links\n- [ ] Full statelessness\n  - [ ] Block exiting while generating, just in case\n  - [ ] Use Redis to persist internal generation state\n- [ ] View \u0026 explore image/video suggestions.\n- [ ] Favourites on the sidebar\n- [ ] Ensure deployments work\n  - [ ] Complete Helm chart for Kubernetes deployment\n- [ ] More agents\n  - [ ] Web agents\n  - [ ] Self-hosted app agents\n\nSee the [open issues](https://github.com/brunostjohn/perplexideez/issues) for a full list of proposed features (and known issues).\n\n\u003ch2 id=\"contributing\"\u003e Contributing \u003c/h2\u003e\n\nContributions are what make the open source community such an amazing place to learn, inspire, and create. Any contributions you make are **greatly appreciated**.\n\nIf you have a suggestion that would make this better, please fork the repo and create a pull request. You can also simply open an issue with the tag \"enhancement\".\nDon't forget to give the project a star! Thanks again!\n\n1. Fork the Project\n2. Create your Feature Branch (`git checkout -b feature/AmazingFeature`)\n3. Commit your Changes (`git commit -m 'Add some AmazingFeature'`)\n4. Push to the Branch (`git push origin feature/AmazingFeature`)\n5. Open a Pull Request\n\n\u003ch2 id=\"license\"\u003e License \u003c/h2\u003e\n\nDistributed under the AGPL License.\n\n\u003ch2 id=\"contact\"\u003e Contact \u003c/h2\u003e\n\nBruno St John - me@brunostjohn.com\n\n\u003ch2 id=\"acknowledgments\"\u003e Acknowledgments \u003c/h2\u003e\n\n- [The Perplexica team](https://github.com/ItzCrazyKns/Perplexica) for implementing the basis for a self-hosted search AI agent.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbrunostjohn%2Fperplexideez","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbrunostjohn%2Fperplexideez","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbrunostjohn%2Fperplexideez/lists"}