Code Monkey home page Code Monkey logo

gotry's Introduction

GoTry

GoDoc codecov Go Report Card GitHub license GitHub tag (latest SemVer)

A small and highly flexible Go library for non-blockingly retrying potentially failing operations and preserving their return values once they succeed.

Heavily inspired by avast/retry-go and giantswarm/retry-go and partially based on the latter.

I didn't want to use either of the two because neither handles return values of the retried operations, which is crucial for things like connecting to a database that may be offline for a short period of time. (I retract that statement but leave it in for posteriority after reading this wonderful comment.)

Usage

You decide whether you want to run Try as a goroutine or not.

package something

import "github.com/yeldiRium/gotry"

func main() {
    resultChannel := make(chan *RetryResult)
    go gotry.Try(
        func() (*ConnectionHandle, error) {
            return connectToSomeDatabaseWhichMightFailButOtherwiseReturnsAHandle()
        },
        resultChannel,
    )

    // do some other things

    for {
        select:
        case res <-resultChannel:
            if res.StopReason != nil {
                // Retrying was stopped because of something.
                switch res.StopReason.(type) {
                    // If you want to find out why retrying stopped failed.
                    case gotry.TooManyRetriesError:
                        //...
                    case gotry.TimeoutError:
                        //...
                    default:
                        // Should not happen.
                }
                // The last error the operation returned
                err := res.LastError
            }
            value := res.Value.(*ConnectionHandle)
            // work with it!
        default:
            doOtherStuffInTheMeanTime()
    }
}

Take a look at the available options for more.

Known Issues / Future Goals

  • Currently operations that are long and blocking block the Try function and delay aborting due to timeouts.

    I.e. if I call Try(op) with op being a complicated computation that takes a while but I want to set a timeout for it, the ErrTimeout can at the earliest be returned after one full execution of f.

    There is already a commented out test for this in gotry_test.go.

    This will probably require a rewrite of the Try logic so that f is run in another goroutine and raced against the timeout.

  • Rewriting this using Contracts would make it even better, since we'd have type safety at compile time.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.