StdAir Logo  0.45.1
C++ Standard Airline IT Object Library
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
FacBomManager.hpp
Go to the documentation of this file.
1 #ifndef __STDAIR_FAC_FACBOMMANAGER_HPP
2 #define __STDAIR_FAC_FACBOMMANAGER_HPP
3 
4 // //////////////////////////////////////////////////////////////////////
5 // Import section
6 // //////////////////////////////////////////////////////////////////////
7 // STL
8 #include <iosfwd>
9 #include <list>
10 #include <map>
11 // Boost
12 #include <boost/static_assert.hpp>
13 #include <boost/type_traits/is_same.hpp>
14 // StdAir
15 #include <stdair/bom/BomHolder.hpp>
19 // Stdair BOM Objects
21 
22 
23 namespace stdair {
24 
28  class FacBomManager : public FacAbstract {
29  public:
30  // ///////////// Business methods. ////////////
39  template <typename OBJECT2, typename OBJECT1>
40  static BomHolder<OBJECT2>* getBomHolderPtr (OBJECT1&);
41 
51  template <typename OBJECT2, typename OBJECT1>
52  static BomHolder<OBJECT2>& addBomHolder (OBJECT1&);
53 
65  template <typename OBJECT1, typename OBJECT2>
66  static void addToList (OBJECT1&, OBJECT2&);
67 
80  template <typename OBJECT1, typename OBJECT2>
81  static void addToMap (OBJECT1&, OBJECT2&, const MapKey_T&);
82 
94  template <typename OBJECT1, typename OBJECT2>
95  static void addToMap (OBJECT1&, OBJECT2&);
96 
108  template <typename OBJECT1, typename OBJECT2>
109  static void addToListAndMap (OBJECT1&, OBJECT2&);
110 
123  template <typename OBJECT1, typename OBJECT2>
124  static void addToListAndMap (OBJECT1&, OBJECT2&, const MapKey_T&);
125 
132  template <typename PARENT, typename CHILD>
133  static void linkWithParent (PARENT&, CHILD&);
134 
145  template <typename OBJECT2, typename OBJECT1>
146  static void cloneHolder (OBJECT1&, const OBJECT1&);
147 
148 
149  private:
162  template <typename OBJECT1, typename OBJECT2>
163  static void addToList (BomHolder<OBJECT2>&, OBJECT1&, OBJECT2&);
164 
178  template <typename OBJECT1, typename OBJECT2>
179  static void addToMap (BomHolder<OBJECT2>&, OBJECT1&, OBJECT2&,
180  const MapKey_T&);
181 
190  template <typename OBJECT2, typename OBJECT1>
191  static BomHolder<OBJECT2>& getBomHolder (OBJECT1&);
192 
193 
194  protected:
201 
202  public:
207  };
208 
209  // ////////////////////////////////////////////////////////////////////
210  // Public business method.
211  // Compile time assertation to check OBJECT1 and OBJECT2 types.
212  template <typename OBJECT2, typename OBJECT1>
214 
215  //
216  // Compile time assertation: this function must never be called with the
217  // following list of couple types:
218  // <SegmentDate, SegmentDate>
219  //
220  BOOST_STATIC_ASSERT ((boost::is_same<OBJECT1, SegmentDate>::value == false
221  || boost::is_same<OBJECT2, SegmentDate>::value == false));
222 
223  BomHolder<OBJECT2>* lBomHolder_ptr =
224  &FacBom<BomHolder<OBJECT2> >::instance().create();
225 
226  const bool hasInsertBeenSuccessful =
227  ioObject1._holderMap.insert (typename HolderMap_T::
228  value_type (&typeid (OBJECT2),
229  lBomHolder_ptr)).second;
230  assert (hasInsertBeenSuccessful == true);
231 
232  return *lBomHolder_ptr;
233  }
234 
235  // ////////////////////////////////////////////////////////////////////
236  // Public business method.
237  // Compile time assertation to check OBJECT1 and OBJECT2 types.
238  template <typename OBJECT2, typename OBJECT1>
240 
241  //
242  // Compile time assertation: this function must never be called with the
243  // following list of couple types:
244  // <SegmentDate, SegmentDate>
245  //
246  BOOST_STATIC_ASSERT ((boost::is_same<OBJECT1, SegmentDate>::value == false
247  || boost::is_same<OBJECT2, SegmentDate>::value == false));
248 
249  BomHolder<OBJECT2>* lBomHolder_ptr = NULL;
250 
251  // Find the corresponding BomHolder within the object1, if existing.
252  HolderMap_T::const_iterator itHolder =
253  ioObject1._holderMap.find (&typeid (OBJECT2));
254 
255  if (itHolder != ioObject1._holderMap.end()) {
256  lBomHolder_ptr = static_cast<BomHolder<OBJECT2>*> (itHolder->second);
257  }
258 
259  return lBomHolder_ptr;
260  }
261 
262  // ////////////////////////////////////////////////////////////////////
263  // Private method.
264  template <typename OBJECT2, typename OBJECT1>
265  BomHolder<OBJECT2>& FacBomManager::getBomHolder (OBJECT1& ioObject1) {
266 
267  BomHolder<OBJECT2>* lBomHolder_ptr = NULL;
268 
269  // Find the corresponding BomHolder within the object1. If it does
270  // not exist, then create one.
271  HolderMap_T::const_iterator itHolder =
272  ioObject1._holderMap.find (&typeid (OBJECT2));
273 
274  if (itHolder == ioObject1._holderMap.end()) {
275  lBomHolder_ptr = &addBomHolder<OBJECT2, OBJECT1> (ioObject1);
276 
277  } else {
278  lBomHolder_ptr = static_cast<BomHolder<OBJECT2>*> (itHolder->second);
279  }
280 
281  assert (lBomHolder_ptr != NULL);
282 
283  return *lBomHolder_ptr;
284  }
285 
286  // ////////////////////////////////////////////////////////////////////
287  // Private method.
288  template <typename OBJECT1, typename OBJECT2>
289  void FacBomManager::addToList (BomHolder<OBJECT2>& ioBomHolder,
290  OBJECT1& ioObject1, OBJECT2& ioObject2) {
291  ioBomHolder._bomList.push_back (&ioObject2);
292  }
293 
294  // ////////////////////////////////////////////////////////////////////
295  // Public business method.
296  // This method is specialized for the following couple types:
297  // <SegmentDate, SegmentDate>
298  template <typename OBJECT1, typename OBJECT2>
299  void FacBomManager::addToList (OBJECT1& ioObject1, OBJECT2& ioObject2) {
300 
301  BomHolder<OBJECT2>& lBomHolder = getBomHolder<OBJECT2> (ioObject1);
302 
303  addToList<OBJECT1, OBJECT2> (lBomHolder, ioObject1, ioObject2);
304  }
305 
306  // ////////////////////////////////////////////////////////////////////
307  // Private method.
308  template <typename OBJECT1, typename OBJECT2>
309  void FacBomManager::addToMap (BomHolder<OBJECT2>& ioBomHolder,
310  OBJECT1& ioObject1, OBJECT2& ioObject2,
311  const MapKey_T& iKey) {
312 
313  const bool insertionSucceeded =
314  ioBomHolder._bomMap.insert (typename std::map<const MapKey_T, OBJECT2*>::
315  value_type (iKey, &ioObject2)).second;
316 
317  if (insertionSucceeded == false) {
318  // Build a nice message, so that the error be fully explicit
319  std::ostringstream oStr;
320  oStr << "The given object ('" << iKey
321  << "') can not be added to the map of '" << ioObject1.describeKey()
322  << "' object. That map already contains: '";
323 
324  unsigned int idx = 0;
325  for (typename std::map<const MapKey_T, OBJECT2*>::const_iterator iter =
326  ioBomHolder._bomMap.begin();
327  iter != ioBomHolder._bomMap.end(); ++iter, ++idx) {
328  const OBJECT2* lCurrentObject_ptr = iter->second;
329  assert (lCurrentObject_ptr != NULL);
330 
331  if (idx != 0) {
332  oStr << "; ";
333  }
334  oStr << lCurrentObject_ptr->describeKey();
335  }
336  oStr << "'";
337 
338  STDAIR_LOG_ERROR (oStr.str());
339  throw ObjectLinkingException (oStr.str());
340  }
341  }
342 
343  // ////////////////////////////////////////////////////////////////////
344  // Public business method.
345  // Compile time assertation to check OBJECT1 and OBJECT2 types.
346  template <typename OBJECT1, typename OBJECT2> void FacBomManager::
347  addToMap (OBJECT1& ioObject1, OBJECT2& ioObject2, const MapKey_T& iKey) {
348 
349  //
350  // Compile time assertation: this function must never be called with the
351  // following list of couple types:
352  // <SegmentDate, SegmentDate>
353  //
354  BOOST_STATIC_ASSERT ((boost::is_same<OBJECT1, SegmentDate>::value == false
355  || boost::is_same<OBJECT2, SegmentDate>::value == false));
356 
357  BomHolder<OBJECT2>& lBomHolder = getBomHolder<OBJECT2> (ioObject1);
358 
359  addToMap<OBJECT1, OBJECT2> (lBomHolder, ioObject1, ioObject2, iKey);
360  }
361 
362  // Public business method.
363  // Compile time assertation to check OBJECT1 and OBJECT2 types.
364  // ////////////////////////////////////////////////////////////////////
365  template <typename OBJECT1, typename OBJECT2>
366  void FacBomManager::addToMap (OBJECT1& ioObject1, OBJECT2& ioObject2) {
367 
368  //
369  // Compile time assertation: this function must never be called with the
370  // following list of couple types:
371  // <SegmentDate, SegmentDate>
372  //
373  BOOST_STATIC_ASSERT ((boost::is_same<OBJECT1, SegmentDate>::value == false
374  || boost::is_same<OBJECT2, SegmentDate>::value == false));
375 
376  const MapKey_T& lKey = ioObject2.describeKey();
377  addToMap (ioObject1, ioObject2, lKey);
378  }
379 
380  // ////////////////////////////////////////////////////////////////////
381  // Public business method.
382  // Compile time assertation to check OBJECT1 and OBJECT2 types.
383  template <typename OBJECT1, typename OBJECT2>
384  void FacBomManager::addToListAndMap (OBJECT1& ioObject1, OBJECT2& ioObject2,
385  const MapKey_T& iKey) {
386  //
387  // Compile time assertation: this function must never be called with the
388  // following list of couple types:
389  // <SegmentDate, SegmentDate>
390  //
391  BOOST_STATIC_ASSERT ((boost::is_same<OBJECT1, SegmentDate>::value == false
392  || boost::is_same<OBJECT2, SegmentDate>::value == false));
393 
394  BomHolder<OBJECT2>& lBomHolder = getBomHolder<OBJECT2> (ioObject1);
395 
396  addToList<OBJECT1, OBJECT2> (lBomHolder, ioObject1, ioObject2);
397  addToMap<OBJECT1, OBJECT2> (lBomHolder, ioObject1, ioObject2, iKey);
398  }
399 
400  // ////////////////////////////////////////////////////////////////////
401  // Public business method.
402  // Compile time assertation to check OBJECT1 and OBJECT2 types.
403  template <typename OBJECT1, typename OBJECT2> void FacBomManager::
404  addToListAndMap (OBJECT1& ioObject1, OBJECT2& ioObject2) {
405 
406  //
407  // Compile time assertation: this function must never be called with the
408  // following list of couple types:
409  // <SegmentDate, SegmentDate>
410  //
411  BOOST_STATIC_ASSERT ((boost::is_same<OBJECT1, SegmentDate>::value == false
412  || boost::is_same<OBJECT2, SegmentDate>::value == false));
413 
414  const MapKey_T& lKey = ioObject2.describeKey();
415  addToListAndMap<OBJECT1, OBJECT2> (ioObject1, ioObject2, lKey);
416  }
417 
418  // Public business method valid for all PARENT and CHILD types.
419  // (No compile time assertation to check PARENT and CHILD types.)
420  // ////////////////////////////////////////////////////////////////////
421  template <typename PARENT, typename CHILD> void FacBomManager::
422  linkWithParent (PARENT& ioParent, CHILD& ioChild) {
423  ioChild._parent = &ioParent;
424  }
425 
426  // ////////////////////////////////////////////////////////////////////
427  // Public business method valid for all PARENT and CHILD types.
428  // (No compile time assertation to check PARENT and CHILD types.)
429  template <typename OBJECT2, typename OBJECT1> void FacBomManager::
430  cloneHolder (OBJECT1& ioDest, const OBJECT1& iOri) {
431 
432  const BomHolder<OBJECT2>& lOriginHolder =
433  BomManager::getBomHolder<OBJECT2> (iOri);
434 
435  BomHolder<OBJECT2>& lDestHolder = getBomHolder<OBJECT2> (ioDest);
436  lDestHolder._bomList = lOriginHolder._bomList;
437  lDestHolder._bomMap = lOriginHolder._bomMap;
438  }
439 
440  // ////////////////////////////////////////////////////////////////////
441  //
442  // Specialization of the template method addToList above for the types
443  // <SegmentDate, SegmentDate>.
444  // Add an element to the marketing segment date list of a segment date.
445  //
446  // ////////////////////////////////////////////////////////////////////
447 
448  template<>
449  inline void FacBomManager::addToList <SegmentDate,SegmentDate>
450  (SegmentDate& ioSegmentDate,
451  SegmentDate& ioMarketingSegmentDate) {
452 
453  ioSegmentDate._marketingSegmentDateList.push_back(&ioMarketingSegmentDate);
454  }
455 
456  // ////////////////////////////////////////////////////////////////////
457  //
458  // TODO:
459  // This specialization is needed for all the objects in the current
460  // BOM tree.
461  // (An inventory is the parent of flight dates, a flight date is the
462  // parent of segment dates and leg dates, ...)
463  //
464  // ////////////////////////////////////////////////////////////////////
465 
466 
467 }
468 
469 // ////////////////////////////////////////////////////////////////////
470 
471 #endif // __STDAIR_FAC_FACBOMMANAGER_HPP