لا يتعامل JSDOM حاليًا مع التحقق من صحة نماذج HTML5 ، وخاصةً checkValidity API.
هذا ضروري لاختبار التطبيقات الحديثة التي تستخدم نماذج HTML5 بدقة.
أتساءل عما إذا كان من الممكن إضافة هذا الدعم ، باستخدام http://www.thecssninja.com/javascript/h5f كنقطة انطلاق. H5F عبارة عن مجموعة متصفح لإضافة دعم نماذج HTML5 للمتصفحات التي لا تدعمها. جانبا ، سأكون سعيدا لإضافة هذا السلوك بنفسي إذا كان شخص ما يمكن أن يرشدني إلى أفضل طريقة للقيام بذلك.
أوافق على أن هذا سيكون لطيفًا ومهمًا. ومع ذلك ، ستكون المهمة تمامًا.
أكبر شيء يحتاجه هذا هو مجموعة اختبار قوية. إذا نظرت في إرشادات Contributing.md ، فهناك بعض المؤشرات حول مكان العثور عليها ، أو إذا فشلت في ذلك ، فما هي القوائم البريدية التي يجب أن تطلبها. إذا كان بإمكانك استكشافها ، أعتقد أن لدينا فرصة لتنفيذ ذلك ، خاصةً كما أشرت باستخدام H5F كنقطة انطلاق.
الجزء المهم الآخر الوحيد من التنفيذ الفعلي هو أنه ليس لدينا مجلد "level4" أو "html5" مناسب لتنفيذ أشياء تتجاوز المستوى 3. لكن هذا شيء احتجناه لفترة ، لذا سأحاول للحصول عليه قريبًا.
: +1: ستكون ميزة رائعة.
أقوم الآن بإضافة https://github.com/hyperform/hyperform باعتباره polyfill بعد إعداد jsdom. إنه يعمل بشكل رائع.
ياي! أنا مؤلف Hyperform. ولحسن الحظ ، أستخدم JSDom بالفعل لإعداد بيئة اختبار .
الجزء الذي قد يكون مثيرًا للاهتمام لمشرفي JSDom: لقد لعبت مع استخدام Hyperform داخل JSDom أيضًا لتغطية اختبارات منصة الويب المناسبة:
$ git diff test/web-platform-tests/create-jsdom.js
diff --git a/test/web-platform-tests/create-jsdom.js b/test/web-platform-tests/create-jsdom.js
index 7009df7..9edcb16 100644
--- a/test/web-platform-tests/create-jsdom.js
+++ b/test/web-platform-tests/create-jsdom.js
@@ -1,5 +1,6 @@
"use strict";
const jsdom = require("../..");
+const hyperform = require("hyperform");
const nodeResolverPromise = require("../util").nodeResolverPromise;
const globalPool = { maxSockets: 6 };
@@ -35,6 +36,9 @@ module.exports = (urlPrefix, testPath) => {
return created
.then(window => {
+ global.window = window;
+ global.document = window.document;
+ hyperform(window);
return new Promise((resolve, reject) => {
const errors = [];
وإلغاء التعليق في اختبارات test/web-platform-tests/index.js
و "html/semantics/forms/constraints/*.html"
.
لسوء الحظ ، لم أحصل إلا على حالتين اختباريتين للتحول إلى اللون الأخضر. ولكن إذا كنت مهتمًا بإضافة (بأي طريقة) ميزات Hyperform إلى JSDom ، فسأضع المزيد من العمل في
أ) اجتياز تلك الاختبارات ، و
ب) توفير إصدار أو تكوين لـ Hyperform ، والذي يستثني واجهة برمجة التطبيقات عالية المستوى
FWIW ، أنا مهتم جدًا بهذا ؛ أنا أعمل على مكون Vue الذي يعرض نموذجًا بناءً على مخطط JSON ، ويعتمد على Validity API للحصول على حالة تحقق عند الإرسال. يتم تشغيل اختبارات الوحدة الخاصة بي باستخدام Jest (الذي يستخدم JSDOM تحت الغطاء) ، وحتى الآن لا يمكنني اختبار هذا الجزء.
Boldewyn إذا كان لديك أي اقتراح بخصوص حالتي ، فسأقبله بكل سرور. ربما يمكنني تقديم بعض المساعدة في تنفيذ هذا أيضًا ، إذا أعطيت بعض الإرشادات للبدء منها :)
تحرير: لقد استخدمت حل EricHenry أدناه ، وقد نجح. كان عليّ فقط تعيين checkValidity
لـ HTMLInputElement
، HTMLSelectElement
، و HTMLTextAreaElement
أيضًا (وفي الواقع لم أكن بحاجة إلى العبث بـ HTMLFormElement
). هتافات!
لأي شخص لديه هذه المشكلة عند اختبار مكونات React باستخدام Jest and Enzyme ، تمكنت من إعادة تعبئة JSDOM باستخدام حزمة hyperform المذكورة أعلاه من خلال fernandopasik و Boldewyn
في ملف الاختبار الخاص بك ، يمكنك القيام بما يلي بعد تثبيت hyperform.
import * as hyperform from 'hyperform';
var global = global;
const defineValidity = {
get() {
return hyperform.ValidityState(this);
},
configurable: true
};
global.HTMLFormElement.prototype.checkValidity = function() {
return hyperform.checkValidity(this);
};
Object.defineProperty(global.HTMLFormElement.prototype, 'validity', defineValidity);
Object.defineProperty(global.HTMLInputElement.prototype, 'validity', defineValidity);
Object.defineProperty(global.HTMLSelectElement.prototype, 'validity', defineValidity);
Object.defineProperty(global.HTMLTextAreaElement.prototype, 'validity', defineValidity);
يمكنك اتباع نفس الطريقة لأية عناصر HTMLE أخرى قد تحتاج إلى تعديلها أو أي سمات أخرى تحتاجها لإعادة التعبئة.
يطبق PR # 2142 واجهة برمجة تطبيقات القيد الكاملة بدون أي حزم متعددة
تقترح مستندات Jest طرقًا للسخرية لم يتم تنفيذها في JSDOM . أعتقد أن هذا حل أنظف من تلويث بيئتك بسبب الاختبارات.
في حالتي المحددة ، كنت بحاجة إلى التحقق من صحة نموذج ثم فحص classList
للنموذج بحثًا عن وجود فئة معينة ، حيث سيعلمني وجودها بصحة النموذج.
كان الحل هو الاستهزاء بخصائص النموذج ، على سبيل المثال ، محاكاة التنفيذ الأصلي لخاصية DOMTokenList
لـ classList
بالداخل
beforeAll(() => {
window.DOMTokenList = jest.fn().mockImplementation(() => {
return {
list: [],
remove: jest.fn().mockImplementation(function (item) {
const idx = this.list.indexOf(item);
if (idx > -1) {
this.list.splice(idx, 1)
}
}),
add: jest.fn().mockImplementation(function (item) {
this.list.push(item);
}),
contains: jest.fn().mockImplementation(function (item) {
return this.list.indexOf(item) > -1;
})
};
});
})
ثم استخدمت ذلك لتمرير الخصائص إلى معالج الأحداث. يمكنني الوصول إلى النموذج في مكون التفاعل الخاص بي من زر الإرسال باستخدام event.currentTarget.form
let mockClassList = new DOMTokenList();
submitBtn.simulate('click', {
currentTarget: {
form: {
checkValidity: () => false,
classList: mockClassList
}
},
preventDefault: jest.fn(),
stopPropagation: jest.fn()
})
يسمح لي هذا بتعيين صلاحية النموذج على خطأ وصحيح ، وفحص mockClassList
لوجود فئة was-validated
في كل مرة
submitBtn.simulate('click', {
currentTarget: {
form: {
checkValidity: () => false,
classList: mockClassList
}
},
preventDefault: jest.fn(),
stopPropagation: jest.fn()
});
expect(mockClassList.contains('was-validated')).toBeTruthy();
submitBtn.simulate('click', {
currentTarget: {
form: {
checkValidity: () => true,
classList: mockClassList
}
},
preventDefault: jest.fn(),
stopPropagation: jest.fn()
});
expect(mockClassList.contains('was-validated')).toBeFalsy();
لمعلوماتك: أنا أستخدم عرض Enzyme الضحل لهذا ، لا يبدو أن mount يعمل مع هذا الحل. ومع ذلك ، فإنني أميل إلى الاعتقاد بأن الاقتراح الآخر لطرق الاستهزاء التي لم يتم تنفيذها في JSDOM ، عندما يتم تنفيذ الطريقة مباشرة في بيان الملف الذي تم اختباره ، قد يعمل فقط مع عرض mount
لدي مشكلة مع input.validity
وهو غير متوفر لي في j [email protected] .
// EditableInput.js:
this.inputElement = React.createRef();
...
const input = this.inputElement.current;
console.error('input.validity: ', input.validity);
// EditableInput.test.js run outcome:
console.error src/components/Form/Input/EditableInput.js:47
input.validity: undefined
// yarn.lock:
jsdom@^11.5.1:
version "11.12.0"
resolved "https://registry.yarnpkg.com/jsdom/-/jsdom-11.12.0.tgz#1a80d40ddd378a1de59656e9e6dc5a3ba8657bc8"
integrity sha512-y8Px43oyiBM13Zc1z780FrfNLJCXTL40EWlty/LXUtcjykRBNgLlCjWXpfSPBl2iv+N7koQN+dvqszHZgT/Fjw==
أرى أن الإصدار الذي كان يجب إصلاحه هو 11.8.0 حيث تم إصداره في اليوم الذي تم فيه دمج PR مع صلاحية inteface. هل فاتني شيء؟
التعليق الأكثر فائدة
: +1: ستكون ميزة رائعة.