summaryrefslogtreecommitdiff
path: root/util/ramlog.h
diff options
context:
space:
mode:
Diffstat (limited to 'util/ramlog.h')
-rw-r--r--util/ramlog.h144
1 files changed, 34 insertions, 110 deletions
diff --git a/util/ramlog.h b/util/ramlog.h
index b2f3aa0..d3d5c8f 100644
--- a/util/ramlog.h
+++ b/util/ramlog.h
@@ -1,4 +1,4 @@
-// log.h
+// ramlog.h
/* Copyright 2009 10gen Inc.
*
@@ -18,124 +18,48 @@
#pragma once
#include "log.h"
-#include "mongoutils/html.h"
namespace mongo {
class RamLog : public Tee {
- enum {
- N = 128,
- C = 256
- };
- char lines[N][C];
- unsigned h, n;
-
public:
- RamLog() {
- h = 0; n = 0;
- for( int i = 0; i < N; i++ )
- lines[i][C-1] = 0;
- }
-
- virtual void write(LogLevel ll, const string& str) {
- char *p = lines[(h+n)%N];
- if( str.size() < C )
- strcpy(p, str.c_str());
- else
- memcpy(p, str.c_str(), C-1);
- if( n < N ) n++;
- else h = (h+1) % N;
- }
-
- void get( vector<const char*>& v) const {
- for( unsigned x=0, i=h; x++ < n; i=(i+1)%N )
- v.push_back(lines[i]);
- }
-
- static int repeats(const vector<const char *>& v, int i) {
- for( int j = i-1; j >= 0 && j+8 > i; j-- ) {
- if( strcmp(v[i]+20,v[j]+20) == 0 ) {
- for( int x = 1; ; x++ ) {
- if( j+x == i ) return j;
- if( i+x>=(int) v.size() ) return -1;
- if( strcmp(v[i+x]+20,v[j+x]+20) ) return -1;
- }
- return -1;
- }
- }
- return -1;
- }
-
-
- static string clean(const vector<const char *>& v, int i, string line="") {
- if( line.empty() ) line = v[i];
- if( i > 0 && strncmp(v[i], v[i-1], 11) == 0 )
- return string(" ") + line.substr(11);
- return v[i];
- }
-
- static string color(string line) {
- string s = str::after(line, "replSet ");
- if( str::startsWith(s, "warning") || startsWith(s, "error") )
- return html::red(line);
- if( str::startsWith(s, "info") ) {
- if( str::endsWith(s, " up\n") )
- return html::green(line);
- else if( str::contains(s, " down ") || str::endsWith(s, " down\n") )
- return html::yellow(line);
- return line; //html::blue(line);
- }
-
- return line;
- }
+ RamLog( string name );
+
+ virtual void write(LogLevel ll, const string& str);
+
+ void get( vector<const char*>& v) const;
+
+ void toHTML(stringstream& s);
+
+ static RamLog* get( string name );
+ static void getNames( vector<string>& names );
+
+ time_t lastWrite() { return _lastWrite; } // 0 if no writes
+
+ protected:
+ static int repeats(const vector<const char *>& v, int i);
+ static string clean(const vector<const char *>& v, int i, string line="");
+ static string color(string line);
/* turn http:... into an anchor */
- string linkify(const char *s) {
- const char *p = s;
- const char *h = strstr(p, "http://");
- if( h == 0 ) return s;
-
- const char *sp = h + 7;
- while( *sp && *sp != ' ' ) sp++;
-
- string url(h, sp-h);
- stringstream ss;
- ss << string(s, h-s) << "<a href=\"" << url << "\">" << url << "</a>" << sp;
- return ss.str();
- }
-
- void toHTML(stringstream& s) {
- vector<const char*> v;
- get( v );
-
- s << "<pre>\n";
- for( int i = 0; i < (int)v.size(); i++ ) {
- assert( strlen(v[i]) > 20 );
- int r = repeats(v, i);
- if( r < 0 ) {
- s << color( linkify( clean(v,i).c_str() ) );
- }
- else {
- stringstream x;
- x << string(v[i], 0, 20);
- int nr = (i-r);
- int last = i+nr-1;
- for( ; r < i ; r++ ) x << '.';
- if( 1 ) {
- stringstream r;
- if( nr == 1 ) r << "repeat last line";
- else r << "repeats last " << nr << " lines; ends " << string(v[last]+4,0,15);
- s << html::a("", r.str(), clean(v,i,x.str()));
- }
- else s << x.str();
- s << '\n';
- i = last;
- }
- }
- s << "</pre>\n";
- }
+ static string linkify(const char *s);
+ private:
+ ~RamLog(); // want this private as we want to leak so we can use them till the very end
+ enum {
+ N = 128, // number of links
+ C = 256 // max size of line
+ };
+ char lines[N][C];
+ unsigned h; // current position
+ unsigned n; // numer of lines stores 0 o N
+ string _name;
+
+ typedef map<string,RamLog*> RM;
+ static mongo::mutex* _namedLock;
+ static RM* _named;
+ time_t _lastWrite;
};
}