From f7708feda1e91f5da6e8ca2797d7594ed2f3350f Mon Sep 17 00:00:00 2001 From: Laurent Ghigonis Date: Mon, 17 Jun 2013 20:08:58 +0200 Subject: jsaccess: WIP on a real file store --- jsaccess/README.txt | 33 +-- jsaccess/doc/put_your_encrypted_files_here.txt | 6 +- .../caf3eefc85fc7c4ee06d38ea679318114b21d88d | 12 -- .../index.html | 0 .../index.txt | 2 - jsaccess/jsa/files/index.html | 1 - jsaccess/jsa/jsa.js | 4 +- .../caf3eefc85fc7c4ee06d38ea679318114b21d88d | 12 ++ .../index.html | 0 .../index.txt | 2 + jsaccess/jsa/store/index.html | 1 + jsaccess/store.sh | 225 +++++++++++++++++---- 12 files changed, 229 insertions(+), 69 deletions(-) delete mode 100644 jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d delete mode 100644 jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.html delete mode 100644 jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt delete mode 100644 jsaccess/jsa/files/index.html create mode 100644 jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d create mode 100644 jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.html create mode 100644 jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt create mode 100644 jsaccess/jsa/store/index.html (limited to 'jsaccess') diff --git a/jsaccess/README.txt b/jsaccess/README.txt index 16f2c98..97813bd 100644 --- a/jsaccess/README.txt +++ b/jsaccess/README.txt @@ -31,10 +31,10 @@ Deployment There are 2 parts: * The jsa/ directory that contains html / javascript files, for the user to -access files list and download. jsa/files/ is the files store. +access files list and download. jsa/store/ is the files store. * The store.sh script for the web server owner to encrypt files It is recomanded to run store.sh on your laptop, and then syncronise the -jsa/files/ file store with your server. +jsa/store/ file store with your server. Put jsa/ directory on your web server, publicly available. @@ -48,9 +48,9 @@ On your laptop: $ ./store.sh myfile # Then enter the passphase you want to use for encryption. # It will tell you something like: -jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0 -CREATED jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/065e18a7f246b800242a778a6e8dd07a3321dac6 -UPDATED jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt +jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0 +CREATED jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/065e18a7f246b800242a778a6e8dd07a3321dac6 +UPDATED jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt 2. Syncronise the file store with you online server On your laptop: @@ -64,23 +64,23 @@ $ rsync jsa/ user@myserver:/var/www/htdocs/ How it works ============ -store.sh creates a directory jsa/files//. +store.sh creates a directory jsa/store//. It encrypts your file using AES256 with the passphrase and stores the result in -jsa/files//. +jsa/store//. It also updates the index of available files per directory called index.txt, that contains real file names. The index is also encrypted using AES256 with the passphrase. Web UI generates rmd160 hash from the passphrase and get the list of files -available for this passphrase (jsa/files//index.txt), +available for this passphrase (jsa/store//index.txt), decrypts it and shows the list of files. When the user clicks on Download, it fetches the file from the rmd160 name, decrypts it with the passphrase and stores it with the real name using the Filesaver JS API. -Dependencies -============ +Dependencies / Compatibility +============================ On the host that runs store.sh: * openssl @@ -90,22 +90,25 @@ On the web server: * Serving static files is enough * optional: https, to protect against clients targeted attacks +On the web user machine: +* Tested with Firefox 21 and Chrome 27 + Git content =========== jsa/ - should be on your webserver, can be renamed -jsa/files// - directory of files to download for a given password -jsa/files//index.txt - list of file name available +jsa/store// - directory of files to download for a given password +jsa/store//index.txt - list of file name available store.sh - to encrypt your files before uploading them to your web server TODO ==== -* Download progress +* web: download progress -* Decrypting progress +* web: decrypting progress Need to modify gibberish-aes -* Make password field appear as full of dots after validation +* web: make password field appear as full of dots after validation diff --git a/jsaccess/doc/put_your_encrypted_files_here.txt b/jsaccess/doc/put_your_encrypted_files_here.txt index 2cab735..162e0ba 100644 --- a/jsaccess/doc/put_your_encrypted_files_here.txt +++ b/jsaccess/doc/put_your_encrypted_files_here.txt @@ -6,9 +6,9 @@ To a new file to download: $ ./store.sh README.txt Enter passphrase used to encrypt: jsa -jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0 -CREATED jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/065e18a7f246b800242a778a6e8dd07a3321dac6 -UPDATED jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt +jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0 +CREATED jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/065e18a7f246b800242a778a6e8dd07a3321dac6 +UPDATED jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt $ rsync jsa/ user@_host:/var/www/htdocs/ diff --git a/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d b/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d deleted file mode 100644 index c3346fd..0000000 --- a/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d +++ /dev/null @@ -1,12 +0,0 @@ -U2FsdGVkX1+2mbnPpMbCiP9tBs1iP/fOPn2Q1wPE+12LpARHzvH3rJG6bG1S/GUA -wKurBstVwBGtrSoZfmt9VuR4gNxRQov1uyI63F9ohSUb4vt+rnkwuQwuvUIE3Vnn -8A6GBSkqw1Cr30lMOx8CQqYf7kd6SKXH0KwjYe/MkliRv6Nt0VnM5bAi/A/1VHC2 -QysdeWUL9G5DtAcKKU2ptRRSLKJTNZLkpYCklBSAJh6A4JqEoFbanERRL2rqcDGN -QaF5ovK42qGnZTzYIYAl7VAv/IYr0qraj3T8OHSxsxSMo6/hI8XRcT5FmkdWiBYm -udAOEzg07Uu4Tw/QtwZ7VCAYTubZuWh0SmiSfRGfWAHihGkMw1rnTnSBBTBWVfHS -FPGMkP1nXbmcRK3C6LPph1Oh3vNEIDfHrntRCC3e7/uokE+PemZqGxJMryRySQ1Q -Pb7TNSrQ1nM041eDOdr1oFFPlF2C4IQ0XX2gxY1pc0gW6wmPaj82SWFgb1N1iaHf -RCpYO/mH2U5jmkYM0NS6CSBzeX6N6AozS7PZ2XS/VnZPAVTyjUDLtwOaHQw9WuV9 -1yKi5f2eAOI2Mle/EmCTnIrwQvBD501iJLCko6/EqD3Lf7gtNgBFhhF7ERxNevPU -wAkBKFw63tSVsaYq2+qKYnO7yG+WnOCUXCJwp2gk147VVCtPEcDn3/1XoB0UM/+c -vaSINZbHNbLhpdbenhPfow== diff --git a/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.html b/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.html deleted file mode 100644 index e69de29..0000000 diff --git a/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt b/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt deleted file mode 100644 index e4debf3..0000000 --- a/jsaccess/jsa/files/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt +++ /dev/null @@ -1,2 +0,0 @@ -U2FsdGVkX1+2gShzEkk/XNr7NmymR1vU6cmQ0/6+i8Sj4RAVNQChZmE2hxn1IQI7 -8C62QF82skGICajSNQ5A3w== diff --git a/jsaccess/jsa/files/index.html b/jsaccess/jsa/files/index.html deleted file mode 100644 index d47b0f4..0000000 --- a/jsaccess/jsa/files/index.html +++ /dev/null @@ -1 +0,0 @@ -The monster has emptied me ! diff --git a/jsaccess/jsa/jsa.js b/jsaccess/jsa/jsa.js index 138ed84..259899c 100644 --- a/jsaccess/jsa/jsa.js +++ b/jsaccess/jsa/jsa.js @@ -36,7 +36,7 @@ function jsagetlist() { _status("Getting file list ..."); listreq = $.ajax({ - url: 'files/' + hash + '/index.txt', + url: 'store/' + hash + '/index.txt', beforeSend: function ( xhr ) { xhr.overrideMimeType("application/base64"); }, @@ -88,7 +88,7 @@ function _dl(file, pass) { var RMD160 = new Hashes.RMD160; var dirhash = RMD160.hex(pass); - var path = 'files/' + dirhash + '/' + RMD160.hex(dirhash + file); + var path = 'store/' + dirhash + '/' + RMD160.hex(dirhash + file); _status("Downloading \""+file+"\" ..."); dlreq = $.ajax({ diff --git a/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d b/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d new file mode 100644 index 0000000..c3346fd --- /dev/null +++ b/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/caf3eefc85fc7c4ee06d38ea679318114b21d88d @@ -0,0 +1,12 @@ +U2FsdGVkX1+2mbnPpMbCiP9tBs1iP/fOPn2Q1wPE+12LpARHzvH3rJG6bG1S/GUA +wKurBstVwBGtrSoZfmt9VuR4gNxRQov1uyI63F9ohSUb4vt+rnkwuQwuvUIE3Vnn +8A6GBSkqw1Cr30lMOx8CQqYf7kd6SKXH0KwjYe/MkliRv6Nt0VnM5bAi/A/1VHC2 +QysdeWUL9G5DtAcKKU2ptRRSLKJTNZLkpYCklBSAJh6A4JqEoFbanERRL2rqcDGN +QaF5ovK42qGnZTzYIYAl7VAv/IYr0qraj3T8OHSxsxSMo6/hI8XRcT5FmkdWiBYm +udAOEzg07Uu4Tw/QtwZ7VCAYTubZuWh0SmiSfRGfWAHihGkMw1rnTnSBBTBWVfHS +FPGMkP1nXbmcRK3C6LPph1Oh3vNEIDfHrntRCC3e7/uokE+PemZqGxJMryRySQ1Q +Pb7TNSrQ1nM041eDOdr1oFFPlF2C4IQ0XX2gxY1pc0gW6wmPaj82SWFgb1N1iaHf +RCpYO/mH2U5jmkYM0NS6CSBzeX6N6AozS7PZ2XS/VnZPAVTyjUDLtwOaHQw9WuV9 +1yKi5f2eAOI2Mle/EmCTnIrwQvBD501iJLCko6/EqD3Lf7gtNgBFhhF7ERxNevPU +wAkBKFw63tSVsaYq2+qKYnO7yG+WnOCUXCJwp2gk147VVCtPEcDn3/1XoB0UM/+c +vaSINZbHNbLhpdbenhPfow== diff --git a/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.html b/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.html new file mode 100644 index 0000000..e69de29 diff --git a/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt b/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt new file mode 100644 index 0000000..e4debf3 --- /dev/null +++ b/jsaccess/jsa/store/af022cd820fdad6cbcac8e15ac565c639a47dab0/index.txt @@ -0,0 +1,2 @@ +U2FsdGVkX1+2gShzEkk/XNr7NmymR1vU6cmQ0/6+i8Sj4RAVNQChZmE2hxn1IQI7 +8C62QF82skGICajSNQ5A3w== diff --git a/jsaccess/jsa/store/index.html b/jsaccess/jsa/store/index.html new file mode 100644 index 0000000..d47b0f4 --- /dev/null +++ b/jsaccess/jsa/store/index.html @@ -0,0 +1 @@ +The monster has emptied me ! diff --git a/jsaccess/store.sh b/jsaccess/store.sh index d730160..d797245 100755 --- a/jsaccess/store.sh +++ b/jsaccess/store.sh @@ -1,7 +1,7 @@ #!/bin/sh # jsaccess - private web file sharing using client side crypto -# store.sh: file encrytion script +# store.sh: file store manager for encrypting new files and deploy to server # Copyright (c) 2013 Laurent Ghigonis # @@ -17,18 +17,140 @@ # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. +VERSION=0.2 + +usage_exit() { + echo "usage: store.sh [-v] [action] [action arguments...] [store]" + echo + echo "actions:" + echo " ls [store] # default action if no arguments" + echo " init " + echo " add [store] # default action if one argument" + echo " rm [store]" + echo " wipe " + echo " pull [store]" + echo " push [store]" + echo " rset [store]" + echo " help|-h" + echo " version|-V" + echo + echo "By default store is ./store/ or ./jsa/store/" + echo "Use \"unset HISTFILE; export JSA_PASS=mypass\" to avoid typing the passphrase" + echo "Use \"unset JSA_PASS\" to forget the passphrase" + exit 1 +} + cleanup() { rm -f $tmp umask $sumask exit 0 } -if [ $# -ne 1 ]; then - echo "usage: store.sh " - exit 1 -fi -clear_path=$1 -clear_name=`basename $clear_path` +_store_get() { + store="" + [[ -d ./jsa/store/ ]] && store="`readlink -f ./jsa/store/`" # priority 3 + [[ -d ./store/ ]] && store="`readlink -f ./store/`" # priority 2 + [[ X"$1" != X"" ]] && store=$1 # priority 1 + [[ -z $store ]] && echo "ERROR: store not found !" && \ + echo "Not specified as argument and local stores" \ + "./store/ or ./jsa/store/ not found" && exit 2 + echo "Using store $store" +} + +_pass_read() { + if [ X"$JSA_PASS" != X"" ]; then + pass=$JSA_PASS + else + echo "Enter encryption passphrase" + echo -n "> " + read pass + fi + enc_dir_hash=`echo -n $pass |openssl rmd160 |cut -d' ' -f2` + enc_path="$store/$enc_dir_hash" +} + +_index_decrypt() { + if [ -f $enc_path/index.txt ]; then + echo -n $pass |openssl enc -d -a -aes-256-cbc -in $enc_path/index.txt -out $tmp -pass stdin ||exit $? + else + echo > $tmp + fi +} + +_index_encrypt() { + rm -f $enc_path/index.txt + echo -n $pass |openssl enc -e -a -aes-256-cbc -in $tmp -out $enc_path/index.txt -pass stdin ||exit $? + echo "UPDATED $enc_path/index.txt" +} + +_file_add() { + # Path / name generation + clear_path=$1 + clear_name=`basename $clear_path` + enc_name=`echo -n ${enc_dir_hash}${clear_name} |openssl rmd160 |cut -d' ' -f2` + mkdir -p $enc_path + touch $enc_path/index.html + + # Encrypt + base64 -w0 $clear_path > $tmp + echo -n $pass |openssl enc -e -a -aes-256-cbc -in $tmp -out $enc_path/$enc_name -pass stdin ||exit $? + echo "CREATED $enc_path/$enc_name" +} + +_file_rm() { + pass # XXX +} + +_rset() { + pass # XXX +} + +_rget() { + pass # XXX +} + +action_ls() { + _pass_read + _index_decrypt + [ ! -f $enc_path/index.txt ] && \ + echo "Passphrase not used in store !" && exit 1 + echo "$enc_dir_hash/index.txt:" + cat $tmp +} + +action_add() { + _pass_read + _file_add $1 + _index_decrypt + echo $1 >> $tmp + _index_encrypt +} + +action_rm() { + _pass_read + _file_rm $1 + _index_decrypt + sed -i d/$1/ $tmp + _index_encrypt +} + +action_wipe() { + _rset $1 +} + +action_pull() { + _rget $1 + rsync $tmp . +} + +action_push() { + _rget $1 + rsync . $tmp +} + +action_rset() { + _rset $1 +} # Check for dependencies if [ X"`which base64`" == X"" \ @@ -43,30 +165,65 @@ umask 077 tmp=`mktemp ./jsaXXXXXXXX` trap cleanup INT TERM EXIT -# Read passphrase -echo -n "Enter encryption passphrase: " -read pass - -# Generate file/directory names -enc_dir_hash=`echo -n $pass |openssl rmd160 |cut -d' ' -f2` -enc_path="jsa/files/$enc_dir_hash" -enc_name=`echo -n ${enc_dir_hash}${clear_name} |openssl rmd160 |cut -d' ' -f2` -echo $enc_path -mkdir -p $enc_path -touch $enc_path/index.html - -# Encrypt file -base64 -w0 $clear_path > $tmp -echo -n $pass |openssl enc -e -a -aes-256-cbc -in $tmp -out $enc_path/$enc_name -pass stdin ||exit $? -echo "CREATED $enc_path/$enc_name" - -# Add to passphrase index -if [ -f $enc_path/index.txt ]; then - echo -n $pass |openssl enc -d -a -aes-256-cbc -in $enc_path/index.txt -out $tmp -pass stdin ||exit $? -else - echo > $tmp -fi -echo $clear_name >> $tmp -rm -f $enc_path/index.txt -echo -n $pass |openssl enc -e -a -aes-256-cbc -in $tmp -out $enc_path/index.txt -pass stdin ||exit $? -echo "UPDATED $enc_path/index.txt" +# Run action +case $1 in +ls) + [ $# -ne 1 -a $# -ne 2 ] && usage_exit + _store_get $2 + action_ls + ;; +init) + [ $# -ne 2 ] && usage_exit + _store_get $2 + action_init + ;; +add) + [ $# -ne 2 -a $# -ne 3 ] && usage_exit + _store_get $3 + action_add $2 + ;; +rm) + [ $# -ne 2 -a $# -ne 3 ] && usage_exit + _store_get $3 + action_rm $1 + ;; +wipe) + [ $# -ne 2 ] && usage_exit + _store_get $2 + action_wipe + ;; +pull) + [ $# -ne 1 -a $# -ne 2 ] && usage_exit + _store_get $2 + action_pull $1 + ;; +push) + [ $# -ne 1 -a $# -ne 2 ] && usage_exit + _store_get $2 + action_push $1 + ;; +rset) + [ $# -ne 2 -a $# -ne 3 ] && usage_exit + _store_get $3 + action_rset $1 + ;; +help|-h) + usage_exit + ;; +version|-V) + echo "v$VERSION" + usage_exit + ;; +"") + [ $# -ne 0 ] && usage_exit + _store_get + action_ls + ;; +*) + [ $# -ne 1 ] && usage_exit + _store_get $2 + action_add $1 +esac + +# cleanup() executed in trap + -- cgit v1.2.3-59-g8ed1b