Script 'mail_helper' called by obssrc Hello community, here is the log from the commit of package b4 for openSUSE:Factory checked in at 2023-03-11 18:24:05 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/b4 (Old) and /work/SRC/openSUSE:Factory/.b4.new.31432 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "b4" Sat Mar 11 18:24:05 2023 rev:33 rq:1070834 version:0.12.2 Changes: -------- --- /work/SRC/openSUSE:Factory/b4/b4.changes 2023-03-06 18:55:32.412661296 +0100 +++ /work/SRC/openSUSE:Factory/.b4.new.31432/b4.changes 2023-03-11 18:24:46.083108261 +0100 @@ -1,0 +2,11 @@ +Sat Mar 11 08:51:30 UTC 2023 - Jiri Slaby <jsl...@suse.cz> + +- update to 0.12.2: + * prep: add ability to use markdown in the cover content (requires + escaping the leading "#" as ">#" that is stripped on cover letter + rendering) + * send: don't require vN to --resend (will resend the latest version) + * test: don't require running from git + * plus several bugfixes mostly dealing with corner-case conditions + +------------------------------------------------------------------- Old: ---- b4-0.12.1.tar.gz New: ---- b4-0.12.2.tar.gz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ b4.spec ++++++ --- /var/tmp/diff_new_pack.BOskfI/_old 2023-03-11 18:24:46.427110053 +0100 +++ /var/tmp/diff_new_pack.BOskfI/_new 2023-03-11 18:24:46.431110074 +0100 @@ -19,7 +19,7 @@ %{?!python_module:define python_module() python-%{**} python3-%{**}} %define pythons python3 Name: b4 -Version: 0.12.1 +Version: 0.12.2 Release: 0 Summary: Helper scripts for kernel.org patches License: GPL-2.0-or-later ++++++ b4-0.12.1.tar.gz -> b4-0.12.2.tar.gz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/b4/__init__.py new/b4-0.12.2/b4/__init__.py --- old/b4-0.12.1/b4/__init__.py 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/b4/__init__.py 2023-03-10 21:47:51.000000000 +0100 @@ -59,7 +59,7 @@ # global setting allowing us to turn off networking can_network = True -__VERSION__ = '0.12.1' +__VERSION__ = '0.12.2' PW_REST_API_VERSION = '1.2' @@ -1040,37 +1040,7 @@ self.date = self.date.replace(tzinfo=datetime.timezone.utc) # walk until we find the first text/plain part - mcharset = self.msg.get_content_charset() - if not mcharset: - mcharset = 'utf-8' - self.charset = mcharset - - for part in msg.walk(): - cte = part.get_content_type() - if cte.find('/plain') < 0 and cte.find('/x-patch') < 0: - continue - payload = part.get_payload(decode=True) - if payload is None: - continue - pcharset = part.get_content_charset() - if not pcharset: - pcharset = mcharset - try: - payload = payload.decode(pcharset, errors='replace') - self.charset = pcharset - except LookupError: - # what kind of encoding is that? - # Whatever, we'll use utf-8 and hope for the best - payload = payload.decode('utf-8', errors='replace') - part.set_param('charset', 'utf-8') - self.charset = 'utf-8' - if self.body is None: - self.body = payload - continue - # If we already found a body, but we now find something that contains a diff, - # then we prefer this part - if DIFF_RE.search(payload): - self.body = payload + self.body, self.charset = LoreMessage.get_payload(self.msg) if self.body is None: # Woah, we didn't find any usable parts @@ -1093,7 +1063,7 @@ if self.reply: for trailer in trailers: # These are commonly part of patch/commit metadata - badtrailers = {'from', 'author', 'cc', 'to'} + badtrailers = {'from', 'author', 'cc', 'to', 'date', 'subject'} if trailer.lname not in badtrailers: self.trailers.append(trailer) @@ -1237,10 +1207,14 @@ if len(bb) > bl: self.body = bb[:bl].decode() # This may have potentially resulted in in-body From/Subject being removed, - # so make sure we account for this in the message headers - self.lsubject.subject = self.subject = i.get('Subject') - self.fromname = i.get('Author') - self.fromemail = i.get('Email') + # so make sure we put them back into the body if they are different + ibh = list() + if i.get('Subject') != self.subject: + ibh.append('Subject: ' + i.get('Subject')) + if i.get('Email') != self.fromemail or i.get('Author') != self.fromname: + ibh.append('From: ' + format_addrs([(i.get('Author'), i.get('Email'))])) + if len(ibh): + self.body = '\n'.join(ibh) + '\n\n' + self.body def _load_patatt_attestors(self) -> None: if not can_patatt: @@ -1397,6 +1371,43 @@ return '\n'.join(out) @staticmethod + def get_payload(msg: email.message.Message) -> Tuple[str, str]: + # walk until we find the first text/plain part + mcharset = msg.get_content_charset() + if not mcharset: + mcharset = 'utf-8' + + mbody = None + for part in msg.walk(): + cte = part.get_content_type() + if cte.find('/plain') < 0 and cte.find('/x-patch') < 0: + continue + payload = part.get_payload(decode=True) + if payload is None: + continue + pcharset = part.get_content_charset() + if not pcharset: + pcharset = mcharset + try: + payload = payload.decode(pcharset, errors='replace') + mcharset = pcharset + except LookupError: + # what kind of encoding is that? + # Whatever, we'll use utf-8 and hope for the best + payload = payload.decode('utf-8', errors='replace') + part.set_param('charset', 'utf-8') + mcharset = 'utf-8' + if mbody is None: + mbody = payload + continue + # If we already found a body, but we now find something that contains a diff, + # then we prefer this part + if DIFF_RE.search(payload): + mbody = payload + + return mbody, mcharset + + @staticmethod def clean_header(hdrval): if hdrval is None: return '' diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/b4/command.py new/b4-0.12.2/b4/command.py --- old/b4-0.12.1/b4/command.py 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/b4/command.py 2023-03-10 21:47:51.000000000 +0100 @@ -317,7 +317,7 @@ sp_send.add_argument('--cc', nargs='+', help='Addresses to add to the Cc: list') sp_send.add_argument('--not-me-too', action='store_true', default=False, help='Remove yourself from the To: or Cc: list') - sp_send.add_argument('--resend', metavar='vN', default=None, + sp_send.add_argument('--resend', metavar='vN', nargs='?', const='latest', help='Resend a previously sent version of the series') sp_send.add_argument('--no-sign', action='store_true', default=False, help='Do not add the cryptographic attestation signature header') diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/b4/ez.py new/b4-0.12.2/b4/ez.py --- old/b4-0.12.1/b4/ez.py 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/b4/ez.py 2023-03-10 21:47:51.000000000 +0100 @@ -288,6 +288,9 @@ logger.debug('Unrecognized cover letter format, will use as-is') cover = cmsg.body + # Escape lines starting with "#" so they don't get lost + cover = re.sub(r'^(#.*)$', r'>\1', cover, flags=re.M) + cover = (f'{cmsg.subject}\n\n' f'EDITME: Imported from f{msgid}\n' f' Please review before sending.\n\n') + cover @@ -452,7 +455,8 @@ cover = ('EDITME: cover title for %s' % seriesname, '', '# Lines starting with # will be removed from the cover letter. You can', - '# use them to add notes or reminders to yourself.', + '# use them to add notes or reminders to yourself. If you want to use', + '# markdown headers in your cover letter, start the line with ">#".', '', 'EDITME: describe the purpose of this series. The information you put', 'here will be used by the project maintainer to make a decision whether', @@ -562,8 +566,11 @@ logger.debug('tracking data: %s', tracking) if strip_comments: cover = re.sub(r'^#.*$', '', cover, flags=re.M) + # Unescape markdown headers + cover = re.sub(r'^>(#.*)$', r'\1', cover, flags=re.M) while '\n\n\n' in cover: cover = cover.replace('\n\n\n', '\n\n') + return cover.strip(), tracking @@ -826,7 +833,7 @@ if not msg: continue commit_map[commit] = msg - body = msg.get_payload(decode=True).decode() + body, charset = b4.LoreMessage.get_payload(msg) patchid = b4.LoreMessage.get_patch_id(body) ls = b4.LoreSubject(msg.get('subject')) by_subject[ls.subject] = commit @@ -876,7 +883,8 @@ logger.debug('No match for %s', lmsg.full_subject) continue - parts = b4.LoreMessage.get_body_parts(commit_map[commit].get_payload(decode=True).decode()) + mbody, mcharset = b4.LoreMessage.get_payload(commit_map[commit]) + parts = b4.LoreMessage.get_body_parts(mbody) for fltr in addtrailers: if fltr not in parts[2]: if commit not in updates: @@ -940,10 +948,13 @@ def get_series_details(start_commit: Optional[str] = None) -> Tuple[str, str, str, List[str], str, str]: if not start_commit: start_commit = get_series_start() - gitargs = ['rev-parse', f'{start_commit}~1'] - lines = b4.git_get_command_lines(None, gitargs) - base_commit = lines[0] strategy = get_cover_strategy() + if strategy == 'commit': + gitargs = ['rev-parse', f'{start_commit}~1'] + lines = b4.git_get_command_lines(None, gitargs) + base_commit = lines[0] + else: + base_commit = start_commit if strategy == 'tip-commit': cover_commit = find_cover_commit() endrange = b4.git_revparse_obj(f'{cover_commit}~1') @@ -1045,7 +1056,7 @@ def mixin_cover(cbody: str, patches: List[Tuple[str, email.message.Message]]) -> None: msg = patches[0][1] - pbody = msg.get_payload(decode=True).decode() + pbody, pcharset = b4.LoreMessage.get_payload(msg) pheaders, pmessage, ptrailers, pbasement, psignature = b4.LoreMessage.get_body_parts(pbody) cheaders, cmessage, ctrailers, cbasement, csignature = b4.LoreMessage.get_body_parts(cbody) nbparts = list() @@ -1257,10 +1268,16 @@ tag_msg = None cl_msgid = None if cmdargs.resend: - tagname, revision = get_sent_tagname(mybranch, SENT_TAG_PREFIX, cmdargs.resend) + if cmdargs.resend == 'latest': + cover, tracking = load_cover() + revstr = tracking['series']['revision'] - 1 + else: + revstr = cmdargs.resend + + tagname, revision = get_sent_tagname(mybranch, SENT_TAG_PREFIX, revstr) if revision is None: - logger.critical('Could not figure out revision from %s', cmdargs.resend) + logger.critical('Could not figure out revision from %s', revstr) sys.exit(1) try: @@ -1311,7 +1328,7 @@ for commit, msg in patches: if not msg: continue - body = msg.get_payload(decode=True).decode() + body, charset = b4.LoreMessage.get_payload(msg) btrs, junk = b4.LoreMessage.find_trailers(body) for btr in btrs: if btr.type != 'person': @@ -1899,7 +1916,7 @@ if b4.LoreMessage.get_clean_msgid(msg) == msgid: # Prepare annotated tag body from the cover letter lsubject = b4.LoreSubject(msg.get('subject')) - cbody = msg.get_payload(decode=True).decode() + cbody, charset = b4.LoreMessage.get_payload(msg) prefixes = lsubject.get_extra_prefixes() if prefixes: subject = '[%s] %s' % (' '.join(prefixes), lsubject.subject) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/b4/mbox.py new/b4-0.12.2/b4/mbox.py --- old/b4-0.12.1/b4/mbox.py 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/b4/mbox.py 2023-03-10 21:47:51.000000000 +0100 @@ -533,9 +533,8 @@ continue if not lsub.reply: - payload = msg.get_payload(decode=True) - if isinstance(payload, bytes): - payload = payload.decode() + payload, charset = b4.LoreMessage.get_payload(msg) + if payload: matches = re.search(r'^change-id:\s+(\S+)', payload, flags=re.I | re.M) if matches: logger.debug('Found change-id %s', matches.groups()[0]) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/b4/ty.py new/b4-0.12.2/b4/ty.py --- old/b4-0.12.1/b4/ty.py 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/b4/ty.py 2023-03-10 21:47:51.000000000 +0100 @@ -627,7 +627,7 @@ BRANCH_INFO = dict() - remotecfg = b4.get_config_from_git('branch\\.%s\\.*' % branch) + remotecfg = b4.get_config_from_git('branch\\.%s\\..*' % branch) if remotecfg is None or 'remote' not in remotecfg: # Did not find a matching branch entry, so look at remotes gitargs = ['remote', 'show'] diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/man/b4.5 new/b4-0.12.2/man/b4.5 --- old/b4-0.12.1/man/b4.5 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/man/b4.5 2023-03-10 21:47:51.000000000 +0100 @@ -604,7 +604,7 @@ .INDENT 0.0 .TP .B usage: -b4 send [\-h] [\-d] [\-o OUTPUT_DIR] [\-\-reflect] [\-\-no\-trailer\-to\-cc] [\-\-to TO [TO ...]] [\-\-cc CC [CC ...]] [\-\-not\-me\-too] [\-\-resend RESEND] [\-\-no\-sign] [\-\-web\-auth\-new] [\-\-web\-auth\-verify VERIFY_TOKEN] +b4 send [\-h] [\-d] [\-o OUTPUT_DIR] [\-\-reflect] [\-\-no\-trailer\-to\-cc] [\-\-to TO [TO ...]] [\-\-cc CC [CC ...]] [\-\-not\-me\-too] [\-\-resend [RESEND]] [\-\-no\-sign] [\-\-web\-auth\-new] [\-\-web\-auth\-verify VERIFY_TOKEN] .TP .B options: .INDENT 7.0 @@ -636,9 +636,13 @@ .TP .B \-\-not\-me\-too Remove yourself from the To: or Cc: list +.UNINDENT +.INDENT 7.0 .TP -.BI \-\-resend \ RESEND +.B \-\-resend [RESEND] Resend a previously sent version of the series +.UNINDENT +.INDENT 7.0 .TP .B \-\-no\-sign Do not add the cryptographic attestation signature header diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/man/b4.5.rst new/b4-0.12.2/man/b4.5.rst --- old/b4-0.12.1/man/b4.5.rst 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/man/b4.5.rst 2023-03-10 21:47:51.000000000 +0100 @@ -388,7 +388,7 @@ b4 send ~~~~~~~ usage: - b4 send [-h] [-d] [-o OUTPUT_DIR] [--reflect] [--no-trailer-to-cc] [--to TO [TO ...]] [--cc CC [CC ...]] [--not-me-too] [--resend RESEND] [--no-sign] [--web-auth-new] [--web-auth-verify VERIFY_TOKEN] + b4 send [-h] [-d] [-o OUTPUT_DIR] [--reflect] [--no-trailer-to-cc] [--to TO [TO ...]] [--cc CC [CC ...]] [--not-me-too] [--resend [RESEND]] [--no-sign] [--web-auth-new] [--web-auth-verify VERIFY_TOKEN] options: -h, --help show this help message and exit @@ -409,8 +409,10 @@ --not-me-too Remove yourself from the To: or Cc: list - --resend RESEND + + --resend [RESEND] Resend a previously sent version of the series + --no-sign Do not add the cryptographic attestation signature header diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/b4-0.12.1/tests/conftest.py new/b4-0.12.2/tests/conftest.py --- old/b4-0.12.1/tests/conftest.py 2023-01-26 18:23:45.000000000 +0100 +++ new/b4-0.12.2/tests/conftest.py 2023-03-10 21:47:51.000000000 +0100 @@ -7,7 +7,7 @@ @pytest.fixture(scope="function", autouse=True) def settestdefaults(tmp_path): topdir = b4.git_get_toplevel() - if topdir != os.getcwd(): + if topdir and topdir != os.getcwd(): os.chdir(topdir) b4.can_patatt = False b4.can_network = False