Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.

14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
14 лет назад
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641
  1. # util __init__.py
  2. import webnotes
  3. user_time_zone = None
  4. month_name = ['','Jan','Feb','Mar','Apr','May','Jun','Jul','Aug','Sep','Oct','Nov','Dec']
  5. month_name_full = ['','January','February','March','April','May','June','July','August','September','October','November','December']
  6. no_value_fields = ['Section Break', 'Column Break', 'HTML', 'Table', 'FlexTable', 'Button', 'Image', 'Graph']
  7. default_fields = ['doctype','name','owner','creation','modified','modified_by','parent','parentfield','parenttype','idx','docstatus']
  8. def getCSVelement(v):
  9. """
  10. Returns the CSV value of `v`, For example:
  11. * apple becomes "apple"
  12. * hi"there becomes "hi""there"
  13. """
  14. v = cstr(v)
  15. if not v: return ''
  16. if (',' in v) or ('\n' in v) or ('"' in v):
  17. if '"' in v: v = v.replace('"', '""')
  18. return '"'+v+'"'
  19. else: return v or ''
  20. def extract_email_id(s):
  21. """
  22. Extract email id from email header format
  23. """
  24. if '<' in s:
  25. s = s.split('<')[1].split('>')[0]
  26. if s:
  27. s = s.strip().lower()
  28. return s
  29. def validate_email_add(email_str):
  30. """
  31. Validates the email string
  32. """
  33. s = extract_email_id(email_str)
  34. import re
  35. #return re.match("^[a-zA-Z0-9._%-]+@[a-zA-Z0-9._%-]+.[a-zA-Z]{2,6}$", email_str)
  36. return re.match("[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?", s)
  37. def sendmail(recipients, sender='', msg='', subject='[No Subject]', parts=[], cc=[], attach=[]):
  38. """
  39. Send an email. For more details see :func:`email_lib.sendmail`
  40. """
  41. import webnotes.utils.email_lib
  42. return email_lib.sendmail(recipients, sender, msg, subject, parts, cc, attach)
  43. def generate_hash():
  44. """
  45. Generates random hash for session id
  46. """
  47. import hashlib, time
  48. return hashlib.sha224(str(time.time())).hexdigest()
  49. def db_exists(dt, dn):
  50. return webnotes.conn.sql('select name from `tab%s` where name="%s"' % (dt, dn))
  51. def load_json(arg):
  52. # already a dictionary?
  53. if type(arg)!=str:
  54. return arg
  55. try: import json
  56. except: import simplejson as json
  57. #return json.loads(unicode(arg, 'iso-8859-15'))
  58. return json.loads(arg)
  59. # Get Traceback
  60. # ==============================================================================
  61. def getTraceback():
  62. """
  63. Returns the traceback of the Exception
  64. """
  65. import sys, traceback, string
  66. type, value, tb = sys.exc_info()
  67. body = "Traceback (innermost last):\n"
  68. list = traceback.format_tb(tb, None) + traceback.format_exception_only(type, value)
  69. body = body + "%-20s %s" % (string.join(list[:-1], ""), list[-1])
  70. if webnotes.logger:
  71. webnotes.logger.error('Db:'+(webnotes.conn and webnotes.conn.cur_db_name or '') + ' - ' + body)
  72. return body
  73. # Log
  74. # ==============================================================================
  75. def log(event, details):
  76. webnotes.logger.info(details)
  77. # Date and Time
  78. # ==============================================================================
  79. def getdate(string_date):
  80. """
  81. Coverts string date (yyyy-mm-dd) to datetime.date object
  82. """
  83. import datetime
  84. if type(string_date)==unicode:
  85. string_date = str(string_date)
  86. if type(string_date) in (datetime.datetime, datetime.date):
  87. return string_date
  88. if ' ' in string_date:
  89. string_date = string_date.split(' ')[0]
  90. t = string_date.split('-')
  91. if len(t)==3:
  92. return datetime.date(cint(t[0]), cint(t[1]), cint(t[2]))
  93. else:
  94. return ''
  95. def add_days(date, days, format='string'):
  96. """
  97. Adds `days` to the given `string_date`
  98. """
  99. import datetime
  100. if not date:
  101. date = now_datetime()
  102. if type(date) not in (datetime.datetime, datetime.date):
  103. date = getdate(date)
  104. dt = date + datetime.timedelta(days)
  105. if format=='string':
  106. return dt.strftime('%Y-%m-%d')
  107. else:
  108. return dt
  109. def add_months(string_date, months):
  110. import datetime
  111. return webnotes.conn.sql("select DATE_ADD('%s',INTERVAL '%s' MONTH)" % (getdate(string_date),months))[0][0]
  112. def add_years(string_date, years):
  113. import datetime
  114. return webnotes.conn.sql("select DATE_ADD('%s',INTERVAL '%s' YEAR)" % (getdate(string_date),years))[0][0]
  115. def date_diff(string_ed_date, string_st_date=None):
  116. import datetime
  117. return webnotes.conn.sql("SELECT DATEDIFF('%s','%s')" %(getdate(string_ed_date), getdate(string_st_date)))[0][0]
  118. def now_datetime():
  119. global user_time_zone
  120. from datetime import datetime
  121. from pytz import timezone
  122. # get localtime
  123. if not user_time_zone:
  124. user_time_zone = webnotes.conn.get_value('Control Panel', None, 'time_zone') or 'Asia/Calcutta'
  125. # convert to UTC
  126. utcnow = timezone('UTC').localize(datetime.utcnow())
  127. # convert to user time zone
  128. return utcnow.astimezone(timezone(user_time_zone))
  129. def now():
  130. """
  131. Returns `time.strftime('%Y-%m-%d %H:%M:%S')`
  132. """
  133. return now_datetime().strftime('%Y-%m-%d %H:%M:%S')
  134. def nowdate():
  135. """
  136. Returns time.strftime('%Y-%m-%d')
  137. """
  138. return now_datetime().strftime('%Y-%m-%d')
  139. def get_first_day(dt, d_years=0, d_months=0):
  140. """
  141. Returns the first day of the month for the date specified by date object
  142. Also adds `d_years` and `d_months` if specified
  143. """
  144. import datetime
  145. # d_years, d_months are "deltas" to apply to dt
  146. y, m = dt.year + d_years, dt.month + d_months
  147. a, m = divmod(m-1, 12)
  148. return datetime.date(y+a, m+1, 1)
  149. def get_last_day(dt):
  150. """
  151. Returns last day of the month using:
  152. `get_first_day(dt, 0, 1) + datetime.timedelta(-1)`
  153. """
  154. import datetime
  155. return get_first_day(dt, 0, 1) + datetime.timedelta(-1)
  156. user_format = None
  157. """
  158. User format specified in :term:`Control Panel`
  159. Examples:
  160. * dd-mm-yyyy
  161. * mm-dd-yyyy
  162. * dd/mm/yyyy
  163. """
  164. def formatdate(string_date):
  165. """
  166. Convers the given string date to :data:`user_format`
  167. """
  168. global user_format
  169. if not user_format:
  170. user_format = webnotes.conn.get_value('Control Panel', None, 'date_format')
  171. d = string_date.split('-');
  172. out = user_format
  173. return out.replace('dd', ('%.2i' % cint(d[2]))).replace('mm', ('%.2i' % cint(d[1]))).replace('yyyy', d[0])
  174. def dict_to_str(args, sep='&'):
  175. """
  176. Converts a dictionary to URL
  177. """
  178. import urllib
  179. t = []
  180. for k in args.keys():
  181. t.append(str(k)+'='+urllib.quote(str(args[k] or '')))
  182. return sep.join(t)
  183. def timestamps_equal(t1, t2):
  184. """Returns true if same the two string timestamps are same"""
  185. scrub = lambda x: x.replace(':', ' ').replace('-',' ').split()
  186. t1, t2 = scrub(t1), scrub(t2)
  187. if len(t1) != len(t2):
  188. return
  189. for i in range(len(t1)):
  190. if t1[i]!=t2[i]:
  191. return
  192. return 1
  193. def global_date_format(date):
  194. import datetime
  195. if type(date) in (str, unicode):
  196. date = getdate(date)
  197. return date.strftime('%d') + ' ' + month_name_full[int(date.strftime('%m'))] + ' ' + date.strftime('%Y')
  198. # Datatype
  199. # ==============================================================================
  200. def isNull(v):
  201. """
  202. Returns true if v='' or v is `None`
  203. """
  204. return (v=='' or v==None)
  205. def has_common(l1, l2):
  206. """
  207. Returns true if there are common elements in lists l1 and l2
  208. """
  209. for l in l1:
  210. if l in l2:
  211. return 1
  212. return 0
  213. def flt(s):
  214. """
  215. Convert to float (ignore commas)
  216. """
  217. if type(s)==str: # if string
  218. s = s.replace(',','')
  219. try: tmp = float(s)
  220. except: tmp = 0
  221. return tmp
  222. def cint(s):
  223. """
  224. Convert to integer
  225. """
  226. try: tmp = int(float(s))
  227. except: tmp = 0
  228. return tmp
  229. def cstr(s):
  230. """
  231. Convert to string
  232. """
  233. if type(s) in (str, unicode):
  234. return s
  235. elif s==None:
  236. return ''
  237. else:
  238. return str(s)
  239. def str_esc_quote(s):
  240. """
  241. Escape quotes
  242. """
  243. if s==None:return ''
  244. return s.replace("'","\'")
  245. def replace_newlines(s):
  246. """
  247. Replace newlines by '<br>'
  248. """
  249. if s==None:return ''
  250. return s.replace("\n","<br>")
  251. # ==============================================================================
  252. def parse_val(v):
  253. """
  254. Converts to simple datatypes from SQL query results
  255. """
  256. import datetime
  257. try: import decimal # for decimal Python 2.5 (?)
  258. except: pass
  259. if type(v)==datetime.date:
  260. v = str(v)
  261. elif type(v)==datetime.timedelta:
  262. v = ':'.join(str(v).split(':')[:2])
  263. elif type(v)==datetime.datetime:
  264. v = str(v)
  265. elif type(v)==long: v=int(v)
  266. try:
  267. if type(v)==decimal.Decimal: v=float(v)
  268. except: pass
  269. return v
  270. # ==============================================================================
  271. def fmt_money(amount, fmt = '%.2f'):
  272. """
  273. Convert to string with commas for thousands, millions etc
  274. """
  275. curr = webnotes.conn.get_value('Control Panel', None, 'currency_format') or 'Millions'
  276. val = 2
  277. if curr == 'Millions': val = 3
  278. if cstr(amount).find('.') == -1: temp = '00'
  279. else: temp = cstr(amount).split('.')[1]
  280. l = []
  281. minus = ''
  282. if flt(amount) < 0: minus = '-'
  283. amount = ''.join(cstr(amount).split(','))
  284. amount = cstr(abs(flt(amount))).split('.')[0]
  285. # main logic
  286. if len(cstr(amount)) > 3:
  287. nn = amount[len(amount)-3:]
  288. l.append(nn)
  289. amount = amount[0:len(amount)-3]
  290. while len(cstr(amount)) > val:
  291. nn = amount[len(amount)-val:]
  292. l.insert(0,nn)
  293. amount = amount[0:len(amount)-val]
  294. if len(amount) > 0: l.insert(0,amount)
  295. amount = ','.join(l)+'.'+temp
  296. amount = minus + amount
  297. return amount
  298. #
  299. # convet currency to words
  300. #
  301. def money_in_words(number, main_currency = None, fraction_currency=None):
  302. """
  303. Returns string in words with currency and fraction currency.
  304. """
  305. d = get_defaults()
  306. if not main_currency:
  307. main_currency = d.get('currency', 'INR')
  308. if not fraction_currency:
  309. fraction_currency = d.get('fraction_currency', 'paise')
  310. n = str(flt(number))
  311. main, fraction = n.split('.')
  312. if len(fraction)==1: fraction += '0'
  313. out = main_currency + ' ' + in_words(main).title()
  314. if cint(fraction):
  315. out = out + ' and ' + in_words(fraction).title() + ' ' + fraction_currency
  316. return out + ' only.'
  317. #
  318. # convert number to words
  319. #
  320. def in_words(integer):
  321. """
  322. Returns string in words for the given integer.
  323. """
  324. in_million = webnotes.conn.get_value('Control Panel',None,'currency_format')=='Millions' and 1 or 0
  325. n=int(integer)
  326. known = {0: 'zero', 1: 'one', 2: 'two', 3: 'three', 4: 'four', 5: 'five', 6: 'six', 7: 'seven', 8: 'eight', 9: 'nine', 10: 'ten',
  327. 11: 'eleven', 12: 'twelve', 13: 'thirteen', 14: 'fourteen', 15: 'fifteen', 16: 'sixteen', 17: 'seventeen', 18: 'eighteen',
  328. 19: 'nineteen', 20: 'twenty', 30: 'thirty', 40: 'forty', 50: 'fifty', 60: 'sixty', 70: 'seventy', 80: 'eighty', 90: 'ninety'}
  329. def psn(n, known, xpsn):
  330. import sys;
  331. if n in known: return known[n]
  332. bestguess, remainder = str(n), 0
  333. if n<=20:
  334. print >>sys.stderr, n, "How did this happen?"
  335. assert 0
  336. elif n < 100:
  337. bestguess= xpsn((n//10)*10, known, xpsn) + '-' + xpsn(n%10, known, xpsn)
  338. return bestguess
  339. elif n < 1000:
  340. bestguess= xpsn(n//100, known, xpsn) + ' ' + 'hundred'
  341. remainder = n%100
  342. else:
  343. if in_million:
  344. if n < 1000000:
  345. bestguess= xpsn(n//1000, known, xpsn) + ' ' + 'thousand'
  346. remainder = n%1000
  347. elif n < 1000000000:
  348. bestguess= xpsn(n//1000000, known, xpsn) + ' ' + 'million'
  349. remainder = n%1000000
  350. else:
  351. bestguess= xpsn(n//1000000000, known, xpsn) + ' ' + 'billion'
  352. remainder = n%1000000000
  353. else:
  354. if n < 100000:
  355. bestguess= xpsn(n//1000, known, xpsn) + ' ' + 'thousand'
  356. remainder = n%1000
  357. elif n < 10000000:
  358. bestguess= xpsn(n//100000, known, xpsn) + ' ' + 'lakh'
  359. remainder = n%100000
  360. else:
  361. bestguess= xpsn(n//10000000, known, xpsn) + ' ' + 'crore'
  362. remainder = n%10000000
  363. if remainder:
  364. if remainder >= 100:
  365. comma = ','
  366. else:
  367. comma = ''
  368. return bestguess + comma + ' ' + xpsn(remainder, known, xpsn)
  369. else:
  370. return bestguess
  371. return psn(n, known, psn)
  372. # Get Defaults
  373. # ==============================================================================
  374. def get_defaults(key=None):
  375. """
  376. Get dictionary of default values from the :term:`Control Panel`, or a value if key is passed
  377. """
  378. if key:
  379. res = webnotes.conn.sql('select defvalue from `tabDefaultValue` where parent = "Control Panel" and defkey=%s', key)
  380. return res and res[0][0] or None
  381. else:
  382. res = webnotes.conn.sql('select defkey, defvalue from `tabDefaultValue` where parent = "Control Panel"')
  383. d = {}
  384. for rec in res:
  385. d[rec[0]] = rec[1] or ''
  386. return d
  387. def set_default(key, val):
  388. """
  389. Set / add a default value to :term:`Control Panel`
  390. """
  391. res = webnotes.conn.sql('select defkey from `tabDefaultValue` where defkey="%s" and parent = "Control Panel"' % key)
  392. if res:
  393. webnotes.conn.sql('update `tabDefaultValue` set defvalue="%s" where parent = "Control Panel" and defkey="%s"' % (val, key))
  394. else:
  395. from webnotes.model.doc import Document
  396. d = Document('DefaultValue')
  397. d.parent = 'Control Panel'
  398. d.parenttype = 'Control Panel'
  399. d.parentfield = 'system_defaults'
  400. d.defkey = key
  401. d.defvalue = val
  402. d.save(1)
  403. #
  404. # Clear recycle bin
  405. #
  406. def clear_recycle_bin():
  407. sql = webnotes.conn.sql
  408. tl = sql('show tables')
  409. total_deleted = 0
  410. for t in tl:
  411. fl = [i[0] for i in sql('desc `%s`' % t[0])]
  412. if 'name' in fl:
  413. total_deleted += sql("select count(*) from `%s` where name like '__overwritten:%%'" % t[0])[0][0]
  414. sql("delete from `%s` where name like '__overwritten:%%'" % t[0])
  415. if 'parent' in fl:
  416. total_deleted += sql("select count(*) from `%s` where parent like '__oldparent:%%'" % t[0])[0][0]
  417. sql("delete from `%s` where parent like '__oldparent:%%'" % t[0])
  418. total_deleted += sql("select count(*) from `%s` where parent like 'oldparent:%%'" % t[0])[0][0]
  419. sql("delete from `%s` where parent like 'oldparent:%%'" % t[0])
  420. total_deleted += sql("select count(*) from `%s` where parent like 'old_parent:%%'" % t[0])[0][0]
  421. sql("delete from `%s` where parent like 'old_parent:%%'" % t[0])
  422. return "%s records deleted" % str(int(total_deleted))
  423. # Send Error Report
  424. # ==============================================================================
  425. def send_error_report():
  426. sql = webnotes.conn.sql
  427. m = ''
  428. acc_id = webnotes.conn.get_value('Control Panel',None,'account_id') or ''
  429. if acc_id: m = 'Account Id : '+acc_id
  430. form = webnotes.form
  431. err_msg = '''
  432. %s <br>
  433. Comment: %s
  434. Err Msg : %s
  435. ''' % (m, form.getvalue('msg') or '', form.getvalue('err_msg'))
  436. sendmail([webnotes.conn.get_value('Control Panel',None,'support_email_id') or 'support@iwebnotes.com'], sender=webnotes.session['user'], msg=err_msg, subject='Error Report '+m)
  437. # Dictionary utils
  438. # ==============================================================================
  439. def remove_blanks(d):
  440. """
  441. Returns d with empty ('' or None) values stripped
  442. """
  443. empty_keys = []
  444. for key in d:
  445. if d[key]=='' or d[key]==None:
  446. # del d[key] raises runtime exception, using a workaround
  447. empty_keys.append(key)
  448. for key in empty_keys:
  449. del d[key]
  450. return d
  451. def pprint_dict(d, level=1, no_blanks=True):
  452. """
  453. Pretty print a dictionary with indents
  454. """
  455. if no_blanks:
  456. remove_blanks(d)
  457. # make indent
  458. indent, ret = '', ''
  459. for i in range(0,level): indent += '\t'
  460. # add lines
  461. comment, lines = '', []
  462. kl = d.keys()
  463. kl.sort()
  464. # make lines
  465. for key in kl:
  466. if key != '##comment':
  467. tmp = {key: d[key]}
  468. lines.append(indent + str(tmp)[1:-1] )
  469. # add comment string
  470. if '##comment' in kl:
  471. ret = ('\n' + indent) + '# ' + d['##comment'] + '\n'
  472. # open
  473. ret += indent + '{\n'
  474. # lines
  475. ret += indent + ',\n\t'.join(lines)
  476. # close
  477. ret += '\n' + indent + '}'
  478. return ret
  479. def get_common(d1,d2):
  480. """
  481. returns (list of keys) the common part of two dicts
  482. """
  483. return [p for p in d1 if p in d2 and d1[p]==d2[p]]
  484. def get_common_dict(d1, d2):
  485. """
  486. return common dictionary of d1 and d2
  487. """
  488. ret = {}
  489. for key in d1:
  490. if key in d2 and d2[key]==d1[key]:
  491. ret[key] = d1[key]
  492. return ret
  493. def get_diff_dict(d1, d2):
  494. """
  495. return common dictionary of d1 and d2
  496. """
  497. diff_keys = set(d2.keys()).difference(set(d1.keys()))
  498. ret = {}
  499. for d in diff_keys: ret[d] = d2[d]
  500. return ret
  501. def get_file_timestamp(fn):
  502. """
  503. Returns timestamp of the given file
  504. """
  505. import os
  506. from webnotes.utils import cint
  507. try:
  508. return str(cint(os.stat(fn).st_mtime))
  509. except OSError, e:
  510. if e.args[0]!=2:
  511. raise e
  512. else:
  513. return None