I get to hear that a lot: that LOCK TABLES with MyISAM is some sort of replacement for transactions; some model we can work with which gives us 'transactional flavor'.
It isn't, and here's why.
When we speak of a transactional database/engine, we check out its ACID compliance. Let's break out the ACID and see what LOCK TABLES provides us with:
- A: Atomicity. MyISAM does not provide atomicity. If we have LOCK TABLES followed by two statements, then closed by UNLOCK TABLES, then it follows that a crash between the two statements will have the first one applied, the second one not not applied. No mechanism ensures an "all or nothing" behavior.
- C: Consistency. An error in a statement would roll back the entire transaction in a transactional database. This won't work on MyISAM: every statement is "committed" immediately.
- I: Isolation. Without LCOK TABLES, working with MyISAM resembles using the read uncommitted, or dirty read isolation level. With LOCK TABLES - it depends. If you were to use LOCK TABLES ... WRITE on all tables in all statements, you would get the serializable isolation level. Actually it would be more than serializable. It would be truely serial.
- D: Durability. Did the INSERT succeed? And did the power went down just after? MyISAM provides not guarantees that the data will be there.
So of all ACID properties, the only thing we could get is a serializable isolation level, and that, too, only if we used LOCK TABLES ... WRITE practically everywhere.
Where does the notion come from, then?
There's one thing which LOCK TABLES does help us with: race conditions. It effectively creates a mutex block. The same effect could be achieved when using GET_LOCK() and RELEASE_LOCK(). Perhaps this is the source of confusion.