diff --git a/Formula/boost-python3.rb b/Formula/boost-python3.rb new file mode 100644 index 0000000000..9b3eb7836d --- /dev/null +++ b/Formula/boost-python3.rb @@ -0,0 +1,95 @@ +class BoostPython3 < Formula + desc "C++ library for C++/Python3 interoperability" + homepage "https://www.boost.org/" + url "https://dl.bintray.com/boostorg/release/1.66.0/source/boost_1_66_0.tar.bz2" + sha256 "5721818253e6a0989583192f96782c4a98eb6204965316df9f5ad75819225ca9" + head "https://github.com/boostorg/boost.git" + + depends_on "boost" + depends_on "python3" + + needs :cxx11 + + resource "numpy" do + url "https://files.pythonhosted.org/packages/ee/66/7c2690141c520db08b6a6f852fa768f421b0b50683b7bbcd88ef51f33170/numpy-1.14.0.zip" + sha256 "3de643935b212307b420248018323a44ec51987a336d1d747c1322afc3c099fb" + end + + def install + # "layout" should be synchronized with boost + args = ["--prefix=#{prefix}", + "--libdir=#{lib}", + "-d2", + "-j#{ENV.make_jobs}", + "--layout=tagged", + "--user-config=user-config.jam", + "threading=multi,single", + "link=shared,static"] + + # Trunk starts using "clang++ -x c" to select C compiler which breaks C++11 + # handling using ENV.cxx11. Using "cxxflags" and "linkflags" still works. + args << "cxxflags=-std=c++11" + if ENV.compiler == :clang + args << "cxxflags=-stdlib=libc++" << "linkflags=-stdlib=libc++" + end + + # disable python detection in bootstrap.sh; it guesses the wrong include + # directory for Python 3 headers, so we configure python manually in + # user-config.jam below. + inreplace "bootstrap.sh", "using python", "#using python" + + pyver = Language::Python.major_minor_version "python3" + py_prefix = Formula["python3"].opt_frameworks/"Python.framework/Versions/#{pyver}" + + numpy_site_packages = buildpath/"homebrew-numpy/lib/python#{pyver}/site-packages" + numpy_site_packages.mkpath + ENV["PYTHONPATH"] = numpy_site_packages + resource("numpy").stage do + system "python3", *Language::Python.setup_install_args(buildpath/"homebrew-numpy") + end + + # Force boost to compile with the desired compiler + (buildpath/"user-config.jam").write <<~EOS + using darwin : : #{ENV.cxx} ; + using python : #{pyver} + : python3 + : #{py_prefix}/include/python#{pyver}m + : #{py_prefix}/lib ; + EOS + + system "./bootstrap.sh", "--prefix=#{prefix}", "--libdir=#{lib}", + "--with-libraries=python", "--with-python=python3", + "--with-python-root=#{py_prefix}" + + system "./b2", "--build-dir=build-python3", "--stagedir=stage-python3", + "python=#{pyver}", *args + + lib.install Dir["stage-python3/lib/*py*"] + doc.install Dir["libs/python/doc/*"] + end + + test do + (testpath/"hello.cpp").write <<~EOS + #include + char const* greet() { + return "Hello, world!"; + } + BOOST_PYTHON_MODULE(hello) + { + boost::python::def("greet", greet); + } + EOS + + pyincludes = Utils.popen_read("python3-config --includes").chomp.split(" ") + pylib = Utils.popen_read("python3-config --ldflags").chomp.split(" ") + + system ENV.cxx, "-shared", "hello.cpp", "-L#{lib}", "-lboost_python3", "-o", + "hello.so", *pyincludes, *pylib + + output = <<~EOS + import hello + print(hello.greet()) + EOS + assert_match "Hello, world!", pipe_output("python3", output, 0) + end +end