note description: "[ An application to produce Eiffel class files from Origo's database tables. The generated files should be copied to `$ORIGO/nodes/storage/objects'. ]" author: "B. Herlig" date: "$Date$" revision: "$Revision$" class DB_INTERFACE_GENERATION inherit ARGUMENTS create make feature {NONE} -- Initialization make -- Run application. local l_argument_parser: AP_PARSER l_host_flag: AP_STRING_OPTION l_DSN_flag: AP_STRING_OPTION l_user_flag: AP_STRING_OPTION l_pwd_flag: AP_STRING_OPTION do -- Setup argument parsing create l_argument_parser.make l_argument_parser.set_application_description ("An application to produce Eiffel class files from Origo's database tables.") create l_host_flag.make ('t', "host") l_host_flag.set_description ("Database Hostname to connect to.") l_host_flag.set_parameter_description ("STRING") l_argument_parser.options.force_last (l_host_flag) create l_DSN_flag.make ('d', "datasource") l_DSN_flag.set_description ("ODBC datasource name (DSN) to connect to.") l_DSN_flag.set_parameter_description ("STRING") l_argument_parser.options.force_last (l_DSN_flag) create l_user_flag.make ('u', "user") l_user_flag.set_description ("Username to connect with.") l_user_flag.set_parameter_description ("STRING") l_argument_parser.options.force_last (l_user_flag) create l_pwd_flag.make ('p', "password") l_pwd_flag.set_description ("Password to authenticate with.") l_pwd_flag.set_parameter_description ("STRING") l_argument_parser.options.force_last (l_pwd_flag) -- parse args l_argument_parser.parse_arguments -- Process arguments -- Host if l_host_flag.was_found then host := l_host_flag.parameter else -- User prompt print ("%NHostname [" + default_host + "]:") io.read_line if io.last_string.is_empty then host := default_host else host := io.last_string.twin end end -- DSN if l_dsn_flag.was_found then dsn := l_dsn_flag.parameter else -- User prompt print ("%NDatasource Name [" + default_dsn + "]:") io.read_line if io.last_string.is_empty then dsn := default_dsn else dsn := io.last_string.twin end end -- User if l_user_flag.was_found then user := l_user_flag.parameter else -- User prompt print ("%NUsername [" + default_user + "]:") io.read_line if io.last_string.is_empty then user := default_user else user := io.last_string.twin end end -- Password if l_pwd_flag.was_found then password := l_pwd_flag.parameter else -- User prompt print ("%NPassword [" + default_password + "]:") io.read_line if io.last_string.is_empty then password := default_password else password := io.last_string.twin end end check -- Are all values attached? host /= Void dsn /= Void user /= Void password /= Void end -- Create & open DB connection print ("%NConnecting to datbase...") create db_application db_application.set_hostname (host) db_application.set_data_source (dsn) db_application.login (user, password) db_application.set_base create db_control.make db_control.connect if not db_control.is_connected then -- Print errormessage & exit. print (" Connection failed: " + db_control.error_message +"%NExiting.%N") else print (" done.%N") load_repositories generate_classes print ("All files generated.%N") -- closing db_control.disconnect end end feature {NONE} -- Access host: STRING -- Database host. dsn: STRING -- Database source host. user: STRING -- Database user. password: STRING -- Database password. feature {NONE}-- Database access db_application: O_DATABASE_APPL [ODBC] -- Database application to use. db_control: DB_CONTROL -- Database control. db_repositories: HASH_TABLE [DB_REPOSITORY, STRING] -- Database repositories mapped to the table name. feature {NONE} -- Implementation load_repositories -- Load repository for each table into db_repositories. local l_query: DB_SELECTION l_tables: ARRAYED_LIST [DB_RESULT] l_result: DB_DATA_SQL l_table: STRING l_repo: DB_REPOSITORY do create db_repositories.make (10) -- get available tables create l_query.make l_query.set_query ("SHOW TABLES") l_query.execute_query if not db_control.is_ok then print (db_control.error_message) else create l_tables.make (10) l_query.set_container (l_tables) l_query.load_result from l_tables.start until l_tables.after loop -- foreach table, create the repository l_result ?= l_tables.item.data l_table := l_result.item (1).out create l_repo.make (l_table) l_repo.load if not l_repo.exists then print ("Could not retrieve repository for table " + l_table) else db_repositories.force (l_repo, l_table) end l_tables.forth end end ensure db_repositories_set: db_repositories /= Void end generate_classes -- Generated classes for each loaded DB_REPOSITORY, i.e. table in the database. local l_repository: DB_REPOSITORY l_file: PLAIN_TEXT_FILE do from db_repositories.start until db_repositories.after loop l_repository := db_repositories.item_for_iteration create l_file.make (file_directory + "/" + l_repository.repository_name.as_lower + ".e") l_file.create_read_write l_repository.generate_class (l_file) l_file.close -- Increment db_repositories.forth end end feature {NONE} -- Constants file_directory: STRING = "gen" -- Directory where the generated files will be put. default_host: STRING = "localhost" -- Default database host. default_dsn: STRING = "origo_test" -- Default database source host. default_user: STRING = "origo_test" -- Default database user. default_password: STRING = "" -- Default database password. invariant db_application_not_void: db_application /= Void db_control_not_void: db_control /= Void db_repositories_not_void: db_repositories /= Void end