How to restore deleted WhatsApp Chats
And that’s how this journey started.
only works on android though
What happend?
My client had a conflict with a business partner of her. In her anger she wanted to block her on WhatsApp, so that further conversations have to be formal. But sadly she reported this partner, and if you do that, whatsapp deletes that chat.
What did I tried?
First I tried restoring an old backup with reinstalling WhatsApp and only have that old backup saved. But that didn’t work, WhatsApp just didn’t want to load any backup other than out of google drive.
Thanks to recent changes, on how the google drive backup system works, it isn’t easy/possible to access the backup.
So the only option is to encrypt the local backup. But therefore you need the key. This key is easy accessible – if your phone is rooted. But sadly every other way to access the key without root failed.
How to do it
1. Safe the local backups
Connect the phone to the computer, accept media access and go into the data system.
The backups are stored as /WhatsApp/Databases/msgstore-20XX-XX-XX.1.db.crypt12
or alike, either on the sd card or the internal storage. Better transfer them all to your computer.
The date of the backup is easily readable.
2. Root the phone
To access the key, you need to root your phone. Sadly I can’t help you with that – every phone is different.
But there are a lot of good tutorials out there. Just google for them.
3. Access the key
If the root is successful, go to the play store and download a „root file manager„. Use it to go to the root dictionary of your android. From there just go to /data/data/com.whatsapp/files/key
and copy the „key“ file to the sd card or the internal storage.
Transfer the key file to your computer
4. Decrypt the backup
I used whatcrypt.com to decrypt the backup.
I hope pretty much that they are trustable. But I’m not able to check it.
So use it on you own risk.
Upload your key there and store it. Then go to „Decrypt WhatsApp Database“ and upload the database, that was created before the chat was deleted.
Congrats! You have an sql database in an zip-file! Uncompress the zip-file!
5. Get the data
To access the database I used DB Browser ( sqlitebrowser.org ).
Go to „Browse Data“ and open the Table „message_view“.
There are them, every message you’ve sent.
The interesting columns are
- chat_row_id : Every chat has one id
- from_me : Who sent the message
- timestamp: When was it sent in UNIX in ms
- data: The content of the message
Now you should check the data for chat messages of the lost chat. Now remember the chat_row_id
from this message.
Go to execute SQL and run the following code, but change ?
for the id you found out.
SELECT from_me, timestamp, data FROM message_view WHERE chat_row_id = ?
6. Use the Data
To get to this point I needed 6 hours. So the rest of the trick is pretty dirty – I wanted to finish. The code is terrible, the methods disgusting and the result just okay.
Please don’t judge.
Copy the table into a new excel sheet and safe it as messages.csv
.
I wrote this code to convert the .csv
to a stylized .html
document. The code has a lot of bugs, is pretty bad code and isn’t commented, but it somehow did work.
puts "Start!" mes = File.read("messages.csv").force_encoding('iso-8859-1') pos = 0 res = [] while mes[pos+6] != nil do me = ( mes[pos] == "1" ) pos += 2 time = Time.at(mes[pos,10].to_i) pos += 14 cont = "" while (mes[pos-1,2] != "0;") and (mes[pos-1,2] != "1;") do cont = cont + mes[pos] pos += 1 end pos -= 1 cont = cont.chop.chop if cont[0] == '"' then cont = cont[1,cont.size - 5] end if cont != "" and cont != nil then res.push( {:time => time , :me => me, :content => cont} ) end end html = "" res.each do |i| if i[:me] then html = '<div class="me"><div class="message">' + i[:content] + '</div><div class="time">' + i[:time].to_s[0,19] + '</div></div>' + html else html = '<div class="her"><div class="message">' + i[:content] + '</div><div class="time">' + i[:time].to_s[0,19] + '</div></div>' + html end end pos = 0 while html[pos] != nil do if html[pos] == "\n" html[pos] = "<br>" end pos += 1 end html = '<html><head> <style> html { border-top: solid 20px #005e54; } body { background: #efe7dd url("https://cloud.githubusercontent.com/assets/398893/15136779/4e765036-1639-11e6-9201-67e728e86f39.jpg") repeat; padding: 20px; padding-top: 5px; } .me, .her { margin: 20px; padding: 20px 20px 8px 20px; width: 70%; max-width: 960px; box-shadow: 0px 5px 10px 0px rgba(0,0,0,0.2); } .me { background-color: #e1ffc7; position: relative; left:20%; border-radius: 15px 0px 15px 15px; } .her { background-color: #fefefe; border-radius: 0px 15px 15px 15px; } .message { font-family: "Roboto", sans-serif; width: 90%; max-width: 820px; line-height: 1.2em; } .time { font-family: "Roboto", sans-serif; color: grey; font-size: .7em; margin-top: 8px; text-align: right; } </style> </head><body>' + html + "</body></html>" output = File.open("messages.html","w") output << html.force_encoding('iso-8859-1') output.close puts "Ende"
You need ruby to run it, but if someone wants, I can make it to an .exe
.
This is the pure css for the WhatsApp like looks:
html { border-top: solid 20px #005e54; } body { background: #efe7dd url("https://cloud.githubusercontent.com/assets/398893/15136779/4e765036-1639-11e6-9201-67e728e86f39.jpg") repeat; padding: 20px; padding-top: 5px; } .me, .her { margin: 20px; padding: 20px 20px 8px 20px; width: 70%; max-width: 960px; box-shadow: 0px 5px 10px 0px rgba(0,0,0,0.2); } .me { background-color: #e1ffc7; position: relative; left:20%; border-radius: 15px 0px 15px 15px; } .her { background-color: #fefefe; border-radius: 0px 15px 15px 15px; } .message { font-family: "Roboto", sans-serif; width: 90%; max-width: 820px; line-height: 1.2em; } .time { font-family: "Roboto", sans-serif; color: grey; font-size: .7em; margin-top: 8px; text-align: right; }
And thats how the .html
looks like:
<html><head> <style> html { border-top: solid 20px #005e54; } body { background: #efe7dd url("https://cloud.githubusercontent.com/assets/398893/15136779/4e765036-1639-11e6-9201-67e728e86f39.jpg") repeat; padding: 20px; padding-top: 5px; } .me, .her { margin: 20px; padding: 20px 20px 8px 20px; width: 70%; max-width: 960px; box-shadow: 0px 5px 10px 0px rgba(0,0,0,0.2); } .me { background-color: #e1ffc7; position: relative; left:20%; border-radius: 15px 0px 15px 15px; } .her { background-color: #fefefe; border-radius: 0px 15px 15px 15px; } .message { font-family: "Roboto", sans-serif; width: 90%; max-width: 820px; line-height: 1.2em; } .time { font-family: "Roboto", sans-serif; color: grey; font-size: .7em; margin-top: 8px; text-align: right; } </style> </head> <body> <div class="her"><div class="message">Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna <br> aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takim</div><div class="time">2020-03-14 08:08:07</div></div> <div class="her"><div class="message">Lorem ipsum dolor</div><div class="time">2020-03-08 46:04:42</div></div> <div class="me"><div class="message">Lorem ipsum dolor sit amet, consetetur sadipscing elitr</div><div class="time">2020-03-06 19:46:58</div></div> <div class="her"><div class="message">Lorem ipsum dolor sit amet, sadipscing elitr</div><div class="time">2020-03-06 18:42:16</div></div> <div class="me"><div class="message">Lorem ipsum dolor sit amet, consetetur sadipscing elitr</div><div class="time">2020-03-06 18:49:48</div></div> <div class="her"><div class="message">Lorem ipsum dolor sit amet, consetetur sadipscing elitr</div><div class="time">2020-03-06 18:45:57</div></div></body> </html>
I hope I could help!