-
Notifications
You must be signed in to change notification settings - Fork 76
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
Separate chain interface for the coordinator package #3650
Merged
Merged
Changes from all commits
Commits
Show all changes
11 commits
Select commit
Hold shift + click to select a range
1343277
Extract chain interface for sweep proposal validation
nkuba 01b0dae
Define separate chain interface for pkg/coordinator
nkuba 9f21e9f
Reflect latest chain interfaces refactoring in test implementations
nkuba d4cfb52
Extract chain interface for redemption proposal validation
nkuba 0760625
Update local chain implementation for wallet maintainer
nkuba 70908bd
Add TODO question for PastDepositSweepProposalSubmittedEvents
nkuba d55dfa2
Clean imports
nkuba 74e0933
Update local chain implementation for coordinator package
nkuba 7eeea1f
Rename local chain file for consistency
nkuba 70bd449
Inline chain interface for validation
nkuba da06660
Remove PastDepositSweepProposalSubmittedEvents function
nkuba File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
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.
As for the functions, it's clear that we want to define them separately for each package, even if it means duplication. But what about the types the functions are expecting or returning?
I don't think duplication is the right way. Alternatively to the current solution where we just import the types from the
tbtc
package, we could alias them, but it doesn't make much sense.I'm curious about your opinion @pdyraga @lukasz-zimnoch.
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.
In my opinion, we should look at the packages as some bounded contexts of the same domain:
pkg/tbtc
is the context corresponding to the tbtc walletpkg/coordinator
is the context of a tbtc wallet coordinatorThat said, both should define domain objects (i.e. types) and functions specific to their contexts. However, some of the domain may be shared between those two contexts and this is the case we observe here. I think we have two options:
I think option 2 is worse in our case as it will introduce unnecessary confusion. In my opinion, we should aim for option 1 as it is more "natural" for our codebase.
The only question is: "Which package should hold the shared objects?". In our case, the
pkg/tbtc
is kind of a core package while thepkg/coordinator
is kind of an overlay specialized for the coordination part. If we agree about that, this implies that all shared objects should live in thepkg/tbtc
package.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.
I would be fine with the duplication for now but I think the problem with the duplication is that those structs are separate types and the chain implementation struct would have to redeclare the same function multiple times. For example:
The current solution is the lesser evil but I think we can do better. Instead of creating a dependency to
tbtc
package, we could have a separate package with the common type declarations.EDIT: Alternatively
/pkg/chain/tbtc/types/types.go
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.
As an alternative, we could also use a similar pattern that we use in
pkg/tecdsa
, i.e.:Worth noting that all sub-packages can depend on
pkg/tbtc
. This would correspond to option 1 from my previous comment where we extract the shared domain into a separate place.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.
I think we intentionally decided to flatten packages compared to
pkg/tecdsa
and treatpkg/tbtc
as the client-side wallet implementation. I don't think the alternative is bad but I also like the fact the packages are currently more flat compared topkg/tecdsa
.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.
Agreed but in fact,
pkg/tbtc
is a little bit broader than we assume here. It also contains some logic that is useful for auxiliary packages, for exampletbtc.ValidateDepositSweepProposal
. That means that even if we extract types topkg/tbtc/types
, we would still have the dependency due to some shared logic. This is why I'm leaning towards leaving shared types inpkg/tbtc
and do not complicate the situation with an additional package.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.
In order to elaborate more on why I'm a bit against
pkg/tbtc/types
:pkg/tbtc
which will make a wrong dependency direction:pkg/tbtc
->pkg/tbtc/types
. In Go, we typically make sub-packages depending on the outer packages (a lot of examples in Go std lib but also ourspkg/net
,pkg/tecdsa
, and so on).If we really insist on extracting, I would rather go with creating
pkg/tbtccore
and put there all core types and shared logic that does not belong to any specific domain context.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.
Yes, we would have to bend this rule. It is not ideal but we wouldn't be the only ones. For example, the
Block
structure is defined ingithub.com/ethereum/go-ethereum/core/types
package and it is imported bygo-ethereum/core/blockchain_insert.go
here. This is exactly our use case. As long as we do it only for thetypes
package, I would be personally fine with it.It is less generic than
tbtccore
:) I see the reasoning behind thetbtccore
but I am afraid this will sooner or later evolve into a common bag of stuff and create even more complicates mesh of dependencies. I think it's nothing wrong ifcoordinator
ormaintainer
packages imports logic fromtbtc
. It is clear, they perform the same validation as the wallet as in the mentionedtbtc.ValidateDepositSweepProposal
example and in my opinion, this is a really nice feature of the current code organization.My slight preference is for a separate types package with good documentation of why it's there and what types should be there. This would give us more flexibility and avoid import cycles. But I am also fine with leaving it as-is with imports from
tbtc
.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.
Unfortunately, it seems that there is no perfect solution.
If we decide to declare the types in a common types package what types should go there? All the types used by chain interfaces across all the packages? We have types that are common to
pkg/tbtc
andpkg/coordinator
and specific to thepkg/tbtc
only. Which do we want to move to the common types?Separating types from the chain interfaces declaration may be confusing, as in V2 we decided to declare the chain interfaces closer to the actual usage in packages.
Importing types defined in
pkg/tbtc
package into thepkg/coordinator
doesn't seem perfect either. Thepkg/coordinator
package usespkg/tbtc
types, but also declares its' own types (e.g.NewWalletRegisteredEvent
).We cannot duplicate the types either, as the functions defined in different packages will require the same type, e.g.
ValidateRedemptionProposal
defined in bothpkg/coordinator
andpkg/tbtc
must use the sameRedemptionProposal
type.I lean towards the current approach where types are defined in
pkg/tbtc
which is considered a broader and core package and we just import them inpkg/coordinator
. This isn't perfect but it doesn't require an aggressive refactor.We could add another issue for the future to find the perfect solution for types definition.
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.
Captured it here: #3652