code in cvs is broken

Linas Vepstas linas@linas.org
Mon, 19 Nov 2001 15:12:46 -0600


On Mon, Nov 19, 2001 at 01:32:24PM -0600, Bill Gribble was heard to remark:
> On Mon, 2001-11-19 at 13:19, Linas Vepstas wrote:
> > Right. Don't write a parser.  Don't load the currencies from a file.
> > Let the engine start out empty, buck-naked.  The engine does not need
> > to know about currencies; the engine shouldn't read initialization info
> > from a file.
> 
> Linas, 
> 
> That's the way it started out.  The engine didn't know anything about
> any currencies. That's why we thought it was OK to do the currency
> parsing in Scheme... it wasn't part of the engine, just the app.

OK.

> However, that approach has caused problems from the get-go with every
> scripting or other application of the engine we've seen.  You can't load

!! I'm slightly at a loss to understand what 'every other application of
the engine' is, since, as far as I know, there are no stand-alone scheme
scripts for gnucash, and, as the erstwhile maintainer of the perl
bindings, I'm all too well aware of the limitations there.  Your
comments surprise me; I had long bit my tongue because I thought I was 
the only one suffereing from these defects ...


> a file without knowing about the ISO currencies, nor can you create or
> save one.  One approach was to figure out which ISO currencies were in
> use by a file, then save those with the other user-created commodities,
> but then what does that really get you?  The ISO currencies really are a
> "universal" and ought not to be saved with the user's data IMO. 

Hmm. OK, I get it now. 

To be bombastic, in unix, a 'file' is not a globally-network-visible 
unique persistant store, and so you can't really map the concept
of "universal" to unix file storage;  that is what is really at the 
root of the problem.  So you have to make do with what you have.  
Unix is evil, and makes you do weird, twisted things.  

If currencies are truly universal, then there is nothing wrong with
hard-coding them in C.  But if they need to be pulled from a file,
then they're not exactly universal.  

I suppose one might try to argue that there's some middle ground for 
a config-file.  But in that case, why not just dump all the currencies 
into an XML file somehwere, and read that during startup?  We've already 
got code that knows how to do this. 

The problem of default pre-loaded data is really a backend problem, not
an engine problem.  Imagine having a config-file setup with a multi-user
backend.   If one user has one config file, and another user has a
different config file, then there is a very real risk of writing garbage 
data into the backend store.  Its not enough to have the engine know about
currencies, the backend must know them, and must furthermore be the
sole, unique arbiter of thier values.

Currently, the SQL backend stores the currencies itself, precisely for
this reason.  Hard-coding them into C structs, or pulling them from a
file is not an elegant solution for this backend.   Actually, its
downright ugly, esp. if you forget to bracket the currencies with
'begin/end' constructs, or load them before the backend is initialized.
If you really, really want the engine come with its own pre-loaded, 
pre-memorized data, then its really a persistant-storage problem.  
Each persistant store (aka backend) needs to be able to store this 
data in its own way, and deal with the shortcomings of its storage 
medium in its own way.  The 'universality' of currencies is really 
a statement about the short-comings of file storage.  The XML backend 
is just plain broken; the SQL backend does not suffer from this 
shortcoming.

> To me, it's important that we support scriptability to the extent that

absolutely.

> you don't have to load the whole gnucash app to deal with your file,
> load a QIF, etc. if you can do it from the command line.  We could
> create another loadable module that pokes the ISO currencies into the
> engine.

As I now realize, this is really a problem with a design decision in the 
file backend, and not with the engine architecture.   

Loading the currency data into the engine from a file, any kind of file,
scheme form or otherwise, is a bad idea if the backend has not yet been
initialized and a specific data store has been connnected to.  

To be very concrete: if you create a transaction with a currency that
the sql backend doesn't know about, or is not identical to what the
backend beleives it knows about this currency, then either you are
misleading the user with bad data, or you risk a core dump or some 
other weird error.  I don't think there's any code in there to just
notice that the currency has magically changed, and deal with it.  
You have to use te API to set/get consistent data.

The right way to do this is to fix the file backend to know about a
default set of currencies.

--linas

-- 
pub  1024D/01045933 2001-02-01 Linas Vepstas (Labas!) <linas@linas.org>
PGP Key fingerprint = 8305 2521 6000 0B5E 8984  3F54 64A9 9A82 0104 5933