Fossil SCM

Two new settings "show-repolist-desc" and "show-repolist-lg" control whether or not the description and the login-group are shown on the repolist, respectively. These settings must be global to be effective. They default to "off".

drh 2025-04-15 15:56 trunk
Commit 1760fa2bf4ab1285ed606c52e77f6f1946a1e5b4560bfb1507d97d4dd84945bd
1 file changed +87 -29
+87 -29
--- src/repolist.c
+++ src/repolist.c
@@ -101,10 +101,25 @@
101101
finish_repo_list:
102102
g.dbIgnoreErrors--;
103103
sqlite3_close(db);
104104
}
105105
106
+/*
107
+** SETTING: show-repolist-desc boolean default=off
108
+**
109
+** If the value of this setting is "1" globally, then the repository-list
110
+** page will show the description of each repository. This setting only
111
+** has effect when it is in the global setting database.
112
+*/
113
+/*
114
+** SETTING: show-repolist-lg boolean default=off
115
+**
116
+** If the value of this setting is "1" globally, then the repository-list
117
+** page will show the login-group for each repository. This setting only
118
+** has effect when it is in the global setting database.
119
+*/
120
+
106121
/*
107122
** Generate a web-page that lists all repositories located under the
108123
** g.zRepositoryName directory and return non-zero.
109124
**
110125
** For the special case when g.zRepositoryName is a non-chroot-jail "/",
@@ -126,12 +141,19 @@
126141
int allRepo; /* True if running "fossil ui all".
127142
** False if a directory scan of base for repos */
128143
Blob html; /* Html for the body of the repository list */
129144
char *zSkinRepo = 0; /* Name of the repository database used for skins */
130145
char *zSkinUrl = 0; /* URL for the skin database */
146
+ int bShowDesc = 0; /* True to show the description column */
147
+ int bShowLg = 0; /* True to show the login-group column */
131148
132149
assert( g.db==0 );
150
+ db_open_config(1, 0);
151
+ bShowDesc = (0!=db_int(0, "SELECT value FROM global_config"
152
+ " WHERE name='show-repolist-desc'"));
153
+ bShowLg = (0!=db_int(0, "SELECT value FROM global_config"
154
+ " WHERE name='show-repolist-lg'"));
133155
blob_init(&html, 0, 0);
134156
if( fossil_strcmp(g.zRepositoryName,"/")==0 && !g.fJail ){
135157
/* For the special case of the "repository directory" being "/",
136158
** show all of the repositories named in the ~/.fossil database.
137159
**
@@ -138,11 +160,10 @@
138160
** On unix systems, then entries are of the form "repo:/home/..."
139161
** and on Windows systems they are like on unix, starting with a "/"
140162
** or they can begin with a drive letter: "repo:C:/Users/...". In either
141163
** case, we want returned path to omit any initial "/".
142164
*/
143
- db_open_config(1, 0);
144165
db_multi_exec(
145166
"CREATE TEMP VIEW sfile AS"
146167
" SELECT ltrim(substr(name,6),'/') AS 'pathname' FROM global_config"
147168
" WHERE name GLOB 'repo:*'"
148169
);
@@ -150,10 +171,12 @@
150171
}else{
151172
/* The default case: All repositories under the g.zRepositoryName
152173
** directory.
153174
*/
154175
blob_init(&base, g.zRepositoryName, -1);
176
+ db_close(0);
177
+ assert( g.db==0 );
155178
sqlite3_open(":memory:", &g.db);
156179
db_multi_exec("CREATE TABLE sfile(pathname TEXT);");
157180
db_multi_exec("CREATE TABLE vfile(pathname);");
158181
vfile_scan(&base, blob_size(&base), 0, 0, 0, ExtFILE);
159182
db_multi_exec("DELETE FROM sfile WHERE pathname NOT GLOB '*[^/].fossil'"
@@ -171,19 +194,50 @@
171194
g.localOpen = 0;
172195
return 0;
173196
}else{
174197
Stmt q;
175198
double rNow;
176
- blob_append_sql(&html,
199
+ char zType[16]; /* Column type letters for class "sortable" */
200
+ int nType;
201
+ zType[0] = 't'; /* Repo name */
202
+ zType[1] = 'x'; /* Space between repo-name and project-name */
203
+ zType[2] = 't'; /* Project name */
204
+ nType = 3;
205
+ if( bShowDesc ){
206
+ zType[nType++] = 'x'; /* Space between name and description */
207
+ zType[nType++] = 't'; /* Project description */
208
+ }
209
+ zType[nType++] = 'x'; /* space before age */
210
+ zType[nType++] = 'k'; /* Project age */
211
+ if( bShowLg ){
212
+ zType[nType++] = 'x'; /* space before login-group */
213
+ zType[nType++] = 't'; /* Login Group */
214
+ }
215
+ zType[nType] = 0;
216
+ blob_appendf(&html,
177217
"<table border='0' class='sortable' data-init-sort='1'"
178
- " data-column-types='txtxtxkxt' cellspacing='0' cellpadding='0'><thead>\n"
179
- "<tr><th>Filename<th width='7'>"
180
- "<th width='25%%'>Project Name<th width='10'>"
181
- "<th width='25%%'>Project Description<th width='5'>"
182
- "<th><nobr>Last Modified</nobr><th width='1'>"
183
- "<th><nobr>Login Group</nobr></tr>\n"
184
- "</thead><tbody>\n");
218
+ " data-column-types='%s' cellspacing='0' cellpadding='0'><thead>\n"
219
+ "<tr><th>Filename</th><th>&emsp;</th>\n"
220
+ "<th%s><nobr>Project Name</nobr></th>\n",
221
+ zType, (bShowDesc ? " width='25%'" : ""));
222
+ if( bShowDesc ){
223
+ blob_appendf(&html,
224
+ "<th>&emsp;</th>\n"
225
+ "<th width='25%%'><nobr>Project Description</nobr></th>\n"
226
+ );
227
+ }
228
+ blob_appendf(&html,
229
+ "<th>&emsp;</th>"
230
+ "<th><nobr>Last Modified</nobr></th>\n"
231
+ );
232
+ if( bShowLg ){
233
+ blob_appendf(&html,
234
+ "<th>&emsp;</th>"
235
+ "<th><nobr>Login Group</nobr></th></tr>\n"
236
+ );
237
+ }
238
+ blob_appendf(&html,"</thead><tbody>\n");
185239
db_prepare(&q, "SELECT pathname"
186240
" FROM sfile ORDER BY pathname COLLATE nocase;");
187241
rNow = db_double(0, "SELECT julianday('now')");
188242
while( db_step(&q)==SQLITE_ROW ){
189243
const char *zName = db_column_text(&q, 0);
@@ -242,21 +296,21 @@
242296
if( x.rMTime==0.0 ){
243297
/* This repository has no entry in the "event" table.
244298
** Its age will still be maximum, so data-sortkey will work. */
245299
zAge = mprintf("unknown");
246300
}
247
- blob_append_sql(&html, "<tr><td valign='top'><nobr>");
301
+ blob_appendf(&html, "<tr><td valign='top'><nobr>");
248302
if( !file_ends_with_repository_extension(zName,0) ){
249303
/* The "fossil server DIRECTORY" and "fossil ui DIRECTORY" commands
250304
** do not work for repositories whose names do not end in ".fossil".
251305
** So do not hyperlink those cases. */
252
- blob_append_sql(&html,"%h",zName);
306
+ blob_appendf(&html,"%h",zName);
253307
} else if( sqlite3_strglob("*/.*", zName)==0 ){
254308
/* Do not show hyperlinks for hidden repos */
255
- blob_append_sql(&html, "%h (hidden)", zName);
309
+ blob_appendf(&html, "%h (hidden)", zName);
256310
} else if( allRepo && sqlite3_strglob("[a-zA-Z]:/?*", zName)!=0 ){
257
- blob_append_sql(&html,
311
+ blob_appendf(&html,
258312
"<a href='%R/%T/home' target='_blank'>/%h</a>\n",
259313
zUrl, zName);
260314
}else if( file_ends_with_repository_extension(zName,1) ){
261315
/* As described in
262316
** https://fossil-scm.org/forum/info/f50f647c97c72fc1: if
@@ -273,56 +327,60 @@
273327
, zDirPart
274328
#if USE_SEE
275329
, zDirPart
276330
#endif
277331
) ){
278
- blob_append_sql(&html,
332
+ blob_appendf(&html,
279333
"<s>%h</s> (directory/repo name collision)\n",
280334
zName);
281335
}else{
282
- blob_append_sql(&html,
336
+ blob_appendf(&html,
283337
"<a href='%R/%T/home' target='_blank'>%h</a>\n",
284338
zUrl, zName);
285339
}
286340
fossil_free(zDirPart);
287341
}else{
288
- blob_append_sql(&html,
342
+ blob_appendf(&html,
289343
"<a href='%R/%T/home' target='_blank'>%h</a>\n",
290344
zUrl, zName);
291345
}
292
- blob_append_sql(&html,"</nobr>");
346
+ blob_appendf(&html,"</nobr></td>\n");
293347
if( x.zProjName ){
294
- blob_append_sql(&html, "<td></td><td valign='top'>%h</td>\n",
295
- x.zProjName);
348
+ blob_appendf(&html, "<td>&emsp;</td><td valign='top'>%h</td>\n",
349
+ x.zProjName);
296350
fossil_free(x.zProjName);
297351
}else{
298
- blob_append_sql(&html, "<td></td><td></td>\n");
352
+ blob_appendf(&html, "<td>&emsp;</td><td></td>\n");
299353
}
300
- if( x.zProjDesc ){
301
- blob_append_sql(&html, "<td></td><td valign='top'>%h</td>\n",
354
+ if( !bShowDesc ){
355
+ /* Do nothing */
356
+ }else if( x.zProjDesc ){
357
+ blob_appendf(&html, "<td>&emsp;</td><td valign='top'>%h</td>\n",
302358
x.zProjDesc);
303359
fossil_free(x.zProjDesc);
304360
}else{
305
- blob_append_sql(&html, "<td></td><td></td>\n");
361
+ blob_appendf(&html, "<td>&emsp;</td><td></td>\n");
306362
}
307
- blob_append_sql(&html,
308
- "<td></td><td data-sortkey='%08x' align='center' valign='top'>"
363
+ blob_appendf(&html,
364
+ "<td>&emsp;</td><td data-sortkey='%08x' align='center' valign='top'>"
309365
"<nobr>%h</nobr></td>\n",
310366
(int)iAge, zAge);
311367
fossil_free(zAge);
312
- if( x.zLoginGroup ){
313
- blob_append_sql(&html, "<td></td><td valign='top'>"
368
+ if( !bShowLg ){
369
+ blob_appendf(&html, "</tr>\n");
370
+ }else if( x.zLoginGroup ){
371
+ blob_appendf(&html, "<td>&emsp;</td><td valign='top'>"
314372
"<nobr>%h</nobr></td></tr>\n",
315373
x.zLoginGroup);
316374
fossil_free(x.zLoginGroup);
317375
}else{
318
- blob_append_sql(&html, "<td></td><td></td></tr>\n");
376
+ blob_appendf(&html, "<td>&emsp;</td><td></td></tr>\n");
319377
}
320378
sqlite3_free(zUrl);
321379
}
322380
db_finalize(&q);
323
- blob_append_sql(&html,"</tbody></table>\n");
381
+ blob_appendf(&html,"</tbody></table>\n");
324382
}
325383
if( zSkinRepo ){
326384
char *zNewBase = mprintf("%s/%s", g.zBaseURL, zSkinUrl);
327385
g.zBaseURL = 0;
328386
set_base_url(zNewBase);
329387
--- src/repolist.c
+++ src/repolist.c
@@ -101,10 +101,25 @@
101 finish_repo_list:
102 g.dbIgnoreErrors--;
103 sqlite3_close(db);
104 }
105
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
106 /*
107 ** Generate a web-page that lists all repositories located under the
108 ** g.zRepositoryName directory and return non-zero.
109 **
110 ** For the special case when g.zRepositoryName is a non-chroot-jail "/",
@@ -126,12 +141,19 @@
126 int allRepo; /* True if running "fossil ui all".
127 ** False if a directory scan of base for repos */
128 Blob html; /* Html for the body of the repository list */
129 char *zSkinRepo = 0; /* Name of the repository database used for skins */
130 char *zSkinUrl = 0; /* URL for the skin database */
 
 
131
132 assert( g.db==0 );
 
 
 
 
 
133 blob_init(&html, 0, 0);
134 if( fossil_strcmp(g.zRepositoryName,"/")==0 && !g.fJail ){
135 /* For the special case of the "repository directory" being "/",
136 ** show all of the repositories named in the ~/.fossil database.
137 **
@@ -138,11 +160,10 @@
138 ** On unix systems, then entries are of the form "repo:/home/..."
139 ** and on Windows systems they are like on unix, starting with a "/"
140 ** or they can begin with a drive letter: "repo:C:/Users/...". In either
141 ** case, we want returned path to omit any initial "/".
142 */
143 db_open_config(1, 0);
144 db_multi_exec(
145 "CREATE TEMP VIEW sfile AS"
146 " SELECT ltrim(substr(name,6),'/') AS 'pathname' FROM global_config"
147 " WHERE name GLOB 'repo:*'"
148 );
@@ -150,10 +171,12 @@
150 }else{
151 /* The default case: All repositories under the g.zRepositoryName
152 ** directory.
153 */
154 blob_init(&base, g.zRepositoryName, -1);
 
 
155 sqlite3_open(":memory:", &g.db);
156 db_multi_exec("CREATE TABLE sfile(pathname TEXT);");
157 db_multi_exec("CREATE TABLE vfile(pathname);");
158 vfile_scan(&base, blob_size(&base), 0, 0, 0, ExtFILE);
159 db_multi_exec("DELETE FROM sfile WHERE pathname NOT GLOB '*[^/].fossil'"
@@ -171,19 +194,50 @@
171 g.localOpen = 0;
172 return 0;
173 }else{
174 Stmt q;
175 double rNow;
176 blob_append_sql(&html,
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
177 "<table border='0' class='sortable' data-init-sort='1'"
178 " data-column-types='txtxtxkxt' cellspacing='0' cellpadding='0'><thead>\n"
179 "<tr><th>Filename<th width='7'>"
180 "<th width='25%%'>Project Name<th width='10'>"
181 "<th width='25%%'>Project Description<th width='5'>"
182 "<th><nobr>Last Modified</nobr><th width='1'>"
183 "<th><nobr>Login Group</nobr></tr>\n"
184 "</thead><tbody>\n");
 
 
 
 
 
 
 
 
 
 
 
 
 
 
185 db_prepare(&q, "SELECT pathname"
186 " FROM sfile ORDER BY pathname COLLATE nocase;");
187 rNow = db_double(0, "SELECT julianday('now')");
188 while( db_step(&q)==SQLITE_ROW ){
189 const char *zName = db_column_text(&q, 0);
@@ -242,21 +296,21 @@
242 if( x.rMTime==0.0 ){
243 /* This repository has no entry in the "event" table.
244 ** Its age will still be maximum, so data-sortkey will work. */
245 zAge = mprintf("unknown");
246 }
247 blob_append_sql(&html, "<tr><td valign='top'><nobr>");
248 if( !file_ends_with_repository_extension(zName,0) ){
249 /* The "fossil server DIRECTORY" and "fossil ui DIRECTORY" commands
250 ** do not work for repositories whose names do not end in ".fossil".
251 ** So do not hyperlink those cases. */
252 blob_append_sql(&html,"%h",zName);
253 } else if( sqlite3_strglob("*/.*", zName)==0 ){
254 /* Do not show hyperlinks for hidden repos */
255 blob_append_sql(&html, "%h (hidden)", zName);
256 } else if( allRepo && sqlite3_strglob("[a-zA-Z]:/?*", zName)!=0 ){
257 blob_append_sql(&html,
258 "<a href='%R/%T/home' target='_blank'>/%h</a>\n",
259 zUrl, zName);
260 }else if( file_ends_with_repository_extension(zName,1) ){
261 /* As described in
262 ** https://fossil-scm.org/forum/info/f50f647c97c72fc1: if
@@ -273,56 +327,60 @@
273 , zDirPart
274 #if USE_SEE
275 , zDirPart
276 #endif
277 ) ){
278 blob_append_sql(&html,
279 "<s>%h</s> (directory/repo name collision)\n",
280 zName);
281 }else{
282 blob_append_sql(&html,
283 "<a href='%R/%T/home' target='_blank'>%h</a>\n",
284 zUrl, zName);
285 }
286 fossil_free(zDirPart);
287 }else{
288 blob_append_sql(&html,
289 "<a href='%R/%T/home' target='_blank'>%h</a>\n",
290 zUrl, zName);
291 }
292 blob_append_sql(&html,"</nobr>");
293 if( x.zProjName ){
294 blob_append_sql(&html, "<td></td><td valign='top'>%h</td>\n",
295 x.zProjName);
296 fossil_free(x.zProjName);
297 }else{
298 blob_append_sql(&html, "<td></td><td></td>\n");
299 }
300 if( x.zProjDesc ){
301 blob_append_sql(&html, "<td></td><td valign='top'>%h</td>\n",
 
 
302 x.zProjDesc);
303 fossil_free(x.zProjDesc);
304 }else{
305 blob_append_sql(&html, "<td></td><td></td>\n");
306 }
307 blob_append_sql(&html,
308 "<td></td><td data-sortkey='%08x' align='center' valign='top'>"
309 "<nobr>%h</nobr></td>\n",
310 (int)iAge, zAge);
311 fossil_free(zAge);
312 if( x.zLoginGroup ){
313 blob_append_sql(&html, "<td></td><td valign='top'>"
 
 
314 "<nobr>%h</nobr></td></tr>\n",
315 x.zLoginGroup);
316 fossil_free(x.zLoginGroup);
317 }else{
318 blob_append_sql(&html, "<td></td><td></td></tr>\n");
319 }
320 sqlite3_free(zUrl);
321 }
322 db_finalize(&q);
323 blob_append_sql(&html,"</tbody></table>\n");
324 }
325 if( zSkinRepo ){
326 char *zNewBase = mprintf("%s/%s", g.zBaseURL, zSkinUrl);
327 g.zBaseURL = 0;
328 set_base_url(zNewBase);
329
--- src/repolist.c
+++ src/repolist.c
@@ -101,10 +101,25 @@
101 finish_repo_list:
102 g.dbIgnoreErrors--;
103 sqlite3_close(db);
104 }
105
106 /*
107 ** SETTING: show-repolist-desc boolean default=off
108 **
109 ** If the value of this setting is "1" globally, then the repository-list
110 ** page will show the description of each repository. This setting only
111 ** has effect when it is in the global setting database.
112 */
113 /*
114 ** SETTING: show-repolist-lg boolean default=off
115 **
116 ** If the value of this setting is "1" globally, then the repository-list
117 ** page will show the login-group for each repository. This setting only
118 ** has effect when it is in the global setting database.
119 */
120
121 /*
122 ** Generate a web-page that lists all repositories located under the
123 ** g.zRepositoryName directory and return non-zero.
124 **
125 ** For the special case when g.zRepositoryName is a non-chroot-jail "/",
@@ -126,12 +141,19 @@
141 int allRepo; /* True if running "fossil ui all".
142 ** False if a directory scan of base for repos */
143 Blob html; /* Html for the body of the repository list */
144 char *zSkinRepo = 0; /* Name of the repository database used for skins */
145 char *zSkinUrl = 0; /* URL for the skin database */
146 int bShowDesc = 0; /* True to show the description column */
147 int bShowLg = 0; /* True to show the login-group column */
148
149 assert( g.db==0 );
150 db_open_config(1, 0);
151 bShowDesc = (0!=db_int(0, "SELECT value FROM global_config"
152 " WHERE name='show-repolist-desc'"));
153 bShowLg = (0!=db_int(0, "SELECT value FROM global_config"
154 " WHERE name='show-repolist-lg'"));
155 blob_init(&html, 0, 0);
156 if( fossil_strcmp(g.zRepositoryName,"/")==0 && !g.fJail ){
157 /* For the special case of the "repository directory" being "/",
158 ** show all of the repositories named in the ~/.fossil database.
159 **
@@ -138,11 +160,10 @@
160 ** On unix systems, then entries are of the form "repo:/home/..."
161 ** and on Windows systems they are like on unix, starting with a "/"
162 ** or they can begin with a drive letter: "repo:C:/Users/...". In either
163 ** case, we want returned path to omit any initial "/".
164 */
 
165 db_multi_exec(
166 "CREATE TEMP VIEW sfile AS"
167 " SELECT ltrim(substr(name,6),'/') AS 'pathname' FROM global_config"
168 " WHERE name GLOB 'repo:*'"
169 );
@@ -150,10 +171,12 @@
171 }else{
172 /* The default case: All repositories under the g.zRepositoryName
173 ** directory.
174 */
175 blob_init(&base, g.zRepositoryName, -1);
176 db_close(0);
177 assert( g.db==0 );
178 sqlite3_open(":memory:", &g.db);
179 db_multi_exec("CREATE TABLE sfile(pathname TEXT);");
180 db_multi_exec("CREATE TABLE vfile(pathname);");
181 vfile_scan(&base, blob_size(&base), 0, 0, 0, ExtFILE);
182 db_multi_exec("DELETE FROM sfile WHERE pathname NOT GLOB '*[^/].fossil'"
@@ -171,19 +194,50 @@
194 g.localOpen = 0;
195 return 0;
196 }else{
197 Stmt q;
198 double rNow;
199 char zType[16]; /* Column type letters for class "sortable" */
200 int nType;
201 zType[0] = 't'; /* Repo name */
202 zType[1] = 'x'; /* Space between repo-name and project-name */
203 zType[2] = 't'; /* Project name */
204 nType = 3;
205 if( bShowDesc ){
206 zType[nType++] = 'x'; /* Space between name and description */
207 zType[nType++] = 't'; /* Project description */
208 }
209 zType[nType++] = 'x'; /* space before age */
210 zType[nType++] = 'k'; /* Project age */
211 if( bShowLg ){
212 zType[nType++] = 'x'; /* space before login-group */
213 zType[nType++] = 't'; /* Login Group */
214 }
215 zType[nType] = 0;
216 blob_appendf(&html,
217 "<table border='0' class='sortable' data-init-sort='1'"
218 " data-column-types='%s' cellspacing='0' cellpadding='0'><thead>\n"
219 "<tr><th>Filename</th><th>&emsp;</th>\n"
220 "<th%s><nobr>Project Name</nobr></th>\n",
221 zType, (bShowDesc ? " width='25%'" : ""));
222 if( bShowDesc ){
223 blob_appendf(&html,
224 "<th>&emsp;</th>\n"
225 "<th width='25%%'><nobr>Project Description</nobr></th>\n"
226 );
227 }
228 blob_appendf(&html,
229 "<th>&emsp;</th>"
230 "<th><nobr>Last Modified</nobr></th>\n"
231 );
232 if( bShowLg ){
233 blob_appendf(&html,
234 "<th>&emsp;</th>"
235 "<th><nobr>Login Group</nobr></th></tr>\n"
236 );
237 }
238 blob_appendf(&html,"</thead><tbody>\n");
239 db_prepare(&q, "SELECT pathname"
240 " FROM sfile ORDER BY pathname COLLATE nocase;");
241 rNow = db_double(0, "SELECT julianday('now')");
242 while( db_step(&q)==SQLITE_ROW ){
243 const char *zName = db_column_text(&q, 0);
@@ -242,21 +296,21 @@
296 if( x.rMTime==0.0 ){
297 /* This repository has no entry in the "event" table.
298 ** Its age will still be maximum, so data-sortkey will work. */
299 zAge = mprintf("unknown");
300 }
301 blob_appendf(&html, "<tr><td valign='top'><nobr>");
302 if( !file_ends_with_repository_extension(zName,0) ){
303 /* The "fossil server DIRECTORY" and "fossil ui DIRECTORY" commands
304 ** do not work for repositories whose names do not end in ".fossil".
305 ** So do not hyperlink those cases. */
306 blob_appendf(&html,"%h",zName);
307 } else if( sqlite3_strglob("*/.*", zName)==0 ){
308 /* Do not show hyperlinks for hidden repos */
309 blob_appendf(&html, "%h (hidden)", zName);
310 } else if( allRepo && sqlite3_strglob("[a-zA-Z]:/?*", zName)!=0 ){
311 blob_appendf(&html,
312 "<a href='%R/%T/home' target='_blank'>/%h</a>\n",
313 zUrl, zName);
314 }else if( file_ends_with_repository_extension(zName,1) ){
315 /* As described in
316 ** https://fossil-scm.org/forum/info/f50f647c97c72fc1: if
@@ -273,56 +327,60 @@
327 , zDirPart
328 #if USE_SEE
329 , zDirPart
330 #endif
331 ) ){
332 blob_appendf(&html,
333 "<s>%h</s> (directory/repo name collision)\n",
334 zName);
335 }else{
336 blob_appendf(&html,
337 "<a href='%R/%T/home' target='_blank'>%h</a>\n",
338 zUrl, zName);
339 }
340 fossil_free(zDirPart);
341 }else{
342 blob_appendf(&html,
343 "<a href='%R/%T/home' target='_blank'>%h</a>\n",
344 zUrl, zName);
345 }
346 blob_appendf(&html,"</nobr></td>\n");
347 if( x.zProjName ){
348 blob_appendf(&html, "<td>&emsp;</td><td valign='top'>%h</td>\n",
349 x.zProjName);
350 fossil_free(x.zProjName);
351 }else{
352 blob_appendf(&html, "<td>&emsp;</td><td></td>\n");
353 }
354 if( !bShowDesc ){
355 /* Do nothing */
356 }else if( x.zProjDesc ){
357 blob_appendf(&html, "<td>&emsp;</td><td valign='top'>%h</td>\n",
358 x.zProjDesc);
359 fossil_free(x.zProjDesc);
360 }else{
361 blob_appendf(&html, "<td>&emsp;</td><td></td>\n");
362 }
363 blob_appendf(&html,
364 "<td>&emsp;</td><td data-sortkey='%08x' align='center' valign='top'>"
365 "<nobr>%h</nobr></td>\n",
366 (int)iAge, zAge);
367 fossil_free(zAge);
368 if( !bShowLg ){
369 blob_appendf(&html, "</tr>\n");
370 }else if( x.zLoginGroup ){
371 blob_appendf(&html, "<td>&emsp;</td><td valign='top'>"
372 "<nobr>%h</nobr></td></tr>\n",
373 x.zLoginGroup);
374 fossil_free(x.zLoginGroup);
375 }else{
376 blob_appendf(&html, "<td>&emsp;</td><td></td></tr>\n");
377 }
378 sqlite3_free(zUrl);
379 }
380 db_finalize(&q);
381 blob_appendf(&html,"</tbody></table>\n");
382 }
383 if( zSkinRepo ){
384 char *zNewBase = mprintf("%s/%s", g.zBaseURL, zSkinUrl);
385 g.zBaseURL = 0;
386 set_base_url(zNewBase);
387

Keyboard Shortcuts

Open search /
Next entry (timeline) j
Previous entry (timeline) k
Open focused entry Enter
Show this help ?
Toggle theme Top nav button