diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml new file mode 100644 index 0000000..5ef1422 --- /dev/null +++ b/.github/workflows/ci.yml @@ -0,0 +1,157 @@ +name: Run Tests + +on: + workflow_dispatch: + push: + branches: + - '*' + tags-ignore: + - '*' + pull_request: + create: + +env: + PKG_NAME: Serd + PKG_UBUNTU: libserd-dev + PKG_HOMEBREW: serd + PKG_MSYS2_MINGW64: mingw-w64-x86_64-serd + PKG_MSYS2_MINGW64_DEPS: >- + base-devel + unzip + mingw-w64-x86_64-toolchain + mingw-w64-x86_64-perl + mingw-w64-x86_64-curl + mingw-w64-x86_64-meson + mingw-w64-x86_64-ninja + mingw-w64-x86_64-pkg-config + +jobs: + notify: + runs-on: ubuntu-latest + continue-on-error: true + if: ${{ always() }} + steps: + - uses: perlrdf/devops/github-actions/irc-notifications@main + with: + target-notifications: true + dist: + if: ${{ github.event_name == 'push' || github.event_name == 'pull_request' }} + name: Make distribution + runs-on: ubuntu-latest + outputs: + min-perl-version: ${{ steps.build-dist.outputs.min-perl-version }} + steps: + - name: Checkout code + uses: actions/checkout@v3 + - id: build-dist + uses: perlrdf/devops/github-actions/build-dist@main + with: + dist-perl-deps-develop: strict # Add modules + test: + needs: [ 'dist', 'notify' ] + runs-on: ${{ matrix.os }} + defaults: + run: + # bash on macos and linux + # powershell on windows + strawberry perl + # msys2 {0} on windows + msys2 + shell: >- + ${{ fromJSON( '["", "bash {0}"]' )[ startsWith(matrix.os, 'ubuntu-' ) || startsWith(matrix.os, 'macos-') ] + }}${{ fromJSON( '["", "powershell {0}"]' )[ startsWith(matrix.os, 'windows-') && matrix.dist == 'strawberry' ] + }}${{ fromJSON( '["", "msys2 {0}"]' )[ startsWith(matrix.os, 'windows-') && matrix.dist == 'msys2' ] }} + strategy: + fail-fast: false + matrix: + os: [ubuntu-latest] + perl-version: ['5.8', '5.20', '5.30', '5.34'] + alien-install-type: [ 'system', 'share' ] + include: + # Windows strawberry | share + - { perl-version: '5.34' , os: windows-latest , dist: strawberry , alien-install-type: 'share' } + # Windows msys2 | system, share + - { perl-version: '5.34' , os: windows-latest , dist: msys2 , alien-install-type: 'system' } + - { perl-version: '5.34' , os: windows-latest , dist: msys2 , alien-install-type: 'share' } + # macOS | system, share + - { perl-version: '5.34' , os: macos-11 , alien-install-type: 'system' } + - { perl-version: '5.34' , os: macos-11 , alien-install-type: 'share' } + name: Perl ${{ matrix.perl-version }} on ${{ matrix.os }} with install-type ${{ matrix.alien-install-type }}, dist ${{ matrix.dist }} + + steps: + - name: Get dist artifact + uses: actions/download-artifact@v3 + with: + name: dist + + # Setup system package + - name: Setup system ${{ env.PKG_NAME }} (apt) + if: runner.os == 'Linux' && matrix.alien-install-type == 'system' + run: | + sudo apt-get -y update && sudo apt-get install -y ${{ env.PKG_UBUNTU }} + - name: Setup system ${{ env.PKG_NAME }} (homebrew) + if: runner.os == 'macOS' && matrix.alien-install-type == 'system' + run: | + brew install ${{ env.PKG_HOMEBREW }} + - name: Set up MSYS2 + uses: msys2/setup-msys2@v2 + if: runner.os == 'Windows' && matrix.dist == 'msys2' + with: + update: true + install: ${{ env.PKG_MSYS2_MINGW64_DEPS }} + - name: Set up ${{ env.PKG_NAME }} (MSYS2/MinGW pacman) + if: runner.os == 'Windows' && matrix.dist == 'msys2' && matrix.alien-install-type == 'system' + shell: msys2 {0} + run: | + pacman -S --needed --noconfirm ${{ env.PKG_MSYS2_MINGW64 }} + + # Setup Perl + - name: Set up perl + uses: shogo82148/actions-setup-perl@v1 + if: runner.os != 'Windows' + with: + perl-version: ${{ matrix.perl-version }} + - name: Set up perl (Strawberry) + uses: shogo82148/actions-setup-perl@v1 + if: runner.os == 'Windows' && matrix.dist == 'strawberry' + with: + distribution: 'strawberry' + + - run: perl -V + - name: Install cpanm + if: runner.os == 'Windows' && matrix.dist == 'msys2' + run: + yes | cpan -T App::cpanminus || true + + - name: Install Perl deps + run: | + cpanm --notest --installdeps . + + - name: Install share install deps before setting ALIEN_INSTALL_TYPE + if: matrix.alien-install-type == 'share' + run: | + cpanm --notest Alien::Meson Alien::Ninja Net::SSLeay IO::Socket::SSL + + - name: Set ALIEN_INSTALL_TYPE + shell: bash + run: | + echo "ALIEN_INSTALL_TYPE=${{ matrix.alien-install-type }}" >> $GITHUB_ENV + + - name: Set ALIEN_BUILD_PKG_CONFIG + if: runner.os == 'Windows' && matrix.dist == 'msys2' + run: | + echo "ALIEN_BUILD_PKG_CONFIG=PkgConfig::CommandLine" >> $GITHUB_ENV + + - name: Run tests + env: + ALIEN_BUILD_GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + run: | + cpanm --verbose --test-only . + build-status: + runs-on: ubuntu-latest + continue-on-error: true + if: ${{ always() }} + needs: test + steps: + - uses: perlrdf/devops/github-actions/irc-notifications@main + with: + target-build-status: true + needs: ${{ toJSON(needs) }} diff --git a/alienfile b/alienfile index 1a38646..d7a5df1 100644 --- a/alienfile +++ b/alienfile @@ -2,10 +2,14 @@ use alienfile; plugin PkgConfig => 'serd-0'; +eval { + require Alien::Meson; + Alien::Meson->_apply_destdir_prefix_hack; +}; + share { - requires 'Alien::Build::Plugin::Gather::Dino'; requires 'Alien::Build::Plugin::Download::GitLab'; - requires 'Alien::Meson'; + requires 'Alien::Meson' => '0.06'; requires 'Alien::Ninja'; # https://gitlab.com/drobilla/serd @@ -18,17 +22,30 @@ share { plugin Extract => 'tar.gz'; + meta->prop->{destdir} = 1; my $build_dir = '_build'; build [ - [ '%{meson}', 'setup', - '--prefix=%{.install.prefix}', - '--libdir=lib', - '--buildtype=release', - '-Ddocs=disabled', # no docs - $build_dir ], + sub { + my $build = shift; + Alien::Build::CommandSequence->new([ + Alien::Meson->exe, 'setup', + ( + $^O ne 'MSWin32' + ? ( '-Ddefault_library=both', ) # both static and shared + : () + ), + '--prefix=%{.install.prefix}', + '--libdir=lib', + '--buildtype=release', + '-Ddocs=disabled', # no docs + $build_dir, + ])->execute($build); + }, [ '%{ninja}', qw(-C), $build_dir, "test" ], [ '%{ninja}', qw(-C), $build_dir, 'install' ], ]; - plugin 'Gather::Dino'; + if( $^O ne 'MSWin32' ) { + plugin 'Gather::IsolateDynamic'; + } } diff --git a/dist.ini b/dist.ini index 96f466e..54db98b 100644 --- a/dist.ini +++ b/dist.ini @@ -6,7 +6,25 @@ copyright_year = 2023 version = 0.01 -[@Starter] -revision = 5 +; has to come before Git::Commit +[NextRelease] +[PkgVersion] +[@Starter::Git] +revision = 5 +[AutoPrereqs] [AlienBuild] +; authordep Alien::Build::Plugin::Download::GitLab +[CheckChangesHasContent] +[GithubMeta] +issues = 1 +[ReadmeAnyFromPod] +type = markdown +location = root +filename = README.md +phase = release +[Regenerate::AfterReleasers] +plugin = ReadmeAnyFromPod + +[MetaResources] +x_IRC = irc://irc.perl.org/#perlrdf diff --git a/lib/Alien/Serd.pm b/lib/Alien/Serd.pm index 8b10470..4232237 100644 --- a/lib/Alien/Serd.pm +++ b/lib/Alien/Serd.pm @@ -5,6 +5,18 @@ use warnings; use base qw( Alien::Base ); use 5.008004; +use File::Spec; +use ExtUtils::PkgConfig; + +sub pkg_config_path { + my ($class) = @_; + if( $class->install_type eq 'share' ) { + return File::Spec->catfile( File::Spec->rel2abs($class->dist_dir), qw(lib pkgconfig) ); + } else { + return ExtUtils::PkgConfig->variable('serd-0', 'pcfiledir'); + } +} + 1; =head1 NAME diff --git a/t/alien_serd.t b/t/alien_serd.t index 5cc1499..319d063 100644 --- a/t/alien_serd.t +++ b/t/alien_serd.t @@ -2,31 +2,49 @@ use Test2::V0; use Test::Alien; use Test::Alien::Diag; use Alien::Serd; +use File::Which; alien_diag 'Alien::Serd'; alien_ok 'Alien::Serd'; -# run_ok([ ... ]) -# ->success -# ->out_like(qr/ ... /); - -# my $xs = <<'END'; -# #include "EXTERN.h" -# #include "perl.h" -# #include "XSUB.h" -# ... -# -# MODULE = main PACKAGE = main -# -# ... -# END -# xs_ok $xs, with_subtest { -# ... -# }; - -# ffi_ok { symbols => [...] }, with_subtest { -# my $ffi = shift; -# ... -# }; +# NOTE Disable tool for now +#if( which 'serdi' ) { +# run_ok([ qw(serdi --version) ]) +# ->success +# ->out_like(qr/serdi\s+([0-9.]+)/); +#} + +my $xs = <<'END'; +#include "EXTERN.h" +#include "perl.h" +#include "XSUB.h" + +#include "serd/serd.h" + +bool wrap_serd_uri_string_has_scheme( const char* class, const uint8_t *utf8) { + return serd_uri_string_has_scheme(utf8); +} + +MODULE = main PACKAGE = main + +bool wrap_serd_uri_string_has_scheme(class, utf8) + const char* class + const char* utf8 + +END +xs_ok $xs, with_subtest { + my ($module) = @_; + ok !! $module->wrap_serd_uri_string_has_scheme("http://example.com"), 'has scheme'; + ok ! $module->wrap_serd_uri_string_has_scheme("example.com"), 'no scheme'; +}; + +ffi_ok { symbols => [ 'serd_uri_string_has_scheme' ] }, with_subtest { + my $ffi = shift; + my $serd_uri_string_has_scheme = $ffi->function( serd_uri_string_has_scheme => ['string'] => 'bool' ); + + ok !! $serd_uri_string_has_scheme->("http://example.com"), 'has scheme'; + ok ! $serd_uri_string_has_scheme->("example.com"), 'no scheme'; + +}; done_testing;