-
Notifications
You must be signed in to change notification settings - Fork 473
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
split Balances Get/Put interface methods into separate methods for creatables #3151
Conversation
Is |
As you recall from the ledger refactoring documentation, the resources table is going to be separate from the account data. There will definitely be a method that would return the basics of what an account could hold, but all the maps are planned to have a separate accessors. |
So it will return a different type that doesn't contain maps? |
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.
Looks good. Please fix the build, comment new functions, and it is ready to go
ledger/apply/asset.go
Outdated
@@ -406,18 +396,10 @@ func AssetFreeze(cf transactions.AssetFreezeTxnFields, header transactions.Heade | |||
} | |||
|
|||
// Get the account to be frozen/unfrozen. | |||
record, err := balances.Get(cf.FreezeAccount, false) | |||
holding, err := balances.GetAssetHolding(cf.FreezeAccount, cf.FreezeAsset) |
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.
wondering why are these "business logic" values passed down to retrieval code?
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.
how so?
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'd expect GetAssetHolding
to return holdings by address (cf.FreezeAccount
in this case), but looks like it also checks/sets cf.FreezeAsset
value
To try and catch anything I missed, I prefixed the maps in AccountData with I found WDYT — I was thinking of moving AccountData.MinBalance() to an internal helper function in ledger called by both callers, would that be a good idea? |
Codecov Report
@@ Coverage Diff @@
## feature/unlimited-assets #3151 +/- ##
============================================================
+ Coverage 47.23% 47.43% +0.20%
============================================================
Files 365 370 +5
Lines 58361 59646 +1285
============================================================
+ Hits 27564 28296 +732
- Misses 27611 28032 +421
- Partials 3186 3318 +132
Continue to review full report at Codecov.
|
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.
Had a few questions, but looks like a nice step forward to me.
ledger/apply/application.go
Outdated
@@ -86,19 +85,22 @@ func createApplication(ac *transactions.ApplicationCallTxnFields, balances Balan | |||
return | |||
} | |||
|
|||
// look up how many apps they have | |||
totalAppParams, err := balances.TotalAppParams(creator) |
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 don't follow why this became a method, but total TotalExtraAppPages is accessed directly. Aren't they both keeping a cached sum of things we would otherwise have to chase down? I suppose the answer might be, "Yes, so we should move TotalExtraAppPages into nice protected method where we can be sure to track it properly too, but that's not the job of this PR."
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 now see that, at least for now, you're not caching a total count. I wonder if we should. The reasoning would be similar, but it does mean writing these objects (man, I really want them to have another name like "AccountHeader" or "AccountBase" so I don't have to distinguish by package name), whenever we add or remove an asset or app. Then again, I guess we already have to, exactly so we can calc min balance.
// ToApplyAccountData returns apply.AccountData from basics.AccountData | ||
func ToApplyAccountData(acct basics.AccountData) AccountData { | ||
return AccountData{ |
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.
This makes me start to wonder if apply.AccountData should be basics.AccountBase and be embedded in basics.AccountData. Why does it belong in apply?
It would also make the distinction I mentioned earlier clear. It's not some sort of "view" of the AccountData that the apply package prefers, it's the constant sized base of the full basics.AccountData.
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 guess apply.AccountData
is a temporary type while we do not have other/better types.
The idea is to have in-mem and persistent data types for components of basics.AccountData
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 get that, but it seems to me that this in-memory type is, in fact, the beginning of basics.AccountData, so why not make that explicit?
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.
There was a bigger potential change I considered, where basics.AccountData loses these maps altogether, ledger.Lookup() gets split into separate acct/app/asset methods too, all former users of AccountData are updated to get asset data separately, and the original AccountData type (and its msgp encoding) is moved inside ledger and becomes an implementation detail of account DB, eval, COW, etc.
I didn't think of embedding it as an AccountBase in AccountData because I figured we this PR was moving us towards that goal, starting with apply.Balances.
However looking at what's missing, really only the REST API is left after this I believe.
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.
oh, also I was worried a change to basics.AccountData directly might involving updating a ton of tests.
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 see, so the plan might be that basics.AccountData becomes what I was calling basics.AccountBase, and it gets (maybe) embedded in ledger.accountFull. The apply package will take the various pieces it needs, never an entire ledger.accountFull.
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.
y'know, I already changed cowForLogicLedger to have Get() return the new apply.AccountData, which is now out of sync with Ledger.Get() returning basics.AccountData, so I will try plumbing through Ledger.GetAppParams, etc to see how much more changes it would be.
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.
Ok, don't get carried away on my behalf. This is nice enough to do as is, and I don't want it to get so large we we have trouble moving forward incrementally.
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 tried tracking down everywhere that was using the maps in basics.AccountData, it was the REST API (account data and dryrun endpoints), tealdbg, and goal, all calling through Ledger.Lookup() basically. I think it's probably best for now to have ledger.Ledger just hide the logic behind Lookup() of joining the asset/app data with account data, rather than change all the tests and callers to Lookup that use basics.AccountData.
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.
ledger/apply/apply.go
Outdated
// AssignAccountData assigns the contents of apply.AccountData to the fields in basics.AccountData | ||
func AssignAccountData(a *basics.AccountData, acct AccountData) { | ||
a.Status = acct.Status | ||
a.MicroAlgos = acct.MicroAlgos |
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.
Now even more so. This would become a simple assignment.
Amount: cc.AssetParams.Total, | ||
} | ||
|
||
if len(record.Assets) > balances.ConsensusParams().MaxAssetsPerAccount { | ||
return fmt.Errorf("too many assets in account: %d > %d", len(record.Assets), balances.ConsensusParams().MaxAssetsPerAccount) | ||
if totalAssets >= balances.ConsensusParams().MaxAssetsPerAccount { |
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.
nit: check this before the above work?
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.
yeah, I was overoptimizing for min diff length, I think there are a few places like this I can pull the "too many X" checks up
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.
No strong need, sometimes I don't really notice what's new and what was already there.
…cloneAssetParams to test code
* Add error strings to v2 TEAL compile endpoint * Move number of errors to end so it is consistent with goal clerk compile * Refactor ReportProblems() to take io.Writer * Don't report number of errors on the API call
* add abi encoding * accord with go-algorand code format * minor modification * add partition test * resolve review, need more testcase rewrite * move from cmd/goal to data, resolve review * rewrite is-dynamic, dynamic array * update dynamic array 0 element support, test needed * minor * minor * minor * add more testcase for abi encode/decode * update comments in encoding test * minor * attempt to split abi.go into 2 files * separate abi files to smaller files * resolve reviews, work on random gen tuple value encode/decode * add random tuple test * remove math-rand, use crypto-rand * minor * minor * some change requested from community * fix for 1 corner case * resolve review comments * resolve review comments * minor * minor * update encode slot capacity * minor * resolve reviews * minor update on bool bytelen calculate * update encode/decode from types * random test remain to be modified * testing variable renaming, encode int support (u)int types * update test scripts and remove value struct * follow golint * partly resolving comments * whoops uint encoding update * update int decode to primitive types method * go fmt * update parseAppArg to accept abi input (attempt) * need to check cmdline arg validity * update unmarshal from JSON in ABI type * unmarshal from json for ABI type * update ABI type unmarshal values from JSON bytes * update ABI methods for string/array/address * update unmarshal from JSON in abi * fix for error in ufixed json unmarshal * fix * update on method sub command * minor * probably better separate abi json to a single file * i just want to add a required flag plz... * minor fix on interface from json * consider some rough test cases * minor * add partition test * update static uint test * update marshal/unmarshal json methods for abi * marshal byte array to b64 string * abi json polish * update golangci lint rules * revert golangci config * update method impl * update method signature return type check * minor * copy-paste code from call app cmd * minor * add method flag to txn flags * minor * update changes * minor * moving helper functions to abi * update comments * update method app call * resolve part in abi impl * add oncomplete support * minor * try to use stringarrayvar * minor * update goal return log handing process * go simple * add a line of e2e test for now * update * minor * minor * minor * go fmt * approval/clear prog nil * discard all changes to e2d-app-cross-round, going to write separately e2e test * update e2d tests * check ret valu * use constant * resolve review partly * resolve review on code reformatting * resolve review on code reformatting, use code chunk for datadir and client * go fmt * export tuple type maker * update comments in e2e test * update filter empty string * resolve issues with JSON abi * minor
* adding missing to opcode docs for external gets * update TEAL_opcodes.md
## Summary * new `ParticipationRegistry` interface designed to manage keys and collect usage metrics. * new REST endpoints for interacting with keys. * improved `goal account partkeyinfo` and `goal account listpartkeys` formatting. ## Test Plan New unit and integration tests.
Integration tests (specifically, e2e-go tests) seem to be having resource issues lately, so this returns integration tests to using large instances (4 cores, ~16GB RAM) after they were downsized to medium (2 cores ~8GB RAM) in algorand#3095. Nightly integration tests are already using large VMs.
## Summary When implementing the catchpoint tracker, I missed the re-initilization location for some of the local variables. This would generate incorrect catchpoint labels after a node completes a fast-catchup. algorand#3085 ## Test Plan - [x] Add unit tests - [x] Perform manual testing
Summary
This adds extra methods to the apply.Balances interface to offer creatable-specific alternatives to Get and Put, including chasing down all the use cases of Get and Put to call the new interface methods. A new apply.AccountData type restricts access to the full basics.AccountData structure.
In later PRs, the goal is to replace basics.AccountData and migrate to a database that uses separate tables for account data and per-(account, app/asset) data.
Test Plan
All the current tests pass. I'm also running it against mainnet and testnet with CatchpointTracking enabled and comparing the resulting catchpoint hashes with historical catchpoint hash values. I'm also looking at coverage of files in apply to see if there are any new tests I could add to master (and then merge into this branch) to cover any corner cases not currently handled by our existing unit tests.