Skip to content
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

all: Refactor db.Session to take ctx into each call, instead of storing it on the session level #3545

Merged
merged 6 commits into from
Apr 23, 2021

Conversation

paulbellamy
Copy link
Contributor

@paulbellamy paulbellamy commented Apr 15, 2021

PR Checklist

PR Structure

  • This PR has reasonably narrow scope (if not, break it down into smaller PRs).
  • This PR avoids mixing refactoring changes with feature changes (split into two PRs
    otherwise).
  • This PR's title starts with name of package that is most changed in the PR, ex.
    services/friendbot, or all or doc if the changes are broad or impact many
    packages.

Thoroughness

  • This PR adds tests for the most critical parts of the new functionality or fixes.
  • I've updated any docs (developer docs, .md
    files, etc... affected by this change). Take a look in the docs folder for a given service,
    like this one.

Release planning

  • I've updated the relevant CHANGELOG (here for Horizon) if
    needed with deprecations, added features, breaking changes, and DB schema changes.
  • I've decided if this PR requires a new major/minor version according to
    semver, or if it's mainly a patch change. The PR is targeted at the next
    release branch if it's not a patch change.

What

The root change is:

 package db

 type Session struct {
        // DB is the database connection that queries should be executed against.
        DB *sqlx.DB

-       // Ctx is the context in which the repo is operating under.
-       Ctx context.Context
-
        tx        *sqlx.Tx
        txOptions *sql.TxOptions
 }

And changing all the db.Session methods (where needed) to take a ctx context.Context params. Then passing that through all the places to get it there.

Why

For #3344, we want to pass different timeouts in different contexts. This change makes that easier, and generally follows the go norms of passing the context late into the method.

Known limitations

It's big. Will be difficult to review and merge. Most of the param passing is pretty mechanical. The interesting parts are around where we create the contexts initially. But, most of that is in tests.

Questions

  • RemoteCaptiveStellarCore.createContext and cancellation semantics. Should we do it everywhere? Only for PrepareRange?
    • Ignored this, keeping the existing semantics, for now. But seems like we should cancel all outstanding requests, not just PrepareRange.
  • OrderBookStream.Run, should we make a new timeout ctx each tick?

Bonus

I also fixed TestOpen_openAndPingFails, because it was intermittently failing and being annoying.

@paulbellamy paulbellamy requested a review from a team April 15, 2021 18:25
@paulbellamy paulbellamy force-pushed the 3344/tick-timeouts branch 2 times, most recently from 767ad96 to 0efc871 Compare April 16, 2021 14:47
.gitignore Outdated Show resolved Hide resolved
@@ -74,8 +75,9 @@ func (*DatabaseBackend) IsPrepared(ledgerRange Range) (bool, error) {

// GetLatestLedgerSequence returns the most recent ledger sequence number present in the database.
func (dbb *DatabaseBackend) GetLatestLedgerSequence() (uint32, error) {
ctx := context.TODO()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this will change the behavior because now we cannot cancel a query via context termination. maybe it's best to move changes to this file to the ledgerbackend PR as well

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this is fixed, with the new changes, but double-check me on that, please.

@paulbellamy
Copy link
Contributor Author

paulbellamy commented Apr 19, 2021

Stuff here is difficult without including the ledgerbackend changes. Going to try doing those first, and see if that makes this change simpler.

Edit: It did not. Updating the LedgerBackend interface changes in DatabaseBackend, depends on these changes. Instead, added some temporary code to simplify this and pull the LedgerBackend interface changes out of this PR.

@paulbellamy
Copy link
Contributor Author

One catch with this, is that we now need to call an explicit .Close() method on places where we relied on the context cancellation to implicitly shutdown everything.

Places where I've found that so far:

  • LedgerBackend shutdown (we were already doing that)
  • LedgerHashStore shotdown (also already doing that)

@paulbellamy paulbellamy force-pushed the 3344/tick-timeouts branch 2 times, most recently from 3f3b26d to e94f3fb Compare April 20, 2021 15:32
@paulbellamy paulbellamy force-pushed the 3344/tick-timeouts branch 2 times, most recently from 42d1a30 to 2f9863f Compare April 21, 2021 16:26
@@ -26,21 +27,32 @@ var _ LedgerBackend = (*DatabaseBackend)(nil)

// DatabaseBackend implements a database data store.
type DatabaseBackend struct {
cancel context.CancelFunc
ctx context.Context
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is it stored instead of using it in method calls? (it would only be OK if a database backend is ephemeral)

Copy link
Contributor Author

@paulbellamy paulbellamy Apr 22, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Belt-and-braces (for now) to ensure shutdown. Normally the parent should call Close(), but apparently there are some intricacies around shutdown ordering, so I wanted to keep the existing behaviour (when the parent ctx is cancelled, this ends as well).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To be clear, it's two separate contexts. This one, to shut down the whole backend; and the one passed in method calls which is per-call.

@@ -67,6 +67,7 @@ type RemoteCaptiveStellarCore struct {
client *http.Client
lock *sync.Mutex
cancel context.CancelFunc
parentCtx context.Context
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same here

@paulbellamy paulbellamy merged commit f362e0c into stellar:master Apr 23, 2021
@paulbellamy paulbellamy deleted the 3344/tick-timeouts branch April 23, 2021 16:52
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants