الإشارات هي مكتبة لإدارة الدولة ذات الأداء مع هدفين أساسيين:
اقرأ منشور الإعلان لمعرفة المزيد عن المشكلات التي تحل إشارات وكيف أصبحت.
# Just the core library
npm install @preact/signals-core
# If you're using Preact
npm install @preact/signals
# If you're using React
npm install @preact/signals-react
# If you're using Svelte
npm install @preact/signals-core
signal(initialValue)
signal.peek()
computed(fn)
effect(fn)
batch(fn)
untracked(fn)
تكشف مكتبة الإشارات أربع وظائف هي لبنات البناء لنمذجة أي منطق عمل يمكنك التفكير فيه.
signal(initialValue)
تنشئ وظيفة signal
إشارة جديدة. الإشارة هي حاوية لقيمة يمكن أن تتغير بمرور الوقت. يمكنك قراءة قيمة الإشارة أو الاشتراك في تحديثات القيمة من خلال الوصول إلى خاصية .value
.
import { signal } from "@preact/signals-core" ;
const counter = signal ( 0 ) ;
// Read value from signal, logs: 0
console . log ( counter . value ) ;
// Write to a signal
counter . value = 1 ;
يتم الكتابة إلى إشارة عن طريق تعيين خاصية .value
. يؤدي تغيير قيمة الإشارة إلى تحديث كل تأثير محسوب ويعتمد على تلك الإشارة ، مما يضمن أن حالة التطبيق الخاصة بك متسقة دائمًا.
signal.peek()
في الحالة النادرة التي يكون لديك تأثير يجب أن تكتب إلى إشارة أخرى بناءً على القيمة السابقة ، لكنك لا تريد أن يتم الاشتراك في التأثير في هذه الإشارة ، يمكنك قراءة القيمة السابقة للإشارات عبر signal.peek()
.
const counter = signal ( 0 ) ;
const effectCount = signal ( 0 ) ;
effect ( ( ) => {
console . log ( counter . value ) ;
// Whenever this effect is triggered, increase `effectCount`.
// But we don't want this signal to react to `effectCount`
effectCount . value = effectCount . peek ( ) + 1 ;
} ) ;
لاحظ أنه يجب عليك استخدام signal.peek()
فقط إذا كنت بحاجة إليها حقًا. قراءة قيمة الإشارة عبر signal.value
هي الطريقة المفضلة في معظم السيناريوهات.
computed(fn)
غالبًا ما يتم اشتقاق البيانات من أجزاء أخرى من البيانات الموجودة. تتيح لك الوظيفة computed
الجمع بين قيم الإشارات المتعددة في إشارة جديدة يمكن أن تتفاعل معها ، أو حتى استخدامها بواسطة محسّنات إضافية. عند تغيير الإشارات التي تم الوصول إليها من داخل تغيير رد الاتصال المحسوب ، يتم إعادة تنفيذ رد الاتصال المحسوب ويصبح قيمة الإرجاع الجديدة هي قيمة الإشارة المحسوبة.
import { signal , computed } from "@preact/signals-core" ;
const name = signal ( "Jane" ) ;
const surname = signal ( "Doe" ) ;
const fullName = computed ( ( ) => name . value + " " + surname . value ) ;
// Logs: "Jane Doe"
console . log ( fullName . value ) ;
// Updates flow through computed, but only if someone
// subscribes to it. More on that later.
name . value = "John" ;
// Logs: "John Doe"
console . log ( fullName . value ) ;
سيتم الاشتراك تلقائيًا أي إشارة يتم الوصول إليها داخل وظيفة رد الاتصال computed
وتتبعها كاعتماد على الإشارة المحسوبة.
effect(fn)
وظيفة effect
هي آخر قطعة تجعل كل شيء رد فعل. عند الوصول إلى إشارة داخل وظيفة رد الاتصال الخاصة بها ، سيتم تنشيط هذه الإشارة وكل تبعية الإشارة المذكورة واشتراكها. في هذا الصدد ، يشبه إلى حد كبير computed(fn)
. بشكل افتراضي ، تكون جميع التحديثات كسولًا ، لذلك لن يتم تحديث أي شيء حتى تصل إلى effect
داخل الإشارة.
import { signal , computed , effect } from "@preact/signals-core" ;
const name = signal ( "Jane" ) ;
const surname = signal ( "Doe" ) ;
const fullName = computed ( ( ) => name . value + " " + surname . value ) ;
// Logs: "Jane Doe"
effect ( ( ) => console . log ( fullName . value ) ) ;
// Updating one of its dependencies will automatically trigger
// the effect above, and will print "John Doe" to the console.
name . value = "John" ;
يمكنك تدمير التأثير وإلغاء الاشتراك من جميع الإشارات التي تم الاشتراك فيها ، من خلال استدعاء الوظيفة التي تم إرجاعها.
import { signal , computed , effect } from "@preact/signals-core" ;
const name = signal ( "Jane" ) ;
const surname = signal ( "Doe" ) ;
const fullName = computed ( ( ) => name . value + " " + surname . value ) ;
// Logs: "Jane Doe"
const dispose = effect ( ( ) => console . log ( fullName . value ) ) ;
// Destroy effect and subscriptions
dispose ( ) ;
// Update does nothing, because no one is subscribed anymore.
// Even the computed `fullName` signal won't change, because it knows
// that no one listens to it.
surname . value = "Doe 2" ;
قد يعيد رد الاتصال تأثير وظيفة التنظيف. يتم تشغيل وظيفة التنظيف مرة واحدة ، إما عندما يتم استدعاء رد اتصال التأثير التالي أو عند التخلص من التأثير ، أيهما يحدث أولاً.
import { signal , effect } from "@preact/signals-core" ;
const count = signal ( 0 ) ;
const dispose = effect ( ( ) => {
const c = count . value ;
return ( ) => console . log ( `cleanup ${ c } ` ) ;
} ) ;
// Logs: cleanup 0
count . value = 1 ;
// Logs: cleanup 1
dispose ( ) ;
batch(fn)
تتيح لك وظيفة batch
الجمع بين إشارات متعددة تكتب في تحديث واحد يتم تشغيله في النهاية عند اكتمال رد الاتصال.
import { signal , computed , effect , batch } from "@preact/signals-core" ;
const name = signal ( "Jane" ) ;
const surname = signal ( "Doe" ) ;
const fullName = computed ( ( ) => name . value + " " + surname . value ) ;
// Logs: "Jane Doe"
effect ( ( ) => console . log ( fullName . value ) ) ;
// Combines both signal writes into one update. Once the callback
// returns the `effect` will trigger and we'll log "Foo Bar"
batch ( ( ) => {
name . value = "Foo" ;
surname . value = "Bar" ;
} ) ;
عند الوصول إلى إشارة كتبتها في وقت سابق داخل رد الاتصال ، أو الوصول إلى إشارة محسوبة تم إبطالها بواسطة إشارة أخرى ، سنقوم بتحديث التبعيات اللازمة فقط للحصول على القيمة الحالية للإشارة التي تقرأها منها. سيتم تحديث جميع الإشارات البطيئة الأخرى في نهاية وظيفة رد الاتصال.
import { signal , computed , effect , batch } from "@preact/signals-core" ;
const counter = signal ( 0 ) ;
const double = computed ( ( ) => counter . value * 2 ) ;
const triple = computed ( ( ) => counter . value * 3 ) ;
effect ( ( ) => console . log ( double . value , triple . value ) ) ;
batch ( ( ) => {
counter . value = 1 ;
// Logs: 2, despite being inside batch, but `triple`
// will only update once the callback is complete
console . log ( double . value ) ;
} ) ;
// Now we reached the end of the batch and call the effect
يمكن تداخل الدُفعات وسيتم مسح التحديثات عند اكتمال مكالمة الدُفعات الخارجية.
import { signal , computed , effect , batch } from "@preact/signals-core" ;
const counter = signal ( 0 ) ;
effect ( ( ) => console . log ( counter . value ) ) ;
batch ( ( ) => {
batch ( ( ) => {
// Signal is invalidated, but update is not flushed because
// we're still inside another batch
counter . value = 1 ;
} ) ;
// Still not updated...
} ) ;
// Now the callback completed and we'll trigger the effect.
untracked(fn)
في حالة تلقي رد اتصال يمكنه قراءة بعض الإشارات ، لكنك لا ترغب في الاشتراك في ذلك ، يمكنك استخدام untracked
لمنع حدوث أي اشتراكات.
const counter = signal ( 0 ) ;
const effectCount = signal ( 0 ) ;
const fn = ( ) => effectCount . value + 1 ;
effect ( ( ) => {
console . log ( counter . value ) ;
// Whenever this effect is triggered, run `fn` that gives new value
effectCount . value = untracked ( fn ) ;
} ) ;
MIT
، انظر ملف الترخيص.