| | @@ -60,11 +60,11 @@ |
| 60 | 60 | " linktagid(t.tagid) AS 'Tag ID'," |
| 61 | 61 | " linktagname(t.tagname) AS 'Name'," |
| 62 | 62 | " DATETIME(tx.mtime) AS 'Timestamp'," |
| 63 | 63 | " linkuuid(b.uuid) AS 'Version'" |
| 64 | 64 | " FROM tag t, tagxref tx, blob b " |
| 65 | | - " WHERE t.tagid=tx.tagid AND tx.srcid=b.rid" |
| 65 | + " WHERE t.tagid=tx.tagid AND tx.rid=b.rid" |
| 66 | 66 | " AND tx.tagtype!=0 %s " |
| 67 | 67 | TAGVIEW_DEFAULT_FILTER |
| 68 | 68 | " ORDER BY tx.mtime DESC %s", |
| 69 | 69 | zLikeClause, zLimit |
| 70 | 70 | ); |
| | @@ -78,11 +78,11 @@ |
| 78 | 78 | ** A small search form which forwards to ?like=SEARCH_STRING |
| 79 | 79 | */ |
| 80 | 80 | static void tagview_page_search_miniform(void){ |
| 81 | 81 | char const * like = P("like"); |
| 82 | 82 | @ <div style='font-size:smaller'> |
| 83 | | - @ <form action='/tagview' method='post'> |
| 83 | + @ <form action='tagview' method='post'> |
| 84 | 84 | @ Search for tags: |
| 85 | 85 | @ <input type='text' name='like' value='%h((like?like:""))' size='10'/> |
| 86 | 86 | @ <input type='submit'/> |
| 87 | 87 | @ </form> |
| 88 | 88 | @ </div> |
| | @@ -105,11 +105,11 @@ |
| 105 | 105 | "SELECT DISTINCT" |
| 106 | 106 | " linktagname(t.tagname) AS 'Tag Name'," |
| 107 | 107 | " DATETIME(tx.mtime) AS 'Timestamp'," |
| 108 | 108 | " linkuuid(b.uuid) AS 'Version'" |
| 109 | 109 | " FROM tag t, tagxref tx, blob b" |
| 110 | | - " WHERE t.tagid=%d AND t.tagid=tx.tagid AND tx.srcid=b.rid " |
| 110 | + " WHERE t.tagid=%d AND t.tagid=tx.tagid AND tx.rid=b.rid " |
| 111 | 111 | TAGVIEW_DEFAULT_FILTER |
| 112 | 112 | " ORDER BY tx.mtime DESC", |
| 113 | 113 | tagid |
| 114 | 114 | ); |
| 115 | 115 | db_generic_query_view(zSql, 1); |
| | @@ -126,23 +126,22 @@ |
| 126 | 126 | "SELECT DISTINCT" |
| 127 | 127 | " linktagid(t.tagid) AS 'Tag ID'," |
| 128 | 128 | " DATETIME(tx.mtime) AS 'Timestamp'," |
| 129 | 129 | " linkuuid(b.uuid) AS 'Version'" |
| 130 | 130 | " FROM tag t, tagxref tx, blob b " |
| 131 | | - " WHERE t.tagname='%q' AND t.tagid=tx.tagid AND tx.srcid=b.rid " |
| 131 | + " WHERE t.tagname='%q' AND t.tagid=tx.tagid AND tx.rid=b.rid " |
| 132 | 132 | TAGVIEW_DEFAULT_FILTER |
| 133 | 133 | " ORDER BY tx.mtime DESC", |
| 134 | 134 | tagname); |
| 135 | 135 | db_generic_query_view(zSql, 1); |
| 136 | 136 | free(zSql); |
| 137 | 137 | } |
| 138 | 138 | |
| 139 | | - |
| 140 | 139 | /* |
| 141 | | -** WEBPAGE: /tagview |
| 140 | +** WEBP AGE: /tagview |
| 142 | 141 | */ |
| 143 | | -void tagview_page(void){ |
| 142 | +void old_tagview_page(void){ |
| 144 | 143 | char const * check = 0; |
| 145 | 144 | login_check_credentials(); |
| 146 | 145 | if( !g.okRdWiki ){ |
| 147 | 146 | login_needed(); |
| 148 | 147 | } |
| | @@ -161,5 +160,108 @@ |
| 161 | 160 | } |
| 162 | 161 | style_footer(); |
| 163 | 162 | } |
| 164 | 163 | |
| 165 | 164 | #undef TAGVIEW_DEFAULT_FILTER |
| 165 | + |
| 166 | +/* |
| 167 | +** Generate a timeline for the chosen tag |
| 168 | +*/ |
| 169 | +void tagview_print_timeline(char const *pName, char const *pPrefix){ |
| 170 | + char *zSql; |
| 171 | + Stmt q; |
| 172 | + zSql = mprintf("%s AND EXISTS (SELECT 1" |
| 173 | + " FROM tagxref" |
| 174 | + " WHERE tagxref.rid = event.objid" |
| 175 | + " AND tagxref.tagid = (SELECT tagid FROM tag" |
| 176 | + " WHERE tagname = %Q||%Q))" |
| 177 | + " ORDER BY 3 desc", |
| 178 | + timeline_query_for_www(), pPrefix, pName); |
| 179 | + db_prepare(&q, zSql); |
| 180 | + free(zSql); |
| 181 | + www_print_timeline(&q); |
| 182 | + db_finalize(&q); |
| 183 | +} |
| 184 | + |
| 185 | +/* |
| 186 | +** WEBPAGE: /tagview |
| 187 | +*/ |
| 188 | +void tagview_page(void){ |
| 189 | + char const *zName = 0; |
| 190 | + int zTcount = 0; |
| 191 | + login_check_credentials(); |
| 192 | + if( !g.okRead ){ |
| 193 | + login_needed(); |
| 194 | + } |
| 195 | + login_anonymous_available(); |
| 196 | + if( 0 != (zName = P("name")) ){ |
| 197 | + Blob uuid; |
| 198 | + style_header("Tagged Baselines"); |
| 199 | + @ <h2>%s(zName):</h2> |
| 200 | + if( sym_tag_to_uuid(zName, &uuid) > 0){ |
| 201 | + tagview_print_timeline(zName, "sym-"); |
| 202 | + }else if( tag_to_uuid(zName, &uuid, "") > 0){ |
| 203 | + tagview_print_timeline(zName, ""); |
| 204 | + }else{ |
| 205 | + @ There is no artifact with this tag. |
| 206 | + } |
| 207 | + }else{ |
| 208 | + Stmt q; |
| 209 | + const char *prefix = "sym-"; |
| 210 | + int preflen = strlen(prefix); |
| 211 | + style_header("Tags"); |
| 212 | + db_prepare(&q, |
| 213 | + "SELECT tagname" |
| 214 | + " FROM tag" |
| 215 | + " WHERE EXISTS(SELECT 1 FROM tagxref" |
| 216 | + " WHERE tagid=tag.tagid" |
| 217 | + " AND tagtype>0)" |
| 218 | + " AND tagid > %d" |
| 219 | + " AND tagname NOT GLOB 'wiki-*'" |
| 220 | + " AND tagname NOT GLOB 'tkt-*'" |
| 221 | + " ORDER BY tagname", |
| 222 | + MAX_INT_TAG |
| 223 | + ); |
| 224 | + @ <ul> |
| 225 | + while( db_step(&q)==SQLITE_ROW ){ |
| 226 | + zTcount++; |
| 227 | + const char *name = db_column_text(&q, 0); |
| 228 | + if( g.okHistory ){ |
| 229 | + if( strncmp(name, prefix, preflen)==0 ){ |
| 230 | + @ <li><a href=%s(g.zBaseURL)/tagview?name=%s(name+preflen)> |
| 231 | + @ %s(name+preflen)</a> |
| 232 | + }else{ |
| 233 | + @ <li><a href=%s(g.zBaseURL)/tagview?name=%s(name)> |
| 234 | + @ %s(name)</a> |
| 235 | + } |
| 236 | + }else{ |
| 237 | + if( strncmp(name, prefix, preflen)==0 ){ |
| 238 | + @ <li><strong>%s(name+preflen)</strong> |
| 239 | + }else{ |
| 240 | + @ <li><strong>%s(name)</strong> |
| 241 | + } |
| 242 | + } |
| 243 | + if( strncmp(name, prefix, preflen)==0 ){ |
| 244 | + @ (symbolic label) |
| 245 | + } |
| 246 | + @ </li> |
| 247 | + } |
| 248 | + @ </ul> |
| 249 | + if( zTcount == 0) { |
| 250 | + @ There are no relevant tags. |
| 251 | + } |
| 252 | + db_finalize(&q); |
| 253 | + } |
| 254 | + /* |
| 255 | + * Put in dummy functions since www_print_timeline has generated calls to |
| 256 | + * them. Some browsers don't seem to care, but better to be safe. |
| 257 | + * Actually, it would be nice to use the functions on this page, but at |
| 258 | + * the moment it looks to be too difficult. |
| 259 | + */ |
| 260 | + @ <script> |
| 261 | + @ function xin(id){ |
| 262 | + @ } |
| 263 | + @ function xout(id){ |
| 264 | + @ } |
| 265 | + @ </script> |
| 266 | + style_footer(); |
| 267 | +} |
| 166 | 268 | |