Knex: لا يمكن إضافة قيد المفتاح الخارجي

تم إنشاؤها على ١٧ أبريل ٢٠١٤  ·  11تعليقات  ·  مصدر: knex/knex

عند تشغيل الترحيل بالرمز أدناه ، تظهر لي رسالة "لا يمكن إضافة قيود المفتاح الخارجي". أي شخص يوجهني في الاتجاه الصحيح؟

exports.up = function(knex, Promise) {
    var defer=Promise.defer();

    knex.schema.createTable('User',function(table){

        //--Create User Table
        table.increments('UserId').primary();
        table.string('username');
        table.string('email',60);
        table.string('password',65);
        table.timestamps();

    })
    .then(function(){
        return knex.schema.createTable('Comment',function(table){

            //--Create Comment Table
            table.increments('CommentId').primary();
            table.string('Comment');

            table.integer('UserId',11).inTable('User').references('UserId');

        });     
    })
    .then(function(){

            defer.resolve();
    });


    return defer.promise;

};

exports.down = function(knex, Promise) {

};  

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

كمعلومات عن الناس في المستقبل يقرؤون هذا:
table.integer('UserId',11).unsigned().inTable('User').references('UserId');
هو الآن
table.integer('UserId',11).unsigned().references('UserId').inTable('User');

ال 11 كومينتر

بافتراض أنك ربما تستخدم mysql ، فأنت بحاجة إلى تحديد أن UserId هو .unsigned()

لا تحتاج أيضًا إلى هذا التأجيل هناك ، يمكنك فقط إرجاع knex.schema.createTable .

exports.up = function(knex, Promise) {
  return knex.schema.createTable('User',function (table){ 
      table.increments('UserId').primary();
      table.string('username');
      table.string('email',60);
      table.string('password',65);
      table.timestamps();
  })
  .then(function () {
    return knex.schema.createTable('Comment',function(table){
      table.increments('CommentId').primary();
      table.string('Comment');
      table.integer('UserId',11).unsigned().inTable('User').references('UserId');
    });     
  });
};

لن تحتاج أبدًا إلى Promise.defer .

رائع. يا رفاق الصخور !! عملت على أكمل وجه. شكرًا لك على الاستجابة السريعة والنصائح حول الرمز الأنظف :)

لك ذالك! قد تجد أنه من الأسهل تقسيم حقول البيانات / حزمة البيانات ومراجع fk إلى عمليتي ترحيل. البديل هو ما فعلته هنا ، ولكن ضع في اعتبارك أنك ستحتاج بعد ذلك إلى ضمان النظام عند التراجع أيضًا.

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

exports.up = function(knex, Promise) {
  return knex.schema.createTable('User', function(table){ 
      table.increments('UserId').primary();
      table.string('username');
      table.string('email',60);
      table.string('password',65);
      table.timestamps();
  }).createTable('Comment',function(table){
      table.increments('CommentId').primary();
      table.string('Comment');
      table.integer('UserId',11).unsigned().inTable('User').references('UserId');  
  });
};

الهجرة إلى أسفل:

exports.down = function(knex, Promise) {
  return knex.schema.dropTable('Comment').dropTable('User');
};

كمعلومات عن الناس في المستقبل يقرؤون هذا:
table.integer('UserId',11).unsigned().inTable('User').references('UserId');
هو الآن
table.integer('UserId',11).unsigned().references('UserId').inTable('User');

شكرا @ باتمان!

وجود أخطاء في notNullable (). دائمًا ما تكون مفاتيحي الخارجية فارغة:
EX 1 :) table.integer('restaurant_id').unsigned().references('id').inTable('Restaurants');
لا يتطابق المفتاح الخارجي ("restaurant_id") مع "المعرّف" في جدول "المطاعم". إنه ببساطة فارغ عندما حاولت استخدام:
EX2:) table.integer('restaurant_id').unsigned().notNullable().references('id').inTable('Restaurants');
الذي ألقى خطأ (لا يمكن إضافة قيود مفتاح خارجي).

لقد رأيت إنشاء مفتاح خارجي لهذا النموذج يعمل إذا كان هذا المفتاح الخارجي عبارة عن سلسلة ، ولكن مع عدد صحيح يشير إلى المفتاح الأساسي ('id). هل هذا بسبب أن المفتاح الأساسي ("المعرف") في الأصل ليس من النوع الصحيح وهو من النوع الافتراضي؟
table.increments('id').primary();

لقد رأيت المفاتيح الخارجية تعمل عندما تكون من نوع String ، ولكن وجود مرجع من نوع عدد صحيح للمفتاح الأساسي ('id') في جدول آخر يلقي بخطأ.

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

شكرا،

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

table.integer('restaurant_id').unsigned();
          table.integer('location_id').unsigned();
          table.foreign('restaurant_id').references('Restaurants.id');
          table.foreign('location_id').references('Locations.id');

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

يعتقد أن كلا الإطارين كانا عربات التي تجرها الدواب.

Juanpam لا حاجة لاستخدامها. العلاقات العامة هي موضع ترحيب رغم ذلك. حظ سعيد :)

elhigu لم أقصد الإساءة إلى أي شخص! أنا بالفعل أستخدم الإطار 😄. فكرت فقط أنه بالنسبة للوافد الجديد ، مثلي ، قد تكون مشكلة شائعة نظرًا لأن العلاقات هي ميزة شائعة الاستخدام في أدوات إدارة السجلات (ORMs) ومنشئي الاستعلام. أيضًا ، MySQL هو نظام RDBMS شائع.

لا يمكنني إجراء العلاقات العامة الآن ، ولكن إذا كان أي شخص مهتمًا ، فقد كنت أحاول استخدام XAMPP MySQL أثناء إنشاء المفاتيح الخارجية. تبين أنه عند استخدام طريقة .primary () ، يكون نوع الحقل الذي تم إنشاؤه هو INT (11) بدون توقيع وعندما تقوم بإنشاء الحقل المرجعي باستخدام .integer () ، يكون نوع الحقل الناتج هو INT (11) موقّع وبالتالي يفشل إنشاء المفتاح الخارجي. يعمل tgriesser fix على إحداث عجائب ، ولكن سيكون من الأفضل إذا تمكنت من العثور على إصلاحات / مشكلات شائعة مثل هذه في المستندات.

على أي حال ، عمل رائع!

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