From 3ac0bfb252d2b6ad36bb8ef338854fccce82d0dd Mon Sep 17 00:00:00 2001 From: prodkt Date: Mon, 16 Sep 2024 12:34:38 -0600 Subject: [PATCH] commit config --- .changeset/README.md | 8 + .changeset/config.json | 11 + .commitlintrc.ts | 56 ++++ .editorconfig | 12 + .github/FUNDING.yml | 2 + .github/ISSUE_TEMPLATE/bug_report.md | 27 ++ .github/ISSUE_TEMPLATE/config.yaml | 1 + .github/ISSUE_TEMPLATE/feature_request.md | 19 ++ .../pull_request_template.md | 7 + .github/actions/setup/action.yml | 24 ++ .github/workflows/main.yml | 111 ++++++++ .github/workflows/pr-cleanup.yml | 20 ++ .github/workflows/pr.yml | 128 +++++++++ .github/workflows/release.yml | 30 +++ .gitignore | 158 +++++++++++ .husky/commit-msg | 1 + .husky/pre-commit | 1 + .husky/prepare-commit-msg | 2 + .markdownlint.json | 8 + .prettierignore | 11 + .vscode/extensions.json | 21 ++ .vscode/settings.json | 46 ++++ CODE_OF_CONDUCT.md | 132 +++++++++ CONTRIBUTING.md | 100 +++++++ LICENSE | 21 ++ README.md | 66 +++++ SECURITY.md | 7 + bun.lockb | Bin 0 -> 1009808 bytes cspell.config.yaml | 255 ++++++++++++++++++ eslint.config.js | 18 ++ package.json | 85 ++++++ prettier.config.js | 46 ++++ tsconfig.json | 7 + turbo.json | 113 ++++++++ 34 files changed, 1554 insertions(+) create mode 100644 .changeset/README.md create mode 100644 .changeset/config.json create mode 100644 .commitlintrc.ts create mode 100644 .editorconfig create mode 100644 .github/FUNDING.yml create mode 100644 .github/ISSUE_TEMPLATE/bug_report.md create mode 100644 .github/ISSUE_TEMPLATE/config.yaml create mode 100644 .github/ISSUE_TEMPLATE/feature_request.md create mode 100644 .github/PULL_REQUEST_TEMPLATE/pull_request_template.md create mode 100644 .github/actions/setup/action.yml create mode 100644 .github/workflows/main.yml create mode 100644 .github/workflows/pr-cleanup.yml create mode 100644 .github/workflows/pr.yml create mode 100644 .github/workflows/release.yml create mode 100644 .gitignore create mode 100644 .husky/commit-msg create mode 100644 .husky/pre-commit create mode 100644 .husky/prepare-commit-msg create mode 100644 .markdownlint.json create mode 100644 .prettierignore create mode 100644 .vscode/extensions.json create mode 100644 .vscode/settings.json create mode 100644 CODE_OF_CONDUCT.md create mode 100644 CONTRIBUTING.md create mode 100644 LICENSE create mode 100644 README.md create mode 100644 SECURITY.md create mode 100644 bun.lockb create mode 100644 cspell.config.yaml create mode 100644 eslint.config.js create mode 100644 package.json create mode 100644 prettier.config.js create mode 100644 tsconfig.json create mode 100644 turbo.json diff --git a/.changeset/README.md b/.changeset/README.md new file mode 100644 index 0000000..e5b6d8d --- /dev/null +++ b/.changeset/README.md @@ -0,0 +1,8 @@ +# Changesets + +Hello and welcome! This folder has been automatically generated by `@changesets/cli`, a build tool that works +with multi-package repos, or single-package repos to help you version and publish your code. You can +find the full documentation for it [in our repository](https://github.com/changesets/changesets) + +We have a quick list of common questions to get you started engaging with this project in +[our documentation](https://github.com/changesets/changesets/blob/main/docs/common-questions.md) diff --git a/.changeset/config.json b/.changeset/config.json new file mode 100644 index 0000000..91b6a95 --- /dev/null +++ b/.changeset/config.json @@ -0,0 +1,11 @@ +{ + "$schema": "https://unpkg.com/@changesets/config@3.0.0/schema.json", + "changelog": "@changesets/cli/changelog", + "commit": false, + "fixed": [], + "linked": [], + "access": "restricted", + "baseBranch": "main", + "updateInternalDependencies": "patch", + "ignore": [] +} diff --git a/.commitlintrc.ts b/.commitlintrc.ts new file mode 100644 index 0000000..0d99793 --- /dev/null +++ b/.commitlintrc.ts @@ -0,0 +1,56 @@ +import { getWorkspacePackageNames } from './scripts/utils' + +// ------------------------------------------------------------------ + +// -- CUSTOM COMMITLINT CONFIGURATION -- +// This configuration is used to enforce the scope-enum rule. +// The scope-enum rule requires that the scope of a commit message +// must be one of the defined values. +// The defined values are the package names of the workspace. +// The package names are extracted from the package.json files. +// +// This was previously achieved using @commitlint/config-pnpm-scopes +// which provides a custom commitlint configuration. + +// ------------------------------------------------------------------ + +interface Context { + cwd?: string +} + +// ------------------------------------------------------------------ + +/** + * Function to get all projects in the workspace + * @param context The context object + * @returns An array of all projects in the workspace + */ +function getProjects(context?: Context): string[] { + const ctx = context ?? {} + const cwd = ctx.cwd ?? process.cwd() + + return getWorkspacePackageNames(cwd) + .reduce((projects: string[], name) => { + if (name.startsWith('@')) { + const project = name.split('/')[1] + + if (typeof project === 'string') { + projects.push(project) + } + + projects.push(name) + } + + return projects + }, []) + .sort() +} + +// We are exporting a custom commitlint configuration +export default { + extends: ['@commitlint/config-conventional'], + utils: { getProjects }, + rules: { + 'scope-enum': (ctx: Context) => [2, 'always', getProjects(ctx)], + }, +} diff --git a/.editorconfig b/.editorconfig new file mode 100644 index 0000000..1166a4a --- /dev/null +++ b/.editorconfig @@ -0,0 +1,12 @@ +# EditorConfig is awesome: https://EditorConfig.org + +# top-most EditorConfig file +root = true + +[*] +indent_style = space +indent_size = 2 +end_of_line = lf +charset = utf-8 +trim_trailing_whitespace = true +insert_final_newline = false \ No newline at end of file diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml new file mode 100644 index 0000000..b7c5cc9 --- /dev/null +++ b/.github/FUNDING.yml @@ -0,0 +1,2 @@ +# These are supported funding model platforms +github: [prodkt] diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md new file mode 100644 index 0000000..8786bfe --- /dev/null +++ b/.github/ISSUE_TEMPLATE/bug_report.md @@ -0,0 +1,27 @@ +--- +name: Bug report +about: Create a report to help us improve +title: '' +labels: '' +assignees: '' +--- + +**Describe the bug** +A clear and concise description of what the bug is. + +**To Reproduce** +Steps to reproduce the behavior: + +1. Go to '...' +2. Click on '....' +3. Scroll down to '....' +4. See error + +**Expected behavior** +A clear and concise description of what you expected to happen. + +**Screenshots** +If applicable, add screenshots to help explain your problem. + +**Additional context** +Add any other context about the problem here. diff --git a/.github/ISSUE_TEMPLATE/config.yaml b/.github/ISSUE_TEMPLATE/config.yaml new file mode 100644 index 0000000..3ba13e0 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/config.yaml @@ -0,0 +1 @@ +blank_issues_enabled: false diff --git a/.github/ISSUE_TEMPLATE/feature_request.md b/.github/ISSUE_TEMPLATE/feature_request.md new file mode 100644 index 0000000..2f28cea --- /dev/null +++ b/.github/ISSUE_TEMPLATE/feature_request.md @@ -0,0 +1,19 @@ +--- +name: Feature request +about: Suggest an idea for this project +title: '' +labels: '' +assignees: '' +--- + +**Is your feature request related to a problem? Please describe.** +A clear and concise description of what the problem is. Ex. I'm always frustrated when [...] + +**Describe the solution you'd like** +A clear and concise description of what you want to happen. + +**Describe alternatives you've considered** +A clear and concise description of any alternative solutions or features you've considered. + +**Additional context** +Add any other context or screenshots about the feature request here. diff --git a/.github/PULL_REQUEST_TEMPLATE/pull_request_template.md b/.github/PULL_REQUEST_TEMPLATE/pull_request_template.md new file mode 100644 index 0000000..b89b6ff --- /dev/null +++ b/.github/PULL_REQUEST_TEMPLATE/pull_request_template.md @@ -0,0 +1,7 @@ +Fixes # + +## Proposed Changes + +- +- +- diff --git a/.github/actions/setup/action.yml b/.github/actions/setup/action.yml new file mode 100644 index 0000000..091b4b0 --- /dev/null +++ b/.github/actions/setup/action.yml @@ -0,0 +1,24 @@ +name: 'Setup' +description: 'Common setup steps for Actions' + +runs: + using: composite + steps: + - uses: oven-sh/setup-bun@v1 + name: Install bun + + - uses: actions/cache@v4 + name: Setup bun cache + with: + path: ~/.bun/install/cache + key: ${{ runner.os }}-${{ matrix.bun }}-bun-${{ hashFiles('**/bun.lockb') }} + restore-keys: | + ${{ runner.os }}-${{ matrix.bun }}-bun- + + - name: Install dependencies + shell: bash + run: bun install + + - name: Install Playwright Browsers + shell: bash + run: bun playwright install --with-deps diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml new file mode 100644 index 0000000..b12142c --- /dev/null +++ b/.github/workflows/main.yml @@ -0,0 +1,111 @@ +name: Main CI + +on: + push: + branches: + - main + +env: + # These are needed to enable turborepo's remote task caching + TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }} + TURBO_TEAM: ${{ vars.TURBO_TEAM }} + +jobs: + spell-and-md-lint: + name: Spellcheck and Markdown Lint + runs-on: ubuntu-latest + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 2 + + - name: Setup + uses: ./.github/actions/setup + + - name: Checks + run: bun turbo lint:md lint:spell + + web: + name: Web CI + runs-on: ubuntu-latest + + environment: Production + + env: + # Database URL + DATABASE_URL: ${{ secrets.DATABASE_URL }} + + # Auth Secret + AUTH_SECRET: ${{ secrets.AUTH_SECRET }} + + # Github OAuth + AUTH_GITHUB_ID: ${{ secrets.AUTH_GITHUB_ID }} + AUTH_GITHUB_SECRET: ${{ secrets.AUTH_GITHUB_SECRET }} + + # Google OAuth + AUTH_GOOGLE_ID: ${{ secrets.AUTH_GOOGLE_ID }} + AUTH_GOOGLE_SECRET: ${{ secrets.AUTH_GOOGLE_SECRET }} + + # Uploadthing + UPLOADTHING_SECRET: ${{ secrets.UPLOADTHING_SECRET }} + UPLOADTHING_APP_ID: ${{ secrets.UPLOADTHING_APP_ID }} + + # Unkey + UNKEY_ROOT_KEY: ${{ secrets.UNKEY_ROOT_KEY }} + UNKEY_NAMESPACE: ${{ secrets.UNKEY_NAMESPACE }} + + # Sentry + NEXT_PUBLIC_SENTRY_DSN: ${{ vars.PUBLIC_SENTRY_DSN }} + SENTRY_ORG: ${{ secrets.SENTRY_ORG }} + SENTRY_PROJECT: web + SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }} + + # Posthog + NEXT_PUBLIC_POSTHOG_HOST: ${{ vars.PUBLIC_POSTHOG_HOST }} + NEXT_PUBLIC_POSTHOG_KEY: ${{ secrets.NEXT_PUBLIC_POSTHOG_KEY }} + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 2 + + - name: Setup + uses: ./.github/actions/setup + + - name: Checks + run: bun turbo lint typecheck build test:e2e --filter=@prodkt/web + + - uses: actions/upload-artifact@v4 + if: always() + with: + name: web-playwright-report + path: apps/web/playwright-report/ + retention-days: 30 + + marketing: + name: Marketing CI + runs-on: ubuntu-latest + + environment: Production + + env: + # Sentry + PUBLIC_SENTRY_DSN: ${{ vars.PUBLIC_SENTRY_DSN }} + SENTRY_ORG: ${{ secrets.SENTRY_ORG }} + SENTRY_PROJECT: marketing + SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }} + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 2 + + - name: Setup + uses: ./.github/actions/setup + + - name: Checks + run: bun turbo lint typecheck build test:e2e --filter=@prodkt/marketing diff --git a/.github/workflows/pr-cleanup.yml b/.github/workflows/pr-cleanup.yml new file mode 100644 index 0000000..64002ce --- /dev/null +++ b/.github/workflows/pr-cleanup.yml @@ -0,0 +1,20 @@ +name: Clean up after after a PR is closed or merged +run-name: Clean up PR database +on: + pull_request: + types: [closed] + +jobs: + delete-db-branch: + runs-on: ubuntu-latest + steps: + - name: Get branch name + id: branch_name + uses: tj-actions/branch-names@v8 + + - name: Delete Neon Branch + uses: neondatabase/delete-branch-action@v3 + with: + project_id: ${{ secrets.NEON_PROJECT_ID }} + branch: web/pr-${{ github.event.number }}-${{ steps.branch_name.outputs.current_branch }} + api_key: ${{ secrets.NEON_API_KEY }} diff --git a/.github/workflows/pr.yml b/.github/workflows/pr.yml new file mode 100644 index 0000000..0b7714b --- /dev/null +++ b/.github/workflows/pr.yml @@ -0,0 +1,128 @@ +name: Pull Request CI + +on: [pull_request] + +env: + # This enables turborepo's remote task caching + TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }} + TURBO_TEAM: ${{ vars.TURBO_TEAM }} + +jobs: + spell-and-md-lint: + name: Spellcheck and Markdown Lint + runs-on: ubuntu-latest + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 2 + + - name: Setup + uses: ./.github/actions/setup + + - name: Checks + run: bun turbo lint:md lint:spell + + web: + name: Web CI + runs-on: ubuntu-latest + + env: + # We need these to create the Neon DB branch for this PR + NEON_DATABASE_USERNAME: ${{ secrets.NEON_DATABASE_USERNAME }} + NEON_API_KEY: ${{ secrets.NEON_API_KEY }} + NEON_PROJECT_ID: ${{ secrets.NEON_PROJECT_ID }} + + # Auth Secret + AUTH_SECRET: ${{ secrets.AUTH_SECRET }} + + # Github OAuth + AUTH_GITHUB_ID: ${{ secrets.AUTH_GITHUB_ID }} + AUTH_GITHUB_SECRET: ${{ secrets.AUTH_GITHUB_SECRET }} + + # Google OAuth + AUTH_GOOGLE_ID: ${{ secrets.AUTH_GOOGLE_ID }} + AUTH_GOOGLE_SECRET: ${{ secrets.AUTH_GOOGLE_SECRET }} + + # Uploadthing + UPLOADTHING_SECRET: ${{ secrets.UPLOADTHING_SECRET }} + UPLOADTHING_APP_ID: ${{ secrets.UPLOADTHING_APP_ID }} + + # Unkey + UNKEY_ROOT_KEY: ${{ secrets.UNKEY_ROOT_KEY }} + UNKEY_NAMESPACE: ${{ secrets.UNKEY_NAMESPACE }} + + # Sentry + NEXT_PUBLIC_SENTRY_DSN: ${{ vars.PUBLIC_SENTRY_DSN }} + SENTRY_ORG: ${{ secrets.SENTRY_ORG }} + SENTRY_PROJECT: web + SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }} + + # Posthog + NEXT_PUBLIC_POSTHOG_HOST: ${{ vars.PUBLIC_POSTHOG_HOST }} + NEXT_PUBLIC_POSTHOG_KEY: ${{ secrets.NEXT_PUBLIC_POSTHOG_KEY }} + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 2 + + - name: Get branch name + id: branch_name + uses: tj-actions/branch-names@v8 + + - name: Setup + uses: ./.github/actions/setup + + - name: Create Neon DB Branch + id: create-branch + uses: neondatabase/create-branch-action@v4 + with: + project_id: ${{ env.NEON_PROJECT_ID }} + branch_name: web/pr-${{ github.event.number }}-${{ steps.branch_name.outputs.current_branch }} + username: ${{ env.NEON_DATABASE_USERNAME }} + api_key: ${{ env.NEON_API_KEY }} + + - name: Set DATABASE_URL + shell: bash + run: | + echo "DATABASE_URL=${{ steps.create-branch.outputs.db_url }}?sslmode=require" >> $GITHUB_ENV + + - name: Checks + run: bun turbo lint typecheck build test:e2e --filter=@prodkt/web + + - uses: actions/upload-artifact@v4 + if: always() + with: + name: web-playwright-report + path: apps/web/playwright-report/ + retention-days: 30 + + marketing: + name: Marketing CI + runs-on: ubuntu-latest + + env: + # Sentry + PUBLIC_SENTRY_DSN: ${{ vars.PUBLIC_SENTRY_DSN }} + SENTRY_ORG: ${{ secrets.SENTRY_ORG }} + SENTRY_PROJECT: marketing + SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }} + + # Posthog + NEXT_PUBLIC_POSTHOG_HOST: ${{ vars.PUBLIC_POSTHOG_HOST }} + NEXT_PUBLIC_POSTHOG_KEY: ${{ secrets.PUBLIC_POSTHOG_KEY }} + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 2 + + - name: Setup + uses: ./.github/actions/setup + + - name: Checks + run: bun turbo lint typecheck build test:e2e --filter=@prodkt/marketing diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 0000000..1d6ec9f --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,30 @@ +name: Release + +on: + push: + branches: + - main + +concurrency: ${{ github.workflow }}-${{ github.ref }} + +jobs: + release: + name: Release + timeout-minutes: 15 + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 2 + + - name: Setup + uses: ./.github/actions/setup + + - name: create and publish versions + uses: changesets/action@v1 + with: + commit: 'chore: update versions' + title: 'chore: update versions' + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + NPM_TOKEN: ${{ secrets.NPM_TOKEN }} diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..a0cb0b6 --- /dev/null +++ b/.gitignore @@ -0,0 +1,158 @@ +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +lerna-debug.log* +.pnpm-debug.log* +.vercel +_* +_data-table + +# Diagnostic reports (https://nodejs.org/api/report.html) +report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json + +# Runtime data +pids +*.pid +*.seed +*.pid.lock + +# Directory for instrumented libs generated by jscoverage/JSCover +lib-cov + +# Coverage directory used by tools like istanbul +coverage +*.lcov + +# nyc test coverage +.nyc_output + +# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) +.grunt + +# Bower dependency directory (https://bower.io/) +bower_components + +# node-waf configuration +.lock-wscript + +# Compiled binary addons (https://nodejs.org/api/addons.html) +build/Release + +# Dependency directories +node_modules/ +jspm_packages/ + +# Snowpack dependency directory (https://snowpack.dev/) +web_modules/ + +# TypeScript cache +*.tsbuildinfo + +# Optional npm cache directory +.npm + +# Optional eslint cache +.eslintcache + +# Optional stylelint cache +.stylelintcache + +# Microbundle cache +.rpt2_cache/ +.rts2_cache_cjs/ +.rts2_cache_es/ +.rts2_cache_umd/ + +# Optional REPL history +.node_repl_history + +# Output of 'npm pack' +*.tgz + +# Yarn Integrity file +.yarn-integrity + +# dotenv environment variable files +.env +.env.development.local +.env.test.local +.env.production.local +.env.local + +# parcel-bundler cache (https://parceljs.org/) +.cache +.parcel-cache + +# Next.js build output +.next +next-env.d.ts +out + +# Nuxt.js build / generate output +.nuxt +dist + +# Gatsby files +.cache/ +# Comment in the public line in if your project uses Gatsby and not Next.js +# https://nextjs.org/blog/next-9-1#public-directory-support +# public + +# vuepress build output +.vuepress/dist + +# vuepress v2.x temp and cache directory +.temp +.cache + +# Docusaurus cache and generated files +.docusaurus + +# Serverless directories +.serverless/ + +# FuseBox cache +.fusebox/ + +# DynamoDB Local files +.dynamodb/ + +# TernJS port file +.tern-port + +# Stores VSCode versions used for testing VSCode extensions +.vscode-test + +# yarn v2 +.yarn/cache +.yarn/unplugged +.yarn/build-state.yml +.yarn/install-state.gz +.pnp.* + +# Storybook +storybook-static + +# Astro +.astro + +# DS_Store files +.DS_Store + +# Turborepo +.turbo + +# NX +.nx + +# Playwright +test-results/ +playwright-report/ +blob-report/ +playwright/.cache/ + +# Cspell cache +.cspellcache \ No newline at end of file diff --git a/.husky/commit-msg b/.husky/commit-msg new file mode 100644 index 0000000..52ec98f --- /dev/null +++ b/.husky/commit-msg @@ -0,0 +1 @@ +bun commitlint --edit ${1} diff --git a/.husky/pre-commit b/.husky/pre-commit new file mode 100644 index 0000000..00a9d3c --- /dev/null +++ b/.husky/pre-commit @@ -0,0 +1 @@ +bun lint-staged diff --git a/.husky/prepare-commit-msg b/.husky/prepare-commit-msg new file mode 100644 index 0000000..e7d5001 --- /dev/null +++ b/.husky/prepare-commit-msg @@ -0,0 +1,2 @@ +# only run this if no git commit message has been provided +[ -z "$2" ] && exec < /dev/tty && bun git-cz --hook || true diff --git a/.markdownlint.json b/.markdownlint.json new file mode 100644 index 0000000..afd2357 --- /dev/null +++ b/.markdownlint.json @@ -0,0 +1,8 @@ +{ + "extends": "markdownlint/style/prettier", + "first-line-h1": false, + "no-inline-html": false, + "no-space-in-emphasis": false, + "no-duplicate-heading": false, + "code-block-style": false +} diff --git a/.prettierignore b/.prettierignore new file mode 100644 index 0000000..9b7334e --- /dev/null +++ b/.prettierignore @@ -0,0 +1,11 @@ +bun.lockb +drizzle/ +.prettierignore +.gitignore +*.env.example + +.changeset/ + +packages/ui/src/primitives/form/form.mdx +packages/ui/src/primitives/toast/toast.mdx +packages/ui/src/primitives/carousel/carousel.mdx diff --git a/.vscode/extensions.json b/.vscode/extensions.json new file mode 100644 index 0000000..7b2e17a --- /dev/null +++ b/.vscode/extensions.json @@ -0,0 +1,21 @@ +{ + "recommendations": [ + "dbaeumer.vscode-eslint", + "esbenp.prettier-vscode", + "astro-build.astro-vscode", + "aaron-bond.better-comments", + "streetsidesoftware.code-spell-checker", + "mikestead.dotenv", + "EditorConfig.EditorConfig", + "dsznajder.es7-react-js-snippets", + "tamasfe.even-better-toml", + "github.vscode-github-actions", + "GitHub.copilot", + "GitHub.copilot-chat", + "GitHub.vscode-pull-request-github", + "DavidAnson.vscode-markdownlint", + "unifiedjs.vscode-mdx", + "christian-kohler.path-intellisense", + "YoavBls.pretty-ts-errors" + ] +} diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..9147f1c --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,46 @@ +{ + // Editor + "editor.tabSize": 2, + "editor.formatOnSave": true, + "editor.defaultFormatter": "esbenp.prettier-vscode", + "prettier.documentSelectors": ["**/*.astro"], + "[astro]": { + "editor.defaultFormatter": "esbenp.prettier-vscode" + }, + + // ESLint + "editor.codeActionsOnSave": { + "source.fixAll.eslint": "explicit" + }, + "eslint.rules.customizations": [ + { + "rule": "workspace:*", + "severity": "warn" + } + ], + "eslint.useFlatConfig": true, + "eslint.workingDirectories": [ + { "pattern": "apps/*/" }, + { "pattern": "packages/*/" }, + { "pattern": "packages/config/*/" } + ], + "eslint.validate": [ + "javascript", + "javascriptreact", + "astro", + "typescript", + "typescriptreact" + ], + + // Tailwind + "files.associations": { + "*.css": "tailwindcss" + }, + "tailwindCSS.experimental.classRegex": [ + ["cva\\(([^)]*)\\)", "[\"'`]([^\"'`]*).*?[\"'`]"], + ["cx\\(([^)]*)\\)", "(?:'|\"|`)([^']*)(?:'|\"|`)"] + ], + + // TypeScript + "typescript.tsdk": "node_modules/typescript/lib" +} diff --git a/CODE_OF_CONDUCT.md b/CODE_OF_CONDUCT.md new file mode 100644 index 0000000..25ba9d1 --- /dev/null +++ b/CODE_OF_CONDUCT.md @@ -0,0 +1,132 @@ +# Contributor Covenant Code of Conduct + +## Our Pledge + +We as members, contributors, and leaders pledge to make participation in our +community a harassment-free experience for everyone, regardless of age, body +size, visible or invisible disability, ethnicity, sex characteristics, gender +identity and expression, level of experience, education, socio-economic status, +nationality, personal appearance, race, caste, color, religion, or sexual +identity and orientation. + +We pledge to act and interact in ways that contribute to an open, welcoming, +diverse, inclusive, and healthy community. + +## Our Standards + +Examples of behavior that contributes to a positive environment for our +community include: + +- Demonstrating empathy and kindness toward other people +- Being respectful of differing opinions, viewpoints, and experiences +- Giving and gracefully accepting constructive feedback +- Accepting responsibility and apologizing to those affected by our mistakes, + and learning from the experience +- Focusing on what is best not just for us as individuals, but for the overall + community + +Examples of unacceptable behavior include: + +- The use of sexualized language or imagery, and sexual attention or advances of + any kind +- Trolling, insulting or derogatory comments, and personal or political attacks +- Public or private harassment +- Publishing others' private information, such as a physical or email address, + without their explicit permission +- Other conduct which could reasonably be considered inappropriate in a + professional setting + +## Enforcement Responsibilities + +Community leaders are responsible for clarifying and enforcing our standards of +acceptable behavior and will take appropriate and fair corrective action in +response to any behavior that they deem inappropriate, threatening, offensive, +or harmful. + +Community leaders have the right and responsibility to remove, edit, or reject +comments, commits, code, wiki edits, issues, and other contributions that are +not aligned to this Code of Conduct, and will communicate reasons for moderation +decisions when appropriate. + +## Scope + +This Code of Conduct applies within all community spaces, and also applies when +an individual is officially representing the community in public spaces. +Examples of representing our community include using an official email address, +posting via an official social media account, or acting as an appointed +representative at an online or offline event. + +## Enforcement + +Instances of abusive, harassing, or otherwise unacceptable behavior may be +reported to the community leaders responsible for enforcement at +[bryan.funk@prodkt.cloud](mailto:bryan.funk@prodkt.cloud). +All complaints will be reviewed and investigated promptly and fairly. + +All community leaders are obligated to respect the privacy and security of the +reporter of any incident. + +## Enforcement Guidelines + +Community leaders will follow these Community Impact Guidelines in determining +the consequences for any action they deem in violation of this Code of Conduct: + +### 1. Correction + +**Community Impact**: Use of inappropriate language or other behavior deemed +unprofessional or unwelcome in the community. + +**Consequence**: A private, written warning from community leaders, providing +clarity around the nature of the violation and an explanation of why the +behavior was inappropriate. A public apology may be requested. + +### 2. Warning + +**Community Impact**: A violation through a single incident or series of +actions. + +**Consequence**: A warning with consequences for continued behavior. No +interaction with the people involved, including unsolicited interaction with +those enforcing the Code of Conduct, for a specified period of time. This +includes avoiding interactions in community spaces as well as external channels +like social media. Violating these terms may lead to a temporary or permanent +ban. + +### 3. Temporary Ban + +**Community Impact**: A serious violation of community standards, including +sustained inappropriate behavior. + +**Consequence**: A temporary ban from any sort of interaction or public +communication with the community for a specified period of time. No public or +private interaction with the people involved, including unsolicited interaction +with those enforcing the Code of Conduct, is allowed during this period. +Violating these terms may lead to a permanent ban. + +### 4. Permanent Ban + +**Community Impact**: Demonstrating a pattern of violation of community +standards, including sustained inappropriate behavior, harassment of an +individual, or aggression toward or disparagement of classes of individuals. + +**Consequence**: A permanent ban from any sort of public interaction within the +community. + +## Attribution + +This Code of Conduct is adapted from the [Contributor Covenant][homepage], +version 2.1, available at +[https://www.contributor-covenant.org/version/2/1/code_of_conduct.html][v2.1]. + +Community Impact Guidelines were inspired by +[Mozilla's code of conduct enforcement ladder][Mozilla CoC]. + +For answers to common questions about this code of conduct, see the FAQ at +[https://www.contributor-covenant.org/faq][FAQ]. Translations are available at +[https://www.contributor-covenant.org/translations][translations]. + +[homepage]: https://www.contributor-covenant.org +[v2.1]: https://www.contributor-covenant.org/version/2/1/code_of_conduct.html +[Mozilla CoC]: https://github.com/mozilla/diversity +[FAQ]: https://www.contributor-covenant.org/faq +[translations]: https://www.contributor-covenant.org/translations diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..eaed2b4 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,100 @@ +# Contributing to Prodkt + +Thank you for considering contributing to Prodkt :tada: + +## How to Contribute + +To contribute to this project, follow these steps: + +1. Fork this repository and clone it to your local machine. +2. Create a new branch for your contribution: `git checkout -b BRANCHNAME` +3. Add your changes to the staging area: `git add [path of files]` +4. Commit your changes: `git commit -m 'Add new feature'` +5. Push to the branch: `git push -u origin BRANCHNAME` +6. Submit a pull request. + +## Quick Guide + +### Prerequisites + +```shell +bun: ">=1.1.12" +``` + +### Setting up your local repo + +Prodkt uses bun workspaces, so you should **always run `bun install` from the top-level project directory**. Running `bun install` in the top-level project root will install dependencies for `Prodkt`, and every package in the repo. + +```shell +git clone && cd ... +bun install +bun turbo build +``` + +### Setting up environment variables + +Checkout the `.env.example` file inside the `apps/web` directory for the environment variables you need to get the project running. You should create an UploadThing and Neon DB accounts and copy the environment variables from their dashboard to a `.env.local` file in `apps/web`. + +You will also need to create a GitHub Oauth token as well as for Google authentication as well. + +### Using GitHub Codespaces for development + +To get started, create a codespace for this repository by clicking this 👇 + +[![Open in GitHub Codespaces](https://github.com/codespaces/badge.svg)](https://codespaces.new/prodkt/prodkt) + +Your new codespace will open in a web-based version of Visual Studio Code. All development dependencies will be preinstalled, and the tests will run automatically ensuring you've got a green base from which to start working. + +### Development + +```shell +# Dev +bun turbo dev + +# Build +bun turbo build + +# Typecheck +bun turbo typecheck + +# Lint +bun turbo lint + +# Storybook +bun turbo storybook + +# Start apps in production mode +bun turbo start +``` + +If you're familiar with turborepo / bun workspaces, running stuff around this repo will be easy to figure out. + +### Other useful commands + +```shell +# auto-format the entire project +bun run format +``` + +```shell +# lint the project +bun run lint +``` + +## Code Style Guidelines + +Please follow the existing code style and conventions used in the project. + +## Issue Reporting + +If you encounter any issues with the project or have suggestions for improvements, please open an issue on the GitHub repository. + +## License + +By contributing to this project, you agree that your contributions will be licensed under the [LICENSE](LICENSE). + +--- + +If you have any suggestions or concerns, consider opening a new issue. + +**[Prodkt](https://github.com/prodkt/prodkt/issues)** diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..6d8b765 --- /dev/null +++ b/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2024 Bryan Funk + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/README.md b/README.md new file mode 100644 index 0000000..b706a93 --- /dev/null +++ b/README.md @@ -0,0 +1,66 @@ +
+ Cover image +
+ +## Note + +> [!IMPORTANT] +> Prodkt is built on top of a very opinionated tech stack, which might not work for every use case/business idea. I offer monorepo architecture consulting or even building something completely custom for you, if you are interested be sure to [DM me on X/Twitter](https://twitter.com/prodkt_). + +## Features + +- [**Monorepo**](https://monorepo.tools/): Prodkt is a monorepo, giving you the ability to scale your project with ease. +- [**TypeScript**](https://www.typescriptlang.org/): type-safety is a core principle of Prodkt. +- [**Astrojs**](https://astro.build): for a clean slate to build your marketing website on top. +- [**Next.js**](https://nextjs.org): Web application is included, giving you a solid foundation for your product. +- [**Posthog**](https://posthog.com): for analytics and event tracking. +- [**Sentry**](https://sentry.io): for error tracking and monitoring. +- [**tRPC**](https://trpc.io) for a fully type-safe api. +- [**Mintlify**](https://mintlify.com): for a clean, fast, and easy to use platform to document your project. +- [**Turborepo**](https://turbo.build/repo): caching builds so you never have to run the same command twice. +- [**Drizzle ORM**](https://orm.drizzle.team): providing a fully type-safe way to interact with your database. +- [**Neon DB**](https://neon.tech): serverless database, with autoscaling, branching, and bottomless storage. +- [**Uploadthing**](https://uploadthing.com/): for an easy, type-safe way of handling file uploads. +- [**Unkey**](https://unkey.dev): for a fast way of rate-limiting the web app. +- [**Playwright**](https://playwright.dev): for end-to-end testing of the applications. +- [**Lucia auth**](https://lucia-auth.com): for authentication, giving you full flexibility and control over your user system. +- [**Tailwind CSS**](https://tailwindcss.com): for styling, with [**Radix UI Colors**](https://www.radix-ui.com/colors) for automatic light/dark mode handling. +- [**Shadcn UI**](https://ui.shadcn.com): full implementation in a dedicated package. +- [**Storybook**](https://storybook.js.org): to develop, test and visualize your components in isolation. +- [**Github Actions**](https://github.com/features/actions): for CI/CD, with automatic DB branching & code checks. +- [**next-themes**](https://github.com/pacocoursey/next-themes): for easy light/dark mode handling in the web app. +- [**Changesets**](https://github.com/changesets/changesets): for managing versioning and changelogs. +- [**vite**](https://vitejs.dev): for bundling & storybook. +- [**ts-reset**](https://github.com/total-typescript/ts-reset): for the apps, improving the types for common JavaScript APIs. +- [**ESLint**](https://eslint.org/), [**Prettier**](https://prettier.io), [**Markdownlint**](https://github.com/DavidAnson/markdownlint), [**Cspell**](https://cspell.org), [**Husky**](https://github.com/typicode/husky), [**Lint-staged**](https://github.com/lint-staged/lint-staged) and [**Commitlint**](https://github.com/conventional-changelog/commitlint) for code quality. +- **ESM Only**: because CJS should be left in the past. + +And much more! + +## Documentation + +To get started with Prodkt, head over to the [documentation](https://prodkt.cloud) website where you can find installation instructions and how to work with the codebase. + +## License + +MIT License + +Copyright (c) 2024 Bryan Funk + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/SECURITY.md b/SECURITY.md new file mode 100644 index 0000000..e9fab57 --- /dev/null +++ b/SECURITY.md @@ -0,0 +1,7 @@ +# Prodkt Security + +## Reporting a Vulnerability + +To report a security issue, please [open a security advisory](https://github.com/prodkt/prodkt/security/advisories/new) on GitHub with a detailed description of the issue, the steps you took to create the issue, affected versions, and, if known, mitigations for the issue. + +Please remember to include everything required for us to reproduce the issue, including but not limited to a publicly accessible git repository and/or StackBlitz repository. diff --git a/bun.lockb b/bun.lockb new file mode 100644 index 0000000000000000000000000000000000000000..65303defdf3ea99bde2d742732f90fe2184fe58f GIT binary patch literal 1009808 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