<?php
/*******************************************************************************
 *
 * LEIDEN OPEN VARIATION DATABASE (LOVD)
 *
 * Created     : 2009-03-17
 * Modified    : 2010-03-12
 * Version     : 1.5
 * For LOVD    : 2.0-25
 *
 * Access      : Curators and up.
 * Purpose     : GenBank uploader: upload a GenBank file into the genbank
 *               directory.
 *
 * Copyright   : 2004-2010 Leiden University Medical Center; http://www.LUMC.nl/
 * Programmers : Ir. Gerard C.P. Schaafsma <G.C.P.Schaafsma@LUMC.nl>
 *               Ing. Ivo F.A.C. Fokkema <I.F.A.C.Fokkema@LUMC.nl>
 * Last edited : Ing. Ivo F.A.C. Fokkema <I.F.A.C.Fokkema@LUMC.nl>
 *
 *
 * This file is part of LOVD.
 *
 * LOVD is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * LOVD is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with LOVD; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 *************/

define('ROOT_PATH', '../');
require ROOT_PATH . 'inc-init.php';
require ROOT_PATH . 'inc-lib-form.php';

// Require curator clearance.
lovd_requireAUTH(LEVEL_CURATOR);

// Check presence or writability of the genbank directory
if (!is_dir(ROOT_PATH . 'genbank') || !is_writable(ROOT_PATH . 'genbank')) {
    require ROOT_PATH . 'inc-top-clean.php';
    print('<SPAN class="S18"><B>LOVD GenBank File Uploader</B></SPAN><BR><BR>' . "\n\n" .
          'The \'genbank\' directory does not exist or is not writable. Please make sure it exists and that it is world writable, otherwise you can\'t use the GenBank File Uploader. For more information or troubleshooting, please refer to the <A href="' . ROOT_PATH . 'docs/lovd_scripts/genbank_file_uploader.php" target="_blank">LOVD manual</A>.<BR><BR>' . "\n\n");
    require ROOT_PATH . 'inc-bot-clean.php';
    exit;
}

$nMaxSize = 10485760; // 10 MB.
$nMaxPHP = ini_get('upload_max_filesize');
$nMaxPHP = substr($nMaxPHP, 0, -1) * pow(1024, 2);
if ($nMaxPHP < $nMaxSize) {
    $nMaxSize = $nMaxPHP;
}

if (isset($_GET['sent'])) {
    lovd_errorClean();

    if (!empty($_POST['refseq_mrna']) && lovd_isCurator($_POST['symbol'])) {
        require ROOT_PATH . 'inc-top-clean.php';
        // 2010-01-11; 2.0-24; Just run the query, report what happened afterwards.
        mysql_query('UPDATE ' . TABLE_DBS . ' SET refseq_mrna = "' . $_POST['refseq_mrna'] . '" WHERE symbol = "' . $_POST['symbol'] . '"');
        if (mysql_affected_rows()) {
            print('The transcript_id: ' . stripslashes($_POST['refseq_mrna']) . ' was linked to your gene.<BR>' . "\n\n");
        } else {
            print('The transcript_id ' . stripslashes($_POST['refseq_mrna']) . ' was already linked to your gene.<BR>' . "\n\n");
        }

        print('<A href="' . $_SERVER['PHP_SELF'] . '">Want to upload more?</A><BR>' . "\n\n");
        // 2009-07-10; 2.0-20; by Gerard added choice to go to the Reference Sequence Parser
        print('      <SCRIPT type="text/javascript">' . "\n" .
              '        <!--' . "\n" .
              '        if (window.name == \'LOVD_' . preg_replace('/[^a-z0-9_]/i', '_', $_STAT['signature']) . '_ScriptsUploadGenBank\') {' . "\n" .
              '            document.writeln(\'<A href="#" onclick="lovd_openWindow(\\\'' . ROOT_PATH . 'scripts/parseRefSeq.php' . lovd_showSID() . '\\\', \\\'ScriptsParseRefSeq\\\', 800, 500); return false;">Go to the Reference Sequence Parser</A><BR>\');' . "\n" .
              '        } else {' . "\n" .
              '            document.writeln(\'<A href="' . ROOT_PATH . 'scripts/parseRefSeq.php?step=1">Go back to the Reference Sequence Parser</A><BR>\');' . "\n" .
              '        }' . "\n" .
              '        // -->' . "\n" .
              '      </SCRIPT>' . "\n\n");
        require ROOT_PATH . 'inc-bot-clean.php';
        exit;
    }
    // 2009-09-21; 2.0-22; Have to select gene.
    if (empty($_POST['symbol'])) {
        lovd_errorAdd('Please select the gene database for which you are uploading the GenBank file.');
    }

    // No file...
    if ($_FILES['upload_file']['error'] > 0 && $_FILES['upload_file']['error'] < 4) {
        lovd_errorAdd('There was a problem with the file transfer. Please try again. The file cannot be larger than ' . round($nMaxSize/pow(1024, 2), 1) . ' MB.');

    } else if ($_FILES['upload_file']['error'] == 4 || !$_FILES['upload_file']['size']) {
        lovd_errorAdd('Please select a file to upload.');

    } else if ($_FILES['upload_file']['size'] > $nMaxSize) {
        lovd_errorAdd('The file cannot be larger than ' . round($nMaxSize/pow(1024, 2), 1) . ' MB.');

    } elseif ($_FILES['upload_file']['error']) {
        // Various errors available from 4.3.0 or later.
        lovd_errorAdd('There was an unknown problem with receiving the file properly, possibly because of the current server settings. If the problem persists, contact the database administrator.');
    }

    if (!lovd_error()) {
        // 2009-12-10; 2.0-24; check for an 'old' GenBank file
        list($sGenBankUri) = mysql_fetch_row(mysql_query('SELECT genbank_uri FROM ' . TABLE_DBS . ' WHERE symbol = "' . $_POST['symbol'] . '" AND genbank = 1'));

        $fInput = @fopen($_FILES['upload_file']['tmp_name'], 'r');
        if (!$fInput) {
            lovd_errorAdd('Cannot open file after it was received by the server.');
        }
        // Read the first line of the file to check if it is a downloaded GenBank sequence file.
        $sLine = @fgets($fInput, 4096);
        $sLine = rtrim($sLine, "\r\n");

        // Check if in the first line LOCUS is present at the first position
        if (strpos($sLine, 'LOCUS') !== 0) {
            lovd_errorAdd('This is not a proper GenBank file.');
        }

        // Verify that this gene exists.
        if (!in_array($_POST['symbol'], lovd_getGeneList())) {
            lovd_errorAdd('This gene does not exists in this LOVD installation!');
        } elseif (!lovd_isCurator($_POST['symbol'])) {
            lovd_errorAdd('You are not allowed access to this gene!');
        }
    }

    if (!lovd_error()) {
        // Generate LOVD gene symbol.
        $sSymbol = substr($_POST['symbol'], 0, strpos($_POST['symbol'] . '_', '_'));

        // Determine the new name of the GenBank file
        // 2009-08-25; 2.0-21; old files will always be overwritten
        if ($_POST['exists'] == 'rename') {
            $sFileName = $sSymbol . '.gb';
        } else {
            $sFileName = (substr($_FILES['upload_file']['name'], -3) == '.gb' ? $_FILES['upload_file']['name'] : $_FILES['upload_file']['name'] . '.gb');

            // 2009-08-19; 2.0-21; Reload Mutalyzer module in case of overwrite.
            if ($_MODULES->isLoaded('mutalyzer')) {
                // Check if the file is present in the TABLE_DBS table
                if ($sGenBankUri && $sGenBankUri == $sFileName) {
                    // Force reload of specifically this gene's genbank file by emptying the field. Otherwise the module may not resend the file.
                    $aSett = $_MODULES->getSettings('mutalyzer');
                    $aSett['accessionid'][$_POST['symbol']] = '';
                    $_MODULES->setSettings('mutalyzer', $aSett);
                    // Then, reload the module.
                    $_MODULES->disable('mutalyzer');
                    $_MODULES->enable('mutalyzer');
                }
            }
        }
        $sPath = ROOT_PATH . 'genbank/';

        // Move the GenBank file to the new location.
        $bMove = move_uploaded_file($_FILES['upload_file']['tmp_name'], $sPath . $sFileName);

        // 2010-01-11; 2.0-24; Now fetch the transcript_id from the uploaded file.
        // Generate LOVD gene symbol.
        $sSymbol = substr($_POST['symbol'], 0, strpos($_POST['symbol'] . '_', '_'));
        $aTranscriptIDs = array();
        $bGene = false;
        // Read rest of the file.
        while (!feof($fInput) && $sLine = rtrim(fgets($fInput, 4096), "\r\n")) {
            $nLine ++;
            if (!trim($sLine)) {
                // Empty line.
                continue;
            }
            $sLine = preg_replace('/[\s"]+/', '', $sLine);
            if ('/gene=' . $sSymbol == $sLine) {
                // we are in the right gene
                $bGene = true;
            } elseif ('/gene=' == substr($sLine, 0, 6) && substr($sLine, 6) != $sSymbol) {
                // we are in the wrong gene
                $bGene = false;
            }
            if ('/transcript_id=' == substr($sLine, 0, 15) && $bGene) {
                // take the transcript_id (mRNA accession number) from the file
                $aTranscriptIDs[] = substr($sLine, 15);
                $bGene = false;
            }
        }

        require ROOT_PATH . 'inc-top-clean.php';
        if ($bMove) {
            lovd_writeLog('MySQL:Event', 'GenBankUpload', $_AUTH['username'] . ' (' . mysql_real_escape_string($_AUTH['name']) . ') successfully uploaded new GenBank file: ' . mysql_real_escape_string($sFileName) . ' (' . $_POST['symbol'] . ')');
            print('Successfully uploaded new GenBank file: ' . $sFileName . '<BR>');
            // 2009-12-11; 2.0-24; remove the old file and update the link
            if ($_POST['old_file'] == 'remove') {
                @mysql_query('UPDATE ' . TABLE_DBS . ' SET genbank_uri = "' . mysql_real_escape_string($sFileName) . '" WHERE symbol = "' . $_POST['symbol']);
                if ($sGenBankUri && $sGenBankUri != $sFileName) {
                    $bUnlink = unlink($sPath . $sGenBankUri);
                    if (!$bUnlink) {
                        print('Removal of the old file was not successful!<BR>' . "\n\n");
                    }
                }
            } else {
                // Now, if this gene never had a GenBank file enabled, we will do so now.
                @mysql_query('UPDATE ' . TABLE_DBS . ' SET genbank = 1, genbank_uri = "' . mysql_real_escape_string($sFileName) . '" WHERE symbol = "' . $_POST['symbol'] . '" AND genbank = 0 AND genbank_uri = ""');
            }
            if ($aTranscriptIDs && count($aTranscriptIDs) == 1) {
                // 2010-01-11; 2.0-24; Always update, report only when there was something changed in the database
                mysql_query('UPDATE ' . TABLE_DBS . ' SET refseq_mrna = "' . mysql_real_escape_string($aTranscriptIDs[0]) . '" WHERE symbol = "' . $_POST['symbol'] . '"');
                if (mysql_affected_rows()) {
                    print('The transcript_id: ' . htmlspecialchars($aTranscriptIDs[0]) . ' was linked to your gene.<BR>' . "\n\n");
                }
            }

        } else {
            lovd_writeLog('MySQL:Error', 'GenBankUpload', $_AUTH['username'] . ' (' . mysql_real_escape_string($_AUTH['name']) . ') failed uploading new GenBank file: ' . mysql_real_escape_string($sFileName) . ' (' . $_POST['symbol'] . ')');
            print('Failed to upload new GenBank file.<BR>' . "\n\n");
        }
        
        if ($aTranscriptIDs && count($aTranscriptIDs) > 1) {
            // 2009-12-16; 2.0-24; more than one transcript ID, user has to choose
            print('      There are more than one transcript ID\'s in this GenBank file, please select the one you are using to number the variants in the database:<BR>' . "\n" .
                  '      <FORM action="' . $_SERVER['PHP_SELF'] . '?sent" method="post">' . "\n" .
                  '        <INPUT type="hidden" name="symbol" value="' . $_POST['symbol'] . '">' . "\n" .
                  '        <SELECT name="refseq_mrna">' . "\n");
            foreach ($aTranscriptIDs as $sRefseq_mRNA) {
                print('          <OPTION value="' . $sRefseq_mRNA . '">' . $sRefseq_mRNA . '</OPTION>' . "\n");
            }
            print('        </SELECT><BR>' . "\n" .
                  '        <INPUT type="submit" value="Submit">' . "\n" .
                  '      </FORM>' . "\n\n");
        } else {
            print('<A href="' . $_SERVER['PHP_SELF'] . '">Want to upload more?</A><BR>' . "\n\n");
            // 2009-07-10; 2.0-20; by Gerard added choice to go to the Reference Sequence Parser
            print('      <SCRIPT type="text/javascript">' . "\n" .
                  '        <!--' . "\n" .
                  '        if (window.name == \'LOVD_' . preg_replace('/[^a-z0-9_]/i', '_', $_STAT['signature']) . '_ScriptsUploadGenBank\') {' . "\n" .
                  '            document.writeln(\'<A href="#" onclick="lovd_openWindow(\\\'' . ROOT_PATH . 'scripts/parseRefSeq.php' . lovd_showSID() . '\\\', \\\'ScriptsParseRefSeq\\\', 800, 500); return false;">Go to the Reference Sequence Parser</A><BR>\');' . "\n" .
                  '        } else {' . "\n" .
                  '            document.writeln(\'<A href="' . ROOT_PATH . 'scripts/parseRefSeq.php?step=1">Go back to the Reference Sequence Parser</A><BR>\');' . "\n" .
                  '        }' . "\n" .
                  '        // -->' . "\n" .
                  '      </SCRIPT>' . "\n\n");
        }
        require ROOT_PATH . 'inc-bot-clean.php';
        exit;
    }

} else {
    // Default values.
    $_POST['symbol'] = $_SESSION['currdb'];
    $_POST['old_file'] = 'remove';
}



require ROOT_PATH . 'inc-top-clean.php';
print('<SPAN class="S18"><B>LOVD GenBank File Uploader</B></SPAN><BR><BR>' . "\n\n");
lovd_showInfoTable('Please note that uploading a new GenBank file will overwrite your current GenBank file, if the file names are the same.', 'warning');

print('      Please select the GenBank file that you wish to import.<BR>' . "\n" .
      '      <BR>' . "\n\n");

lovd_errorPrint();

print('      <FORM action="' . $_SERVER['PHP_SELF'] . '?sent" method="post" enctype="multipart/form-data">' . "\n" .
      '        <INPUT type="hidden" name="MAX_FILE_SIZE" value="' . $nMaxSize . '">' . "\n" .
      '        <TABLE border="0" cellpadding="1" cellspacing="0" width="760">' . "\n");

// Find genes we're applying this to.
$sQ = 'SELECT g.symbol, CONCAT(g.symbol, " (", g.gene, ")") AS gene FROM ';
if ($_AUTH['level'] == LEVEL_CURATOR) {
    $sQ .= TABLE_CURATES . ' AS c LEFT JOIN ' . TABLE_DBS . ' AS g USING (symbol) WHERE userid = "' . $_AUTH['userid'] . '" ORDER BY c.symbol';
} else {
    $sQ .= TABLE_DBS . ' AS g ORDER BY symbol';
}
$qGenes = mysql_query($sQ);

// 2009-08-26; 2.0-21; In order to provide a decent suggested name for the GenBank file, we need some Javascript.
$sGeneList = '<SELECT name="symbol" onchange="javascript: document.forms[0].exists.options[1].text=\'Yes, rename it to \' + document.forms[0].symbol.value + \'.gb\';">' . "\n" .
             '                <OPTION value="">-- select --</OPTION>';
while ($r = mysql_fetch_row($qGenes)) {
    // 2010-03-12; 2.0-25; This will shorten the gene names nicely, to prevent long gene names from messing up the form.
    $r[1] = lovd_shortenString($r[1], 50);
    if (substr($r[1], -3) == '...') {
        $r[1] .= str_repeat(')', substr_count($r[1], '('));
    }
    $sGeneList .= "\n" .
                  '                <OPTION value="' . $r[0] . '">' . $r[1] . '</OPTION>';
}
$sGeneList .= '</SELECT>';

$aForm = array();
$aForm[] = array('POST', '', '', '50%', '50%');
$aForm[] = array('Select the gene for which you are uploading', 'print', $sGeneList);
$aForm[] = array('Select the GenBank file', 'file', 'upload_file', 30);
// 2009-08-25; 2.0-21; options for the file name were changed, old files will always be overwritten.
$aForm[] = array('Should LOVD rename your file?', 'select', 'exists', 1, array('overwrite' => 'No (but LOVD will always add a .gb extension)', 'rename' => 'Yes, rename it to ' . $_SESSION['currdb'] . '.gb'), false, false, false);
// 2009-12-11; 2.0-24; optional removal of old GenBank file
$aForm[] = array('Do you want to delete the old file GenBank file, if present?<BR><SPAN class="form_note">If a GenBank file is already linked to this gene, selecting this option will remove this file and the newly uploaded file will take its place.</SPAN>', 'select', 'old_file', 1, array('leave' => 'No, keep the old file', 'remove' => 'Yes, delete the old file'), false, false, false);
$aForm[] = array('', 'submit', 'Upload');
lovd_viewForm($aForm);

print('</TABLE><BR>' . "\n\n" .
      '  </FORM><BR>' . "\n\n");

require ROOT_PATH . 'inc-bot-clean.php';
?>