#!/bin/bash fgaddon_url=https://sourceforge.net/p/flightgear/fgaddon/HEAD/tree/trunk/Aircraft fgaddon_svn=https://svn.code.sf.net/p/flightgear/fgaddon/trunk/Aircraft fgaddon_path=$HOME/.fgfs/flightgear-addons/Aircraft attribute_regex='s/^.*id="l[0-9]+" class="code_block">.*<__attribute__><.span>(.+)<.__attribute__><.span>.*$/\1/p' aircrafts=$(mktemp --dry-run /dev/shm/Aircraft-XXXXXXXXX) aircraft=$(mktemp --dry-run /dev/shm/aircraft-XXXXXXX) setxml=$(mktemp --dry-run /dev/shm/setxml-XXXXXXXX) in_ram_database=$(mktemp --dry-run /dev/shm/XXXXXXX) database=${DB:-$0.db} attributes=(description long_description author flight_model) function get_attribute () { eval "unset $1" result=$(sed -rn "${attribute_regex//__attribute__/${1//_/-}}" $setxml) eval "$1=\$\"$result\"" } function sqlite_request () { sqlite3 "$in_ram_database" <<< "$1" } function trap_exit () { if test -r "$database" && md5sum $in_ram_database | sed "s,$in_ram_database,$database," | md5sum --status -c -; then rm -f $in_ram_database elif test -w "$database"; then mv -f $in_ram_database "$database" elif ! test -e "$database"; then mv $in_ram_database "$database" else rm -f $in_ram_database fi rm -f $aircrafts $aircraft $setxml } update_database () { let progress++ echo "[ ${progress}${total:+/$total} ] $ac" dbupdate=$(sqlite_request "select date from aircrafts where name is '$ac'") if test -z "$dbupdate"; then sqlite_request "insert into aircrafts (name, date) values ('$ac', $update)" elif test $dbupdate -ne $update; then sqlite_request "update aircrafts set date = $update where name is '$ac'" fi id=$(sqlite_request "select id from aircrafts where name is '$ac'") wget -qO- $fgaddon_url/$ac > $aircraft for sx in $(sed -rn 's/.+$/\1/p' $aircraft); do echo " -> ${sx/-set.xml}" wget -qO- $fgaddon_url/$ac/$sx > $setxml for attribute in ${attributes[@]}; do get_attribute $attribute done test -e $fgaddon_path/$ac/$sx installed=$? if test -n "$description" -a -z "$flight_model"; then grep -qi 'jsbsim' <<< "$description" && flight_model='jsb' grep -qi 'yasim' <<< "$description" && flight_model='yasim' fi known=$(sqlite_request "select variantof from setxml where file is '$sx'") if test -n "$known"; then for attribute in ${attributes[@]}; do dbvalue=$(sqlite_request "select $attribute from setxml where file is '$sx'") eval "wgvalue=\$$attribute" if test "$dbvalue" != "$wgvalue"; then sqlite_request "update setxml set $attribute = '$wgvalue' where file is '$sx'" fi done else sqlite_request "insert into setxml values ('$sx', $id, '$description', '$long_description', '$author', '$type', '$flight_model', $installed)" fi done } trap trap_exit EXIT test -e $database && cp $database $in_ram_database sqlite_request "create table if not exists aircrafts (id integer primary key, name text, date integer)" sqlite_request "create table if not exists setxml (file text, variantof integer, description text, long_description text, author text, type text, flight_model text, installed integer)" test -z "$1" && echo "mode RSS" case ${1:-rss} in 'full') echo "downloading the FGADDON list" wget -qO- $fgaddon_url > $aircrafts total=$(grep -c ' ' $aircrafts) for ac in $(sed -rn 's/^\s* '$ac'<' $aircrafts | sed -rn '$s/^\s*.*$/\1/p') update=$(date +%s -d"$update") update_database done ;; 'rss') xmlgetnext () { local IFS='>' read -d '<' TAG VALUE } get_updates_from_rss () { wget -qO- https://sourceforge.net/p/flightgear/fgaddon/feed | while xmlgetnext; do case "$TAG" in 'item') let entry++ unset link pubDate revision title file;; 'link') link="$VALUE";; 'title') title="$VALUE";; 'guid isPermaLink="false"') revision=$(sed -r 's,^.+/([0-9]+)/$,\1,' <<< $VALUE);; 'pubDate') pubDate=$(date +%s -d "$VALUE") if test $entry -eq 1 -a $pubDate -eq ${latest_update:-0}; then echo "no new updates" >&2 break fi ;; '/item') echo "checking $revision ($(date +"%d %B" -d@$pubDate)): $title" >&2 wget -qO- "$link" > $aircrafts for file in $(egrep '/trunk/Aircraft/.*/.*-set.xml$' $aircrafts); do file=${file/\/trunk\/Aircraft\/} echo ${file%/*} echo $pubDate done ;; '/channel') if test ${latest_update:-0} -lt $pubDate; then echo "WARNING: $(( ($pubDate - ${latest_update:-0}) / 86400 )) days between the oldest RSS entry and last DB entry" >&2 echo "a $0 full may be useful" >&2 fi ;; esac done } latest_update=$(sqlite_request "select max(date) from aircrafts") ac_list=($(get_updates_from_rss)) total=$(( ${#ac_list[@]} / 2 )) for ((i=0; i < ${#ac_list[@]}; i=i+2)); do ac=${ac_list[i]} update=${ac_list[i+1]} update_database done ;; *) echo "usage: [DB=path/to/database] $0 [rss|full]" echo echo "rss: updates only last repo changes" echo "full: updates from all repo" ;; esac