انتقل إلى المحتوى

خيارات التصفية ​

في الوضع full، يحمل الرأس لوحة Graph Filters (رمز المسار، أو Shift+K) الذي تم تصميم شكله خصيصًا لك. بشكل افتراضي تستمد المكتبة هذا النموذج عن طريق مسح بيانات العقدة؛ UI.filter يتيح لك تولي ذلك.

ts
const options = {
    UI: {
        filter: {
            facets: [ /* … */ ],   // declare the facets — the form follows
            excludeKeys: ['uuid'], // or just prune the derived ones
        },
    },
}

UI.filter.enabled: false يزيل اللوحة وحبوبها و Shift+K تمامًا؛ graph.queryEngine لا يزال يقوم بالتصفية من الكود.

النموذج ينطبق على نفسه: يتم تنفيذ الاختيار أو العلامة في اللحظة التي تقوم فيها بذلك، أو إرسال رسالة نصية أو حقل النمط ينبض بعد التوقف عن الكتابة. لا يوجد زر تطبيق، لذا يمكن للوحة ذلك لا تعرض أبدًا مرشحًا لم تحتوي عليه اللوحة القماشية. إعادة تعيين، بجانب تسمية القسم، يمسح كل مرشح السمات مرة واحدة.

تصفية الحواف، وليس العقد

كل شيء في هذه الصفحة يختار العقد. لتصفية الحواف — إخفاء العلاقة بأكملها اكتب دون تحريك الرسم البياني — أعلن UI.filter.edgeFacets بدلاً من ذلك؛ يعيدون استخدام نفس المفردات الجانبية وتم توثيقها ضمن طبقات الحافة.

الاشتقاق التلقائي (الافتراضي) ​

مع عدم وجود UI.filter على الإطلاق، تقوم اللوحة بالتنقل بين مفاتيح بيانات كل عقدة، وتجمع البيانات قيم مميزة لكل مفتاح، ويختار عنصر واجهة مستخدم مما يجده:

كيف تبدو القيمالقطعة
جميع الأرقامnumberRange (الحد الأدنى / الحد الأقصى)
3+ سلاسل قصيرةmultiselect
1-2 سلاسل قصيرةselect
منطقيةselect (صحيح / خطأ)
أي شيء آخرtext

يتم تجميل الملصقات من المفتاح (attr-type → نوع Attr). هذا جيد الإعداد الافتراضي هو صفر للبيانات الاستكشافية، لكن ليس لديه طريقة لمعرفة المفاتيح هي أوجه وهي داخلية - أ uuid تصبح قائمة منسدلة بخيار واحد لكل عقدة، ويتحول حقل النص الحر الطويل إلى مربع نص.

excludeKeys ​

الحل الرخيص عندما يكون الاشتقاق صحيحًا تقريبًا: قم بإسقاط المفاتيح التي تسبب الضوضاء.

ts
UI: { filter: { excludeKeys: ['uuid', 'imageUrl', 'description'] } }

الجوانب المعلنة ​

اضبط facets وسيتم إنشاء النموذج من إعلانك بدلاً من ذلك — بالضبط الحقول التي تدرجها، بالترتيب الذي تدرجها به، مع تسمياتك. الاشتقاق التلقائي هو تم تخطيها بالكامل، لذلك لا شيء يتغير مع تغير البيانات.

ts
UI: {
    filter: {
        facets: [
            { key: 'category', label: 'Category', type: 'multiselect',
              options: (graph) => distinct(graph, 'category') },
            { key: 'to_ids',   label: 'IDS flag', type: 'boolean' },
            { key: 'value',    label: 'Value',    type: 'regex' },
        ],
    },
}

الوجه key هو أيضًا مفتاح استخدامات queryEngine.setFilter(key, …)، لذا التصفية الآلية وتبقى اللوحة على نفس المستوى.

أنواع الواجهة ​

  • text — سلسلة فرعية أو تطابق تام، لكل matchMode.
  • regex — نمط تم تجميعه غير حساس لحالة الأحرف. نمط غير قابل للترجمة يتم الإبلاغ عنها في الميدان وتترك المرشحات النشطة دون تغيير.
  • select / multiselect — اختر من options. تمرير مصفوفة، أو تم حل الوظيفة مقابل الرسم البياني المباشر بحيث تتبع قوائم الخيارات البيانات دون أن يتغير الوجه.
  • numberRange — زوج الحد الأدنى / الحد الأقصى.
  • boolean — قائمة منسدلة صحيحة / خاطئة / غير محددة.

التسميات ​

يتم استخدام label المعلن حرفيًا، لذلك يمكن أن يأتي من ترجمتك طبقة. احذفه ويتم تجميل المفتاح كما هو الحال في الاشتقاق التلقائي.

الأوجه المحسوبة: accessor ​

بشكل افتراضي يقرأ الوجه node.getData()[key]. يقرأ accessor ما تريد مثل - بما في ذلك الأشياء غير الموجودة في العقدة على الإطلاق:

ts
// "this object contains an attribute of type X" — reads the node's children
{ key: 'child_type', label: 'Contains attribute of type', type: 'multiselect',
  options: () => ATTRIBUTE_TYPES,
  accessor: (node) => node.children.map((child) => child.getData()['attr-type']) }

يعد إرجاع المصفوفة أمرًا جيدًا — راجع مطابقة المصفوفات أدناه.

السيطرة الكاملة: predicate ​

أ predicate يقرر العضوية بنفسه، ويفوز على accessor / matchMode. يتم تشغيله لكل عقدة لكل تطبيق مرشح، لذا اجعله رخيصًا.

ts
{ key: 'busy', label: 'Busy services', type: 'text',
  predicate: (node, value) => node.getData().load >= Number(value) }

الوجه الذي رمياته accessor أو predicate يتوقف عن المطابقة (ويحذر مرة واحدة) بدلاً من أخذ العرض معه.

الطلب ​

الحقول تتبع ترتيب الإعلان. اضبط order على الوجه لوضعه بشكل صريح — مفيد عندما يتم تجميع الجوانب من عدة أماكن.

مطابقة ​

matchMode يقرر كيفية مقارنة قيمة المرشح:

  • 'exact' افتراضي — المساواة الصارمة. ل التحديد المتعدد (مجموعة من الاختيارات) هذه هي العضوية: أي منها.
  • 'partial' — تطابق السلسلة الفرعية، String(nodeValue).includes(value).
  • 'all' — و-الدلالات: يجب أن تكون كل قيمة محددة موجودة.

مطابقة المصفوفات ​

عندما تكون قيمة العقدة array — data.tags = ['tlp:amber', 'malware'] — أ اختبارات التصفية العضوية وليست المساواة:

ts
// matches nodes tagged 'malware'; does NOT match a node tagged 'not-malware'
graph.queryEngine.setFilter('tags', { value: 'malware' })

// any-of: amber OR green
graph.queryEngine.setFilter('tags', { value: ['tlp:amber', 'tlp:green'] })

// all: amber AND green
graph.queryEngine.setFilter('tags', { value: ['tlp:amber', 'tlp:green'], matchMode: 'all' })

مع 'partial'، قد يتطابق أي عنصر منفرد مع السلسلة الفرعية. ا numberRange ضد تتطابق المصفوفة عندما يقع أي عنصر داخل النطاق.

تغيير السلوك

قبل أن يتم دعم ذلك، وصلت قيمة عقدة الصفيف إلى String(nodeValue).includes(value) — لذا قم بتصفية malware بالخطأ تطابقت مع عقدة تحمل علامة not-malware، ولم تتم مطابقة قيمة مرشح الصفيف مطلقًا الكل. كلاهما يتصرف الآن كما هو موضح أعلاه.

النفي ​

negate: true يحتفظ بما قد يخفيه الفلتر. يحتوي كل حقل في اللوحة على is / is not قم بتشغيل صف التسمية الخاص به الذي يحدده؛ يتم رسم الحقل الذي تم التبديل إليه ليس الأحمر، ضربت اللقطات من خلال.

ts
// every type but domain, including types added later
graph.queryEngine.setFilter('type', { value: ['domain'], negate: true })

// nothing tagged malware
graph.queryEngine.setFilter('tags', { value: ['malware'], negate: true })

تتم قراءته في الاتجاه المعاكس لكل عنصر واجهة مستخدم: القائمة هي لا شيء من، حقل نصي لا يحتوي على (مع 'partial')، نمط لا يتطابق، نطاق خارج. مع 'all' هو ليس كل. إجابة الوجه predicate مقلوبة.

يتم الاحتفاظ بالعقدة التي تحتوي على لا قيمة للمفتاح، لأنها ليست مجالًا أيضًا. لذلك مرشح ونفيه يقسم الرسم البياني دائمًا إلى قسمين، كل عقدة على جانب واحد بالضبط. قيمة لا يضيق شيئًا (قائمة فارغة، سلسلة فارغة، نطاق مفتوح، نمط غير قابل للاستخدام) لا يزال يضيق شيئا.

حقول الصواب/الخطأ ليس لها أي تبديل: ليس صحيحًا هو خطأ. مرشحات الحافة (setEdgeFilter) خذ negate أيضًا. قسم أسطورة يشترك في أحد الجوانب يبقي المفتاح عامل التصفية المُلغى مُلغى عند النقر فوقه.

إخفاء العقد غير المتصلة ​

تصفية العلاقات بعيدًا تترك العقد خلفها. التبديل ان طبقة الحافة معطلة وتبقى العقدة التي كانت علاقتها الوحيدة بها على قماش بدون أي شيء مرفق – وهو أمر متعمد، لأن الطبقة عبارة عن عدسة. عندما do تريد إزالة تلك العقد، هذه قاعدة جانب العقدة:

ts
const options = {
    UI: {
        filter: { hideDisconnected: true },
    },
}

يتم إخفاء العقدة عندما لا تحتوي على حافة يسارية مرئية، تُحسب بعد الطبقات والطبقة كان لمرشحات العقدة رأيها. تعتبر الحلقة الذاتية بمثابة علاقة؛ ملاحظة مثبتة على أ العقدة لا.

يوجد المفتاح نفسه في القائمة المنبثقة عرض كـ إخفاء غير متصل، على كل رسم بياني، مع إيقاف التشغيل ما لم يتم تشغيله - حتى يتمكن المستخدم من تنظيف الطبقات اليتيمة من خلال تبديل الطبقة إلى اليسار، أو أعد تلك التي أخفيتها. بينما هو مختبئ، الصف يقول كم.

هذا واحد يتحرك الرسم البياني

كل شيء آخر في هذه الصفحة، وكل طبقة حافة، يترك التخطيط بمفرده. مخفي العقدة تترك المحاكاة، وبالتالي فإن الباقي يستقر مرة أخرى. تلك هي التجارة مقابل لوحة قماشية مرتبة، وهذا هو سبب إيقاف تشغيل القاعدة بشكل افتراضي.

شيئان لا يفعلهما عمدا:

  • ** يتم ترك التصميمات الداخلية للكتلة بمفردها.** تقوم المجموعات بشكل روتيني بتجميع العقد بدون علاقات بينهما، لذا فإن تطبيق القاعدة داخل أحدهما سيفتح صندوقًا فارغًا.
  • ** لا شيء محمي.** قم بإيقاف تشغيل كل طبقة ولا يوجد شيء متصل، لذلك لا شيء يتم رسمها. التبديل هو طريق العودة.
ts
graph.queryEngine.setHideDisconnected(true)  // same as the switch
graph.queryEngine.isHideDisconnected()
graph.queryEngine.getDisconnectedNodeCount() // what the switch row reports

إعادة التقديم بعد تغير البيانات ​

يتم تطبيق المرشحات عندما يتغير المرشح، وليس عندما تتغير بيانات الرسم البياني. أضف الحافة كانت العقدة مفقودة وتظل مخفية حتى يتم إعادة حساب شيء ما:

ts
graph.updateData(newNodes, newEdges)
graph.queryEngine.reapply()   // recompute now

يستحق المعرفة قبل أن تسميه: إعادة اشتقاق الرؤية ** يلغي الدليل graph.hideNode()**، الذي لا يذكره شيء. queryEngine.excludeNode() هو الإخفاء الذي يبقى — هو ما تستخدمه قائمة السياق والإجراءات المجمعة، وعرض فقط العقدة عكسها.

حيث تحصل اللوحة على قيمها ​

تصفية القيم تتدفق دائمًا خلال graph.queryEngine، أيًا كانت طريقة النموذج مُصمم - إذن عدد عوامل التصفية النشطة للرأس، وقائمة العقد المخفية، و يستمر النشر في الرسم البياني الفرعي للمجموعة الموسعة في العمل. الجوانب المعلنة يتم تسليمها إلى الرسم البياني الفرعي للمجموعة أيضًا، لذا فإن الوجه accessor / predicate يقوم بتصفية الأطفال تمامًا كما يقوم بتصفية العقد ذات المستوى الأعلى.

اللوحة القماشية أسطورة هي طريقة ثالثة لنفس المحرك: النقر فوق يخفي صف وسيلة الإيضاح هذه الفئة. امنح الأسطورة key المعلن عنها select / multiselect الوجه والمحركان واحد مرشح، وبالتالي فإن اللوحة السيطرة والأسطورة البقاء في الخطوة.

جدول البيانات هو الرابع: زر تطبيق على الرسم البياني يخفي العناصر التي تتركها مرشحات الأعمدة الخاصة به. هذا الدفع يهبط تحت مفتاح محجوز خاصة بها، لذا فهي تنجو من أي شيء ينطبق عليه نموذج هذه اللوحة ويتم دمجه مع أي شيء آخر تقوم هذه اللوحة بالتصفية بدلاً من استبدالها. لأن النموذج من الناحية الهيكلية لا يمكن أن يظهر أ مفتاح محجوز، تنمو اللوحة على شكل صف من الجدول يذكر ما يخفيه الدفع — والمكان الآخر الوحيد الذي يمكن إخلاءه منه بمجرد طي الرصيف بعيدًا.

شاهد محرك التصفية/الاستعلام بطاقة المعرض للحصول على مثال حي، و FilterFacet ل النوع الكامل.