Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[16.0][OU-ADD] delivery: migration #4112

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion docsource/modules150-160.rst
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,7 @@ Module coverage 15.0 -> 16.0
+-------------------------------------------------+----------------------+-------------------------------------------------+
| |new| data_recycle | | |
+-------------------------------------------------+----------------------+-------------------------------------------------+
| delivery | | |
| delivery | Done | |
+-------------------------------------------------+----------------------+-------------------------------------------------+
| delivery_mondialrelay | |No DB layout changes. |
+-------------------------------------------------+----------------------+-------------------------------------------------+
Expand Down
136 changes: 136 additions & 0 deletions openupgrade_scripts/scripts/delivery/16.0.1.0/post-migration.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,136 @@
# SPDX-FileCopyrightText: 2023 Coop IT Easy SC
#
# SPDX-License-Identifier: AGPL-3.0-or-later

import logging
import string
from inspect import cleandoc

from openupgradelib import openupgrade

_logger = logging.getLogger(__name__)

ALPHANUM = string.digits + string.ascii_uppercase


def increment_alphanum(value):
result = []
carry = False
first = True
for digit in reversed(value):
# Preserve spaces and hyphens
if digit in [" ", "-"]:
result.append(digit)
elif digit == "Z" and (first or carry):
result.append("0")
carry = True
elif carry or first:
result.append(ALPHANUM[ALPHANUM.index(digit) + 1])
carry = False
else:
result.append(digit)
first = False
if carry:
result.append("1")
return "".join(result[::-1])


def fill_prefix(prefix, length, item, spaces, dashes):
result = prefix + (length * item)
for index in spaces:
result = result[:index] + " " + result[index + 1 :]
for index in dashes:
result = result[:index] + "-" + result[index + 1 :]
return result


def prefix_works(prefix, start, end, spaces, dashes):
# Get the highest and lowest values for the prefix, and compare them against
# the two extremes.
fill_length = len(start) - len(prefix)
highest = fill_prefix(prefix, fill_length, "Z", spaces, dashes)
lowest = fill_prefix(prefix, fill_length, "0", spaces, dashes)
return lowest >= start and highest <= end


def next_alphanum(prefix, length, end, spaces, dashes):
result = increment_alphanum(prefix)
fill_length = length - len(prefix)
if fill_length:
result = fill_prefix(result, length - len(prefix), "0", spaces, dashes)
if result > end:
return None
return result


def find_occurrences(item, iterable):
return [i for i, val in enumerate(iterable) if val == item]


def range_to_prefixes(start, end):
if len(start) != len(end):
raise ValueError(f"{start!r} and {end!r} do not have an equal length")
# Implementation detail: It is assumed that spaces and dashes occur in
# identical places in start and end. If this is not true, the whole thing
# doesn't work.
spaces = find_occurrences(" ", start)
dashes = find_occurrences("-", start)
if find_occurrences(" ", end) != spaces or find_occurrences("-", end) != dashes:
raise ValueError(
f"{start!r} and {end!r} do not have spaces or dashes in identical"
f" locations"
)

prefixes = set()
not_prefixes = set()
alphanum = start
while alphanum:
prefix = alphanum
candidate = prefix
while prefix:
if prefix in not_prefixes:
break
if prefix_works(prefix, start, end, spaces, dashes):
candidate = prefix
prefix = prefix[:-1]
else:
not_prefixes.add(prefix)
break
prefixes.add(candidate)
alphanum = next_alphanum(candidate, len(start), end, spaces, dashes)
return prefixes


@openupgrade.migrate()
def migrate(env, version):
delivery_methods = env["delivery.carrier"].search([])
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

One may restrict to delivery carriers having values in zip_from and / or zip_to.
(As @dansanti mentioned it, you should query this info in DB)

if not delivery_methods:
return
_logger.warning(
cleandoc(
"""
TODO: warn that this creates weird results that are technically
correct.
"""
)
)
for method in delivery_methods:
try:
prefixes = range_to_prefixes(method.zip_from, method.zip_to)
except Exception as error:
_logger.error(
f"Failed to convert the zip range '{method.zip_from} --"

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

hello, , If this code is performed from odoo 16.0 environment, make a AttributeError: 'delivery.carrier' object has no attribute 'zip_from', because zip_from is no longer in 16.0

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ah, I may need to directly query the database for these values.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@carmenbianca any update on this?

f" {method.zip_to}'of delivery method {method!r} to a set of"
f" prefixes. Got error:\n\n{error}"
)
continue

for prefix in prefixes:
try:
prefix_record = env["delivery.zip.prefix"].create({"name": prefix})
# TODO: which exception?
except Exception:
prefix_record = env["delivery.zip.prefix"].search(
[("name", "=", prefix)]
)
method.zip_prefix_ids |= prefix_record
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
---Models in module 'delivery'---
new model delivery.zip.prefix
---Fields in module 'delivery'---
delivery / delivery.carrier / carrier_description (text) : NEW
delivery / delivery.carrier / shipping_insurance (integer) : NEW hasdefault: default
# NOTHING TO DO
delivery / delivery.carrier / zip_from (char) : DEL
delivery / delivery.carrier / zip_prefix_ids (many2many) : NEW relation: delivery.zip.prefix
delivery / delivery.carrier / zip_to (char) : DEL
delivery / delivery.zip.prefix / name (char) : NEW required
# TODO
delivery / product.template / country_of_origin (many2one) : NEW relation: res.country
delivery / stock.move.line / carrier_name (char) : NEW isrelated: related, stored
# NOTHING TO DO
---XML records in module 'delivery'---
NEW ir.actions.act_window: delivery.action_delivery_zip_prefix_list
NEW ir.model.access: delivery.access_delivery_carrier_system
NEW ir.model.access: delivery.access_delivery_zip_prefix
NEW ir.model.access: delivery.access_delivery_zip_prefix_stock_manager
NEW ir.model.constraint: delivery.constraint_delivery_carrier_shipping_insurance_is_percentage
NEW ir.model.constraint: delivery.constraint_delivery_zip_prefix_name_uniq
NEW ir.ui.menu: delivery.menu_delivery_zip_prefix
NEW ir.ui.view: delivery.delivery_report_saleorder_document
NEW ir.ui.view: delivery.label_package_template_view_delivery
NEW ir.ui.view: delivery.stock_move_line_view_search_delivery
NEW ir.ui.view: delivery.view_picking_type_form_delivery
NEW ir.ui.view: delivery.view_stock_rule_form_delivery
# NOTHING TO DO
Loading