Relation edge settings

Bug #1026422 reported by Gustavo Niemeyer
24
This bug affects 4 people
Affects Status Importance Assigned to Milestone
juju-core
Won't Fix
Low
Unassigned

Bug Description

Clint described a feature in the mailing list we must look at:

----

I"ve run into this problem a few times, and I think there's a hole in
the current model that needs filling.

Recently Juan Negron and Tom Haddon submitted a really awesome set of
enhancements for the haproxy charm.

https://code.launchpad.net/~mthaddon/charms/precise/haproxy/mini-sprint-sf/+merge/114951

You can see there a lot of it was some nice abstraction for juju commands
which I think belongs in its own package. But thats not what I'm writing
about.

Tom and Juan felt that there needed to be a way to assign units of
a backend web service to servics, which were created by dumping raw
haproxy service configs into a config option.

They're right! But I have some deep concerns about the proposed method.

The merge proposal wants to add a parameter for the "provides" side of
the http interface which uniquely identifies which endpoint service this
web server wants to belong to. Right now most web services do something
like this in an http interface 'joined' hook:

relation-set hostname=$(unit-get private-address) port=$(config-get myport)

Then load balancers can just add this hostname/port combo to their
backend list to spray content to.

This presents issues though, because now we can't do multi-site on either
the load balancer *or* the backend. This is what the Host: header is
meant for.

The proposal has us passing in a yaml list of services to define:

  - service_name: website1
    service_host: "website1.foo.bar"
    service_port: 80
    service_options: [balance leastconn]
    server_options: maxconn 100
  - service_name: website2
    service_host: "website2.foo.bar"
    service_port: 80
    service_options: [balance leastconn]
    server_options: maxconn 100

Then each backend service which wants to be able to be bound to a specific
frontend would change their joined to do:

relation-set hostname=$(unit-get private-address) \
             port=$(config-get myport) \
             service_name=$(config-get my-service-name)

This feels *very* limiting. In order to close the loop we have to set
configs on both ends of a relationship, and the configs we have to set
are extremely complicated and error prone.

I think there's a need for relations to have config items, as this would
solve the problem far more elegantly.

I'd propose that it work like this:

* metadata.yaml:

requires:
  backends:
    interface: http
    options:
        endpoint-host:
            type: string
            description: Host to tie this traffic to.
        endpoint-port:
            type: int
            default: 80
            description: Port to tie this traffic to.

* relation-config-get

A new command, like config-get, but works in relation context only to
pick these up. Changes to relation config settings would fire the same
relation-changed hooks as changes on the units fire.

* juju add-relation , juju set-relation

Commands to set values for these per-relation. So

juju add-relation wp1 loadbalancer endpoint-host="website1.foo.bar"

For the simple case (one frontend, one backend) nothing would then change,
but this would also allow this:

juju add-relation wp2 loadbalancer endpoint-host="website2.foo.bar"

So now haproxy has become multi-site, which is crucial, as load balancing
is really quite a low-impact duty and one m1.small can handle thousands
of requests per second.

But what about wordpress? It could be multi-site too. So I think we
should also enable this:

juju add-relation wp1 loadbalancer endpoint-host="website1.foo.bar"
juju add-relation wp1 loadbalancer endpoint-host="website2.foo.bar"

Note that this is the same two services related, but with two different
relationships. This would allow both haproxy and wordpress to be
multi-site.

This is not the only case of this. There are quite a few others. For
instance one might want to have multiple services accessing the same
mysql db. This makes more sense doing at relation time, and not with
config settings. The way it works now:

juju deploy mysql mydb
juju deploy service1 --set store-db=foo
juju deploy service2 --set service-db=foo
juju add-relation mydb service1
juju add-relation mydb service2

Versus

juju deploy mysql mydb
juju deploy service1
juju deploy service2
juju add-relation mydb service1 db=foo
juju add-relation mydb service2 db=foo

Changed in juju-core:
status: New → Confirmed
importance: Undecided → Medium
summary: - Relation-bound settings
+ Relation edge settings
Tom Haddon (mthaddon)
tags: added: canonical-losa-ue
Haw Loeung (hloeung)
tags: added: canonical-webops-juju
Revision history for this message
William Reade (fwereade) wrote :

This is very cool, but I'm not sure we have space in the schedule for R. Can we drop it to wishlist?

William Reade (fwereade)
Changed in juju-core:
status: Confirmed → Triaged
importance: Medium → Wishlist
Curtis Hovey (sinzui)
tags: added: canonical-webops
removed: canonical-losa-ue canonical-webops-juju
Curtis Hovey (sinzui)
tags: added: improvement
Curtis Hovey (sinzui)
Changed in juju-core:
importance: Wishlist → Low
Tom Haddon (mthaddon)
tags: added: canonical-is
removed: canonical-webops
Changed in juju-core:
status: Triaged → Won't Fix
To post a comment you must log in.
This report contains Public information  
Everyone can see this information.

Other bug subscribers

Remote bug watches

Bug watches keep track of this bug in other bug trackers.