-
Notifications
You must be signed in to change notification settings - Fork 1
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
Clean up operator backend proxy endpoints #23
Conversation
- prefix request builders to "operator - " - generate examples for proxy endpoints
* A list of identifiers and a new (unsigned) value for preferences | ||
*/ | ||
export interface NewUnsignedPreferences { | ||
unsignedPreferences?: { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
IMHO, the semantics and compositions of the Preferences models are confusing. If I translate this line: "new unsigned preferences object that potentially contains unsigned preferences"...
Can you describe how this class helps us, please? It will help to find an alternative.
More generally speaking, in this file, we have many entities that express the Preferences concept: Preferences, PreferenceData, NewUnsignedPreferences, IdsAndPreferences. I have the impression that we generate classes based on the JSON-Schema and so the readability of the models is impacted by how the JSON-Schema works.
Can it be simplified with less class and more semantics? I want to be constructive so here are a few examples but I may not have all the corner cases in mind.
Example 1, the simplest
interface Preferences {
version: Version;
data: {
use_browsing_for_personalization: boolean;
};
/** Has a source if the preferences is signed */
source?: Source;
/** Weak but explicit relationship to the identifiers. */
identifiers: Identifier[];
}
// That's it.
Exemple 2, more atomical approach
interface UnsignedPreferences {
version: Version;
data: {
use_browsing_for_personalization: boolean;
};
}
interface Preferences : UnsignedPreference {
source: Source;
}
interface PrebidData {
preferences: Preferences;
identifiers: Identifier[];
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks.
I get your point and I agree this model is becoming confusing.
I will rework to rename and refine some models.
However, a few comments:
- The example you commented is a mistake from me:
unsignedPreferences
shouldn't be optional, I'll fix it, thanks for the heads up. - It is complex by nature: here, we want to model an unsigned preferences object, with a list of signed identifiers. I don't have an obvious solution to even name this object. Defining an API often means defining an object per request and response which ends up being quite verbose.
- I want to avoid using optional attributes like in your suggestion 1. I think strong typing is always safer and more practical than weak typing + validation methods. (I don't want to add a method "if should be signed, then source should exist, otherwise it can be null")
- I think example 2 that you propose is actually my current approach, except that you mix inheritance and composition, whereas I only used composition. Another difference is that you used names such as
PrebidData
where I favored explicit (but sometimes pretty long) names such asIdsAndPreferences
. I'm not sure PrebidData is more explicit, WDYT?
To sum up, I'll rework these interfaces to make names more explicit and when possible, simplify it, in line with your suggestion 2.
…d missing comments
# Conflicts: # paf-mvp-frontend/src/lib/paf-lib.ts
# Conflicts: # paf-mvp-frontend/src/lib/paf-lib.ts
I've renamed Note that I haven't used inheritance but only composition, for two reasons:
I think the current state of the data model is satisfying, again, considering that it is complex by nature. WDYT? |
I think that it is more understandable. Thank you. However, it makes me thinking that using json-schema for the domain was irrelevant. The domain and particularly the models are the most valuable parts of a software because it helps us to understand the business logic. So the expressiness of those entities must be maximized with all the features of the used language. By using json-schema for models, we reduce the possibility offer by the used language and we end up with odd interfaces. json-schema is meaningful for instance for Data Transfere Objects between two services. The two services relies on the same schema. It is a way to agree on the interface of the communication. |
Honestly, I don't really understand what issues you have with the current model definition. Or better, can we take it as a separate git issue? |
I won't create an issue for now. I need to think about it first because I am not sure that it is worth doing the change for a demo. It may be a bit annoying for operator. Briefly, if I reformulate you said that you don't use inheritance because it is not easy with the json-schema. It seems pretty much like the Hammer law. And instead of having optional or state machine or inheritance, we have multiple classes for preferences like |
Make all proxy endpoints available under
/paf-proxy/