0.9.8.10
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
StatusPersister.cc
Go to the documentation of this file.
1 /* -*- c++ -*-
2  * Copyright (C) 2007-2014 Hypertable, Inc.
3  *
4  * This file is part of Hypertable.
5  *
6  * Hypertable is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; version 3 of the
9  * License, or any later version.
10  *
11  * Hypertable is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19  * 02110-1301, USA.
20  */
21 
26 
27 #include <Common/Compat.h>
28 
29 #include "StatusPersister.h"
30 
31 #include <Common/FileUtils.h>
32 #include <Common/Logger.h>
33 #include <Common/System.h>
34 
35 #include <cstdio>
36 #include <cstring>
37 #include <ctime>
38 
39 extern "C" {
40 #include <fcntl.h>
41 #include <sys/stat.h>
42 #include <sys/types.h>
43 #include <unistd.h>
44 }
45 
46 using namespace Hypertable;
47 using namespace std;
48 
50 std::string StatusPersister::ms_fname;
52 
53 namespace {
54  const char *header =
55  "# Persistent Status Log for %s\n"
56  "# The last entry in this file will be returned during the %s\n"
57  "# status check. Once the issues described below have been dealt with, this file\n"
58  "# can be removed to clear the %s persistent status and\n"
59  "# return to normal dynamic status checking.\n"
60  "#\n";
61  string header_string() {
62  return format(header, System::exe_name.c_str(), System::exe_name.c_str(),
63  System::exe_name.c_str());
64  }
65 }
66 
83  std::vector<std::string> additional_lines) {
84  lock_guard<mutex> lock(ms_mutex);
85 
86  if (ms_fname.empty())
87  initialize();
88 
89  bool append {true};
90  string text;
91 
92  if (!FileUtils::exists(ms_fname)) {
93  text = header_string();
94  append = false;
95  }
96 
97  ms_status = status;
98 
99  Status::Code code;
100  string status_text;
101  ms_status.get(&code, status_text);
102  text += format("%s - %s\n", Status::code_to_string(code), status_text.c_str());
103 
104  {
105  time_t rawtime;
106  tm* timeinfo;
107  char buffer [80];
108  time(&rawtime);
109  timeinfo = localtime(&rawtime);
110  strftime(buffer, 80, "%Y-%m-%d %H:%M:%S", timeinfo);
111  text += format("- Time %s\n", (const char *)buffer);
112  }
113 
114  for (auto & str : additional_lines) {
115  if (!str.empty())
116  text += format("- %s\n", str.c_str());
117  }
118 
119  if (append) {
120  int fd = ::open(ms_fname.c_str(), O_WRONLY | O_APPEND);
121  if (fd < 0) {
122  string message = strerror(errno);
123  HT_ERRORF("Unable to open file \"%s\" for writing - %s", ms_fname.c_str(),
124  message.c_str());
125  }
126  else {
127  FileUtils::write(fd, text);
128  ::close(fd);
129  }
130  }
131  else
132  FileUtils::write(ms_fname, text);
133 }
134 
136  lock_guard<mutex> lock(ms_mutex);
137  if (ms_fname.empty())
138  initialize();
139  status = ms_status;
140 }
141 
143  ms_fname = System::install_dir + "/run/STATUS." + System::exe_name;
144  if (FileUtils::exists(ms_fname)) {
145  string last_line, contents;
146  FileUtils::read(ms_fname, contents);
147  const char *base = contents.c_str();
148  const char *ptr = strchr(base, '\n');
149  while (ptr) {
150  if (*base != '#' && *base != '-')
151  last_line = string(base, ptr-base);
152  base = ptr+1;
153  ptr = strchr(base, '\n');
154  }
155  if (*base && *base != '#' && *base != '-')
156  last_line = string(base, ptr-base);
157  if (!last_line.empty()) {
158  if (last_line.find("WARNING - ") == 0)
159  ms_status.set(Status::Code::WARNING, last_line.substr(10));
160  else if (last_line.find("CRITICAL - ") == 0)
161  ms_status.set(Status::Code::CRITICAL, last_line.substr(11));
162  else if (last_line.find("UNKNOWN - ") == 0)
163  ms_status.set(Status::Code::UNKNOWN, last_line.substr(10));
164  else if (last_line.find("OK - ") != 0)
165  HT_INFOF("Corrupt persistent status file %s", ms_fname.c_str());
166  }
167  }
168 }
Retrieves system information (hardware, installation directory, etc)
static std::mutex mutex
Definition: Logger.cc:43
void initialize(const String &name)
Public initialization function - creates a singleton instance of LogWriter.
Definition: Logger.cc:45
Holds Nagios-style program status information.
Definition: Status.h:42
static bool read(const String &fname, String &contents)
Reads a whole file into a String.
Definition: FileUtils.cc:59
String format(const char *fmt,...)
Returns a String using printf like format facilities Vanilla snprintf is about 1.5x faster than this...
Definition: String.cc:37
Po::typed_value< String > * str(String *v=0)
Definition: Properties.h:166
static ssize_t write(const String &fname, const std::string &contents)
Writes a String buffer to a file; the file is overwritten if it already exists.
Definition: FileUtils.cc:124
static bool exists(const String &fname)
Checks if a file or directory exists.
Definition: FileUtils.cc:420
STL namespace.
Code
Enumeration for status codes.
Definition: Status.h:47
static const char * code_to_string(Code code)
Definition: Status.cc:39
File system utility functions.
static Status ms_status
Current persistent status.
bool status(ContextPtr &context, Timer &timer, Status &status)
Runs a status check on the master.
Definition: Utility.cc:408
static String exe_name
The exe file name.
Definition: System.h:120
Logging routines and macros.
static std::mutex ms_mutex
Mutex for serializaing access to members
Compatibility Macros for C/C++.
Hypertable definitions
static void set(const Status &status, std::vector< std::string > additional_lines)
Sets persistent status.
static void get(Status &status)
Gets persistent status.
#define HT_INFOF(msg,...)
Definition: Logger.h:272
static String install_dir
The installation directory.
Definition: System.h:114
static void initialize()
Initializes variables.
Declarations for StatusPersister.
#define HT_ERRORF(msg,...)
Definition: Logger.h:300
static std::string ms_fname
Name of persistent status file.