We're planting a tree for every job application! Click here toΒ learn more

Go (golang) service options (dependencies)

Roman Romadin

26 Oct 2020

β€’

2 min read

Go (golang) service options (dependencies)
  • Go

About me: I am mostly backend developer and looking for new opportunities in Europe/US as Software Engineer / Backend Developer. My Linkedin: https://www.linkedin.com/in/roman-romadin/


How to dynamically inject dependencies into "Service" in Go?

This solution (approach) is based on:

  1. variadic functions (https://yourbasic.org/golang/variadic-function/) and
  2. self-referential functions (https://www.geeksforgeeks.org/self-referential-structures/).

At first glance, this seems a bit confusing, but it's actually a simple solution. This approach can be used to initialize the application as a whole and to load configuration and other services.

Using variadic function:

type Option func(*accs)

func (f *accs) AddOptions(opts ...Option) {
    for _, opt := range opts {
        opt(f)
    }
}

Using self-referential functions:

func BindSubscriptions(v subscriptions.Client) Option {
    return func(f *accs) {
        f.srvSubscriptions = v
    }
}

First of all you should create main service. In our snippet it is accounts:

accs := accounts.New()

Init the second service (it will be property for main service):

srvSubscriptions := subscriptions.New(111)

After that you should bind second service and set properties for first service:

sbs := accounts.BindSubscriptions(srvSubscriptions)
accs.AddOptions(sbs)

And finally we process business logic (process):

accs.Process(222)

As well we can change any properties in second service (accounts or billing in our snippet): set value = 222

And in addition by using variadic functions we can add one or more properties into first service:

accs.AddOptions(sbs, bl)

or by this way:

accs.AddOptions(sbs)
accs.AddOptions(bl)

Full code:

.
β”œβ”€β”€ cmd
β”‚Β Β  └── main.go
β”œβ”€β”€ pkg
β”‚Β Β  β”œβ”€β”€ accounts
β”‚Β Β  β”‚Β Β  └── service.go
β”‚Β Β  β”œβ”€β”€ billing
β”‚Β Β  β”‚Β Β  └── service.go
β”‚Β Β  └── subscriptions
β”‚Β Β      └── service.go
└── README.md
package main

import (
    "../pkg/billing"
    "../pkg/subscriptions"
    "../pkg/accounts"
    "fmt"
)

func main() {
    fmt.Println("Variant_1:")
    variant1()

    fmt.Println("Variant_2:")
    variant2()

    fmt.Println("Variant_3:")
    variant3()
}


func variant1() {
    accs := accounts.New()

    srvAccounts := subscriptions.New(111)

    sbs := accounts.BindSubscriptions(srvAccounts)

    accs.AddOptions(sbs)

    accs.Process(222)
}

func variant2() {
    accs := accounts.New()

    srvAccounts := subscriptions.New(333)
    srvBilling := billing.New()

    sbs := accounts.BindSubscriptions(srvAccounts)
    bl := accounts.BindBilling(srvBilling)

    accs.AddOptions(sbs, bl)

    accs.Process(444)
}

func variant3() {
    accs := accounts.New()

    srvAccounts := subscriptions.New(555)
    srvBilling := billing.New()

    sbs := accounts.BindSubscriptions(srvAccounts)
    bl := accounts.BindBilling(srvBilling)

    accs.AddOptions(sbs)
    accs.AddOptions(bl)

    accs.Process(777)
}


Output result:

Variant_1:
        a.Prop (before): 111
        a.Prop (after): 222

Variant_2:
        a.Prop (before): 333
        a.Prop (after): 444

Variant_3:
        a.Prop (before): 555
        a.Prop (after): 777

Thank you for reading.

All sources you can find in my repository: https://github.com/romanitalian/go-service-options

PR's are welcome.

Any questions: https://twitter.com/romanitalian are also welcome!

Did you like this article?

Roman Romadin

rmn:dev

See other articles by Roman

Related jobs

See all

Title

The company

  • Remote

Title

The company

  • Remote

Title

The company

  • Remote

Title

The company

  • Remote

Related articles

JavaScript Functional Style Made Simple

JavaScript Functional Style Made Simple

Daniel Boros

β€’

12 Sep 2021

JavaScript Functional Style Made Simple

JavaScript Functional Style Made Simple

Daniel Boros

β€’

12 Sep 2021

WorksHub

CareersCompaniesSitemapFunctional WorksBlockchain WorksJavaScript WorksAI WorksGolang WorksJava WorksPython WorksRemote Works
hello@works-hub.com

Ground Floor, Verse Building, 18 Brunswick Place, London, N1 6DZ

108 E 16th Street, New York, NY 10003

Subscribe to our newsletter

Join over 111,000 others and get access to exclusive content, job opportunities and more!

Β© 2024 WorksHub

Privacy PolicyDeveloped by WorksHub