Build MySQL 8 from the source rpm in OL9

After discussing with Simon about some issues when trying to recompile MySQL 8.0.34 on CentOS 9 (see #111159), I also tried it and indeed some dependencies are not listed when compiling via the source RPM.

Let’s see how to recompile the two latest versions of MySQL (8.0.34 and 8.1.0) using the source RPMs.

I use Oracle Linux 9 as build machine.

Getting the source RPM

To get the source RPM, you need first to install the MySQL Community’s repo:

$ sudo dnf install https://dev.mysql.com/get/mysql80-community-release-el9-3.noarch.rpm

Then depending on which version you want to compile, you can use one of the following commands:

For latest 8.0:

$ dnf download --source mysql-community-server

For latest Innovation Release (8.1 at the moment):

$ dnf download --source mysql-community-server --enablerepo mysql-innovation-community

Now you have the src RPM files you can use to rebuild all the RPMS:

$ ls -lh *src.rpm
-rw-r--r--. 1 root root 514M Aug  7 09:30 mysql-community-8.0.34-1.el9.src.rpm
-rw-r--r--. 1 root root 515M Aug  8 21:27 mysql-community-8.1.0-1.el9.src.rpm

Dependencies

To build RPMs, you need at least the following package:

$ sudo dnf install -y rpm-build

Then, if you try to build the downloaded src rpm, some dependencies will be required.

Let’s see how to install them:

$ sudo dnf install -y cmake cyrus-sasl-devel gcc-toolset-12-annobin-annocheck \
    gcc-toolset-12-annobin-plugin-gcc libaio-devel ncurses-devel numactl-devel \ 
    openldap-devel rpcgen perl perl-JSON perl-Time
$ sudo dnf install -y https://yum.oracle.com/repo/OracleLinux/OL9/codeready/builder/x86_64/getPackage/libtirpc-devel-1.3.3-1.el9.x86_64.rpm

There are also some other packages that are required but not listed as BuildRequires in the spec file:

$ sudo dnf install -y krb5-devel libudev-devel libcurl-devel
$ sudo dnf install -y https://yum.oracle.com/repo/OracleLinux/OL9/codeready/builder/x86_64/getPackage/libfido2-devel-1.6.0-7.el9.x86_64.rpm

Building RPMs

Now we are ready to build all the rpms from source.

This is the command to rebuild everything for the version you want:

$ rpmbuild --rebuild mysql-community-8.1.0-1.el9.src.rpm

When done (this takes some time), you will find all the new rpms in ~/rpmbuild/RPMS/x86_64/:

$ ls -lh 
-rw-r--r--. 1 root root 3.5M Aug  8 23:24 mysql-community-client-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root  23M Aug  8 23:24 mysql-community-client-debuginfo-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 1.4M Aug  8 23:25 mysql-community-client-plugins-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 1.9M Aug  8 23:24 mysql-community-client-plugins-debuginfo-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 559K Aug  8 23:24 mysql-community-common-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 3.9M Aug  8 23:24 mysql-community-debuginfo-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root  21M Aug  8 23:25 mysql-community-debugsource-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 2.1M Aug  8 23:24 mysql-community-devel-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 2.3M Aug  8 23:25 mysql-community-icu-data-files-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 1.5M Aug  8 23:25 mysql-community-libs-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 2.2M Aug  8 23:24 mysql-community-libs-debuginfo-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root  20M Aug  8 23:24 mysql-community-server-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root  25M Aug  8 23:25 mysql-community-server-debug-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 127M Aug  8 23:28 mysql-community-server-debug-debuginfo-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 181M Aug  8 23:28 mysql-community-server-debuginfo-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 349M Aug  8 23:27 mysql-community-test-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root  18M Aug  8 23:25 mysql-community-test-debuginfo-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 3.7M Aug  8 23:24 mysql-router-community-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root  32M Aug  8 23:24 mysql-router-community-debuginfo-8.1.0-1.el9.x86_64.rpm

Patching MySQL and build the RPMs

From the same source RPM it’s also possible to modify MySQL and create RPMS.

To illustrate this, we will create a RPM for a component of ours.

The first step is to install the RPM package with the source (the one we used to rebuild the packages):

$ rpm -ivh mysql-community-8.1.0-1.el9.src.rpm

The component we will use is uuid_v7 available on GitHub.

The recommended way is to create a patch for the component and then include it in the spec file.

There are plenty methods to create a patch, this is how I personally did:

$ cd /tmp
$ wget https://github.com/lefred/mysql-component-uuid_v7/archive/refs/heads/main.zip
$ unzip main.zip
$ mkdir components components_new
$ mv mysql-component-uuid_v7-main components_new/uuid_v7
$ diff -urN components components_new > mysql-component-uuid_v7.patch

We need to add the patch ~/rpmbuild/SOURCES (where boost and MySQL source tarballs should be already):

$ cp mysql-component-uuid_v7.patch ~/rpmbuild/SOURCES

Now we need to modify the mysql.spec file in ~/rpmbuild/SPECS to include the patch and the new package.

After the last source:

[...]
Source91:     filter-requires.sh

We add the patch:

Patch0:       mysql-component-uuid_v7.patch

Then after the definition and description of the client-plugins package:

[...]
%description    client-plugins
This package contains the client-plugins libraries used by MySQL client applications.

We add the 2 new packages (the normal one and the debug one):

%package        component-uuidv7
Summary:        Adding a UUID v7 generator user function
Group:          Applications/Databases
Provides:       mysql-component-uuidv7 = %{version}-%{release}
Provides:       MySQL-component-uuidv7 = %{version}-%{release}
Requires:       mysql-server = %{version}-%{release}

%description    component-uuidv7
This package contains the component to generate uuid v7 within MySQL Server.

%if 0%{?with_debuginfo}
%package        component-uuidv7-debug
Summary:        Adding a UUID v7 generator user function
Group:          Applications/Databases

%description    component-uuidv7-debug
This package contains the component to generate uuid v7 within MySQL Server with debug info.
%endif # with_debuginfo

We need now to also use our patch, this is done at the end of the %prep section:

%prep
%if 0%{?compatlib}
%setup -q -T -a 0 -a 7 -a 10 -c -n %{src_dir}
%else
%setup -q -T -a 0 -a 10 -c -n %{src_dir}
%endif # 0%{?compatlib}

We need to add:

%patch0 -p1
mv uuid_v7 mysql-%{version}/components

And finally, after the %files libs section:

%files libs
%defattr(-, root, root, -)
%doc %{?license_files_server}
%dir %attr(755, root, root) %{_libdir}/mysql
%attr(644, root, root) %{_sysconfdir}/ld.so.conf.d/mysql-%{_arch}.conf
%{_libdir}/mysql/libmysqlclient.so.22*
%if 0%{?ssl_bundled}
%attr(755, root, root) %{_libdir}/mysql/private/libssl.so
%attr(755, root, root) %{_libdir}/mysql/private/libssl.so.1.1
%attr(755, root, root) %{_libdir}/mysql/private/libcrypto.so
%attr(755, root, root) %{_libdir}/mysql/private/libcrypto.so.1.1
%endif # ssl_bundled

We add the files that must be included in each packages:

%files component-uuidv7
%defattr(-, root, root, -)
%doc %{?license_files_server}
%attr(755, root, root) %{_libdir}/mysql/plugin/component_uuid_v7.so

%if 0%{?with_debuginfo}
%files component-uuidv7-debug
%defattr(-, root, root, -)
%doc %{?license_files_server}
%attr(755, root, root) %{_libdir}/mysql/plugin/component_uuid_v7.so
%attr(755, root, root) %{_libdir}/mysql/plugin/debug/component_uuid_v7.so
#%attr(755, root, root) %{_libdir}/mysql/plugin/component_uuid_v7.so-8.1.0-1.el9.x86_64.debug
%endif # with_debuginfo

We can now compile all the packages using the spec file:

$ rpmbuild -ba mysql.spec

You can also use macro to no redo everything, for example, to not rebuild MySQL Router your can use:

$ rpmbuild -ba mysql.spec --define 'with_router 0'

When finished, you will have a new rpm to install your own component:

$ cd ~/rpmbuild/RPMS/x86_64/
$ ls -lh *uuid*
-rw-r--r--. 1 root root 114K Aug  9 20:00 mysql-community-component-uuidv7-8.1.0-1.el9.x86_64.rpm
-rw-r--r--. 1 root root 169K Aug  9 20:00 mysql-community-component-uuidv7-debug-8.1.0-1.el9.x86_64.rpm

And we can check the info provided by the package:

$ rpm -qi  mysql-community-component-uuidv7-8.1.0-1.el9.x86_64.rpm 
Name        : mysql-community-component-uuidv7
Version     : 8.1.0
Release     : 1.el9
Architecture: x86_64
Install Date: (not installed)
Group       : Applications/Databases
Size        : 520488
License     : Copyright (c) 2000, 2023, Oracle and/or its affiliates. Under GPLv2 license as shown in the Description field.
Signature   : (none)
Source RPM  : mysql-community-8.1.0-1.el9.src.rpm
Build Date  : Wed 09 Aug 2023 06:13:23 PM GMT
Build Host  : build-ol9-x86-64.mysqlpub.mysqlvcn.oraclevcn.com
Packager    : MySQL Release Engineering <mysql-build@oss.oracle.com>
Vendor      : Oracle and/or its affiliates
URL         : http://www.mysql.com/
Summary     : Adding a UUID v7 generator user function
Description :
This package contains the component to generate uuid v7 within MySQL Server.

And the files included in it:

$ rpm -ql mysql-community-component-uuidv7-8.1.0-1.el9.x86_64.rpm 
/usr/lib/.build-id
/usr/lib/.build-id/8e/eb48888cfd2f338d4b11148cd515b9d3ab92ee
/usr/lib64/mysql/plugin/component_uuid_v7.so
/usr/share/doc/mysql-community-component-uuidv7
/usr/share/doc/mysql-community-component-uuidv7/LICENSE
/usr/share/doc/mysql-community-component-uuidv7/README

Conclusion

You have seen how you can build or rebuild MySQL from the source RPM on OL9 (and similar) and you are now also able to patch MySQL and include your patch as part of the rpm or even better if you use a component on it’s own rpm that you can distribute or install easily on multiple instances.

Enjoy compiling MySQL and building RPMs !

In case you are using MySQL 8.1 on OL9 (or similar), here is the RPM of the component if you want to test it:

Subscribe to Blog via Email

Enter your email address to subscribe to this blog and receive notifications of new posts by email.

2 Comments

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.

As MySQL Community Manager, I am an employee of Oracle and the views expressed on this blog are my own and do not necessarily reflect the views of Oracle.

You can find articles I wrote on Oracle’s blog.