عن المشروع
# @querry-kit/nest
أدوات NestJS الموحّدة لواجهات Query Kit البرمجية: إسقاط الحقول، وخدمات استعلام بنمط Prisma، وسياسات CASL، ومزخرفات OpenAPI، وأنابيب، وكائنات نقل البيانات للترقيم، وأدوات مساعدة للكائنات.
## 🌐 منظومة Querry Kit
يربط [نظرة عامة على Querry Kit](https://querry-kit.github.io/querry-kit/) الحزم الأساسية الثلاث:
- [`@querry-kit/nest`](https://github.com/querry-kit/nest) توفر واجهة NestJS وأنماط المتحكمات.
- [`@querry-kit/nuxt`](https://github.com/querry-kit/nuxt) توفر عملاء API مُنمّطين وعناصر بيانات Vue/Nuxt بلا واجهة.
- [`@querry-kit/nuxt-ui`](https://github.com/querry-kit/nuxt-ui) توفر عناصر تحكم جداول Nuxt UI المبنية على تلك العناصر.
## 📦 التثبيت
```sh
pnpm add @querry-kit/nest
pnpm add @nestjs/common @nestjs/core @nestjs/swagger class-transformer class-validator reflect-metadata
```
لمحوّل CASL الاختياري:
```sh
pnpm add @casl/ability @casl/prisma
```
إصدار الحزمة الحالي منشور على npm. وnpm هي قناة التوزيع الأساسية.
تبقى وسوم إصدارات GitHub متاحة كخيار احتياطي:
```sh
pnpm add github:querry-kit/nest#v0.0.1
```
## 🚀 سير عمل الإصدار
تُدار الإصدارات عبر Changesets وGitHub Actions. لا يحتوي فرع `main` على ملفات `dist` مُلتزَمة؛ بل يحتوي فقط على المصدر وREADME وإعدادات سير العمل.
يجب أن تتضمن التغييرات المرئية للحزمة changeset:
```sh
pnpm changeset
```
عند وصول التغييرات إلى `main`، ينشئ سير عمل `changesets` أو يحدّث طلب سحب للإصدار. يحتوي ذلك الطلب على رفع الإصدار وتحديثات سجل التغييرات الناتجة عن:
```sh
pnpm changeset version
```
يستخدم سير عمل النشر إلى npm خاصية Trusted Publishing عبر GitHub Actions OIDC. يجب ربط حزمة npm بهذا المستودع وسير العمل في إعدادات نشر حزمة npm:
- المستودع: `querry-kit/nest`
- ملف سير العمل: `release.yml`
- البيئة: غير محددة
بعد دمج طلب سحب الإصدار، يعمل سير عمل `npm publish` لتغييرات الإصدار/سجل التغييرات. يشغّل فحوصات الحزمة، ويبني `dist` في CI، وينشر `@querry-kit/nest` إلى npm، ويضع وسم `vX.Y.Z` على التزام الإصدار، وينشئ إصدار GitHub.
ينبغي للمستهلكين التثبيت من npm:
```sh
pnpm add @querry-kit/nest
```
## 🧩 الاستخدام
يغطي `ResourceQuery` تدفق المتحكم الشائع: تحليل `fields` الاختيارية، ودمج التضمينات المطلوبة من نقطة النهاية مع قيم `include` من العميل، وإنشاء تضمينات Prisma للعلاقات المحددة، واستدعاء `QueryService`، وتحويل النماذج إلى DTOs، وإسقاط الاستجابة.
```ts
import { Get, Query, Req } from '@nestjs/common';
import { ApiErrorResponses, ApiPaginatedResponse, ApiResourceQuery, QueryDTO, ResourceQuery } from '@querry-kit/nest';
@Get()
@ApiResourceQuery()
@ApiPaginatedResponse({ model: CustomerDTO })
@ApiErrorResponses({ badRequestDescription: 'Invalid query parameter.' })
async query(@Req() req: AuthRequest, @Query() query: QueryDTO<CustomerTypeMap>) {
return ResourceQuery.query({
service: this.customersService,
query,
schema: CustomerDTO,
ability: req.ability,
map: (customer, ability) => CustomerDTO.fromModel(customer, ability),
});
}
```
أنشئ خدمات الموارد باستخدام `QueryService` ومفوّض متوافق مع Prisma:
```ts
import { Injectable } from '@nestjs/common';
import { QueryService, type BaseDelegateTypeMap } from '@querry-kit/nest';
import { Prisma, PrismaService } from '../prisma';
interface CustomerTypeMap extends BaseDelegateTypeMap {
select: Prisma.CustomerSelect;
include: Prisma.CustomerInclude;
whereInput: Prisma.CustomerWhereInput;
orderByWithRelationInput: Prisma.CustomerOrderByWithRelationInput;
whereUniqueInput: Prisma.CustomerWhereUniqueInput;
scalarFieldEnum: Prisma.CustomerScalarFieldEnum;
}
@Injectable()
export class CustomersService extends QueryService<typeof PrismaService.prototype.customer, CustomerTypeMap> {
constructor(prisma: PrismaService) {
super(prisma.customer);
}
}
```
تتوفر مسارات فرعية مركّزة لعمليات استيراد أصغر:
```ts
import { createCaslAccessibleWhere, filterCaslFields } from '@querry-kit/nest/casl';
import { ApiResourceQuery } from '@querry-kit/nest/decorators';
import { Fields } from '@querry-kit/nest/fields';
import { parseObject } from '@querry-kit/nest/object';
import { QueryService } from '@querry-kit/nest/query-service';
```
## 🔐 CASL
CASL اختياري. مرّر `ability` فقط عندما ينبغي لنقطة النهاية دمج شرط `where` واعٍ بالتفويض عبر `QueryService`؛ احذفه لواجهات API التي لا تستخدم CASL.
```ts
import { createCaslAccessibleWhere } from '@querry-kit/nest/casl';
super(prisma.customer, {
subject: 'Customer',
accessibleWhere: createCaslAccessibleWhere({ action: 'read' }),
});
```
عند تمرير ability إلى `query`، تدمج الخدمة شرط CASL where مع مرشحات المستخدم كـ `{ AND: [accessibleWhere, parsedWhere] }`.
لأذونات الاستجابة على مستوى الحقول، رشّح DTO المكتمل دون تعديله:
```ts
return filterCaslFields(dto, 'Customer', ability);
```
تستخدم الأداة المساعدة إجراء `read` افتراضيًا. مرّر `{ action: RoleAction.READ }` عندما يستخدم التطبيق إجراءات بأحرف كبيرة أو مدعومة بـ enum. إنها ترشّح حقول DTO المُسلسَلة فقط؛ استمر في تمرير ability إلى `QueryService` لتقييد قراءات قاعدة البيانات أيضًا.
## 🎯 الحقول
`fields` اختيارية افتراضيًا. عند حذفها، تُرجع Query Kit استجابة DTO الكاملة. عند وجودها، تتحقق من الصياغة والحقول المحددة، وتضيف تضمينات العلاقات المطلوبة، وتُسقط DTOs المُرجَعة. الأقواس الخارجية اختيارية، لذا `{id,title}` مكافئة لـ `id,title`.
```txt
GET /books?fields=id,title
GET /books?fields={id,title}
GET /books?fields=items{id,title},meta{page,perPage,itemCount,pageCount}
GET /books?fields=items{},meta{page}
```
قيمة فارغة صريحة (`?fields=`) أو تحديد خارجي فارغ (`?fields={}`) يُرجع `{}`. التحديدات المتداخلة الفارغة صالحة أيضًا: `items{}` ينتج كائنات عناصر فارغة، بينما `meta{page}` يحتفظ فقط ببيانات الصفحة المطلوبة. القيمة التي تحتوي على مسافات بيضاء فقط تبقى غير صالحة.
استخدم `prepareFieldsQuery` مباشرة عندما يحتاج المتحكم إلى تنسيق خدمة مخصص:
```ts
import { Fields, prepareFieldsQuery } from '@querry-kit/nest/fields';
const prepared = prepareFieldsQuery({
fields: query.fields,
include: query.include,
schema: BookDTO,
requiredInclude: { author: true },
});
const { items, pageMeta } = await booksService.query({ ...query, include: prepared.include });
return {
items: Fields.project(items.map(BookDTO.fromModel), prepared.projection),
meta: Fields.project(pageMeta, prepared.metaProjection),
};
```
## 📖 التوثيق
- [البدء](https://querry-kit.github.io/querry-kit/docs/nest/guide/getting-started)
- [مثال API كامل](https://querry-kit.github.io/querry-kit/docs/nest/guide/example-app)
- [متحكم CRUD](https://querry-kit.github.io/querry-kit/docs/nest/guide/crud-controller)
- [الحقول](https://querry-kit.github.io/querry-kit/docs/nest/api/fields/)
- [خدمة الاستعلام](https://querry-kit.github.io/querry-kit/docs/nest/api/query-service)
- [DTOs والترقيم](https://querry-kit.github.io/querry-kit/docs/nest/api/dtos-pagination)
- [مزخرفات OpenAPI](https://querry-kit.github.io/querry-kit/docs/nest/api/openapi)
- [CASL](https://querry-kit.github.io/querry-kit/docs/nest/api/casl)
- [مرجع API](https://querry-kit.github.io/querry-kit/docs/nest/api/)
## 🛠 التطوير
```sh
pnpm install
pnpm lint
pnpm check
pnpm test
pnpm test:coverage
pnpm build
```
تسمح قائمة السماح لبناء مساحة العمل بالسكربتات الأصلية المطلوبة لسلسلة أدوات الاختبار والتوثيق، بما في ذلك مراقب ملفات Parcel.
يجمع `pnpm test:coverage` جميع ملفات المصدر، ويطبع ملخص التغطية، ويكتب تقارير HTML وLCOV إلى `coverage/`. يشغّل GitHub Actions الأمر نفسه ويحتفظ بالتقرير كأثر لسير العمل.
Comments
0 Rating appears after 10 ratings
Sign in to join the discussion.