Three logicians walk into a bar. The bartender goes, three beers?
The first logician says: I don't know.
The second logician says: I don't know.
The third logician says: yes.
Three logicians walk into a bar. The bartender goes, three beers?
The first logician says: I don't know.
The second logician says: I don't know.
The third logician says: yes.
So in my spare time, I've had a project thrust upon me that needs a site built. As a PHP guy, I figured, sure. I'll help. So they gave me FTP credentials to have a look. Of course, this "framework" is some of the shittiest code I've ever seen. Those of you who have had the displeasure of having to work with legacy PHP code will appreciate the following:
$ grep -r 'error_reporting(0)' | wc -l
26
Can someone please brexit my life for me right now? I'm not even being paid for this. :(
So at work, we have certain things that users can process. I can't go into what sort of things without giving away the industry I work in. Let's say these things are stories, and they are divided into chapters, and each chapter has one or more paragraphs. Basically, our client has customers, the customer gives out licenses to their customers. The licensees have several people assigned to them, we'll call those storytellers. The storytellers supply the end users with stories.
We built a feature for our client to prepare her own template stories. She can allocate those to some or all of her customers, and their licensees' storytellers can then make a copy and then edit the story, or simply use it as-is. I personally think this is a great feature, considering the business our client is in. Anyway, yesterday our client called. She said, "Hey toon, those three stories we've been writing, I've tried to couple them to WritaCorp but it seems to be taking a long time." Sure enough, turns out it takes three and a half minutes. For a single story to get coupled to a single customer, their biggest one, with about 60 licenses.
So I took the debug log that the operation dumped, and saw that it took not one, not two, not three, not four, not five, not six, but seven fucking thousand (7,000) database queries. I spent some time alleviating the problem and turned those 7,000 into 3,600 in about half an hour, shaving about a minute off the running time. The decoupling, the reverse operation, took about 4,500 queries and I got that down to about a dozen.
Why o toon, you might ask, are so many database queries needed: after all you still have 3,600 left? Well, perhaps considering how this coupling was implemented may illuminate things.
In the olden days, there used to just be stories, with chapters and pararaphs. Then templates arrived, adding a column to the story table that equals 1 if and only if it's a template. Also to the stories were added a license ID column, and a customer ID column. So you can have a story template for just one license, or a story template that's available to all licensees of the customer. So far so reasonably decently.
Subsequently, a co-employee who is no longer with the company, was tasked with giving our client the ability to make template stories that she can then couple to customers, or some/all of their licenses. A set of screens was added that gives our client the means to do this. What happens when you couple a story template to a customer is, it gets duplicated and added to each license. So in the case of WritaCorp, 60 copies were made, each with a set of chapters, and each of those with a set of paragraphs, all of which were inserted into the database separately. This is why I was able to easily halve the number of queries: I simply combined thousands of INSERT queries into a single one.
"Foreign key constraints? We don't need no stinkin' foreign key constraints. We'll just insert one row, get the inserted ID back, then insert all the rows in the other table. If they have "children" then we'll obviously have to do the same for them!" Of course, even without foreign key constraints there may be several better ways to go about this, but this, apparently, is how this sort of thing is done.
Wait, you shout! What happens if the client changes something in the story template? All those duplicates will need to change along with it! Well, my ex-coworker thought of that in advance. He added a "set ID" column to the story template table, but there is no such thing as a "set" table in our application. What this column does, is group all of those template stories together. That way, you can find the templates that belong together! So if the client changes the title of a chapter, why you just get all of the chapters of all of the other templates with the same set ID, but just the ones with the same position, and then update those (one by one, of course). Rearranging chapters becomes a great exercise in creative bookkeeping, and of course there are other WTFs that arise from this implementation.
Now, I thoroughly dislike this sort of thing, because I hate what I like to call "bookkeeping code". With an extra hour of thinking, probably making the thought process span about 65 minutes, my ex-coworker should have come up with a much better solution. See, the whole premise behind this bookkeeping code my coworker wrote, is of course that you're somehow guaranteed to start out with a consistent state, you do something (without using transactions or anything like that), ergo you're sure to end up with the state still being consistent afterwards.
Now recall that I said the coupling took three and a half minutes. Our server (a PHP 4 box, for a whole other extra bonus WTF) is set to timeout any scripts at four minutes. So if someone decided to refresh the page because editing a story took too long, or the script timed out after only 6,000 out of 7,000 queries finished, you're stuck with an inconsistent database state. Nobody realizes this at the time of course, and our client, thinking we built something that works, merrily keeps editing, only making the database state more inconsistent, after which this sort of situation turns into what I believe Donald Knuth, in many of his seminal works, terms a "clusterfuck".
I don't even know how to unmangle this mess without spending several days on rethinking and rewriting whole parts of our application.
The hidden premise here seems to be that you need to be good at Windows to be a good developer, or so I thought at first.
Thinking about it more made me realize that what you guys all seem to be agreeing on is not that the dude is a bad developer for not knowing how to change the extension, but for not being able to find out, and coping with that by writing a shitty hack instead.
If there's anything I've learned in my short career, it's that what makes a good developer is being able to solve problems you've never seen before, because of a thoroughly developery mindset.
So I'm finding that one page of a site I'm working on, hangs. It only happens locally, not online (thank goodness). I'm working with PHP4 so I can't get XDebug and stuff, this is legacy code so no logging or anything. So what do I do? I put an exit('test'); statement in and move it around. Finally, I come to the point where I find out that this doesn't hang:
exit('test'); if (extension_loaded('curl')) { // do stuff } else { // do other stuff }
And this does:
if (extension_loaded('curl')) { exit('test'); // do stuff } else { // do other stuff }
My conclusion: HOLY SHIT the extension_loaded function hangs my site! So I spend about half an hour googling, before realizing the problem is inside the else clause. Can I hand my programming license please? :(
... you can apply permission and make sure contractors are actually doing their working and committing their incremental changes somewhere safe instead of the local repo on their C drive.
Situation my company encountered: they employed a developer who was very sloppy, in that he would push code to production without checking it, and not use VSS properly. As I've mentioned in another comment, we're switching to Git at the moment. One reason against switching from VSS, is the "bliss" of file locking and check-in, check-out mentality of having everything at a central hub so at least the boss knows what the guy is doing!
My argument against this was, well, Git won't be much different because the guy will just go from not checking in or checking out, to not committing and pushing, which of course is exactly what happened. They still had production sites that didn't match source control, they were still mile high in regressions and spaghetti code, and they discover that honestly, with VSS it was just the same except at least they could see which files he had checked out, but they discovered that unfortunately they had no magic mirror that looked into his workstation.
You see, he'd just do what I do when I need to work with VSS: flip the read-only bit, do some work, then do a project diff, and check in/out the changes you need to commit all at once. Except he'd skip the checking in/out part.
But in the end they solved the problem!
So what was the solution? What source control software trick saved the day? What productivity management tool did the trick? They canned the guy, that's what.
If your contractors can't be fucked to work with you, hire someone else and state in their contract that they are obligated to manage your code responsibly. This sort of thing should not be enforced by software, but by people.
I find it interesting that you say both "Git may take a while to get used to" and "it's a breeze to use". That's like saying a complicated piece of construction equipment is easy to use because the guy with years of experience is having no problems.
Good analogy, but you're taking my words out of context so it looks like I'm contradicting myself. What I actually said was:
[quote=toon, post:133, topic:3005]Git may take a while to get used to, but if you learn a few commands and get used to a couple of GUI's then it's a breeze to use.[/quote]
That's not a contradiction from where I'm standing.
Take a forklift: I used to drive one for a living. Forklifts definitely take a while to get used to. They handle differently from most other kinds of vehicle you might drive, such as cars or trucks. You need to know a fair bit about the forklift in question to be able to maintain one. There are even things you need to be aware of, to be able to drive one without seriously risking property damage or human injury. So yeah, I'd say you shouldn't be driving a forklift around other people unless you know what you're doing, and that takes a definite amount of effort.
But would I argue that forklifts are not easy to use? No, I wouldn't. In fact, I'd say at least 95% of all adults under 65 could do it if they were so inclined. Of course, I'd also argue that pallet jacks are much easier to use than a forklift. Basically anyone who can walk upright can use those. But if I need to move a tank of water over dozens of yards of pavement through the rain to the next warehouse, why I can do it with both, but I know which tool I'd consider better suited for the job, and it's not the more easily usable one.
Look, this is a forum where people go, "this person should have his keyboard license revoked". Developing software is a craft, there are ways to do it properly and improperly, and some of the best tools you can have in any craft, take time to get used to, and then all of that time pays itself back tenfold. DBMS'es, web servers, debuggers, IDE's, text editors, even web browsers, it's all the same in that respect, they all come with manuals, and I don't see why VCS should be any exception.
Trying to install Bugzilla on a server that only runs the 9 year old Perl version of 5.8.8, which is a whole WTF in and of itself. Anyway, when installing the required modules this happens:
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Please tell me where I can find your apache src
[../apache_x.x/src] ../apache_x.x/src
Can't stat `../apache_x.x/src'
Etcetera etcetera. Good thing I was paying attention so I could hit Ctrl-C, after which the installation went on its merry way.
I hate you, Bugzilla. I hate you, Perl.
Y'know, that's one of the things that gets me wondering: PHP has been around for ages and yet it doesn't seem like anyone has developed much in the way of best practices, patterns and things never-to-do-under-any-circumstances.
You are quite mistaken. 5-10 years ago that was true, but not anymore. The thing is, this standardization is coming from the developer community, not the PHP team itself. There is a number of excellent frameworks out there (e.g. Laravel), and the different framework development teams have banded together to see what can be done standards wise, and have already come up with a few good recommendations, known as PSRs.
Also, there is this. This last one in particular is a great way to see what can be done with PHP these days, and what problems have been solved. It gets thrown at newbies all the time, or at people who have been away from PHP and are looking to see what they've been missing out on.
Don't get me wrong, there's still a lot of cruft out there in terms of shitty code and shitty PHP programmers, but there is also a big, and growing, number of really good developers out there who write solid code riddled with best practices. In PHP, you can do OOP and TDD, there are great build systems and things like Vagrant support PHP out-of-the-box.
I mean, PHP is primarily used for web development and most of the time you're likely to be dealing with a relatively small number of standard problems (DB access, accepting input, display) that really should have been adequately solved by now. However, it seems to me that sensible solutions are drowning in a sea of downright insane ones - including (especially?) mature and well-known software. Why is this?
I don't know that that's true. If you pick a decent framework, all of those things will have good solutions that are present in the framework, and more, such as session encryption, CSRF prevention, caching, and templating. Folks who know what they're doing use them.
And let's not forget that it's entirely possible to write really, really crappy code in any language, with any framework. I understand why PHP is often singled out, but it's not like writing an application riddled with spaghetti code that's full or SQL injection vulnerabilities is mathematically impossible in C#/.NET.
So I'm about to start a project in my spare time for charity; literally for starving children in Africa.
Anyway, about ten actual seconds in, I see this:
$nrs_lookup = array( 1 => "01", 2 => "02", 3 => "03", 4 => "04", 5 => "05", 6 => "06", 7 => "07", 8 => "08", 9 => "09", 10 => "10",
11 => "11", 12 => "12", 13 => "13", 14 => "14", 15 => "15", 16 => "16", 17 => "17", 18 => "18", 19 => "19", 20 => "20",
21 => "21", 22 => "22", 23 => "23", 24 => "24", 25 => "25", 26 => "26", 27 => "27", 28 => "28", 29 => "29", 30 => "30",
31 => "31", 32 => "32", 33 => "33", 34 => "34", 35 => "35", 36 => "26", 37 => "37", 38 => "38", 39 => "39", 40 => "40" );
disgunbegud.gif
A few months ago, I posted this topic: Bookkeeping code or: how I learned to stop worrying and love data duplication.
TL;DR of previous topic: we have an application that among other things, manages "stories" (actually they're not stories, don't want to give away too much), which can have many chapters, which can have many paragraphs. These stories can be linked to clients and their licensees. An ex-coworker thought it would be a good idea to interpret "licenses share stories", as "each license gets a deep copy of the story", resulting in lots of bookkeeping code and thousands of database queries.
I'd already pulled a few tricks out of my top hat and this alleviated the problem, but still, when the client would try to change a chapter title, it would take five minutes. This was basically my fault: I'd written a method that would take one story, delete all the data in the copies, and then repopulate the copied stories. It would get called each time a story got saved. This is the only way I knew how to be sure that the whole bookkeeping code thing didn't cause any bugs. This problem would, of course, only get worse with time unless something was done, and I was just about out of tricks. So I talked to my boss about it, and although he knew a bit about what was causing these screens to be so unresponsive, it turned out that he didn't really realize how bad the problem actually was. So I decided to clue him in, and flat-out recommend that I just yank out the whole godawful mess. And he agreed.
So last week I spent about a day and a half rewriting this stuff. Now we have an extra database table, and also we have 80,000-100,000 fewer records overall, that no longer need all that bookkeeping code to manage them. Many, many known and unknown bugs got squashed. Screens went from thousands of database queries, to like two or three. Git tells me I took 1,151 LOC out and wrote 333 new ones, not including any whitespace changes.
I'll be deploying tomorrow. I did a good thing last week.
I'm a guitar player in my spare time. I'll bet this would work great as a comedy duet.
Talk about distracting images in bug reports.
Also, as someone who likes to read this forum on mobile, thanks for slowing down the thread. /s
I work with legacy PHP code a lot and sometimes I'll spend some time tracking down unused functions and stuff, and big blocks of commented code, and just yank them out. I always figure, they can only serve to confuse people and if someone is very emotionally attached to them they can just go into the Git repo to get them out again.
It might have something to do with VSS being deprecated like A FUCKING DECADE AGO, why the holy shit in hell do people keep bringing up VSS in source control treads as if it were relevant at all? Christ.
Although I wholeheartedly agree with you, the company I work at used VSS until they started having applicants go "fuck this noise" and apply somewhere else. This was a year ago. Faced with the fact that it's probably time to switch somewhere else, they decided to go for Git. Our company is loosely structured into a .NET department and a PHP department, I'm part of the latter. We've been using Git, the .NET guys are still on VSS.
I know it's just an anecdote, but I do feel I need to pipe up here and say that there are jackasses out there who think VSS is awesome and don't want to use anything else, and some of those jackasses are lead developers at companies that employ a dozen people.
Wow. I'll have to try that one out sometime.
I had a cool one in a PHP 4 project the other day. It only happened in production and only for me, because it only happened when a certain variable equaled true, and this variable is used to provide us with debugging information.
When I would write include("somefile.php");
that would take 30 seconds but without the parentheses it would be as fast as I'd expect. And the difference, I'm absolutely sure about this, is in the step where PHP includes the file. It's in the execution of the include statement itself. Still no clue why this happens or how to replicate the problem.
@Zemm said:
@toon said:PHP4TRWTF. Unsupported for at least 5 years, maybe even 13 years.
PHP is bad enough but am ancient one would drive me to ragequit life!
Unfortunately, I'm stuck with PHP 4 for many legacy projects. I actually think 5.2, which our PHP 5 projects use, is old. All the cool PHP people are doing stuff with namespaces. Can't do that with 5.2. If it were up to me, we'd switch to 5.4 or even 5.5.
I don't know about you, but I can think of one great and glorious, quite fundamental difference between men and women right off the top of my head.
<button class="button" id="buttonOK" type="submit">OK</button>
<script type="text/javascript">
document.getElementById("buttonOK").style.display = "none";
</script>
What if 512 posts were made, then one got deleted, then another was made?
I don't see why it's anyone's business what I do in my own local repo. Stuff like that goes in the remote in a receive hook, not in a local pre-commit hook. I want to be able to make shitty test branches or be able to make lots of commits that I may throw away or combine and/or split with rebase -i
.
I'll push things that are ready to be pushed and I think it makes perfect sense that I am not allowed to push whatever I want. But until then I want to be able to do my job without getting nagged by management's mandatory micromanagement tools. I don't want to have someone write a program that keeps checking if I'm making a mistake, before I've made it in any real sense.
TFS works like this too. I see no problem with the paradigm of "Whoa, you better verify your changes before committing them, someone else messed with these files". Otherwise, you get a blind merge and no one verifies that the merged code actually works.
You, as a developer, should be responsible for checking that the code actually works. If nobody's checking that, you who committed the code at the very least are at fault.
In Git, the philosophy is that you can do whatever you want, and then decide what to share by deciding which commits to push to the outside world. So you work, you commit but check your fucking work while you commit, and then if necessary, you merge stuff other people did and proceed to check your fucking merge before you push. In Git, a merge is just a commit with more than one parent, so if you push a merge, you should be responsible.
@TimeBandit yeah, I did in fact remove them first thing, I was getting white screens with no clue why. Quickly set error_reporting
to E_ERROR | E_WARNING
though. Choose your battles and such...
Linux user here, can't reproduce.
Chromium Version 34.0.1847.116 Built on Ubuntu 13.10, running on LinuxMint 16 (260972)
Firefox version 29.0 (according to the dialog it's "for Linux Mint")
I must have gotten that joke from the old forums. Sorry, if I'd remembered that I wouldn't have posted it.
Someone who wants to make a joke about men vs. women.
Also, the gender binary? People engaged in a discussion about gender, where the obvious hidden premisr is that male and female are the only two options, are a pet peeve of mine. In actual fact, there is no such binary and there is a large grey area between, and beside, the two. I personally am a male and I feel like one and am comfortable being one, but many people don't share my feelings about their own respective genders.
Some people are born both male and female, some neither, some feel they are the wrong flavor. And here you are saying everybody is fundamentally the same? Not afaic.
Agreed. 96-99% probably fit one gender fine.
Me neither.
This is a fine joke for poking fun at stereotypes. If you want to go into the reality, then it breaks down. It's all well and good for @Buddy to be all PC about gender, but they should probably either lighten up or make decent arguments, I guess that's my point.
Yesterday at band practice, I explained this to my non-programmer bandmates. I think it's telling that they understood exactly what the WTF was, even though they know nothing about databases or web development.
I guess odds are good that it'll run on 5, but some of it is pretty shitty.
Personally I think you should have to go through a competence test to use frameworks: if you can build something like it yourself, then you get to play with the grown up toys. If you can't, you have no business playing with one.
Yeah, well I don't know about you, or anyone else who uses PHP on here, but I've seen my share of people trying to build "something like it" themselves, and my experience is that people build POS systems when they decide they want to build a framework.
I only learned how it's done by experience and by being exposed to proper frameworks, and I don't see why exposing people to decent software development at an early stage is a bad thing.
Are you suggesting people need to be the next Taylor Otwell to aspire to use Laravel? Because that, being an experienced PHP developer, makes no sense to me whatsoever.
No problem. I think there's some miscommunication here, as you mentioned a pre-commit hook, which I took to mean that this hook would execute locally. I think that the hook that both of us have in mind, is called post-receive in Git.
@bb36e I found 25 instances, excluding legitimate uses such as doc comments and stuff. I also decided to exclude Smarty, because I happen to know that those guys use the @ operator deliberately as a way of writing code that's dirty, but optimized for speed. For instance, if in benchmarking, they find that checking if a file exists and then getting the mtime, is slower than just getting the mtime with an @
, then they'll go for the @
.