File Origin Tracker (for SPM)

If you’re annoyed by having to memorize the meaning and origin of all those thousands of files that you generate every day with SPM, I’ve got something for you. A file origin tracker that will record the checksums of all the Nifti files created by SPM, along with their origins (be it manual creation, in this case 100 last lines of the command history will be recorded or via SPM’s Batch Editor – in this case the whole batch will be recorded). Later you can retrieve all the filenames and origins that generated that particular content, determined by the SHA-1 checksum of the file using a clean web interface.

Database schema:

CREATE TABLE file_origin_tracker_files
  checksum character(40) NOT NULL,
  filename character varying,
  origin_checksum character(40),
  CONSTRAINT file_origin_tracker_files_checksum_filename_origin_checksum_key UNIQUE (checksum, filename, origin_checksum)
CREATE TABLE file_origin_tracker_origins
  checksum character(40),
  content character varying,
  CONSTRAINT file_origin_tracker_origins_checksum_content_key UNIQUE (checksum, content)

This needs to be appended to spm_write_plane.m:

if strcmp(n(1), ':') || n(1) == V.dim(3)
    checksum = DataHash(V.fname, struct('Method','SHA-1','Format','hex','Input','file'));

    origin = '';

    if ~all(cellfun(@(x) isempty(x), strfind({}, 'cfg_util')))
        [tag, matlabbatch] = cfg_util('harvest', 1);
        code = gencode(matlabbatch, tag);
        for i=1:numel(code)
            origin = [origin sprintf('%sn', code{i})]; %#ok<AGROW>
        history = com.mathworks.mlservices.MLCommandHistoryServices.getSessionHistory;
        historyText = cellstr(char(history));
        historyText = historyText(max(1,end-100):end);
        for i=1:numel(historyText)
            origin = [origin sprintf('%sn', historyText{i})]; %#ok<AGROW>

    curDir = pwd();
    [path, name, ext] = fileparts(V.fname);
    if ~isempty(path)
    abspath=fullfile(pwd(), [name ext]);

    urlread(['http://localhost:8123/file_origin_tracker/submit_origin?filename=' urlencode(abspath) '&checksum=' checksum '&origin=' urlencode(origin)]);

Of course http://localhost:8123 has to be replaced by whatever address you set this service up at.

List of settings:

In file ~/.auto_db_access/srvProps:
port – the port the server is going to listen on, default: 8123

In file ~/.auto_db_access/dbProps:
dbUri – database URI, default: jdbc:postgresql://localhost:5432/hbp
user – database username, default: hbp
password – database password, default: hbp

After everything is up and going and you have generated some files, you can go to http://localhost:8123/file_origin_tracker.html and either drag on those files into the drop zone (marked with dashed border) or select it using classical file selection dialog. A query will be made to the database, fetching all the filenames under which this content has appeared before along with its origin (either history or batch).

And here goes the juicy part, the whole package including modified spm_write_plane.m, DataHash.m and Jetty-based server:


Enjoy. I do.

Leave a Reply

Your email address will not be published. Required fields are marked *