Skip to content

Commit 28f8664

Browse files
Merge branch 'feature/WL16411' into trunk
2 parents c27d1fe + 2b44eef commit 28f8664

File tree

4 files changed

+174
-36
lines changed

4 files changed

+174
-36
lines changed

CHANGES.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ v9.1.0
1212
======
1313

1414
- WL#16444: Drop build support for DEB packages
15+
- WL#16411: Improve wheel metadata information for Classic and XDevAPI connectors
1516
- WL#16306: Add support for Python 3.13
1617

1718
v9.0.0

README.rst

Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,15 +8,22 @@ MySQL Connector/Python
88
.. image:: https://img.shields.io/pypi/l/mysql-connector-python.svg
99
:target: https://pypi.org/project/mysql-connector-python/
1010

11+
.. === <mysql> ====
1112
MySQL Connector/Python enables Python programs to access MySQL databases, using
1213
an API that is compliant with the `Python Database API Specification v2.0
1314
(PEP 249) <https://www.python.org/dev/peps/pep-0249/>`_ - We refer to it as the
1415
`Classic API <https://dev.mysql.com/doc/connector-python/en/connector-python-reference.html>`_.
1516

17+
.. === </mysql> ====
18+
19+
.. === <mysqlx> [repl("It also", "MySQL Connector/Python")] ===
1620
It also contains an implementation of the `XDevAPI <https://dev.mysql.com/doc/x-devapi-userguide/en>`_
1721
- An Application Programming Interface for working with the `MySQL Document Store
1822
<https://dev.mysql.com/doc/refman/en/document-store.html>`_.
1923

24+
.. === </mysqlx> ===
25+
26+
.. === <mysql> [repl("* `XDevAPI <https://dev.mysql.com/doc/x-devapi-userguide/en>`_", "")] ====
2027
Features
2128
--------
2229

@@ -25,6 +32,8 @@ Features
2532
* `Telemetry <https://dev.mysql.com/doc/connector-python/en/connector-python-opentelemetry.html>`_
2633
* `XDevAPI <https://dev.mysql.com/doc/x-devapi-userguide/en>`_
2734

35+
.. === </mysql> ====
36+
2837
2938
Installation
3039
------------
@@ -35,13 +44,17 @@ Make sure you have a recent `pip <https://pip.pypa.io/>`_ version installed
3544
on your system. If your system already has ``pip`` installed, you might need
3645
to update it. Or you can use the `standalone pip installer <https://pip.pypa.io/en/latest/installation/>`_.
3746

47+
.. === <mysql> [repl("The *classic API* can be installed via pip as follows:", "")] ===
3848
The *classic API* can be installed via pip as follows:
3949

4050
.. code-block:: bash
4151
4252
$ pip install mysql-connector-python
4353
44-
, similarly, the *XDevAPI* can be installed with:
54+
.. === </mysql> ====
55+
56+
.. === <mysqlx> [repl("similarly, the *XDevAPI* can be installed with:", "")] ===
57+
similarly, the *XDevAPI* can be installed with:
4558

4659
.. code-block:: bash
4760
@@ -50,42 +63,57 @@ The *classic API* can be installed via pip as follows:
5063
Please refer to the `installation tutorial <https://dev.mysql.com/doc/dev/connector-python/installation.html>`_
5164
for installation alternatives of the XDevAPI.
5265

66+
.. === </mysqlx> ===
67+
68+
5369
++++++++++++++++++++
5470
Installation Options
5571
++++++++++++++++++++
5672

5773
Connector packages included in MySQL Connector/Python allow you to install
5874
optional dependencies to unleash certain functionalities.
5975

76+
.. === <mysql> ===
6077
.. code-block:: bash
6178
6279
# 3rd party packages to unleash the telemetry functionality are installed
6380
$ pip install mysql-connector-python[telemetry]
6481
82+
.. === </mysql> ===
83+
84+
.. === <mysqlx> [repl("similarly, for the XDevAPI:", "")] ===
6585
similarly, for the XDevAPI:
6686

6787
.. code-block:: bash
6888
6989
# 3rd party packages to unleash the compression functionality are installed
7090
$ pip install mysqlx-connector-python[compression]
7191
92+
.. === </mysqlx> ===
93+
7294
This installation option can be seen as a shortcut to install all the
7395
dependencies needed by a particular feature. Mind that this is optional
7496
and you are free to install the required dependencies by yourself.
7597

98+
.. === <mysql> [repl("Options for the Classic connector:", "Available options:")] ===
7699
Options for the Classic connector:
77100

78101
* dns-srv
79102
* gssapi
80103
* fido2
81104
* telemetry
82105

106+
.. === </mysql> ===
107+
108+
.. === <mysqlx> [repl("Options for the XDevAPI connector:", "Available options:")] ===
83109
Options for the XDevAPI connector:
84110

85111
* dns-srv
86112
* compression
87113

114+
.. === </mysqlx> ===
88115
116+
.. === <mysql> [repl("Classic", "Sample Code"), repl("-------", "-----------")] ===
89117
Classic
90118
-------
91119

@@ -113,7 +141,9 @@ Classic
113141
# Close connection
114142
cnx.close()
115143
144+
.. === </mysql> ===
116145
146+
.. === <mysqlx> [repl("XDevAPI", "Sample Code"), repl("-------", "-----------")] ===
117147
XDevAPI
118148
-------
119149

@@ -145,7 +175,9 @@ XDevAPI
145175
# Close session
146176
session.close()
147177
178+
.. === </mysqlx> ===
148179
180+
.. === <both> [repl-mysql("- `MySQL Connector/Python X DevAPI Reference <https://dev.mysql.com/doc/dev/connector-python/>`_", ""), repl-mysqlx("- `MySQL Connector/Python Developer Guide <https://dev.mysql.com/doc/connector-python/en/>`_", "")] ===
149181
Additional Resources
150182
--------------------
151183

@@ -157,6 +189,8 @@ Additional Resources
157189
- `Stack Overflow <https://stackoverflow.com/questions/tagged/mysql-connector-python>`_
158190
- `Oracle Blogs <https://blogs.oracle.com/search.html?q=connector-python>`_
159191

192+
.. === </both> ===
193+
160194
161195
Contributing
162196
------------

mysql-connector-python/setup.py

Lines changed: 68 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131

3232
import os
3333
import pathlib
34+
import re
3435
import shutil
3536
import sys
3637

@@ -87,50 +88,64 @@
8788
),
8889
]
8990

90-
LONG_DESCRIPTION = """
91-
MySQL driver written in Python which does not depend on MySQL C client
92-
libraries and implements the DB API v2.0 specification (PEP-249).
93-
"""
94-
9591

9692
def main() -> None:
9793
setup(
9894
name="mysql-connector-python",
9995
version=VERSION_TEXT,
100-
description="MySQL driver written in Python",
101-
long_description=LONG_DESCRIPTION,
96+
description=(
97+
"A self-contained Python driver for communicating with MySQL "
98+
"servers, using an API that is compliant with the Python "
99+
"Database API Specification v2.0 (PEP 249)."
100+
),
101+
long_description=get_long_description(),
102+
long_description_content_type="text/x-rst",
102103
author="Oracle and/or its affiliates",
103104
author_email="",
104105
license="GNU GPLv2 (with FOSS License Exception)",
105-
keywords="mysql db",
106-
url="http://dev.mysql.com/doc/connector-python/en/index.html",
107-
download_url="http://dev.mysql.com/downloads/connector/python/",
106+
keywords=[
107+
"mysql",
108+
"database",
109+
"db",
110+
"connector",
111+
"driver",
112+
],
113+
project_urls={
114+
"Homepage": "https://dev.mysql.com/doc/connector-python/en/",
115+
"Documentation": "https://dev.mysql.com/doc/connector-python/en/",
116+
"Downloads": "https://dev.mysql.com/downloads/connector/python/",
117+
"Release Notes": "https://dev.mysql.com/doc/relnotes/connector-python/en/",
118+
"Source Code": "https://github.com/mysql/mysql-connector-python",
119+
"Bug System": "https://bugs.mysql.com/",
120+
"Slack": "https://mysqlcommunity.slack.com/messages/connectors",
121+
"Forums": "https://forums.mysql.com/list.php?50",
122+
"Blog": "https://blogs.oracle.com/mysql/",
123+
},
108124
package_dir={"": "lib"},
109125
packages=find_packages(where="lib"),
110126
classifiers=[
111127
"Development Status :: 5 - Production/Stable",
112-
"Environment :: Other Environment",
113128
"Intended Audience :: Developers",
114129
"Intended Audience :: Education",
115-
"Intended Audience :: Information Technology",
116-
"Intended Audience :: System Administrators",
117130
"License :: OSI Approved :: GNU General Public License (GPL)",
118-
"Operating System :: OS Independent",
131+
"Operating System :: MacOS :: MacOS X",
132+
"Operating System :: Microsoft :: Windows",
133+
"Operating System :: POSIX :: Linux",
134+
"Operating System :: Unix",
119135
"Programming Language :: Python :: 3",
120-
"Programming Language :: Python :: 3.8",
121136
"Programming Language :: Python :: 3.9",
122137
"Programming Language :: Python :: 3.10",
123138
"Programming Language :: Python :: 3.11",
124139
"Programming Language :: Python :: 3.12",
125140
"Programming Language :: Python :: 3.13",
126141
"Topic :: Database",
127142
"Topic :: Software Development",
128-
"Topic :: Software Development :: Libraries :: Application Frameworks",
129143
"Topic :: Software Development :: Libraries :: Python Modules",
144+
"Typing :: Typed",
130145
],
131146
ext_modules=EXTENSIONS,
132147
cmdclass=COMMAND_CLASSES,
133-
python_requires=">=3.8",
148+
python_requires=">=3.9",
134149
extras_require={
135150
"dns-srv": ["dnspython==2.6.1"],
136151
"gssapi": ["gssapi>=1.6.9,<=1.8.2"],
@@ -152,6 +167,42 @@ def copy_metadata_files() -> None:
152167
shutil.copy(pathlib.Path(os.getcwd(), f"../{filename}"), pathlib.Path(f"./"))
153168

154169

170+
def get_long_description() -> str:
171+
"""Extracts a long description from the README.rst file that is suited for this specific package.
172+
"""
173+
with open(pathlib.Path(os.getcwd(), "../README.rst")) as file_handle:
174+
# The README.rst text is meant to be shared by both mysql and mysqlx packages, so after getting it we need to
175+
# parse it in order to remove the bits of text that are not meaningful for this package (mysql)
176+
long_description = file_handle.read()
177+
block_matches = re.finditer(
178+
pattern=(
179+
r'(?P<module_start>\.{2}\s+={2,}\s+(?P<module_tag>\<(?P<module_name>mysql|mysqlx|both)\>)(?P<repls>\s+'
180+
r'\[(?:(?:,\s*)?(?:repl(?:-mysql(?:x)?)?)\("(?:[^"]+)",\s*"(?:[^"]*)"\))+\])?\s+={2,})'
181+
r'(?P<block_text>.+?(?=\.{2}\s+={2,}))(?P<module_end>\.{2}\s+={2,}\s+\</(?P=module_name)\>\s+={2,})'
182+
),
183+
string=long_description,
184+
flags=re.DOTALL)
185+
for block_match in block_matches:
186+
if block_match.group("module_name") == 'mysqlx':
187+
long_description = long_description.replace(block_match.group(), "")
188+
else:
189+
block_text = block_match.group("block_text")
190+
if block_match.group("repls"):
191+
repl_matches = re.finditer(pattern=r'(?P<repl_name>repl(?:-mysql(?:x)?)?)\("'
192+
r'(?P<repl_source>[^"]+)",\s*"(?P<repl_target>[^"]*)"\)+',
193+
string=block_match.group("repls"))
194+
for repl_match in repl_matches:
195+
repl_name = repl_match.group("repl_name")
196+
repl_source = repl_match.group("repl_source")
197+
repl_target = repl_match.group("repl_target")
198+
if repl_target is None:
199+
repl_target = ""
200+
if repl_name == "repl" or repl_name.endswith("mysql"):
201+
block_text = block_text.replace(repl_source, repl_target)
202+
long_description = long_description.replace(block_match.group(), block_text)
203+
return long_description
204+
205+
155206
def remove_metadata_files() -> None:
156207
"""Remove files copied by `copy_metadata_files()`"""
157208
for filename in METADATA_FILES:

0 commit comments

Comments
 (0)