Import_Export


Data Structures

struct  _accountpickerdialog
struct  _transactioninfo
struct  _matchinfo
struct  _main_matcher_info
struct  _GncImportMatchMap
struct  account_token_count
struct  token_accounts_info
struct  account_probability
struct  account_info
struct  _transpickerdialog
struct  _genimportsettings
struct  _split_record

Modules

 Export a chart of accounts.
 AqBanking

Files

file  import-account-matcher.h
 Generic and very flexible account matcher/picker.
file  import-backend.h
 Generic importer backend interface.
file  import-commodity-matcher.h
 A Generic commodity matcher/picker.
file  import-main-matcher.h
 Transaction matcher main window.
file  import-match-map.h
 Generic import mapper service, maps strings->accounts.
file  import-match-picker.h
 The transaction match picker dialog interface.
file  import-settings.h
 Import preference handling. User preference interface for transaction matching (for both the gui and the backend).
file  import-utilities.h
 Utility functions for writing import modules.

Defines

#define GCONF_SECTION   "dialogs/import/generic_matcher/account_matcher"
#define GCONF_SECTION   "dialogs/import/generic_matcher"
#define BAYES_OPTION   "use_bayes"
#define GCONF_SECTION   "dialogs/import/generic_matcher/transaction_list"
#define COLOR_RED   "brown1"
#define COLOR_YELLOW   "gold"
#define COLOR_GREEN   "DarkSeaGreen1"
#define IMAP_FRAME   "import-map"
#define IMAP_FRAME_BAYES   "import-map-bayes"
#define PROBABILITY_FACTOR   100000
#define threshold   (.90 * PROBABILITY_FACTOR)
#define GCONF_SECTION   "dialogs/import/generic_matcher/match_picker"
#define GCONF_SECTION   "dialogs/import/generic_matcher"
#define GCONF_SECTION   "dialogs/log_replay"
#define STRING_FIELD_SIZE   256
#define GCONF_SECTION   "dialogs/import/ofx"

Typedefs

typedef struct _transactioninfo GNCImportTransInfo
typedef struct _matchinfo GNCImportMatchInfo
typedef enum _action GNCImportAction
typedef struct _main_matcher_info GNCImportMainMatcher
typedef struct _GncImportMatchMap GncImportMatchMap
typedef struct _transpickerdialog GNCImportMatchPicker
typedef struct _genimportsettings GNCImportSettings
typedef struct _split_record split_record

Enumerations

enum  _action {
  GNCImport_SKIP, GNCImport_ADD, GNCImport_CLEAR, GNCImport_EDIT,
  GNCImport_LAST_ACTION, GNCImport_INVALID_ACTION
}
enum  downloaded_cols {
  DOWNLOADED_COL_DATE = 0, DOWNLOADED_COL_ACCOUNT, DOWNLOADED_COL_AMOUNT, DOWNLOADED_COL_DESCRIPTION,
  DOWNLOADED_COL_MEMO, DOWNLOADED_COL_ACTION_ADD, DOWNLOADED_COL_ACTION_CLEAR, DOWNLOADED_COL_ACTION_EDIT,
  DOWNLOADED_COL_ACTION_INFO, DOWNLOADED_COL_ACTION_PIXBUF, DOWNLOADED_COL_DATA, DOWNLOADED_COL_COLOR,
  NUM_DOWNLOADED_COLS, DOWNLOADED_COL_ACCOUNT = 0, DOWNLOADED_COL_DATE, DOWNLOADED_COL_AMOUNT,
  DOWNLOADED_COL_DESCRIPTION, DOWNLOADED_COL_MEMO, DOWNLOADED_COL_BALANCED, DOWNLOADED_COL_INFO_PTR,
  NUM_DOWNLOADED_COLS
}
enum  downloaded_cols {
  DOWNLOADED_COL_DATE = 0, DOWNLOADED_COL_ACCOUNT, DOWNLOADED_COL_AMOUNT, DOWNLOADED_COL_DESCRIPTION,
  DOWNLOADED_COL_MEMO, DOWNLOADED_COL_ACTION_ADD, DOWNLOADED_COL_ACTION_CLEAR, DOWNLOADED_COL_ACTION_EDIT,
  DOWNLOADED_COL_ACTION_INFO, DOWNLOADED_COL_ACTION_PIXBUF, DOWNLOADED_COL_DATA, DOWNLOADED_COL_COLOR,
  NUM_DOWNLOADED_COLS, DOWNLOADED_COL_ACCOUNT = 0, DOWNLOADED_COL_DATE, DOWNLOADED_COL_AMOUNT,
  DOWNLOADED_COL_DESCRIPTION, DOWNLOADED_COL_MEMO, DOWNLOADED_COL_BALANCED, DOWNLOADED_COL_INFO_PTR,
  NUM_DOWNLOADED_COLS
}
enum  matcher_cols {
  MATCHER_COL_CONFIDENCE = 0, MATCHER_COL_CONFIDENCE_PIXBUF, MATCHER_COL_DATE, MATCHER_COL_AMOUNT,
  MATCHER_COL_DESCRIPTION, MATCHER_COL_MEMO, MATCHER_COL_INFO_PTR, NUM_MATCHER_COLS
}

Functions

char * libgncmod_csv_gnc_module_path (void)
char * libgncmod_csv_gnc_module_description (void)
int libgncmod_csv_gnc_module_init (int refcount)
int libgncmod_csv_gnc_module_end (int refcount)
void gnc_file_aqbanking_import (const gchar *aqbanking_importername, const gchar *aqbanking_profilename, gboolean execute_transactions)
Accountgnc_import_select_account (gncUIWidget parent, const gchar *account_online_id_value, gboolean auto_create, const gchar *account_human_description, gnc_commodity *new_account_default_commodity, GNCAccountType new_account_default_type, Account *default_selection, gboolean *ok_pressed)
gnc_commoditygnc_import_select_commodity (char *cusip, char auto_create, char *default_fullname, char *default_mnemonic)
void gnc_gen_trans_list_delete (GNCImportMainMatcher *info)
GNCImportMainMatcher * gnc_gen_trans_list_new (GtkWidget *parent, const gchar *heading, gboolean all_from_same_account, gint match_date_hardlimit)
gboolean gnc_gen_trans_list_run (GNCImportMainMatcher *info)
void gnc_gen_trans_list_add_trans (GNCImportMainMatcher *gui, Transaction *trans)
void gnc_imap_destroy (GncImportMatchMap *imap)
void gnc_imap_clear (GncImportMatchMap *imap)
Accountgnc_imap_find_account (GncImportMatchMap *imap, const char *category, const char *key)
void gnc_imap_add_account (GncImportMatchMap *imap, const char *category, const char *key, Account *acc)
Accountgnc_imap_find_account_bayes (GncImportMatchMap *imap, GList *tokens)
void gnc_imap_add_account_bayes (GncImportMatchMap *imap, GList *tokens, Account *acc)
void gnc_import_match_picker_run_and_close (GNCImportTransInfo *transaction_info)
GNCImportSettings * gnc_import_Settings_new (void)
void gnc_import_Settings_delete (GNCImportSettings *settings)
gboolean gnc_import_trans_has_online_id (Transaction *transaction)
gboolean gnc_import_split_has_online_id (Split *split)
void gnc_file_log_replay (void)
char * libgncmod_log_replay_gnc_module_path (void)
char * libgncmod_log_replay_gnc_module_description (void)
int libgncmod_log_replay_gnc_module_init (int refcount)
int libgncmod_log_replay_gnc_module_end (int refcount)
int ofx_proc_security_cb (const struct OfxSecurityData data, void *security_user_data)
int ofx_proc_transaction_cb (struct OfxTransactionData data, void *transaction_user_data)
int ofx_proc_account_cb (struct OfxAccountData data, void *account_user_data)
double ofx_get_investment_amount (struct OfxTransactionData data)
void gnc_file_ofx_import (void)
char * libgncmod_ofx_gnc_module_path (void)
char * libgncmod_ofx_gnc_module_description (void)
int libgncmod_ofx_gnc_module_init (int refcount)
int libgncmod_ofx_gnc_module_end (int refcount)

Variables

int libgncmod_csv_gnc_module_system_interface = 0
int libgncmod_csv_gnc_module_current = 0
int libgncmod_csv_gnc_module_revision = 0
int libgncmod_csv_gnc_module_age = 0
int libgncmod_log_replay_gnc_module_system_interface = 0
int libgncmod_log_replay_gnc_module_current = 0
int libgncmod_log_replay_gnc_module_revision = 0
int libgncmod_log_replay_gnc_module_age = 0
GNCImportMainMatcher * gnc_ofx_importer_gui = NULL
int libgncmod_ofx_gnc_module_system_interface = 0
int libgncmod_ofx_gnc_module_current = 0
int libgncmod_ofx_gnc_module_revision = 0
int libgncmod_ofx_gnc_module_age = 0

Define Documentation

#define PROBABILITY_FACTOR   100000

convert a hash table of account names and (struct account_probability*) into a hash table of 100000x the percentage match value, ie. 10% would be 0.10 * 100000 = 10000

Definition at line 226 of file import-match-map.c.


Function Documentation

GdkPixbuf * gen_probability_pixbuf ( gint  score,
GNCImportSettings *  settings,
GtkWidget *  widget 
)

This function generates a new pixmap representing a match score. It is a series of vertical bars of different colors. -Below or at the add_threshold the bars are red -Above or at the clear_threshold the bars are green -Between the two threshold the bars are yellow

Parameters:
score The score for which to generate a pixmap.
settings The user settings from which to get the threshold
widget The parent widget in which the pixmap will eventually be added. Will be used to generate the colormap.

Definition at line 260 of file import-backend.c.

00261 {
00262     GdkPixbuf* retval = NULL;
00263     gint i, j;
00264     gint score;
00265     const gint height = 15;
00266     const gint width_each_bar = 7;
00267     gchar * green_bar = ("bggggb ");
00268     gchar * yellow_bar = ("byyyyb ");
00269     gchar * red_bar = ("brrrrb ");
00270     gchar * black_bar = ("bbbbbb ");
00271     const gint width_first_bar = 1;
00272     gchar * black_first_bar = ("b");
00273     const gint num_colors = 5;
00274     gchar * size_str;
00275     gchar * none_color_str = g_strdup_printf("  c None");
00276     gchar * green_color_str = g_strdup_printf("g c green");
00277     gchar * yellow_color_str = g_strdup_printf("y c yellow");
00278     gchar * red_color_str = g_strdup_printf("r c red");
00279     gchar * black_color_str = g_strdup_printf("b c black");
00280     gchar * xpm[2+num_colors+height];
00281     gint add_threshold, clear_threshold;
00282 
00283     g_assert(settings);
00284     g_assert(widget);
00285     if (score_original < 0)
00286     {
00287         score = 0;
00288     }
00289     else
00290     {
00291         score = score_original;
00292     }
00293     size_str = g_strdup_printf("%d%s%d%s%d%s", (width_each_bar * score) + width_first_bar/*width*/, " ", height, " ", num_colors, " 1"/*characters per pixel*/);
00294 
00295     /*DEBUG("Begin");*/
00296     xpm[0] = size_str;
00297     xpm[1] = none_color_str;
00298     xpm[2] = green_color_str;
00299     xpm[3] = yellow_color_str;
00300     xpm[4] = red_color_str;
00301     xpm[5] = black_color_str;
00302     add_threshold = gnc_import_Settings_get_add_threshold(settings);
00303     clear_threshold = gnc_import_Settings_get_clear_threshold(settings);
00304 
00305     for (i = 0; i < height; i++)
00306     {
00307         xpm[num_colors+1+i] = g_new0(char, (width_each_bar * score) + width_first_bar + 1);
00308         for (j = 0; j <= score; j++)
00309         {
00310             if (i == 0 || i == height - 1)
00311             {
00312                 if (j == 0)
00313                 {
00314                     strcat(xpm[num_colors+1+i], black_first_bar);
00315                 }
00316                 else
00317                 {
00318                     strcat(xpm[num_colors+1+i], black_bar);
00319                 }
00320             }
00321             else
00322             {
00323                 if (j == 0)
00324                 {
00325                     strcat(xpm[num_colors+1+i], black_first_bar);
00326                 }
00327                 else if (j <= add_threshold)
00328                 {
00329                     strcat(xpm[num_colors+1+i], red_bar);
00330                 }
00331                 else if (j >= clear_threshold)
00332                 {
00333                     strcat(xpm[num_colors+1+i], green_bar);
00334                 }
00335                 else
00336                 {
00337                     strcat(xpm[num_colors+1+i], yellow_bar);
00338                 }
00339             }
00340         }
00341     }
00342 
00343     retval =  gdk_pixbuf_new_from_xpm_data((const gchar **)xpm);
00344     for (i = 0; i <= num_colors + height; i++)
00345     {
00346         /*DEBUG("free_loop i=%d%s%s",i,": ",xpm[i]);*/
00347         g_free(xpm[i]);
00348     }
00349 
00350     return retval;
00351 }

void gnc_file_aqbanking_import ( const gchar *  aqbanking_importername,
const gchar *  aqbanking_formatname,
gboolean  exec_as_aqbanking_jobs 
)

This routine will pop up a standard file selection dialog asking the user to pick a file to import. This file will be opened and read. Its contents will be imported into the current book, using the import matcher from import-main-matcher.h.

Parameters:
aqbanking_importername The aqbanking importer module that should be used. Possible values: "dtaus", "csv", "swift", or more.
aqbanking_formatname In aqbanking, each importer has one or more data formats available which define the actual data fields that should be used. In aqbanking, such a different format is called a "profile". Possible values for swift: "swift-mt940" or "swift-mt942", but for all others: "default", or more precisely: Look into $datadir/aqbanking/imexporters and look into the "name" field of the foo.conf files.
exec_as_aqbanking_jobs If TRUE, additionally queue the imported transactions as online jobs over aqbanking/HBCI. If FALSE, just import the transactions and that's it.

Definition at line 65 of file hbci/gnc-file-aqb-import.c.

00068 {
00069     char *selected_filename;
00070     char *default_dir;
00071     int dtaus_fd;
00072 
00073     DEBUG("gnc_file_dtaus_import(): Begin...\n");
00074 
00075     default_dir = gnc_get_default_directory(GCONF_SECTION);
00076     selected_filename = gnc_file_dialog(_("Select a file to import"),
00077                                         NULL,
00078                                         default_dir,
00079                                         GNC_FILE_DIALOG_IMPORT);
00080     g_free(default_dir);
00081 
00082     if (selected_filename != NULL)
00083     {
00084         /* Remember the directory as the default. */
00085         default_dir = g_path_get_dirname(selected_filename);
00086         gnc_set_default_directory(GCONF_SECTION, default_dir);
00087         g_free(default_dir);
00088 
00089         /*strncpy(file,selected_filename, 255);*/
00090         DEBUG("Filename found: %s", selected_filename);
00091 
00092         DEBUG("Opening selected file");
00093         dtaus_fd = g_open(selected_filename, O_RDONLY, 0);
00094         if (dtaus_fd == -1)
00095         {
00096             DEBUG("Could not open file %s", selected_filename);
00097             return;
00098         }
00099         g_free(selected_filename);
00100 
00101         {
00102             int result;
00103             AB_BANKING *ab;
00104             AB_IMEXPORTER *importer;
00105             AB_IMEXPORTER_CONTEXT *ctx = 0;
00106             GWEN_BUFFEREDIO *buffio;
00107             GWEN_DB_NODE *dbProfiles;
00108             GWEN_DB_NODE *dbProfile;
00109             GNCInteractor *interactor = NULL;
00110             const char *importerName = aqbanking_importername;
00111             const char *profileName = aqbanking_profilename;
00112 
00113             /* Get API */
00114             ab = gnc_AB_BANKING_new_currentbook (NULL, &interactor);
00115             if (ab == NULL)
00116             {
00117                 g_message("gnc_file_dtaus_import: Couldn't get HBCI API. Nothing will happen.\n");
00118                 return;
00119             }
00120             g_assert (interactor);
00121 
00122             /* get import module */
00123             importer = AB_Banking_GetImExporter(ab, importerName);
00124             if (!importer)
00125             {
00126                 DEBUG("Import module %s not found", importerName);
00127                 gnc_error_dialog(NULL, "%s", ("Import module for DTAUS import not found."));
00128                 return;
00129             }
00130             g_assert(importer);
00131 
00132             /* load the import profile */
00133             dbProfiles = AB_Banking_GetImExporterProfiles(ab, importerName);
00134 
00135             /* select profile */
00136             dbProfile = GWEN_DB_GetFirstGroup(dbProfiles);
00137             while (dbProfile)
00138             {
00139                 const char *name;
00140 
00141                 name = GWEN_DB_GetCharValue(dbProfile, "name", 0, 0);
00142                 g_assert(name);
00143                 if (strcasecmp(name, profileName) == 0)
00144                     break;
00145                 dbProfile = GWEN_DB_GetNextGroup(dbProfile);
00146             }
00147             if (!dbProfile)
00148             {
00149                 g_warning("Profile \"%s\" for importer \"%s\" not found\n",
00150                           profileName, importerName);
00151                 /* For debugging: Print those available names that have been found. */
00152                 dbProfile = GWEN_DB_GetFirstGroup(dbProfiles);
00153                 while (dbProfile)
00154                 {
00155                     const char *name;
00156                     name = GWEN_DB_GetCharValue(dbProfile, "name", 0, 0);
00157                     g_assert(name);
00158                     g_warning("Only found profile \"%s\"\n", name);
00159                     dbProfile = GWEN_DB_GetNextGroup(dbProfile);
00160                 }
00161                 return;
00162             }
00163             g_assert(dbProfile);
00164 
00165             /* import new context */
00166             ctx = AB_ImExporterContext_new();
00167             g_assert(ctx);
00168 
00169             /* Wrap file in gwen_bufferedio */
00170             buffio = GWEN_BufferedIO_File_new(dtaus_fd);
00171             g_assert(buffio);
00172             GWEN_BufferedIO_SetReadBuffer(buffio, 0, 1024);
00173 
00174             result = AB_ImExporter_Import(importer,
00175                                           ctx,
00176                                           buffio,
00177                                           dbProfile);
00178 
00179             DEBUG("Parsing result: %d\n", result);
00180 
00181             GWEN_BufferedIO_Close(buffio);
00182             GWEN_BufferedIO_free(buffio);
00183             GWEN_DB_Group_free(dbProfiles);
00184 
00185             {
00186                 /* Now get all accountinfos */
00187                 GNCImportMainMatcher *importer_generic_gui;
00188                 GtkWidget *parent = NULL;
00189                 gboolean successful = FALSE;
00190                 GList *ab_job_list;
00191 
00192                 /* Create importer GUI */
00193                 importer_generic_gui = gnc_gen_trans_list_new(parent, NULL, TRUE, 14);
00194 
00195                 /* Import the transactions from the ctx into gnucash. */
00196                 ab_job_list = gnc_hbci_import_ctx(ab, ctx, importer_generic_gui,
00197                                                   execute_transactions);
00198                 /* Finished importing. */
00199 
00200                 /* We clean up here. */
00201                 AB_ImExporterContext_free(ctx);
00202 
00203                 if (execute_transactions)
00204                 {
00205                     /* Wait for the gnucash importer to be finished (it is being
00206                        run anyway). */
00207                     result = gnc_gen_trans_list_run (importer_generic_gui);
00208 
00209                     if (result)
00210                         /* Execute these jobs now. This function already delete()s the
00211                            job. */
00212                         /* no parent so far; otherwise add this: GNCInteractor_reparent (interactor, parent); */
00213                         successful = gnc_hbci_multijob_execute (parent, ab, ab_job_list, interactor);
00214                     /* else */
00215 
00216                     /* Delete all jobs from queue in any case. */
00217                     gnc_hbci_clearqueue (ab, ab_job_list);
00218                 }
00219                 else
00220                 {
00221                     successful = TRUE;
00222                 }
00223 
00224                 if (successful)
00225                 {
00226                     /* If execution was not successful, leave the log window
00227                        still intact and open. */
00228                     gnc_AB_BANKING_fini (ab);
00229                     gnc_AB_BANKING_delete (ab);
00230                 }
00231             }
00232         }
00233     }
00234 }

void gnc_file_log_replay ( void   ) 

The gnc_file_log_replay() routine will pop up a standard file selection dialogue asking the user to pick a log file to replay. If one is selected the the .log file is opened and read. It's contents are then silently merged in the current log file.

Definition at line 506 of file gnc-log-replay.c.

00507 {
00508     char *selected_filename;
00509     char *default_dir;
00510     char read_buf[256];
00511     char *read_retval;
00512     GtkFileFilter *filter;
00513     FILE *log_file;
00514     char * record_start_str = "===== START";
00515     /* NOTE: This string must match src/engine/TransLog.c (sans newline) */
00516     char * expected_header_orig = "mod\ttrans_guid\tsplit_guid\ttime_now\t"
00517                                   "date_entered\tdate_posted\tacc_guid\tacc_name\tnum\tdescription\t"
00518                                   "notes\tmemo\taction\treconciled\tamount\tvalue\tdate_reconciled";
00519     static char *expected_header = NULL;
00520 
00521     /* Use g_strdup_printf so we don't get accidental tab -> space conversion */
00522     if (!expected_header)
00523         expected_header = g_strdup(expected_header_orig);
00524 
00525     qof_log_set_level(GNC_MOD_IMPORT, QOF_LOG_DEBUG);
00526     ENTER(" ");
00527 
00528     default_dir = gnc_get_default_directory(GCONF_SECTION);
00529 
00530     filter = gtk_file_filter_new();
00531     gtk_file_filter_set_name(filter, "*.log");
00532     gtk_file_filter_add_pattern(filter, "*.[Ll][Oo][Gg]");
00533     selected_filename = gnc_file_dialog(_("Select a .log file to replay"),
00534                                         g_list_prepend(NULL, filter),
00535                                         default_dir,
00536                                         GNC_FILE_DIALOG_OPEN);
00537     g_free(default_dir);
00538 
00539     if (selected_filename != NULL)
00540     {
00541         /* Remember the directory as the default. */
00542         default_dir = g_path_get_dirname(selected_filename);
00543         gnc_set_default_directory(GCONF_SECTION, default_dir);
00544         g_free(default_dir);
00545 
00546         /*strncpy(file,selected_filename, 255);*/
00547         DEBUG("Filename found: %s", selected_filename);
00548         if (xaccFileIsCurrentLog(selected_filename))
00549         {
00550             g_warning("Cannot open the current log file: %s", selected_filename);
00551             gnc_error_dialog(NULL,
00552                              /* Translators: %s is the file name. */
00553                              _("Cannot open the current log file: %s"),
00554                              selected_filename);
00555         }
00556         else
00557         {
00558             DEBUG("Opening selected file");
00559             log_file = g_fopen(selected_filename, "r");
00560             if (!log_file || ferror(log_file) != 0)
00561             {
00562                 int err = errno;
00563                 perror("File open failed");
00564                 gnc_error_dialog(NULL,
00565                                  /* Translation note:
00566                                   * First argument is the filename,
00567                                   * second argument is the error.
00568                                   */
00569                                  _("Failed to open log file: %s: %s"),
00570                                  selected_filename,
00571                                  strerror(err));
00572             }
00573             else
00574             {
00575                 if ((read_retval = fgets(read_buf, sizeof(read_buf), log_file)) == NULL)
00576                 {
00577                     DEBUG("Read error or EOF");
00578                     gnc_info_dialog(NULL, "%s",
00579                                     _("The log file you selected was empty."));
00580                 }
00581                 else
00582                 {
00583                     if (strncmp(expected_header, read_buf, strlen(expected_header)) != 0)
00584                     {
00585                         PERR("File header not recognised:\n%s", read_buf);
00586                         PERR("Expected:\n%s", expected_header);
00587                         gnc_error_dialog(NULL, "%s",
00588                                          _("The log file you selected cannot be read.  "
00589                                            "The file header was not recognized."));
00590                     }
00591                     else
00592                     {
00593                         do
00594                         {
00595                             read_retval = fgets(read_buf, sizeof(read_buf), log_file);
00596                             /*DEBUG("Chunk read: %s",read_retval);*/
00597                             if (strncmp(record_start_str, read_buf, strlen(record_start_str)) == 0) /* If a record started */
00598                             {
00599                                 process_trans_record(log_file);
00600                             }
00601                         }
00602                         while (feof(log_file) == 0);
00603                     }
00604                 }
00605                 fclose(log_file);
00606             }
00607         }
00608         g_free(selected_filename);
00609     }
00610     LEAVE("");
00611 }

void gnc_file_ofx_import ( void   ) 

The gnc_file_ofx_import() routine will pop up a standard file selection dialogue asking the user to pick a OFX/QFX file. If one is selected the the OFX file is opened and read. It's contents are merged into the existing session (if any). The current session continues to remain open for editing.

Definition at line 725 of file gnc-ofx-import.c.

00726 {
00727     extern int ofx_PARSER_msg;
00728     extern int ofx_DEBUG_msg;
00729     extern int ofx_WARNING_msg;
00730     extern int ofx_ERROR_msg;
00731     extern int ofx_INFO_msg;
00732     extern int ofx_STATUS_msg;
00733     char *selected_filename;
00734     char *default_dir;
00735     LibofxContextPtr libofx_context = libofx_get_new_context();
00736 
00737     ofx_PARSER_msg = false;
00738     ofx_DEBUG_msg = false;
00739     ofx_WARNING_msg = true;
00740     ofx_ERROR_msg = true;
00741     ofx_INFO_msg = true;
00742     ofx_STATUS_msg = false;
00743 
00744     DEBUG("gnc_file_ofx_import(): Begin...\n");
00745 
00746     default_dir = gnc_get_default_directory(GCONF_SECTION);
00747     selected_filename = gnc_file_dialog(_("Select an OFX/QFX file to process"),
00748                                         NULL,
00749                                         default_dir,
00750                                         GNC_FILE_DIALOG_IMPORT);
00751     g_free(default_dir);
00752 
00753     if (selected_filename != NULL)
00754     {
00755 #ifdef G_OS_WIN32
00756         gchar *conv_name;
00757 #endif
00758 
00759         /* Remember the directory as the default. */
00760         default_dir = g_path_get_dirname(selected_filename);
00761         gnc_set_default_directory(GCONF_SECTION, default_dir);
00762         g_free(default_dir);
00763 
00764         /*strncpy(file,selected_filename, 255);*/
00765         DEBUG("Filename found: %s", selected_filename);
00766 
00767         /* Create the Generic transaction importer GUI. */
00768         gnc_ofx_importer_gui = gnc_gen_trans_list_new(NULL, NULL, FALSE, 42);
00769 
00770         /* Initialize libofx */
00771 
00772         /*ofx_set_statement_cb(libofx_context, ofx_proc_statement_cb, 0);*/
00773         ofx_set_account_cb(libofx_context, ofx_proc_account_cb, 0);
00774         ofx_set_transaction_cb(libofx_context, ofx_proc_transaction_cb, 0);
00775         ofx_set_security_cb(libofx_context, ofx_proc_security_cb, 0);
00776         /*ofx_set_status_cb(libofx_context, ofx_proc_status_cb, 0);*/
00777 
00778 #ifdef G_OS_WIN32
00779         conv_name = g_win32_locale_filename_from_utf8(selected_filename);
00780         g_free(selected_filename);
00781         selected_filename = conv_name;
00782 #endif
00783 
00784         DEBUG("Opening selected file");
00785         libofx_proc_file(libofx_context, selected_filename, AUTODETECT);
00786         g_free(selected_filename);
00787     }
00788 
00789 }

void gnc_gen_trans_list_add_trans ( GNCImportMainMatcher *  gui,
Transaction trans 
)

Add a newly imported Transaction to the Transaction Importer. The Importer takes over ownership of the passed transaction.

Parameters:
gui The Transaction Importer to use.
trans The Transaction to add. The must contain at least one split, and this split must have been associated with an account Only the first split will be used for matching. The transaction must NOT be commited. The Importer takes over ownership of the passed transaction.

Definition at line 753 of file import-main-matcher.c.

00754 {
00755     GNCImportTransInfo * transaction_info = NULL;
00756     GtkTreeModel *model;
00757     GtkTreeIter iter;
00758     g_assert (gui);
00759     g_assert (trans);
00760 
00761 
00762     if (gnc_import_exists_online_id (trans))
00763         return;
00764     else
00765     {
00766         transaction_info = gnc_import_TransInfo_new(trans, NULL);
00767 
00768         gnc_import_TransInfo_init_matches (transaction_info,
00769                                            gui->user_settings);
00770 
00771         model = gtk_tree_view_get_model(gui->view);
00772         gtk_list_store_append(GTK_LIST_STORE(model), &iter);
00773         refresh_model_row (gui, model, &iter, transaction_info);
00774     }
00775     return;
00776 }/* end gnc_import_add_trans() */

void gnc_gen_trans_list_delete ( GNCImportMainMatcher *  info  ) 

Deletes the given object.

Definition at line 91 of file import-main-matcher.c.

00092 {
00093     GtkTreeModel *model;
00094     GtkTreeIter iter;
00095     GNCImportTransInfo *trans_info;
00096 
00097     if (info == NULL)
00098         return;
00099 
00100     model = gtk_tree_view_get_model(info->view);
00101     if (gtk_tree_model_get_iter_first(model, &iter))
00102     {
00103         do
00104         {
00105             gtk_tree_model_get(model, &iter,
00106                                DOWNLOADED_COL_DATA, &trans_info,
00107                                -1);
00108             gnc_import_TransInfo_delete(trans_info);
00109         }
00110         while (gtk_tree_model_iter_next (model, &iter));
00111     }
00112 
00113     gnc_save_window_size(GCONF_SECTION, GTK_WINDOW(info->dialog));
00114     gnc_import_Settings_delete (info->user_settings);
00115     gtk_widget_destroy (GTK_WIDGET (info->dialog));
00116     g_free (info);
00117 }

GNCImportMainMatcher * gnc_gen_trans_list_new ( GtkWidget *  parent,
const gchar *  heading,
gboolean  all_from_same_account,
gint  match_date_hardlimit 
)

Create a new generic transaction dialog window and return it.

Parameters:
parent The parent GtkWidget. May be NULL.
heading The heading label in the Importer window. May be NULL.
all_from_same_account Set this to TRUE if ALL the transaction that will be added with gnc_gen_trans_list_add_trans are from the same source account. This will cause the account column to be hidden.
match_date_hardlimit The number of days that a matching split may differ from the given transaction before it is discarded immediately. In other words, any split that is more distant from the given transaction than this match_date_hardlimit days will be ignored altogether. For use cases without paper checks (e.g. HBCI), values like 14 (days) might be appropriate, whereas for use cases with paper checks (e.g. OFX, QIF), values like 42 (days) seem more appropriate.

Definition at line 493 of file import-main-matcher.c.

00497 {
00498     GNCImportMainMatcher *info;
00499     GladeXML *xml;
00500     GtkWidget *heading_label;
00501     gboolean show_edit;
00502 
00503     info = g_new0 (GNCImportMainMatcher, 1);
00504 
00505     /* Initialize user Settings. */
00506     info->user_settings = gnc_import_Settings_new ();
00507     gnc_import_Settings_set_match_date_hardlimit (info->user_settings, match_date_hardlimit);
00508 
00509     /* Initialize the GtkDialog. */
00510     xml = gnc_glade_xml_new ("generic-import.glade", "transaction_matcher");
00511 
00512     info->dialog = glade_xml_get_widget (xml, "transaction_matcher");
00513     g_assert (info->dialog != NULL);
00514     info->view = GTK_TREE_VIEW(glade_xml_get_widget (xml, "downloaded_view"));
00515     g_assert (info->view != NULL);
00516 
00517     show_edit = gnc_import_Settings_get_action_edit_enabled (info->user_settings);
00518     gnc_gen_trans_init_view(info, all_from_same_account, show_edit);
00519     heading_label = glade_xml_get_widget (xml, "heading_label");
00520     g_assert (heading_label != NULL);
00521 
00522     /* if (parent)
00523       gtk_window_set_transient_for (GTK_WINDOW (info->dialog),
00524                           GTK_WINDOW (parent));*/
00525 
00526     /* Connect signals */
00527     glade_xml_signal_connect_data(xml, "on_matcher_ok_clicked",
00528                                   G_CALLBACK(on_matcher_ok_clicked),
00529                                   info);
00530     glade_xml_signal_connect_data(xml, "on_matcher_cancel_clicked",
00531                                   G_CALLBACK(on_matcher_cancel_clicked),
00532                                   info);
00533     glade_xml_signal_connect_data(xml, "on_matcher_help_clicked",
00534                                   G_CALLBACK(on_matcher_help_clicked),
00535                                   info);
00536 
00537     /*Initialise the colors */
00538     gdk_color_parse(COLOR_RED,    &info->color_back_red);
00539     gdk_color_parse(COLOR_YELLOW, &info->color_back_yellow);
00540     gdk_color_parse(COLOR_GREEN,  &info->color_back_green);
00541 
00542     if (heading)
00543         gtk_label_set_text (GTK_LABEL (heading_label), heading);
00544 
00545     gnc_restore_window_size(GCONF_SECTION, GTK_WINDOW(info->dialog));
00546     gtk_widget_show_all (GTK_WIDGET (info->dialog));
00547     return info;
00548 }

gboolean gnc_gen_trans_list_run ( GNCImportMainMatcher *  info  ) 

Run this dialog and return only after the user pressed Ok, Cancel, or closed the window. This means that all actual importing will have been finished upon returning.

Definition at line 550 of file import-main-matcher.c.

00551 {
00552     gboolean result;
00553 
00554     /* DEBUG("Begin"); */
00555 
00556     result = gtk_dialog_run (GTK_DIALOG (info->dialog));
00557 
00558     /* DEBUG("Result was %d", result); */
00559 
00560     /* No destroying here since the dialog was already destroyed through
00561        the ok_clicked handlers. */
00562     return result;
00563 }

void gnc_imap_add_account ( GncImportMatchMap *  imap,
const char *  category,
const char *  key,
Account acc 
)

Store an Account in the map

Store an Account in the map. This mapping is immediatly stored in the underlying kvp frame, regardless of whether the MatchMap is destroyed later or not.

Definition at line 142 of file import-match-map.c.

00144 {
00145     kvp_value *value;
00146 
00147     if (!imap || !key || !acc || (strlen (key) == 0)) return;
00148     if (!category)
00149     {
00150         category = key;
00151         key = NULL;
00152     }
00153 
00154     value = kvp_value_new_guid (xaccAccountGetGUID (acc));
00155     g_return_if_fail (value != NULL);
00156 
00157     kvp_frame_set_slot_path (imap->frame, value, IMAP_FRAME, category, key, NULL);
00158     kvp_value_delete (value);
00159 
00160     /* XXX Mark the account (or book) as dirty! */
00161 }

void gnc_imap_add_account_bayes ( GncImportMatchMap *  imap,
GList *  tokens,
Account acc 
)

Updates the imap for a given account using a list of tokens

Store an Account in the map. This mapping is immediatly stored in the underlying kvp frame, regardless of whether the MatchMap is destroyed later or not.

Definition at line 461 of file import-match-map.c.

00462 {
00463     GList *current_token;
00464     kvp_value *value;
00465     gint64 token_count;
00466     char* account_fullname;
00467     kvp_value *new_value; /* the value that will be added back into the kvp tree */
00468 
00469     ENTER(" ");
00470 
00471     /* if imap is null return */
00472     if (!imap)
00473     {
00474         LEAVE(" ");
00475         return;
00476     }
00477 
00478     account_fullname = gnc_account_get_full_name(acc);
00479 
00480     PINFO("account name: '%s'\n", account_fullname);
00481 
00482     /* process each token in the list */
00483     for (current_token = g_list_first(tokens); current_token;
00484             current_token = current_token->next)
00485     {
00486         /* Jump to next iteration if the pointer is not valid or if the
00487                  string is empty. In HBCI import we almost always get an empty
00488                  string, which doesn't work in the kvp loopkup later. So we
00489                  skip this case here. */
00490         if (!current_token->data || (*((char*)current_token->data) == '\0'))
00491             continue;
00492 
00493         /* start off with no tokens for this account */
00494         token_count = 0;
00495 
00496         PINFO("adding token '%s'\n", (char*)current_token->data);
00497 
00498         /* is this token/account_name already in the kvp tree? */
00499         value = kvp_frame_get_slot_path(imap->frame, IMAP_FRAME_BAYES,
00500                                         (char*)current_token->data, account_fullname,
00501                                         NULL);
00502 
00503         /* if the token/account is already in the tree, read the current
00504          * value from the tree and use this for the basis of the value we
00505          * are putting back
00506          */
00507         if (value)
00508         {
00509             PINFO("found existing value of '%ld'\n",
00510                   (long)kvp_value_get_gint64(value));
00511 
00512             /* convert this value back into an integer */
00513             token_count += kvp_value_get_gint64(value);
00514         }
00515 
00516         /* increment the token count */
00517         token_count++;
00518 
00519         /* create a new value */
00520         new_value = kvp_value_new_gint64(token_count);
00521 
00522         /* insert the value into the kvp tree at
00523          * /imap->frame/IMAP_FRAME/token_string/account_name_string
00524          */
00525         kvp_frame_set_slot_path(imap->frame, new_value, IMAP_FRAME_BAYES,
00526                                 (char*)current_token->data, account_fullname, NULL);
00527 
00528         /* kvp_frame_set_slot_path() copied the value so we
00529          * need to delete this one ;-) */
00530         kvp_value_delete(new_value);
00531     }
00532 
00533     /* free up the account fullname string */
00534     g_free(account_fullname);
00535 
00536     LEAVE(" ");
00537 }

void gnc_imap_clear ( GncImportMatchMap *  imap  ) 

Clear an import map -- this removes ALL entries in the map

Definition at line 107 of file import-match-map.c.

00108 {
00109     if (!imap) return;
00110 
00111     /* Clear the IMAP_FRAME kvp */
00112     kvp_frame_set_slot_path (imap->frame, NULL, IMAP_FRAME);
00113 
00114     /* Clear the bayes kvp, IMAP_FRAME_BAYES */
00115     kvp_frame_set_slot_path (imap->frame, NULL, IMAP_FRAME_BAYES);
00116 
00117     /* XXX: mark the account (or book) as dirty! */
00118 }

GncImportMatchMap * gnc_imap_create_from_account ( Account acc  ) 

Obtain an ImportMatchMap object from an Account or a Book

Obtain an ImportMatchMap object from an Account or a Book

Definition at line 77 of file import-match-map.c.

00078 {
00079     kvp_frame * frame;
00080 
00081     if (!acc) return NULL;
00082     frame = xaccAccountGetSlots (acc);
00083     g_return_val_if_fail (frame != NULL, NULL);
00084 
00085     return gnc_imap_create_from_frame (frame, acc, NULL);
00086 }

void gnc_imap_destroy ( GncImportMatchMap *  imap  ) 

Destroy an import map

Destroy an import map. But all stored entries will still continue to exist in the underlying kvp frame of the account or book.

Definition at line 100 of file import-match-map.c.

00101 {
00102     if (!imap) return;
00103     g_free (imap);
00104 }

Account * gnc_imap_find_account ( GncImportMatchMap *  imap,
const char *  category,
const char *  key 
)

Look up an Account in the map

Definition at line 121 of file import-match-map.c.

00123 {
00124     kvp_value *value;
00125     GUID * guid;
00126 
00127     if (!imap || !key) return NULL;
00128     if (!category)
00129     {
00130         category = key;
00131         key = NULL;
00132     }
00133 
00134     value = kvp_frame_get_slot_path (imap->frame, IMAP_FRAME, category, key, NULL);
00135     if (!value) return NULL;
00136 
00137     guid = kvp_value_get_guid (value);
00138     return xaccAccountLookup (guid, imap->book);
00139 }

Account * gnc_imap_find_account_bayes ( GncImportMatchMap *  imap,
GList *  tokens 
)

Look up an Account in the map

Look up an Account in the map from a GList* of pointers to strings(tokens) from the current transaction

Definition at line 287 of file import-match-map.c.

00288 {
00289     struct token_accounts_info tokenInfo; 
00291     GList *current_token;                       
00293     GList *current_account_token;               
00295     struct account_token_count *account_c; 
00298     struct account_probability *account_p; 
00301     GHashTable *running_probabilities = g_hash_table_new(g_str_hash, g_str_equal);
00302     GHashTable *final_probabilities = g_hash_table_new(g_str_hash, g_str_equal);
00303     struct account_info account_i;
00304     kvp_value* value;
00305     kvp_frame* token_frame;
00306 
00307     ENTER(" ");
00308 
00309     /* check to see if the imap is NULL */
00310     if (!imap)
00311     {
00312         PINFO("imap is null, returning null");
00313         LEAVE(" ");
00314         return NULL;
00315     }
00316 
00317     /* find the probability for each account that contains any of the tokens
00318      * in the input tokens list
00319      */
00320     for (current_token = tokens; current_token; current_token = current_token->next)
00321     {
00322         /* zero out the token_accounts_info structure */
00323         memset(&tokenInfo, 0, sizeof(struct token_accounts_info));
00324 
00325         PINFO("token: '%s'", (char*)current_token->data);
00326 
00327         /* find the slot for the given token off of the source account
00328          * for these tokens, search off of the IMAP_FRAME_BAYES path so
00329          * we aren't looking from the parent of the entire kvp tree
00330          */
00331         value = kvp_frame_get_slot_path(imap->frame, IMAP_FRAME_BAYES,
00332                                         (char*)current_token->data, NULL);
00333 
00334         /* if value is null we should skip over this token */
00335         if (!value)
00336             continue;
00337 
00338         /* convert the slot(value) into a the frame that contains the
00339          * list of accounts
00340          */
00341         token_frame = kvp_value_get_frame(value);
00342 
00343         /* token_frame should NEVER be null */
00344         if (!token_frame)
00345         {
00346             PERR("token '%s' has no accounts", (char*)current_token->data);
00347             continue; /* skip over this token */
00348         }
00349 
00350         /* process the accounts for this token, adding the account if it
00351          * doesn't already exist or adding to the existing accounts token
00352          * count if it does
00353          */
00354         kvp_frame_for_each_slot(token_frame, buildTokenInfo, &tokenInfo);
00355 
00356         /* for each account we have just found, see if the account already exists
00357          * in the list of account probabilities, if not add it
00358          */
00359         for (current_account_token = tokenInfo.accounts; current_account_token;
00360                 current_account_token = current_account_token->next)
00361         {
00362             /* get the account name and corresponding token count */
00363             account_c = (struct account_token_count*)current_account_token->data;
00364 
00365             PINFO("account_c->account_name('%s'), "
00366                   "account_c->token_count('%ld')/total_count('%ld')",
00367                   account_c->account_name, (long)account_c->token_count,
00368                   (long)tokenInfo.total_count);
00369 
00370             account_p = g_hash_table_lookup(running_probabilities,
00371                                             account_c->account_name);
00372 
00373             /* if the account exists in the list then continue
00374              * the running probablities
00375              */
00376             if (account_p)
00377             {
00378                 account_p->product =
00379                     ((double)account_c->token_count / (double)tokenInfo.total_count)
00380                     * account_p->product;
00381                 account_p->product_difference =
00382                     ((double)1 - ((double)account_c->token_count /
00383                                   (double)tokenInfo.total_count))
00384                     * account_p->product_difference;
00385                 PINFO("product == %f, product_difference == %f",
00386                       account_p->product, account_p->product_difference);
00387             }
00388             else
00389             {
00390                 /* add a new entry */
00391                 PINFO("adding a new entry for this account");
00392                 account_p = (struct account_probability*)
00393                             g_new0(struct account_probability, 1);
00394 
00395                 /* set the product and product difference values */
00396                 account_p->product = ((double)account_c->token_count /
00397                                       (double)tokenInfo.total_count);
00398                 account_p->product_difference =
00399                     (double)1 - ((double)account_c->token_count /
00400                                  (double)tokenInfo.total_count);
00401 
00402                 PINFO("product == %f, product_difference == %f",
00403                       account_p->product, account_p->product_difference);
00404 
00405                 /* add the account name and (struct account_probability*)
00406                  * to the hash table */
00407                 g_hash_table_insert(running_probabilities,
00408                                     account_c->account_name, account_p);
00409             }
00410         } /* for all accounts in tokenInfo */
00411 
00412         /* free the data in tokenInfo */
00413         for (current_account_token = tokenInfo.accounts; current_account_token;
00414                 current_account_token = current_account_token->next)
00415         {
00416             /* free up each struct account_token_count we allocated */
00417             g_free((struct account_token_count*)current_account_token->data);
00418         }
00419 
00420         g_list_free(tokenInfo.accounts); /* free the accounts GList */
00421     }
00422 
00423     /* build a hash table of account names and their final probabilities
00424      * from each entry in the running_probabilties hash table
00425      */
00426     g_hash_table_foreach(running_probabilities, buildProbabilities,
00427                          final_probabilities);
00428 
00429     /* find the highest probabilty and the corresponding account */
00430     memset(&account_i, 0, sizeof(struct account_info));
00431     g_hash_table_foreach(final_probabilities, highestProbability, &account_i);
00432 
00433     /* free each element of the running_probabilities hash */
00434     g_hash_table_foreach(running_probabilities, freeProbabilities, NULL);
00435 
00436     /* free the hash tables */
00437     g_hash_table_destroy(running_probabilities);
00438     g_hash_table_destroy(final_probabilities);
00439 
00440     PINFO("highest P('%s') = '%d'",
00441           account_i.account_name ? account_i.account_name : "(null)",
00442           account_i.probability);
00443 
00444     /* has this probability met our threshold? */
00445     if (account_i.probability >= threshold)
00446     {
00447         PINFO("found match");
00448         LEAVE(" ");
00449         return gnc_account_lookup_by_full_name(gnc_book_get_root_account(imap->book),
00450                                                account_i.account_name);
00451     }
00452 
00453     PINFO("no match");
00454     LEAVE(" ");
00455 
00456     return NULL; /* we didn't meet our threshold, return NULL for an account */
00457 }

gboolean gnc_import_exists_online_id ( Transaction trans  ) 

Checks whether the given transaction's online_id already exists in its parent account.

Checks whether the given transaction's online_id already exists in its parent account. The given transaction has to be open for editing. If a matching online_id exists, the transaction is destroyed (!) and TRUE is returned, otherwise FALSE is returned.

Parameters:
trans The transaction for which to check for an existing online_id.

Definition at line 1008 of file import-backend.c.

01009 {
01010     int i;
01011     gboolean online_id_exists = FALSE;
01012     Account *dest_acct;
01013     Split *source_split;
01014 
01015     /* Look for an online_id in the first split */
01016     source_split = xaccTransGetSplit(trans, 0);
01017 
01018     /* DEBUG("%s%d%s","Checking split ",i," for duplicates"); */
01019     dest_acct = xaccSplitGetAccount(source_split);
01020     online_id_exists = xaccAccountForEachTransaction(dest_acct,
01021                        check_trans_online_id,
01022                        source_split);
01023 
01024     /* If it does, abort the process for this transaction, since it is
01025        already in the system. */
01026     if (online_id_exists == TRUE)
01027     {
01028         DEBUG("%s", "Transaction with same online ID exists, destroying current transaction");
01029         xaccTransDestroy(trans);
01030         xaccTransCommitEdit(trans);
01031     }
01032     return online_id_exists;
01033 }

void gnc_import_find_split_matches ( GNCImportTransInfo *  trans_info,
gint  process_threshold,
double  fuzzy_amount_difference,
gint  match_date_hardlimit 
)

/brief Iterate through all splits of the originating account of the given transaction, and find all matching splits there.

Iterate through all splits of the originating account of the given transaction, find all matching splits there, and store them in the GNCImportTransInfo structure.

Parameters:
trans_info The TransInfo for which the corresponding matching existing transactions should be found.
process_threshold Each match whose heuristics are smaller than this value is totally ignored.
fuzzy_amount_difference For fuzzy amount matching, a certain fuzzyness in the matching amount is allowed up to this value. May be e.g. 3.00 dollars for ATM fees, or 0.0 if you only want to allow exact matches.
match_date_hardlimit The number of days that a matching split may differ from the given transaction before it is discarded immediately. In other words, any split that is more distant from the given transaction than this match_date_hardlimit days will be ignored altogether. For use cases without paper checks (e.g. HBCI), values like 14 (days) might be appropriate, whereas for use cases with paper checks (e.g. OFX, QIF), values like 42 (days) seem more appropriate.

Definition at line 775 of file import-backend.c.

00779 {
00780     GList * list_element;
00781     Query *query = xaccMallocQuery();
00782     g_assert (trans_info);
00783 
00784     /* Get list of splits of the originating account. */
00785     {
00786         /* We used to traverse *all* splits of the account by using
00787            xaccAccountGetSplitList, which is a bad idea because 90% of these
00788            splits are outside the date range that is interesting. We should
00789            rather use a query according to the date region, which is
00790            implemented here.
00791         */
00792         Account *importaccount =
00793             xaccSplitGetAccount (gnc_import_TransInfo_get_fsplit (trans_info));
00794         time_t download_time = xaccTransGetDate (gnc_import_TransInfo_get_trans (trans_info));
00795 
00796         xaccQuerySetBook (query, gnc_get_current_book());
00797         xaccQueryAddSingleAccountMatch (query, importaccount,
00798                                         QOF_QUERY_AND);
00799         xaccQueryAddDateMatchTT (query,
00800                                  TRUE, download_time - match_date_hardlimit * 86400,
00801                                  TRUE, download_time + match_date_hardlimit * 86400,
00802                                  QOF_QUERY_AND);
00803         list_element = xaccQueryGetSplits (query);
00804         /* Sigh. Doesnt help too much. We still create and run one query
00805            for each imported transaction. Maybe it would improve
00806            performance further if there is one single (master-)query at
00807            the beginning, matching the full date range and all accounts in
00808            question. However, this doesnt quite work because this function
00809            here is called from each gnc_gen_trans_list_add_trans(), which
00810            is called one at a time. Therefore the whole importer would
00811            have to change its behaviour: Accept the imported txns via
00812            gnc_gen_trans_list_add_trans(), and only when
00813            gnc_gen_trans_list_run() is called, then calculate all the
00814            different match candidates. That's too much work for now.
00815         */
00816     }
00817 
00818     /* Traverse that list, calling split_find_match on each one. Note
00819        that xaccAccountForEachSplit is declared in Account.h but
00820        implemented nowhere :-( */
00821     while (list_element != NULL)
00822     {
00823         split_find_match (trans_info, list_element->data,
00824                           process_threshold, fuzzy_amount_difference);
00825         list_element = g_list_next (list_element);
00826     }
00827 
00828     xaccFreeQuery (query);
00829 }

void gnc_import_match_picker_run_and_close ( GNCImportTransInfo *  transaction_info  ) 

Run a match_picker dialog so that the selected-MatchInfo in the given trans_info is updated accordingly. This functions will only return after the user clicked Ok, Cancel, or Window-Close.

Run a match_picker dialog where the user should pick the best match for 'one' given transaction, so that the selected-MatchInfo in the given trans_info is updated accordingly. This functions will only return after the user clicked Ok, Cancel, or Window-Close.

The dialog uses the same functionality as the one created through gnc_import_add_trans(), except that its two listviews are shown above one another, and the listview of downloaded transactions shows only one transaction, namely, the given trans_info.

This function is used from the gnc-gen-transaction code.

Parameters:
transaction_info The TransInfo for which the user is supposed to pick a matching transaction.

Definition at line 441 of file import-match-picker.c.

00442 {
00443     GNCImportMatchPicker *matcher;
00444     gint response;
00445     GNCImportMatchInfo *old;
00446     g_assert (transaction_info);
00447 
00448     /* Create a new match_picker, even though it's stored in a
00449        transmatcher struct :-) */
00450     matcher = g_new0(GNCImportMatchPicker, 1);
00451     /* DEBUG("Init match_picker"); */
00452     init_match_picker_gui(matcher);
00453 
00454     /* Append this single transaction to the view and select it */
00455     downloaded_transaction_append(matcher, transaction_info);
00456 
00457     old = gnc_import_TransInfo_get_selected_match(transaction_info);
00458 
00459     /* Let this dialog run and close. */
00460     /*DEBUG("Right before run and close");*/
00461     gtk_window_set_modal(GTK_WINDOW(matcher->transaction_matcher), TRUE);
00462     response = gtk_dialog_run (GTK_DIALOG (matcher->transaction_matcher));
00463     gnc_save_window_size(GCONF_SECTION,
00464                          GTK_WINDOW (matcher->transaction_matcher));
00465     gtk_widget_destroy (matcher->transaction_matcher);
00466     /*DEBUG("Right after run and close");*/
00467     /* DEBUG("Response was %d.", response); */
00468     if (response == GTK_RESPONSE_OK && matcher->selected_match_info != old)
00469     {
00470         /* OK was pressed */
00471         gnc_import_TransInfo_set_selected_match (transaction_info,
00472                 matcher->selected_match_info,
00473                 TRUE);
00474     }
00475 }

gint gnc_import_MatchInfo_get_probability ( const GNCImportMatchInfo *  info  ) 

Get the probability (confidence level) of this MatchInfo.

Parameters:
info Can be NULL, in which case the function returns 0

Definition at line 224 of file import-backend.c.

00225 {
00226     if (info)
00227     {
00228         return info->probability;
00229     }
00230     else
00231     {
00232         return 0;
00233     }
00234 }

Split * gnc_import_MatchInfo_get_split ( const GNCImportMatchInfo *  info  ) 

Get the split ('this-side split') of this MatchInfo.

Definition at line 217 of file import-backend.c.

00218 {
00219     g_assert (info);
00220     return info->split;
00221 }

gboolean gnc_import_process_trans_item ( GncImportMatchMap *  matchmap,
GNCImportTransInfo *  trans_info 
)

/brief -- Processes one match according to its selected action.

This function is intended to be called when the importer dialog is finished. It should be called once for each imported transaction and processes each ImportTransInfo according to its selected action: For GNCImport_ADD, the transaction is added etc. etc.

Each succesful match is also stored in the given ImportMatchMap, or, if that argument is NULL, in the ImportMatchMap of each originating account.

Parameters:
matchmap The ImportMatchMap where each match should be stored. May be NULL, in which case the ImportMatchMap of each account will be used.
trans_info The ImportTransInfo item to process.
Returns:
TRUE if the item has been processed.

Definition at line 838 of file import-backend.c.

00840 {
00841     /* DEBUG("Begin"); */
00842 
00843     g_assert (trans_info);
00844     /*DEBUG("Iteration %d, action %d, split %s", i,
00845         trans_info->action,
00846         xaccTransGetDescription (gnc_import_TransInfo_get_trans
00847         (trans_info)))*/
00848     switch (gnc_import_TransInfo_get_action (trans_info))
00849     {
00850     case GNCImport_SKIP:
00851         return FALSE;
00852     case GNCImport_ADD:
00853         /* Transaction gets imported. */
00854 
00855         /* Is the transaction not balanced and there is a non-NULL destination account? */
00856         if (gnc_import_TransInfo_is_balanced(trans_info) == FALSE
00857                 && gnc_import_TransInfo_get_destacc(trans_info) != NULL)
00858         {
00859             /* Create the 'other' split. */
00860             Split *split =
00861                 xaccMallocSplit
00862                 (gnc_account_get_book
00863                  (gnc_import_TransInfo_get_destacc (trans_info)));
00864             xaccTransAppendSplit
00865             (gnc_import_TransInfo_get_trans (trans_info), split);
00866             xaccAccountInsertSplit
00867             (gnc_import_TransInfo_get_destacc (trans_info), split);
00868             /*xaccSplitSetBaseValue
00869               (split,
00870                gnc_numeric_neg(xaccTransGetImbalance
00871                        (gnc_import_TransInfo_get_trans (trans_info))),
00872                xaccTransGetCurrency
00873                (gnc_import_TransInfo_get_trans (trans_info)));*/
00874             {
00875                 /* This is a quick workaround for the bug described in
00876                                  http://gnucash.org/pipermail/gnucash-devel/2003-August/009982.html
00877                        Assume that importers won't create transactions involving two or more
00878                        currencies so we can use xaccTransGetImbalanceValue. */
00879                 gnc_numeric v =
00880                     gnc_numeric_neg (xaccTransGetImbalanceValue
00881                                      (gnc_import_TransInfo_get_trans (trans_info)));
00882                 xaccSplitSetValue (split, v);
00883                 xaccSplitSetAmount (split, v);
00884             }
00885             /*xaccSplitSetMemo (split, _("Auto-Balance split"));
00886               -- disabled due to popular request */
00887         }
00888 
00889         xaccSplitSetReconcile(gnc_import_TransInfo_get_fsplit (trans_info), CREC);
00890         /*Set reconcile date to today*/
00891         xaccSplitSetDateReconciledSecs(gnc_import_TransInfo_get_fsplit (trans_info),
00892                                        time(NULL));
00893         /* Done editing. */
00894         xaccTransCommitEdit
00895         (gnc_import_TransInfo_get_trans (trans_info));
00896         return TRUE;
00897     case GNCImport_CLEAR:
00898     {
00899         GNCImportMatchInfo *selected_match =
00900             gnc_import_TransInfo_get_selected_match (trans_info);
00901 
00902         /* If there is no selection, ignore this transaction. */
00903         if (!selected_match)
00904         {
00905             PWARN("No matching translaction to be cleared was chosen. Imported transaction will be ignored.");
00906             break;
00907         }
00908 
00909         /* Transaction gets not imported but the matching one gets
00910            reconciled. */
00911         if (gnc_import_MatchInfo_get_split (selected_match) == NULL)
00912         {
00913             PERR("The split I am trying to reconcile is NULL, shouldn't happen!");
00914         }
00915         else
00916         {
00917             /* Reconcile the matching transaction */
00918             /*DEBUG("BeginEdit selected_match")*/
00919             xaccTransBeginEdit(selected_match->trans);
00920 
00921             if (xaccSplitGetReconcile
00922                     (selected_match->split) == NREC)
00923                 xaccSplitSetReconcile
00924                 (selected_match->split, CREC);
00925             /* Set reconcile date to today */
00926             xaccSplitSetDateReconciledSecs
00927             (selected_match->split, time(NULL));
00928 
00929             /* Copy the online id to the reconciled transaction, so
00930                          the match will be remembered */
00931             if (gnc_import_split_has_online_id(trans_info->first_split))
00932                 gnc_import_set_split_online_id
00933                 (selected_match->split,
00934                  gnc_import_get_split_online_id(trans_info->first_split));
00935 
00936             /* Done editing. */
00937             /*DEBUG("CommitEdit selected_match")*/
00938             xaccTransCommitEdit
00939             (selected_match->trans);
00940 
00941             /* Store the mapping to the other account in the MatchMap. */
00942             matchmap_store_destination (matchmap, trans_info, TRUE);
00943 
00944             /* Erase the downloaded transaction */
00945             xaccTransDestroy(trans_info->trans);
00946             /*DEBUG("CommitEdit trans")*/
00947             xaccTransCommitEdit(trans_info->trans);
00948             /* Very important: Make sure the freed transaction is not freed again! */
00949             trans_info->trans = NULL;
00950         }
00951     }
00952     return TRUE;
00953     case GNCImport_EDIT:
00954         PERR("EDIT action is UNSUPPORTED!");
00955         break;
00956     default:
00957         DEBUG("Invalid GNCImportAction for this imported transaction.");
00958     }
00959     /*DEBUG("End");*/
00960     return FALSE;
00961 }

Account * gnc_import_select_account ( gncUIWidget  parent,
const gchar *  account_online_id_value,
gboolean  auto_create,
const gchar *  account_human_description,
gnc_commodity new_account_default_commodity,
GNCAccountType  new_account_default_type,
Account default_selection,
gboolean *  ok_pressed 
)

Must be called with a string containing a unique identifier for the account. If an account with a matching online_id kvp_frame is found, the function immediately returns with a pointer to that account. Otherwise, the user is prompted to select a GnuCash account or create a new one (in both cases, the unique identifier is written to the account's kvp_frame, so the user won't be prompted again). If the user refuses to select or create an account, NULL is returned.

Parameters:
parent The parent widget. Can be NULL.
account_online_id_value The string containing your unique account_id coming from some string of your module. This is the normal mode of operation. Can be NULL.
If account_online_id_value==NULL, you basically end up with an account selector that allows you to select an account whose GUID will be remembered elsewhere. You would fill account_human_description to tell the user what he is looking for. In this mode, the online_id kvp_frame of the found account will not be touched. To use this mode, auto_create must NOT be set to 0.

Parameters:
account_human_description A human-readable description of the account. Can be NULL. If it is not NULL, it will be shown before the id in the account matching dialog. It will also be used as the default account name if a new account is created.
new_account_default_commodity Default commodity of the new account. Can be NULL. If not NULL, it will be the account's commodity if a new account is created. Also, if not NULL, the function will also warn the user if the found or created account's commodity doesn't match.
new_account_default_type Default account type of a new account. Can be NULL. If not ACCT_TYPE_NONE, it will be the account's type if a new account is created. If not ACCT_TYPE_NONE, the function will also warn the user if the found or created account's commodity doesn't match.
auto_create Only active if no account with the account_online_id_value could be found in gnucash, or if online-id was NULL. In that case, if auto_create is TRUE (nonzero), the user will be asked to create a new account. If auto_create is FALSE (zero), this function will simply return NULL but will neither select nor create any account.
default_selection If not NULL, that account will be pre-selected by default.
ok_pressed A pointer to gboolean. If non-NULL, whether or not the picker dialog was closed by the user pressing ok will be stored in the parameter. If no dialog was created by the gnc_import_select_account() call, TRUE is always returned.
Returns:
A pointer to the found or created Account, or NULL if no account was found or created.

Definition at line 145 of file import-account-matcher.c.

00153 {
00154 #define ACCOUNT_DESCRIPTION_MAX_SIZE 255
00155     struct _accountpickerdialog * picker;
00156     gint response;
00157     Account * retval = NULL;
00158     const gchar *retval_name = NULL;
00159     GladeXML *xml;
00160     GtkWidget * online_id_label, *button;
00161     gchar account_description_text[ACCOUNT_DESCRIPTION_MAX_SIZE] = "";
00162     gboolean ok_pressed_retval = FALSE;
00163 
00164     ENTER("Default commodity received: %s", gnc_commodity_get_fullname( new_account_default_commodity));
00165     DEBUG("Default account type received: %s", xaccAccountGetTypeStr( new_account_default_type));
00166     picker = g_new0(struct _accountpickerdialog, 1);
00167 
00168     picker->account_online_id_value = account_online_id_value;
00169     picker->account_human_description =  account_human_description;
00170     picker->new_account_default_commodity = new_account_default_commodity;
00171     picker->new_account_default_type = new_account_default_type;
00172 
00173     /*DEBUG("Looking for account with online_id: %s", account_online_id_value);*/
00174     if (account_online_id_value != NULL)
00175     {
00176         retval =
00177             gnc_account_foreach_descendant_until(gnc_get_current_root_account (),
00178                     test_acct_online_id_match,
00179                     /* This argument will only be
00180                                                           used as a "const char*" */
00181                     (void*)account_online_id_value);
00182     }
00183     if (retval == NULL && auto_create != 0)
00184     {
00185         /* load the interface */
00186         xml = gnc_glade_xml_new ("generic-import.glade", "Generic Import Account Picker");
00187         /* connect the signals in the interface */
00188         if (xml == NULL)
00189         {
00190             PERR("Error opening the glade interface");
00191         }
00192 
00193         picker->dialog     = glade_xml_get_widget (xml, "Generic Import Account Picker");
00194         if (parent)
00195             gtk_window_set_transient_for (GTK_WINDOW (picker->dialog),
00196                                           GTK_WINDOW (parent));
00197         picker->account_tree_sw   = glade_xml_get_widget (xml, "account_tree_sw");
00198         online_id_label = glade_xml_get_widget (xml, "online_id_label");
00199         button = glade_xml_get_widget (xml, "newbutton");
00200         gtk_button_set_use_stock (GTK_BUTTON(button), TRUE);
00201 
00202         //printf("gnc_import_select_account(): Fin get widget\n");
00203 
00204         if (account_human_description != NULL)
00205         {
00206             strncat(account_description_text, account_human_description,
00207                     ACCOUNT_DESCRIPTION_MAX_SIZE - strlen(account_description_text));
00208             strncat(account_description_text, "\n",
00209                     ACCOUNT_DESCRIPTION_MAX_SIZE - strlen(account_description_text));
00210         }
00211         if (account_online_id_value != NULL)
00212         {
00213             strncat(account_description_text, _("(Full account ID: "),
00214                     ACCOUNT_DESCRIPTION_MAX_SIZE - strlen(account_description_text));
00215             strncat(account_description_text, account_online_id_value,
00216                     ACCOUNT_DESCRIPTION_MAX_SIZE - strlen(account_description_text));
00217             strncat(account_description_text, ")",
00218                     ACCOUNT_DESCRIPTION_MAX_SIZE - strlen(account_description_text));
00219         }
00220         gtk_label_set_text((GtkLabel*)online_id_label, account_description_text);
00221         build_acct_tree(picker);
00222         gnc_tree_view_account_set_selected_account(picker->account_tree, default_selection);
00223 
00224         gtk_window_set_modal(GTK_WINDOW(picker->dialog), TRUE);
00225         g_signal_connect(picker->account_tree, "row-activated",
00226                          G_CALLBACK(account_tree_row_activated_cb), picker);
00227         do
00228         {
00229             response = gtk_dialog_run(GTK_DIALOG(picker->dialog));
00230             switch (response)
00231             {
00232             case GTK_RESPONSE_OK:
00233                 retval = gnc_tree_view_account_get_selected_account(picker->account_tree);
00234                 if (retval)
00235                     retval_name = xaccAccountGetName(retval);
00236                 if (!retval_name)
00237                     retval_name = "(null)";
00238                 DEBUG("Selected account %p, %s", retval, retval_name);
00239 
00240                 /* See if the selected account is a placeholder. */
00241                 if (retval && xaccAccountGetPlaceholder (retval))
00242                 {
00243                     gnc_error_dialog
00244                     (picker->dialog,
00245                      _("The account %s is a placeholder account and does not allow "
00246                        "transactions. Please choose a different account."),
00247                      retval_name);
00248                     response = GNC_RESPONSE_NEW;
00249                     break;
00250                 }
00251 
00252                 if ( account_online_id_value != NULL)
00253                 {
00254                     gnc_import_set_acc_online_id(retval, account_online_id_value);
00255                 }
00256                 ok_pressed_retval = TRUE;
00257                 break;
00258             case GNC_RESPONSE_NEW:
00259                 gnc_import_add_account(picker);
00260                 break;
00261             default:
00262                 ok_pressed_retval = FALSE;
00263                 break;
00264             }
00265         }
00266         while (response == GNC_RESPONSE_NEW);
00267         gtk_widget_destroy(picker->dialog);
00268     }
00269     else
00270     {
00271         retval_name = xaccAccountGetName(retval);
00272         ok_pressed_retval = TRUE; /* There was no dialog involved, so the computer "pressed" ok */
00273     }
00274     /*FIXME: DEBUG("WRITEME: gnc_import_select_account() Here we should check if account type is compatible, currency matches, etc.\n"); */
00275     g_free(picker);
00276     /*DEBUG("Return value: %p%s%s%s",retval,", account name:",xaccAccountGetName(retval),"\n");*/
00277     if (ok_pressed != NULL)
00278     {
00279         *ok_pressed = ok_pressed_retval;
00280     }
00281     LEAVE("Selected account %p, %s", retval, retval_name ? retval_name : "(null)");
00282     return retval;
00283 }

gnc_commodity * gnc_import_select_commodity ( char *  cusip,
char  auto_create,
char *  default_fullname,
char *  default_mnemonic 
)

Must be called with a string containing a unique identifier for the commodity. If an commodity with a matching cusip is found, the function immediately returns with a pointer to that commodity. Otherwise, the user may be prompted to select a GnuCash account or create a new one (in both cases, the cusip is written to the commodity's cusip field, overwriting anything that was there before.

Parameters:
cusip The string containing the code for which you want a matching commodity. A CUISP code or similar UNIQUE code. The stock ticker is NOT appropriate, unless you have no other option.
auto_create If 0, if the cusip value in unknown, the function returns NULL, otherwise, the user will be asked to create a new account.
default_fullname A human-readable description of the commodity, such as the stock name. Can be NULL. If it is not NULL, it will be shown to the user when selecting a commodity. It will also be used as the default if a new commodity is created.
default_mnemonic Usually the stock ticker or similar. Can be NULL. If it is not NULL, it will be shown to the user when selecting a commodity. It will also be used as the default if a new commodity is created.
Returns:
A pointer to the found or created commodity, or NULL if no account was found or created.

Definition at line 54 of file import-commodity-matcher.c.

00058 {
00059     gnc_commodity_table * commodity_table = gnc_get_current_commodities ();
00060     gnc_commodity * retval = NULL;
00061     gnc_commodity * tmp_commodity = NULL;
00062     char * tmp_namespace = NULL;
00063     GList * commodity_list = NULL;
00064     GList * namespace_list = NULL;
00065     DEBUG("Default fullname received: %s",
00066           default_fullname ? default_fullname : "(null)");
00067     DEBUG("Default mnemonic received: %s",
00068           default_mnemonic ? default_mnemonic : "(null)");
00069 
00070     DEBUG("Looking for commodity with exchange_code: %s", cusip);
00071 
00072     namespace_list = gnc_commodity_table_get_namespaces(commodity_table);
00073 
00074 
00075     namespace_list = g_list_first(namespace_list);
00076     while ( namespace_list != NULL && retval == NULL)
00077     {
00078         tmp_namespace = namespace_list->data;
00079         DEBUG("Looking at namespace %s", tmp_namespace);
00080 
00081 
00082         /*Nested loop*/
00083         commodity_list = gnc_commodity_table_get_commodities(commodity_table,
00084                          tmp_namespace);
00085         commodity_list  = g_list_first(commodity_list);
00086         while ( commodity_list != NULL && retval == NULL)
00087         {
00088             tmp_commodity = commodity_list->data;
00089             DEBUG("Looking at commodity %s", gnc_commodity_get_fullname(tmp_commodity));
00090 
00091             if (gnc_commodity_get_cusip(tmp_commodity) != NULL &&
00092                     cusip != NULL &&
00093                     strncmp(gnc_commodity_get_cusip(tmp_commodity), cusip, strlen(cusip)) == 0)
00094             {
00095                 retval = tmp_commodity;
00096                 DEBUG("Commodity %s%s", gnc_commodity_get_fullname(retval), " matches.");
00097             }
00098             commodity_list = g_list_next(commodity_list);
00099         }
00100         /*End nested loop*/
00101 
00102         namespace_list = g_list_next(namespace_list);
00103     }
00104 
00105 
00106 
00107 
00108     g_list_free(commodity_list);
00109     g_list_free(namespace_list);
00110 
00111     if (retval == NULL && auto_create != 0)
00112     {
00113         const gchar *message =
00114             _("Please select a commodity to match the following exchange "
00115               "specific code. Please note that the exchange code of the "
00116               "commodity you select will be overwritten.");
00117         retval = gnc_ui_select_commodity_modal_full(NULL,
00118                  NULL,
00119                  DIAG_COMM_ALL,
00120                  message,
00121                  cusip,
00122                  default_fullname,
00123                  default_mnemonic);
00124 
00125     }
00126     /* There seems to be a problem here - if the matched commodity does not
00127        have a cusip defined (gnc_commodity_get_cusip returns NULL) then
00128        it does not get overwritten - which is not consistent with the
00129        message - so Im adding it to do this.  Looks like this is all
00130        that was needed to fix the cash value used as stock units problem
00131        for pre-defined commodities which didnt have the cusip defined! */
00132     if (retval != NULL &&
00133             gnc_commodity_get_cusip(retval) != NULL &&
00134             cusip != NULL &&
00135             (strncmp(gnc_commodity_get_cusip(retval), cusip, strlen(cusip)) != 0))
00136     {
00137         gnc_commodity_set_cusip(retval, cusip);
00138     }
00139     else if (gnc_commodity_get_cusip(retval) == NULL && cusip != NULL)
00140     {
00141         gnc_commodity_set_cusip(retval, cusip);
00142     }
00143     return retval;
00144 };

void gnc_import_Settings_delete ( GNCImportSettings *  settings  ) 

Destructor

Definition at line 107 of file import-settings.c.

00108 {
00109     if (settings)
00110     {
00111         g_free(settings);
00112     }
00113 }

gboolean gnc_import_Settings_get_action_add_enabled ( GNCImportSettings *  settings  ) 

Return the selected action is enable state.

Definition at line 128 of file import-settings.c.

00129 {
00130     g_assert (settings);
00131     return settings->action_add_enabled;
00132 };

gboolean gnc_import_Settings_get_action_clear_enabled ( GNCImportSettings *  settings  ) 

Return the selected action is enable state.

Definition at line 140 of file import-settings.c.

00141 {
00142     g_assert (settings);
00143     return settings->action_clear_enabled;
00144 };

gboolean gnc_import_Settings_get_action_edit_enabled ( GNCImportSettings *  settings  ) 

Return the selected action is enable state.

Definition at line 134 of file import-settings.c.

00135 {
00136     g_assert (settings);
00137     return settings->action_edit_enabled;
00138 };

gboolean gnc_import_Settings_get_action_skip_enabled ( GNCImportSettings *  settings  ) 

Return the selected action is enable state.

Definition at line 122 of file import-settings.c.

00123 {
00124     g_assert (settings);
00125     return settings->action_skip_enabled;
00126 };

gint gnc_import_Settings_get_add_threshold ( GNCImportSettings *  settings  ) 

Return the selected threshold.

Definition at line 152 of file import-settings.c.

00153 {
00154     g_assert (settings);
00155     return settings->add_threshold;
00156 };

gint gnc_import_Settings_get_clear_threshold ( GNCImportSettings *  settings  ) 

Return the selected threshold.

Definition at line 146 of file import-settings.c.

00147 {
00148     g_assert (settings);
00149     return settings->clear_threshold;
00150 };

gint gnc_import_Settings_get_display_threshold ( GNCImportSettings *  settings  ) 

Return the selected threshold.

Definition at line 158 of file import-settings.c.

00159 {
00160     g_assert (settings);
00161     return settings->display_threshold;
00162 };

double gnc_import_Settings_get_fuzzy_amount ( GNCImportSettings *  settings  ) 

Return the allowed amount range for fuzzy amount matching.

Returns:
The allowed amount range for fuzzy amount matching, in the users default commodity.

Definition at line 116 of file import-settings.c.

00117 {
00118     g_assert (settings);
00119     return settings->fuzzy_amount;
00120 };

gint gnc_import_Settings_get_match_date_hardlimit ( const GNCImportSettings *  settings  ) 

Returns the hard-limiting number of days that a matching split may differ.

Definition at line 169 of file import-settings.c.

00170 {
00171     g_assert(s);
00172     return s->match_date_hardlimit;
00173 }

GNCImportSettings * gnc_import_Settings_new ( void   ) 

Allocates a new GNCImportSettings object, and initialize it with the appropriate user prefs.

Definition at line 79 of file import-settings.c.

00080 {
00081     GNCImportSettings * settings;
00082 
00083     settings = g_new0 ( GNCImportSettings, 1);
00084 
00085 
00086     settings->action_skip_enabled =
00087         gnc_gconf_get_bool(GCONF_SECTION, "enable_skip", NULL);
00088     settings->action_edit_enabled =
00089         gnc_gconf_get_bool(GCONF_SECTION, "enable_edit", NULL);
00090     settings->action_add_enabled = DEFAULT_ACTION_ADD_ENABLED;
00091     settings->action_clear_enabled = DEFAULT_ACTION_CLEAR_ENABLED;
00092     settings->clear_threshold =
00093         gnc_gconf_get_float(GCONF_SECTION, "auto_clear_threshold", NULL);
00094     settings->add_threshold =
00095         gnc_gconf_get_float(GCONF_SECTION, "auto_add_threshold", NULL);
00096     settings->display_threshold =
00097         gnc_gconf_get_float(GCONF_SECTION, "match_threshold", NULL);
00098 
00099     settings->fuzzy_amount =
00100         gnc_gconf_get_float(GCONF_SECTION, "atm_fee_threshold", NULL);
00101 
00102     settings->match_date_hardlimit = 42; /* 6 weeks */
00103     return settings;
00104 }

void gnc_import_Settings_set_match_date_hardlimit ( GNCImportSettings *  settings,
gint  match_date_hardlimit 
)

Parameters:
match_date_hardlimit The number of days that a matching split may differ from the given transaction before it is discarded immediately. In other words, any split that is more distant from the given transaction than this match_date_hardlimit days will be ignored altogether. For use cases without paper checks (e.g. HBCI), values like 14 (days) might be appropriate, whereas for use cases with paper checks (e.g. OFX, QIF), values like 42 (days) seem more appropriate.

Definition at line 164 of file import-settings.c.

00165 {
00166     g_assert(s);
00167     s->match_date_hardlimit = m;
00168 }

void gnc_import_TransInfo_delete ( GNCImportTransInfo *  info  ) 

Destructor

Definition at line 236 of file import-backend.c.

00237 {
00238     if (info)
00239     {
00240         g_list_free (info->match_list);
00241         /*If the transaction exists and is still open, it must be destroyed*/
00242         if (info->trans && xaccTransIsOpen(info->trans))
00243         {
00244             xaccTransDestroy(info->trans);
00245             xaccTransCommitEdit(info->trans);
00246         }
00247         if (info->match_tokens)
00248         {
00249             GList *node;
00250 
00251             for (node = info->match_tokens; node; node = node->next)
00252                 g_free (node->data);
00253 
00254             g_list_free (info->match_tokens);
00255         }
00256         g_free(info);
00257     }
00258 }

GNCImportAction gnc_import_TransInfo_get_action ( const GNCImportTransInfo *  info  ) 

Returns the currently selected action for this TransInfo.

Definition at line 170 of file import-backend.c.

00171 {
00172     g_assert (info);
00173     return info->action;
00174 }

Account * gnc_import_TransInfo_get_destacc ( const GNCImportTransInfo *  info  ) 

Returns the 'other account' of this transaction. May return NULL.

Definition at line 189 of file import-backend.c.

00190 {
00191     g_assert (info);
00192     return info->dest_acc;
00193 }

gboolean gnc_import_TransInfo_get_destacc_selected_manually ( const GNCImportTransInfo *  info  ) 

Returns if the currently selected destination account for auto-matching was selected by the user.

Definition at line 210 of file import-backend.c.

00211 {
00212     g_assert (info);
00213     return info->dest_acc_selected_manually;
00214 }

Split * gnc_import_TransInfo_get_fsplit ( const GNCImportTransInfo *  info  ) 

Returns the first split of the transaction of this TransInfo.

Definition at line 139 of file import-backend.c.

00140 {
00141     g_assert (info);
00142     return info->first_split;
00143 }

GList * gnc_import_TransInfo_get_match_list ( const GNCImportTransInfo *  info  ) 

Returns the stored list of possible matches.

Definition at line 108 of file import-backend.c.

00109 {
00110     g_assert (info);
00111     return info->match_list;
00112 }

gboolean gnc_import_TransInfo_get_match_selected_manually ( const GNCImportTransInfo *  info  ) 

Returns if the currently selected match was selected by the user.

Definition at line 163 of file import-backend.c.

00164 {
00165     g_assert (info);
00166     return info->match_selected_manually;
00167 }

GNCImportMatchInfo * gnc_import_TransInfo_get_selected_match ( const GNCImportTransInfo *  info  ) 

Returns the currently selected match in this TransInfo.

Definition at line 146 of file import-backend.c.

00147 {
00148     g_assert (info);
00149     return info->selected_match_info;
00150 }

Transaction * gnc_import_TransInfo_get_trans ( const GNCImportTransInfo *  info  ) 

Returns the transaction of this TransInfo.

Definition at line 115 of file import-backend.c.

00116 {
00117     g_assert (info);
00118     return info->trans;
00119 }

void gnc_import_TransInfo_init_matches ( GNCImportTransInfo *  trans_info,
GNCImportSettings *  settings 
)

Iterates through all splits of the originating account of trans_info. Sorts the resulting list and sets the selected_match and action fields in the trans_info.

Iterates through all splits of the originating account of trans_info. Sorts the resulting list and sets the selected_match and action fields in the trans_info.

Parameters:
trans_info The TransInfo for which the matches should be found, sorted, and selected.
settings The structure that holds all the user preferences.

Definition at line 1074 of file import-backend.c.

01076 {
01077     GNCImportMatchInfo * best_match;
01078     g_assert (trans_info);
01079 
01080 
01081     /* Find all split matches in originating account. */
01082     gnc_import_find_split_matches(trans_info,
01083                                   gnc_import_Settings_get_display_threshold (settings),
01084                                   gnc_import_Settings_get_fuzzy_amount (settings),
01085                                   gnc_import_Settings_get_match_date_hardlimit (settings));
01086 
01087     if (trans_info->match_list != NULL)
01088     {
01089         trans_info->match_list = g_list_sort(trans_info->match_list,
01090                                              compare_probability);
01091         best_match = g_list_nth_data(trans_info->match_list, 0);
01092         gnc_import_TransInfo_set_selected_match (trans_info,
01093                 best_match,
01094                 FALSE);
01095         if (best_match != NULL &&
01096                 best_match->probability >= gnc_import_Settings_get_clear_threshold(settings))
01097         {
01098             trans_info->action = GNCImport_CLEAR;
01099             trans_info->selected_match_info = best_match;
01100         }
01101         else if (best_match == NULL ||
01102                  best_match->probability <= gnc_import_Settings_get_add_threshold(settings) )
01103         {
01104             trans_info->action = GNCImport_ADD;
01105         }
01106         else
01107         {
01108             trans_info->action = GNCImport_SKIP;
01109         }
01110     }
01111     else
01112         trans_info->action = GNCImport_ADD;
01113 
01114     trans_info->previous_action = trans_info->action;
01115 }

gboolean gnc_import_TransInfo_is_balanced ( const GNCImportTransInfo *  info  ) 

Returns if the transaction stored in the TransInfo is currently balanced.

Definition at line 122 of file import-backend.c.

00123 {
00124     g_assert (info);
00125     /* Assume that the importer won't create a transaction that involves two or more
00126        currencies and no non-currency commodity.  In that case can use the simpler
00127        value imbalance check. */
00128     if (gnc_numeric_zero_p(xaccTransGetImbalanceValue(gnc_import_TransInfo_get_trans(info))))
00129     {
00130         return TRUE;
00131     }
00132     else
00133     {
00134         return FALSE;
00135     }
00136 }

GNCImportTransInfo * gnc_import_TransInfo_new ( Transaction trans,
GncImportMatchMap *  matchmap 
)

Create a new object of GNCImportTransInfo here.

Allocates a new TransInfo object, with the Transaction 'trans' already stored in there. Also, this already checks the ImportMatchMap for automated destination account matching. The given MatchMap may be NULL, in which case the ImportMatchMap of the originating account will be used.

Parameters:
trans The transaction that this TransInfo should work with.
matchmap MatchMap used for automated destination account choosing. This may be NULL, in which case the MatchMap of the originating account will be used.

Definition at line 1041 of file import-backend.c.

01042 {
01043     GNCImportTransInfo *transaction_info;
01044     g_assert (trans);
01045 
01046     transaction_info = g_new0(GNCImportTransInfo, 1);
01047 
01048     transaction_info->trans = trans;
01049     /* Only use first split, the source split */
01050     transaction_info->first_split = xaccTransGetSplit(trans, 0);
01051 
01052     /* Try to find a previously selected destination account
01053        string match for the ADD action */
01054     gnc_import_TransInfo_set_destacc (transaction_info,
01055                                       matchmap_find_destination (matchmap, transaction_info),
01056                                       FALSE);
01057     return transaction_info;
01058 }

gboolean gnc_import_TransInfo_refresh_destacc ( GNCImportTransInfo *  transaction_info,
GncImportMatchMap *  matchmap 
)

Try to automatch a given transaction to a destination account

Definition at line 1121 of file import-backend.c.

01123 {
01124     Account *orig_destacc;
01125     Account *new_destacc = NULL;
01126     g_assert(transaction_info);
01127 
01128     orig_destacc = gnc_import_TransInfo_get_destacc(transaction_info);
01129 
01130     /* if we haven't manually selected a destination account for this transaction */
01131     if (gnc_import_TransInfo_get_destacc_selected_manually(transaction_info) == FALSE)
01132     {
01133         /* Try to find the destination account for this transaction based on prior ones */
01134         new_destacc = matchmap_find_destination(matchmap, transaction_info);
01135         gnc_import_TransInfo_set_destacc(transaction_info, new_destacc, FALSE);
01136     }
01137     else
01138     {
01139         new_destacc = orig_destacc;
01140     }
01141 
01142     /* account has changed */
01143     if (new_destacc != orig_destacc)
01144     {
01145         return TRUE;
01146     }
01147     else   /* account is the same */
01148     {
01149         return FALSE;
01150     }
01151 }

void gnc_import_TransInfo_set_action ( GNCImportTransInfo *  info,
GNCImportAction  action 
)

Set the action for this TransInfo. Also sets the previous action.

Definition at line 177 of file import-backend.c.

00179 {
00180     g_assert (info);
00181     if (action != info->action)
00182     {
00183         info->previous_action = info->action;
00184         info->action = action;
00185     }
00186 }

void gnc_import_TransInfo_set_destacc ( GNCImportTransInfo *  info,
Account acc,
gboolean  selected_manually 
)

Set the 'other account' of this transaction (used for auto-balance if needed). May be set to NULL.

Parameters:
selected_manually TRUE or FALSE; Was this account set as a result of a selection by the user or by an algorithm?

Definition at line 194 of file import-backend.c.

00197 {
00198     g_assert (info);
00199     info->dest_acc = acc;
00200     info->dest_acc_selected_manually = selected_manually;
00201 
00202     /* Store the mapping to the other account in the MatchMap. */
00203     if (selected_manually)
00204     {
00205         matchmap_store_destination (NULL, info, FALSE);
00206     }
00207 }

void gnc_import_TransInfo_set_selected_match ( GNCImportTransInfo *  info,
GNCImportMatchInfo *  match,
gboolean  selected_manually 
)

Sets the currently selected match in this TransInfo.

Parameters:
selected_manually TRUE or FALSE; Was this match set as a result of a selection by the user or by an algorithm?

Definition at line 153 of file import-backend.c.

00156 {
00157     g_assert (info);
00158     info->selected_match_info = match;
00159     info->match_selected_manually = selected_manually;
00160 }


Generated on Thu Mar 18 04:44:43 2010 for GnuCash by  doxygen 1.5.7.1