old_contents: import frappe
  from frappe.query_builder import DocType
  
  
  def execute():
  	RATING_FIELD_TYPE = "decimal(3,2)"
  	rating_fields = frappe.get_all(
  		"DocField", fields=["parent", "fieldname"], filters={"fieldtype": "Rating"}
  	)
  
  	custom_rating_fields = frappe.get_all(
  		"Custom Field", fields=["dt", "fieldname"], filters={"fieldtype": "Rating"}
  	)
  
  	for _field in rating_fields + custom_rating_fields:
  		doctype_name = _field.get("parent") or _field.get("dt")
  		doctype = DocType(doctype_name)
  		field = _field.fieldname
  
  		# TODO: Add postgres support (for the check)
  		if (
  			frappe.conf.db_type == "mariadb"
  			and frappe.db.get_column_type(doctype_name, field) == RATING_FIELD_TYPE
  		):
  			continue
  
  		# update NULL values to 0 to avoid data truncated error (temp)
  		# commit for upcoming DLL
  		frappe.qb.update(doctype).set(
  			doctype[field], 0
  		).where(
  			doctype[field].isnull()
  		).run()
  		frappe.db.commit()
  
  		# alter column types for rating fieldtype
  		frappe.db.change_column_type(doctype_name, column=field, type=RATING_FIELD_TYPE)
  
  		# update data: int => decimal
  		frappe.qb.update(doctype).set(
  			doctype[field], doctype[field] / 5
  		).run()
  
  		# revert 0 to NULL conversion
  		frappe.qb.update(doctype).set(
  			doctype[field], None
  		).where(
  			doctype[field] == 0
  		).run()
  
  		# commit to flush updated rows
  		frappe.db.commit()
  
new_contents: import frappe
  from frappe.query_builder import DocType
  
  
  def execute():
  	RATING_FIELD_TYPE = "decimal(3,2)"
  	rating_fields = frappe.get_all(
  		"DocField", fields=["parent", "fieldname"], filters={"fieldtype": "Rating"}
  	)
  
  	custom_rating_fields = frappe.get_all(
  		"Custom Field", fields=["dt", "fieldname"], filters={"fieldtype": "Rating"}
  	)
  
  	for _field in rating_fields + custom_rating_fields:
  		doctype_name = _field.get("parent") or _field.get("dt")
  		doctype = DocType(doctype_name)
  		field = _field.fieldname
  
  		# TODO: Add postgres support (for the check)
  		if (
  			frappe.conf.db_type == "mariadb"
  			and frappe.db.get_column_type(doctype_name, field) == RATING_FIELD_TYPE
  		):
  			continue
  
  		# commit any changes so far for upcoming DDL
  		frappe.db.commit()
  
  		# alter column types for rating fieldtype
  		frappe.db.change_column_type(doctype_name, column=field, type=RATING_FIELD_TYPE, nullable=True)
  
  		# update data: int => decimal
  		frappe.qb.update(doctype).set(
  			doctype[field], doctype[field] / 5
  		).run()
  
  		# commit to flush updated rows
  		frappe.db.commit()
  
subject: make ratings field nullable while altering