Fossil SCM
Simply the "fileage" webpage by converting to use of the "files_of_checkin" virtual table.
Commit
a0cc614326fa40e943f80126b2015256c35e9949
Parent
522cf5f66db5a6e…
1 file changed
+74
-43
+74
-43
| --- src/browse.c | ||
| +++ src/browse.c | ||
| @@ -733,45 +733,34 @@ | ||
| 733 | 733 | ** files, the pathname, the check-in where the file was added, and the |
| 734 | 734 | ** mtime on that checkin. If zGlob and *zGlob then only files matching |
| 735 | 735 | ** the given glob are computed. |
| 736 | 736 | */ |
| 737 | 737 | int compute_fileage(int vid, const char* zGlob){ |
| 738 | - Manifest *pManifest; | |
| 739 | - ManifestFile *pFile; | |
| 740 | 738 | int nFile = 0; |
| 741 | 739 | double vmtime; |
| 742 | - Stmt ins; | |
| 743 | 740 | Stmt q1, q2, q3; |
| 744 | 741 | Stmt upd; |
| 745 | 742 | if(zGlob && !*zGlob) zGlob = NULL; |
| 746 | 743 | db_multi_exec( |
| 747 | 744 | /*"DROP TABLE IF EXISTS temp.fileage;"*/ |
| 748 | - "CREATE TEMP TABLE fileage(" | |
| 749 | - " fid INTEGER," | |
| 750 | - " mid INTEGER," | |
| 751 | - " mtime DATETIME," | |
| 752 | - " pathname TEXT" | |
| 753 | - ");" | |
| 754 | - "CREATE INDEX fileage_fid ON fileage(fid);" | |
| 755 | - ); | |
| 756 | - pManifest = manifest_get(vid, CFTYPE_MANIFEST, 0); | |
| 757 | - if( pManifest==0 ) return 1; | |
| 758 | - manifest_file_rewind(pManifest); | |
| 759 | - db_prepare(&ins, | |
| 760 | - "INSERT INTO temp.fileage(fid, pathname)" | |
| 761 | - " SELECT rid, :path FROM blob WHERE uuid=:uuid" | |
| 762 | - ); | |
| 763 | - while( (pFile = manifest_file_next(pManifest, 0))!=0 ){ | |
| 764 | - if( zGlob && sqlite3_strglob(zGlob, pFile->zName)!=0 ) continue; | |
| 765 | - db_bind_text(&ins, ":uuid", pFile->zUuid); | |
| 766 | - db_bind_text(&ins, ":path", pFile->zName); | |
| 767 | - db_step(&ins); | |
| 768 | - db_reset(&ins); | |
| 769 | - nFile++; | |
| 770 | - } | |
| 771 | - db_finalize(&ins); | |
| 772 | - manifest_destroy(pManifest); | |
| 745 | + "CREATE TEMP TABLE fileage(\n" | |
| 746 | + " fid INTEGER,\n" | |
| 747 | + " mid INTEGER,\n" | |
| 748 | + " mtime DATETIME,\n" | |
| 749 | + " pathname TEXT\n" | |
| 750 | + ");\n" | |
| 751 | + "CREATE INDEX fileage_fid ON fileage(fid);\n" | |
| 752 | + "CREATE VIRTUAL TABLE temp.foci USING files_of_checkin;\n" | |
| 753 | + "INSERT INTO temp.fileage(fid,pathname)" | |
| 754 | + " SELECT blob.rid, foci.filename\n" | |
| 755 | + " FROM foci, blob\n" | |
| 756 | + " WHERE foci.checkinID=%d\n" | |
| 757 | + " AND blob.uuid=foci.uuid\n" | |
| 758 | + " AND foci.filename GLOB '%q';", | |
| 759 | + vid, zGlob ? zGlob : "*" | |
| 760 | + ); | |
| 761 | + nFile = db_int(0, "SELECT count(*) FROM fileage"); | |
| 773 | 762 | db_prepare(&q1,"SELECT fid FROM mlink WHERE mid=:mid"); |
| 774 | 763 | db_prepare(&upd, "UPDATE fileage SET mid=:mid, mtime=:vmtime" |
| 775 | 764 | " WHERE fid=:fid AND mid IS NULL"); |
| 776 | 765 | db_prepare(&q2,"SELECT pid FROM plink WHERE cid=:vid AND isprim"); |
| 777 | 766 | db_prepare(&q3,"SELECT mtime FROM event WHERE objid=:vid"); |
| @@ -802,10 +791,63 @@ | ||
| 802 | 791 | db_finalize(&upd); |
| 803 | 792 | db_finalize(&q2); |
| 804 | 793 | db_finalize(&q3); |
| 805 | 794 | return 0; |
| 806 | 795 | } |
| 796 | + | |
| 797 | +/* | |
| 798 | +** Render the number of days in rAge as a more human-readable time span. | |
| 799 | +** Different units (seconds, minutes, hours, days, months, years) are | |
| 800 | +** selected depending on the magnitude of rAge. | |
| 801 | +** | |
| 802 | +** The string returned is obtained from fossil_malloc() and should be | |
| 803 | +** freed by the caller. | |
| 804 | +*/ | |
| 805 | +char *human_readable_age(double rAge){ | |
| 806 | + if( rAge*86400.0<120 ){ | |
| 807 | + return mprintf("%d seconds", (int)(rAge*86400.0)); | |
| 808 | + }else if( rAge*1440.0<90 ){ | |
| 809 | + return mprintf("%.1f minutes", rAge*1440.0); | |
| 810 | + }else if( rAge*24.0<36 ){ | |
| 811 | + return mprintf("%.1f hours", rAge*24.0); | |
| 812 | + }else if( rAge<365.0 ){ | |
| 813 | + return mprintf("%.1f days", rAge); | |
| 814 | + }else{ | |
| 815 | + return mprintf("%.2f years", rAge/365.0); | |
| 816 | + } | |
| 817 | +} | |
| 818 | + | |
| 819 | + | |
| 820 | +/* | |
| 821 | +** COMMAND: test-fileage | |
| 822 | +** | |
| 823 | +** Usage: %fossil test-fileage CHECKIN | |
| 824 | +*/ | |
| 825 | +void test_fileage_cmd(void){ | |
| 826 | + int mid; | |
| 827 | + Stmt q; | |
| 828 | + const char *zGlob = find_option("glob",0,1); | |
| 829 | + db_find_and_open_repository(0,0); | |
| 830 | + verify_all_options(); | |
| 831 | + if( g.argc!=3 ) usage("test-fileage CHECKIN"); | |
| 832 | + mid = name_to_typed_rid(g.argv[2],"ci"); | |
| 833 | + compute_fileage(mid, zGlob); | |
| 834 | + db_prepare(&q, | |
| 835 | + "SELECT fid, mid, julianday('now') - mtime, pathname" | |
| 836 | + " FROM fileage" | |
| 837 | + ); | |
| 838 | + while( db_step(&q)==SQLITE_ROW ){ | |
| 839 | + char *zAge = human_readable_age(db_column_double(&q,2)); | |
| 840 | + fossil_print("%8d %8d %16s %s\n", | |
| 841 | + db_column_int(&q,0), | |
| 842 | + db_column_int(&q,1), | |
| 843 | + zAge, | |
| 844 | + db_column_text(&q,3)); | |
| 845 | + fossil_free(zAge); | |
| 846 | + } | |
| 847 | + db_finalize(&q); | |
| 848 | +} | |
| 807 | 849 | |
| 808 | 850 | /* |
| 809 | 851 | ** WEBPAGE: fileage |
| 810 | 852 | ** |
| 811 | 853 | ** Parameters: |
| @@ -851,35 +893,24 @@ | ||
| 851 | 893 | ); |
| 852 | 894 | while( db_step(&q)==SQLITE_ROW ){ |
| 853 | 895 | double age = baseTime - db_column_double(&q, 0); |
| 854 | 896 | int mid = db_column_int(&q, 2); |
| 855 | 897 | const char *zFUuid = db_column_text(&q, 1); |
| 856 | - char zAge[200]; | |
| 898 | + char *zAge = 0; | |
| 857 | 899 | if( lastMid!=mid ){ |
| 858 | 900 | @ <tr><td colspan=3><hr></tr> |
| 859 | 901 | lastMid = mid; |
| 860 | - if( age*86400.0<120 ){ | |
| 861 | - sqlite3_snprintf(sizeof(zAge), zAge, "%d seconds", (int)(age*86400.0)); | |
| 862 | - }else if( age*1440.0<90 ){ | |
| 863 | - sqlite3_snprintf(sizeof(zAge), zAge, "%.1f minutes", age*1440.0); | |
| 864 | - }else if( age*24.0<36 ){ | |
| 865 | - sqlite3_snprintf(sizeof(zAge), zAge, "%.1f hours", age*24.0); | |
| 866 | - }else if( age<365.0 ){ | |
| 867 | - sqlite3_snprintf(sizeof(zAge), zAge, "%.1f days", age); | |
| 868 | - }else{ | |
| 869 | - sqlite3_snprintf(sizeof(zAge), zAge, "%.2f years", age/365.0); | |
| 870 | - } | |
| 871 | - }else{ | |
| 872 | - zAge[0] = 0; | |
| 902 | + zAge = human_readable_age(age); | |
| 873 | 903 | } |
| 874 | 904 | @ <tr> |
| 875 | - @ <td>%s(zAge) | |
| 905 | + @ <td>%s(zAge?zAge:"") | |
| 876 | 906 | @ <td width="25"> |
| 877 | 907 | @ <td>%z(href("%R/artifact/%s?ln", zFUuid))%h(db_column_text(&q, 3))</a> |
| 878 | 908 | @ </tr> |
| 879 | 909 | @ |
| 910 | + fossil_free(zAge); | |
| 880 | 911 | } |
| 881 | 912 | @ <tr><td colspan=3><hr></tr> |
| 882 | 913 | @ </table> |
| 883 | 914 | db_finalize(&q); |
| 884 | 915 | style_footer(); |
| 885 | 916 | } |
| 886 | 917 |
| --- src/browse.c | |
| +++ src/browse.c | |
| @@ -733,45 +733,34 @@ | |
| 733 | ** files, the pathname, the check-in where the file was added, and the |
| 734 | ** mtime on that checkin. If zGlob and *zGlob then only files matching |
| 735 | ** the given glob are computed. |
| 736 | */ |
| 737 | int compute_fileage(int vid, const char* zGlob){ |
| 738 | Manifest *pManifest; |
| 739 | ManifestFile *pFile; |
| 740 | int nFile = 0; |
| 741 | double vmtime; |
| 742 | Stmt ins; |
| 743 | Stmt q1, q2, q3; |
| 744 | Stmt upd; |
| 745 | if(zGlob && !*zGlob) zGlob = NULL; |
| 746 | db_multi_exec( |
| 747 | /*"DROP TABLE IF EXISTS temp.fileage;"*/ |
| 748 | "CREATE TEMP TABLE fileage(" |
| 749 | " fid INTEGER," |
| 750 | " mid INTEGER," |
| 751 | " mtime DATETIME," |
| 752 | " pathname TEXT" |
| 753 | ");" |
| 754 | "CREATE INDEX fileage_fid ON fileage(fid);" |
| 755 | ); |
| 756 | pManifest = manifest_get(vid, CFTYPE_MANIFEST, 0); |
| 757 | if( pManifest==0 ) return 1; |
| 758 | manifest_file_rewind(pManifest); |
| 759 | db_prepare(&ins, |
| 760 | "INSERT INTO temp.fileage(fid, pathname)" |
| 761 | " SELECT rid, :path FROM blob WHERE uuid=:uuid" |
| 762 | ); |
| 763 | while( (pFile = manifest_file_next(pManifest, 0))!=0 ){ |
| 764 | if( zGlob && sqlite3_strglob(zGlob, pFile->zName)!=0 ) continue; |
| 765 | db_bind_text(&ins, ":uuid", pFile->zUuid); |
| 766 | db_bind_text(&ins, ":path", pFile->zName); |
| 767 | db_step(&ins); |
| 768 | db_reset(&ins); |
| 769 | nFile++; |
| 770 | } |
| 771 | db_finalize(&ins); |
| 772 | manifest_destroy(pManifest); |
| 773 | db_prepare(&q1,"SELECT fid FROM mlink WHERE mid=:mid"); |
| 774 | db_prepare(&upd, "UPDATE fileage SET mid=:mid, mtime=:vmtime" |
| 775 | " WHERE fid=:fid AND mid IS NULL"); |
| 776 | db_prepare(&q2,"SELECT pid FROM plink WHERE cid=:vid AND isprim"); |
| 777 | db_prepare(&q3,"SELECT mtime FROM event WHERE objid=:vid"); |
| @@ -802,10 +791,63 @@ | |
| 802 | db_finalize(&upd); |
| 803 | db_finalize(&q2); |
| 804 | db_finalize(&q3); |
| 805 | return 0; |
| 806 | } |
| 807 | |
| 808 | /* |
| 809 | ** WEBPAGE: fileage |
| 810 | ** |
| 811 | ** Parameters: |
| @@ -851,35 +893,24 @@ | |
| 851 | ); |
| 852 | while( db_step(&q)==SQLITE_ROW ){ |
| 853 | double age = baseTime - db_column_double(&q, 0); |
| 854 | int mid = db_column_int(&q, 2); |
| 855 | const char *zFUuid = db_column_text(&q, 1); |
| 856 | char zAge[200]; |
| 857 | if( lastMid!=mid ){ |
| 858 | @ <tr><td colspan=3><hr></tr> |
| 859 | lastMid = mid; |
| 860 | if( age*86400.0<120 ){ |
| 861 | sqlite3_snprintf(sizeof(zAge), zAge, "%d seconds", (int)(age*86400.0)); |
| 862 | }else if( age*1440.0<90 ){ |
| 863 | sqlite3_snprintf(sizeof(zAge), zAge, "%.1f minutes", age*1440.0); |
| 864 | }else if( age*24.0<36 ){ |
| 865 | sqlite3_snprintf(sizeof(zAge), zAge, "%.1f hours", age*24.0); |
| 866 | }else if( age<365.0 ){ |
| 867 | sqlite3_snprintf(sizeof(zAge), zAge, "%.1f days", age); |
| 868 | }else{ |
| 869 | sqlite3_snprintf(sizeof(zAge), zAge, "%.2f years", age/365.0); |
| 870 | } |
| 871 | }else{ |
| 872 | zAge[0] = 0; |
| 873 | } |
| 874 | @ <tr> |
| 875 | @ <td>%s(zAge) |
| 876 | @ <td width="25"> |
| 877 | @ <td>%z(href("%R/artifact/%s?ln", zFUuid))%h(db_column_text(&q, 3))</a> |
| 878 | @ </tr> |
| 879 | @ |
| 880 | } |
| 881 | @ <tr><td colspan=3><hr></tr> |
| 882 | @ </table> |
| 883 | db_finalize(&q); |
| 884 | style_footer(); |
| 885 | } |
| 886 |
| --- src/browse.c | |
| +++ src/browse.c | |
| @@ -733,45 +733,34 @@ | |
| 733 | ** files, the pathname, the check-in where the file was added, and the |
| 734 | ** mtime on that checkin. If zGlob and *zGlob then only files matching |
| 735 | ** the given glob are computed. |
| 736 | */ |
| 737 | int compute_fileage(int vid, const char* zGlob){ |
| 738 | int nFile = 0; |
| 739 | double vmtime; |
| 740 | Stmt q1, q2, q3; |
| 741 | Stmt upd; |
| 742 | if(zGlob && !*zGlob) zGlob = NULL; |
| 743 | db_multi_exec( |
| 744 | /*"DROP TABLE IF EXISTS temp.fileage;"*/ |
| 745 | "CREATE TEMP TABLE fileage(\n" |
| 746 | " fid INTEGER,\n" |
| 747 | " mid INTEGER,\n" |
| 748 | " mtime DATETIME,\n" |
| 749 | " pathname TEXT\n" |
| 750 | ");\n" |
| 751 | "CREATE INDEX fileage_fid ON fileage(fid);\n" |
| 752 | "CREATE VIRTUAL TABLE temp.foci USING files_of_checkin;\n" |
| 753 | "INSERT INTO temp.fileage(fid,pathname)" |
| 754 | " SELECT blob.rid, foci.filename\n" |
| 755 | " FROM foci, blob\n" |
| 756 | " WHERE foci.checkinID=%d\n" |
| 757 | " AND blob.uuid=foci.uuid\n" |
| 758 | " AND foci.filename GLOB '%q';", |
| 759 | vid, zGlob ? zGlob : "*" |
| 760 | ); |
| 761 | nFile = db_int(0, "SELECT count(*) FROM fileage"); |
| 762 | db_prepare(&q1,"SELECT fid FROM mlink WHERE mid=:mid"); |
| 763 | db_prepare(&upd, "UPDATE fileage SET mid=:mid, mtime=:vmtime" |
| 764 | " WHERE fid=:fid AND mid IS NULL"); |
| 765 | db_prepare(&q2,"SELECT pid FROM plink WHERE cid=:vid AND isprim"); |
| 766 | db_prepare(&q3,"SELECT mtime FROM event WHERE objid=:vid"); |
| @@ -802,10 +791,63 @@ | |
| 791 | db_finalize(&upd); |
| 792 | db_finalize(&q2); |
| 793 | db_finalize(&q3); |
| 794 | return 0; |
| 795 | } |
| 796 | |
| 797 | /* |
| 798 | ** Render the number of days in rAge as a more human-readable time span. |
| 799 | ** Different units (seconds, minutes, hours, days, months, years) are |
| 800 | ** selected depending on the magnitude of rAge. |
| 801 | ** |
| 802 | ** The string returned is obtained from fossil_malloc() and should be |
| 803 | ** freed by the caller. |
| 804 | */ |
| 805 | char *human_readable_age(double rAge){ |
| 806 | if( rAge*86400.0<120 ){ |
| 807 | return mprintf("%d seconds", (int)(rAge*86400.0)); |
| 808 | }else if( rAge*1440.0<90 ){ |
| 809 | return mprintf("%.1f minutes", rAge*1440.0); |
| 810 | }else if( rAge*24.0<36 ){ |
| 811 | return mprintf("%.1f hours", rAge*24.0); |
| 812 | }else if( rAge<365.0 ){ |
| 813 | return mprintf("%.1f days", rAge); |
| 814 | }else{ |
| 815 | return mprintf("%.2f years", rAge/365.0); |
| 816 | } |
| 817 | } |
| 818 | |
| 819 | |
| 820 | /* |
| 821 | ** COMMAND: test-fileage |
| 822 | ** |
| 823 | ** Usage: %fossil test-fileage CHECKIN |
| 824 | */ |
| 825 | void test_fileage_cmd(void){ |
| 826 | int mid; |
| 827 | Stmt q; |
| 828 | const char *zGlob = find_option("glob",0,1); |
| 829 | db_find_and_open_repository(0,0); |
| 830 | verify_all_options(); |
| 831 | if( g.argc!=3 ) usage("test-fileage CHECKIN"); |
| 832 | mid = name_to_typed_rid(g.argv[2],"ci"); |
| 833 | compute_fileage(mid, zGlob); |
| 834 | db_prepare(&q, |
| 835 | "SELECT fid, mid, julianday('now') - mtime, pathname" |
| 836 | " FROM fileage" |
| 837 | ); |
| 838 | while( db_step(&q)==SQLITE_ROW ){ |
| 839 | char *zAge = human_readable_age(db_column_double(&q,2)); |
| 840 | fossil_print("%8d %8d %16s %s\n", |
| 841 | db_column_int(&q,0), |
| 842 | db_column_int(&q,1), |
| 843 | zAge, |
| 844 | db_column_text(&q,3)); |
| 845 | fossil_free(zAge); |
| 846 | } |
| 847 | db_finalize(&q); |
| 848 | } |
| 849 | |
| 850 | /* |
| 851 | ** WEBPAGE: fileage |
| 852 | ** |
| 853 | ** Parameters: |
| @@ -851,35 +893,24 @@ | |
| 893 | ); |
| 894 | while( db_step(&q)==SQLITE_ROW ){ |
| 895 | double age = baseTime - db_column_double(&q, 0); |
| 896 | int mid = db_column_int(&q, 2); |
| 897 | const char *zFUuid = db_column_text(&q, 1); |
| 898 | char *zAge = 0; |
| 899 | if( lastMid!=mid ){ |
| 900 | @ <tr><td colspan=3><hr></tr> |
| 901 | lastMid = mid; |
| 902 | zAge = human_readable_age(age); |
| 903 | } |
| 904 | @ <tr> |
| 905 | @ <td>%s(zAge?zAge:"") |
| 906 | @ <td width="25"> |
| 907 | @ <td>%z(href("%R/artifact/%s?ln", zFUuid))%h(db_column_text(&q, 3))</a> |
| 908 | @ </tr> |
| 909 | @ |
| 910 | fossil_free(zAge); |
| 911 | } |
| 912 | @ <tr><td colspan=3><hr></tr> |
| 913 | @ </table> |
| 914 | db_finalize(&q); |
| 915 | style_footer(); |
| 916 | } |
| 917 |