Hi David,

Thanks for your thoughtful reply.

From: "David Brady" <ruby_talk / shinybit.com>
>
> Bill Kelly wrote:
> 
> >Again, I'd ask to see what sort of test you'd propose that would
> >catch the problem I described.  (My post, the one you quoted, was
> >about CGI, not the Logger.)
> >  
> >
> I find that the hardest tests to write are the ones that I overlooked 
> because I am unaware of my blind spots.

Yes - agreed.

> Until I read your post, I thought like you did--that to_s flattened an 
> object into a chunk of text.  But now I see that it doesn't.  It doesn't 
> even return a String object!  It returns an object that behaves--dare I 
> say quacks?--like a String.
> 
> Another assumption you may be making--and once I state it, the test for 
> it should become obvious--is that YAML should output pleasingly human 
> readable text, even if it loses the ability to correctly restore objects.

Hmm... Actually my assumption (or hope) would be that YAML always
be able to write out objects that it can correctly restore.  My 
reason for wanting my application to be serializing "real" simple
strings isn't really tied, I think, to any assumptions about how
YAML itself should behave.

But yes, I want my *application* to, using YAML, output simple
strings that are not only pleasingly human readable, but also
compact*.  I have no problem with YAML doing exactly what I've 
asked it to.  I just didn't realize I was feeding it complex
singleton String instances with "extra" instance variables.

(*) The compactness is desirable for performance reasons:
I'm already splitting my databases via hashing into 4093 sub-
files, so each component file of the database can be loaded/saved
quickly enough.  YAML Ain't Mercurial Lightning... ?  ;)

> I know, I know.  There exists in business the concept of "approprately 
> incorrect".  You are using YAML to produce "appropriately incorrect" files.

I'm not sure I agree.  I'm using YAML to accurately serialize my
data.  It's my fault for feeding it unexpectedly complex data.

> The behavior you want is "take a Stringlike object, and emit pleasingly 
> simplified text".  That's easily testable.  Take your CGI object, have 
> YAML dump it, then open the YAML file manually and see that the text is 
> correct.  Or build a CGI object, then build an equivalent object using 
> Strings, output them to different files and then assert that there is no 
> difference between the files.  The second method may seem more robust, 
> because it lets you not care how YAML stores Strings... but that's the 
> rabbit that led us down this hole in the first place.  Use the first 
> method, because you don't care if YAML stores CGI the same as a String, 
> you care that the output is pleasing to read.  If YAML changes the way 
> it stores String, you'll want this test to break.  Your app should 
> shriek until you have verified that the new format is pleasant.

One test I had in mind was,

assert( cgi['something'].to_s.to_yaml ==
        String.new(cgi['something'].to_s).to_yaml )

...but that test does rely on my modified String#to_s behavior.

One complication is that, for the time being, my application needs
to run on systems with the 1.8.1 CGI behavior (which returns a
parameter value as a non-String-object that quacks like a String),
and the 1.8.2 CGI behavior (which returns a paramater value as a
genuine String instance whose singleton class happens to have been
extend'ed with a module that includes some bonus instance variables.)

So far, my String#to_s hack still seems like a reasonable enough
way to enforce the behavior I need in my current application.  (But
again, I'd NOT take this hack approach if I were writing a library.)

So, given my String#to_s hack, I think the above assert() should
cover the specific problem I was having.

A more direct approach might have been for me to open the CGI class
and replace CGI#[] so that it returned simple String instances, not
complex extend'ed ones.  (Again, something I'd consider for my app,
but not for a library.)

I'm not sure if more general tests involving YAML and Strings would
help, since I don't *really* want to change YAML's behavior - I just
want to not accidentally feed it complex objects.


Regards,

Bill