Giter VIP home page Giter VIP logo

Comments (6)

travist avatar travist commented on July 26, 2024

I am 100% on board with this approach and can envision an architecture that would facilitate this. I believe what we need are a few abstraction classes that would expose the "model" interface and then create classes that extend this interface. One of those classes would be the Mongoose model class, while the other would simply provide either in-memory manipulation or "virtual" restful capabilities.

Great idea and I am very supportive of your development of that feature.

Thanks for your help.

Travis.

from resourcejs.

biofractal avatar biofractal commented on July 26, 2024

I now have a working solution that I would like to run by you. Its solves my specific use-case and seems to be generally useful as a means of presenting virtual resources. I have attempted to re-use as much of the original resourcejs design features as I could to minimise the code impact and hopefully keep to the principle of least-surprise.

I have added a new pseudo-method called virtual. As with the index pseudo-method, the new virtual method is based on the intrinsic get method.

Given a concrete resource defined by a schema, one to many virtual methods can be described by passing options to the resource.virtual method and any of the other isomorphic techniques for defining a resourcejs method that is usual for the other methods - index, get etc.

The virtual method further expects a new options parameter called name to be provided. This will be used to generate the virtual-resource API end-point according to the following pattern:

/[resource-name]/virtual/[virtual-resource-name]

The shape of json data returned is determined by a before function that is also passed as an options param. This function is expected to act on the concrete resource to return a virtual-resource of arbitrary shape. Typically I would expect this to be a mongodb aggregate function although any process supported by the mongoose model can be used here.

For example, given a resource called 'product' with the following schema

{Schema} = require 'mongoose'
schema: new Schema
    name        : String
    price       : Number
    stock       : Number

I can define a couple of aggregate functions called max-price and max-stock

maxPrice = (req, res, next)->
    req.modelQuery = @model
    .aggregate()
    .group _id:null, maxPrice:$max:'$price'
    next()

maxStock = (req, res, next)->
    req.modelQuery = @model
    .aggregate()
    .group _id:null, maxStock: $max:'$stock'
    .select
    next()

I then setup the product resource via resourcejs passing in the name and the aggregate functions in the options, for example:

product.virtual({name:'max-price', before:maxPrice})
product.virtual({name:'max-stock', before:maxStock})
product.get (etc...)

I can then retrieve the virtual resources using the following urls:

/product/virtual/max-price
returns {_id:null, maxPrice:123}

/product/virtual/max-stock
returns json {_id:null, maxStock:321}

My criticism of this approach is the need to insert the hard-coded /virtual/ url segment. I would prefer not to do this but using the more concise (and less surprising) url [resource-name]/[virtual-resource-name] caused conflicts with the existing get by id method. Can you suggest how to simplify the virtual url structure without causing conflicts?

I hope that is clear. If this feels like an acceptable approach to you then I will issue a pull request so you can review the code.

Thanks

from resourcejs.

travist avatar travist commented on July 26, 2024

I like this approach. Why not define the path of the method during the registration process?

product.virtual({path: 'max', name:'max-stock', before:maxStock})

This allows you to define the path for the resource... this may seem somewhat redundant with the name parameter so is there a reason the name parameter could not be the path to the virtual resource?

from resourcejs.

biofractal avatar biofractal commented on July 26, 2024

Good idea on re-using the path options param. I will make that change.

This will still leave us with the url schema containing the hard-coded url element virtual:

[resource-name]/virtual/[path]

Are you happy with this?

from resourcejs.

biofractal avatar biofractal commented on July 26, 2024

I have made the changes as requested and we can now use the options.path param instead of the options.name. There was some confusion as I had problems with corrupt idx files and had to re-fork. The pull request is #13

from resourcejs.

biofractal avatar biofractal commented on July 26, 2024

merged

from resourcejs.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.