1
  
2
  
3
  
4
  
5
  
6
  
7
  
8
  
9
  
10
  
11
  
12
  
13
  
14
  
15
  
16
  
17
  
18
  
19
  
20
  
21
  
22
  
23
  
24
  
25
  
26
  
27
  
28
  
29
  
30
  
31
  
32
  
33
  
34
  
35
  
36
  
37
  
38
  
39
  
40
  
41
  
42
  
43
  
44
  
45
  
46
  
47
  
48
  
49
  
50
  
51
  
52
  
53
  
54
  
55
  
56
  
57
  
58
  
59
  
60
  
61
  
62
  
63
  
64
  
65
  
66
  
67
  
68
  
69
  
70
  
71
  
72
  
73
  
74
  
75
  
76
  
77
  
78
  
79
  
80
  
81
  
82
  
83
  
84
  
85
  
86
  
87
  
88
  
89
  
90
  
91
  
92
  
93
  
94
  
95
  
96
  
97
  
98
  
99
  
100
  
101
  
102
  
103
  
104
  
105
  
106
  
107
  
108
  
109
  
110
  
111
  
112
  
113
  
114
  
115
  
116
  
117
  
118
  
119
  
120
  
121
  
122
  
123
  
124
  
// This file is part of Roxen Search 
// Copyright © 2001 Roxen IS. All rights reserved. 
// 
// $Id: Utils.pmod,v 1.8 2001/07/04 20:42:20 nilsson Exp $ 
 
public array(string) tokenize_and_normalize( string what ) 
//! This can be optimized quite significantly when compared to 
//! tokenize( normalize( x ) ) in the future, currently it's not all 
//! that much faster, but still faster. 
{ 
  return Unicode.split_words_and_normalize( lower_case(what) ); 
} 
 
public array(string) tokenize(string in) 
//! Tokenize the input string (Note: You should first call normalize 
//! on it) 
{ 
  return Unicode.split_words( in ); 
} 
 
 
public string normalize(string in) 
//! Normalize the input string. Performs unicode NFKD normalization 
//! and then lowercases the whole string 
{ 
  return Unicode.normalize( lower_case(in), "KD" ); 
} 
 
class Logger { 
 
  private string|Sql.Sql logdb; 
  private int profile; 
 
  private Sql.Sql get_db() { 
    Sql.Sql db; 
#if constant(DBManager) 
    if(stringp(logdb)) 
      db = DBManager.get(logdb); 
    else 
#endif 
      db = logdb; 
 
    //    if(!logdb || !logdb->query) 
    //      throw( ({ "Couldn't find any database object.\n", backtrace() }) ); 
 
    return db; 
  } 
 
  void create(string|Sql.Sql _logdb, int _profile) { 
    logdb = _logdb; 
    profile = _profile; 
 
    // create table eventlog (event int unsigned auto_increment primary key, 
    // at timestamp(14) not null, code int unsigned not null, extra varchar(255)) 
 
    Sql.Sql db = get_db(); 
 
    if(catch(db->query("SELECT code FROM eventlog WHERE event=0"))) 
      db->query("CREATE TABLE eventlog (" 
                "event int unsigned auto_increment primary key," 
                "at timestamp(14) not null," 
                "profile int unsigned not null," 
                "code int unsigned not null," 
                "type enum('error','warning','notice') not null," 
                "extra varchar(255))"); 
  } 
 
  void log_event( int code, string type, void|string extra ) { 
    Sql.Sql db = get_db(); 
    if(!db) return; 
 
    if(extra) 
      db->query("INSERT INTO eventlog (profile,code,type,extra) VALUES (%d,%d,%s,%s)", 
                profile, code, type, extra); 
    else 
      db->query("INSERT INTO eventlog (profile, code,type) VALUES (%d,%d,%s)", 
                profile, code, type); 
  } 
 
  void log_error( int code, void|string extra ) { 
    log_event( code, "error", extra ); 
  } 
 
  void log_warning( int code, void|string extra ) { 
    log_event( code, "warning", extra ); 
  } 
 
  void log_notice( int code, void|string extra ) { 
    log_event( code, "notices", extra ); 
  } 
 
  private mapping codes = ([ 
    404 : "File %s not found", 
  ]); 
 
  array(array(string|int)) get_log( int profile, array(string) types, 
                                int from, int to ) { 
 
    string sql = ""; 
#define SQLADD(X) do{sizeof(sql)?(sql=" WHERE "+(X)):(sql+=" AND "+(X));}while(0) 
    if(profile) 
      SQLADD("profile=" + profile); 
    if(!sizeof(types)) 
      return ({}); 
    if(sizeof(types)!=3) 
      SQLADD("(type='" + (types*"' OR type='") + "')"); 
    if(from) 
      SQLADD("at>" + from); 
    if(to) 
      SQLADD("to<" + to); 
#undef SQLADD 
 
    Sql.Sql db = get_db(); 
    if(!db) return ({}); 
 
    return map(db->query("SELECT unix_timestamp(at) as at,profile,code,type,extra FROM eventlog"+sql), 
               lambda(mapping in) { 
                 return ({ (int)in->at, (int)in->profile, in->type, 
                           in->extra?sprintf(codes[(int)in->code], in->extra):codes[(int)in->code] }); 
               } ); 
  } 
}