IWETHEY v. 0.3.0 | TODO
1,095 registered users | 0 active users | 0 LpH | Statistics
Login | Create New User
IWETHEY Banner

Welcome to IWETHEY!

New [ siiiiiiiiiiiiiiiiiiiiiiigggggghhhhhhhhhhhhhh ]
What a shit day this has been. Project lead for our largest integration is on vacation. Backup sends me a change to roll out. One line looks suspect, but he explains what it's for. We recently finished finally building a full development DB environment. The new code was to detect what IP the transmission was coming from and route to the right environment.

Did you know that if you don't define a constant but test for its value anyway, it may return true anyway? ie:
if( DevelMode ){\n    // point to devel DB environment;\n}

But since PHP is loosely typed, and case sensetive, and the constant (when defined) is DEVELMODE ... it interprets DevelMode as the string 'DevelMode'. And if( [string] ) returns true.

And the devel DB is a snapshot of the live DB from a couple of weeks back. So all the offices that had been activated in the last couple weeks had thier orders rejected.

So like I said ... siiiiiiiiiiiiiiiiiiiiiiigggggghhhhhhhhhhhhhh.
===

Implicitly condoning stupidity since 2001.
New Does PHP have the equivalent of 'use strict;'?
The (mis)feature that you describe is in Perl as well. There it is called "The Poetry Optimization". But Perl has the strict pragma that turns it off and flags barewords that aren't something else as syntax errors.

Does PHP have any similar feature for avoiding targeting your own feet?

The bigger lesson is that embedding if tests is the wrong way to go for compatibility. Read [link|http://www.kerneltraffic.org/kernel-traffic/kt20000501_65.html#5|http://www.kerneltra...0000501_65.html#5] and then apply the lesson to any other language you are in.

The way that I do development switches is to have an initialization section that sets key variables (like which database to connect to) based on what environment you're in. It then connects to the database named in the variable. In this case that would have kept the code from successfully running in development, and therefore caught the error before it got into production.

You also don't need to worry about whether someone slipped something important into an if condition and didn't duplicate it properly. That type of error just goes away.

Cheers,
Ben
To deny the indirect purchaser, who in this case is the ultimate purchaser, the right to seek relief from unlawful conduct, would essentially remove the word consumer from the Consumer Protection Act
- [link|http://www.techworld.com/opsys/news/index.cfm?NewsID=1246&Page=1&pagePos=20|Nebraska Supreme Court]
New or Option Explicit for the VB world :-)
Seems PHP doesn't have a use strict type thing but apparently you can set it to report it as an error during runtime:

[link|http://www.faqts.com/knowledge_base/view.phtml/aid/651/fid/38|The closest thing to 'strict' in PHP is setting error_reporting to E_ALL.]
New Trying to figure out how I can use this
His solution is that when there needs to be a compatibility layer, it should be back-ported to the old code. We have a huge collection of code that is all effectively dynamically linked at run time. And no test cases or regression-testing scripts. Globally back-porting a change in the way we handle our DB environment would take weeks. (Not that I don't want to do it.)

The problem we had today is because we are trying to move to a sane environment where all of our database connections[1] use the same environment. This case was just a poor implementation of the beginnings of a good idea.


[1] Why "connections", plural? If you look through our older code, every function that needed a database connection created its own. Even functions that were executed inside of tight loops. If it weren't for the fact that PHP and MySQL conspire to recycle the same connection from one call to the next, we've got reports that attempt to create literally thousands of DB connections for a single page load. Now we pass around one connection per DB server. (Our version of MySQL doesn't do cross-server joins, so we still need one connection per box.)
===

Implicitly condoning stupidity since 2001.
New His solution is more general than that
The basic solution can be read as, Decide the API that you want to program to, create a compatibility layer that supports that API for each platform, program to that compatibility layer. In the simple case the compatibility layer is trivially simple in one case.

If you'll read [link|http://www.oreilly.com/catalog/opensources/book/linus.html|http://www.oreilly.c...s/book/linus.html] you'll note that the solution within Linux for how to support so many architectures takes this exact form, again.

In this case you can follow a strategy like this (written in Perl, badly):
\n# A badly done compatibility layer.\nmy $DATABASE;\nif ($IS_DEVELOPMENT) {\n  ...\n  $DATABASE = 'DEV';\n  ...\n}\nelse {\n  ...\n  $DATABASE = 'PROD';\n}\n\n# and outside of the compatbility layer...\nmy $dbh;\nsub open_connection {\n  unless ($dbh) {\n    # If somebody typoed, there will be no database\n    # to connect to of the name this gets, and things\n    # will (properly) blow up.\n    $dbh = open_database($DATABASE);\n  }\n  return $dbh;\n}\n

Now the error that you had becomes very different. Getting the variable name wrong somewhere results in an instant highly visible crash.

The flaws in how I've written this are many.

For one thing you often want to support cascading defaults since many configuration variables should be the same in development and production. But cascading defaults open you up again to accidentally having something cascade that shouldn't. Therefore have both development and production cascade back to sane defaults. Most configuration items go into the defaults. The few that have to differ do not go into the defaults.

For another you're likely to need at least 3 environments some day. (Development, staging, production.) Build that flexibility in. I've seen multiple ways of doing that. One of the better ones is to build up a hash of hashes. Each sub-hash is a possible configuration. The outer hash is a mapping of environment to configuration variables. In building it up, you make some sub-hashes start as copies of others - right there you have your cascading logic! That is very nice if you, for instance, want to give each developer their own machine with a customized installation to play with.

But for all of its flaws, the above demonstrates the key idea. Have a section devoted to configuration information only. Then don't scatter if-tests around. Instead have other functions that act in a very generic way upon the configuration data.

Cheers,
Ben
To deny the indirect purchaser, who in this case is the ultimate purchaser, the right to seek relief from unlawful conduct, would essentially remove the word consumer from the Consumer Protection Act
- [link|http://www.techworld.com/opsys/news/index.cfm?NewsID=1246&Page=1&pagePos=20|Nebraska Supreme Court]
New Finally had time to reply to this
And the reply is, "Yeah, no shit."
Then don't scatter if-tests around.
The reason it was written this way is that the devel database is not actually a complete snapshot of live. Lots of tables and some whole databases aren't there, so pages break horribly in the devel environment. This should of course be solved by replicating the rest of the db. Instead it was handled by adding a configuration option to the db class to over-ride devel mode and connect to the live server anyway. So the developer then had to track, "For this function I want a connection to the live db, for that function I want a connection to devel."

That stops now. Devel is devel, and if it doesn't work in devel then you fucking fix it.

For another you're likely to need at least 3 environments some day. (Development, staging, production.) ... That is very nice if you, for instance, want to give each developer their own machine with a customized installation to play with.
Actually we've got four:
  • Devel, where each developer has his own vhost and all db connections (starting tomorrow morning) are to the devel db.
  • Stage, for testing (assuming we hire some testers [sub-rant deleted here]), which also (as of tomrrow morning) points to devel db.
  • Cert, for QA (assuming we hire ... oh, I already went there) which points to live data.
  • Live.
===

Implicitly condoning stupidity since 2001.
New Re: Finally had time to reply to this
The thing is, devel needs full-time attention like live, and it never gets that, because it's junk (not really, but...)
-drl
New That's backwards :-(
The reason it was written this way is that the devel database is not actually a complete snapshot of live. Lots of tables and some whole databases aren't there, so pages break horribly in the devel environment. This should of course be solved by replicating the rest of the db...

It sounds like changes have been made directly on live and never propagated back. Which means that you're walking on a highwire twice.

Of course the way that you should do it is write scripts to update dev, and then when you're happy, run them against prod. That way dev either matches prod or is ahead of it. (Data, of course, gets copied from time to time from prod to dev.)

But you know that. Convincing the rest of the company is your problem...

Cheers,
Ben
To deny the indirect purchaser, who in this case is the ultimate purchaser, the right to seek relief from unlawful conduct, would essentially remove the word consumer from the Consumer Protection Act
- [link|http://www.techworld.com/opsys/news/index.cfm?NewsID=1246&Page=1&pagePos=20|Nebraska Supreme Court]
New Gosh, really?
Remember, we didn't have a devel DB until recently. Building a new one from scratch takes one of our report servers out of the rotation for most of a day, so we've been copying stuff "as needed".

Our other problem is that the one person who has access to make changes on the live DBs doesn't use the devel DBs at all.
===

Implicitly condoning stupidity since 2001.
New Gah. I wish that was unusual. :-(
To deny the indirect purchaser, who in this case is the ultimate purchaser, the right to seek relief from unlawful conduct, would essentially remove the word consumer from the Consumer Protection Act
- [link|http://www.techworld.com/opsys/news/index.cfm?NewsID=1246&Page=1&pagePos=20|Nebraska Supreme Court]
New Using PHP since 2001, I see... :(
New Yup, many compilers just leave . .
. . whatever junk was in the asigned space, and have loose rules for true (if it isn't 0 it's true), so unless you initialize it false it'll be true most of the time.
[link|http://www.aaxnet.com|AAx]
New This is why I dislike PHP's set-ness model.
Had I written this, I would have been a lot more defensive and done if( isset(DevelMode) && DevelMode == 'yes' ) or similar.

Wade.

Is it enough to love
Is it enough to breathe
Somebody rip my heart out
And leave me here to bleed
 
Is it enough to die
Somebody save my life
I'd rather be Anything but Ordinary
Please

-- "Anything but Ordinary" by Avril Lavigne.

New Re: This is why I dislike PHP's set-ness model.
Why does any sane idiom allow uninitialized objects to exist? What does this have to do with "set-ness"?
-drl
New PHP and "set" variables.
PHP has a simpler version of The Visual BASIC Variable Problem. In PHP, you can query the symbol table to see if a variable is defined or not. Whilst this seems like a good idea, in practice it's not. It is much easier if the language does not distinguish between a variable not in the symbol table versus containing a special value, usually null. PHP unfortunately evaluates expressions involving non-existent variables uniquely compared to a particular value; this the constant checking that variables "exist" or are "set". When I programmed with PHP, it often drove me up the wall.

(Visual BASIC lets variables have several states other than simply existing with a value. These include Empty and Nothing as well as actually not existing.)

Wade.

Is it enough to love
Is it enough to breathe
Somebody rip my heart out
And leave me here to bleed
 
Is it enough to die
Somebody save my life
I'd rather be Anything but Ordinary
Please

-- "Anything but Ordinary" by Avril Lavigne.

New gawd
Some cutesy idiot's idea of "depth".
-drl
New (Dupe.)

Is it enough to love
Is it enough to breathe
Somebody rip my heart out
And leave me here to bleed
 
Is it enough to die
Somebody save my life
I'd rather be Anything but Ordinary
Please

-- "Anything but Ordinary" by Avril Lavigne.

Expand Edited by static July 21, 2004, 11:37:41 PM EDT
New Just off a 42-minute call, 3 a.m. local time, must sleep












Then tomorrow, must install new orifice on someone's hind quarters.
===

Implicitly condoning stupidity since 2001.
     [ siiiiiiiiiiiiiiiiiiiiiiigggggghhhhhhhhhhhhhh ] - (drewk) - (17)
         Does PHP have the equivalent of 'use strict;'? - (ben_tilly) - (8)
             or Option Explicit for the VB world :-) - (ChrisR)
             Trying to figure out how I can use this - (drewk) - (6)
                 His solution is more general than that - (ben_tilly) - (5)
                     Finally had time to reply to this - (drewk) - (4)
                         Re: Finally had time to reply to this - (deSitter)
                         That's backwards :-( - (ben_tilly) - (2)
                             Gosh, really? - (drewk) - (1)
                                 Gah. I wish that was unusual. :-( -NT - (ben_tilly)
         Using PHP since 2001, I see... :( -NT - (FuManChu)
         Yup, many compilers just leave . . - (Andrew Grygus)
         This is why I dislike PHP's set-ness model. - (static) - (4)
             Re: This is why I dislike PHP's set-ness model. - (deSitter) - (3)
                 PHP and "set" variables. - (static) - (1)
                     gawd - (deSitter)
                 (Dupe.) -NT - (static)
         Just off a 42-minute call, 3 a.m. local time, must sleep - (drewk)

Zeptotechnology is just around the corner!
84 ms