2017-02-13 41 views
0

我有SQL Server中的預先存在的表,我想在NodeJs項目中使用這些表。SequelizeJs關聯在NodeJs中的MsSql

第一個表格是Report表格,它有{ReportId,ReportName}列。

第二個表是收藏夾表,它有{FavouriteId,ReportId,UserName}列。

您可以在下面找到模型定義。我想分配外鍵並進行依賴。最後,我想爲特定用戶選擇帶有收藏標誌的報表。

module.exports = function(sequelize, DataTypes) { 
    var Favourite = sequelize.define("IUI_Favourites", { 
      favourite_id: { 
       type: DataTypes.INTEGER, 
       primaryKey: true, 
       field: 'iui_favourite_id' 
      }, 
      report_id: { 
       type: DataTypes.INTEGER, 
       field: 'iui_report_id' 
      }, 
      username: { 
       type: DataTypes.STRING, 
       field: 'iui_username' 
      } 
     }, 
     { 
      timestamps: false, 
      freezeTableName: true 
     }); 
    return Favourite; 
}; 


module.exports = function(sequelize, DataTypes) { 
    var Report = sequelize.define("IUI_Reports", { 
     report_id: { 
      type: DataTypes.INTEGER, 
      primaryKey: true, 
      field: 'iui_report_id' 
     }, 
     report_name: { 
      type: DataTypes.STRING, 
      field: 'iui_report_name' 
     } 
    }, 
    { 
     timestamps: false, 
     freezeTableName: true 
    }); 
    return Report; 
}; 

你能幫我嗎? 在此先感謝。

回答

3

Favourite模型中,您需要創建屬性classMethodsassociate函數。

// in Favourite model 
    classMethods: { 
     associate: function(models){ 
      this.belongsTo(models.Report, { foreignKey: 'iui_report_id' }); 
     } 
    }, 
    timestamps: false, 
    freezeTableName: true 
}); 

這個定義模型Favourite可以通過iui_report_id外鍵字段指定數據庫Report

然後,在Report模型,你必須定義1:M關係:

// in Report model 
    classMethods: { 
     associate: function(models){ 
      this.hasMany(models.Favourite, { foreignKey: 'iui_report_id' }); 
     } 
    }, 
    timestamps: false, 
    freezeTableName: true 
}); 

爲了返回報告由指定的用戶收藏最多,你就必須在調用findAll()方法Report在規定的條件:

Report.findAll({ 
    include: [ 
     { 
      model: Favourite, 
      where: { 
       username: 'admin' 
      } 
     } 
    ] 
}).then((reports) => { 
    // here you get reports that are favourited by user with username 'admin' 
}); 

這將產生一個SQL查詢,該查詢將返回兩個Report和使用JOIN條件的3210個對象reports.id = favourite.report_idfavourite.username = 'admin'。我希望這是你正在尋找的。

編輯

根據該意見,你想,如果指定的報告是由任何用戶收藏最多最喜歡的標誌設置爲true。爲此,您必須將此標誌字段添加到Report型號,例如is_favourited。它可以是存儲在數據庫中的字段,也可以是自己的getter(虛擬字段未存儲在數據庫中)的virtual後綴字段。

在虛擬領域的情況下,它可能看起來像:

var Report = sequelize.define('report', { 
    ... 
    is_favourited: { 
     type: DataTypes.VIRTUAL(DataTypes.BOOLEAN), 
     get: function() { 
      return sequelize.models.Favourite.count({ 
       where: { iui_report_id: this.get('report_id') } 
      }).then((countResult) => { 
       return countResult > 0; 
      }); 
     } 
    } 
}, { 
    // additional model options e.g. classMethods etc. 
}); 

這個虛擬屬性返回true如果有任何Favourite對象與指定iui_report_id值。但是,它是異步的,所以你需要一個像report.get('is_favourited').then((result) => { console.log(result); });

.then()調用它。另一方面,如果你想存儲在數據庫中的標誌,你就必須創造新的當is_favourited字段值手動設置爲true Favourite模型實例。爲了做到這一點,您可以使用Favourite模型上的afterCreate掛鉤。

// in Favourite model 
timestamps: false, 
freezeTableName: true, 
hooks: { 
    afterCreate: function(instance, options) { 
     return sequelize.models.Report.findById(instance.get('iui_report_id').then((report) => { 
      if (company && !company.get('is_favourited')) { 
       return company.set('is_favourited', true).save().then(() => { return; }); 
      } 
    } 
} 

// in Report model 
var Report = sequelize.define('report', { 
    ... 
    is_favourited: { 
     type: DataTypes.BOOLEAN, 
     defaultValue: false 
    } 
}, { 
    // other model options... 
}); 

EDIT 2

根據你的最後評論你想創建這樣

SELECT Reps.rep_id, Reps.rep_name, CASE WHEN Favs.rep_id IS NULL THEN FALSE ELSE TRUE END is_favourited 
FROM Reps 
LEFT OUTER JOIN (SELECT rep_id FROM Favs WHERE user = 'alex') Favs ON Reps.rep_id = Favs.rep_id 

查詢此查詢將始終返回is_favourited = TRUE,因爲你ON條件的JOIN子句是Reps.rep_id = Favs.rep_id,所以即使Favs.rep_idNULL,則ON條件不會通過(因爲Reps.rep_id是主鍵,不能是NULL)。

但是,如果你真的想進行這樣的查詢,它看起來像這樣

Report.findAll({ 
    include: [ 
     { 
      model: Favourite, 
      where: { username: 'alex' }, // or any other passed value 
      attributes: [] 
     } 
    ], 
    attributes: ['report_id', 'report_name', sequelize.literal('CASE WHEN "IUI_Favourites"."report_id" IS NULL THEN FALSE ELSE TRUE END is_favourited')], 
    raw: true // because your Report model does not have is_favourited field 
}).then((rows) => { 
    // result 
}); 
+0

偉大的回答謝謝。最後一件事,我想用一個最喜歡的標誌獲得所有報告。這意味着如果一個報告受到管理員用戶的青睞,則標誌應該爲真,否則爲false。怎麼可能?當我選擇表格時,最喜歡的表格是複數形式。我怎麼能得到那個單數? –

+0

我不完全理解喜歡的旗子的部分。你的意思是說,如果特定的報告被任何用戶喜愛,它應該將收藏標誌設置爲真?如果涉及到最喜歡的表格,由於這是1:M關係,所以'Report'對象帶有許多'Favourite'對象。 – piotrbienias

+0

抱歉誤會,最喜歡的旗幟是第一個問題。多部分是第二個問題。最喜歡的旗幟是重要的一部分。是的,你是對的,如果任何用戶喜歡報告,它應該將喜歡的標誌設置爲真,否則應該是錯誤的。如果你幫忙,我將不勝感激。謝謝。 –