Non puoi selezionare più di 25 argomenti Gli argomenti devono iniziare con una lettera o un numero, possono includere trattini ('-') e possono essere lunghi fino a 35 caratteri.
 
 
 
 
 
 

287 righe
8.6 KiB

  1. # Copyright (c) 2012 Web Notes Technologies Pvt Ltd (http://erpnext.com)
  2. #
  3. # MIT License (MIT)
  4. #
  5. # Permission is hereby granted, free of charge, to any person obtaining a
  6. # copy of this software and associated documentation files (the "Software"),
  7. # to deal in the Software without restriction, including without limitation
  8. # the rights to use, copy, modify, merge, publish, distribute, sublicense,
  9. # and/or sell copies of the Software, and to permit persons to whom the
  10. # Software is furnished to do so, subject to the following conditions:
  11. #
  12. # The above copyright notice and this permission notice shall be included in
  13. # all copies or substantial portions of the Software.
  14. #
  15. # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
  16. # INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
  17. # PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  18. # HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
  19. # CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
  20. # OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  21. #
  22. from __future__ import unicode_literals
  23. import webnotes
  24. import webnotes.db
  25. import webnotes.utils
  26. import webnotes.profile
  27. import conf
  28. from webnotes.sessions import Session
  29. class HTTPRequest:
  30. def __init__(self):
  31. # Get Environment variables
  32. self.domain = webnotes.get_env_vars('HTTP_HOST')
  33. if self.domain and self.domain.startswith('www.'):
  34. self.domain = self.domain[4:]
  35. # language
  36. self.set_lang(webnotes.get_env_vars('HTTP_ACCEPT_LANGUAGE'))
  37. webnotes.remote_ip = webnotes.get_env_vars('REMOTE_ADDR')
  38. # load cookies
  39. webnotes.cookie_manager = CookieManager()
  40. webnotes.request_method = webnotes.get_env_vars("REQUEST_METHOD")
  41. # override request method. All request to be of type POST, but if _type == "POST" then commit
  42. if webnotes.form_dict.get("_type"):
  43. webnotes.request_method = webnotes.form_dict.get("_type")
  44. del webnotes.form_dict["_type"]
  45. # set db
  46. self.connect()
  47. # login
  48. webnotes.login_manager = LoginManager()
  49. # start session
  50. webnotes.session_obj = Session()
  51. webnotes.session = webnotes.session_obj.data
  52. # check status
  53. if webnotes.conn.get_global("__session_status")=='stop':
  54. webnotes.msgprint(webnotes.conn.get_global("__session_status_message"))
  55. raise webnotes.SessionStopped('Session Stopped')
  56. # load profile
  57. self.setup_profile()
  58. # run login triggers
  59. if webnotes.form_dict.get('cmd')=='login':
  60. webnotes.login_manager.run_trigger('on_login_post_session')
  61. # write out cookies
  62. webnotes.cookie_manager.set_cookies()
  63. def set_lang(self, lang):
  64. try:
  65. from startup import lang_list
  66. except ImportError, e:
  67. return
  68. if not lang:
  69. return
  70. if ";" in lang: # not considering weightage
  71. lang = lang.split(";")[0]
  72. if "," in lang:
  73. lang = lang.split(",")
  74. else:
  75. lang = [lang]
  76. for l in lang:
  77. code = l.strip()
  78. if code in lang_list:
  79. webnotes.lang = code
  80. return
  81. # check if parent language (pt) is setup, if variant (pt-BR)
  82. if "-" in code:
  83. code = code.split("-")[0]
  84. if code in lang_list:
  85. webnotes.lang = code
  86. return
  87. def setup_profile(self):
  88. webnotes.user = webnotes.profile.Profile()
  89. def get_db_name(self):
  90. """get database name from conf"""
  91. return conf.db_name
  92. def connect(self, ac_name = None):
  93. """connect to db, from ac_name or db_name"""
  94. webnotes.conn = webnotes.db.Database(user = self.get_db_name(), \
  95. password = getattr(conf,'db_password', ''))
  96. class LoginManager:
  97. def __init__(self):
  98. if webnotes.form_dict.get('cmd')=='login':
  99. # clear cache
  100. from webnotes.sessions import clear_cache
  101. clear_cache(webnotes.form_dict.get('usr'))
  102. self.authenticate()
  103. self.post_login()
  104. info = webnotes.conn.get_value("Profile", self.user, ["user_type", "first_name", "last_name"], as_dict=1)
  105. if info.user_type=="Partner":
  106. webnotes.response["message"] = "No App"
  107. full_name = " ".join(filter(None, [info.first_name, info.last_name]))
  108. webnotes.response["full_name"] = full_name
  109. webnotes.add_cookies["full_name"] = full_name
  110. else:
  111. webnotes.response['message'] = 'Logged In'
  112. def post_login(self):
  113. self.run_trigger()
  114. self.validate_ip_address()
  115. self.validate_hour()
  116. def authenticate(self, user=None, pwd=None):
  117. if not (user and pwd):
  118. user, pwd = webnotes.form_dict.get('usr'), webnotes.form_dict.get('pwd')
  119. if not (user and pwd):
  120. self.fail('Incomplete login details')
  121. self.check_if_enabled(user)
  122. self.user = self.check_password(user, pwd)
  123. def check_if_enabled(self, user):
  124. """raise exception if user not enabled"""
  125. from webnotes.utils import cint
  126. if user=='Administrator': return
  127. if not cint(webnotes.conn.get_value('Profile', user, 'enabled')):
  128. self.fail('User disabled or missing')
  129. def check_password(self, user, pwd):
  130. """check password"""
  131. user = webnotes.conn.sql("""select `user` from __Auth where `user`=%s
  132. and `password`=password(%s)""", (user, pwd))
  133. if not user:
  134. self.fail('Incorrect password')
  135. else:
  136. return user[0][0] # in correct case
  137. def fail(self, message):
  138. webnotes.response['message'] = message
  139. raise webnotes.AuthenticationError
  140. def run_trigger(self, method='on_login'):
  141. try:
  142. from startup import event_handlers
  143. if hasattr(event_handlers, method):
  144. getattr(event_handlers, method)(self)
  145. return
  146. except ImportError, e:
  147. pass
  148. def validate_ip_address(self):
  149. """check if IP Address is valid"""
  150. ip_list = webnotes.conn.get_value('Profile', self.user, 'restrict_ip', ignore=True)
  151. if not ip_list:
  152. return
  153. ip_list = ip_list.replace(",", "\n").split('\n')
  154. ip_list = [i.strip() for i in ip_list]
  155. for ip in ip_list:
  156. if webnotes.remote_ip.startswith(ip):
  157. return
  158. webnotes.msgprint('Not allowed from this IP Address')
  159. raise webnotes.AuthenticationError
  160. def validate_hour(self):
  161. """check if user is logging in during restricted hours"""
  162. login_before = int(webnotes.conn.get_value('Profile', self.user, 'login_before', ignore=True) or 0)
  163. login_after = int(webnotes.conn.get_value('Profile', self.user, 'login_after', ignore=True) or 0)
  164. if not (login_before or login_after):
  165. return
  166. from webnotes.utils import now_datetime
  167. current_hour = int(now_datetime().strftime('%H'))
  168. if login_before and current_hour > login_before:
  169. webnotes.msgprint('Not allowed to login after restricted hour', raise_exception=1)
  170. if login_after and current_hour < login_after:
  171. webnotes.msgprint('Not allowed to login before restricted hour', raise_exception=1)
  172. def login_as_guest(self):
  173. """login as guest"""
  174. self.user = 'Guest'
  175. self.post_login()
  176. def logout(self, arg='', user=None):
  177. if not user: user = webnotes.session.user
  178. self.user = user
  179. self.run_trigger('on_logout')
  180. if user in ['demo@erpnext.com', 'Administrator']:
  181. webnotes.conn.sql('delete from tabSessions where sid=%s', webnotes.session.get('sid'))
  182. webnotes.cache().delete_value("session:" + webnotes.session.get("sid"))
  183. else:
  184. from webnotes.sessions import clear_sessions
  185. clear_sessions(user)
  186. webnotes.add_cookies["full_name"] = ""
  187. class CookieManager:
  188. def __init__(self):
  189. import Cookie
  190. webnotes.cookies = Cookie.SimpleCookie()
  191. self.get_incoming_cookies()
  192. def get_incoming_cookies(self):
  193. import os
  194. cookies = {}
  195. if 'HTTP_COOKIE' in os.environ:
  196. c = os.environ['HTTP_COOKIE']
  197. webnotes.cookies.load(c)
  198. for c in webnotes.cookies.values():
  199. cookies[c.key] = c.value
  200. webnotes.incoming_cookies = cookies
  201. def set_cookies(self):
  202. if not webnotes.session.get('sid'): return
  203. import datetime
  204. # sid expires in 3 days
  205. expires = datetime.datetime.now() + datetime.timedelta(days=3)
  206. expires = expires.strftime('%a, %d %b %Y %H:%M:%S')
  207. webnotes.cookies[b'sid'] = webnotes.session['sid'].encode('utf-8')
  208. webnotes.cookies[b'sid'][b'expires'] = expires.encode('utf-8')
  209. webnotes.cookies[b'country'] = webnotes.session.get("session_country")
  210. def set_remember_me(self):
  211. from webnotes.utils import cint
  212. if not cint(webnotes.form_dict.get('remember_me')): return
  213. remember_days = webnotes.conn.get_value('Control Panel', None,
  214. 'remember_for_days') or 7
  215. import datetime
  216. expires = datetime.datetime.now() + \
  217. datetime.timedelta(days=remember_days)
  218. expires = expires.strftime('%a, %d %b %Y %H:%M:%S')
  219. webnotes.cookies[b'remember_me'] = 1
  220. for k in webnotes.cookies.keys():
  221. webnotes.cookies[k][b'expires'] = expires.encode('utf-8')
  222. def update_password(user, password):
  223. webnotes.conn.sql("""insert into __Auth (user, `password`)
  224. values (%s, password(%s))
  225. on duplicate key update `password`=password(%s)""", (user,
  226. password, password))