2019-02-28 20:45:31 +07:00
|
|
|
# -*- coding: utf-8 -*-
|
2019-11-07 14:14:45 +07:00
|
|
|
import itertools
|
|
|
|
import time
|
|
|
|
|
2019-02-28 20:45:31 +07:00
|
|
|
|
[FIX] forwardport: don't break forward porting on huge conflicts
On forward-porting, odoo/odoo#170183 generates a conflict on pretty
much every one of the 1111 files it touches, because they are
modify/delete conflicts that generates a conflict message over 200
bytes per file, which is over 200kB of output.
For this specific scenario, the commit message was being passed
through arguments to the `git` command, resulting in a command line
exceeding `MAX_ARG_STRLEN`[^1]. The obvious way to fix this is to pass
the commit message via stdin as is done literally in the line above
where we just copy a non-generated commit message.
However I don't think hundreds of kbytes worth of stdout[^2] is of any
use, so shorten that a bit, and stderr while at it.
Don't touch the commit message size for now, possibly forever, but
note that some log diving reveals a commit with a legit 18kB message
(odoo/odoo@42a3b704f7c7889a74338253138d0201d3b6e7a3) so if we want to
restrict that the limit should be at least 32k, and possibly 64. But
it might be a good idea to make that limit part of the ready / merge
checks too, rather than cut things off or trigger errors during
staging.
Fixes #900
[^1]: Most resources on "Argument list too long" reference `ARG_MAX`,
but on both my machine and the server it is 2097152 (25% of the
default stack), which is ~10x larger than the commit message we
tried to generate. The actual limit is `MAX_ARG_STRLEN` which
can't be queried directly but is essentially hard-coded to
PAGE_SIZE * 32 = 128kiB, which tracks.
[^2]: Somewhat unexpectedly, that's where `git-cherry-pick` sends the
conflict info.
2024-06-25 18:11:32 +07:00
|
|
|
def shorten(text_ish, length, cont='...'):
|
2019-02-28 20:45:31 +07:00
|
|
|
""" If necessary, cuts-off the text or bytes input and appends ellipsis to
|
|
|
|
signal the cutoff, such that the result is below the provided length
|
|
|
|
(according to whatever "len" means on the text-ish so bytes or codepoints
|
|
|
|
or code units).
|
|
|
|
"""
|
|
|
|
if len(text_ish or ()) <= length:
|
|
|
|
return text_ish
|
|
|
|
|
|
|
|
if isinstance(text_ish, bytes):
|
|
|
|
cont = cont.encode('ascii') # whatever
|
|
|
|
# add enough room for the ellipsis
|
[FIX] forwardport: don't break forward porting on huge conflicts
On forward-porting, odoo/odoo#170183 generates a conflict on pretty
much every one of the 1111 files it touches, because they are
modify/delete conflicts that generates a conflict message over 200
bytes per file, which is over 200kB of output.
For this specific scenario, the commit message was being passed
through arguments to the `git` command, resulting in a command line
exceeding `MAX_ARG_STRLEN`[^1]. The obvious way to fix this is to pass
the commit message via stdin as is done literally in the line above
where we just copy a non-generated commit message.
However I don't think hundreds of kbytes worth of stdout[^2] is of any
use, so shorten that a bit, and stderr while at it.
Don't touch the commit message size for now, possibly forever, but
note that some log diving reveals a commit with a legit 18kB message
(odoo/odoo@42a3b704f7c7889a74338253138d0201d3b6e7a3) so if we want to
restrict that the limit should be at least 32k, and possibly 64. But
it might be a good idea to make that limit part of the ready / merge
checks too, rather than cut things off or trigger errors during
staging.
Fixes #900
[^1]: Most resources on "Argument list too long" reference `ARG_MAX`,
but on both my machine and the server it is 2097152 (25% of the
default stack), which is ~10x larger than the commit message we
tried to generate. The actual limit is `MAX_ARG_STRLEN` which
can't be queried directly but is essentially hard-coded to
PAGE_SIZE * 32 = 128kiB, which tracks.
[^2]: Somewhat unexpectedly, that's where `git-cherry-pick` sends the
conflict info.
2024-06-25 18:11:32 +07:00
|
|
|
return text_ish[:length-len(cont)] + cont
|
2019-11-07 14:14:45 +07:00
|
|
|
|
|
|
|
BACKOFF_DELAYS = (0.1, 0.2, 0.4, 0.8, 1.6)
|
|
|
|
def backoff(func=None, *, delays=BACKOFF_DELAYS, exc=Exception):
|
|
|
|
if func is None:
|
|
|
|
return lambda func: backoff(func, delays=delays, exc=exc)
|
|
|
|
|
|
|
|
for delay in itertools.chain(delays, [None]):
|
|
|
|
try:
|
|
|
|
return func()
|
|
|
|
except exc:
|
|
|
|
if delay is None:
|
|
|
|
raise
|
|
|
|
time.sleep(delay)
|
2023-02-14 19:38:37 +07:00
|
|
|
|
|
|
|
def make_message(pr_dict):
|
|
|
|
title = pr_dict['title'].strip()
|
|
|
|
body = (pr_dict.get('body') or '').strip()
|
|
|
|
return f'{title}\n\n{body}' if body else title
|