-
Notifications
You must be signed in to change notification settings - Fork 52
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
Do not break public interfaces, have a policy #595
Comments
With this policy, the goal should be to have an answer to this immediately: "Is this a public API or not?" |
xref: #399 |
This has been discussed with the team. @nkaretnikov will add notes from the discussion here. |
Proposed conda-store backward- and forward-compatibility policy Making changesIncompatible changes should be avoided if possible. Note that this only applies to client-facing code, such as HTTP routes or public Python APIs. For example, changes to a database table can be done without versioning if data can be migrated in a backward- and forward-compatible way. Everything in the When it's not possible to make a compatible change, client disruption needs to be minimized via versioning, see below. The main goal: clients should be able to upgrade without any changes. When downgrading, they'll only lose access to certain functionality or APIs, but it should be a pretty simple update on the client side, not a major breakage. We're mainly concerned about clients being able to use new features, so the update process needs to be transparent. In practice, the downgrade process should only matter when attempting to update, but then rolling back to an existing version. Database changesDatabase changes need to be forward- and backward-compatible to allow users to test new versions and rollback if needed. If it's not possible to make a change to a table in a compatible way, a new table should be introduced, while keeping the old one around. HTTP routesRoute handlers need to be versioned. As of writing this, we already have the New incompatible routes or incompatible changes to existing routes should be part of the new API. If a new route is added in Incompatible changes need to be declared as part of the Experimental routes have no guarantees attached to them, we can remove them at any moment. This allows us to add features without committing to support, and test it with clients in real-world scenarios. Once we determine the routes are stable and want to support them, they need to move to the versioned API, like Note: once a new API version is introduced, the rest of routes, which are compatible, need to add a new declaration, saying they are compatible with this new API. The goal is to make it clear which routes work together. So all For The above also applies to removing features, like parameters, this needs to be part of a new versioned API, as explained above. Example HTTP routesExample: versioned stable route
Explanation: this route is compatible with all We will not support routes with Example: new route added in
|
A few comments/opinions. Database
I would say I agree but also if it is possible to reconstruct the tables from scratch e.g. the packages/channels we should also also delete the data/reconstruct (guess this would still fit under backwards/forward compatible changes). I think the database out of all the components should not tolerate breaking changes. RoutesI am fine and agree with the need for experimental to promote development without locking us into a particular api too early. At the same time I want to make sure that this approach/work is not too burdensome on the developer |
Yeah, I have some thoughts as well after trying to implement role mappings using this new formula. I’ll write down my comments soon, but the main idea: I don’t like sticking to things for too long because it creates problems on the dev side. What we need is to just deprecate things for at least 1 release (so 2 weeks) and communicate things in release notes. Because we don’t use semver, we cannot rely on version numbers. So just need to communicate better, that’s the main idea. |
@dcmcand needs to comment on this. |
My 2c:
|
@nkaretnikov Thanks for putting this together. Here are my proposed changes : Noteworthy changes,
I very much welcome discussion about all of the above. I also think there is some discussion to be had about if we want to commit to supporting backwards compatibility for Python API's as well as REST API endpoints. It seems to me that conda-store is an application that is intended to be used through the public REST API and it would be reasonable to only apply the backwards compatibility policy to that. Is there a use case where we expect users to interact with conda-store as a library? If so, then it definitely belongs in here. If not, I personally think we can remove that from this policy. Conda-Store backwards compatibility policyIntroductionIn software development, it is essential to strike a balance between progress and maintaining a stable environment for existing users. This policy will provide guidance on how to the Conda-Store project will handle changes to software and services, ensuring that they do not disrupt or invalidate the experiences of current users, while still enabling innovation and forward progress. Breaking versus Non-Breaking ChangesBreaking changes in code refer to modifications or updates made to software that have the potential to disrupt the functionality of existing applications, integrations, or systems. Breaking changes involve removing existing functionality, altering existing functionality, or adding new requirements. These changes can lead to compatibility issues, causing frustration for end-users, higher maintenance costs, and even system downtime, thus undermining the trust and reputation of the software or service provider. In contrast non-Breaking changes can add functionality or reduce requirements. Previously working code will continue to work with non-breaking changes. These changes allow software to evolve and grow without impacting existing users negatively. Note: the term breaking changes within this policy only refers to REST API endpoints, Database changes and public Python APIs. As long as no breaking changes are introduced to REST API endpoints, Database, or public Python APIs, changes will not be considered breaking. To summarize: Users of Conda-Store should be able to upgrade to newer versions without worrying that this will break existing integrations. Newer features will be available for users to adopt when they need to, but all existing code should continue to work. Specific Implementation GuidanceDatabase changesDatabases are one of the most critical areas to ensure there are no breaking changes. Databases hold state for the application and breaking changes to the Database can be destructive to data and prevent rolling back to earlier versions of Conda-Store. To avoid breaking older features, discipline needs to be exercised around database migrations.
REST API EndpointsREST API endpoints need to be versioned this versioning should be done on a per endpoint basis. This will allow individual endpoints to be versioned independently of each other. Endpoint routes without an explicit version will be assumed to use the latest version. For example: Non-breaking changes do not require a new version of an endpoint. Adding a parameter to the return value of an endpoint or making a previously mandatory input optional can be done without a new endpoint version. However, removing a parameter from the return value, altering the meaning of a value, or making a formerly optional parameter mandatory are breaking changes and would require a new endpoint version. It is not necessary to backport nonbreaking changes to previous versions of endpoints. Experimental changesConda-Store will expose experimental features within the For example, if a new version of the This allows Conda-Store contributers to test new changes and get community feedback without commiting to supporting a new version of an API endpoint. Note: using the Experimental routes have no guarantees attached to them, they can removed or changed at any time without warning. This allows testing features with users in real-world scenarios without needing to commit to support that feature as is. Once we determine the routes are stable and want to support them, they will be moved into the existing latest version of the API endpoint for nonbreaking changes or a new version for breaking changes. If the route is an entirely new endpoint, it will start at Example HTTP routesExample: versioned stable route
Explanation: This route has breaking changes between Example: Route that has never had breaking changes
Explanation: This route has never had breaking changes introduced. Example: new
|
Chris, Chuck and Nikita will meet to discuss this and define a single path forward and report back the decision |
--
I don't think this is flexible enough to be practical. conda-store-server uses
This article is from Datomic. Their whole thing is to never remove, which is why
I dislike this for the same reason this is listed as an advantage. It doesn't
I'm against this. Clients will depend on this. Once we update, their stuff will
conda-store's config can include arbitrary Python code. We already had an The relevant issue is linked in the first message in this issue.
FYI: the style guide says it's always lowercase. conda-store/docs/contributing.md Line 3 in 0760fa2
This is a problem I mention above, which is why I want to have versioned Imagine I'm a client using the original v1 APIs that were added 5 years ago. Now This also prevents us from removing routes, ever. I'm not saying we should
Not sure if this is a mistake or deliberate. But we have a different versioning
I like the current one better because it allows you to have any structure behind
Again, I don't agree with this. It seems not flexible enough for a real-world Keeping things around is convenient and safe, but it does have a maintenance cost, Because this talks about removing routes in the context of vulnerabilities, this |
Chuck, Chris, and I had a chat. We have agreed on a way forward. I'm only going to address the things that we disagreed on before, based on my comment above.
Give me a thumbs up below if you agree. Otherwise, add a comment. |
Status update:
|
Tania says this also needs to be on Docusaurus. |
@dcmcand Will take over to do the writing part, I'll review. Was discussed during the meeting today. |
Status update: reviewed the initial draft of the policy submitted by Chuck in #687. The direction is good, but it needs some fixes. The file needs to be moved to the right place. |
Status update: it was discussed during yesterday's meeting that we want to split public and private Python APIs to make things easier to maintain. To determine what will be public, we'll see what Nebari uses. Other things can be exposed as public later. @pavithraes wanted to link to an issue to track this. UPD: The BC policy doesn't need to be updated to reflect this because we already talk about private/public there. It's just that we might want to make code changes to not expose too much APIs as public on the Python side. |
(Apologies for the notification noise, I closed this issue accidentally. I've re-opened it and reset the status to what it was before.) |
Context
We need to have a backward compatibility policy.
This policy needs to specify what our public interfaces are. Example interfaces:
This policy needs to document how we make changes to those interfaces. Examples:
As an example, here's BC/FC policy for PyTorch: https://github.com/pytorch/pytorch/wiki/PyTorch's-Python-Frontend-Backward-and-Forward-Compatibility-Policy
An example where a Python API change broke nebari: #593 (comment).
Value and/or benefit
We don't break other software that depends on conda-store, like nebari.
When we introduce changes, things are easier to debug because an error/warning is raised.
Anything else?
No response
The text was updated successfully, but these errors were encountered: