मुझे न्यूनतम कॉन्फ़िगरेशन के साथ Vite और Cloudflare Workers-Pages के साथ Remix का उपयोग करने का एक तरीका चाहिए था।
मैंने अन्य रिपॉजिटरी भी देखीं, जैसे:
लेकिन उनकी कुछ सीमाएँ थीं:
मैं इसे पहले से बनाना नहीं चाहता था, क्योंकि मैं रिपॉजिटरीज में और अधिक कॉन्फ़िगरेशन फ़ाइलें नहीं डालना चाहता था।
क्लाउडफ्लेयर वर्कर्स/पेजेस का लक्ष्य अलग है। इसे tsup के साथ लक्षित करना मुश्किल हो गया, क्योंकि पोस्टग्रेस जैसे पैकेज रीमिक्स में आयात किए जाने पर नोड निर्भरता को तोड़ देंगे।
मुझे विभिन्न लक्ष्यों (रीमिक्स-क्लाउडफ्लेयर, नोड/बुन) का उपभोग करने का एक तरीका भी चाहिए था
फिर भी, मैं उनका धन्यवाद करता हूं, क्योंकि उन्होंने इसे संभव बनाने का मार्ग प्रशस्त किया!
नीचे दिए गए नुकसान वाले अनुभाग को अवश्य पढ़ें!
मैं उत्पादन में उन 1% त्रुटियों को पकड़ने के लिए सार्वजनिक रूप से एक स्वचालित परीक्षण मंच का निर्माण कर रहा हूं।
मैं अपनी प्रगति साझा करता हूँ:
आप यहां पूर्ण कार्यान्वयन देख सकते हैं।
यद्यपि यह आपको एक नए मोनो-रिपॉजिटरी के माध्यम से ले जाता है, लेकिन मौजूदा को एक में बदलने के लिए यह पूरी तरह से वैध है।
यह भी मान लिया जाएगा कि आपके पास मोनो रेपो का कुछ ज्ञान है।
टिप्पणी:
libs
और packages
निर्देशिकाओं के बाहर होगा।टर्बोरेपो आपके पैकेज मैनेजर के वर्कस्पेस के ऊपर काम करता है ताकि आपके प्रोजेक्ट की स्क्रिप्ट और आउटपुट को मैनेज किया जा सके (यह आपके आउटपुट को कैश भी कर सकता है)। अब तक, यह रश (जिसे मैंने आजमाया नहीं है और मुझे पसंद नहीं है) के अलावा एकमात्र मोनो-रेपो टूल है जो काम करने में सक्षम है।
NX में रीमिक्स का Vite समर्थन नहीं है (इस लेखन के अनुसार - 28 अगस्त, 2024)।
pnpm dlx create-turbo@latest
हम निर्भरताओं के प्रबंधन के लिए PNPM की कार्यक्षेत्र क्षमताओं का उपयोग करेंगे।
अपनी मोनोरेपो निर्देशिका पर, pnpm-workspace.yaml
बनाएं।
इसके अंदर जोड़ें:
packages: - "apps/*" - "libs/*"
यह pnpm को बताएगा कि सभी रिपॉजिटरी apps
और libs
अंदर होंगी। ध्यान दें कि libs
या packages
(जैसा कि आपने कहीं और देखा होगा) का उपयोग करना कोई मायने नहीं रखता।
pnpm init
{ "name": "@repo/main", "version": "1.0.0", "scripts": {}, "keywords": [], "author": "", "license": "ISC" }
name:@repo/main
यह हमें बताता है कि यह एप्लिकेशन की मुख्य प्रविष्टि है। आपको किसी विशेष परंपरा का पालन करने या @
उपसर्ग का उपयोग करने की आवश्यकता नहीं है। लोग इसे स्थानीय/दूरस्थ पैकेजों से अलग करने या इसे किसी संगठन में समूहीकृत करना आसान बनाने के लिए इसका उपयोग करते हैं।
turbo.json
फ़ाइल बनाएँ: { "$schema": "https://turbo.build/schema.json", "tasks": { "build": {}, "dev": { "cache": false, "persistent": true }, "start": { "dependsOn": ["^build"], "persistent": true }, "preview": { "cache": false, "persistent": true }, "db:migrate": {} } }
टर्बो.json फ़ाइल टर्बो रेपो को बताती है कि हमारे आदेशों की व्याख्या कैसे की जाए। tasks
कुंजी के अंदर जो कुछ भी है वह सभी package.json में पाए जाने वाले से मेल खाएगा।
ध्यान दें कि हमने चार कमांड परिभाषित किए हैं। ये प्रत्येक रिपॉजिटरी के package.json के स्क्रिप्ट सेक्शन में मौजूद कमांड से मेल खाते हैं। हालाँकि, सभी package.json को इन कमांड को लागू करना ज़रूरी नहीं है।
उदाहरण: dev
कमांड को turbo dev
द्वारा ट्रिगर किया जाएगा, और यह उन सभी पैकेजों को निष्पादित करेगा जो dev
package.json में पाए जाते हैं। यदि आप इसे turbo में शामिल नहीं करते हैं, तो यह निष्पादित नहीं होगा।
apps
फ़ोल्डर बनाएँ mkdir apps
apps
फ़ोल्डर में रीमिक्स ऐप बनाएं (या मौजूदा ऐप को स्थानांतरित करें) npx create-remix --template edmundhung/remix-worker-template
जब यह आपसे Install any dependencies with npm
के लिए कहता है तो 'नहीं' कहें।
name
बदलकर @repo/my-remix-cloudflare-app
(या आपका नाम) रखें { - "name": "my-remix-cloudflare-app", + "name": "@repo/my-remix-cloudflare-app", "version": "1.0.0", "keywords": [], "author": "", "license": "ISC" }
apps/<app>/package.json
से Dependencies और devDependencies को रूट के package.json
में कॉपी करेंउदाहरण:
<रूट>/package.json
{ "name": "@repo/main", "version": "1.0.0", "scripts": {}, "keywords": [], "author": "", "license": "ISC", "dependencies": { "@markdoc/markdoc": "^0.4.0", "@remix-run/cloudflare": "^2.8.1", "@remix-run/cloudflare-pages": "^2.8.1", "@remix-run/react": "^2.8.1", "isbot": "^3.6.5", "react": "^18.2.0", "react-dom": "^18.2.0" }, "devDependencies": { "@cloudflare/workers-types": "^4.20240222.0", "@octokit/types": "^12.6.0", "@playwright/test": "^1.42.1", "@remix-run/dev": "^2.8.1", "@remix-run/eslint-config": "^2.8.1", "@tailwindcss/typography": "^0.5.10", "@types/react": "^18.2.64", "@types/react-dom": "^18.2.21", "autoprefixer": "^10.4.18", "concurrently": "^8.2.2", "cross-env": "^7.0.3", "eslint": "^8.57.0", "eslint-config-prettier": "^9.1.0", "husky": "^9.0.11", "lint-staged": "^15.2.2", "msw": "^2.2.3", "postcss": "^8.4.35", "prettier": "^3.2.5", "prettier-plugin-tailwindcss": "^0.5.12", "rimraf": "^5.0.5", "tailwindcss": "^3.4.1", "typescript": "^5.4.2", "vite": "^5.1.5", "vite-tsconfig-paths": "^4.3.1", "wrangler": "^3.32.0" } }
सत्यापित करें कि टर्बो package.json के devDependencies के अंदर है। यदि यह सूचीबद्ध नहीं है, तो निम्न आदेश निष्पादित करें:
pnpm add turbo -D -w
-w
ध्वज pnpm को इसे कार्यक्षेत्र रूट पर स्थापित करने के लिए कहता है।
scripts
में dev
कमांड जोड़ें
packageManager
को विकल्प में जोड़ें
{ "name": "@repo/main", "version": "1.0.0", "scripts": { "dev": "turbo dev" }, "keywords": [], "author": "", "license": "ISC", "packageManager": "[email protected]", "dependencies": { // omitted for brevity }, "devDependencies": { // omitted for brevity } }
pnpm dev
चलाकर सत्यापित करें कि सब कुछ काम कर रहा है pnpm dev
mkdir -p libs/config libs/db libs/utils
src/index.ts
जोड़ें। touch libs/config/src/index.ts libs/db/src/index.ts libs/utils/src/index.ts
libs/config/package.json
फ़ाइल में निम्नलिखित जोड़ें: { "name": "@repo/config", "version": "1.0.0", "type": "module", "exports": { ".": { "import": "./src/index.ts", "default": "./src/index.ts" } } }
libs/db/package.json
के लिए भी यही करें: { "name": "@repo/db", "version": "1.0.0", "exports": { ".": { "import": "./src/index.ts", "default": "./src/index.ts" } } }
libs/utils/package.json
: { "name": "@repo/utils", "version": "1.0.0", "exports": { ".": { "import": "./src/index.ts", "default": "./src/index.ts" } } }
टिप्पणियाँ:
मैं ORM से घृणा करने लगा हूँ। मैंने 6 अलग-अलग ORM सीखने में 10 साल से ज़्यादा का समय बिताया है, और यह ऐसा ज्ञान है जिसे आप हस्तांतरित नहीं कर सकते।
जब नई तकनीकें आती हैं तो आपको समस्याएँ होती हैं। Prisma क्लाउडफ्लेयर वर्कर्स को बॉक्स से बाहर समर्थन नहीं करता है।
एलएलएम के साथ, जटिल SQL क्वेरीज़ लिखना पहले से कहीं अधिक आसान हो गया है।
SQL सीखना एक सार्वभौमिक भाषा है और इसमें कोई परिवर्तन होने की सम्भावना नहीं है।
pnpm add drizzle-orm drizle-kit --filter=@repo/db
वर्कस्पेस स्तर पर Postgres स्थापित करें। नुकसान अनुभाग देखें ।
pnma add postgres -w
टिप्पणियाँ:
--filter=@repo/db
फ्लैग pnpm को पैकेज को db रिपोजिटरी में जोड़ने के लिए कहता है। pnpm add dotenv -w
नोट्स
-w
फ्लैग pnpm को रूट के package.json पर इसे स्थापित करने के लिए कहता है pnpm add @repo/config -r --filter=!@repo/config
टिप्पणियाँ :
-r
फ्लैग pnpm को पैकेज को सभी रिपॉजिटरी में जोड़ने के लिए कहता है।--filter=!
ध्वज pnpm को कॉन्फ़िगरेशन रिपोजिटरी को बाहर करने के लिए कहता है।!
पर ध्यान दें यदि pnpm रिपोजिटरी से पैकेज खींच रहा है, तो हम प्रोजेक्ट के रूट पर एक .npmrc
फ़ाइल बना सकते हैं।
.npmrc
link-workspace-packages= true prefer-workspace-packages=true
tsconfig.json
कॉन्फ़िगर करेंpnpm वर्कस्पेस की शक्ति का उपयोग करके, आप कॉन्फ़िगरेशन फ़ाइलें बना सकते हैं जिन्हें परियोजनाओं में साझा किया जा सकता है।
हम एक आधार tsconfig.lib.json बनाएंगे जिसका उपयोग हम अपनी लाइब्रेरीज़ के लिए करेंगे।
libs/config
के अंदर tsconfig.lib.json
को तत्काल बनाएं:
touch "libs/config/tsconfig.base.lib.json"
फिर, निम्नलिखित जोड़ें:
tsconfig.base.lib.json
{ "$schema": "https://json.schemastore.org/tsconfig", "compilerOptions": { "lib": ["ES2022"], "module": "ESNext", "moduleResolution": "Bundler", "resolveJsonModule": true, "target": "ES2022", "strict": true, "esModuleInterop": true, "skipLibCheck": true, "forceConsistentCasingInFileNames": true, "allowImportingTsExtensions": true, "allowJs": true, "noUncheckedIndexedAccess": true, "noEmit": true, "incremental": true, "composite": false, "declaration": true, "declarationMap": true, "inlineSources": false, "isolatedModules": true, "noUnusedLocals": false, "noUnusedParameters": false, "preserveWatchOutput": true, "experimentalDecorators": true, "emitDecoratorMetadata": true, "sourceMap": true, } }
// libs/db/drizzle.config.ts (Yes, this one is at root of the db package, outside the src folder) // We don't want to export this file as this is ran at setup. import "dotenv/config"; // make sure to install dotenv package import { defineConfig } from "drizzle-kit"; export default defineConfig({ dialect: "postgresql", out: "./src/generated", schema: "./src/drizzle/schema.ts", dbCredentials: { url: process.env.DATABASE_URL!, }, // Print all statements verbose: true, // Always ask for confirmation strict: true, });
स्कीमा फ़ाइल:
// libs/db/src/drizzle/schema.ts export const User = pgTable("User", { userId: char("userId", { length: 26 }).primaryKey().notNull(), subId: char("subId", { length: 36 }).notNull(), // We are not making this unique to support merging accounts in later // iterations email: text("email"), loginProvider: loginProviderEnum("loginProvider").array().notNull(), createdAt: timestamp("createdAt", { precision: 3, mode: "date" }).notNull(), updatedAt: timestamp("updatedAt", { precision: 3, mode: "date" }).notNull(), });
क्लाइंट फ़ाइल:
// libs/db/src/drizzle-client.ts import { drizzle, PostgresJsDatabase } from "drizzle-orm/postgres-js"; import postgres from "postgres"; import * as schema from "./schema"; export type DrizzleClient = PostgresJsDatabase<typeof schema>; let drizzleClient: DrizzleClient | undefined; type GetClientInput = { databaseUrl: string; env: string; mode?: "cloudflare" | "node"; }; declare var window: typeof globalThis; declare var self: typeof globalThis; export function getDrizzleClient(input: GetClientInput) { const { mode, env } = input; if (mode === "cloudflare") { return generateClient(input); } const globalObject = typeof globalThis !== "undefined" ? globalThis : typeof global !== "undefined" ? global : typeof window !== "undefined" ? window : self; if (env === "production") { drizzleClient = generateClient(input); } else if (globalObject) { if (!(globalObject as any).__db__) { (globalObject as any).__db__ = generateClient(input); } drizzleClient = (globalObject as any).__db__; } else { drizzleClient = generateClient(input); } return drizzleClient; } type GenerateClientInput = { databaseUrl: string; env: string; }; function generateClient(input: GenerateClientInput) { const { databaseUrl, env } = input; const isLoggingEnabled = env === "development"; // prepare: false for serverless try { const client = postgres(databaseUrl, { prepare: false }); const db = drizzle(client, { schema, logger: isLoggingEnabled }); return db; } catch (e) { console.log("ERROR", e); return undefined!; } }
माइग्रेशन फ़ाइल:
// libs/db/src/drizzle/migrate.ts import { config } from "dotenv"; import { migrate } from "drizzle-orm/postgres-js/migrator"; import postgres from "postgres"; import { drizzle } from "drizzle-orm/postgres-js"; import "dotenv/config"; import path from "path"; config({ path: "../../../../apps/my-remix-cloudflare-app/.dev.vars" }); const ssl = process.env.ENVIRONMENT === "development" ? undefined : "require"; const databaseUrl = drizzle( postgres(`${process.env.DATABASE_URL}`, { ssl, max: 1 }) ); // Somehow the current starting path is /libs/db // Remember to have the DB running before running this script const migration = path.resolve("./src/generated"); const main = async () => { try { await migrate(databaseUrl, { migrationsFolder: migration, }); console.log("Migration complete"); } catch (error) { console.log(error); } process.exit(0); }; main();
इसे माइग्रेशन के बाद निष्पादित किया जाना चाहिए
और क्लाइंट और स्कीमा को src/index.ts
फ़ाइल में निर्यात करें। अन्य को विशिष्ट समय पर चलाया जाता है।
// libs/db/src/index.ts export * from "./drizzle/drizzle-client"; export * from "./drizzle/schema "
अपने package.json
में, drizzle-kit generate
और माइग्रेशन कमांड चलाने के लिए कोड जोड़ें:
{ "name": "@repo/db", "version": "1.0.0", "main": "./src/index.ts", "module": "./src/index.ts", "types": "./src/index.ts", "scripts": { "db:generate": "drizzle-kit generate", "db:migrate": "dotenv tsx ./drizzle/migrate", }, "exports": { ".": { "import": "./src/index.ts", "default": "./src/index.ts" } }, "dependencies": { "@repo/configs": "workspace:^", "drizzle-kit": "^0.24.1", "drizzle-orm": "^0.33.0", }, "devDependencies": { "@types/node": "^22.5.0" } }
libs/db
और libs/utils
के लिए साझा tsconfig.json
उपयोग करें libs/db
और libs/utils
के लिए tsconfig.json बनाएँ
touch "libs/db/tsconfig.json" "libs/utils/tsconfig.json"
फिर प्रत्येक में जोड़ें:
{ "extends": "@repo/configs/tsconfig.base.lib.json", "include": ["./src"], }
@repo/configs
उपयोग हमारे tsconfig.base.lib.json को संदर्भित करने के लिए पथ के रूप में किया जाता है।टाइपस्क्रिप्ट एक्ज़ीक्यूट (TSX) ts-node का एक लाइब्रेरी विकल्प है। हम इसका उपयोग ड्रिज़ल के माइग्रेशन को निष्पादित करने के लिए करेंगे।
pnpm add tsx -D --filter=@repo/db
libs/db
डायरेक्टरी में एक खाली .env जोड़ें touch "libs/db/.env"
निम्नलिखित सामग्री जोड़ें:
DATABASE_URL="postgresql://postgres:postgres@localhost:5432/postgres" NODE_ENV="development" MODE="node"
libs/db
रिपॉजिटरी जोड़ेंप्रोजेक्ट के मूल से चलाएँ:
pnpm add @repo/db --filter=@repo/my-remix-cloudflare-app
यदि यह काम नहीं करता है, तो apps/my-remix-cloudflare-app
के package.json पर जाएं, और निर्भरता को मैन्युअल रूप से जोड़ें।
{ "name": "@repo/my-remix-cloudflare-app", "version": "1.0.0", "dependencies": { "@repo/db": "workspace:*" } }
वर्शन फ़ील्ड में workspace:*
पर ध्यान दें। यह pnpm को वर्कस्पेस में पैकेज के किसी भी वर्शन का उपयोग करने के लिए कहता है।
यदि आपने इसे pnpm add,
आपको संभवतः workspace:^
जैसा कुछ दिखाई देगा। जब तक आप स्थानीय पैकेज संस्करणों को नहीं बढ़ाते हैं, तब तक इससे कोई फर्क नहीं पड़ता है।
यदि आपने इसे मैन्युअल रूप से जोड़ा है, तो प्रोजेक्ट के रूट से pnpm install
चलाएँ।
हमें अपने प्रोजेक्ट में @repo/db का उपयोग करने में सक्षम होना चाहिए।
इस कोड को libs/utils/src/index.ts
फ़ाइल में जोड़ें:
// libs/utils/src/index.ts export function hellowWorld() { return "Hello World!"; }
pnpm add @repo/db --filter=@repo/my-remix-cloudflare-app
यदि आपके पास Postgres इंस्टेंस नहीं चल रहा है, तो हम docker-compose का उपयोग करके इसे लॉन्च कर सकते हैं। ध्यान दें, मैं मान रहा हूँ कि आप Docker जानते हैं।
प्रोजेक्ट के मूल में docker-compose.yml
फ़ाइल बनाएँ.
# Auto-generated docker-compose.yml file. version: '3.8' # Define services. services: postgres: image: postgres:latest restart: always environment: - POSTGRES_USER=postgres - POSTGRES_PASSWORD=postgres - POSTGRES_DB=postgres ports: - "5432:5432" volumes: - ./postgres-data:/var/lib/postgresql/data pgadmin: # To connect PG Admin, navigate to http://localhost:8500 use: # host.docker.internal # postgres # (username) postgres # (password) postgres image: dpage/pgadmin4 ports: - "8500:80" environment: PGADMIN_DEFAULT_EMAIL: [email protected] PGADMIN_DEFAULT_PASSWORD: admin
फिर आप चला सकते हैं:
docker-compose up -d
-d
फ्लैग docker-compose को अलग से चलने के लिए कहता है ताकि आप फिर से अपने टर्मिनल तक पहुंच सकें।
अब, libs/db रिपोजिटरी पर जाएँ और db:generate
चलाएँ।
cd `./libs/db` && pnpm db:generate
db:generate
एक उपनाम है: drizzle-kit generate
हमें अपने डेटाबेस के भीतर सभी तालिकाओं को स्कैफोल्ड करने के लिए माइग्रेशन चलाने की आवश्यकता है।
libs/db रिपोजिटरी पर जाएं (यदि आप वहां नहीं हैं) और db:generate
चलाएं।
cd `./libs/db` && pnpm db:migrate
db:migrate
एक उपनाम है: dotenv tsx ./drizzle/migrate
// apps/my-remix-cloudflare-app/app/routes/_index.tsx import type { LoaderFunctionArgs } from '@remix-run/cloudflare'; import { json, useLoaderData } from '@remix-run/react'; import { getDrizzleClient } from '@repo/db'; import { Markdown } from '~/components'; import { getFileContentWithCache } from '~/services/github.server'; import { parse } from '~/services/markdoc.server'; export async function loader({ context }: LoaderFunctionArgs) { const client = await getDrizzleClient({ databaseUrl: context.env.DATABASE_URL, env: 'development', mode: 'cloudflare', }); if (client) { const res = await client.query.User.findFirst(); console.log('res', res); } const content = await getFileContentWithCache(context, 'README.md'); return json( { content: parse(content), // user: firstUser, }, { headers: { 'Cache-Control': 'public, max-age=3600', }, }, ); } export default function Index() { const { content } = useLoaderData<typeof loader>(); return <Markdown content={content} />; }
ऐप्स/माई-रीमिक्स-क्लाउडफ्लेयर-ऐप/.dev.vars
DATABASE_URL="postgresql://postgres:postgres@localhost:5432/postgres"
पोस्टग्रेज इंस्टैंस लॉन्च करें (यदि तैयार नहीं है)
docker-compose up -d
परियोजना का शुभारंभ
pnpm turbo dev
अपनी परियोजनाओं में, मैं CQRS पैटर्न , 2 को लागू करने का प्रयास करता हूँ। यह इस ट्यूटोरियल के दायरे से बाहर है।
फिर भी, लोड संदर्भ में, मैं एक मध्यस्थ (और एक कुकी फ्लैश संदेश) को इंजेक्ट करता हूं जो मेरे पूरे रीमिक्स एप्लिकेशन को मेरे व्यावसायिक तर्क से अलग कर देगा।
यह कुछ इस तरह दिखता है:
export const getLoadContext: GetLoadContext = async ({ context, request }) => { const isEnvEmpty = Object.keys(context.cloudflare.env).length === 0; const env = isEnvEmpty ? process.env : context.cloudflare.env; const sessionFlashSecret = env.SESSION_FLASH_SECRET; const flashStorage = createCookieSessionStorage({ cookie: { name: "__flash", httpOnly: true, maxAge: 60, path: "/", sameSite: "lax", secrets: [sessionFlashSecret], secure: true, }, }); return { ...context, cloudflare: { ...context.cloudflare, env, }, dispatch: (await dispatchWithContext({ env: env as unknown as Record<string, string>, request, })) as Dispatch, flashStorage, }; };
ध्यान दें कि डिस्पैच कोड छोड़ा गया है। आप इसके बारे में मेरे लेख में अधिक जानकारी पा सकते हैं कि अपने TypeScript डेवलपर अनुभव को 10 गुना कैसे बढ़ाया जाए ।
मैं अपने कोड में बदलाव किए बिना रीमिक्स को हटा सकता हूं या किसी अन्य उपभोक्ता का उपयोग कर सकता हूं।
लेकिन…।
जब आप टर्बोरेपो का उपयोग करके मोनोरेपो संरचना में काम करते हैं तो एक अतिरिक्त चुनौती होती है।
यदि आप लोड-संदर्भ के भीतर किसी पैकेज से टाइपस्क्रिप्ट फ़ाइल आयात करते हैं, मान लीजिए @repo/db
Vite एक त्रुटि लौटाएगा कि एक्सटेंशन .ts
वाली फ़ाइल अज्ञात है, और यह नहीं जानता कि इसे कैसे संसाधित किया जाए।
ऐसा इसलिए होता है क्योंकि लोड-संदर्भ + वर्कस्पेस साइट के मुख्य आयात ग्राफ के बाहर होते हैं, जिससे टाइपस्क्रिप्ट फ़ाइलें प्ले के बाहर रह जाती हैं।
तरकीब यह है कि tsx
उपयोग करें और Vite को कॉल करने से पहले इसे लोड करें, जो काम करेगा। यह महत्वपूर्ण है क्योंकि यह निम्नलिखित सीमाओं को पार करता है:
क्लाउडफ्लेयर पैकेज निर्भरताएँ.
क्लाउडफ्लेयर पैकेज निर्भरताएँ और प्री-बिल्डिंग
सबसे पहले, यह वह चरण था जिसे मैं टालने की कोशिश कर रहा था, क्योंकि इसका मतलब था कि मुझे प्रत्येक पैकेज के लिए एक निर्माण चरण शुरू करना होगा, जिसका मतलब था अधिक कॉन्फ़िगरेशन।
सौभाग्य से, यह क्लाउडफ्लेयर पेज के लिए काम नहीं करता है। Postgres जैसी विशिष्ट लाइब्रेरी रनटाइम का पता लगाएगी और आवश्यक पैकेज खींचेगी।
इसका एक समाधान है: हम सभी टाइपस्क्रिप्ट फ़ाइलों को लोड करने के लिए tsx का उपयोग कर सकते हैं और निष्पादन से पहले उन्हें ट्रांसपाइल कर सकते हैं।
आप यह तर्क दे सकते हैं कि यह एक पूर्व-निर्माण चरण है, लेकिन चूंकि यह अभी भी रीमिक्स के रिपोजिटरी स्तर पर है, इसलिए मुझे इस दृष्टिकोण में कोई महत्वपूर्ण समस्या नहीं दिखती।
इसे हल करने के लिए, हम tsx को निर्भरता के रूप में जोड़ते हैं:
pnpm add tsx -D --filter=@repo/my-remix-cloudflare-app
और फिर, हमें अपने package.json
को संशोधित करने और हमारी प्रत्येक रीमिक्स स्क्रिप्ट में tsx प्रक्रिया को जोड़ने की आवश्यकता है:
{ "name": "@repo/my-remix-cloudflare-app", "version": "1.0.0", "scripts": { // Other scripts omitted "build": "NODE_OPTIONS=\"--import tsx/esm\" remix vite:build", "dev": "NODE_OPTIONS=\"--import tsx/esm\" remix vite:dev", "start": "NODE_OPTIONS=\"--import tsx/esm\" wrangler pages dev ./build/client" } }
.npmrc
फ़ाइल बनाना यदि आपको कमांड लाइन के साथ अपने स्थानीय पैकेज जोड़ते समय समस्या आ रही है, तो आप प्रोजेक्ट के रूट में .npmrc
फ़ाइल बना सकते हैं।
.npmrc
link-workspace-packages= true prefer-workspace-packages=true
यह pnpm को पहले वर्कस्पेस पैकेजों का उपयोग करने के लिए कहेगा।
Reddit के ZoWnx को धन्यवाद जिन्होंने मुझे .nprmc फ़ाइल बनाने में मदद की
अपनी फ़ाइलों में .client
और .server
नाम देते समय सावधान रहें। भले ही यह किसी अलग लाइब्रेरी में हो। रीमिक्स इनका उपयोग यह निर्धारित करने के लिए करता है कि यह क्लाइंट या सर्वर फ़ाइल है। प्रोजेक्ट को रिपॉजिटरी के अनुसार संकलित नहीं किया गया है, इसलिए यह एक आयात त्रुटि फेंक देगा!
यदि आपको Postgres जैसे मल्टी-प्लेटफ़ॉर्म पैकेज के साथ समस्या हो रही है, तो इसे वर्कस्पेस स्तर पर इंस्टॉल करना बेहतर है। यह उचित आयात का पता लगाएगा। इसे सीधे @repo/db रिपॉजिटरी में इंस्टॉल करने से इसे रीमिक्स में आयात करते समय टूट जाएगा।
बस इतना ही, मित्रों!!!
आप यहां पूर्ण कार्यान्वयन देख सकते हैं।
मैं उत्पादन में उन 1% त्रुटियों को पकड़ने के लिए सार्वजनिक रूप से एक स्वचालित परीक्षण इंजीनियर का निर्माण कर रहा हूं।
मैं अपनी प्रगति साझा करता हूँ: