Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
52 changes: 36 additions & 16 deletions sms-backup.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,19 @@
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
# SOFTWARE.

import sys
py = sys.version_info
py3k = py >= (3,0,0)
py25 = py < (2,6,0)

if py3k:
unicode = str
import io
else:
bytes = str
import cStringIO

import csv
import cStringIO
import fnmatch
import json
import logging
Expand All @@ -34,14 +45,23 @@

from datetime import datetime

def encode_str(s,enc='utf8'):
if py3k:
return s
else:
return s.encode(enc)# if isinstance(s, unicode) else bytes(s)

def decode_str(s, enc='utf8', err='strict'):
return s.decode(enc, err) if isinstance(s, bytes) else unicode(s)

# argparse isn't in standard library until 2.7
try:
test = argparse.ArgumentParser()
except NameError:
try:
import argparse
except:
print "argparse required. Try `pip install argparse`."
print("argparse required. Try `pip install argparse`.")
sys.exit(1)

# silence Python 2.6 buggy warnings about Exception.message
Expand Down Expand Up @@ -155,7 +175,7 @@ def format_phone(phone):
phone = "(%s) %s-%s" % (ph[-10:-7], ph[-7:-4], ph[-4:])
elif len(ph) == 11 and ph[0] =='1':
phone = "(%s) %s-%s" % (ph[-10:-7], ph[-7:-4], ph[-4:])
return phone.decode('utf-8')
return decode_str(phone)

def format_address(address):
"""If address is email, leave alone. Otherwise, call format_phone()."""
Expand Down Expand Up @@ -216,7 +236,7 @@ def validate(args):
validate_aliases(args.aliases)
validate_numbers(args.numbers)
except ValueError as err:
print err, '\n'
print(err, '\n')
raise

def find_sms_db():
Expand Down Expand Up @@ -282,7 +302,7 @@ def alias_map(aliases):
m2 = re.search('@', key)
if not m2:
key = trunc(key)
amap[key] = alias.decode('utf-8')
amap[key] = decode_str(alias)
return amap

def build_msg_query(numbers, emails):
Expand Down Expand Up @@ -365,7 +385,7 @@ def convert_date(unix_date, format):
"""Convert unix epoch time string to formatted date string."""
dt = datetime.fromtimestamp(int(unix_date))
ds = dt.strftime(format)
return ds.decode('utf-8')
return decode_str(ds)

def convert_address_imessage(row, me, alias_map):
"""
Expand All @@ -385,7 +405,7 @@ def convert_address_imessage(row, me, alias_map):
outgoing_flags = (36869, 102405)

if isinstance(me, str):
me = me.decode('utf-8')
me = decode_str(me)

# If madrid_handle is phone number, have to truncate it.
email_match = re.search('@', row['madrid_handle'])
Expand Down Expand Up @@ -423,7 +443,7 @@ def convert_address_sms(row, me, alias_map):
3 = 'outgoing'
"""
if isinstance(me, str):
me = me.decode('utf-8')
me = decode_str(me)

tr_address = trunc(row['address'])
if tr_address in alias_map:
Expand Down Expand Up @@ -541,18 +561,18 @@ def msgs_human(messages, header):

msgs = []
if header:
htemplate = u"{0:{1}} | {2:{3}} | {4:{5}} | {6}"
htemplate = "{0:{1}} | {2:{3}} | {4:{5}} | {6}".decode('utf8')
hrow = htemplate.format('Date', date_width, 'From', from_width,
'To', to_width, 'Text')
msgs.append(hrow)
for m in messages:
text = m['text'].replace("\n","\n" + " " * headers_width)
template = u"{0:{1}} | {2:>{3}} | {4:>{5}} | {6}"
template = "{0:{1}} | {2:>{3}} | {4:>{5}} | {6}".decode('utf8')
msg = template.format(m['date'], date_width, m['from'], from_width,
m['to'], to_width, text)
msgs.append(msg)
msgs.append('')
output = '\n'.join(msgs).encode('utf-8')
output = encode_str('\n'.join(msgs))
return output

def msgs_csv(messages, header):
Expand All @@ -562,18 +582,18 @@ def msgs_csv(messages, header):
if header:
writer.writerow(['Date', 'From', 'To', 'Text'])
for m in messages:
writer.writerow([m['date'].encode('utf-8'),
m['from'].encode('utf-8'),
m['to'].encode('utf-8'),
m['text'].encode('utf-8')])
writer.writerow([encode_str(m['date']),
encode_str(m['from']),
encode_str(m['to']),
encode_str(m['text'])])
output = queue.getvalue()
queue.close()
return output

def msgs_json(messages, header=False):
"""Return messages in JSON format"""
output = json.dumps(messages, sort_keys=True, indent=2, ensure_ascii=False)
return output.encode('utf-8')
return encode_str(output)

def output(messages, out_file, format, header):
"""Output messages to out_file in format."""
Expand Down