summaryrefslogtreecommitdiff
path: root/boost/log/sinks/text_file_backend.hpp
diff options
context:
space:
mode:
authorChanho Park <chanho61.park@samsung.com>2014-12-11 18:55:56 +0900
committerChanho Park <chanho61.park@samsung.com>2014-12-11 18:55:56 +0900
commit08c1e93fa36a49f49325a07fe91ff92c964c2b6c (patch)
tree7a7053ceb8874b28ec4b868d4c49b500008a102e /boost/log/sinks/text_file_backend.hpp
parentbb4dd8289b351fae6b55e303f189127a394a1edd (diff)
downloadboost-08c1e93fa36a49f49325a07fe91ff92c964c2b6c.tar.gz
boost-08c1e93fa36a49f49325a07fe91ff92c964c2b6c.tar.bz2
boost-08c1e93fa36a49f49325a07fe91ff92c964c2b6c.zip
Imported Upstream version 1.57.0upstream/1.57.0
Diffstat (limited to 'boost/log/sinks/text_file_backend.hpp')
-rw-r--r--boost/log/sinks/text_file_backend.hpp539
1 files changed, 539 insertions, 0 deletions
diff --git a/boost/log/sinks/text_file_backend.hpp b/boost/log/sinks/text_file_backend.hpp
new file mode 100644
index 0000000000..1d39a633c0
--- /dev/null
+++ b/boost/log/sinks/text_file_backend.hpp
@@ -0,0 +1,539 @@
+/*
+ * Copyright Andrey Semashev 2007 - 2014.
+ * Distributed under the Boost Software License, Version 1.0.
+ * (See accompanying file LICENSE_1_0.txt or copy at
+ * http://www.boost.org/LICENSE_1_0.txt)
+ */
+/*!
+ * \file text_file_backend.hpp
+ * \author Andrey Semashev
+ * \date 09.06.2009
+ *
+ * The header contains implementation of a text file sink backend.
+ */
+
+#ifndef BOOST_LOG_SINKS_TEXT_FILE_BACKEND_HPP_INCLUDED_
+#define BOOST_LOG_SINKS_TEXT_FILE_BACKEND_HPP_INCLUDED_
+
+#include <ios>
+#include <string>
+#include <ostream>
+#include <boost/limits.hpp>
+#include <boost/cstdint.hpp>
+#include <boost/smart_ptr/shared_ptr.hpp>
+#include <boost/date_time/date_defs.hpp>
+#include <boost/date_time/special_defs.hpp>
+#include <boost/date_time/gregorian/greg_day.hpp>
+#include <boost/date_time/posix_time/posix_time_types.hpp>
+#include <boost/filesystem/path.hpp>
+#include <boost/log/keywords/max_size.hpp>
+#include <boost/log/keywords/min_free_space.hpp>
+#include <boost/log/keywords/target.hpp>
+#include <boost/log/keywords/file_name.hpp>
+#include <boost/log/keywords/open_mode.hpp>
+#include <boost/log/keywords/auto_flush.hpp>
+#include <boost/log/keywords/rotation_size.hpp>
+#include <boost/log/keywords/time_based_rotation.hpp>
+#include <boost/log/detail/config.hpp>
+#include <boost/log/detail/light_function.hpp>
+#include <boost/log/detail/parameter_tools.hpp>
+#include <boost/log/sinks/basic_sink_backend.hpp>
+#include <boost/log/sinks/frontend_requirements.hpp>
+#include <boost/log/detail/header.hpp>
+
+#ifdef BOOST_HAS_PRAGMA_ONCE
+#pragma once
+#endif
+
+namespace boost {
+
+BOOST_LOG_OPEN_NAMESPACE
+
+namespace sinks {
+
+namespace file {
+
+//! The enumeration of the stored files scan methods
+enum scan_method
+{
+ no_scan, //!< Don't scan for stored files
+ scan_matching, //!< Scan for files with names matching the specified mask
+ scan_all //!< Scan for all files in the directory
+};
+
+/*!
+ * \brief Base class for file collectors
+ *
+ * All file collectors, supported by file sink backends, should inherit this class.
+ */
+struct BOOST_LOG_NO_VTABLE collector
+{
+ /*!
+ * Default constructor
+ */
+ BOOST_DEFAULTED_FUNCTION(collector(), {})
+
+ /*!
+ * Virtual destructor
+ */
+ virtual ~collector() {}
+
+ /*!
+ * The function stores the specified file in the storage. May lead to an older file
+ * deletion and a long file moving.
+ *
+ * \param src_path The name of the file to be stored
+ */
+ virtual void store_file(filesystem::path const& src_path) = 0;
+
+ /*!
+ * Scans the target directory for the files that have already been stored. The found
+ * files are added to the collector in order to be tracked and erased, if needed.
+ *
+ * The function may scan the directory in two ways: it will either consider every
+ * file in the directory a log file, or will only consider files with names that
+ * match the specified pattern. The pattern may contain the following placeholders:
+ *
+ * \li %y, %Y, %m, %d - date components, in Boost.DateTime meaning.
+ * \li %H, %M, %S, %f - time components, in Boost.DateTime meaning.
+ * \li %N - numeric file counter. May also contain width specification
+ * in printf-compatible form (e.g. %5N). The resulting number will always be zero-filled.
+ * \li %% - a percent sign
+ *
+ * All other placeholders are not supported.
+ *
+ * \param method The method of scanning. If \c no_scan is specified, the call has no effect.
+ * \param pattern The file name pattern if \a method is \c scan_matching. Otherwise the parameter
+ * is not used.
+ * \param counter If not \c NULL and \a method is \c scan_matching, the method suggests initial value
+ * of a file counter that may be used in the file name pattern. The parameter
+ * is not used otherwise.
+ * \return The number of found files.
+ *
+ * \note In case if \a method is \c scan_matching the effect of this function is highly dependent
+ * on the \a pattern definition. It is recommended to choose patterns with easily
+ * distinguished placeholders (i.e. having delimiters between them). Otherwise
+ * either some files can be mistakenly found or not found, which in turn may lead
+ * to an incorrect file deletion.
+ */
+ virtual uintmax_t scan_for_files(
+ scan_method method, filesystem::path const& pattern = filesystem::path(), unsigned int* counter = 0) = 0;
+
+ BOOST_DELETED_FUNCTION(collector(collector const&))
+ BOOST_DELETED_FUNCTION(collector& operator= (collector const&))
+};
+
+namespace aux {
+
+ //! Creates and returns a file collector with the specified parameters
+ BOOST_LOG_API shared_ptr< collector > make_collector(
+ filesystem::path const& target_dir,
+ uintmax_t max_size,
+ uintmax_t min_free_space
+ );
+ template< typename ArgsT >
+ inline shared_ptr< collector > make_collector(ArgsT const& args)
+ {
+ return aux::make_collector(
+ filesystem::path(args[keywords::target]),
+ args[keywords::max_size | (std::numeric_limits< uintmax_t >::max)()],
+ args[keywords::min_free_space | static_cast< uintmax_t >(0)]);
+ }
+
+} // namespace aux
+
+#ifndef BOOST_LOG_DOXYGEN_PASS
+
+template< typename T1 >
+inline shared_ptr< collector > make_collector(T1 const& a1)
+{
+ return aux::make_collector(a1);
+}
+template< typename T1, typename T2 >
+inline shared_ptr< collector > make_collector(T1 const& a1, T2 const& a2)
+{
+ return aux::make_collector((a1, a2));
+}
+template< typename T1, typename T2, typename T3 >
+inline shared_ptr< collector > make_collector(T1 const& a1, T2 const& a2, T3 const& a3)
+{
+ return aux::make_collector((a1, a2, a3));
+}
+
+#else
+
+/*!
+ * The function creates a file collector for the specified target directory.
+ * Each target directory is managed by a single file collector, so if
+ * this function is called several times for the same directory,
+ * it will return a reference to the same file collector. It is safe
+ * to use the same collector in different sinks, even in a multithreaded
+ * application.
+ *
+ * One can specify certain restrictions for the stored files, such as
+ * maximum total size or minimum free space left in the target directory.
+ * If any of the specified restrictions is not met, the oldest stored file
+ * is deleted. If the same collector is requested more than once with
+ * different restrictions, the collector will act according to the most strict
+ * combination of all specified restrictions.
+ *
+ * The following named parameters are supported:
+ *
+ * \li \c target - Specifies the target directory for the files being stored in. This parameter
+ * is mandatory.
+ * \li \c max_size - Specifies the maximum total size, in bytes, of stored files that the collector
+ * will try not to exceed. If the size exceeds this threshold the oldest file(s) is
+ * deleted to free space. Note that the threshold may be exceeded if the size of
+ * individual files exceed the \c max_size value. The threshold is not maintained,
+ * if not specified.
+ * \li \c min_free_space - Specifies the minimum free space, in bytes, in the target directory that
+ * the collector tries to maintain. If the threshold is exceeded, the oldest
+ * file(s) is deleted to free space. The threshold is not maintained, if not
+ * specified.
+ *
+ * \return The file collector.
+ */
+template< typename... ArgsT >
+shared_ptr< collector > make_collector(ArgsT... const& args);
+
+#endif // BOOST_LOG_DOXYGEN_PASS
+
+/*!
+ * The class represents the time point of log file rotation. One can specify one of three
+ * types of time point based rotation:
+ *
+ * \li rotation takes place every day, at the specified time
+ * \li rotation takes place on the specified day of every week, at the specified time
+ * \li rotation takes place on the specified day of every month, at the specified time
+ *
+ * The time points are considered to be local time.
+ */
+class rotation_at_time_point
+{
+public:
+ typedef bool result_type;
+
+private:
+ enum day_kind
+ {
+ not_specified,
+ weekday,
+ monthday
+ };
+
+ day_kind m_DayKind : 2;
+ unsigned char m_Day : 6;
+ unsigned char m_Hour, m_Minute, m_Second;
+
+ mutable posix_time::ptime m_Previous;
+
+public:
+ /*!
+ * Creates a rotation time point of every day at the specified time
+ *
+ * \param hour The rotation hour, should be within 0 and 23
+ * \param minute The rotation minute, should be within 0 and 59
+ * \param second The rotation second, should be within 0 and 59
+ */
+ BOOST_LOG_API explicit rotation_at_time_point(unsigned char hour, unsigned char minute, unsigned char second);
+
+ /*!
+ * Creates a rotation time point of each specified weekday at the specified time
+ *
+ * \param wday The weekday of the rotation
+ * \param hour The rotation hour, should be within 0 and 23
+ * \param minute The rotation minute, should be within 0 and 59
+ * \param second The rotation second, should be within 0 and 59
+ */
+ BOOST_LOG_API explicit rotation_at_time_point(
+ date_time::weekdays wday,
+ unsigned char hour = 0,
+ unsigned char minute = 0,
+ unsigned char second = 0);
+
+ /*!
+ * Creates a rotation time point of each specified day of month at the specified time
+ *
+ * \param mday The monthday of the rotation, should be within 1 and 31
+ * \param hour The rotation hour, should be within 0 and 23
+ * \param minute The rotation minute, should be within 0 and 59
+ * \param second The rotation second, should be within 0 and 59
+ */
+ BOOST_LOG_API explicit rotation_at_time_point(
+ gregorian::greg_day mday,
+ unsigned char hour = 0,
+ unsigned char minute = 0,
+ unsigned char second = 0);
+
+ /*!
+ * Checks if it's time to rotate the file
+ */
+ BOOST_LOG_API bool operator() () const;
+};
+
+/*!
+ * The class represents the time interval of log file rotation. The log file will be rotated
+ * after the specified time interval has passed.
+ */
+class rotation_at_time_interval
+{
+public:
+ typedef bool result_type;
+
+private:
+ posix_time::time_duration m_Interval;
+ mutable posix_time::ptime m_Previous;
+
+public:
+ /*!
+ * Creates a rotation time interval of the specified duration
+ *
+ * \param interval The interval of the rotation, should be no less than 1 second
+ */
+ explicit rotation_at_time_interval(posix_time::time_duration const& interval) :
+ m_Interval(interval)
+ {
+ BOOST_ASSERT(!interval.is_special());
+ BOOST_ASSERT(interval.total_seconds() > 0);
+ }
+
+ /*!
+ * Checks if it's time to rotate the file
+ */
+ BOOST_LOG_API bool operator() () const;
+};
+
+} // namespace file
+
+
+/*!
+ * \brief An implementation of a text file logging sink backend
+ *
+ * The sink backend puts formatted log records to a text file.
+ * The sink supports file rotation and advanced file control, such as
+ * size and file count restriction.
+ */
+class text_file_backend :
+ public basic_formatted_sink_backend<
+ char,
+ combine_requirements< synchronized_feeding, flushing >::type
+ >
+{
+ //! Base type
+ typedef basic_formatted_sink_backend<
+ char,
+ combine_requirements< synchronized_feeding, flushing >::type
+ > base_type;
+
+public:
+ //! Character type
+ typedef base_type::char_type char_type;
+ //! String type to be used as a message text holder
+ typedef base_type::string_type string_type;
+ //! Stream type
+ typedef std::basic_ostream< char_type > stream_type;
+
+ //! File open handler
+ typedef boost::log::aux::light_function< void (stream_type&) > open_handler_type;
+ //! File close handler
+ typedef boost::log::aux::light_function< void (stream_type&) > close_handler_type;
+
+ //! Predicate that defines the time-based condition for file rotation
+ typedef boost::log::aux::light_function< bool () > time_based_rotation_predicate;
+
+private:
+ //! \cond
+
+ struct implementation;
+ implementation* m_pImpl;
+
+ //! \endcond
+
+public:
+ /*!
+ * Default constructor. The constructed sink backend uses default values of all the parameters.
+ */
+ BOOST_LOG_API text_file_backend();
+
+ /*!
+ * Constructor. Creates a sink backend with the specified named parameters.
+ * The following named parameters are supported:
+ *
+ * \li \c file_name - Specifies the file name pattern where logs are actually written to. The pattern may
+ * contain directory and file name portions, but only the file name may contain
+ * placeholders. The backend supports Boost.DateTime placeholders for injecting
+ * current time and date into the file name. Also, an additional %N placeholder is
+ * supported, it will be replaced with an integral increasing file counter. The placeholder
+ * may also contain width specification in the printf-compatible form (e.g. %5N). The
+ * printed file counter will always be zero-filled. If \c file_name is not specified,
+ * pattern "%5N.log" will be used.
+ * \li \c open_mode - File open mode. The mode should be presented in form of mask compatible to
+ * <tt>std::ios_base::openmode</tt>. If not specified, <tt>trunc | out</tt> will be used.
+ * \li \c rotation_size - Specifies the approximate size, in characters written, of the temporary file
+ * upon which the file is passed to the file collector. Note the size does
+ * not count any possible character conversions that may take place during
+ * writing to the file. If not specified, the file won't be rotated upon reaching
+ * any size.
+ * \li \c time_based_rotation - Specifies the predicate for time-based file rotation.
+ * No time-based file rotations will be performed, if not specified.
+ * \li \c auto_flush - Specifies a flag, whether or not to automatically flush the file after each
+ * written log record. By default, is \c false.
+ *
+ * \note Read the caution note regarding file name pattern in the <tt>sinks::file::collector::scan_for_files</tt>
+ * documentation.
+ */
+#ifndef BOOST_LOG_DOXYGEN_PASS
+ BOOST_LOG_PARAMETRIZED_CONSTRUCTORS_CALL(text_file_backend, construct)
+#else
+ template< typename... ArgsT >
+ explicit text_file_backend(ArgsT... const& args);
+#endif
+
+ /*!
+ * Destructor
+ */
+ BOOST_LOG_API ~text_file_backend();
+
+ /*!
+ * The method sets file name wildcard for the files being written. The wildcard supports
+ * date and time injection into the file name.
+ *
+ * \param pattern The name pattern for the file being written.
+ */
+ template< typename PathT >
+ void set_file_name_pattern(PathT const& pattern)
+ {
+ set_file_name_pattern_internal(filesystem::path(pattern));
+ }
+
+ /*!
+ * The method sets the file open mode
+ *
+ * \param mode File open mode
+ */
+ BOOST_LOG_API void set_open_mode(std::ios_base::openmode mode);
+
+ /*!
+ * The method sets the log file collector function. The function is called
+ * on file rotation and is being passed the written file name.
+ *
+ * \param collector The file collector function object
+ */
+ BOOST_LOG_API void set_file_collector(shared_ptr< file::collector > const& collector);
+
+ /*!
+ * The method sets file opening handler. The handler will be called every time
+ * the backend opens a new temporary file. The handler may write a header to the
+ * opened file in order to maintain file validity.
+ *
+ * \param handler The file open handler function object
+ */
+ BOOST_LOG_API void set_open_handler(open_handler_type const& handler);
+
+ /*!
+ * The method sets file closing handler. The handler will be called every time
+ * the backend closes a temporary file. The handler may write a footer to the
+ * opened file in order to maintain file validity.
+ *
+ * \param handler The file close handler function object
+ */
+ BOOST_LOG_API void set_close_handler(close_handler_type const& handler);
+
+ /*!
+ * The method sets maximum file size. When the size is reached, file rotation is performed.
+ *
+ * \note The size does not count any possible character translations that may happen in
+ * the underlying API. This may result in greater actual sizes of the written files.
+ *
+ * \param size The maximum file size, in characters.
+ */
+ BOOST_LOG_API void set_rotation_size(uintmax_t size);
+
+ /*!
+ * The method sets the predicate that defines the time-based condition for file rotation.
+ *
+ * \note The rotation always occurs on writing a log record, so the rotation is
+ * not strictly bound to the specified condition.
+ *
+ * \param predicate The predicate that defines the time-based condition for file rotation.
+ * If empty, no time-based rotation will take place.
+ */
+ BOOST_LOG_API void set_time_based_rotation(time_based_rotation_predicate const& predicate);
+
+ /*!
+ * Sets the flag to automatically flush buffers of all attached streams after each log record
+ */
+ BOOST_LOG_API void auto_flush(bool f = true);
+
+ /*!
+ * Performs scanning of the target directory for log files that may have been left from
+ * previous runs of the application. The found files are considered by the file collector
+ * as if they were rotated.
+ *
+ * The file scan can be performed in two ways: either all files in the target directory will
+ * be considered as log files, or only those files that satisfy the file name pattern.
+ * See documentation on <tt>sinks::file::collector::scan_for_files</tt> for more information.
+ *
+ * \pre File collector and the proper file name pattern have already been set.
+ *
+ * \param method File scanning method
+ * \param update_counter If \c true and \a method is \c scan_matching, the method attempts
+ * to update the internal file counter according to the found files. The counter
+ * is unaffected otherwise.
+ * \return The number of files found.
+ *
+ * \note The method essentially delegates to the same-named function of the file collector.
+ */
+ BOOST_LOG_API uintmax_t scan_for_files(
+ file::scan_method method = file::scan_matching, bool update_counter = true);
+
+ /*!
+ * The method writes the message to the sink
+ */
+ BOOST_LOG_API void consume(record_view const& rec, string_type const& formatted_message);
+
+ /*!
+ * The method flushes the currently open log file
+ */
+ BOOST_LOG_API void flush();
+
+ /*!
+ * The method rotates the file
+ */
+ BOOST_LOG_API void rotate_file();
+
+private:
+#ifndef BOOST_LOG_DOXYGEN_PASS
+ //! Constructor implementation
+ template< typename ArgsT >
+ void construct(ArgsT const& args)
+ {
+ construct(
+ filesystem::path(args[keywords::file_name | filesystem::path()]),
+ args[keywords::open_mode | (std::ios_base::trunc | std::ios_base::out)],
+ args[keywords::rotation_size | (std::numeric_limits< uintmax_t >::max)()],
+ args[keywords::time_based_rotation | time_based_rotation_predicate()],
+ args[keywords::auto_flush | false]);
+ }
+ //! Constructor implementation
+ BOOST_LOG_API void construct(
+ filesystem::path const& pattern,
+ std::ios_base::openmode mode,
+ uintmax_t rotation_size,
+ time_based_rotation_predicate const& time_based_rotation,
+ bool auto_flush);
+
+ //! The method sets file name mask
+ BOOST_LOG_API void set_file_name_pattern_internal(filesystem::path const& pattern);
+#endif // BOOST_LOG_DOXYGEN_PASS
+};
+
+} // namespace sinks
+
+BOOST_LOG_CLOSE_NAMESPACE // namespace log
+
+} // namespace boost
+
+#include <boost/log/detail/footer.hpp>
+
+#endif // BOOST_LOG_SINKS_TEXT_FILE_BACKEND_HPP_INCLUDED_