Ви не можете вибрати більше 25 тем Теми мають розпочинатися з літери або цифри, можуть містити дефіси (-) і не повинні перевищувати 35 символів.
 
 
 
 
 
 

270 рядки
7.7 KiB

  1. # Copyright (c) 2013, Web Notes Technologies Pvt. Ltd.
  2. # MIT License. See license.txt
  3. from __future__ import unicode_literals
  4. import webnotes
  5. import webnotes.db
  6. import webnotes.utils
  7. import webnotes.profile
  8. import conf
  9. from webnotes.sessions import Session
  10. class HTTPRequest:
  11. def __init__(self):
  12. # Get Environment variables
  13. self.domain = webnotes.get_env_vars('HTTP_HOST')
  14. if self.domain and self.domain.startswith('www.'):
  15. self.domain = self.domain[4:]
  16. # language
  17. self.set_lang(webnotes.get_env_vars('HTTP_ACCEPT_LANGUAGE'))
  18. webnotes.remote_ip = webnotes.get_env_vars('REMOTE_ADDR')
  19. # load cookies
  20. webnotes.cookie_manager = CookieManager()
  21. webnotes.request_method = webnotes.get_env_vars("REQUEST_METHOD")
  22. # override request method. All request to be of type POST, but if _type == "POST" then commit
  23. if webnotes.form_dict.get("_type"):
  24. webnotes.request_method = webnotes.form_dict.get("_type")
  25. del webnotes.form_dict["_type"]
  26. # set db
  27. self.connect()
  28. # login
  29. webnotes.login_manager = LoginManager()
  30. # start session
  31. webnotes.session_obj = Session()
  32. webnotes.session = webnotes.session_obj.data
  33. # check status
  34. if webnotes.conn.get_global("__session_status")=='stop':
  35. webnotes.msgprint(webnotes.conn.get_global("__session_status_message"))
  36. raise webnotes.SessionStopped('Session Stopped')
  37. # load profile
  38. self.setup_profile()
  39. # run login triggers
  40. if webnotes.form_dict.get('cmd')=='login':
  41. webnotes.login_manager.run_trigger('on_login_post_session')
  42. # write out cookies
  43. webnotes.cookie_manager.set_cookies()
  44. def set_lang(self, lang):
  45. import translate
  46. lang_list = translate.get_lang_dict()
  47. lang_list = lang_list and lang_list.values() or []
  48. if not lang:
  49. return
  50. if ";" in lang: # not considering weightage
  51. lang = lang.split(";")[0]
  52. if "," in lang:
  53. lang = lang.split(",")
  54. else:
  55. lang = [lang]
  56. for l in lang:
  57. code = l.strip()
  58. if code in lang_list:
  59. webnotes.lang = code
  60. return
  61. # check if parent language (pt) is setup, if variant (pt-BR)
  62. if "-" in code:
  63. code = code.split("-")[0]
  64. if code in lang_list:
  65. webnotes.lang = code
  66. return
  67. def setup_profile(self):
  68. webnotes.user = webnotes.profile.Profile()
  69. def get_db_name(self):
  70. """get database name from conf"""
  71. return conf.db_name
  72. def connect(self, ac_name = None):
  73. """connect to db, from ac_name or db_name"""
  74. webnotes.conn = webnotes.db.Database(user = self.get_db_name(), \
  75. password = getattr(conf,'db_password', ''))
  76. class LoginManager:
  77. def __init__(self):
  78. if webnotes.form_dict.get('cmd')=='login':
  79. # clear cache
  80. from webnotes.sessions import clear_cache
  81. clear_cache(webnotes.form_dict.get('usr'))
  82. self.authenticate()
  83. self.post_login()
  84. info = webnotes.conn.get_value("Profile", self.user, ["user_type", "first_name", "last_name"], as_dict=1)
  85. if info.user_type=="Website User":
  86. webnotes.response["message"] = "No App"
  87. full_name = " ".join(filter(None, [info.first_name, info.last_name]))
  88. webnotes.response["full_name"] = full_name
  89. webnotes.add_cookies["full_name"] = full_name
  90. else:
  91. webnotes.response['message'] = 'Logged In'
  92. def post_login(self):
  93. self.run_trigger()
  94. self.validate_ip_address()
  95. self.validate_hour()
  96. def authenticate(self, user=None, pwd=None):
  97. if not (user and pwd):
  98. user, pwd = webnotes.form_dict.get('usr'), webnotes.form_dict.get('pwd')
  99. if not (user and pwd):
  100. self.fail('Incomplete login details')
  101. self.check_if_enabled(user)
  102. self.user = self.check_password(user, pwd)
  103. def check_if_enabled(self, user):
  104. """raise exception if user not enabled"""
  105. from webnotes.utils import cint
  106. if user=='Administrator': return
  107. if not cint(webnotes.conn.get_value('Profile', user, 'enabled')):
  108. self.fail('User disabled or missing')
  109. def check_password(self, user, pwd):
  110. """check password"""
  111. user = webnotes.conn.sql("""select `user` from __Auth where `user`=%s
  112. and `password`=password(%s)""", (user, pwd))
  113. if not user:
  114. self.fail('Incorrect password')
  115. else:
  116. return user[0][0] # in correct case
  117. def fail(self, message):
  118. webnotes.response['message'] = message
  119. raise webnotes.AuthenticationError
  120. def run_trigger(self, method='on_login'):
  121. try:
  122. from startup import event_handlers
  123. if hasattr(event_handlers, method):
  124. getattr(event_handlers, method)(self)
  125. except ImportError, e:
  126. pass
  127. cp = webnotes.bean("Control Panel", "Control Panel")
  128. cp.run_method(method)
  129. def validate_ip_address(self):
  130. """check if IP Address is valid"""
  131. ip_list = webnotes.conn.get_value('Profile', self.user, 'restrict_ip', ignore=True)
  132. if not ip_list:
  133. return
  134. ip_list = ip_list.replace(",", "\n").split('\n')
  135. ip_list = [i.strip() for i in ip_list]
  136. for ip in ip_list:
  137. if webnotes.remote_ip.startswith(ip):
  138. return
  139. webnotes.msgprint('Not allowed from this IP Address')
  140. raise webnotes.AuthenticationError
  141. def validate_hour(self):
  142. """check if user is logging in during restricted hours"""
  143. login_before = int(webnotes.conn.get_value('Profile', self.user, 'login_before', ignore=True) or 0)
  144. login_after = int(webnotes.conn.get_value('Profile', self.user, 'login_after', ignore=True) or 0)
  145. if not (login_before or login_after):
  146. return
  147. from webnotes.utils import now_datetime
  148. current_hour = int(now_datetime().strftime('%H'))
  149. if login_before and current_hour > login_before:
  150. webnotes.msgprint('Not allowed to login after restricted hour', raise_exception=1)
  151. if login_after and current_hour < login_after:
  152. webnotes.msgprint('Not allowed to login before restricted hour', raise_exception=1)
  153. def login_as_guest(self):
  154. """login as guest"""
  155. self.user = 'Guest'
  156. self.post_login()
  157. def logout(self, arg='', user=None):
  158. if not user: user = webnotes.session.user
  159. self.run_trigger('on_logout')
  160. if user in ['demo@erpnext.com', 'Administrator']:
  161. webnotes.conn.sql('delete from tabSessions where sid=%s', webnotes.session.get('sid'))
  162. webnotes.cache().delete_value("session:" + webnotes.session.get("sid"))
  163. else:
  164. from webnotes.sessions import clear_sessions
  165. clear_sessions(user)
  166. if user == webnotes.session.user:
  167. webnotes.add_cookies["full_name"] = ""
  168. webnotes.add_cookies["sid"] = ""
  169. class CookieManager:
  170. def __init__(self):
  171. import Cookie
  172. webnotes.cookies = Cookie.SimpleCookie()
  173. self.get_incoming_cookies()
  174. def get_incoming_cookies(self):
  175. import os
  176. cookies = {}
  177. if 'HTTP_COOKIE' in os.environ:
  178. c = os.environ['HTTP_COOKIE']
  179. webnotes.cookies.load(c)
  180. for c in webnotes.cookies.values():
  181. cookies[c.key] = c.value
  182. webnotes.incoming_cookies = cookies
  183. def set_cookies(self):
  184. if not webnotes.session.get('sid'): return
  185. import datetime
  186. # sid expires in 3 days
  187. expires = datetime.datetime.now() + datetime.timedelta(days=3)
  188. expires = expires.strftime('%a, %d %b %Y %H:%M:%S')
  189. webnotes.cookies[b'sid'] = webnotes.session['sid'].encode('utf-8')
  190. webnotes.cookies[b'sid'][b'expires'] = expires.encode('utf-8')
  191. webnotes.cookies[b'country'] = webnotes.session.get("session_country")
  192. def set_remember_me(self):
  193. from webnotes.utils import cint
  194. if not cint(webnotes.form_dict.get('remember_me')): return
  195. remember_days = webnotes.conn.get_value('Control Panel', None,
  196. 'remember_for_days') or 7
  197. import datetime
  198. expires = datetime.datetime.now() + \
  199. datetime.timedelta(days=remember_days)
  200. expires = expires.strftime('%a, %d %b %Y %H:%M:%S')
  201. webnotes.cookies[b'remember_me'] = 1
  202. for k in webnotes.cookies.keys():
  203. webnotes.cookies[k][b'expires'] = expires.encode('utf-8')
  204. def update_password(user, password):
  205. webnotes.conn.sql("""insert into __Auth (user, `password`)
  206. values (%s, password(%s))
  207. on duplicate key update `password`=password(%s)""", (user,
  208. password, password))