def enable_all_roles_and_domains(): """ enable all roles and domain for testing """ # add all roles to users domains = dataent.get_all("Domain") if not domains: return from dataent.desk.page.setup_wizard.setup_wizard import add_all_roles_to dataent.get_single('Domain Settings').set_active_domains(\ [d.name for d in domains]) add_all_roles_to('Administrator')
def test_subscription_cancellation_invoices_with_prorata_true(self): settings = dataent.get_single('Subscription Settings') to_prorate = settings.prorate settings.prorate = 1 settings.save() subscription = dataent.new_doc('Subscription') subscription.customer = '_Test Customer' subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1}) subscription.save() subscription.cancel_subscription() invoice = subscription.get_current_invoice() diff = flt( date_diff(nowdate(), subscription.current_invoice_start) + 1) plan_days = flt( date_diff(subscription.current_invoice_end, subscription.current_invoice_start) + 1) prorate_factor = flt(diff / plan_days) self.assertEqual(flt(invoice.grand_total, 2), flt(prorate_factor * 900, 2)) settings.prorate = to_prorate settings.save() subscription.delete()
def test_subscription_is_past_due_doesnt_change_within_grace_period(self): settings = dataent.get_single('Subscription Settings') grace_period = settings.grace_period settings.grace_period = 1000 settings.save() subscription = dataent.new_doc('Subscription') subscription.customer = '_Test Customer' subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1}) subscription.start = '2018-01-01' subscription.insert() subscription.process() # generate first invoice self.assertEqual(subscription.status, 'Past Due Date') subscription.process() # Grace period is 1000 days so status should remain as Past Due Date self.assertEqual(subscription.status, 'Past Due Date') subscription.process() self.assertEqual(subscription.status, 'Past Due Date') subscription.process() self.assertEqual(subscription.status, 'Past Due Date') settings.grace_period = grace_period settings.save() subscription.delete()
def test_subcription_cancellation_and_process(self): settings = dataent.get_single('Subscription Settings') default_grace_period_action = settings.cancel_after_grace settings.cancel_after_grace = 1 settings.save() subscription = dataent.new_doc('Subscription') subscription.customer = '_Test Customer' subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1}) subscription.start = '2018-01-01' subscription.insert() subscription.process() # generate first invoice invoices = len(subscription.invoices) self.assertEqual(subscription.status, 'Past Due Date') self.assertEqual(len(subscription.invoices), invoices) subscription.cancel_subscription() self.assertEqual(subscription.status, 'Cancelled') self.assertEqual(len(subscription.invoices), invoices) subscription.process() self.assertEqual(subscription.status, 'Cancelled') self.assertEqual(len(subscription.invoices), invoices) subscription.process() self.assertEqual(subscription.status, 'Cancelled') self.assertEqual(len(subscription.invoices), invoices) settings.cancel_after_grace = default_grace_period_action settings.save() subscription.delete()
def get_directions(route, optimize): """ Retrieve map directions for a given route and departure time. If optimize is `True`, Google Maps will return an optimized order for the intermediate waypoints. NOTE: Google's API does take an additional `departure_time` key, but it only works for routes without any waypoints. Args: route (list of str): Route addresses (origin -> waypoint(s), if any -> destination) optimize (bool): `True` if route needs to be optimized, else `False` Returns: (dict): Route legs and, if `optimize` is `True`, optimized waypoint order """ settings = dataent.get_single("Google Maps Settings") maps_client = settings.get_client() directions_data = { "origin": route[0], "destination": route[-1], "waypoints": route[1:-1], "optimize_waypoints": optimize } try: directions = maps_client.directions(**directions_data) except Exception as e: dataent.throw(_(e.message)) return directions[0] if directions else False
def test_subscription_unpaid_back_to_active(self): settings = dataent.get_single('Subscription Settings') default_grace_period_action = settings.cancel_after_grace settings.cancel_after_grace = 0 settings.save() subscription = dataent.new_doc('Subscription') subscription.customer = '_Test Customer' subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1}) subscription.start = '2018-01-01' subscription.insert() subscription.process() # generate first invoice self.assertEqual(subscription.status, 'Past Due Date') subscription.process() # This should change status to Cancelled since grace period is 0 self.assertEqual(subscription.status, 'Unpaid') invoice = subscription.get_current_invoice() invoice.db_set('outstanding_amount', 0) invoice.db_set('status', 'Paid') subscription.process() self.assertEqual(subscription.status, 'Active') # A new invoice is generated subscription.process() self.assertEqual(subscription.status, 'Past Due Date') settings.cancel_after_grace = default_grace_period_action settings.save() subscription.delete()
def test_prepaid_subscriptions_with_prorate_true(self): settings = dataent.get_single('Subscription Settings') to_prorate = settings.prorate settings.prorate = 1 settings.save() subscription = dataent.new_doc('Subscription') subscription.customer = '_Test Customer' subscription.generate_invoice_at_period_start = True subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1}) subscription.save() subscription.cancel_subscription() self.assertEqual(len(subscription.invoices), 1) current_inv = subscription.get_current_invoice() self.assertEqual(current_inv.status, "Unpaid") diff = flt( date_diff(nowdate(), subscription.current_invoice_start) + 1) plan_days = flt( date_diff(subscription.current_invoice_end, subscription.current_invoice_start) + 1) prorate_factor = flt(diff / plan_days) self.assertEqual(flt(current_inv.grand_total, 2), flt(prorate_factor * 900, 2)) settings.prorate = to_prorate settings.save() subscription.delete()
def test_timesheet_time_overlap(self): settings = dataent.get_single('Projects Settings') initial_setting = settings.ignore_employee_time_overlap settings.ignore_employee_time_overlap = 0 settings.save() update_activity_type("_Test Activity Type") timesheet = dataent.new_doc("Timesheet") timesheet.employee = "_T-Employee-00001" timesheet.append( 'time_logs', { "billable": 1, "activity_type": "_Test Activity Type", "from_time": now_datetime(), "to_time": now_datetime() + datetime.timedelta(hours=3), "company": "_Test Company" }) timesheet.append( 'time_logs', { "billable": 1, "activity_type": "_Test Activity Type", "from_time": now_datetime(), "to_time": now_datetime() + datetime.timedelta(hours=3), "company": "_Test Company" }) self.assertRaises(dataent.ValidationError, timesheet.save) settings.ignore_employee_time_overlap = 1 settings.save() timesheet.save() # should not throw an error settings.ignore_employee_time_overlap = initial_setting settings.save()
def backup_to_s3(): from dataent.utils.backups import new_backup from dataent.utils import get_backups_path doc = dataent.get_single("S3 Backup Settings") bucket = doc.bucket conn = boto3.client( 's3', aws_access_key_id=doc.access_key_id, aws_secret_access_key=doc.get_password('secret_access_key'), endpoint_url=doc.endpoint_url or 'https://s3.amazonaws.com' ) backup = new_backup(ignore_files=False, backup_path_db=None, backup_path_files=None, backup_path_private_files=None, force=True) db_filename = os.path.join(get_backups_path(), os.path.basename(backup.backup_path_db)) files_filename = os.path.join(get_backups_path(), os.path.basename(backup.backup_path_files)) private_files = os.path.join(get_backups_path(), os.path.basename(backup.backup_path_private_files)) folder = os.path.basename(db_filename)[:15] + '/' # for adding datetime to folder name upload_file_to_s3(db_filename, folder, conn, bucket) upload_file_to_s3(private_files, folder, conn, bucket) upload_file_to_s3(files_filename, folder, conn, bucket) delete_old_backups(doc.backup_limit, bucket)
def register_users(user_list): user_list = json.loads(user_list) settings = dataent.get_single('Marketplace Settings') for user in user_list: settings.add_hub_user(user) return user_list
def execute(): dataent.reload_doctype('System Settings') doc = dataent.get_single('System Settings') doc.enable_chat = 1 # Changes prescribed by Nabin Hait ([email protected]) doc.flags.ignore_mandatory = True doc.flags.ignore_permissions = True doc.save()
def get_website_settings(): hooks = dataent.get_hooks() context = dataent._dict({ 'top_bar_items': get_items('top_bar_items'), 'footer_items': get_items('footer_items'), "post_login": [ {"label": _("My Account"), "url": "/me"}, # {"class": "divider"}, {"label": _("Logout"), "url": "/?cmd=web_logout"} ] }) settings = dataent.get_single("Website Settings") for k in ["banner_html", "brand_html", "copyright", "twitter_share_via", "facebook_share", "google_plus_one", "twitter_share", "linked_in_share", "disable_signup", "hide_footer_signup", "head_html", "title_prefix", "navbar_search"]: if hasattr(settings, k): context[k] = settings.get(k) if settings.address: context["footer_address"] = settings.address for k in ["facebook_share", "google_plus_one", "twitter_share", "linked_in_share", "disable_signup"]: context[k] = int(context.get(k) or 0) if dataent.request: context.url = quote(str(get_request_site_address(full_address=True)), safe="/:") context.encoded_title = quote(encode(context.title or ""), str("")) for update_website_context in hooks.update_website_context or []: dataent.get_attr(update_website_context)(context) context.web_include_js = hooks.web_include_js or [] context.web_include_css = hooks.web_include_css or [] via_hooks = dataent.get_hooks("website_context") for key in via_hooks: context[key] = via_hooks[key] if key not in ("top_bar_items", "footer_items", "post_login") \ and isinstance(context[key], (list, tuple)): context[key] = context[key][-1] add_website_theme(context) if not context.get("favicon"): context["favicon"] = "/assets/dataent/images/favicon.png" if settings.favicon and settings.favicon != "attach_files:": context["favicon"] = settings.favicon return context
def is_past_grace_period(self): """ Returns `True` if the grace period for the `Subscription` has passed """ current_invoice = self.get_current_invoice() if self.current_invoice_is_past_due(current_invoice): subscription_settings = dataent.get_single('Subscription Settings') grace_period = cint(subscription_settings.grace_period) return getdate(nowdate()) > add_days(current_invoice.due_date, grace_period)
def setUp(self): create_driver() create_vehicle() create_delivery_notification() create_test_contact_and_address() settings = dataent.get_single("Google Maps Settings") settings.home_address = dataent.get_last_doc("Address").name settings.save() self.delivery_trip = create_delivery_trip()
def set_status_grace_period(self): """ Sets the `Subscription` `status` based on the preference set in `Subscription Settings`. Used when the `Subscription` needs to decide what to do after the current generated invoice is past it's due date and grace period. """ subscription_settings = dataent.get_single('Subscription Settings') if self.status == 'Past Due Date' and self.is_past_grace_period(): self.status = 'Cancelled' if cint( subscription_settings.cancel_after_grace) else 'Unpaid'
def get_hub_connection(): settings = dataent.get_single('Marketplace Settings') marketplace_url = settings.marketplace_url hub_user = settings.get_hub_user(dataent.session.user) if hub_user: password = hub_user.get_password() hub_connection = DataentClient(marketplace_url, hub_user.user, password) return hub_connection else: read_only_hub_connection = DataentClient(marketplace_url) return read_only_hub_connection
def execute(): dataent.reload_doc('stock', 'doctype', 'item') language = dataent.get_single("System Settings").language if language and language.startswith('en'): return dataent.local.lang = language all_domains = dataent.get_hooks("domains") for domain in all_domains: translated_domain = _(domain, lang=language) if dataent.db.exists("Domain", translated_domain): #if domain already exists merged translated_domain and domain merge = False if dataent.db.exists("Domain", domain): merge = True dataent.rename_doc("Domain", translated_domain, domain, ignore_permissions=True, merge=merge) domain_settings = dataent.get_single("Domain Settings") active_domains = [d.domain for d in domain_settings.active_domains] try: for domain in active_domains: domain = dataent.get_doc("Domain", domain) domain.setup_domain() if int( dataent.db.get_single_value('System Settings', 'setup_complete')): domain.setup_sidebar_items() domain.setup_desktop_icons() domain.set_default_portal_role() except dataent.LinkValidationError: pass
def create_delivery_notification(): if not dataent.db.exists("Email Template", "Delivery Notification"): dispatch_template = dataent.get_doc({ 'doctype': 'Email Template', 'name': 'Delivery Notification', 'response': 'Test Delivery Trip', 'subject': 'Test Subject', 'owner': dataent.session.user }) dispatch_template.insert() delivery_settings = dataent.get_single("Delivery Settings") delivery_settings.dispatch_template = 'Delivery Notification' delivery_settings.save()
def register_marketplace(company, company_description): validate_registerer() settings = dataent.get_single('Marketplace Settings') message = settings.register_seller(company, company_description) if message.get('hub_seller_name'): settings.registered = 1 settings.hub_seller_name = message.get('hub_seller_name') settings.save() settings.add_hub_user(dataent.session.user) return { 'ok': 1 }
def set_subscription_status(self): """ Sets the status of the `Subscription` """ if self.is_trialling(): self.status = 'Trialling' elif self.status == 'Past Due Date' and self.is_past_grace_period(): subscription_settings = dataent.get_single('Subscription Settings') self.status = 'Cancelled' if cint( subscription_settings.cancel_after_grace) else 'Unpaid' elif self.status == 'Past Due Date' and not self.has_outstanding_invoice( ): self.status = 'Active' elif self.current_invoice_is_past_due(): self.status = 'Past Due Date' elif self.is_new_subscription(): self.status = 'Active' # todo: then generate new invoice self.save()
def test_subscription_cancellation_invoices_with_prorata_false(self): settings = dataent.get_single('Subscription Settings') to_prorate = settings.prorate settings.prorate = 0 settings.save() subscription = dataent.new_doc('Subscription') subscription.customer = '_Test Customer' subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1}) subscription.save() subscription.cancel_subscription() invoice = subscription.get_current_invoice() self.assertEqual(invoice.grand_total, 900) settings.prorate = to_prorate settings.save() subscription.delete()
def test_clean_html(self): settings = dataent.get_single('Stock Settings') settings.clean_description_html = 1 settings.save() item = dataent.get_doc( dict( doctype='Item', item_code='Item for description test', item_group='Products', description= '<p><span style="font-size: 12px;">Drawing No. 07-xxx-PO132<br></span><span style="font-size: 12px;">1800 x 1685 x 750<br></span><span style="font-size: 12px;">All parts made of Marine Ply<br></span><span style="font-size: 12px;">Top w/ Corian dd<br></span><span style="font-size: 12px;">CO, CS, VIP Day Cabin</span></p>' )).insert() self.assertEqual( item.description, '<p>Drawing No. 07-xxx-PO132<br>1800 x 1685 x 750<br>All parts made of Marine Ply<br>Top w/ Corian dd<br>CO, CS, VIP Day Cabin</p>' ) item.delete()
def test_batch_name_with_naming_series(self): stock_settings = dataent.get_single('Stock Settings') use_naming_series = cint(stock_settings.use_naming_series) if not use_naming_series: dataent.set_value('Stock Settings', 'Stock Settings', 'use_naming_series', 1) batch = self.make_new_batch('_Test Stock Item For Batch Test1') batch_name = batch.name self.assertTrue(batch_name.startswith('BATCH-')) batch.delete() batch = self.make_new_batch('_Test Stock Item For Batch Test2') self.assertEqual(batch_name, batch.name) # reset Stock Settings if not use_naming_series: dataent.set_value('Stock Settings', 'Stock Settings', 'use_naming_series', 0)
def settings(fields = None): fields = safe_json_loads(fields) dsettings = dataent.get_single('Website Settings') response = dict( socketio = dict( port = dataent.conf.socketio_port ), enable = bool(dsettings.chat_enable), enable_from = dsettings.chat_enable_from, enable_to = dsettings.chat_enable_to, room_name = dsettings.chat_room_name, welcome_message = dsettings.chat_welcome_message, operators = [ duser.user for duser in dsettings.chat_operators ] ) if fields: response = filter_dict(response, fields) return response
def form_route_list(self, optimize): """ Form a list of address routes based on the delivery stops. If locks are present, and the routes need to be optimized, then they will be split into sublists at the specified lock position(s). Args: optimize (bool): `True` if route needs to be optimized, else `False` Returns: (list of list of str): List of address routes split at locks, if optimize is `True` """ settings = dataent.get_single("Google Maps Settings") home_address = get_address_display( dataent.get_doc("Address", settings.home_address).as_dict()) route_list = [] # Initialize first leg with origin as the home address leg = [home_address] for stop in self.delivery_stops: leg.append(stop.customer_address) if optimize and stop.lock: route_list.append(leg) leg = [stop.customer_address] # For last leg, append home address as the destination # only if lock isn't on the final stop if len(leg) > 1: leg.append(home_address) route_list.append(leg) route_list = [[sanitize_address(address) for address in route] for route in route_list] return route_list
def delete_old_backups(limit, bucket): all_backups = list() doc = dataent.get_single("S3 Backup Settings") backup_limit = int(limit) s3 = boto3.resource( 's3', aws_access_key_id=doc.access_key_id, aws_secret_access_key=doc.get_password('secret_access_key'), endpoint_url=doc.endpoint_url or 'https://s3.amazonaws.com' ) bucket = s3.Bucket(bucket) objects = bucket.meta.client.list_objects_v2(Bucket=bucket.name, Delimiter='/') for obj in objects.get('CommonPrefixes'): all_backups.append(obj.get('Prefix')) oldest_backup = sorted(all_backups)[0] if len(all_backups) > backup_limit: print("Deleting Backup: {0}".format(oldest_backup)) for obj in bucket.objects.filter(Prefix=oldest_backup): # delete all keys that are inside the oldest_backup s3.Object(bucket.name, obj.key).delete()
def test_subscription_cancellation_invoices(self): settings = dataent.get_single('Subscription Settings') to_prorate = settings.prorate settings.prorate = 1 settings.save() subscription = dataent.new_doc('Subscription') subscription.customer = '_Test Customer' subscription.append('plans', {'plan': '_Test Plan Name', 'qty': 1}) subscription.save() self.assertEqual(subscription.status, 'Active') subscription.cancel_subscription() # Invoice must have been generated self.assertEqual(len(subscription.invoices), 1) invoice = subscription.get_current_invoice() diff = flt( date_diff(nowdate(), subscription.current_invoice_start) + 1) plan_days = flt( date_diff(subscription.current_invoice_end, subscription.current_invoice_start) + 1) prorate_factor = flt(diff / plan_days) self.assertEqual( flt( get_prorata_factor(subscription.current_invoice_end, subscription.current_invoice_start), 2), flt(prorate_factor, 2)) self.assertEqual(flt(invoice.grand_total, 2), flt(prorate_factor * 900, 2)) self.assertEqual(subscription.status, 'Cancelled') subscription.delete() settings.prorate = to_prorate settings.save()
def create(kind, owner, users=None, name=None): authenticate(owner) users = safe_json_loads(users) create = True if kind == 'Visitor': room = squashify( dataent.db.sql(""" SELECT name FROM `tabChat Room` WHERE owner = "{owner}" """.format(owner=owner), as_dict=True)) if room: room = dataent.get_doc('Chat Room', room.name) create = False if create: room = dataent.new_doc('Chat Room') room.type = kind room.owner = owner room.room_name = name dusers = [] if kind != 'Visitor': if users: users = listify(users) for user in users: duser = dataent.new_doc('Chat Room User') duser.user = user dusers.append(duser) room.users = dusers else: dsettings = dataent.get_single('Website Settings') room.room_name = dsettings.chat_room_name users = [user for user in room.users] if hasattr(room, 'users') else [] for user in dsettings.chat_operators: if user.user not in users: # appending user to room.users will remove the user from chat_operators # this is undesirable, create a new Chat Room User instead chat_room_user = { "doctype": "Chat Room User", "user": user.user } room.append('users', chat_room_user) room.save(ignore_permissions=True) room = get(owner, rooms=room.name) users = [room.owner] + [u for u in room.users] for u in users: dataent.publish_realtime('dataent.chat.room:create', room, user=u, after_commit=True) return room
def setUp(self): settings = dataent.get_single('Stock Settings') settings.clean_description_html = 0 settings.save() dataent.delete_doc('Item', 'Item for description test')
def tearDown(self): settings = dataent.get_single('Stock Settings') settings.clean_description_html = 1 settings.save()