3

我有一个用户实体和一个爱好实体,它们的模型都在 Loopback 中定义,我在 API 资源管理器中看到它们。

我有一个表 UserHobbie,它将 User 和 Hobbie 以 ManyToMany 关系链接起来。我正在尝试声明一个环回hasManyThrough关系,例如

User.hasMany(Hobbie, {through: UserHobbie});

但我似乎做得不好,因为它没有出现在 explorer 中。我在/server/server.js引导部分之后立即声明了它,并且我尝试在/common/User.jsand中执行它/common/Hobbie.js(但在其中任何一个中,另一个模型不可见)。

是否有适当的语法可以在 User.json 或 Hobbie.json 中添加它?这将是我的首选方式,因为我放入 json 定义中的任何内容都会显示在资源管理器中。

4

2 回答 2

9

为了解决您的模型 JSON 中的问题,我将在下面概述解决方案。但是,使用“hasAndBelongsToMany”关系可以更简单地解决您的问题,我也会在下面概述。

在您的 User.json 中:

  "relations": {
    "Hobbies": {
      "type": "hasMany",
      "model": "Hobbie",
      "through": "UserHobbie",
      "foreignKey": "hobbieId"
    }
  }

在您的 Hobbie.json 中:

  "relations": {
    "Users": {
      "type": "hasMany",
      "model": "User",
      "through": "UserHobbie",
      "foreignKey": "userId"
    }
  }

您的 UserHobbie.json 看起来像这样(请注意,您没有在“属性”中定义 userId 或 hobbieId:

{
  "name": "UserHobbie",
  "plural": "UserHobbies",
  "base": "PersistedModel",
  "properties": {
    "id": {
      "type": "String",
      "id": true
    }
  },
  "validations": [],
  "relations": {
    "Users": {
        "type": "belongsTo",
        "model": "User",
        "foreignKey": "userId"
    },
    "Hobbies": {
        "type": "belongsTo",
        "model": "Hobbie",
        "foreignKey": "hobbieId"
    }
  },
  "acls": [],
  "methods": []
}

这种更简单的方法如下:

不要明确创建 UserHobbies 模型。Loopback 将自动为您创建一个连接模型。

在您的用户模型中:

  "relations": {
    "Hobbies": {
      "type": "hasAndBelongsToMany",
      "model": "Hobbie"
    }
  }

在你的爱好模型中:

  "relations": {
    "Users": {
      "type": "hasAndBelongsToMany",
      "model": "User"
    }
  }

如果您想在代码中执行此操作,您是正确的,有引导时序问题使这些关系不会出现在资源管理器中。我将很快添加另一个回复,向您展示如何使其工作。

于 2014-09-30T18:09:15.140 回答
3

现在,为了让您在资源管理器中显示创建关系的基于代码的原始实现,您应该执行以下操作。

首先,从您的 Loopback Projects 的 ./server/boot 目录中,将“explorer.js”移动到 ./server(其中 server.js 在项目中。

./server/server.js 的最后一部分应该看起来像这样(为简洁起见,我删除了一些注释。

boot(app, __dirname);

... // Removed for brevity

app.use(loopback.urlNotFound());

// The ultimate error handler.
app.use(loopback.errorHandler());

app.start = function() {
  // start the web server
  return app.listen(function() {
    app.emit('started');
    console.log('Web server listening at: %s', app.get('url'));
  });
};

// start the server if `$ node server.js`
if (require.main === module) {
  app.start();
}

现在编辑 .server/server.js 的最后一部分,如下所示:

boot(app, __dirname);
    // We took explorer.js out of /boot and put it in /server root next to server.js


var programmaticLoopbackSetup = require('./programmaticLoopbackSetup');
    // If the User has any special Programmatic Loopback Setup (create Model Relationships, etc.) do it first

if (programmaticLoopbackSetup !== undefined) {
    programmaticLoopbackSetup(app, finishUp);
}
else {
    finishUp();  // If you didn't want any Code based Setup
}

// Defer all the rest of the Startup Work until Explorer 
// has all the Model Info it needs from any Async or Programmatic Setup.
function finishUp() {

    require('./explorer')(app);
        // This was formerly done within "boot" above...

        ...  // removed for brevity...

    // Requests that get this far won't be handled
    // by any middleware. Convert them into a 404 error
    // that will be handled later down the chain.
    app.use(loopback.urlNotFound());

    // The ultimate error handler.
    app.use(loopback.errorHandler());

    app.start = function() {
      // start the web server
      return app.listen(function() {
        app.emit('started');
        console.log('Web server listening at: %s', app.get('url'));
      });
    };

    // start the server if `$ node server.js`
    if (require.main === module) {
      app.start();
    }
}

在 ./server/programmaticLoopbackSetup.js 添加一个新文件,使其看起来像下面这样(注意它是如何在“启动”之后和完成应用程序初始化之前调用的

module.exports = function programmaticLoopbackSetup(app, next) {
    var User = app.models.User;
    var Hobbie = app.models.Hobbie;


    // This Block Below Creates a Many to Many User / Hobbie Relationship directly 

        User.hasAndBelongsToMany(Hobbie);
        Hobbie.hasAndBelongsToMany(User);

    next();  // Callback to finish App Init...
};

您将在 Explorer 中看到用户/爱好关系(在本例中使用“hasAndBelongsToMany”)。在 programmaticLoopbackSetup.js 中执行任何基于代码的 LoopBack 模型、数据源或其他改进

于 2014-10-02T05:08:13.440 回答