Changes between Initial Version and Version 1 of Guidelines/MaintenanceGuidelines


Ignore:
Timestamp:
Nov 22, 2008, 6:06:34 PM (14 years ago)
Author:
viboes
Comment:

--

Legend:

Unmodified
Added
Removed
Modified
  • Guidelines/MaintenanceGuidelines

    v1 v1  
     1Please be free to improve this page directly or post on the Boost mailing list.
     2
     3= Motivation =
     4''To be added''
     5
     6= Introduction =
     7Nobody wants to completely disallow changes, we need them.
     8Everybody wants to avoid breaking changes, but sometimes these are also necessary.
     9
     10This page describes guidelines that could be followed by the Boost community '''to avoid user code breaking when the user upgrades to a more recent Boost release'''.
     11
     12The difference between '''breaking changes''' and '''bugs''' concerns documentation. A documented modification breaking user code can not be considered as a bug while the same non documented modification could be a bug.
     13
     14The key issue are:
     15 * Documenting and tracking the changes.
     16 * Avoiding completely silent breakage by a deep inspection of code changes.
     17 * Using a deprecation period to give users notice that a breaking change is coming.
     18 * Running the regression tests from the _previous_ major release against the current release as a way to automatically detect and flag interface/behavioral changes.
     19 * Versioning individual Boost.Libraries.
     20
     21These guidelines are related mainly to how to document changes. There are also some guidelines that can be followed to detect breaking changes either by test or by inspections. And of course this pages contains also some guidelines related to the code itself.
     22
     23But, why user code can break when upgrading Boost?
     24
     25 * '''Syntactical''' breaking: detected at compile time
     26It is evident that the removal of files, namespaces, classes, function, variables or macros could break user code. What it is less evident is the addition namespaces, classes, function, variables at the namespace level or macros can also break user code. Note that modifications can be considered as deletion+addition.
     27
     28The following user code example
     29
     30{{{
     31#!cpp
     32using namespace boost;
     33
     34class foo {
     35  // ...
     36};
     37
     38void bar() {
     39  // ...
     40}
     41}}}
     42
     43breaks when
     44 * we add the namespace foo in one of the files included by the user program
     45{{{
     46#!cpp
     47// boost/file.hpp
     48namespace boost {
     49  namespace foo {
     50    // ...
     51  }
     52}
     53}}}
     54
     55 * we add the class foo in one of the files included by the user program
     56{{{
     57#!cpp
     58// boost/file.hpp
     59namespace boost {
     60  class foo {
     61    // ...
     62  };
     63}
     64}}}
     65
     66
     67
     68 * we add the function bar in one of the files included by the user program
     69{{{
     70#!cpp
     71// boost/file.hpp
     72namespace boost {
     73  void bar() {
     74    // ...
     75  }
     76}
     77}}}
     78
     79
     80Adding macros
     81We should don't have user code breaking until we preserve the macro naming rule BOOST_LIBNAME_NAME.
     82
     83 * '''Semantical''' breaking: detected at runtime
     84Some times the user code will compile with the upgraded Boost release, but the code will not behaves as before. This kind of changes that could lead to this situation must be over documented because the compiler can not help the user to catch the breaking code.
     85
     86''Add an example on overloading''
     87
     88These guidelines are not only addressed to the Boost library authors, but also to the users and the release manager team (RM). Every member of the Boost community has its role to play. Note that the author plays also the role of user of all libraries on which its library depends and on its own library when writing the library tests.
     89
     90
     91= Deprecating features =
     92
     93''To be added''
     94
     95
     96= Cross version testing =
     97
     98
     99Running the regression tests from the _previous_ major release against the current release is a way to automatically detect and flag interface/behavioral changes. Sure, there are many potential problems with such an approach:
     100
     101- Some library tests are likely to also exercise code at the
     102implementation/detail level.
     103- Already limited testing resources (on the other hand, interface changes
     104are likely to be detected by running such tests for a single, reasonably
     105compliant, compiler).
     106- ...
     107
     108In order to have the better we can preserve the test of the older releases and run them on the current release.
     109
     110= Versioning individual Boost libraries =
     111
     112This page do not contains any advice related to individual Boost libraries packaging. There is already a project working on that. But tagging individual Boost libraries with a specific version has already some advantages.
     113
     114
     115= Documentation =
     116
     117== Tag Boost library with specific library version [author] ==
     118Tagging each library release with a version, is the better way to signal to the user of possible incompatibilities.
     119
     120== Create a Feature Request ticket for each deprecated/suppressed/modified/new  feature [author, user] ==
     121Each modification should be tracked with a ticket on the track system.
     122
     123
     124== Release note and track system traceability [author] ==
     125The release note should include
     126    * the list of all the bug tickets that have been solved
     127    * the list of all deprecated/suppressed/modified/new features with its associated ticket.
     128
     129== Include a diff file showing the modification respect to the previous release [author, RM] ==
     130This file is the explicit report of all the changes in the library. It could be used by the Boost community to inspect that every change has been correctly documented (see inspections bellow).
     131
     132= Codding =
     133== Do not use using sentences [user] ==
     134As seen before the use of using sentences in user code is one of the source of user code breaking, so it will be safer to use instead namespace synonyms and prefix each symbol with them.
     135
     136Instead of doing
     137
     138{{{
     139#!cpp
     140   using namespace boost::interprocess;
     141
     142   shared_memory_object::remove("MySharedMemory");
     143}}}
     144
     145do
     146
     147
     148{{{
     149#!cpp
     150    namespace bip = boost::interprocess;
     151
     152    bip::shared_memory_object::remove("MySharedMemory");
     153}}}
     154
     155
     156== Do not delete files prematurely [author] ==
     157Before deleting a file "file.hpp" deprecate it and let the user modify its code during some versions (e.g. until 1_40). Replace it by
     158
     159{{{
     160#!cpp
     161// boost/old_header_file.hpp
     162// include whatever file is needed to preserve the old file contents
     163#if defined(BOOST_WARMS_DEPRECEATED) || defined(BOOST_WARMS_DEPRECEATED_ON_1_40)
     164#warning "boost/old_header_file.hpp is deprecated, please include boost/new_header_file.hpp instead
     165#endif
     166}}}
     167
     168It will be up to the user to define the macros BOOST_WARMS_DEPRECEATED and BOOST_WARMS_DEPRECEATED_ON_1_40 when the user wants to be warmed for deprecated features on Boost or on the Boost version 1.40 respectively.
     169
     170== Do not delete namespaces prematurely [author] ==
     171Use the using sentence to import from the new namespace to the old one.
     172
     173== Do not delete classes/functions/variables prematurely [author] ==
     174Instead of delete a class on the next version protect its definition by BOOST_DONT_INCLUDE_DEPRECATED or BOOST_LIBX_DONT_INCLUDE_DEPRECATED.
     175
     176{{{
     177#!cpp
     178// boost/libx/header_file.hpp
     179namespace boost {
     180namespace libx {
     181
     182#if defined(BOOST_DONT_INCLUDE_DEPRECATED) || defined(BOOST_DONT_INCLUDE_DEPRECATED_ON_1_41) || defined(BOOST_LIBX_DONT_INCLUDE_DEPRECATED)  || defined(BOOST_LIBX_DONT_INCLUDE_DEPRECATED_ON_1_41) || defined(BOOST_LIBX_DONT_INCLUDE_DEPRECATED_NAME)
     183  #define BOOST_LIBX_NAME_DONT_DEFINED
     184#else
     185  #warning "name is deprecated, please use new_name instead"
     186
     187  class name {
     188    // as before
     189  };
     190#endif
     191
     192}
     193}
     194
     195}}}
     196
     197The same applies to functions and variables.
     198
     199== Do not modify functions prototype prematurely [author] ==
     200Instead of modifying an existing function prototype, do as you were deleted it and added the new one. As both prototypes should cohabit during some releases, check if this overloading could cause user code breaks.
     201
     202
     203
     204
     205= Test and Inspections =
     206
     207== Regression Test and track system traceability ==
     208A bug ticket must be associated to a test case, either the test case exists already and there is a regression for some toolset, or a new toolset is considered, or a new test case is needed to check the bug is there (problem reproducible) and the modification solve the problem.
     209 * State clearly which test cases prove the bug it it exists [user]
     210 * Propose a new test case reproducing the bug [user]
     211
     212== Preserve the test from the preceding versions as much as possible ==
     213The test from the preceding versions should not be changed when the author modifies its library. These  not changed tests are a probe of compatibility with the preceding version. When these test must be changed they indicate a breaking user code issue. So instead of changing them add new ones stating explicitly on which version they were included and remove these tests from the Jamfile.
     214