diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index ccb67909..dd243234 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -9,12 +9,6 @@ jobs: fail-fast: false matrix: include: - - os: ubuntu-latest - python-version: 2.7 - install: '' - flags: '--coverage' - tests: RMF - build: Debug - os: ubuntu-latest python-version: 3.9 install: '' @@ -57,7 +51,7 @@ jobs: if: matrix.os == 'macos-latest' run: | brew install swig boost log4cxx ${{ matrix.install }} - pip install coverage + pip install coverage numpy - name: Build and test run: | mkdir build diff --git a/CMakeLists.txt b/CMakeLists.txt index 503ca657..d11890ba 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,4 +1,4 @@ -cmake_minimum_required(VERSION 2.8.12) +cmake_minimum_required(VERSION 2.8.12...3.6.0) project(RMF) # needs to be in main CMakeLists.txt @@ -139,8 +139,9 @@ set(LIBRARY_OUTPUT_PATH ${CMAKE_BINARY_DIR}/lib) # Version information set (RMF_VERSION_MAJOR 1) -set (RMF_VERSION_MINOR 5) -set (RMF_VERSION_MICRO 1) +set (RMF_VERSION_MINOR 6) +set (RMF_VERSION_MICRO 0) +math (EXPR RMF_VERSION "${RMF_VERSION_MAJOR} * 100000 + ${RMF_VERSION_MINOR} * 100 + ${RMF_VERSION_MICRO}") set(RMF_SOVERSION "${RMF_VERSION_MAJOR}.${RMF_VERSION_MINOR}" CACHE INTERNAL "" FORCE) set(RMF_HAS_DEBUG_VECTOR 0 CACHE BOOL "Whether to use a bounds checked vector") diff --git a/ChangeLog.md b/ChangeLog.md index 217ffa84..1e9c8abb 100644 --- a/ChangeLog.md +++ b/ChangeLog.md @@ -1,8 +1,16 @@ Change Log {#changelog} ========== +# 1.6.0 - 2023-12-14 # {#changelog_1_6_0} +- RPM packages for IMP for RedHat Linux (and clones such as Alma or Rocky) + and for Fedora are now provided by the + [COPR project](https://copr.fedorainfracloud.org/coprs/salilab/salilab/). +- RMF::decorator::Chain can now store a per-chain sequence offset and UniProt + accession. The offset, which defaults to zero, maps from the sequence index + (which always starts at 1) to the residue index (which may not). + # 1.5.1 - 2023-06-08 # {#changelog_1_5_1} -- Any String or Strings attributes containing fileystem paths are now +- Any String or Strings attributes containing filesystem paths are now rewritten when the RMF static frame is cloned (e.g. during `rmf_slice` or `rmf_cat`) so that they are relative to the new file, not the old one. This relies on the convention that path attributes have names ending in @@ -57,7 +65,7 @@ Change Log {#changelog} be accurately stored in the file.) # 1.1 - 2014-03-07 # {#changelog_1_1} -- To be more consisent, RMF::decorator::Domain and +- To be more consistent, RMF::decorator::Domain and RMF::decorator::Fragment had their access methods modified to include `residue` in the name. - A Pymol plugin was added diff --git a/bin/rmf3_dump.cpp b/bin/rmf3_dump.cpp index d6201697..8f0f7ddd 100644 --- a/bin/rmf3_dump.cpp +++ b/bin/rmf3_dump.cpp @@ -3,7 +3,7 @@ */ #include -#include +#include #include #include #include diff --git a/bin/rmf_cat.cpp b/bin/rmf_cat.cpp index c0d11e15..9ec94438 100644 --- a/bin/rmf_cat.cpp +++ b/bin/rmf_cat.cpp @@ -25,7 +25,7 @@ int main(int argc, char** argv) { "input-files,i", boost::program_options::value >(&inputs), "input rmf file"); - positional_names.push_back("input_1.rmf input_2.rmf ... output.rmf"); + positional_names.emplace_back("input_1.rmf input_2.rmf ... output.rmf"); positional_options_description.add("input-files", -1); process_options(argc, argv); if (inputs.size() < 3) { diff --git a/bin/rmf_interpolate.cpp b/bin/rmf_interpolate.cpp index 983c5e0a..a3f14121 100644 --- a/bin/rmf_interpolate.cpp +++ b/bin/rmf_interpolate.cpp @@ -118,7 +118,7 @@ void interpolate_frames(int num, double noise, double angle_noise, // boost::random_device seed_gen; boost::mt19937 rng; // rng.seed(seed_gen()); - rng.seed(static_cast(std::time(NULL))); + rng.seed(static_cast(std::time(nullptr))); boost::normal_distribution<> nd(0.0, noise); boost::variate_generator > normal_random(rng, nd); diff --git a/bin/rmf_pdb.cpp b/bin/rmf_pdb.cpp index aba75052..9e3b516f 100644 --- a/bin/rmf_pdb.cpp +++ b/bin/rmf_pdb.cpp @@ -148,8 +148,8 @@ RMF_ENABLE_WARNINGS namespace { out << str; } RMF::NodeConstHandles ch = nh.get_children(); - for (unsigned int i = 0; i < ch.size(); ++i) { - current_index = write_atoms(out, current_index, ch[i], ipf, af, cf, rf, + for (const auto &c : ch) { + current_index = write_atoms(out, current_index, c, ipf, af, cf, rf, chain, residue_index, residue_type); } return current_index; diff --git a/bin/rmf_transform.cpp b/bin/rmf_transform.cpp index 25cee949..0f5260ce 100644 --- a/bin/rmf_transform.cpp +++ b/bin/rmf_transform.cpp @@ -67,8 +67,8 @@ void transform(RMF::NodeHandle nh, RMF_TRANSFORM_LIST(cf, Cylinder, coordinates_list); RMF_TRANSFORM_LIST(sf, Segment, coordinates_list); RMF::NodeHandles children = nh.get_children(); - for (unsigned int i = 0; i < children.size(); ++i) { - transform(children[i], ipf, rpf, rff, bf, cf, sf, scale, translation); + for (const auto &child: children) { + transform(child, ipf, rpf, rff, bf, cf, sf, scale, translation); } } } diff --git a/bin/rmf_xml.cpp b/bin/rmf_xml.cpp index 40c3a338..018ba32c 100644 --- a/bin/rmf_xml.cpp +++ b/bin/rmf_xml.cpp @@ -74,14 +74,14 @@ void show_hierarchy(RMF::NodeConstHandle nh, const RMF::Categories& cs, << "type=\"" << nh.get_type() << "\">\n"; if (seen.find(nh) == seen.end()) { if (variables_map.count("verbose")) { - for (unsigned int i = 0; i < cs.size(); ++i) { - show_data_xml(nh, cs[i], out); + for (const auto &c : cs) { + show_data_xml(nh, c, out); } } RMF::NodeConstHandles children = nh.get_children(); - for (unsigned int i = 0; i < children.size(); ++i) { + for (const auto &child : children) { out << "\n"; - show_hierarchy(children[i], cs, seen, out); + show_hierarchy(child, cs, seen, out); out << "\n"; } seen.insert(nh); diff --git a/config.h.in b/config.h.in index 6ce2e0a1..1ef4be00 100644 --- a/config.h.in +++ b/config.h.in @@ -34,6 +34,7 @@ #define RMF_VERSION_MAJOR @RMF_VERSION_MAJOR@ #define RMF_VERSION_MINOR @RMF_VERSION_MINOR@ #define RMF_VERSION_MICRO @RMF_VERSION_MICRO@ +#define RMF_VERSION @RMF_VERSION@ #define RMF_HAS_LOG4CXX @RMF_HAS_LOG4CXX@ #define RMF_HAS_NUMPY @RMF_HAS_NUMPY@ diff --git a/data/uncrustify.cfg b/data/uncrustify.cfg index 27fcfcf1..184f3a73 100644 --- a/data/uncrustify.cfg +++ b/data/uncrustify.cfg @@ -1496,7 +1496,7 @@ cmt_insert_func_header = "" # string # Will substitute $(class) with the class name. cmt_insert_class_header = "" # string -# The filename that contains text to insert before a Obj-C message specification if the method isn't preceeded with a C/C++ comment. +# The filename that contains text to insert before a Obj-C message specification if the method isn't preceded with a C/C++ comment. # Will substitute $(message) with the function name and $(javaparam) with the javadoc @param and @return stuff. cmt_insert_oc_msg_header = "" # string diff --git a/doc/DecoratorsAndAttributes.md b/doc/DecoratorsAndAttributes.md index e7475ab8..89717f59 100644 --- a/doc/DecoratorsAndAttributes.md +++ b/doc/DecoratorsAndAttributes.md @@ -71,7 +71,9 @@ The category name is `sequence` and it includes information about the types and | `residue index` | int | The index of a residue | | `chain id` | string | The chain ID | | `sequence` | string | Primary sequence of a chain | +| `sequence offset`| int | Offset from sequence index to residue index | | `chain type` | string | Type of chain sequence (e.g. Protein, DNA, RNA) | +| `uniprot accession`| string | UniProt accession code for the sequence | | `first residue index` | int | The index of the first residue (in a domain) | | `last residue index` | int | The index of the last residue (in a domain) | | `residue indexes` | ints | The list of indexes in a fragment | diff --git a/doc/Doxyfile.in b/doc/Doxyfile.in index 41ede599..3201f630 100644 --- a/doc/Doxyfile.in +++ b/doc/Doxyfile.in @@ -1089,7 +1089,7 @@ HTML_STYLESHEET = # defined cascading style sheet that is included after the standard style sheets # created by doxygen. Using this option one can overrule certain style aspects. # This is preferred over using HTML_STYLESHEET since it does not replace the -# standard style sheet and is therefor more robust against future updates. +# standard style sheet and is therefore more robust against future updates. # Doxygen will copy the style sheet file to the output directory. For an example # see the documentation. # This tag requires that the tag GENERATE_HTML is set to YES. @@ -1962,9 +1962,9 @@ PREDEFINED = RMF_DOXYGEN \ EXPAND_AS_DEFINED = # If the SKIP_FUNCTION_MACROS tag is set to YES then doxygen's preprocessor will -# remove all refrences to function-like macros that are alone on a line, have an -# all uppercase name, and do not end with a semicolon. Such function macros are -# typically used for boiler-plate code, and will confuse the parser if not +# remove all references to function-like macros that are alone on a line, have +# an all uppercase name, and do not end with a semicolon. Such function macros +# are typically used for boiler-plate code, and will confuse the parser if not # removed. # The default value is: YES. # This tag requires that the tag ENABLE_PREPROCESSING is set to YES. diff --git a/doc/Installation.md b/doc/Installation.md index 99c150f0..45a5d8f8 100644 --- a/doc/Installation.md +++ b/doc/Installation.md @@ -14,6 +14,10 @@ or on a Mac with [Homebrew](https://brew.sh/), install with brew tap salilab/salilab; brew install rmf +or on a Fedora or RedHat Enterprise Linux system, install with + + dnf copr enable salilab/salilab; dnf install RMF + IMP: Download an IMP binary (which includes RMF) from the [IMP download page](https://integrativemodeling.org/download.html). diff --git a/doc/Library.md b/doc/Library.md index a3027402..43a1dee5 100644 --- a/doc/Library.md +++ b/doc/Library.md @@ -32,7 +32,7 @@ its hierarchy and objects in the program accessing. The methods RMF::FileConstHandle::get_node_handle_from_association(), RMF::NodeConstHandle::set_association() and RMF::NodeConstHandle::get_assocation() can be used to take advantage of -this. The idea is that one can store pointers to the programatic +this. The idea is that one can store pointers to the programmatic data structures corresponding to the nodes and so avoid maintaining ones own lookup table. Any function used in an association must support a `get_uint()` function. An implementation is provided for pointers. diff --git a/examples/cloning.py b/examples/cloning.py index 81fa3b13..a62a1f76 100644 --- a/examples/cloning.py +++ b/examples/cloning.py @@ -1,6 +1,6 @@ ## \example cloning.py # RMF includes functions to help cloning files an extracting parts. They are -# also exposed throught the [rmf_slice](\ref rmf_slice) application. +# also exposed through the [rmf_slice](\ref rmf_slice) application. from __future__ import print_function import RMF diff --git a/plugins/vmd/Data.cpp b/plugins/vmd/Data.cpp index 7e9b41c8..1ae2998b 100644 --- a/plugins/vmd/Data.cpp +++ b/plugins/vmd/Data.cpp @@ -179,7 +179,7 @@ std::array Data::fill_bodies(RMF::NodeConstHandle cur, int body, std::array segment, double resolution) { std::array ret = {{0}}; - // must be firest due to ret + // must be first due to ret if (altf_.get_is(cur)) boost::tie(cur, altid, ret) = handle_alternative( cur, body, chain, resid, resname, altid, segment, resolution); diff --git a/plugins/vmd/include/molfile_plugin.h b/plugins/vmd/include/molfile_plugin.h index bad69780..4f683c73 100644 --- a/plugins/vmd/include/molfile_plugin.h +++ b/plugins/vmd/include/molfile_plugin.h @@ -298,7 +298,7 @@ typedef struct { int memory; /**< amount of memory used in Mbyte. */ int runtype; /**< flag indicating the calculation method. */ int scftype; /**< SCF type: RHF, UHF, ROHF, GVB or MCSCF wfn. */ - int status; /**< indicates wether SCF and geometry optimization + int status; /**< indicates whether SCF and geometry optimization * have converged properly. */ int num_electrons; /**< number of electrons. XXX: can be fractional in some DFT codes */ @@ -324,7 +324,7 @@ typedef struct { int *num_shells_per_atom; /**< number of shells per atom */ int *num_prim_per_shell; /**< number of shell primitives shell */ - float *basis; /**< contraction coeffients and exponents for + float *basis; /**< contraction coefficients and exponents for * the basis functions in the form * {exp(1), c-coeff(1), exp(2), c-coeff(2), ...}; * array size = 2*num_basis_funcs @@ -633,7 +633,7 @@ typedef struct { #endif /** - * XXX this function will be augmented and possibly superceded by a + * XXX this function will be augmented and possibly superseded by a * new QM-capable version named read_timestep(), when finished. * * Read the next timestep from the file. Return MOLFILE_SUCCESS, or diff --git a/src/backend/BackwardsIO.cpp b/src/backend/BackwardsIO.cpp index b1a8e2ef..6cf51b1e 100644 --- a/src/backend/BackwardsIO.cpp +++ b/src/backend/BackwardsIO.cpp @@ -26,7 +26,7 @@ std::array make_array(std::string a, std::string b, return ret; } } -typedef std::pair > P3; +using P3 = std::pair >; const P3 vector_3_names[] = { P3("coordinates", make_array("cartesian x", "cartesian y", "cartesian z")), P3("translation", @@ -44,7 +44,7 @@ const int vector_3_names_size = V3N vector_3_names_map(vector_3_names, vector_3_names + vector_3_names_size); -typedef std::pair > P4; +using P4 = std::pair >; const P4 vector_4_names[] = { P4("orientation", make_array("orientation r", "orientation i", diff --git a/src/backend/avro/traits.cpp b/src/backend/avro/traits.cpp index 86d6755b..6dd0de6f 100644 --- a/src/backend/avro/traits.cpp +++ b/src/backend/avro/traits.cpp @@ -398,7 +398,7 @@ struct BackwardsTypeDatas { }; struct BackwardsFrame { - typedef rmf_raw_avro2::_Frame_json_Union__0__ info_t; + using info_t = rmf_raw_avro2::_Frame_json_Union__0__; info_t info; std::vector nodes; std::vector keys; diff --git a/src/backend/deprecated_avro/create.cpp b/src/backend/deprecated_avro/create.cpp index c6fea31d..26626157 100644 --- a/src/backend/deprecated_avro/create.cpp +++ b/src/backend/deprecated_avro/create.cpp @@ -36,12 +36,12 @@ namespace RMF { namespace avro_backend { namespace { -typedef backends::BackwardsIO > SingleAvroShareData; -typedef backends::BackwardsIO > AvroWriterShareData; -typedef backends::BackwardsIO > AvroReaderShareData; +using SingleAvroShareData = backends::BackwardsIO >; +using AvroWriterShareData = backends::BackwardsIO >; +using AvroReaderShareData = backends::BackwardsIO >; struct SingleTextAvroFactory : public RMF::backends::IOFactory { virtual std::string get_file_extension() const override { @@ -55,7 +55,7 @@ struct SingleTextAvroFactory : public RMF::backends::IOFactory { const std::string& name) const override { return std::make_shared(name, true, false); } - virtual ~SingleTextAvroFactory() {} + virtual ~SingleTextAvroFactory() = default; }; struct SingleAvroFactory : public SingleTextAvroFactory { @@ -76,7 +76,7 @@ struct SingleAvroFactory : public SingleTextAvroFactory { return std::shared_ptr(); } } - virtual ~SingleAvroFactory() {} + virtual ~SingleAvroFactory() = default; }; struct MultipleAvroFactory : public RMF::backends::IOFactory { @@ -91,7 +91,7 @@ struct MultipleAvroFactory : public RMF::backends::IOFactory { const std::string& name) const override { return std::make_shared(name, true, false); } - virtual ~MultipleAvroFactory() {} + virtual ~MultipleAvroFactory() = default; }; } // namespace std::vector > get_factories() { diff --git a/src/backend/deprecated_hdf5/HDF5SharedData.cpp b/src/backend/deprecated_hdf5/HDF5SharedData.cpp index 341f8adc..aa164358 100644 --- a/src/backend/deprecated_hdf5/HDF5SharedData.cpp +++ b/src/backend/deprecated_hdf5/HDF5SharedData.cpp @@ -278,10 +278,9 @@ unsigned int HDF5SharedData::add_category_impl(std::string name) { Categories HDF5SharedData::get_categories() const { Categories ret; - for (CategoryDataMap::const_iterator it = category_data_map_.begin(); - it != category_data_map_.end(); ++it) { - if (it->second.name == "link") continue; - ret.push_back(it->first); + for (const auto &it : category_data_map_) { + if (it.second.name == "link") continue; + ret.push_back(it.first); } return ret; } diff --git a/src/backend/deprecated_hdf5/HDF5SharedData.h b/src/backend/deprecated_hdf5/HDF5SharedData.h index 6bce5006..f384bb6b 100644 --- a/src/backend/deprecated_hdf5/HDF5SharedData.h +++ b/src/backend/deprecated_hdf5/HDF5SharedData.h @@ -13,7 +13,7 @@ #include #include #include -#include +#include #include #include #include diff --git a/src/backend/deprecated_hdf5/create.cpp b/src/backend/deprecated_hdf5/create.cpp index d236559c..fb8fdee0 100644 --- a/src/backend/deprecated_hdf5/create.cpp +++ b/src/backend/deprecated_hdf5/create.cpp @@ -29,7 +29,7 @@ namespace RMF { namespace hdf5_backend { namespace { -typedef backends::BackwardsIO MIO; +using MIO = backends::BackwardsIO; struct HDF5Factory : public RMF::backends::IOFactory { virtual std::string get_file_extension() const override { @@ -43,7 +43,7 @@ struct HDF5Factory : public RMF::backends::IOFactory { const std::string& name) const override { return std::make_shared(name, true, false); } - virtual ~HDF5Factory() {} + virtual ~HDF5Factory() = default; }; } // namespace diff --git a/src/exceptions.cpp b/src/exceptions.cpp index 65ebe3c7..5fc0a223 100644 --- a/src/exceptions.cpp +++ b/src/exceptions.cpp @@ -17,7 +17,7 @@ RMF_ENABLE_WARNINGS namespace RMF { -Exception::Exception() {} +Exception::Exception() = default; const char* Exception::what() const noexcept { try { @@ -30,7 +30,8 @@ const char* Exception::what() const noexcept { return message_.c_str(); } -Exception::~Exception() noexcept {} +Exception::~Exception() noexcept = default; + std::string get_message(const Exception& e) { using namespace RMF::internal::ErrorInfo; try { @@ -95,16 +96,16 @@ std::string get_message(const Exception& e) { } } UsageException::UsageException() : Exception() {} -UsageException::~UsageException() noexcept {} +UsageException::~UsageException() noexcept = default; IOException::IOException() : Exception() {} -IOException::~IOException() noexcept {} +IOException::~IOException() noexcept = default; IndexException::IndexException() : Exception() {} -IndexException::~IndexException() noexcept {} +IndexException::~IndexException() noexcept = default; InternalException::InternalException() : Exception() {} -InternalException::~InternalException() noexcept {} +InternalException::~InternalException() noexcept = default; } /* namespace RMF */ diff --git a/src/hdf5_wrapper.cpp b/src/hdf5_wrapper.cpp index 06bdfdfb..da39c71f 100644 --- a/src/hdf5_wrapper.cpp +++ b/src/hdf5_wrapper.cpp @@ -223,8 +223,8 @@ std::string File::get_name() const { return std::string(buf.get()); } -File::~File() {} -ConstFile::~ConstFile() {} +File::~File() = default; +ConstFile::~ConstFile() = default; int get_number_of_open_handles(ConstFile f) { H5garbage_collect(); diff --git a/swig/CMakeLists.txt b/swig/CMakeLists.txt index 45714107..e9623821 100644 --- a/swig/CMakeLists.txt +++ b/swig/CMakeLists.txt @@ -37,7 +37,7 @@ ENDIF() set_property(TARGET "${SWIG_MODULE_RMF_REAL_NAME}" PROPERTY FOLDER "RMF") if(APPLE) - set_target_properties("${SWIG_MODULE_RMF_REAL_NAME}" PROPERTIES LINK_FLAGS "-flat_namespace -undefined suppress") + set_target_properties("${SWIG_MODULE_RMF_REAL_NAME}" PROPERTIES LINK_FLAGS "-undefined dynamic_lookup") endif(APPLE) set_target_properties("${SWIG_MODULE_RMF_REAL_NAME}" PROPERTIES RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/lib") @@ -76,7 +76,7 @@ ENDIF() set_property(TARGET "${SWIG_MODULE_RMF_HDF5_REAL_NAME}" PROPERTY FOLDER "RMF") if(APPLE) - set_target_properties("${SWIG_MODULE_RMF_HDF5_REAL_NAME}" PROPERTIES LINK_FLAGS "-flat_namespace -undefined suppress") + set_target_properties("${SWIG_MODULE_RMF_HDF5_REAL_NAME}" PROPERTIES LINK_FLAGS "-undefined dynamic_lookup") endif(APPLE) set_target_properties("${SWIG_MODULE_RMF_HDF5_REAL_NAME}" PROPERTIES RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/lib") @@ -97,7 +97,7 @@ ENDIF(WIN32) # Apple linkers complain by default if there are undefined symbols IF(APPLE) SET(CMAKE_SHARED_MODULE_CREATE_CXX_FLAGS - "${CMAKE_SHARED_MODULE_CREATE_CXX_FLAGS} -flat_namespace -undefined suppress") + "${CMAKE_SHARED_MODULE_CREATE_CXX_FLAGS} -undefined dynamic_lookup") ENDIF(APPLE) INSTALL(TARGETS ${SWIG_MODULE_RMF_HDF5_REAL_NAME} DESTINATION ${CMAKE_INSTALL_PYTHONDIR}) diff --git a/test/test_associations.cpp b/test/test_associations.cpp index b16ac289..4aa7c8d9 100644 --- a/test/test_associations.cpp +++ b/test/test_associations.cpp @@ -5,7 +5,7 @@ * Copyright 2007-2022 IMP Inventors. All rights reserved. * */ -#include +#include #include #include #include diff --git a/test/test_avro2_low_level.cpp b/test/test_avro2_low_level.cpp index c0e2c5cf..d1d70eda 100644 --- a/test/test_avro2_low_level.cpp +++ b/test/test_avro2_low_level.cpp @@ -1,4 +1,4 @@ -#include +#include #include #include #include diff --git a/test/test_avro2_validate.cpp b/test/test_avro2_validate.cpp index 029af4ea..cc6f896b 100644 --- a/test/test_avro2_validate.cpp +++ b/test/test_avro2_validate.cpp @@ -107,10 +107,10 @@ void validate() { fr.id = FrameID(1); validate_one(fr, Frame()); FileDataChanges changes; - changes.categories.push_back(std::make_pair(Category(0), "hi")); - changes.node_types.push_back(std::make_pair(ROOT, "root")); - changes.frame_types.push_back(std::make_pair(STATIC, "static")); - changes.node_sets.push_back(std::make_pair(1, NodeIDs(2, NodeID(10)))); + changes.categories.emplace_back(Category(0), "hi"); + changes.node_types.emplace_back(ROOT, "root"); + changes.frame_types.emplace_back(STATIC, "static"); + changes.node_sets.emplace_back(1, NodeIDs(2, NodeID(10))); FileData data; validate_one(changes, data); validate_raw(fr); diff --git a/test/test_buffer.cpp b/test/test_buffer.cpp index ab639865..5d056a9b 100644 --- a/test/test_buffer.cpp +++ b/test/test_buffer.cpp @@ -5,7 +5,7 @@ * Copyright 2007-2022 IMP Inventors. All rights reserved. * */ -#include +#include #include "RMF/BufferHandle.h" #include "RMF/FileConstHandle.h" diff --git a/test/test_chain.py b/test/test_chain.py index 488feec8..107be42f 100644 --- a/test/test_chain.py +++ b/test/test_chain.py @@ -19,9 +19,13 @@ def test_chain(self): # Check defaults self.assertEqual(c.get_chain_type(), 'UnknownChainType') self.assertEqual(c.get_sequence(), '') + self.assertEqual(c.get_sequence_offset(), 0) + self.assertEqual(c.get_uniprot_accession(), '') # Check setters c.set_chain_type('LPolypeptide') c.set_sequence('CGY') + c.set_sequence_offset(10) + c.set_uniprot_accession('Q13098') c.set_chain_id('X') # Check both const and non-const getters @@ -34,6 +38,8 @@ def check_rmf(self, cf, c0, c1): c = cf.get(c0) self.assertEqual(c.get_chain_type(), 'LPolypeptide') self.assertEqual(c.get_sequence(), 'CGY') + self.assertEqual(c.get_sequence_offset(), 10) + self.assertEqual(c.get_uniprot_accession(), 'Q13098') self.assertEqual(c.get_chain_id(), 'X') if __name__ == '__main__': diff --git a/test/test_fill.cpp b/test/test_fill.cpp index c6a301a1..985491c6 100644 --- a/test/test_fill.cpp +++ b/test/test_fill.cpp @@ -15,7 +15,7 @@ #include #include #include -#include +#include #include #define HDF5_CALL(x) \ @@ -48,12 +48,13 @@ void set_value(hid_t ds, int i, int j, double v) { ij[0] = i; ij[1] = j; hsize_t one = 1; - HDF5_HANDLE(ids, H5Screate_simple(1, &one, NULL), &H5Sclose); + HDF5_HANDLE(ids, H5Screate_simple(1, &one, nullptr), &H5Sclose); hsize_t ones[2]; ones[0] = 1; ones[1] = 1; HDF5_HANDLE(space, H5Dget_space(ds), &H5Sclose); - HDF5_CALL(H5Sselect_hyperslab(space, H5S_SELECT_SET, ij, ones, ones, NULL)); + HDF5_CALL(H5Sselect_hyperslab(space, H5S_SELECT_SET, ij, ones, ones, + nullptr)); HDF5_CALL(H5Dwrite(ds, H5T_NATIVE_DOUBLE, ids, space, H5P_DEFAULT, &v)); } } diff --git a/test/test_json_encode_decode.cpp b/test/test_json_encode_decode.cpp index cdae7804..688ccca3 100644 --- a/test/test_json_encode_decode.cpp +++ b/test/test_json_encode_decode.cpp @@ -1,4 +1,4 @@ -#include +#include #include #include #include diff --git a/test/test_ranges.cpp b/test/test_ranges.cpp index b7b7257d..8500ded2 100644 --- a/test/test_ranges.cpp +++ b/test/test_ranges.cpp @@ -1,4 +1,4 @@ -#include +#include #include #include #include diff --git a/tools/RMF.spec b/tools/RMF.spec new file mode 100644 index 00000000..de918b50 --- /dev/null +++ b/tools/RMF.spec @@ -0,0 +1,200 @@ +# On modern Fedora/RHEL, use Python 3 by default (and provide an RMF-python2 +# subpackage; on RHEL 9 or later, use Python 3 only). +# On older systems, the RMF package uses Python 2 only. +%if 0%{?fedora} > 12 || 0%{?rhel} >= 8 +%define with_python3 1 +%define cmake_use_python2 off +%define default_python python3 +%else +%define with_python3 0 +%define cmake_use_python2 on +%define default_python python2 +%endif + +%if 0%{?rhel} >= 9 +%define with_python2 0 +%else +%define with_python2 1 +%endif + +# Old RHEL only has a python-devel package, but RHEL8 only has python2-devel +%if 0%{?fedora} || 0%{?rhel} >= 8 +%define PYTHON2 python2 +%else +%define PYTHON2 python +%endif + +Name: RMF +Version: 1.6.0 +Release: 1%{?dist} +License: Apache 2.0 +Summary: Library to support reading and writing of RMF files +Group: Applications/Engineering +Packager: Ben Webb +URL: https://integrativemodeling.org/rmf/ +Source0: rmf-%{version}.tar.gz +%if 0%{?with_python2} +BuildRequires: %{PYTHON2}-devel >= 2.7 +%endif +%if 0%{?with_python3} +BuildRequires: python3-devel, symlinks +%endif +BuildRequires: gcc-c++, hdf5-devel >= 1.8 +%if 0%{?rhel} == 7 +# The default SWIG package in RHEL7 is SWIG 2, but SWIG 3 is provided +# (in the CentOS Extras repository) +BuildRequires: swig3 >= 3.0 +%else +BuildRequires: swig >= 3.0 +%endif + +BuildRequires: cmake >= 2.8 +BuildRequires: boost-devel >= 1.53 + +# Add numpy support if available (the Python 2 variant is no longer shipped +# with modern Fedora). +%if 0%{?with_python3} +BuildRequires: python3-numpy +Requires: python3-numpy +%if 0%{?with_python2} && (0%{?fedora} < 34 || 0%{?rhel}) +BuildRequires: python2-numpy +%endif +%else +BuildRequires: numpy +Requires: numpy +%endif + +# Use user-visible (not "platform") Python on RHEL8 +%if 0%{?rhel} >= 8 +%define __python3 /usr/bin/python3 +%endif + +# Don't build debug source packages; they cause the build to fail with +# error: Empty %files file [...]/debugsourcefiles.list +%if 0%{?fedora} > 26 || 0%{?rhel} >= 8 +%undefine _debugsource_packages +%endif + +%description +The library provides support for the RMF file format for storing hierarchical +molecular data (such as atomic or coarse grained representations of proteins), +along with markup, including geometry and score data. + +%package devel +Group: Applications/Engineering +Summary: Development package for RMF developers. +Requires: %{name} = %{version}-%{release} +Requires: boost-devel, hdf5-devel +%if 0%{?with_python3} +Requires: python3-devel +%else +Requires: %{PYTHON2}-devel +%endif + +%description devel +This package contains the include files for building applications that link +against RMF. + +%if 0%{?with_python2} && 0%{?with_python3} +%package python2 +Group: Applications/Engineering +Summary: Python wrappers for Python 2 +Requires: %{name} = %{version}-%{release} +Requires: python2 +%if 0%{?fedora} < 34 || 0%{?rhel} +Requires: python2-numpy +%endif + +%description python2 +This package contains wrappers for Python 2 (the base package already +includes Python 3 wrappers). +%endif + +%prep +%setup -n rmf-%{version} + +%build +mkdir build && cd build + +cmake .. -DCMAKE_BUILD_TYPE=Release \ + -DCMAKE_INSTALL_PREFIX=%{_prefix} \ + -DUSE_PYTHON2=%{cmake_use_python2} +make %{?_smp_mflags} + +%install +cd build +make %{?_smp_mflags} DESTDIR=${RPM_BUILD_ROOT} install + +%if 0%{?with_python2} && 0%{?with_python3} +# Build Python 2 wrappers +py2_ver=`%{PYTHON2} -c "import sys; print('%d.%d' % sys.version_info[:2])"` +py3_ver=`python3 -c "import sys; print('%d.%d' % sys.version_info[:2])"` +py2_lib=`echo %{_libdir}/libpython2.*.so` +py2_inc=`echo /usr/include/python2.*` +cmake .. \ + -DCMAKE_INSTALL_PREFIX=%{_prefix} \ + -DCMAKE_INSTALL_PYTHONDIR=%{_libdir}/python${py2_ver}/site-packages \ + -DSWIG_PYTHON_LIBRARIES=${py2_lib} \ + -DPYTHON_INCLUDE_DIRS=${py2_inc} \ + -DPYTHON_INCLUDE_PATH=${py2_inc} \ + -DPYTHON_LIBRARIES=${py2_lib} -DUSE_PYTHON2=on +make %{?_smp_mflags} DESTDIR=${RPM_BUILD_ROOT} install + +# Replace .py files with symlinks to Python 3 files (since they are the same) +# but not the SWIG-generated __init__.py files (since these contain config +# information which might be different; e.g. on Fedora the Python 3 wrappers +# include numpy support but the Python 2 wrappers do not) +(cd ${RPM_BUILD_ROOT}%{_libdir}/python${py2_ver} \ + && find site-packages -name '*.py' -a ! -name __init__.py \ + -exec ln -sf ${RPM_BUILD_ROOT}%{_libdir}/python${py3_ver}/\{\} \{\} \; \ + && symlinks -rc .) +%endif + +%check +# Basic check of installed Python wrappers and command line tools +export LD_LIBRARY_PATH=${RPM_BUILD_ROOT}%{_libdir} +${RPM_BUILD_ROOT}%{_prefix}/bin/rmf3_dump --version + +%if 0%{?with_python3} + py3_ver=`python3 -c "import sys; print('%d.%d' % sys.version_info[:2])"` + export PYTHONPATH=${RPM_BUILD_ROOT}%{_libdir}/python${py3_ver}/site-packages + python3 -c "import RMF; assert(RMF.__version__ == '%{version}')" + python3 -c "import RMF; assert(hasattr(RMF, 'get_all_global_coordinates'))" +%endif + +%if 0%{?with_python2} + py2_ver=`%{PYTHON2} -c "import sys; print('%d.%d' % sys.version_info[:2])"` + export PYTHONPATH=${RPM_BUILD_ROOT}%{_libdir}/python${py2_ver}/site-packages + %{PYTHON2} -c "import RMF; assert(RMF.__version__ == '%{version}')" +%endif + +%files +%defattr(-,root,root) +%{_prefix}/bin/* +%{_libdir}/libRMF*.so.* +%{_libdir}/%{default_python}*/site-packages/RMF* +%{_libdir}/%{default_python}*/site-packages/_RMF*so +%if 0%{?with_python3} +%{_libdir}/python3*/site-packages/__pycache__ +%endif + +%if 0%{?with_python2} && 0%{?with_python3} +%files python2 +%defattr(-,root,root) +%{_libdir}/python2*/site-packages/RMF* +%{_libdir}/python2*/site-packages/_RMF*so +%endif + +%files devel +%defattr(-,root,root) +%{_prefix}/share/RMF/swig +%{_prefix}/include/RMF +%{_prefix}/include/RMF.h +%{_libdir}/libRMF*.so + +%changelog +* Thu Dec 14 2023 Ben Webb 1.6.0-1 +- Update for 1.6.0 release. + +* Mon Jul 31 2023 Ben Webb 1.5.1-1 +- Initial build. diff --git a/tools/build/make_decorators.py b/tools/build/make_decorators.py index 7cb5a873..d803003b 100755 --- a/tools/build/make_decorators.py +++ b/tools/build/make_decorators.py @@ -177,6 +177,8 @@ "Chain", [Attribute("chain id", "String"), Attribute("sequence", "String", default=""), + Attribute("sequence offset", "Int", default=0), + Attribute("uniprot accession", "String", default=""), Attribute("chain type", "String", default='UnknownChainType')]) diff --git a/tools/new-release.txt b/tools/new-release.txt index 600e8a39..0a137c72 100644 --- a/tools/new-release.txt +++ b/tools/new-release.txt @@ -1,6 +1,6 @@ To make a new release: -- Update ChangeLog.md with release date and features. +- Update ChangeLog.md and tools/RMF.spec with release date and features. - Add version number as RMF_VERSION_(MAJOR,MINOR,MICRO) to CMakeLists.txt. - git push origin develop - Make sure all CI passes