Open marktani opened 6 years ago
Comment by zth Thursday Jan 12, 2017 at 19:23 GMT
I'm building an app where you'll regularly answer forms. My use case will be calculating averages and scores for those forms on the fly for certain periods of time, without needing to fetch all the data on the client and calculate it there.
Comment by marktani Monday Feb 06, 2017 at 22:47 GMT
compute the millisecond representation of a
DateTime
field
This is useful for the Algolia integration as Algolia expects that format for times. But better handled by #91.
Comment by wallslide Monday Mar 06, 2017 at 13:57 GMT
I'd also find this functionality extremely useful. I can see needing to have parts of dates for different queries. The month, the day, day of week. It would be helpful if I could just add a new computed property when I need it rather than having to update my schema and go back and calculate the value for all nodes.
Comment by tonyxiao Thursday Mar 09, 2017 at 18:02 GMT
This would be HUGE. Without it I find it to be hugely limiting to be using a hosted GraphQL service rather than just write my own GraphQL server. Effectively this is like being able to create my own resolver function right?
Here's my use case while trying to create a waitlist app. I want to create the following type
type Reservation {
id: String!
email: String!
peopleAhead: Int!
peopleBehind: Int!
referralCode: String!
}
However peopleAhead
and peopleBehind
depends on how many ppl are there on the waitlist in total, which is not a stored field but rather computed field
Comment by mattfysh Saturday Jul 29, 2017 at 13:50 GMT
Super useful. Also wondering whether you'd be applying a caching layer to the computed result? One that's invalidated in certain circumstances, e.g:
1 - function to compute value changes 2 - underlying source data changes
At this stage, a workaround might be to store the result statically against the object, and updating via server-side subscription. Will also need a dummy value that can be updated on the object which triggers a refresh of the computed value (and an external tool which batches up this process for all objects)
Comment by kbrandwijk Saturday Jul 29, 2017 at 13:57 GMT
A lot of these use cases could actually be implemented using RP hooks, if you can calculate the values at the moment you're saving/updating a node. The other usecases are clearly about querying, where the values cannot be calculated in advance. For these specific use cases, calculated fields would be a great option.
Comment by mattfysh Sunday Jul 30, 2017 at 03:44 GMT
The use case I'm looking for is updating an average score e.g. on a Product based on all of its Reviews
Comment by vincenzo Thursday Nov 23, 2017 at 10:46 GMT
@tristancaron Was wondering that myself, but I suspect the only workaround at the moment is to implement your customer query using a resolver function. This, effectively, would be the logic you'd have implemented for the computed field. However, in this case, you'll have to make two requests, rather than a single one (which kind of defeats one of the main "pros" of GraphQL).
@marktani @kbrandwijk Any other way to work around this using a single request?
The thing I am trying to do is have a resolver function which wraps our external places API and I can use that resolver as a field in my other models. Don't know if it fits the profile here.
While you can write your own field resolver functions, the challenge is the necessary data for a given resolver may not be provided as part of the query itself.
Using the canonical User
and Post
example, say you wanted a resolver for postCount
on User
. The resolver for postCount
would need to know the user's id
to perform the aggregation. You could imagine a query like:
{
users {
id
postCount
}
}
In this case the resolver for postCount
would know the user's id
and could provide the answer. However, if the query looked like:
{
users {
username
postCount
}
}
The resolver wouldn't have the necessary id
to do the lookup. It's nice that prisma loads the minimal set of data from the db at the time of the query, but in this case it severely limits the flexibility of the framework.
It seems like one way to guarantee the id
s are always loaded, is to drop the info
parameter from the users
resolver, which would then load the entire record from the db. For example:
users(parent, args, ctx) {
return ctx.db.query.users();
}
instead of:
users(parent, args, ctx, info) {
return ctx.db.query.users({}, info);
}
This is what I did (I'm using the mysql backend):
Seems to be working...
I'm trying to implement a function that applies custom linear weights to a set of stats and return the total computed value for each row.
Typically one would send the weights to the server in the request, i.e.:
# Linear weight to apply to each stat. Any field on Player can have a weight.
type Weights {
stat1: Int,
stat2: Int,
...
statN: Int
}
# A 'Player' has stats.
type Player {
stat1: Int,
stat2: Int,
...
statN: Int,
#This field is the goal of the exercise:
#Its value is given by: `SUM((stat1 * weight1), ... (statN * weightN))`
scrore: Int
}
type Query {
getScores(weights: Weights, skip: Int, take: Int, orderBy: score_Desc): [Player!]!
}
This would be trivial in SQL:
SELECT stat1, stat1 * :weight1, stat2, stat2 * :weight2, ... statN, statN * :weightN
FROM PLAYERS
ORDER BY stat1 * :weight1 + stat2 * :weight2 + ... statN * :weightN DESC
LIMIT 10
I can eschew Prisma for this task and add a custom query + resolver in my application layer graphql server, but it would no longer conform to the API exposed by Prisma. Things like pagination and cursors would have to either be manually implemented or refactored into another paging mechanism. (i.e. the skip
+ take
params above).
Ideally a lambda that gets evaluated for each record at data retrieval time would be ideal. Obviously I do not know what is needed to make that happen, but I figured explaining my use case would be useful to the discussion since it seems pretty representative of the issue.
BTW I love Prisma. Keep up the great work!
Issue by schickling Thursday Dec 22, 2016 at 14:38 GMT Originally opened as https://github.com/graphcool/prisma/issues/56
Computed fields allow you to extend a model's schema by executing functions to calculate the value of the field for every request.