From 6994fcbc662fe3b8cae29d12dd57b633886afa85 Mon Sep 17 00:00:00 2001 From: paul Date: Wed, 22 Nov 2017 22:02:20 +0000 Subject: [PATCH 1/1] start of complete rewrite svn path=/trunk/; revision=6 --- .htaccess | 5 - .proxy | 0 bookmarks.css | 189 ++++++++++++++++++++----------- bookmarks.sh | 109 ------------------ error.sh | 2 - index.cgi | 307 +++++++++++++++++++++++++++++++++++++++++++++----- 6 files changed, 400 insertions(+), 212 deletions(-) delete mode 100644 .htaccess create mode 100644 .proxy delete mode 100644 bookmarks.sh delete mode 100644 error.sh diff --git a/.htaccess b/.htaccess deleted file mode 100644 index d947339..0000000 --- a/.htaccess +++ /dev/null @@ -1,5 +0,0 @@ -Options +ExecCGI -AddHandler cgi-script .cgi -DirectoryIndex index.cgi - -Require valid-user diff --git a/.proxy b/.proxy new file mode 100644 index 0000000..e69de29 diff --git a/bookmarks.css b/bookmarks.css index 8f2ee81..cadf1aa 100644 --- a/bookmarks.css +++ b/bookmarks.css @@ -1,83 +1,136 @@ -body { - text-align: left; - background-color: #EEF; - color: #000; +* { /* RESET */ + font-size: 12pt; + margin: 0; + padding: 0; + text-decoration: none; + font-weight: normal; + color: black; + background-color: white; + box-sizing: border-box; } -.folder { - column-width: 16em; - -moz-column-width: 16em; - -webkit-column-width: 16em; - column-gap: .5em; - -moz-column-gap: .5em; - -webkit-column-gap: .5em; - column-rule: 1px solid #BBB; - -moz-column-rule: 1px solid #BBB; - -webkit-column-rule: 1px solid #BBB; - - background-color: #FFF; - overflow: none; - - padding: .1em 1em .5em 1em; - margin: 0em 1em 1em 0em ; +html, body { + background-color: #DDD; +} - border-width: 1px; - border-style: solid; - -moz-border-radius: 1em 1em .5em .5em; - -webkit-border-radius: 1em 1em .5em .5em; - border-radius: 1em 1em .5em .5em; +.folder, form.newfolder{ + display: block; + width: 98%; + border: 1px solid black; + border-radius: .5em; + margin: 1em auto; + padding: 0; + overflow: hidden; + #column-width: 16em; + #column-rule: 1px solid #BBB; } -.fName { - width: 100%; - margin: 0px 0px .2em 0px; - border-style: none none solid none; - border-width: 1px; - border-color: #999; - text-indent: 1.5em; +.folder > h1 { + font-size: 1.25em; font-weight: bold; - font-size: 1.3em; - color: #333; - -moz-column-span: all; - -webkit-column-span: all; - column-span: all; + padding: .125em 1em .125em 2em; + border-bottom: 1px solid black; + background-color: #ACF; + border-radius: .375em .375em 0 0; + min-height: 1em; + #column-span: all; } -.fName a { - text-decoration: none; - font-weight: normal; + +.folder > h1 + a { + display: block; + position: relative; + top: -1.5em; + margin-left: 1em; + color: transparent; + background-color: transparent; + width: 0; height: 0; +} +.folder > h1 + a:before { + content: '\2699'; color: #333; } -.efName { - width: 100%; - border-style: none none solid none; - border-width: 1px; - border-color: #999; - display: none; - -moz-column-span: all; - -webkit-column-span: all; - column-span: all; -} -.efName a { - text-decoration: none; + +.modfolder { + display: block; + position: fixed; + left: 50%; margin: 0 -15em; + vertical-align: middle; + text-align: center; + width: 30em; + min-width: 240px; + z-index: 3; + border-radius: .5em; + border: 1px solid black; + padding: .125em 0; + min-height: 3em; + background-color: #ACF; +} +.modfolder:before { + display: block; + content: ''; + border: 1px solid black; + border-radius: 0 0 .5em .5em; + border-top: 0px; + top: 1.75em; bottom: .125em; left: .5%; right: .5%; + position: absolute; + background-color: white; + z-index: -1; +} +.modfolder + *:after { + content: ' '; + position: fixed; + top: 0; bottom: 0; left: 0; right: 0; + background-color: rgba(0,0,0,.5); } -.edButton { - width: 4em; - margin: 2px; - text-decoration: none; +.modfolder > label, +.modfolder > a { + display: inline-block; + width: 33%; + padding: .25em; + border: 1px solid black; + border-radius: .5em .5em 0 0; } +.modfolder > label { border-bottom: 0px; } +.modfolder > a { background-color: #EEE; } -.bmEdit { - display: none; - margin: .3em 0em .3em 0em; - border-style: solid none solid none; - border-width: 1px; - border-color: #BBB; - -moz-break-inside: avoid; - -webkit-break-inside: avoid; - break-inside: avoid; +.modfolder > input { + display: block; + width: 28em; + max-width: 95%; + margin: 1em; } -.bmDisplay img { - position: relative; - top: 4px; +.modfolder > button { + display: inline-block; + float: right; + margin: .5em; + padding: 0 .5em; +} + +.bookmark { + width: 16em; + display: inline-block; + margin: .5em 1em; +} + +.bookmark > a.modify { + font-size: 0; + color: white; +} +.bookmark > a.modify:before { + content: '\2699'; + color: #333; + font-size: initial; +} + +.bookmark > a.link > img { + height: 1.25em; + vertical-align: text-bottom; + margin: 0 .5ex; +} + +form.newbookmark, +form.modbookmark { + margin: .5em 1em; + break-inside: avoid; } diff --git a/bookmarks.sh b/bookmarks.sh deleted file mode 100644 index 212ac8f..0000000 --- a/bookmarks.sh +++ /dev/null @@ -1,109 +0,0 @@ -#!/bin/zsh -bdir="bookmarks/${REMOTE_USER}" -icodir=icodir -alias wget="/usr/bin/wget -T 5 -t 1 -q -U ''" - -if [ -n "${CONTENT_LENGTH}" -a "${CONTENT_LENGTH}" -gt 0 ]; then - (head -c "${CONTENT_LENGTH}" | sed 's:&:\n:g'; echo) >$bdir/$(date +%s) -fi - -moveName="$(echo -en "$(sed -rn '/mn=.+&mc=.+/{s:(^|.+&)mn=(.+)(&.+|$):\2:;s:\+: :g;s:%:\\x:g;p}' <<<"$QUERY_STRING")")" -moveCont="$(echo -en "$(sed -rn '/mn=.+&mc=.+/{s:(^|.+&)mc=(.+)(&.+|$):\2:;s:\+: :g;s:%:\\x:g;p}' <<<"$QUERY_STRING")")" -[ -n "$moveName" -a -n "$moveCont" ] && move=true || move=false - -[ -d "$bdir" ] || mkdir -p "$bdir" -names=$(sed -rn 's:^name=(.*)$:\1:pg' $bdir/$(ls $bdir |tail -n1)) -hidecmd=$(for each in $(echo $names); do echo "try{hide('e_$each');}catch(e){};"; done) -showcmd=$(for each in $(echo $names); do echo "try{show('d_$each');}catch(e){};"; done) - -delFolder=false -delBookmark=false - -echo " -
-
- qs $QUERY_STRING - mn $moveName - mc $moveCont -" - -cat $bdir/$(ls $bdir |tail -n1) |while read line; do - case "$line" in - deleteFolder=*) delFolder=true - ;; - deleteBookmark=*) delBookmark=true - ;; - folder=*) echo '' - fId=$(sed 's:^folder=::' <<<"$line") - [ -z "$fId" ] && fId='###' - fName="$(echo -ne "$(sed 's:+: :g;s:%:\\x:g' <<<"$fId")")" - $delFolder || echo " - - -
-
- $fName -
- - - -
- " - delFolder=false - $move && echo " -
- - -
- " - ;; - title=*) - bmId=$(sed 's:^title=::' <<<"$line") - [ -z "$bmId" ] && bmId='###' - bmName="$(echo -ne "$(sed 's:+: :g;s:%:\\x:g' <<<"$bmId")")" - ;; - content=*) - bmLink="$(echo -ne "$(sed 's:^content=::;s:+: :g;s:%:\\x:g' <<<"$line")")" - bmBase="$(sed -r 's:^(https?\://[^/]+)/?.*$:\1:' <<<"$bmLink")" - bmFav="$(sed -r 's:^(https?\://[^/]+)/?.*$:\1/favicon.ico:' <<<"$bmLink")" - bmFavFile="$icodir/$(sed -r 's:^https?\://([^/]+)/?.*$:\1.ico:' <<<"$bmLink")" - [ -f "$bmFavFile" ] || (wget -O - "$bmLink" |head -c 4096 |\ - sed -rn "//Is:^.* - - - $bmName -
- -
- Move Bookmark
- Name:
- Link: -
- " - $delBookmark || ($move && echo " -
- - -
- ") - delBookmark=false - ;; - *) echo "" - ;; - esac -done - -echo " - - - - - -
-" diff --git a/error.sh b/error.sh deleted file mode 100644 index 8fa6b50..0000000 --- a/error.sh +++ /dev/null @@ -1,2 +0,0 @@ -echo 'No user authentication occured.
' -echo 'This does Probably mean, that this service is misconfigured.' diff --git a/index.cgi b/index.cgi index a0a8490..8129b7e 100644 --- a/index.cgi +++ b/index.cgi @@ -1,31 +1,282 @@ -#!/bin/zsh -echo 'Content-type: text/html\n' +#!/bin/sh -cat < - - - Bookmarks! - - - - - -NOTES - -if [ -z "${REMOTE_USER}" ]; then - . ./error.sh -else - . ./bookmarks.sh +exec 2>>error.log + +. shcgi/cgilite.sh +mkdir -p users +#env >>debug +printf 'POST: %s\n' "$cgilite_post" >>debug +printf 'action: %s\n' "$(GET action)" >>debug + +wget="$(which wget)" +wget(){ "$wget" -T 5 -t 1 -q -U '' $@; } +checkid(){ grep -m 1 -xE '[0-9a-zA-Z:_]{12}'; } + +genid(){ + # generate random ID + head -c9 /dev/urandom \ + | uuencode -m - \ + | sed -n '2{y;+/;:_;;p}' +} + +timeid(){ + # generate time based ID + d=$(date +%s) + { printf $( + while [ "$d" -gt 0 ]; do + printf \\%o $((d % 256)) + d=$((d / 256)) + done + ) | tac + head -c5 /dev/urandom + } \ + | uuencode -m - \ + | sed -n '2{y;+/;:_;;p}' +} + +getFavicon(){ + url="$1" + bid="$2" + prot=${url%%://*} + domain="${url#*://}" + domain="${domain%%/*}" + ubase="${prot}://${domain}" + file="${BDB}/favicons/${bid}.ico" + + mkdir -p "${BDB}/favicons/" && chmod a+rx "${BDB}/favicons/" + + favinfo="$( + wget -O- "$url" \ + | head -c4096 \ + | sed -rn \ + 's;^.*(<[Ll][Ii][Nn][Kk]( [^>]*)? [Rr][Re][Ll]='\''([Ss][Hh][Oo][Rr][Tt][Cc][Uu][Tt] )?[Ii][Cc][Oo][Nn]'\''[^>]*>).*$;\1;; + s;^.*(<[Ll][Ii][Nn][Kk]( [^>]*)? [Rr][Re][Ll]="([Ss][Hh][Oo][Rr][Tt][Cc][Uu][Tt] )?[Ii][Cc][Oo][Nn]"[^>]*>).*$;\1;; + tX; b; :X; + s;^.*<([^>]+) [Hh][Rr][Ee][Ff]="([^"]+)".*$:\2;; + s;^.*<([^>]+) [Hh][Rr][Ee][Ff]='\''([^'\'']+)'\''.*$:\2;; + tY; b; :Y; p + ' + )" + + printf 'Shortcut icon for %s is %s\n' "$url" "$favinfo" >>debug + [ -z "$favinfo" ] && favinfo="${ubase}/favicon.ico" + case "$favinfo" in + http://*|https://*|//*) wget -O "$file" "$favinfo" + ;; + /*) wget -O "$file" "${ubase}/${favinfo}" + ;; + *) wget -O "$file" "${url%/*}/${favinfo}" + ;; + esac + [ -f "${file}.1" ] && mv "${file}.1" "$file" + chmod a+r "$file" +} + +QRYID="$(GET id |checkid)" +COKID="$(COOKIE id |checkid)" +BDB="users/${QRYID}" + +case "$(GET action)" in + newid) + NEWID="$(genid)" + + { git init "users/${NEWID}" || mkdir -p "users/${NEWID}"; } >&- + + printf '%s 303 See Other\r\n' "$SERVER_PROTOCOL" + printf 'Location: %s\r\n' "${SCRIPT_NAME}?id=${NEWID}" + SET_COOKIE +8640000 "id=${NEWID}" + printf '\r\n' + exit 0 + ;; + newfolder) + name="$(POST name |head -n1)" + fid="$(timeid)" + order="$( + head -qn1 "${BDB}"/????????????.bm \ + | cut -f3 \ + | sort -n \ + | tail -n1 \ + || printf 1 + )" + order="$(((order + 1000) / 1000 * 1000))" + if [ -n "$name" -a -d "${BDB}" ]; then + printf '%s\t%s\t%s\n' "$fid" "$(HTML "$name")" "$order" >"${BDB}/${fid}.bm" + fi + REDIRECT "${SCRIPT_NAME}?id=${QRYID}#${fid}" + ;; + modfolder) + name="$(POST name |head -n1)" + fid="$(POST fid | checkid)" + file="${BDB}/${fid}.bm" + if [ "$(POST control)" = confirm -a -n "$name" -a -f "$file" ]; then + order="$(head -n1 "$file" |cut -f3 || printf 1000)" + printf '%s\t%s\t%s\n' "$fid" "$(HTML "$name")" "$order" >"${file%.bm}.tmp" + tail -n+2 "$file" >>"${file%.bm}.tmp" + mv "${file%.bm}.tmp" "$file" + fi + REDIRECT "${SCRIPT_NAME}?id=${QRYID}#${fid}" + ;; + newbookmark) + fid="$(POST fid | checkid)" + name="$(POST name |head -n1)" + url="$(POST url |head -n1)" + file="${BDB}/${fid}.bm" + bid="$(timeid)" + if [ -n "$name" -a -f "${file}" ]; then + printf '%s\t%s\t%s\n' "$bid" "$(HTML "$name")" "$(HTML "$url")" >>"${file}" + fi + getFavicon "$url" "$bid" + REDIRECT "${SCRIPT_NAME}?id=${QRYID}#${fid}" + ;; + modbookmark) + bid="$(POST bid | checkid)" + name="$(POST name |head -n1)" + url="$(POST url |head -n1)" + file="$(grep -lE "^${bid}" "${BDB}"/????????????.bm)" + if [ -w "$file" -a -n "$name" -a -n "$url" ]; then + bm="$(printf '%s\t%s\t%s' "$bid" "$(HTML "$name")" "$(HTML "$url")" |sed -r 's;[\&\;];\\&;g;')" + sed -ri "s;^${bid}\t.*$;${bm};" "$file" + fi + getFavicon "$url" "$bid" + REDIRECT "${SCRIPT_NAME}?id=${QRYID}#${fid}" + ;; +esac + +if [ -z "$QRYID" -a -n "$COKID" ]; then + REDIRECT "${SCRIPT_NAME}?id=${COKID}" +elif [ -n "$QRYID" -a -z "$COKID" ]; then + SET_COOKIE +8640000 "id=${QRYID}" +fi + +if [ -z "$QRYID" -a -z "$COKID" ]; then + printf 'Content-Type: text/html; charset=utf-8\r\n\r\n' + + cat <<-EOF + + + Bookman - New Collection + +

You have not yet set up a collection on this server.

+ Click here to start a new collection. + + EOF + exit 0 +elif ! [ -d "users/${QRYID}" ]; then + printf '%s 404 Not Found\r\n' "$SERVER_PROTOCOL" + printf 'Content-Type: text/html; charset=utf-8\r\n\r\n' + + cat <<-EOF + + + Bookman - 404 + +

The collection you requested does not exist on this server.

+ Click here to start a new collection. + + EOF + exit 0 fi -echo '' +list_bookmarks(){ + fid="$1" + bmodify="$(GET bmodify |checkid)" + + tail -n+2 "${BDB}/${fid}.bm" \ + | while read bid name url; do + if [ "${bid}" = "$bmodify" ]; then + cat <<-EOF +
+ + + + +
+ EOF + else + cat <<-EOF +
+ Modify + ${name} +
+ EOF + fi + done +} + +list_folders(){ + fmodify="$(GET fmodify |checkid )" + fdelete="$(GET fdelete |checkid )" + fmove="$(GET fmove |checkid )" + + head -qn1 "${BDB}"/????????????.bm \ + | sort -nk3 \ + | while read fid fname order; do + cat <<-EOF +
+

${fname}

+ Modify + $(list_bookmarks "$fid") +
+ + + + +
+
+ EOF + if [ "$fid" = "$fmodify" ]; then + cat <<-EOF +
+ + DeleteMove + + + +
+ EOF + elif [ "$fid" = "$fdelete" ]; then + cat <<-EOF +
+ + RenameMove + + + +
+ EOF + elif [ "$fid" = "$fmove" ]; then + cat <<-EOF +
+ + RenameDelete + + + +
+ EOF + fi + done +} + +printf 'Content-Type: text/html; charset=utf-8\r\n\r\n' +cat < + + Bookman - Your Collection + + + $(list_folders) +
+ + +
+ +EOF + +#set filetype=sh -- 2.39.2