← Back to team overview

launchpad-dev team mailing list archive

Re: API issue moving branches

 

> I find this quite hard to do since the API exposes our model objects.
> 
> I'd love to have a separate layer, like we have with the browser.

In theory, you are 100% free to write your own Entry classes instead of
having them generated from annotated model objects. As an example, the
web service defined in lazr.restful doc/webservice.txt creates its Entry
classes from scratch. But, we would rather not have two different data
models (one for internal use, one for the web service). We'd rather have
one, and when we first designed the web service we had a specific policy
for making sure we only had one.

We developed the annotation technique to make it really easy for the
Launchpad developers to publish a web service for their field of
responsibility, without having to learn a lot about web service design
or make a lot of changes. The price we paid was a coupling of the web
service model to the underlying data model. There's no free lunch. You
either put some work into designing your web service, or you get a web
service that reflects the work you already did.

The original idea was that when we ran into a mismatch between the
underlying data model and the web service data model, we would refactor
the underlying data model. We would think to ourselves: "design X is
going to confuse our users; it would be nice to publish design Y
instead", and then we'd start using design Y _everywhere_. Because why
should we have a confusing design when our users get a nice design? The
web service would be a way to make piecemeal improvements to our
underlying design.

Yeah, the named operation setTarget(package, project) is confusing. But
the internal method setTarget(self, package, project) is also confusing,
in exactly the same way! If we leave it in place internally and patch
over it for the web service (which is what we talk about when we talk
about annotations), we're letting our users have the good stuff but
we're still using the not-so-good stuff internally.

It sounds like we are approaching the point where we either need to
start refactoring, or decide that the refactoring idea won't work after
all and we need to fall back to writing our own Entry classes. In this
particular instance (setTarget) I think we can resolve the problem with,
at most, a minor change to the underlying data model. But let's take
another example.

When I look at the HWDB data model (as published through the web
service) I have absolutely no idea what is going on. If I wanted to
write a web service script using the HWDB it would take me days just to
get started. I'm sure the domain experts know what is going on, and I'm
also sure that if they put some work into client use cases they could
come up with a public-facing data model that was simpler. 

At this point, I'd suggest we refactor the existing HWDB data model into
the simpler data model, rather than have to keep two different data
models in our heads. Why not? It's a lot of work, but not that much more
work than writing a whole other data model, and at the end our
application will be better. Because the public-facing data model is less
efficient? That's a reason not to publish at all--it's a bad idea to
publish an inefficient data model and hope our users don't use it too
much. Are the two data models just totally irreconcilable for some other
reason? In that case, it probably makes more sense to go ahead and
create our own Entry classes.

I hope it doesn't feel like I'm suddenly springing this on you. This has
been our plan for quite a while, but up to this point we've been
focusing on creating a web service with a solid foundation that
publishes all the Launchpad artifacts. Now is a good time to start
talking about the best way to *improve* the design of the web service.

Leonard

Attachment: signature.asc
Description: This is a digitally signed message part


Follow ups

References