Script for Last Sync Checkin

Hi community,

i was trying to save this server script for generating an auto value at night every day for Last Sync Checkin. Code looks like this:

s = frappe.get_doc(‘Shift Type’,‘Normal shift’) s.last_sync_of_checkin = frappe.utils.add_to_date(frappe.utils.today(), days=-1, as_string=True) + ’ 23:59:59’ s.save()

But i am getting a Syntax error, i am not a Python coder can someone help me to write a script for Auto Last Sync Checkin?

Maybe, an Indentation issue. Please check the format.

import frappe
from frappe.utils import add_to_date, today

def update_last_sync_checkin():
    s = frappe.get_doc('Shift Type', 'Normal shift')
    last_sync_date = add_to_date(today(), days=-1, as_string=True) + ' 23:59:59'
    s.last_sync_of_checkin = last_sync_date
    s.save()

frappe.enqueue(update_last_sync_checkin, schedule_time='23:59:00')

Hi, i was able to save it, will see if it is working and give feedback, Thanks a lot. Have a nice day.

Hi, i have an error massage, script failed. Can anybody help?

Details:

Traceback with variables (most recent call last):
File “apps/frappe/frappe/core/doctype/scheduled_job_type/scheduled_job_type.py”, line 141, in execute
frappe.get_doc(“Server Script”, script_name).execute_scheduled_method()
self = <ScheduledJobType: sync_checkin_daily>
script_name = ‘Sync Checkin’
File “apps/frappe/frappe/core/doctype/server_script/server_script.py”, line 185, in execute_scheduled_method
safe_exec(self.script, script_filename=self.name)
self = <ServerScript: Sync Checkin>
File “apps/frappe/frappe/utils/safe_exec.py”, line 92, in safe_exec
frappe.throw(msg, ServerScriptNotEnabled, title=“Server Scripts Disabled”)
script = “import frappe\r\nfrom frappe.utils import add_to_date, today\r\n\r\ndef update_last_sync_checkin():\r\n s = frappe.get_doc(‘Shift Type’, ‘Normal shift’)\r\n last_sync_date = add_to_date(today(), days=-1, as_string=True) + ’ 23:59:59’\r\n s.last_sync_of_checkin = last_sync_date\r\n s.save()\r\n\r\nfrappe.enqueue(update_last_sync_checkin, schedule_time=‘23:59:00’)”
_globals = None
_locals = None
restrict_commit_rollback = False
script_filename = ‘Sync Checkin’
msg = “Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more
docs_cta = ‘Read the documentation to know more’
File “apps/frappe/frappe/init.py”, line 645, in throw
msgprint(
msg = “Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more
exc = <class ‘frappe.utils.safe_exec.ServerScriptNotEnabled’>
title = ‘Server Scripts Disabled’
is_minimizable = False
wide = False
as_list = False
primary_action = None
File “apps/frappe/frappe/init.py”, line 610, in msgprint
_raise_exception()
msg = “Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more
title = ‘Server Scripts Disabled’
raise_exception = <class ‘frappe.utils.safe_exec.ServerScriptNotEnabled’>
as_table = False
as_list = False
indicator = ‘red’
alert = False
primary_action = None
is_minimizable = False
wide = False
realtime = False
sys = <module ‘sys’ (built-in)>
_raise_exception = <function msgprint.._raise_exception at 0x7f01e7bb3380>
inspect = <module ‘inspect’ from ‘/usr/lib/python3.11/inspect.py’>
out = {‘message’: “Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more”, ‘title’: ‘Server Scripts Disabled’, ‘indicator’: ‘red’, ‘raise_exception’: 1, ‘__frappe_exc_id’: ‘41528d426f77f0cdf358c40f8fa1b81076d51bd2cb36aa16c380fb40’}
File “apps/frappe/frappe/init.py”, line 561, in _raise_exception
raise exc
exc = ServerScriptNotEnabled(“Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more”)
inspect = <module ‘inspect’ from ‘/usr/lib/python3.11/inspect.py’>
msg = “Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more
out = {‘message’: “Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more”, ‘title’: ‘Server Scripts Disabled’, ‘indicator’: ‘red’, ‘raise_exception’: 1, ‘__frappe_exc_id’: ‘41528d426f77f0cdf358c40f8fa1b81076d51bd2cb36aa16c380fb40’}
raise_exception = <class ‘frappe.utils.safe_exec.ServerScriptNotEnabled’>
frappe.utils.safe_exec.ServerScriptNotEnabled: Server Scripts are disabled. Please enable server scripts from bench configuration.
Read the documentation to know more

Please read this.

If you use the server script doctype then you have to enable the server script.

bench --site sitename set-config -g server_script_enabled 1
1 Like

Hi bench --site sitename set-config -g server_script_enabled 1 is done but i get still the information that it does not work.

Any idea what i can do?

Site_config.json
image

Adding it ito console nothing is happening:
image (1)

Now, create a server script and check it

1 Like

Sorry but it failed again:

Traceback with variables (most recent call last):
File “apps/frappe/frappe/core/doctype/scheduled_job_type/scheduled_job_type.py”, line 141, in execute
frappe.get_doc(“Server Script”, script_name).execute_scheduled_method()
self = <ScheduledJobType: sync_daily>
script_name = ‘Sync’
File “apps/frappe/frappe/core/doctype/server_script/server_script.py”, line 185, in execute_scheduled_method
safe_exec(self.script, script_filename=self.name)
self = <ServerScript: Sync>
File “apps/frappe/frappe/utils/safe_exec.py”, line 111, in safe_exec
exec(
script = “import frappe\r\nfrom frappe.utils import add_to_date, today\r\n\r\ndef update_last_sync_checkin():\r\n s = frappe.get_doc(‘Shift Type’, ‘Normal shift’)\r\n last_sync_date = add_to_date(today(), days=-1, as_string=True) + ’ 15:45:00’\r\n s.last_sync_of_checkin = last_sync_date\r\n s.save()\r\n\r\nfrappe.enqueue(update_last_sync_checkin, schedule_time=‘15:40:00’)”
_globals = None
_locals = None
restrict_commit_rollback = False
script_filename = ‘Sync’
exec_globals = {‘json’: {‘loads’: <function loads at 0x7f2d00be6520>, ‘dumps’: <function dumps at 0x7f2d00be5da0>}, ‘as_json’: <function as_json at 0x7f2cffc1cb80>, ‘dict’: <class ‘dict’>, ‘log’: <function log at 0x7f2cffd44b80>, ‘_dict’: <class ‘frappe._dict’>, ‘args’: {}, ‘frappe’: {‘call’: <function call_whitelisted_function at 0x7f2cfc2a2ac0>, ‘flags’: {}, ‘format’: <function format_value at 0x7f2cffc1cd60>, ‘format_value’: <function format_value at 0x7f2cffc1cd60>, ‘date_format’: ‘dd-mm-yyyy’, ‘time_format’: ‘HH:mm:ss’, ‘format_date’: <function global_date_format at 0x7f2cffcf5b20>, ‘form_dict’: {}, ‘bold’: <function bold at 0x7f2cffc1d580>, ‘copy_doc’: <function copy_doc at 0x7f2cffc1c680>, ‘errprint’: <function errprint at 0x7f2cffd44a40>, ‘qb’: <class ‘frappe.query_builder.builder.MariaDB’>, ‘get_meta’: <function get_meta at 0x7f2cffd46700>, ‘new_doc’: <function new_doc at 0x7f2cffd45c60>, ‘get_doc’: <function get_doc at 0x7f2cffd46520>, ‘get_mapped_doc’: <function get_mapped_doc at 0x7f2cfc2…
filename = ‘: sync’
File “: sync”, line 1, in
json = {‘loads’: <function loads at 0x7f2d00be6520>, ‘dumps’: <function dumps at 0x7f2d00be5da0>}
as_json = <function as_json at 0x7f2cffc1cb80>
dict = <class ‘dict’>
log = <function log at 0x7f2cffd44b80>
_dict = <class ‘frappe._dict’>
args = {}
frappe = {‘call’: <function call_whitelisted_function at 0x7f2cfc2a2ac0>, ‘flags’: {}, ‘format’: <function format_value at 0x7f2cffc1cd60>, ‘format_value’: <function format_value at 0x7f2cffc1cd60>, ‘date_format’: ‘dd-mm-yyyy’, ‘time_format’: ‘HH:mm:ss’, ‘format_date’: <function global_date_format at 0x7f2cffcf5b20>, ‘form_dict’: {}, ‘bold’: <function bold at 0x7f2cffc1d580>, ‘copy_doc’: <function copy_doc at 0x7f2cffc1c680>, ‘errprint’: <function errprint at 0x7f2cffd44a40>, ‘qb’: <class ‘frappe.query_builder.builder.MariaDB’>, ‘get_meta’: <function get_meta at 0x7f2cffd46700>, ‘new_doc’: <function new_doc at 0x7f2cffd45c60>, ‘get_doc’: <function get_doc at 0x7f2cffd46520>, ‘get_mapped_doc’: <function get_mapped_doc at 0x7f2cfc28a160>, ‘get_last_doc’: <function get_last_doc at 0x7f2cffd465c0>, ‘get_cached_doc’: <function get_cached_doc at 0x7f2cffd45da0>, ‘get_list’: <function get_list at 0x7f2cffc1c9a0>, ‘get_all’: <function get_all at 0x7f2cffc1ca40>, ‘get_system_settings’: <function get_sys…
FrappeClient = <class ‘frappe.frappeclient.FrappeClient’>
style = {‘border_color’: ‘#d1d8dd’}
get_toc = <function get_toc at 0x7f2cfc61a020>
get_next_link = <function get_next_link at 0x7f2cfc61a0c0>
_ = <function _ at 0x7f2d00c956c0>
scrub = <function scrub at 0x7f2cffbc76a0>
guess_mimetype = <function guess_type at 0x7f2d0070c5e0>
html2text = <function html2text at 0x7f2cfc708900>
dev_server = 0
run_script = <function run_script at 0x7f2cfc2a2b60>
is_job_queued = <function is_job_queued at 0x7f2cfc2a2980>
get_visible_columns = <function get_visible_columns at 0x7f2cfc2a20c0>
builtins = {‘build_class’: , ‘None’: None, ‘False’: False, ‘True’: True, ‘abs’: , ‘bool’: <class ‘bool’>, ‘bytes’: <class ‘bytes’>, ‘callable’: , ‘chr’: , ‘complex’: <class ‘complex’>, ‘divmod’: , ‘float’: <class ‘float’>, ‘hash’: , ‘hex’: , ‘id’: , ‘int’: <class ‘int’>, ‘isinstance’: , ‘issubclass’: , ‘len’: , ‘oct’: , ‘ord’: , ‘pow’: , ‘range’: <class ‘range’>, ‘repr’: , ‘round’: , ‘slice’: <class ‘slice’>, ‘sorted’: , ‘str’: <class ‘str’>, ‘tuple’: <class ‘tuple’>, ‘zip’: <class ‘zip’>, ‘ArithmeticError’: <class ‘ArithmeticError’>, ‘AssertionError’: <class 'Assertion…
write = <function _write at 0x7f2cfc2a3420>
getitem = <function _getitem at 0x7f2cfc2a31a0>
getattr = <function _getattr_for_safe_exec at 0x7f2cfc2a3240>
print = <class ‘frappe.utils.safe_exec.FrappePrintCollector’>
getiter =
iter_unpack_sequence = <function guarded_iter_unpack_sequence at 0x7f2cfc3605e0>
abs =
all =
any =
bool = <class ‘bool’>
enumerate = <class ‘enumerate’>
isinstance =
issubclass =
list = <class ‘list’>
max =
min =
range = <class ‘range’>
set = <class ‘set’>
sorted =
sum =
tuple = <class ‘tuple’>
builtins.ImportError: import not found

Now the server script works properly but there is a limitation in the server script doctype.

Please check it.

Ok thank you . But is there any solution? In this topic there is no solution.

You have to define it in your custom app.

please check the concept of the hook.

1 Like

Thank you sir, to be honest i am a complet noob. Can you give me a step by step advice?

Please check the video.

Thank you for sharing this video it is interesting but i dont get a point how to implement this server script into hook

In Hooks.py it should look like this?

scheduler_events = {
“daily”: [
“sync_scripts.update_last_sync_checkin”
]
}

Dear Frappe community,

i have still problem to get Clockin SYNC server script to work.
This is my last LOG, maybee someone can give me a hint how to set it up propperly.

Traceback with variables (most recent call last):
File “apps/frappe/frappe/core/doctype/scheduled_job_type/scheduled_job_type.py”, line 141, in execute
frappe.get_doc(“Server Script”, script_name).execute_scheduled_method()
self = <ScheduledJobType: synccheckin_daily>
script_name = ‘SyncCheckin’
File “apps/frappe/frappe/core/doctype/server_script/server_script.py”, line 185, in execute_scheduled_method
safe_exec(self.script, script_filename=self.name)
self = <ServerScript: SyncCheckin>
File “apps/frappe/frappe/utils/safe_exec.py”, line 111, in safe_exec
exec(
script = “import frappe\r\nfrom frappe.utils import add_to_date, today\r\n\r\ndef update_last_sync_checkin():\r\n s = frappe.get_doc(‘Shift Type’, ‘Normal shift’)\r\n last_sync_date = add_to_date(today(), days=-1, as_string=True) + ’ 23:59:59’\r\n s.last_sync_of_checkin = last_sync_date\r\n s.save()\r\n\r\nfrappe.enqueue(update_last_sync_checkin, schedule_time=‘23:59:00’)”
_globals = None
_locals = None
restrict_commit_rollback = False
script_filename = ‘SyncCheckin’
exec_globals = {‘json’: {‘loads’: <function loads at 0x7f2d00be6520>, ‘dumps’: <function dumps at 0x7f2d00be5da0>}, ‘as_json’: <function as_json at 0x7f2cffc1cb80>, ‘dict’: <class ‘dict’>, ‘log’: <function log at 0x7f2cffd44b80>, ‘_dict’: <class ‘frappe._dict’>, ‘args’: {}, ‘frappe’: {‘call’: <function call_whitelisted_function at 0x7f2cfc2a2c00>, ‘flags’: {}, ‘format’: <function format_value at 0x7f2cffc1cd60>, ‘format_value’: <function format_value at 0x7f2cffc1cd60>, ‘date_format’: ‘dd-mm-yyyy’, ‘time_format’: ‘HH:mm:ss’, ‘format_date’: <function global_date_format at 0x7f2cffcf5b20>, ‘form_dict’: {}, ‘bold’: <function bold at 0x7f2cffc1d580>, ‘copy_doc’: <function copy_doc at 0x7f2cffc1c680>, ‘errprint’: <function errprint at 0x7f2cffd44a40>, ‘qb’: <class ‘frappe.query_builder.builder.MariaDB’>, ‘get_meta’: <function get_meta at 0x7f2cffd46700>, ‘new_doc’: <function new_doc at 0x7f2cffd45c60>, ‘get_doc’: <function get_doc at 0x7f2cffd46520>, ‘get_mapped_doc’: <function get_mapped_doc at 0x7f2cfc2…
filename = ‘: synccheckin’
File “: synccheckin”, line 1, in
json = {‘loads’: <function loads at 0x7f2d00be6520>, ‘dumps’: <function dumps at 0x7f2d00be5da0>}
as_json = <function as_json at 0x7f2cffc1cb80>
dict = <class ‘dict’>
log = <function log at 0x7f2cffd44b80>
_dict = <class ‘frappe._dict’>
args = {}
frappe = {‘call’: <function call_whitelisted_function at 0x7f2cfc2a2c00>, ‘flags’: {}, ‘format’: <function format_value at 0x7f2cffc1cd60>, ‘format_value’: <function format_value at 0x7f2cffc1cd60>, ‘date_format’: ‘dd-mm-yyyy’, ‘time_format’: ‘HH:mm:ss’, ‘format_date’: <function global_date_format at 0x7f2cffcf5b20>, ‘form_dict’: {}, ‘bold’: <function bold at 0x7f2cffc1d580>, ‘copy_doc’: <function copy_doc at 0x7f2cffc1c680>, ‘errprint’: <function errprint at 0x7f2cffd44a40>, ‘qb’: <class ‘frappe.query_builder.builder.MariaDB’>, ‘get_meta’: <function get_meta at 0x7f2cffd46700>, ‘new_doc’: <function new_doc at 0x7f2cffd45c60>, ‘get_doc’: <function get_doc at 0x7f2cffd46520>, ‘get_mapped_doc’: <function get_mapped_doc at 0x7f2cfc28a2a0>, ‘get_last_doc’: <function get_last_doc at 0x7f2cffd465c0>, ‘get_cached_doc’: <function get_cached_doc at 0x7f2cffd45da0>, ‘get_list’: <function get_list at 0x7f2cffc1c9a0>, ‘get_all’: <function get_all at 0x7f2cffc1ca40>, ‘get_system_settings’: <function get_sys…
FrappeClient = <class ‘frappe.frappeclient.FrappeClient’>
style = {‘border_color’: ‘#d1d8dd’}
get_toc = <function get_toc at 0x7f2cfc61a160>
get_next_link = <function get_next_link at 0x7f2cfc61a200>
_ = <function _ at 0x7f2d00c956c0>
scrub = <function scrub at 0x7f2cffbc76a0>
guess_mimetype = <function guess_type at 0x7f2d0070c5e0>
html2text = <function html2text at 0x7f2cfc708a40>
dev_server = 0
run_script = <function run_script at 0x7f2cfc2a2ca0>
is_job_queued = <function is_job_queued at 0x7f2cfc2a2ac0>
get_visible_columns = <function get_visible_columns at 0x7f2cfc2a2200>
builtins = {‘build_class’: , ‘None’: None, ‘False’: False, ‘True’: True, ‘abs’: , ‘bool’: <class ‘bool’>, ‘bytes’: <class ‘bytes’>, ‘callable’: , ‘chr’: , ‘complex’: <class ‘complex’>, ‘divmod’: , ‘float’: <class ‘float’>, ‘hash’: , ‘hex’: , ‘id’: , ‘int’: <class ‘int’>, ‘isinstance’: , ‘issubclass’: , ‘len’: , ‘oct’: , ‘ord’: , ‘pow’: , ‘range’: <class ‘range’>, ‘repr’: , ‘round’: , ‘slice’: <class ‘slice’>, ‘sorted’: , ‘str’: <class ‘str’>, ‘tuple’: <class ‘tuple’>, ‘zip’: <class ‘zip’>, ‘ArithmeticError’: <class ‘ArithmeticError’>, ‘AssertionError’: <class 'Assertion…
write = <function _write at 0x7f2cfc2a3560>
getitem = <function _getitem at 0x7f2cfc2a32e0>
getattr = <function _getattr_for_safe_exec at 0x7f2cfc2a3380>
print = <class ‘frappe.utils.safe_exec.FrappePrintCollector’>
getiter =
iter_unpack_sequence = <function guarded_iter_unpack_sequence at 0x7f2cfc35c720>
abs =
all =
any =
bool = <class ‘bool’>
enumerate = <class ‘enumerate’>
isinstance =
issubclass =
list = <class ‘list’>
max =
min =
range = <class ‘range’>
set = <class ‘set’>
sorted =
sum =
tuple = <class ‘tuple’>
builtins.ImportError: import not found

I build a Server Script solution for this. Here is my code for example:

def update_last_sync_checkin():
try:
# Get all Shift Types
shift_types = frappe.get_all(‘Shift Type’, fields=[‘name’])

    # Use frappe.utils.nowdate() to get the current date and subtract 1 day for yesterday's date
    yesterday = frappe.utils.add_days(frappe.utils.nowdate(), -1)
    last_sync_date = yesterday + ' 23:59:59'  # Add time component manually

    # Iterate over all shift types and update the "last_sync_of_checkin" field
    for shift in shift_types:
        s = frappe.get_doc('Shift Type', shift.name)
        s.db_set('last_sync_of_checkin', last_sync_date, update_modified=True)

except Exception as e:
    # Log the error in case of failure
    frappe.log_error(str(e), "Sync Checkin Error")

Call the function to execute the sync

update_last_sync_checkin()