Merge branch 'dev' of https://github.com/mdbtools/mdbtools into bounds-check-mdb-bind-column

This commit is contained in:
James Woodcock 2020-10-31 09:38:03 +00:00
commit 2e8480d7e5
18 changed files with 183 additions and 110 deletions

View File

@ -319,10 +319,10 @@ dnl doc/reference/libmdb/Makefile])
##################################################
bold_red=$(tput bold)$(tput setf 4)
bold_green=$(tput bold)$(tput setf 2)
bold=$(tput bold)
reset=$(tput sgr0)
bold_red=$(tput bold 2>/dev/null)$(tput setf 4 2>/dev/null)
bold_green=$(tput bold 2>/dev/null)$(tput setf 2 2>/dev/null)
bold=$(tput bold 2>/dev/null)
reset=$(tput sgr0 2>/dev/null)
AC_MSG_NOTICE([])
AC_MSG_NOTICE([${bold}MDB Tools $VERSION - Configuration summary${reset}])
AC_MSG_NOTICE([])

View File

@ -2,7 +2,8 @@ NAME
mdb-export - Export data in an MDB database table to CSV format.
SYNOPSIS
mdb-export [-H] [-d delim] [-R delim] [[-Q] | [-q char [-X char]]] [-I backend] [-D fmt] [-N prefix] [-b strip|raw|octal] database table
mdb-export [--no-header] [--delimiter delim] [--row-delimiter delim] [[--no-quote] | [--quote char [--escape char]]] [--date-format fmt] [--datetime-format fmt] [--bin strip|raw|octal|hex] [--boolean-words] database table
mdb-export --insert backend [--namespace prefix] [--batch-size int] database table
mdb-export -h|--help
DESCRIPTION
@ -10,19 +11,26 @@ DESCRIPTION
It produces a CSV (comma separated value) output for the given table. Such output is suitable for importation into databases or spreadsheets.
Used with --insert, it outputs SQL specific to backend dialect, including some constraints like NOT NULL and foreign keys.
OPTIONS
-H, --no-header Suppress header row.
-Q, --no-quote Don't wrap text-like fields (text, memo, date) in quotes. If not specified text fiels will be surrounded by " (double quote) characters.
-d, --delimiter delim Specify an alternative column delimiter. Default is , (comma).
-R, --row-delimiter delim Specify a row delimiter. Default is \\n (ASCII value 10).
-Q, --no-quote Don't wrap text-like fields (text, memo, date) in quotes. If not specified text fiels will be surrounded by " (double quote) characters.
-q, --quote char Use char to wrap text-like fields. Default is " (double quote).
-X, --escape char Use char to escape quoted characters within a field. Default is doubling.
-I, --insert backend INSERT statements (instead of CSV). You must specify which SQL backend dialect to use. Allowed values are: access, sybase, oracle, postgres, mysql and sqlite.
-D, --date-format fmt Set the date format (see strftime(3) for details).
-q, --quote char Use to wrap text-like fields. Default is " (double quote).
-X, --escape char Use to escape quoted characters within a field. Default is doubling.
-N, --namespace prefix Prefix identifiers with prefix.
-S, --batch-size int Size of insert batches on supported platforms.
-D, --date-format fmt Set the date format (see strftime(3) for details.
-T, --datetime-format fmt Set the date/time format (see strftime(3) for details.
-0, --null char Use char to represent a NULL value.
-b, --bin strip|raw|octal|hex Binary export mode: strip binaries, export as-is, output \\ooo style octal data or output \\xx style hexadecimal data.
-B, --boolean-words Use TRUE/FALSE in Boolean fields (default is 0/1).
NOTES
Most of the formatting options actually also works with --insert.
ENVIRONMENT
MDB_JET3_CHARSET Defines the charset of the input JET3 (access 97) file. Default is CP1252. See iconv(1).

View File

@ -12,7 +12,7 @@ DESCRIPTION
OPTIONS
-L List queries in the database (default if no query name is passed)
-1 Use newline as the delimiter (used in conjuction with listing)
-1 Use newline as the delimiter (used in conjunction with listing)
-d delim Specify delimiter to use
NOTES

View File

@ -383,7 +383,7 @@ mdb_index_hash_text(MdbHandle *mdb, char *text, char *hash)
{
#ifdef __MSWSTR_H__
char *out_ptr = alloca((len+1)*2);
int i;
unsigned int i;
// mdb_ascii2unicode doesn't work, we don't want unicode compression!
for (i=0; i<len+1; i++) {
out_ptr[i*2] = text[i];

View File

@ -1,4 +1,4 @@
if ENABLE_BASH_COMPLETION
bashcompletiondir = $(BASH_COMPLETION_DIR)
dist_bashcompletion_DATA = mdb-export mdb-hexdump mdb-import mdb-parsecsv mdb-prop mdb-schema mdb-sql mdb-tables mdb-ver
dist_bashcompletion_DATA = mdb-count mdb-export mdb-hexdump mdb-import mdb-json mdb-parsecsv mdb-prop mdb-queries mdb-schema mdb-sql mdb-tables mdb-ver
endif

View File

@ -0,0 +1,21 @@
#-*- mode: shell-script;-*-
_mdb_count()
{
local cur prev words cword
_init_completion || return
if [[ "$prev" == *@(mdb|mdw|accdb) ]] ; then
local dbname
local tablenames
dbname=$prev
__expand_tilde_by_ref dbname
local IFS=$'\n'
tablenames="$(eval mdb-tables -S -1 "${dbname}" 2>/dev/null)"
compopt -o filenames
COMPREPLY=( $( compgen -W '${tablenames}' -- "$cur" ) )
else
_filedir '@(mdb|mdw|accdb)'
fi
return 0
} &&
complete -F _mdb_count mdb-count

View File

@ -1,28 +1,31 @@
#-*- mode: shell-script;-*-
_mdb_export()
{
local cur prev
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
prev=${COMP_WORDS[COMP_CWORD-1]}
local cur prev words cword split
_init_completion -s || return
if [[ "$prev" == -@(d|-delimiter|R|-row-delimiter|q|-quote|X|-escape|D|-date-format|N|-namespace|h|-help) ]] ; then
if [[ "$prev" == -@(d|-delimiter|R|-row-delimiter|q|-quote|X|-escape|N|-namespace|S|-batch-size|D|-date-format|T|-datetime-format|0|-null|h|-help) ]] ; then
return 0
elif [[ "$prev" == -I ]] ; then
COMPREPLY=( $( compgen -W 'access sybase oracle postgres mysql' -- $cur ) )
elif [[ "$prev" == -@(I|-insert) ]] ; then
COMPREPLY=( $( compgen -W 'access sybase oracle postgres mysql sqlite' -- "$cur" ) )
elif [[ "$prev" == -@(b|-bin) ]] ; then
COMPREPLY=( $( compgen -W 'strip raw octal' -- $cur ) )
elif [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '-H -d -R -Q -q -X -I -D -N -b -h \
--no-header --no-quote --delimiter --row-delimiter --insert \
--date-format --quote --escape --namespace --bin --help' -- $cur ) )
COMPREPLY=( $( compgen -W 'strip raw octal hex' -- "$cur" ) )
fi
$split && return
if [[ "$cur" == -* ]]; then
COMPREPLY=($(compgen -W '$(_parse_help "$1")' -- "$cur"))
[[ $COMPREPLY == *= ]] && compopt -o nospace
elif [[ "$prev" == *@(mdb|mdw|accdb) ]] ; then
local dbname
local tablenames
dbname=$prev
__expand_tilde_by_ref dbname
tablenames=$(eval mdb-tables -S -d / "${dbname}" 2>/dev/null)
COMPREPLY=( $( IFS=/ compgen -W "${tablenames}" -- $cur ) )
local IFS=$'\n'
tablenames="$(eval mdb-tables -S -1 "${dbname}" 2>/dev/null)"
compopt -o filenames
COMPREPLY=( $( compgen -W '${tablenames}' -- "$cur" ) )
else
_filedir '@(mdb|mdw|accdb)'
fi

View File

@ -1,11 +1,10 @@
#-*- mode: shell-script;-*-
_mdb_hexdump()
{
local cur
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
local cur prev words cword
_init_completion || return
if (( COMP_CWORD == 1 )); then
if (( $cword == 1 )); then
_filedir '@(mdb|mdw|accdb)'
fi
return 0

View File

@ -1,25 +1,27 @@
#-*- mode: shell-script;-*-
_mdb_import()
{
local cur
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
prev=${COMP_WORDS[COMP_CWORD-1]}
local cur prev words cword split
_init_completion -s || return
if [[ "$prev" == -@(d|-delimiter) ]]; then
if [[ "$prev" == -@(H|--header|d|-delimiter) ]]; then
return 0
elif [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '-H --header \
-d --delimiter \
-h --help' -- $cur ) )
fi
$split && return
if [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '--header= --delimiter= --help' -- "$cur" ) )
[[ $COMPREPLY == *= ]] && compopt -o nospace
elif [[ "$prev" == @(*mdb|*mdw|*accdb) ]]; then
local dbname
local tablenames
dbname=$prev
__expand_tilde_by_ref dbname
tablenames=$(eval mdb-tables -S -d / "${dbname}" 2>/dev/null)
COMPREPLY=( $( IFS=/ compgen -W "${tablenames}" -- $cur ) )
local IFS=$'\n'
tablenames="$(eval mdb-tables -S -1 "${dbname}" 2>/dev/null)"
compopt -o filenames
COMPREPLY=( $( compgen -W '${tablenames}' -- "$cur" ) )
else
_filedir '@(mdb|mdw|accdb|txt|csv)'
fi

View File

@ -0,0 +1,30 @@
#-*- mode: shell-script;-*-
_mdb_json()
{
local cur prev words cword split
_init_completion -s || return
if [[ "$prev" == -@(D|-date-format|T|-datetime-format|U|--no-unprintable|h|-help) ]] ; then
return 0
fi
$split && return
if [[ "$cur" == -* ]]; then
COMPREPLY=($(compgen -W '$(_parse_help "$1")' -- "$cur"))
[[ $COMPREPLY == *= ]] && compopt -o nospace
elif [[ "$prev" == *@(mdb|mdw|accdb) ]] ; then
local dbname
local tablenames
dbname=$prev
__expand_tilde_by_ref dbname
local IFS=$'\n'
tablenames="$(eval mdb-tables -S -1 "${dbname}" 2>/dev/null)"
compopt -o filenames
COMPREPLY=( $( compgen -W '${tablenames}' -- "$cur" ) )
else
_filedir '@(mdb|mdw|accdb)'
fi
return 0
} &&
complete -F _mdb_json mdb-json

View File

@ -1,11 +1,10 @@
#-*- mode: shell-script;-*-
_mdb_parsecsv()
{
local cur
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
local cur prev words cword
_init_completion || return
if (( COMP_CWORD == 1 )); then
if (( $cword == 1 )); then
_filedir '@(txt|csv)'
fi
return 0

View File

@ -1,22 +1,22 @@
#-*- mode: shell-script;-*-
_mdb_prop()
{
local cur
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
local cur prev words cword
_init_completion || return
if (( COMP_CWORD == 1 )); then
if (( $cword == 1 )); then
_filedir '@(mdb|mdw|accdb)'
elif (( COMP_CWORD == 2 )); then
elif (( $cword == 2 )); then
local dbname
local tablenames
dbname=${COMP_WORDS[1]}
dbname=$prev
__expand_tilde_by_ref dbname
tablenames=$(eval mdb-tables -S -d / "${dbname}" 2>/dev/null)
COMPREPLY=( $( IFS=/ compgen -W "${tablenames}" -- $cur ) )
elif (( COMP_CWORD == 3 )); then
COMPREPLY=( $( compgen -W 'Lv LvProp LvModule LvExtra' -- $cur ) )
local IFS=$'\n'
tablenames="$(eval mdb-tables -S -1 "${dbname}" 2>/dev/null)"
compopt -o filenames
COMPREPLY=( $( compgen -W '${tablenames}' -- "$cur" ) )
elif (( $cword == 3 )); then
COMPREPLY=( $( compgen -W 'Lv LvProp LvModule LvExtra' -- "$cur" ) )
fi
return 0
} &&

View File

@ -0,0 +1,25 @@
#-*- mode: shell-script;-*-
_mdb_queries()
{
local cur prev words cword
_init_completion || return
if [[ "$prev" == -@(d) ]]; then
return 0
elif [[ "$cur" == -* ]]; then
COMPREPLY=($(compgen -W '$(_parse_help "$1")' -- "$cur"))
elif [[ "$prev" == *@(mdb|mdw|accdb) ]] ; then
local dbname
local querynames
dbname=$prev
__expand_tilde_by_ref dbname
local IFS=$'\n'
querynames="$(eval mdb-queries -1 "${dbname}" 2>/dev/null)"
compopt -o filenames
COMPREPLY=( $( compgen -W "${querynames}" -- "$cur" ) )
else
_filedir '@(mdb|mdw|accdb)'
fi
return 0
} &&
complete -F _mdb_queries mdb-queries

View File

@ -1,26 +1,20 @@
#-*- mode: shell-script;-*-
_mdb_schema()
{
local cur prev
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
prev=${COMP_WORDS[COMP_CWORD-1]}
local cur prev words cword split
_init_completion -s || return
if [[ "$prev" == -@(T|-table|N|-namespace) ]] ; then
return 0
elif [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '-T --table \
-N --namespace \
--drop-table --no-drop-table \
--not-null --no-not-null \
--default-values --no-default-values \
--not-empty --no-not-empty \
--indexes --no-indexes \
--relations --no-relations
-h --help' -- $cur ) )
fi
$split && return
if [[ "$cur" == -* ]]; then
COMPREPLY=($(compgen -W '$(_parse_help "$1")' -- "$cur"))
[[ $COMPREPLY == *= ]] && compopt -o nospace
elif [[ "$prev" == @(*mdb|*mdw|*accdb) ]]; then
COMPREPLY=( $( compgen -W 'access sybase oracle postgres mysql' -- $cur ) )
COMPREPLY=( $( compgen -W 'access sybase oracle postgres mysql sqlite' -- "$cur" ) )
else
_filedir '@(mdb|mdw|accdb)'
fi

View File

@ -1,24 +1,20 @@
#-*- mode: shell-script;-*-
_mdb_sql()
{
local cur prev
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
prev=${COMP_WORDS[COMP_CWORD-1]}
local cur prev words cword split
_init_completion -s || return
if [[ "$prev" == -d ]] ; then
if [[ "$prev" == -@(P|-no-pretty-print|H|-no-header|F|-no-footer) ]] ; then
return 0
fi
$split && return
if [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '$(_parse_help "$1")' -- "$cur"))
[[ $COMPREPLY == *= ]] && compopt -o nospace
elif [[ "$prev" == -@(i|-input|o|-output) ]] ; then
_filedir
elif [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '-H --no-header \
-F --no-footer \
-p --no-pretty-print \
-d --delimiter \
-i --input \
-o --output \
-h --help' -- $cur ) )
else
_filedir '@(mdb|mdw|accdb)'
fi

View File

@ -1,24 +1,21 @@
#-*- mode: shell-script;-*-
_mdb_tables()
{
local cur prev
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
prev=${COMP_WORDS[COMP_CWORD-1]}
local cur prev words cword split
_init_completion -s || return
if [[ "$prev" == -@(d|-delimiter) ]]; then
return 0
elif [[ "$prev" == -@(t|-type) ]]; then
COMPREPLY=( $( compgen -W 'form table macro systable report query linkedtable module relationship dbprop any all' -- $cur ) )
COMPREPLY=( $( compgen -W 'form table macro systable report query linkedtable module relationship dbprop any all' -- "$cur" ) )
return 0
elif [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '-S --system\
-1 --single-column \
-d --delimiter \
-t --type \
-T --showtype \
-h --help' -- $cur ) )
fi
$split && return
if [[ "$cur" == -* ]]; then
COMPREPLY=($(compgen -W '$(_parse_help "$1")' -- "$cur"))
[[ $COMPREPLY == *= ]] && compopt -o nospace
else
_filedir '@(mdb|mdw|accdb)'
fi

View File

@ -1,13 +1,12 @@
#-*- mode: shell-script;-*-
_mdb_ver()
{
local cur
COMPREPLY=()
cur=${COMP_WORDS[COMP_CWORD]}
local cur prev words cword
_init_completion || return
if [[ "$cur" == -* ]]; then
COMPREPLY=( $( compgen -W '-M -h --help' -- $cur ) )
COMPREPLY=($(compgen -W '$(_parse_help "$1")' -- "$cur"))
#COMPREPLY=($(compgen -W '--help --mdbtools' -- "$cur"))
else
_filedir '@(mdb|mdw|accdb)'
fi

View File

@ -54,19 +54,19 @@ main(int argc, char **argv)
GOptionEntry entries[] = {
{"no-header", 'H', G_OPTION_FLAG_REVERSE, G_OPTION_ARG_NONE, &header_row, "Suppress header row.", NULL},
{"no-quote", 'Q', G_OPTION_FLAG_REVERSE, G_OPTION_ARG_NONE, &quote_text, "Don't wrap text-like fields in quotes.", NULL},
{"delimiter", 'd', 0, G_OPTION_ARG_STRING, &delimiter, "Specify an alternative column delimiter. Default is comma.", "char"},
{"row-delimiter", 'R', 0, G_OPTION_ARG_STRING, &row_delimiter, "Specify a row delimiter", "char"},
{"no-quote", 'Q', G_OPTION_FLAG_REVERSE, G_OPTION_ARG_NONE, &quote_text, "Don't wrap text-like fields in quotes.", NULL},
{"quote", 'q', 0, G_OPTION_ARG_STRING, &quote_char, "Use <char> to wrap text-like fields. Default is double quote.", "char"},
{"backend", 'I', 0, G_OPTION_ARG_STRING, &insert_dialect, "INSERT statements (instead of CSV)", "backend"},
{"escape", 'X', 0, G_OPTION_ARG_STRING, &escape_char, "Use <char> to escape quoted characters within a field. Default is doubling.", "format"},
{"insert", 'I', 0, G_OPTION_ARG_STRING, &insert_dialect, "INSERT statements (instead of CSV)", "backend"},
{"namespace", 'N', 0, G_OPTION_ARG_STRING, &namespace, "Prefix identifiers with namespace", "namespace"},
{"batch-size", 'S', 0, G_OPTION_ARG_INT, &batch_size, "Size of insert batches on supported platforms.", "int"},
{"date-format", 'D', 0, G_OPTION_ARG_STRING, &shortdate_fmt, "Set the date format (see strftime(3) for details)", "format"},
{"datetime-format", 'T', 0, G_OPTION_ARG_STRING, &date_fmt, "Set the date/time format (see strftime(3) for details)", "format"},
{"escape", 'X', 0, G_OPTION_ARG_STRING, &escape_char, "Use <char> to escape quoted characters within a field. Default is doubling.", "format"},
{"namespace", 'N', 0, G_OPTION_ARG_STRING, &namespace, "Prefix identifiers with namespace", "namespace"},
{"null", '0', 0, G_OPTION_ARG_STRING, &null_text, "Use <char> to represent a NULL value", "char"},
{"bin", 'b', 0, G_OPTION_ARG_STRING, &str_bin_mode, "Binary export mode", "strip|raw|octal|hex"},
{"boolean-words", 'B', 0, G_OPTION_ARG_NONE, &boolean_words, "Use TRUE/FALSE in Boolean fields (default is 0/1)", NULL},
{"batch-size", 'S', 0, G_OPTION_ARG_INT, &batch_size, "Size of insert batches on supported platforms.", "int"},
{NULL},
};
GError *error = NULL;