Typescript: دعم خصائص ES Rest / Spread المقترحة

تم إنشاؤها على ٢١ فبراير ٢٠١٥  ·  96تعليقات  ·  مصدر: microsoft/TypeScript

اقتراح es7: https://github.com/sebmarkbage/ecmascript-rest-spread

خصائص انتشار

الكتابة

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

var obj = { x: 1, y: 2};
var obj1 = {...obj, z: 3, y: 4}; // not an error

لدي خوارزمية تحقق من النوع ساذج جدًا لميزة مماثلة ( JSXSpreadAttribute ) في شوكة jsx-typescript الصغيرة الخاصة بي: أنا فقط أنسخ خصائص الكائن _spread_ في جدول الخصائص عندما أصادف كائنًا منتشرًا ، وتجاوز تلك الممتلكات إذا صادفت إعلانًا يحمل اسمًا مشابهًا.

انبعاث

استخدم jstransform Object.assign ، قدم بابل الرقاقة:

var _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; };

ونحن إما أن يجبر وجود assign الدالة على ObjectConstructor اجهة، أو توفير وظيفة مشابهة (مع اسم مختلف).

أعتقد أن الحل الأمثل هو عدم إرسال أي مساعد في الهدف es6 (أو إذا تم تحديد Object.assign ) ، وإصدار دالة مساعدة لـ es5 ، es3 .

var obj = { x: 1, y: 2};
var obj1 = {...obj, z: 3};

/// ES6 emit
var obj = {x: 1, y: 2};
var obj1= Object.assign({}, obj, { z: 3 });

//ES3 emit
var __assign = function (target) { 
    for (var i = 1; i < arguments.length; i++) { 
        var source = arguments[i]; 
        for (var key in source) { 
            if (Object.prototype.hasOwnProperty.call(source, key)) { 
                target[key] = source[key];
            } 
        } 
    } 
    return target; 
};

var obj = {x: 1, y: 2};
var obj1= __assign({}, obj, { z: 3 });

خصائص الراحة

الكتابة

بالنسبة للكائن البسيط ، النوع الجديد هو نوع فرعي من التخصيص الذي لا يحتوي على الخصائص التي تم التقاطها قبل خصائص الباقي:

var obj = {x:1, y: 1, z: 1};
var {z, ...obj1} = obj;
obj1// {x: number; y:number};

إذا كانت مهمة الإتلاف تحتوي على إعلان فهرس ، فإن النتيجة لها أيضًا إعلان فهرس مشابه:

var obj: { [string: string]: string };
var {[excludedId], ...obj1} = obj;
obj1// { [string: string]: string };

من الواضح أنه لم يتم التقاط التصريحات الجديدة / المكالمات:

var obj: { (): void; property: string};
var { ...obj1} = obj;
obj1// { property: string };

انبعاث

لا يمكن إصدار _rest properties_ بدون وظيفة مساعد ، هذه الوظيفة من babel:

var obj = {x:1, y: 1, z: 1};
var {z, ...obj1} = obj;
var __objectWithoutProperties = function(obj, keys) {
    var target = {};
    for (var i in obj) {
        if (keys.indexOf(i) >= 0) continue;
        if (!Object.prototype.hasOwnProperty.call(obj, i)) continue;
        target[i] = obj[i];
    }
    return target;
};

var obj = {x:1, y: 1, z: 1};
var z = obj.z;
var obj1 = __objectWithoutProperties(obj, ["z"]);

_Edit: تمت إضافة بعض الأمثلة الصغيرة على الكتابة / البث

Committed ES Next Fixed Suggestion

التعليق الأكثر فائدة

لست متأكدًا من كيفية شحنه في النهاية ، لكنني بدأت العمل على الراحة / الانتشار في الكائنات الحرفية والتدمير . في الوقت الحالي ، تتمثل الخطة في استخدام polyfill __assign الخاص بنا للإصدار.

ال 96 كومينتر

ربما نحتاج إلى بعض الأمثلة حول كيفية إصدار هذا بشكل معقول في المستوى الأدنى (إذا كان ذلك في النطاق).

RyanCavanaugh ، أضفت بعض الأمثلة الصغيرة التي تنبعث منها وفكرة الكتابة.
أرغب في العمل على هذه الميزة لأنها على أي حال ميزة jsx وسأحتاج إلى إضافتها إلى مفترقتي ، ولكن إذا تمت إضافتها إلى مركز الطباعة فمن الأفضل ^^.

لقد اكتشفت مؤخرًا هذه الميزة في ES7 عبر هذه المقالة . يجب أن أقول ، إنه سهل الاستخدام!

أحب أن أرى هذا في TypeScript!

أي تحديثات على هذا؟ أحب أن أرى هذا في 1.6 لأنه سيكون مفيدًا للغاية عند استخدامه مع React: smile:

prabirshrestha للسجل ، لدينا حاليًا عامل JSX على master .

DanielRosenwasser هل يمكنك التفصيل؟ هل هذا يعني أن هذا يعمل بشكل جيد مع العلم --jsx؟ هل يشمل ذلك خصائص الراحة أم مجرد نشر الخصائص ؟

آسف mnpenner و prabirshrestha ، نعم ، قصدته على master . RyanCavanaugh يعرف أكثر عن هذا مما

تدعم JSX سمات الانتشار_ ، على سبيل المثال <TagName {...spreadedExpr} /> . لا علاقة لعامل انتشار ES6 بخلاف مشاركة نفس الرمز والحصول على دلالات مكافئة تقريبًا.

أنا مهتم جدًا بكل من Redux و React ، أصبح التلاعب في الحالة أسهل بكثير مع هذا. أتمنى أن أرى هذا مطبق

تمت الموافقة على الراحة / الانتشار للمرحلة الثانية الآن https://github.com/tc39/tc39-notes/blob/master/es7/2015-07/july-30.md

نريد انتظار وصول الاقتراح إلى المرحلة 3 قبل معالجة هذا الأمر.

إنه مفيد جدًا في التفاعل والإعادة ، يرجى تنفيذه في أسرع وقت ممكن ، من فضلك :-)

هذه وحدة مساعدة كنت أستخدمها للتغلب على هذا. إنه ليس مثاليًا حيث يتعين عليك تحديد جميع المفاتيح مرتين ، مرة على الجانب الأيسر ومرة ​​أخرى كسلاسل على الجانب الأيمن ، لكن لا يمكنني التفكير في طريقة أفضل للقيام بذلك. نرحب بأي ملاحظات ، أنا متأكد من أن هناك سلوك متطور فاتني!

https://gist.github.com/tomduncalf/fbae862b123445c117cb

هل هذا شيء تقبل التصحيح لأجله؟ (يتم دمجه بمجرد وصوله إلى المرحلة 3). وإذا كان الأمر كذلك ، فهل لديك أي مؤشرات حول مكان البدء في إجراء التغييرات لدعمه؟

هذه هي آخر ميزة ES7 + التي يستخدمها فريقي بكثافة والتي تمنعنا من التبديل إلى الكتابة المطبوعة ؛ أحب بالتأكيد أن يكون عاجلا ، إذا كان ذلك ممكنا.

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

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

في أي حال ،: +1: لمشغلي الانتشار في TS. :ابتسامة:

xogeny سأكون مهتمًا جدًا بإلقاء نظرة على تلك المكتبة. شكرا

@ cur3n4 لدي مستودع حيث كنت ألعب بهذه الأفكار. يتغير قليلاً (لأن كل هذا لا يزال يتطور). كنت أستخدم وحدات خاصة استفادت من updeep البداية وهذه الوظيفة لا تزال في المكتبة . لكني توقفت عن استخدامه لأنني وجدت صعوبة في الحفاظ على قيود النوع الضرورية. أظن أنه إذا كان Typescript يحتوي على شيء على غرار قيود النوع العام لـ Java super ، فيمكن أن يكون updeep (والعديد من المكتبات الأخرى ، مثل lodash أو ramda ) جعل الكثير من النوع الآمن.

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

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

: +1:

أحب أن أرى هذا.

+1

يجب أن يكون لديك ميزة ، يرجى تنفيذها

+1

+1 بناء جملة أجمل بكثير من دعم Object.assign + JSX

+1 يجب أن يكون لتطوير التفاعل لتمرير الدعائم لأسفل ( var { checked, ...other } = this.props; . انظر مستندات رد الفعل

يجب أن يكون لتطوير رد الفعل

لنكن صادقين ، إنها وسيلة راحة وليست ضرورية. الاقتراح في المرحلة 2 مع TC39. أوضح فريق TypeScript أنهم لا يريدون التفكير في تنفيذ الأشياء التي لم تنشأ في TypeScript حتى تصل إلى المرحلة 3. مكان "+1" هو TC39.

kitsonk - لا يمكنك توقع اعتماد جيد عندما تستدعي أطر عمل مثل التفاعل / إلخ هذه الأنواع من الأشياء في

حسنًا ، أعتقد أننا نتحدث عن موضوع أوسع. لن يقوم بائع متصفح واحد بتنفيذ أي شيء غير موجود في المرحلة 3 (ما لم يعجبه شخصيًا). يحاول TC39 إعطاء مستوى معين من التنظيم لجزء من الويب. لقد تعرض TypeScript للعض ، بشكل كبير ، من خلال القفز من البندقية من قبل (الوحدات النمطية ، وانظر إلى الفوضى التي تسببت في ذلك منذ ذلك الحين). أحترم أنهم يحاولون على الأقل وضع بعض التوجيهات والبنية حول ما يرغبون في تنفيذه ومتى. هل هناك اقتراح آخر بشأن المعيار الذي ينبغي استخدامه؟ لا أعتقد أن عبارة "لأن إطار عمل X يذكره في مستنداتهم" سيكون جيدًا.

أطر عمل مثل رد فعل / إلخ على وجه التحديد تستدعي هذه الأنواع من الأشياء في مستنداتها

التي يضعونها على أنها مجرد اقتراح ثم ينتقلون لإرشادك حول كيفية القفز عبر الأطواق لتهيئة Babel 6 لاستخدامه. أفضل إلقاء اللوم على الأطر للاعتماد على التقنيات النحوية التي هي فقط في مسودة المواصفات. شخصيا ، نحن في Dojo ، أحرقنا Object.observe وأنا متحفظ مرة أخرى لمحاولة الاعتماد على التقنيات قبل أن يصلوا إلى المرحلة 3 في Dojo.

المسار المحدد هو أكثر بكثير من مجرد دعم تحويل بناء الجملة على الانبعاث لـ TypeScript. هناك كل نوع الاستدلال الذي يجب أن يتبعه. لقد ألقيت نظرة على مسودة المواصفات لأفهمها ، ولكن إلى أين تذهب الرموز؟ أين تذهب الخصائص غير المعدودة؟ أفترض في كلتا الحالتين أنهم يختفون في الأثير ، ولكن سيكون هناك كل أنواع تقسيم ودمج الأنواع التي ستحتاج إلى الاستمرار في الخلفية لهذا ، لذا يمكنني أن أفهم تمامًا أن فريق TypeScript يقول "حسنًا ، دعنا نتوقف على هذا الأمر حتى بدأ TC39 حقًا في ركل الإطارات على هذا ".

بشكل عام ، أعتقد أن TS مميزة جدًا اليوم. كان هناك وقت (حوالي 1.4 ~ 1.5 على ما أعتقد) شعرت فيه بالإحباط بسبب عدم وجود بعض ميزات ES2015 ، ولكن اعتبارًا من اليوم ، تمكنت TS من اللحاق بالمعيار بشكل جيد.

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

ولكن في نفس الوقت علينا أن نعترف بأن فريق TS يأخذ التوافق بجدية أكبر بكثير من Babel. إنهم لا يريدون تغيير دلالات الكود الخاص بك بين الإصدارات ، أو ببساطة إزالة ميزة ، وهو ما يفعله Babel. بالنسبة لبعض المشاريع (المؤسسة؟) هذا مهم.

يمكنني أيضًا أن أفهم أن MS لا ترغب في استثمار الكثير من الموارد في الميزات التي قد يتم إسقاطها ، يتبادر إلى الذهن الفشل الذريع Object.observe . في الواقع ، قالوا إنهم سيفكرون في العلاقات العامة في هذا على سبيل المثال: wink :.

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

مجرد ملاحظة سريعة هنا. لقد كنا بطيئين نوعًا ما في اعتماد ميزات ES المقترحة للمرحلة 0-1 ويرجع ذلك أساسًا إلى مخاوف التوافق مع الإصدارات السابقة. نحن نتابع المناقشات في اجتماعات TC39 عن كثب ، ونشارك مباشرة في الاجتماعات أو في الاستعدادات للمقترح قبل الاجتماعات ؛ وعندما نضع ميزة ما ، نود أن نعرف ما يعنيه ذلك للمستخدمين الذين يعتمدون عليها.
إذا نظرت إلى وثائق عملية TC39 ، يمكن أن تتوقع ميزة في المرحلة 1 تغييرات قبول "رئيسية" بعد ذلك. كان هذا هو الحال بالنسبة للفئات والوحدات والمكررات وجميع ميزات ES6 غير التافهة تقريبًا ..
ارتداء قبعة المستخدم الخاصة بي ، فإن كسر التغييرات في بناء الجملة يمكن أن يكون ميكانيكيًا للاستجابة لها ، في حين أن كسر التغييرات في الدلالات قد يكون من الصعب للغاية اكتشافه وإصلاحه ؛ قد يكون هذا تكلفة ضخمة على الفرق التي تستخدم أيًا من هذه الميزات ، و / أو مانعًا لاعتماد إصدارات أحدث من الأدوات. ونود تقليل ذلك قدر الإمكان. هذا هو سبب اعتمادنا سياسة لتمكين الميزات افتراضيًا عندما تصل إلى المرحلة 3 ، وتحت علامة تجريبية قبل ذلك (مثل أدوات التزيين).
بعد قولي هذا ، تنتشر خاصية الكائن والباقي في خريطة الطريق الخاصة بنا ، ونخطط لمعالجتها في إصدار مستقبلي.

ربما يجدر التفكير في الإضافة إلى قدرة المترجم على حقن بعض ملحقات الطرف الثالث ، كما هو الحال في بابل؟

فكرة أخرى: ماذا عن دعم المعالجة المسبقة للمصادر المطبوعة (مع بابل)؟

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

kitsonk - موضوع أوسع

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

لقد انطلقوا وقاموا بالتنفيذ الخاص بهم عكس NET. لا يستخدمون أي شيء من المجتمع ، وهذا خطأهم.

وضع بعض التوجيهات والبنية حول ما هم على استعداد لتنفيذه ومتى

يقومون بتنفيذ الديكور (المرحلة 1) ، خصائص الفصل (المرحلة 1) ، إلخ.

لا أعتقد أن عبارة "لأن إطار عمل X يذكره في مستنداتهم" سيكون جيدًا.

انت تمزح صحيح؟ رد فعل هو إطار العمل الأكثر شيوعًا ولديه توقعات للبقاء على هذا النحو لبعض الوقت الآن. عدم دعم ذلك سوف / قد أضر حقًا بالتبني.

أعتقد أن TypeScript لديه الكثير من اللحاق ببرنامج Babel ولديه الكثير من التحديات مثل: من الصعب حقًا البدء في استخدامه مع تطبيق موجود ، فإن الترحيل من babel إلى الكتابة المطبوعة لـ A2 يعد بمثابة NIGHTMARE! ، نقص في المكونات الإضافية المنفصلة يجعل العمل مع Node صعبًا للغاية.

انت تمزح صحيح؟ رد فعل هو إطار العمل الأكثر شيوعًا ولديه توقعات للبقاء على هذا النحو لبعض الوقت الآن. عدم دعم ذلك سوف / قد أضر حقًا بالتبني.

لدي الكثير من الاحترام لـ React ، لكنني لا أمزح. إنها ليست اللعبة الوحيدة في المدينة وهي بالتأكيد على منحنى الضجيج الكبير. منذ 6 أشهر كانت React + Flux ، والآن أصبح React + Redux هو نكهة اليوم. قبل عام ، الزاوي والبوليمر. قبل عامين كان العمود الفقري و Ember. قبل ست سنوات كانت Dojo ، MooTools ، jQuery ، gwt ، ExtJS ، إلخ ...

لا تبدأ حروب الإطار هنا: التعجب:
بناء الجملة {..., } كما هو ، بغض النظر عن أي إطار

لقد انطلقوا وقاموا بالتنفيذ الخاص بهم عكس NET. لا يستخدمون أي شيء من المجتمع ، وهذا خطأهم.

amcdnl إلى ماذا تشير بالضبط؟ لا يمكنني إلا أن أفترض أنك تشير إلى الوحدة على أنها مشكلة في مساحة الاسم ، والتي لا علاقة لها بـ .NET وهي أيضًا ليست واحدة من نقاط الضعف الرئيسية مع الوحدات النمطية في TypeScript.

+1 لإدراجها في العقدة المطبوعة js تدعمها بشكل تجريبي

اسمحوا printcript = {... typescript، object_spread} ؛ // نعم من فضلك.

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

أتساءل ما إذا كان الصلصا يغير أي شيء للعبة؟

أتفهم أن TS لا تريد تنفيذ ميزات غير مستقرة مبكرًا: موارد محدودة ، وحماية المستخدمين من التغييرات المحتملة ، وما إلى ذلك.

ولكن الآن بعد أن أصبح Salsa هو محرك VS Code الافتراضي JS ، فإن الضغط على بناء جملة JS الأحدث (على الأقل بناء الجملة ، وليس كتابة TS الكاملة) سوف يزداد. خاصة بالنظر إلى شعبية بابل.

هل ستكون لغة السالسا قادرة على قبول بناء جملة أوسع بشكل أسرع من TS؟

+1

هل سيكون هذا في 2.1 بدلاً من 2.0؟ :بكاء:
https://github.com/Microsoft/TypeScript/wiki/Roadmap#21

بالنظر إلى مدى ضخامة 2.0 بالفعل ، فأنا لست مندهشًا جدًا.

نحاول الفصل بين الإصدارات من 6 إلى 8 أسابيع ؛ بحيث يحد ذلك مما يمكن أن يدخل. نحن نقوم ببعض إعادة هيكلة الباعث في الوقت الحالي ، ويجب أن نكون قادرين على إضافة هذه الميزة بمجرد اكتمالها.

فهل هذا ثابت؟

... وظيفة مساعد قائمة بذاتها لسمات الانتشار
https://github.com/Microsoft/TypeScript/releases/tag/v1.8.10

نظرًا لأنني ما زلت أتلقى "توقع نمط إعادة هيكلة الممتلكات"

ليس تماما. هذا الإصلاح مخصص لسمات انتشار JSX:

const props = { foo: "bar" };
return <SomeComponent {...props} />;

التي نجحت بالفعل ، قبل أن يزيل React v15 وظيفة داخلية غير موثقة كان يعتمد عليها مترجم JSX من TypeScript. عفوا 😃

يعد انتشار الكائن اقتراحًا مختلفًا ، مع بنية متشابهة (ربما تم اقتراحه من قبل مهندسي Facebook واستلهامًا من مكافئ JSX ، على الرغم من أنني لا أعرف على وجه اليقين).

بما أن {...props} لا يعمل بعد ، فكيف يمكنك استخدام TypeScript لتحقيق شيء مشابه لذلك؟

لذلك بما أن {... props} لا يعمل بعد ، فكيف يمكنك استخدام TypeScript لتحقيق شيء مشابه لذلك

استخدم xtend : https://www.npmjs.com/package/xtend يحتوي على كتابات رائعة: https://github.com/typed-typings/npm-xtend (بواسطة blakeembrey : rose :) شكرًا لنوع التقاطع

أو لا تستخدم أي مكتبة على الإطلاق!

const newProps = Object.assign({} /*new object*/, props /* add all attributes of props */, {
   // add additional props
  bar: "baz"
});

إنها مطولة بعض الشيء ، لكنها _ موطنها الأصلي لـ ES2015 ، لذلك إذا كنت قد حصلت بالفعل على تعبئة متعددة لذلك ، فأنت قوي.

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

يغير اللعبة تمامًا للتعامل مع الأشياء بشكل ثابت.

كبديل ، هل هناك أي شيء مخطط يسمح لك بتوصيل تحويل مخصص إلى TSC كما يمكنك القيام به في بابل؟ ربما استنادًا إلى نفس واجهة برمجة التطبيقات ، سيكون ذلك رائعًا ويحل مشكلات مثل هذه.

كبديل ، هناك أي شيء مخطط يسمح لك بتوصيل تحويل مخصص إلى TSC كما يمكنك القيام به في بابل

Niondir نعم. ابحث فقط عن علامات [Transforms] . هذه مطلوبة للحصول على نقل غير متزامن / انتظار / مولد مناسب في مترجم TypeScript: rose:

بعد بحث بسيط ، هل تشير إلى هذا؟ https://github.com/Microsoft/TypeScript/wiki/Using-the-Compiler-API

يبدو رائعًا ، فأنا لا أجد أي شيء متعلق بـ Object Spread لواجهة برمجة التطبيقات تلك. ربما سيكون مشروعًا صغيرًا لطيفًا لحل هذه المشكلة استنادًا إلى Compiler API :)

Niondir آسف لعدم تقديم مساعدة أفضل في رسالتي الأصلية. أنا أتحدث عن https://github.com/Microsoft/TypeScript/issues/5595 <والذي سيسمح بالتوصيل emit لبناء جملة ESNext. تعد TypeScript أكثر انخراطًا من Babel لأنها تحتاج إلى فهم نظام من النوع _semantic_ لشفرتك ، لذا ربما يحتاج عمل انتشار الكائن إلى أن يأتي من فريق TypeScript.

وجود باعث قائم على البرنامج المساعد سيجعل هذا أسهل. نعم ، يمكنك استخدام API للمجمع (أو ربما fork المترجم في البداية حتى يصبح نظام البرنامج المساعد عامًا + لمنطق الدلالي / الماسح الضوئي)

قد يكون هذا سؤالاً يتعلق بمشكلة أخرى ، لكن ألن يكون من الممكن إضافة خيار "allow-التجريبية" وجعل TypeScript يسمح بأشياء مستقبلية؟ على سبيل المثال ، اسمح عامل الانتشار والإخراج كما هو. يمكنني التعامل مع ذلك مع بابل بعد ذلك.

هذه ميزة لا غنى عنها لبعض المشاريع التي أعمل عليها ولا يمكنني الترحيل بدون أشياء أساسية مثل هذه. سيكون رائعا لو استطعت.

لست متأكدًا من كيفية شحنه في النهاية ، لكنني بدأت العمل على الراحة / الانتشار في الكائنات الحرفية والتدمير . في الوقت الحالي ، تتمثل الخطة في استخدام polyfill __assign الخاص بنا للإصدار.

هذا أفضل خبر سمعته في الأشهر الثلاثة الماضية!

لسوء الحظ ، اتضح أن جعل هذا يعمل مع الأدوية الجنيسة هو الكثير من العمل. عليك أن تدعم الكود بشكل صحيح مثل هذا:

function addId<T>(t: T): {...T, id: number} {
    return { ...t, id: 1 };
}

كما ترى ، يُرجع addId نوعًا جديدًا ، وهو نوع كائن يتضمن عامل تشغيل.

بعد بعض المناقشة ، قررنا التأجيل حتى 2.1 وننظر إلى هذا مرة أخرى. نحن بحاجة إلى التركيز على إنجاز ميزات 2.0 الآن.

سامح جهلي ... لكن يبدو الأمر وكأنه addId في هذه الحالة أن تكون قادرًا على إرجاع T & { id: number } ؟ أم أن هناك بعض أنواع النقابات الغريبة التي تمنع ذلك من أن يكون الحل الأمثل؟

أعتقد أنه يعني أنه في الواقع يجب التحقق من T ، حيث يمكنك تمرير أي شيء إلى T.

addId<boolean>(true);
addId<number>(5);

يتجاهل Babel بصمت مثل هذه العبارات let a = { ...true } لكني أعتقد أنها لا ينبغي أن تكون صالحة

إنه ليس T & { id: number } لأنه إذا كان T يحتوي على خاصية id ، فسيتم تجاوزه.

من ناحية أخرى ، فإن التقاطع ، الناتج من النوع id سيكون تقاطع T 's id و number .

إذن ما يقوله sandersn هو أنك بحاجة إلى عامل نوع منفصل.

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

سيؤدي ذلك إلى تخفيف الكثير من المخاوف بشأن الميزة المفقودة ولن يؤدي إلى سلوك غير مرغوب فيه نظرًا لأن الأشخاص يستخدمون بالفعل Object.assign بدلاً من ذلك.

لقد فوجئت بشدة أن هذا لم يكن مدعومًا.

بمجرد أن نحصل على هذا ، يكون الأمر أكثر مرحًا. ستعمل بشكل رائع مع التفاعل!

سأكون سعيدا حتى لو لم يتم كتابتها

@ 2426021684 قد يبدو معقولاً ولكن ضع في اعتبارك الآثار المترتبة. إذا لم يتم كتابته ، أي أنه كتب كـ any ، فإن أي استخدامات للصياغة ستنتقل any إلى أوراق التعبيرات.

aluanhaddad سيكون هو نفسه Object.assign وهو الحل الذي يجب على الجميع استخدامه لأنه ليس لديهم خيار (انظر منشور JabX أعلاه)

يرجى النظر في تنفيذ اقتراحJabX في المدى القريب. هذا الاقتراح هو المرحلة الثالثة في الكل ما عدا الاسم ، وسيكون جزءًا من المعيار ، وله دلالات واضحة وبسيطة للغاية. سيكون وضع الدعم النحوي في مكانه لفروق الملكية + الكتابة الساذجة لـ Object.assign بمثابة فجوة مؤقتة مفيدة للغاية أثناء انتظار التنفيذ "الصحيح". لا تدع الكمال يكون عدو الخير.

تعتبر خصائص الراحة مهمة للغاية مع React 15.2 كما يمكن رؤيته هنا https://facebook.github.io/react/warnings/unknown-prop.html

const divProps = Object.assign({}, props)
delete divProps.layout

قبيح جدًا ، خاصةً إذا كانت كمية الدعائم على أحد المكونات أعلى

بالنسبة لأولئك الذين لا يستطيعون الانتظار بعد الآن ، يوجد حل بديل:

function steal(result: any, data: any): any {
    for (var key in data) {
        if (value.hasOwnProperty(key)) {
            result[key] = data[key];
        }
    }
    return result;
}

export class SameAs<a> {
    constructor(public result: a) { }
    public and<b>(value: b): SameAs<a & b> {
        return new SameAs<a & b>(steal(this.result, value));
    }
}
export function sameAs<a>(value: a): SameAs<a> {
    return new SameAs(steal({}, value));
}

// example of use:

const mixture = sameAs(one).and(anotherOne).and(yetAnotherOne).result; // <-- ta-da!

تجاهل هذا المنشور ، انظر أدناه للحصول على تطبيق أفضل

هذا ما توصلت إليه بخصوص عملية تدمير مشفر فقيرة (مطبوعة):

declare interface ObjectConstructor {
  destruct<T extends Object>(data: T, props: any): T;
  destruct<T extends Object>(data: T, ...propNames: string[]): T;
}

function destruct<T extends Object>(data: T, ...removals: string[]) {
  const rest = <T>{};

  const keys = removals.length === 1 && typeof removals[0] === 'object' ?
    Object.getOwnPropertyNames(removals[0]) :
    <string[]>removals;

  Object
    .getOwnPropertyNames(data)
    .filter(x => keys.indexOf(x) < 0)
    .forEach(x => {
      (<any>rest)[x] = (<any>data)[x];
    });

  return rest;
}

Object.destruct = destruct;

// Usage example:

const srcObj = { A: 'a', B: 'b', C: 'c' };
// destruct using an object template
const onlyC = Object.destruct(srcObj, { A: null, B: null });
// destruct using property names
const onlyA = Object.destruct(srcObj, 'B', 'C');

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

تحديث (تجاهل هذا أيضًا ، انظر أدناه للأفضل)

لقد أعدت صياغة هذا (بعد العبث به في بيئة العالم الحقيقي) وتوصلت إلى بعض أسهل بكثير للعمل مع الوظائف.

function deconstruct<TResult, TData>(
  result: TResult,
  data: TData,
  onHit: (result: TResult, data: TData, x: string) => void,
  onMiss: (result: TResult, data: TData, x: string) => void,
  propNames: string[]
  ) {

  Object
    .getOwnPropertyNames(data)
    .forEach(x => {
      if (propNames.indexOf(x) < 0) {
        if (onMiss != null) {
          onMiss(result, data, x);
        }
      }
      else {
        if (onHit != null) {
          onHit(result, data, x);
        }
      }
    });

  return result;
}

// shallow clone data and create a destructuring array of objects
// i.e., const [ myProps, rest] = destruct(obj, 'propA', 'propB');
function destruct<T>(data: T, ...propNames: string[]) {
  return deconstruct(
    [ <T>{}, <T>{} ],
    data,
    (r, d, x) => (<any>r[0])[x] = (<any>d)[x],
    (r, d, x) => (<any>r[1])[x] = (<any>d)[x],
    propNames
  );
}

// shallow clone data and create a destructuring array of properties
// i.e., const [ propA, propB, rest] = destructProps(obj, 'propA', 'propB');
function destructProps(data: any, ...propNames: string[]) {
  return deconstruct(
    [ <any>{} ],
    data,
    (r, d, x) => r.splice(r.length - 1, 0, d[x]),
    (r, d, x) => r[r.length - 1][x] = d[x],
    propNames
  );
}

// shallow clone data and remove provided props
// i.e., const excluded = omit(obj, 'excludeA', 'excludeB');
function omit<T>(data: T, ...propNames: string[]) {
  return deconstruct(
    <T>{},
    data,
    null,
    (r, d, x) => (<any>r)[x] = (<any>d)[x],
    propNames
  );
}

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

const [ props, restProps ] = destruct(omit(this.props, 'key', 'ref'), 'id', 'text');

في هذه الحالة ، تتم كتابة props تمامًا مثل this.props ، ولكنها لا تحتوي على أي من الدعائم المخصصة للنقل إلى أسفل السطر (والتي تعيش الآن في restProps )

IMO ، لا يتم اكتساب الكثير من خلال نشر الحلول غير الآمنة لهذه المشكلة.

موافق ، أنا أعمل على إصدار أكثر أمانًا في الوقت الحالي.

طعنة أخرى في هذا:

امتداد الكائن الرئيسي:

declare interface ObjectConstructor {
    rest<TData, TProps>(data: TData, propsCreator: (x: TData) => TProps, ...omits: string[]): { rest: TData, props: TProps };
}

function rest<TData, TProps>(data: TData, propsCreator: (x: TData) => TProps, ...omits: string[]) {
  const rest = <TData>{};
  const props = <TProps>propsCreator.apply(this, [ data ]);

  Object
    .getOwnPropertyNames(data)
    .filter(x => props.hasOwnProperty(x) === false && omits.indexOf(x) < 0)
    .forEach(x => {
      (<any>rest)[x] = (<any>data)[x];
    });

  return {
    rest,
    props,
  };
}

Object.rest = rest;

ملحق خاص بـ React:

declare module React {
  interface Component<P, S> {
    restProps<T>(propsCreator: (x: P) => T, ...omits: string[]): { rest: P, props: T };
  }
}

function restProps<P, S, T>(propsCreator: (x: P) => T, ...omits: string[]) {
  return Object.rest((<React.Component<P, S>>this).props, propsCreator, ...omits.concat('key', 'ref'));
}

React.Component.prototype.restProps = restProps;

بعض استخدام العينة:

const src = { A: 'a', B: 'b', C: 'c' };
const { rest, props } = Object.rest(src, x => {
    const props = { A, C } = x;
  return { A, C };
});

وعينة من استخدام امتداد رد الفعل:

const { rest, props } = this.restProps(x => {
  const { header, footer } = x;
  return { header, footer };
});

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

هنا كمان للعب به.

أعتقد أن إرجاع مصفوفة قد يكون أكثر منطقية ، حيث يمكنك إعادة تسمية المخرجات حسب الحاجة.

خدش ذلك ، فهذا من شأنه أن يمنع الحصول على الكتابة الصحيحة للدعائم.

نظرًا لأن معظم الأشخاص هنا يريدون استخدام هذا مع التفاعل ، فلماذا لا يتم تطبيق هذا فقط لملفات * .tsx حتى يصل إلى المرحلة 3؟

يمكن كتابة مخفضات Redux كملفات * .tsx أيضًا ، فقطالهدف يجب تحويل مثيلات التلبيس إلى كائن كنوع

هذا مفيد جدًا ليس فقط للتفاعل ، ولكن في مخفضات إعادة الإرسال على سبيل المثال.

أعتقد أن العلامات والمعلمات المفقودة في هذا الأمر قديمة بعض الشيء. لأن هذا ملتزم ويجري العمل عليه (# 10727) لـ TypeScript 2.1. لذلك لا داعي لمناقشة قيمة ذلك بعد الآن.

pingmhegazy

تحديث العلامات. يجب أن أوضح أن سبب عدم تنفيذ ذلك حتى الآن ليس هو القيمة ، ولكن بالأحرى تعقيد تنفيذ نظام النوع. التحول الذاتي تافه نوعًا ما ، على سبيل المثال {...x} إلى Object.assign({}, x) . القضية هي كيف يتم اختبار هذه الأنواع وكيف تتصرف. على سبيل المثال بالنسبة لمعامل النوع العام T هو {...T} قابل للتخصيص لـ T ، ماذا عن {x: number, ...T} ، ماذا عن T لديه طرق ، إلخ .. https://github.com/Microsoft/TypeScript/issues/10727 يوفر شرحًا أكثر عمقًا لتغييرات نظام النوع المطلوبة.

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

إن وضع الدعم النحوي لامتداد الخاصية + الكتابة الساذجة لـ Object.assign سيكون بمثابة فجوة مؤقتة مفيدة للغاية أثناء انتظار التنفيذ "الصحيح". لا تدع الكمال يكون عدو الخير.

يبدو أن الاقتراح قد وصل إلى المرحلة الثالثة: https://github.com/tc39/proposals

ddaghan لن يعمل المثال الخاص بك مع tsx

أي إطار زمني لهذه الميزة؟

@ SpyMaster356 لقد كنت sandersn كان يركل هذا الأمر (على الأقل) في الأسابيع القليلة الماضية. 🙌

يمكنك المتابعة هنا (https://github.com/Microsoft/TypeScript/pull/12028) وهنا (https://github.com/Microsoft/TypeScript/pull/11150)

يجب على شخص ما تحديث خارطة الطريق

يبدو أن استخدام هذه الميزة يسمح بإسناد الدعائم غير المعروفة:

interface State {
  a: string;
  b: number;
}

let state: State = { a: "a", b: 0 };

state = {...state, x: "x"}; // No error

كنت أتوقع خطأ مفاده أن x ليس خاصية معروفة State . أليست هذه هي الطريقة التي تعمل بها الميزة؟

على سبيل المثال ، كان الحل الحالي قبل هذا العلاقات العامة هو:

state = update(state, { x: "x" }); // Error: Property 'x' is missing in type 'State'.

function update<S extends C, C>(state: S, changes: C): S {
  return Object.assign({}, state, changes);
}

هل من الممكن تحقيق ذلك من خلال انتشار / راحة الكائن؟

يتصرف Object Rest and Spread ، وفقًا لاقتراح ES ، بشكل مشابه لـ Object.assign . آخر ذكر للممتلكات "يفوز". لم يتم الإبلاغ عن أية أخطاء. في المثال الذي لديك ، نوع {...state, x:"X"} هو { a: string, b:number, x:string } ؛ وهذا النوع قابل للتخصيص إلى State وبالتالي فإن المهمة تعمل. هذا مماثل لما نقول إن let state: State = { a: "a", b:0, x: "X" }; سيسمح به أيضًا.

ولكن هذا ما أنا محتار بشأنه: يعطي let state: State = { a: "a", b:0, x: "X" } الخطأ Object literal may only specify known properties, and 'x' does not exist in type 'State' وهو ما أريده ... لماذا هو واجب صالح عند الخروج من كائن حرفي يحتوي على انتشار؟

آسف .. الكائنات الحرفية هي حالة خاصة. كان المثال الخاص بي خاطئا. هنا أفضل مثال:

let obj = { a: "a", b:0, x: "X" };
let state: State = obj; // OK

القضية هنا إذا كانت ذاتية بالأحرى. عندما يرى المترجم let state:State = { a: "a", b:0, x: "X" } ، فإن الاحتمالات هي x خطأ إملائي ، إما ملكية قديمة تم إيقافها بعد إعادة البناء ، أو نوع خاص بخاصية اختيارية ، وهذا هو سبب الإبلاغ عنها على أنها خاصية خطأ.

ومع ذلك ، إذا قمت بنشر كائن ، دعنا نقول let myConfig : State= { a: 1, ...myOtherBigConfigBag} ، إذا كان myOtherBigConfigBag يحتوي على بعض الخصائص التي لا تهتم بها ، فأنت تحتاج فقط a و b ، سيجبرك الخطأ هنا على إبقاء هاتين الواجهتين متزامنتين ، أو إرسالهما لإزالة هذه الأخطاء.

هكذا قال. يجب أن نعيد النظر في هذا القرار. قدم https://github.com/Microsoft/TypeScript/issues/12717 لتتبع ذلك.

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

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

مرحبًا يا شباب ، مبروك على الإصدار الرائع! حان الوقت للراحة المستحقة ... التحدث عما لدي مشكلة مع العامل الباقي :)

باستخدام React ، لديك عنصرًا تلميحًا مثل:

export interface MyLinkProps extends React.HTMLAttributes {
    myUrl: string
}

class MyLink{

    render(){
      const {myUrl, ...attrs } = this.props;
     return <a href={calculate(myUrl)} ...attrs>Click here</a>;
   }
}

تكمن المشكلة في أنك عندما تحوم بالماوس فوق attrs تحصل على قائمة بجميع الخصائص (مئات) بدلاً من React.HtmlAttributes.

أعلم أن الكتابة المطبوعة تتم كتابتها هيكليًا وكل ذلك ، ولكن هل من الممكن تعيين نوع واضح للمتغير الباقي؟

بعض البدائل:

    const {myUrl, ...attrs as React.HtmlAttributes } = this.props; //Is not really a casting

    const {myUrl, ...attrs : React.HtmlAttributes } = this.props; //conflicts with ES6?

    const attrs : React.HTMLAttributes; 
    const { myUrl, ...attrs } = this.props;  //re-declare the variable

bondz حسنًا ، هذا ليس صحيحًا في 100٪ من الاستخدامات في مشروعي. :) ولكن في مشروع آخر قد يكون الأمر مزعجًا للغاية. في حالتي ، أستخدم Redux و React وأستخدم بشكل مكثف الحالة الثابتة ، مما يعني تحديث أو إنشاء كائنات الحالة ، يجب أن أنسخ جميع الدعائم على كائن جديد حرفي ... في جميع الحالات ، أريد أمانًا من النوع بنسبة 100٪. أحاول نسخ البيانات الصحيحة على واجهة الحالة المستهدفة. أستخدم حاليًا وظائف لضمان هذه الأمان ، لكنني أفضل استخدام انتشار الكائن لأنه أكثر نظافة (سهل القراءة ، معبر ، بناء جملة قياسي.) ولكن في مشروع شخص آخر ، قد يرغبون في سلوك مختلف لأنهم يستخدمون الكثير من الكائنات غير المكتوبة أو المفكوكة الهياكل ، لذلك أرى كيف أنها ذاتية تمامًا. أعتقد أن اقتراح # 12717 هو حل وسط جيد (وأكثر اتساقًا مع أمان النوع الحرفي الموجود.)

https://github.com/Microsoft/TypeScript/issues/2103#issuecomment -145688774
نريد انتظار وصول الاقتراح إلى المرحلة 3 قبل معالجة هذا الأمر.

يبدو أنها بالفعل 3 ، أي خطة لدعم هذا؟

راجع للشغل ، نحن نستخدم VSCode بشكل أساسي لتطوير ES ، وليس TS بعد :)

evisong تم شحن هذه الميزة وهي متوفرة بالفعل في أحدث إصدار من vsCode. قم بتحديث vsCode الخاص بك إلى الإصدار 1.8

هل كانت هذه الصفحة مفيدة؟
0 / 5 - 0 التقييمات