Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to add the model name in the REST response #11

Closed
lionelrudaz opened this issue Jan 26, 2016 · 12 comments
Closed

How to add the model name in the REST response #11

lionelrudaz opened this issue Jan 26, 2016 · 12 comments

Comments

@lionelrudaz
Copy link
Contributor

Hi David,

First of all, thanks for your code, it looks really interesting and I'm sure it will be heavily useful to me.

I just have a quick newbie question.

I'm building a JS app with Ember and Ember Data for my frontend. I'm using Feathers and Sequelize for my API, hence feathers-sequelize is meant for me.

Ember Data expects that the REST response contains the name of the object. For a call to GET conversations, instead of returning this:

[
{
id: 1,
title: "First conversation",
createdAt: "2016-01-26T19:01:28.466Z",
updatedAt: "2016-01-26T19:01:28.466Z"
}
]

It expects this:

{
conversations: [
{
id: 1,
title: "Test conversation - 1453476145564",
createdAt: "2016-01-22T15:22:25.650Z",
updatedAt: "2016-01-22T15:22:25.650Z"
}
]
}

Is there an easy way to achieve that on Service definition? I thought about creating a handler based on what I read there: http://feathersjs.com/docs/#toc2 But I'm not sure that's the proper way.

Let me know if you need more information. Thanks in advance.

Cheers,

Lionel

@daffl
Copy link
Member

daffl commented Jan 26, 2016

Thank you! If you are using the latest feathers-sequelize you can extend the service through Hooks, as an ES6 class or .extend and change the data in the returned Promise. Personally I'd recommend hooks but the easiest way would be something like:

var sequelize = require('feathers-sequelize');
var conversationsService = sequelize({
  Model: MyModel
}).extend({
  find: function() {
    return this._super.apply(this, arguments).then(function(data) {
      var result = {};
      result.conversations = data;
      return result;
    });
  }
});

app.use('/conversations', conversationService);

As a hook it would instead be

app.service('conversations').after({
  find: function(hook) {
     var result = {};
     result.conversations = hook.result;
     hook.result = result;
  }
});

@ekryski
Copy link
Member

ekryski commented Jan 26, 2016

Hey @lionelrudaz. Like @daffl said you can add an after hook to serialize data to the format that you want.

We are almost ready to release Feathers 2.0 so we are updating the new docs. We haven't gotten to hooks yet but the new docs live at docs.feathersjs.com but it would look something like this:

var SequelizeModel = require('./models/mymodel');
var sequelize = require('feathers-sequelize');

var formatResponse = function(hook) {
    var newFormat = hook.result;

     // manipulate your newFormat

    // re-assign your format
     hook.result = newFormat;
};

var conversationService = app.use('/conversations', sequelize({
  Model: SequelizeModel
}));

conversationService.after({
   find: formatResponse
});

@ekryski
Copy link
Member

ekryski commented Jan 26, 2016

This might be something that we want to add as a common hook. Wrapping the resource name around the data.

@lionelrudaz
Copy link
Contributor Author

Thanks for your quick answer guys.

I'm quite new to Node, so I don't know what I'm doing wrong. I adapted the code based on what I got from your answers. Here it is: /~https://github.com/lionelrudaz/wellnow-node/blob/master/app.js

The repo contains also package.json if you want to take a look.

I've got the error: "TypeError: conversationService.after is not a function" :-(

Let me know if you need more information.

@daffl
Copy link
Member

daffl commented Jan 26, 2016

You have to get the service through app.service when using hooks:

app.use('/api/v1/conversations', service({
  Model: Conversation
}));

var conversationService = app.service('/api/v1/conversations');

conversationService.after({
   all: formatResponse
});

@lionelrudaz
Copy link
Contributor Author

OK all clear.

Last question since I see you guys active :-)

How do I get the service name from the hook? I believe there should be something in hook.app.service, but I don't know where to search for the value.

Thanks again for your help.

@daffl
Copy link
Member

daffl commented Jan 26, 2016

I don't think you need that for your case especially since the service path is probably different than the property name. You could change formatResponse to take the property name it should use and return a hook function for that:

var formatResponse = function(propertyName) {
  return function(hook) {
    var result = {};
    result[propertyName] = hook.result;
    hook.result = result;
  };
}

var conversationService = service({
  Model: Conversation
});

app.use('/api/v1/conversations', service({
  Model: Conversation
}));

var conversationService = app.service('/api/v1/conversations');

conversationService.after({
   all: formatResponse('conversations')
});

app.listen(3030);

@ekryski
Copy link
Member

ekryski commented Jan 26, 2016

@daffl that was my exact idea for a generic hook 😉.

@lionelrudaz my bad, I forgot the app.service('/conversations') line.

@lionelrudaz
Copy link
Contributor Author

Thanks a lot for your time guys. It works great now.

I also added a before hook to format the payload that I receive from Ember. I updated my repo with this.

I still think there's a bit of repetition, but it works.

Have a good night.

@daffl
Copy link
Member

daffl commented Jan 27, 2016

Glad we could help! If you are interested in sharing we'd love to add a guide on how to use Feathers with Ember and ember-data to build real-time apps. I don't think anybody of the current contributors is using it but it would be great to have one in there.

@lionelrudaz
Copy link
Contributor Author

I don't know if I'm talented enough to write a guide about it, but I would be glad to help. Cheers

@daffl
Copy link
Member

daffl commented Jan 27, 2016

A demo app and some notes on how to set it up would be a huge help already 😄

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants