[interchange-cvs] interchange - racke modified 2082 files

interchange-core@icdevgroup.org interchange-core@icdevgroup.org
Sat Jan 25 18:20:02 2003


User:      racke
Date:      2003-01-25 22:21:35 GMT
Modified:  .        Tag: LINUXIA .cvsignore MANIFEST MANIFEST.SKIP
Modified:           Makefile.PL README README.cvs README.debian
Modified:           WHATSNEW configure hints.pl test.pl
Modified:  SPECS    Tag: LINUXIA interchange.spec
Modified:  dist     Tag: LINUXIA catalog_after.cfg catalog_before.cfg
Modified:           interchange.cfg.dist
Modified:  dist/lib/UI Tag: LINUXIA Primitive.pm ui.cfg
Modified:  dist/lib/UI/pages/admin Tag: LINUXIA access.html
Modified:           access_permissions.html add_meta_option.html
Modified:           affiliates.html bug_report.html build_related.html
Modified:           button_builder.html customer.html
Modified:           customer_bill.html customer_change_pass.html
Modified:           customer_pref.html customer_select.html
Modified:           customer_ship.html customer_view.html
Modified:           dbdownload.html dbinfo.html do_upload.html
Modified:           do_view.html entry.html entry_select.html
Modified:           env_vars.html error.html error_item.html
Modified:           export_table.html flex_editor.html flex_select.html
Modified:           fr_index.html genconfig.html gentable.html
Modified:           group.html group_edit.html import_table.html
Modified:           index.html item.html item_cross.html item_edit.html
Modified:           item_feature.html item_inventory.html
Modified:           item_price.html item_up.html layout.html login.html
Modified:           merchandising.html meta_editor.html order.html
Modified:           order_status.html order_view.html orderstats.html
Modified:           payment.html preferences.html quicklinks.html
Modified:           reconfig.html regen.html regenerate.html
Modified:           report.html report_results.html report_save.html
Modified:           search_wizard.html search_wizard2.html
Modified:           search_wizard3.html search_wizard_results.html
Modified:           ship.html ship_data.html ship_edit.html
Modified:           ship_range.html sku_selector.html spread.html
Modified:           spread_control.html tablereport.html tax.html
Modified:           trafficstats.html upload_config.html
Modified:           upload_file.html upload_image.html
Modified:           upload_pages.html user_change_pass.html
Modified:           user_edit.html
Modified:  dist/lib/UI/pages/admin/reports/order Tag: LINUXIA
Modified:           ByAffiliate.html Detail.html Monthly.html
Modified:  dist/lib/UI/pages/admin/reports/traffic Tag: LINUXIA
Modified:           ByAffiliate.html
Modified:  dist/lib/UI/pages/admin/special Tag: LINUXIA
Modified:           key_violation.html
Modified:  dist/lib/UI/profiles Tag: LINUXIA login order_button_build
Modified:  dist/lib/UI/vars Tag: LINUXIA UI_STD_FILE_NAV UI_STD_FOOTER
Modified:           UI_STD_HEAD
Modified:  dist/src Tag: LINUXIA config.h.in mod_perl_tlink.pl mvctl.c
Modified:           tlink.c tlink.pl vlink.c vlink.pl
Modified:  dist/src/mod_interchange Tag: LINUXIA Makefile README
Modified:           mod_interchange.c mod_interchange.html
Modified:           mod_interchange.spec
Modified:  dist/test Tag: LINUXIA catalog.cfg
Modified:  dist/test/products Tag: LINUXIA mv_metadata.asc pricing.asc
Modified:           tests.asc
Modified:  eg/globalsub Tag: LINUXIA authorizenet
Modified:  extensions/quickbooks Tag: LINUXIA README ic_qb.pod
Modified:           qb.catalog.cfg
Modified:  extensions/quickbooks/etc Tag: LINUXIA trans_quickbooks
Modified:  extra/URI Tag: LINUXIA URL.pm
Modified:  lib      Tag: LINUXIA .cvsignore
Modified:  lib/Vend Tag: LINUXIA Cart.pm Config.pm Control.pm Data.pm
Modified:           DbSearch.pm Document.pm Error.pm External.pm
Modified:           Glimpse.pm Imagemap.pm Interpolate.pm MakeCat.pm
Modified:           Order.pm Page.pm Parse.pm Parser.pm Scan.pm
Modified:           Search.pm Server.pm Session.pm SessionDB.pm
Modified:           SessionFile.pm Tags.pm TextSearch.pm Track.pm
Modified:           UserDB.pm Util.pm
Modified:  lib/Vend/Table Tag: LINUXIA Common.pm DBI.pm DB_File.pm
Modified:           GDBM.pm InMemory.pm LDAP.pm
Modified:  scripts  Tag: LINUXIA .cvsignore compile_link.PL
Modified:           config_prog.PL configdump.PL dump.PL expire.PL
Modified:           expireall.PL interchange.PL localize.PL makecat.PL
Modified:           offline.PL restart.PL update.PL
Added:     .        Tag: LINUXIA README.rpm-dist UPGRADE relocate.pl
Added:     SPECS    Tag: LINUXIA interchange-init interchange-logrotate
Added:              interchange-wrapper
Added:     code/ActionMap Tag: LINUXIA foo.am
Added:     code/Filter Tag: LINUXIA convert_date.filter
Added:              date2time.filter encrypt.filter lc.filter
Added:              linkdecode.filter next_sequential.filter
Added:     code/SystemTag Tag: LINUXIA accessories.coretag
Added:              accounting.coretag area.coretag assign.coretag
Added:              attr_list.coretag banner.coretag calc.coretag
Added:              calcn.coretag cart.coretag catch.coretag
Added:              cgi.coretag charge.coretag checked.coretag
Added:              control.coretag control_set.coretag counter.coretag
Added:              currency.coretag data.coretag default.coretag
Added:              deliver.coretag description.coretag
Added:              discount.coretag dump.coretag either.coretag
Added:              error.coretag export.coretag field.coretag
Added:              file.coretag filter.coretag flag.coretag
Added:              fly_list.coretag fly_tax.coretag handling.coretag
Added:              harness.coretag html_table.coretag image.tag
Added:              import.coretag include.coretag index.coretag
Added:              input_filter.coretag item_list.coretag
Added:              levies.coretag levy_list.coretag log.coretag
Added:              loop.coretag mail.coretag menu.coretag msg.coretag
Added:              mvasp.coretag nitems.coretag onfly.coretag
Added:              options.coretag order.coretag output_to.tag
Added:              page.coretag parse_locale.coretag perl.coretag
Added:              price.coretag process.coretag profile.coretag
Added:              query.coretag read_cookie.coretag record.coretag
Added:              region.coretag row.coretag salestax.coretag
Added:              scratch.coretag scratchd.coretag
Added:              search_region.coretag selected.coretag set.coretag
Added:              set_cookie.coretag seti.coretag setlocale.coretag
Added:              shipping.coretag shipping_desc.coretag soap.coretag
Added:              sql.coretag strip.coretag subtotal.coretag
Added:              tag.coretag time.coretag timed_build.coretag
Added:              tmp.coretag tmpn.coretag total_cost.coretag
Added:              tree.coretag try.coretag unpack.coretag
Added:              update.coretag userdb.coretag value.coretag
Added:              value_extended.coretag warnings.coretag
Added:     code/UI_Tag Tag: LINUXIA add_gpg_key.coretag
Added:              assume_identity.tag auto_wizard.coretag
Added:              available_ups_internal.coretag
Added:              available_www_shipping.coretag
Added:              backup_database.coretag backup_file.coretag
Added:              base_url.coretag check_upload.coretag
Added:              content_editor.coretag content_info.coretag
Added:              content_modify.coretag cp.coretag crypt.coretag
Added:              db_columns.coretag db_hash.coretag diff.coretag
Added:              diffmerge.coretag directive_value.coretag
Added:              display.coretag dump_session.coretag
Added:              export_database.coretag file_info.coretag
Added:              file_navigator.coretag filters.coretag
Added:              get_gpg_keys.coretag global_value.coretag
Added:              grep_mm.coretag if_mm.coretag image_collate.coretag
Added:              import_fields.coretag jsq.coretag jsqn.coretag
Added:              list_databases.coretag list_glob.coretag
Added:              list_keys.coretag list_pages.coretag
Added:              menu_load.coretag meta_record.coretag
Added:              mm_locale.coretag mm_value.coretag newer.coretag
Added:              quick_table.coretag read_shipping.coretag
Added:              reconfig.coretag reconfig_time.coretag
Added:              regenerate.coretag return_to.coretag
Added:              rotate_table.coretag row_edit.coretag
Added:              run_profile.coretag su.coretag
Added:              substitute_file.coretag tabbed_display.coretag
Added:              table_editor.coretag uneval.coretag
Added:              unlink_file.coretag update_order_status.tag
Added:              version.coretag widget.coretag
Added:              write_relative_file.coretag write_shipping.coretag
Added:     code/UserTag Tag: LINUXIA bar_button.tag button.tag
Added:              component.tag convert_date.tag db_date.tag
Added:              delete_cart.tag email.tag email_raw.tag env.tag
Added:              fedex_query.tag formel.tag fortune.tag forum.tag
Added:              get_url.tag history_scan.tag load_cart.tag loc.tag
Added:              page_meta.tag rand.tag save_cart.tag summary.tag
Added:              table_organize.tag title_bar.tag ups_query.tag
Added:              usertrack.tag var.tag
Added:     code/Widget Tag: LINUXIA gpg_keys.widget imagedir.widget
Added:              imagehelper.widget uploadhelper.widget
Added:     debian   Tag: LINUXIA 400mod_interchange.info CREDITS.debian
Added:              interchange-cat-foundation.config
Added:              interchange-cat-foundation.files
Added:              interchange-cat-foundation.postinst
Added:              interchange-cat-foundation.postrm
Added:              interchange-cat-foundation.prerm
Added:              interchange-cat-foundation.templates
Added:              interchange-ui.config interchange-ui.postrm
Added:              interchange-ui.preinst interchange-ui.prerm
Added:              interchange-ui.templates interchange.preinst
Added:              interchange.prerm interchangeconfig
Added:              libapache-mod-interchange.doc-base
Added:     dist/etc Tag: LINUXIA varnames
Added:     dist/foundation Tag: LINUXIA catalog.cfg
Added:     dist/foundation/backup Tag: LINUXIA .empty
Added:     dist/foundation/config Tag: LINUXIA additional_fields
Added:              additional_help installsample makedirs
Added:              postcopy_commands precopy_commands
Added:     dist/foundation/dbconf/default_db Tag: LINUXIA 2ndDayAir.dbm
Added:              Ground.dbm NextDayAir.dbm access.dbm affiliate.dbm
Added:              area.dbm cat.dbm component.dbm country.dbm
Added:              default_db.cfg forum.dbm gift_certs.dbm
Added:              inventory.dbm locale.dbm merchandising.dbm
Added:              mv_metadata.dbm options.dbm order_returns.dbm
Added:              orderline.dbm pricing.dbm products.dbm state.dbm
Added:              survey.dbm transactions.dbm tree.dbm userdb.dbm
Added:              variable.dbm
Added:     dist/foundation/dbconf/locales Tag: LINUXIA de_DE.cfg
Added:              default.cfg
Added:     dist/foundation/dbconf/mysql Tag: LINUXIA 2ndDayAir.dbm
Added:              Ground.dbm NextDayAir.dbm access.dbm
Added:              affiliate.mysql area.mysql cat.mysql component.dbm
Added:              country.mysql forum.mysql gift_certs.mysql
Added:              inventory.mysql locale.dbm merchandising.mysql
Added:              mv_metadata.dbm mysql.cfg options.mysql
Added:              order_returns.mysql orderline.mysql pricing.mysql
Added:              products.mysql state.mysql survey.dbm
Added:              transactions.mysql tree.mysql userdb.mysql
Added:              variable.dbm
Added:     dist/foundation/dbconf/oracle Tag: LINUXIA 2ndDayAir.dbm
Added:              Ground.dbm NextDayAir.dbm access.dbm affiliate.ora
Added:              area.ora cat.ora component.dbm country.ora
Added:              gift_certs.ora inventory.ora locale.dbm
Added:              merchandising.ora mv_metadata.dbm options.ora
Added:              oracle.cfg order_returns.ora orderline.ora
Added:              pricing.ora products.ora state.ora survey.dbm
Added:              transactions.ora tree.ora userdb.ora variable.dbm
Added:     dist/foundation/dbconf/pgsql Tag: LINUXIA 2ndDayAir.dbm
Added:              Ground.dbm NextDayAir.dbm access.dbm
Added:              affiliate.pgsql area.pgsql cat.pgsql component.dbm
Added:              country.pgsql forum.pgsql gift_certs.pgsql
Added:              inventory.pgsql locale.dbm merchandising.pgsql
Added:              mv_metadata.dbm options.pgsql order_returns.pgsql
Added:              orderline.pgsql pgsql.cfg pricing.pgsql
Added:              products.pgsql state.pgsql survey.dbm
Added:              transactions.pgsql tree.pgsql userdb.pgsql
Added:              variable.dbm
Added:     dist/foundation/etc Tag: LINUXIA area.recordnumber
Added:              cat.recordnumber log_entry log_transaction
Added:              mail_receipt order.number profiles.login
Added:              profiles.order receipt.html report return.number
Added:              rma.number ship_notice
Added:     dist/foundation/html Tag: LINUXIA index.html
Added:     dist/foundation/images Tag: LINUXIA bg.gif computer.xls
Added:              construct.xls download.png fc.gif fo.gif
Added:              reports.xls smallamex.png smalldisc.png smallmc.png
Added:              smallvisa.png template.xls
Added:     dist/foundation/images/affiliate Tag: LINUXIA hardhat.gif
Added:     dist/foundation/images/blueyellow Tag: LINUXIA about.gif
Added:              banner.gif bar_filler.gif buynow.gif cart.gif
Added:              checkout.gif checkout_button.gif
Added:              continue_shopping.gif gift_certificate_large.gif
Added:              go.gif home.gif littlebar.gif login.gif logo.gif
Added:              logo2.gif logout.gif placeorder.gif poweredby.gif
Added:              recalculate_button.gif savecart.gif saverecur.gif
Added:              search.gif sep.gif service.gif thumb.gif
Added:              yourimage.gif
Added:     dist/foundation/images/fixedwidth Tag: LINUXIA about.gif
Added:              banner.gif bar_filler.gif buynow.gif cart.gif
Added:              checkout.gif checkout_button.gif
Added:              continue_shopping.gif go.gif home.gif littlebar.gif
Added:              login.gif logo.gif logo2.gif logout.gif
Added:              placeorder.gif poweredby.gif recalculate_button.gif
Added:              savecart.gif saverecur.gif search.gif sep.gif
Added:              service.gif thumb.gif yourimage.gif
Added:     dist/foundation/images/foundation Tag: LINUXIA about.gif
Added:              buynow.gif cart.gif checkout.gif
Added:              checkout_button.gif go.gif home.gif littlebar.gif
Added:              login.gif logo.gif logo2.gif logout.gif
Added:              placeorder.gif poweredby.gif recalculate_button.gif
Added:              savecart.gif saverecur.gif sep.gif service.gif
Added:              thumb.gif
Added:     dist/foundation/images/grayorange Tag: LINUXIA about.gif
Added:              banner.gif bar_filler.gif buynow.gif cart.gif
Added:              checkout.gif checkout_button.gif
Added:              continue_shopping.gif gift_certificate_large.gif
Added:              go.gif home.gif littlebar.gif login.gif logo.gif
Added:              logo2.gif logout.gif placeorder.gif poweredby.gif
Added:              recalculate_button.gif savecart.gif saverecur.gif
Added:              search.gif sep.gif service.gif thumb.gif
Added:              yourimage.gif
Added:     dist/foundation/images/grayscale Tag: LINUXIA about.gif
Added:              banner.gif bar_filler.gif buynow.gif cart.gif
Added:              checkout.gif checkout_button.gif
Added:              continue_shopping.gif gift_certificate_large.gif
Added:              go.gif home.gif littlebar.gif login.gif logo.gif
Added:              logo2.gif logout.gif placeorder.gif poweredby.gif
Added:              recalculate_button.gif savecart.gif saverecur.gif
Added:              search.gif sep.gif service.gif thumb.gif
Added:              yourimage.gif
Added:     dist/foundation/images/greens Tag: LINUXIA about.gif
Added:              banner.gif bar_filler.gif buynow.gif cart.gif
Added:              checkout.gif checkout_button.gif
Added:              continue_shopping.gif gift_certificate_large.gif
Added:              go.gif home.gif littlebar.gif login.gif logo.gif
Added:              logo2.gif logout.gif placeorder.gif poweredby.gif
Added:              recalculate_button.gif savecart.gif saverecur.gif
Added:              search.gif sep.gif service.gif thumb.gif
Added:              yourimage.gif
Added:     dist/foundation/images/items Tag: LINUXIA yourimage.gif
Added:     dist/foundation/images/purpleyellow Tag: LINUXIA about.gif
Added:              banner.gif bar_filler.gif buynow.gif cart.gif
Added:              checkout.gif checkout_button.gif
Added:              continue_shopping.gif gift_certificate_large.gif
Added:              go.gif home.gif littlebar.gif login.gif logo.gif
Added:              logo2.gif logout.gif placeorder.gif poweredby.gif
Added:              recalculate_button.gif savecart.gif saverecur.gif
Added:              search.gif sep.gif service.gif thumb.gif
Added:              yourimage.gif
Added:     dist/foundation/images/thumb Tag: LINUXIA thumb.gif
Added:     dist/foundation/include/checkout Tag: LINUXIA
Added:              billing_address initialization login_form
Added:              mailing_status new_browser_payment
Added:              old_browser_payment payment_select shipping_address
Added:              shopping_cart tax_popup
Added:     dist/foundation/include/forum Tag: LINUXIA reply_form
Added:              submit_form
Added:     dist/foundation/pages Tag: LINUXIA aboutus.html account.html
Added:              advancedsearch.html browse.html canceled.html
Added:              change_password.html contact.html
Added:              customerservice.html deliver.html flypage.html
Added:              help.html index.html login.html logout.html
Added:              lost_password.html modular_modify.html
Added:              new_account.html privacypolicy.html
Added:              process_return.html quantity.html results.html
Added:              results_big.html returns.html saved_carts.html
Added:              ship_addresses.html ship_addresses_added.html
Added:              ship_addresses_removed.html splash.html
Added:              stock-alert-added.html stock-alert.html
Added:              swap_results.html test_order.html
Added:     dist/foundation/pages/admin/report_def Tag: LINUXIA
Added:              Order%20Status.html Products%20to%20edit.html
Added:     dist/foundation/pages/admin/reports Tag: LINUXIA
Added:              Order%20Status.html Products%20to%20edit.html
Added:     dist/foundation/pages/affiliate Tag: LINUXIA index.html
Added:              login.html
Added:     dist/foundation/pages/forum Tag: LINUXIA display.html
Added:              reply.html submit.html
Added:     dist/foundation/pages/ord Tag: LINUXIA basket.html
Added:              checkout.html
Added:     dist/foundation/pages/query Tag: LINUXIA check_orders.html
Added:              get_password.html order_detail.html
Added:              order_return.html unsub.html
Added:     dist/foundation/pages/survey Tag: LINUXIA graph.html
Added:              graph.png.html standard.html
Added:     dist/foundation/products Tag: LINUXIA 2ndDayAir.csv 450.csv
Added:              Ground.csv NextDayAir.csv access.asc affiliate.txt
Added:              area.txt cat.txt component.txt country.txt
Added:              downloadable.txt files.txt forum.txt gift_certs.txt
Added:              inventory.txt locale.txt merchandising.txt
Added:              mv_metadata.asc options.txt order_returns.txt
Added:              orderline.txt pricing.txt products.txt route.txt
Added:              salestax.asc shipping.asc state.txt survey.txt
Added:              transactions.txt tree.txt userdb.txt variable.txt
Added:     dist/foundation/special_pages Tag: LINUXIA badsearch.html
Added:              canceled.html cc_not_valid.html confirmation.html
Added:              failed.html interact.html missing.html
Added:              needfield.html nomatch.html noproduct.html
Added:              notfound.html order_security.html reconfig.html
Added:              sec_faq.html security.html violation.html
Added:     dist/foundation/templates Tag: LINUXIA leftonly leftright
Added:              noleft
Added:     dist/foundation/templates/blueyellow Tag: LINUXIA theme.cfg
Added:     dist/foundation/templates/blueyellow/regions Tag: LINUXIA
Added:              CATTOP_LEFTONLY_BOTTOM CATTOP_LEFTONLY_TOP
Added:              CATTOP_LEFTRIGHT_BOTTOM CATTOP_LEFTRIGHT_TOP
Added:              CATTOP_NOLEFT_BOTTOM CATTOP_NOLEFT_TOP
Added:              LEFTONLY_BOTTOM LEFTONLY_TOP LEFTRIGHT_BOTTOM
Added:              LEFTRIGHT_TOP NOLEFT_BOTTOM NOLEFT_TOP
Added:     dist/foundation/templates/components Tag: LINUXIA
Added:              affiliate_receptor best cart cart_display cart_tiny
Added:              category_horizontal category_vert_toggle
Added:              category_vertical category_vertical_tree cross
Added:              fortune product_flyout product_tree promo random
Added:              results_big results_buylist results_grid
Added:              saved_carts_list_small search_box_small
Added:              search_box_small_top upsell
Added:     dist/foundation/templates/fixedwidth Tag: LINUXIA theme.cfg
Added:     dist/foundation/templates/fixedwidth/regions Tag: LINUXIA
Added:              CATTOP_LEFTONLY_BOTTOM CATTOP_LEFTONLY_TOP
Added:              CATTOP_LEFTRIGHT_BOTTOM CATTOP_LEFTRIGHT_TOP
Added:              CATTOP_NOLEFT_BOTTOM CATTOP_NOLEFT_TOP
Added:              LEFTONLY_BOTTOM LEFTONLY_TOP LEFTRIGHT_BOTTOM
Added:              LEFTRIGHT_TOP NOLEFT_BOTTOM NOLEFT_TOP
Added:     dist/foundation/templates/foundation Tag: LINUXIA cart
Added:              simple theme.cfg
Added:     dist/foundation/templates/foundation/regions Tag: LINUXIA
Added:              LEFTONLY_BOTTOM LEFTONLY_TOP LEFTRIGHT_BOTTOM
Added:              LEFTRIGHT_TOP NOLEFT_BOTTOM NOLEFT_TOP
Added:     dist/foundation/templates/grayorange Tag: LINUXIA theme.cfg
Added:     dist/foundation/templates/grayorange/regions Tag: LINUXIA
Added:              CATTOP_LEFTONLY_BOTTOM CATTOP_LEFTONLY_TOP
Added:              CATTOP_LEFTRIGHT_BOTTOM CATTOP_LEFTRIGHT_TOP
Added:              CATTOP_NOLEFT_BOTTOM CATTOP_NOLEFT_TOP
Added:              LEFTONLY_BOTTOM LEFTONLY_TOP LEFTRIGHT_BOTTOM
Added:              LEFTRIGHT_TOP NOLEFT_BOTTOM NOLEFT_TOP
Added:     dist/foundation/templates/grayscale Tag: LINUXIA theme.cfg
Added:     dist/foundation/templates/grayscale/regions Tag: LINUXIA
Added:              CATTOP_LEFTONLY_BOTTOM CATTOP_LEFTONLY_TOP
Added:              CATTOP_LEFTRIGHT_BOTTOM CATTOP_LEFTRIGHT_TOP
Added:              CATTOP_NOLEFT_BOTTOM CATTOP_NOLEFT_TOP
Added:              LEFTONLY_BOTTOM LEFTONLY_TOP LEFTRIGHT_BOTTOM
Added:              LEFTRIGHT_TOP NOLEFT_BOTTOM NOLEFT_TOP
Added:     dist/foundation/templates/greens Tag: LINUXIA theme.cfg
Added:     dist/foundation/templates/greens/regions Tag: LINUXIA
Added:              CATTOP_LEFTONLY_BOTTOM CATTOP_LEFTONLY_TOP
Added:              CATTOP_LEFTRIGHT_BOTTOM CATTOP_LEFTRIGHT_TOP
Added:              CATTOP_NOLEFT_BOTTOM CATTOP_NOLEFT_TOP
Added:              LEFTONLY_BOTTOM LEFTONLY_TOP LEFTRIGHT_BOTTOM
Added:              LEFTRIGHT_TOP NOLEFT_BOTTOM NOLEFT_TOP
Added:     dist/foundation/templates/purpleyellow Tag: LINUXIA
Added:              theme.cfg
Added:     dist/foundation/templates/purpleyellow/regions Tag: LINUXIA
Added:              CATTOP_LEFTONLY_BOTTOM CATTOP_LEFTONLY_TOP
Added:              CATTOP_LEFTRIGHT_BOTTOM CATTOP_LEFTRIGHT_TOP
Added:              CATTOP_NOLEFT_BOTTOM CATTOP_NOLEFT_TOP
Added:              LEFTONLY_BOTTOM LEFTONLY_TOP LEFTRIGHT_BOTTOM
Added:              LEFTRIGHT_TOP NOLEFT_BOTTOM NOLEFT_TOP
Added:     dist/foundation/templates/sampledata/reports/download Tag:
Added:              LINUXIA 00352as.pdf 11993ab.pdf 22083da.pdf
Added:              49503cg.pdf 59330rt.pdf 59402fw.pdf 66548ch.pdf
Added:              73358ee.pdf 83491vp.pdf 90773sh.pdf
Added:     dist/foundation/templates/sampledata/reports/products Tag:
Added:              LINUXIA area.txt cat.txt inventory.txt
Added:              merchandising.txt options.txt pricing.txt
Added:              products.txt userdb.txt
Added:     dist/foundation/templates/sampledata/tools/etc Tag: LINUXIA
Added:              after.cfg before.cfg
Added:     dist/foundation/templates/sampledata/tools/images/items Tag:
Added:              LINUXIA gift_cert.gif os28004.gif os28005.gif
Added:              os28006.gif os28007.gif os28008.gif os28009.gif
Added:              os28011.gif os28044.gif os28057a.gif os28057b.gif
Added:              os28057c.gif os28062.gif os28064.gif os28065.gif
Added:              os28066.gif os28068.gif os28068a.gif os28068b.gif
Added:              os28069.gif os28070.gif os28072.gif os28073.gif
Added:              os28074.gif os28075.gif os28076.gif os28077.gif
Added:              os28080.gif os28081.gif os28082.gif os28084.gif
Added:              os28085.gif os28086.gif os28087.gif os28108.gif
Added:              os28109.gif os28110.gif os28111.gif os28112.gif
Added:              os28113.gif os29000.gif
Added:     dist/foundation/templates/sampledata/tools/images/thumb Tag:
Added:              LINUXIA gift_cert.gif os28004_b.gif os28005_b.gif
Added:              os28006_b.gif os28007_b.gif os28008_b.gif
Added:              os28009_b.gif os28011_b.gif os28044_b.gif
Added:              os28057a_b.gif os28057b_b.gif os28057c_b.gif
Added:              os28062_b.gif os28064_b.gif os28065_b.gif
Added:              os28066_b.gif os28068_b.gif os28068a_b.gif
Added:              os28068b_b.gif os28069_b.gif os28070_b.gif
Added:              os28072_b.gif os28073_b.gif os28074_b.gif
Added:              os28075_b.gif os28076_b.gif os28077_b.gif
Added:              os28080_b.gif os28081_b.gif os28082_b.gif
Added:              os28084_b.gif os28085_b.gif os28086_b.gif
Added:              os28087_b.gif os28108_b.gif os28109_b.gif
Added:              os28110_b.gif os28111_b.gif os28112_b.gif
Added:              os28113_b.gif os29000_b.gif
Added:     dist/foundation/templates/sampledata/tools/products Tag:
Added:              LINUXIA affiliate.txt area.txt area_de_DE.txt
Added:              cat.txt cat_de_DE.txt inventory.txt
Added:              merchandising.txt options.txt orderline.txt
Added:              pricing.txt products.txt products_de_DE.txt
Added:              specs.txt transactions.txt userdb.txt
Added:     dist/foundation/upload Tag: LINUXIA .empty products.xls
Added:     dist/lib/UI Tag: LINUXIA ContentEditor.pm ichelp.txt
Added:     dist/lib/UI/locales Tag: LINUXIA README TODO da_DK.cfg
Added:              de_DE.cfg default.cfg en_US.cfg es_ES.cfg he_IL.cfg
Added:              ja_JP.cfg nl_NL.cfg pt_BR.cfg sv_SE.cfg
Added:     dist/lib/UI/pages/admin Tag: LINUXIA .access .autoload
Added:              auto_wizard.html commerce.html content.html
Added:              content_components.html content_editor.html
Added:              content_preview.html content_publish.html
Added:              content_push.html content_templates.html
Added:              customer_all.html customer_comments.html
Added:              customer_mailing.html db_metaconfig.html
Added:              db_newview.html dbconfig.html dbconfig_save.html
Added:              direct_sql.html edit_metaconfig.html
Added:              file_transfer.html flex_group.html generic.html
Added:              genfunction.html gpg_key.html help.html
Added:              item_group.html item_option.html
Added:              item_option_phantom.html layout_auto.html
Added:              menu_editor.html menu_loader.html merge_meta.html
Added:              misc_order_number.html order_status_alt.html
Added:              page_metaconfig.html page_upload.html
Added:              pref_colors.html pref_select.html
Added:              quick_question.html search_replace.html
Added:              show_session.html tax_simple.html test_code.html
Added:     dist/lib/UI/pages/admin/accounting Tag: LINUXIA index.html
Added:              return.html
Added:     dist/lib/UI/pages/admin/reports/order Tag: LINUXIA .access
Added:              .autoload
Added:     dist/lib/UI/pages/admin/reports/traffic Tag: LINUXIA .access
Added:              .autoload
Added:     dist/lib/UI/pages/admin/special Tag: LINUXIA .access
Added:              .autoload
Added:     dist/lib/UI/pages/admin/survey Tag: LINUXIA index.html
Added:              overall.html question.html
Added:     dist/lib/UI/pages/admin/wizard Tag: LINUXIA .access
Added:              .autoload X_dump.html X_test.html demo_init.html
Added:              demo_zero.html do_launch.html do_save.html
Added:              guess_info.html index.html step_about.html
Added:              step_company.html step_email.html
Added:              step_groupcontent.html step_grouppolicy.html
Added:              step_index.html step_launch.html step_pay.html
Added:              step_pay_auth.html step_pay_cyber.html
Added:              step_pay_itransact.html step_pay_pgp.html
Added:              step_pay_signio.html step_pay_skipjack.html
Added:              step_preview.html step_products.html
Added:              step_security.html step_ship.html
Added:              step_ship_country.html step_ship_default.html
Added:              step_ship_fedex.html step_ship_ups.html
Added:              step_style.html step_style_logo.html step_tax.html
Added:     dist/lib/UI/pages/include Tag: LINUXIA component_editor
Added:              item_option_matrix item_option_modular
Added:              item_option_simple order_delete_archive page_editor
Added:              table_populator template_editor wizard_checklist
Added:              wizard_profiles
Added:     dist/lib/UI/pages/include/menus Tag: LINUXIA Accounting.txt
Added:              Admin.txt Commerce.txt Content.txt ContentEdit.txt
Added:              Customers.txt DbConfig.txt Design.txt Fixed.txt
Added:              Items.txt Layout.txt Legacy.txt Merchandising.txt
Added:              Misc.txt MiscFunction.txt None.txt OrderView.txt
Added:              Orders.txt Quicklinks.txt Reports.txt Surveys.txt
Added:              Tables.txt Top.txt Wizard.txt uiExport.txt
Added:     dist/lib/UI/pages/include/meta Tag: LINUXIA mv_metadata.asc
Added:     dist/lib/UI/pages/include/templates Tag: LINUXIA ui_type1
Added:              ui_type2 ui_type3 ui_type5
Added:     dist/lib/UI/profiles Tag: LINUXIA Cancel db_maintenance
Added:              file_maintenance miscellaneous process_filter
Added:              recompute_transaction
Added:     eg       Tag: LINUXIA gpg_display reset_order_number
Added:              survey_graph.tag te
Added:     eg/globalsub Tag: LINUXIA ccvs test_card
Added:     eg/news_feature Tag: LINUXIA README
Added:     eg/news_feature/dbconf/default_db Tag: LINUXIA news.dbm
Added:     eg/news_feature/dbconf/mysql Tag: LINUXIA news.mysql
Added:     eg/news_feature/dbconf/oracle Tag: LINUXIA news.ora
Added:     eg/news_feature/dbconf/pgsql Tag: LINUXIA news.pgsql
Added:     eg/news_feature/pages Tag: LINUXIA news.html
Added:     eg/news_feature/products Tag: LINUXIA news.txt
Added:     eg/news_feature/templates/components Tag: LINUXIA news
Added:     extensions Tag: LINUXIA Interchange.pm
Added:     extensions/ECML Tag: LINUXIA ecml.coretag
Added:     extensions/ECML/Vend Tag: LINUXIA ECML.pm
Added:     extensions/quickbooks Tag: LINUXIA mv_metadata-additions.asc
Added:              qb_getord.pl
Added:     extensions/quickbooks/pages/admin/quickbooks Tag: LINUXIA
Added:              export_coa.html export_items.html get_orders.html
Added:              import_items.html index.html
Added:     extensions/quickbooks/usertag Tag: LINUXIA
Added:              export_quicken_coa.tag export_quicken_items.tag
Added:              get_quicken_orders.tag import_quicken_items.tag
Added:     extra/Business Tag: LINUXIA Fedex.pm
Added:     extra/Tie Tag: LINUXIA ShadowHash.pm
Added:     lib/Vend Tag: LINUXIA Accounting.pm CounterFile.pm
Added:              Dispatch.pm Form.pm Menu.pm ModPerl.pm Payment.pm
Added:              RefSearch.pm SOAP.pm Swish.pm
Added:     lib/Vend/Accounting Tag: LINUXIA SQL_Ledger.pm
Added:     lib/Vend/Payment Tag: LINUXIA AuthorizeNet.pm BoA.pm CCVS.pm
Added:              CyberCash.pm ECHO.pm MCVE.pm Signio.pm Skipjack.pm
Added:              TCLink.pm TestPayment.pm WellsFargo.pm iTransact.pm
Added:     lib/Vend/SOAP Tag: LINUXIA Transport.pm
Added:     lib/Vend/Table Tag: LINUXIA Editor.pm SDBM.pm Shadow.pm
Added:     scripts  Tag: LINUXIA findtags.PL ic_mod_perl.PL newcat.PL
Added:     share/interchange Tag: LINUXIA ic.css ic1.css
Added:     share/interchange/en_US Tag: LINUXIA az.gif bg.gif
Added:              box_checked.gif box_empty.gif delete.gif delsm.gif
Added:              doc.gif down.gif folder.gif folder.open.gif
Added:              forward.gif generic.gif graylogo.gif icfooter.gif
Added:              iclogo.gif ico_download.gif ico_duck.gif
Added:              ico_export.gif ico_folder.gif ico_import.gif
Added:              ico_magnify.gif ico_pen.gif ico_upload.gif
Added:              icon_config.gif icon_design.gif icon_error.gif
Added:              icon_ic.gif icon_item.gif icon_merch.gif
Added:              icon_orders.gif icon_pages.gif icon_people.gif
Added:              icon_regen.gif icon_stats.gif index.gif
Added:              interchange.css layout.gif left.gif logo.gif
Added:              meta.png minus.gif photo.jpg plus.gif poweredby.gif
Added:              right.gif smindex.gif specmeta.png text.gif
Added:              tminus.gif tplus.gif transfer.gif unknown.gif
Added:              up.gif
Added:     share/interchange/u Tag: LINUXIA subtab_down_fill.gif
Added:              subtab_down_left.gif subtab_down_right.gif
Added:              subtab_fill.gif subtab_filllwr.gif subtab_left.gif
Added:              subtab_right.gif tab_dark_left.gif
Added:              tab_dark_right.gif tab_down_fill.gif
Added:              tab_down_left.gif tab_down_right.gif tab_fill.gif
Added:              tab_left.gif tab_light_left.gif tab_light_right.gif
Added:              tab_right.gif
Removed:   .        Tag: LINUXIA UPGRADE_FROM_MV3
Removed:   dist/barry Tag: LINUXIA catalog.cfg
Removed:   dist/barry/backup Tag: LINUXIA .empty
Removed:   dist/barry/config Tag: LINUXIA additional_fields
Removed:            additional_help copyright leftonly leftside logobar
Removed:            menubar menubottom no_left no_right
Removed:            postcopy_commands precopy_commands rightside
Removed:   dist/barry/etc Tag: LINUXIA area.recordnumber
Removed:            cat.recordnumber profiles.login profiles.order
Removed:            receipt.html report ship_notice
Removed:   dist/barry/html Tag: LINUXIA index.html
Removed:   dist/barry/images Tag: LINUXIA about.gif addtocart.gif
Removed:            addtocart2.gif banner.gif bg.gif bikeparts.gif
Removed:            bikes.gif bookpick.gif books.gif clamps.gif
Removed:            clear.gif cleardot.gif contactus.gif cranky.gif
Removed:            create.gif customer.gif download.png
Removed:            front_collage.gif go.gif header_about.gif
Removed:            header_bikes.gif header_books.gif
Removed:            header_contactus.gif header_customerservice.gif
Removed:            header_feedback.gif header_help.gif
Removed:            header_login.gif header_new_account.gif
Removed:            header_newaccount.gif header_parts.gif
Removed:            header_sandals.gif header_search.gif
Removed:            header_shoes.gif help.gif home.gif leftside.gif
Removed:            leftside_b.gif login.gif mvlogo.png mvlogo_dark.png
Removed:            new.png next.gif order.gif poweredby.gif
Removed:            rightside.gif rightside_b.gif sandals.gif
Removed:            satisfied.gif search.gif shoes.gif shoppingcart.gif
Removed:            smallamex.png smalldisc.png smallmc.png
Removed:            smallvisa.png space.gif specials.gif tan_line.gif
Removed:            white_line.gif
Removed:   dist/barry/images/header_multi Tag: LINUXIA basket.gif
Removed:   dist/barry/images/header_ord Tag: LINUXIA basket.gif
Removed:   dist/barry/images/items Tag: LINUXIA KHS.soft99.jpg
Removed:            RST.381R.jpg aspen.gif avid.arch50.jpg
Removed:            barbntrini.gif charlesnfox.gif chrono.deepV.jpg
Removed:            george.gif housefelt.gif jurassic.gif
Removed:            kore.elite.stem.jpg man.99sxti.GIF manhattan.gif
Removed:            mystery.gif oklahoma.gif panaracer.mach.gif
Removed:            pedal.jpg racing.gif rf.lpcrank.jpg rf.system.jpg
Removed:            river.gif shimano.pedal.434.JPG shimano.pedal.jpg
Removed:            shimano.xtr.jpg shoebox.gif shoeleather.gif
Removed:            spinergy.spox.jpg terry.men.gif tire.conti.gif
Removed:            women.gif xtr.cassette.jpg xtrcrank.jpg zinn.gif
Removed:   dist/barry/images/thumb Tag: LINUXIA KHS.soft99.jpg
Removed:            RST.381R.jpg aspen.gif avid.arch50.jpg
Removed:            barbntrini.gif charlesnfox.gif chrono.deepV.jpg
Removed:            george.gif housefelt.gif jurassic.gif
Removed:            kore.elite.stem.jpg man.99sxti.GIF manhattan.gif
Removed:            mystery.gif oklahoma.gif panaracer.mach.gif
Removed:            pedal.jpg racing.gif rf.lpcrank.jpg rf.system.jpg
Removed:            river.gif shimano.pedal.434.JPG shimano.pedal.jpg
Removed:            shimano.xtr.jpg shoebox.gif shoeleather.gif
Removed:            spinergy.spox.jpg terry.men.gif tire.conti.gif
Removed:            women.gif xtr.cassette.jpg xtrcrank.jpg zinn.gif
Removed:   dist/barry/logs Tag: LINUXIA .empty
Removed:   dist/barry/mysql Tag: LINUXIA affiliate.mysql area.mysql
Removed:            cat.mysql country.mysql inventory.mysql
Removed:            merchandising.mysql orderline.mysql pricing.mysql
Removed:            products.mysql transactions.mysql userdb.mysql
Removed:   dist/barry/orders Tag: LINUXIA .empty
Removed:   dist/barry/pages Tag: LINUXIA about.html account.html
Removed:            browse.html browse1.html canceled.html contact.html
Removed:            deliver.html flypage.html help.html index.html
Removed:            last_search.html login.html logout.html
Removed:            new_account.html news.html no_cookie.html
Removed:            nothing.html privacy.html quantity.html
Removed:            results.html splash.html srchform.html subcat.html
Removed:   dist/barry/pages/action Tag: LINUXIA get_password.html
Removed:   dist/barry/pages/examples Tag: LINUXIA test_banner.html
Removed:   dist/barry/pages/multi Tag: LINUXIA b_address.html
Removed:            basket.html checkout.html final.html nobasket.html
Removed:            shipping.html
Removed:   dist/barry/pages/ord Tag: LINUXIA basket.html checkout.html
Removed:            nobasket.html
Removed:   dist/barry/pages/query Tag: LINUXIA check_orders.html
Removed:            order_detail.html
Removed:   dist/barry/pages/special Tag: LINUXIA feedback.html
Removed:            needfield.html
Removed:   dist/barry/pgsql Tag: LINUXIA area.pgsql cat.pgsql
Removed:            country.pgsql inventory.pgsql merchandising.pgsql
Removed:            orderline.pgsql pricing.pgsql products.pgsql
Removed:            transactions.pgsql userdb.pgsql
Removed:   dist/barry/products Tag: LINUXIA 2ndDayAir.csv
Removed:            2ndDayAirAM.csv 3DaySelect.csv 3DaySelectRes.csv
Removed:            450.csv Ground.csv GroundComm.csv GroundRes.csv
Removed:            NextDayAir.csv NextDayAirSaver.csv access.asc
Removed:            affiliate.txt area.txt banner.txt cat.txt
Removed:            inventory.txt locale.txt merchandising.txt
Removed:            orderline.txt pricing.txt products.txt route.txt
Removed:            salestax.asc shipping.asc state.txt
Removed:            transactions.txt ups_zone.asc variable.txt
Removed:   dist/barry/session Tag: LINUXIA .empty
Removed:   dist/barry/special_pages Tag: LINUXIA badsearch.html
Removed:            canceled.html cc_not_valid.html confirmation.html
Removed:            failed.html interact.html missing.html
Removed:            needfield.html nomatch.html noproduct.html
Removed:            notfound.html order_security.html reconfig.html
Removed:            sec_faq.html security.html violation.html
Removed:   dist/barry/templates Tag: LINUXIA fullwidth leftonly
Removed:            standard
Removed:   dist/barry/tmp Tag: LINUXIA .empty
Removed:   dist/barry/upload Tag: LINUXIA .empty
Removed:   dist/compat/backend Tag: LINUXIA AsciiBackend
Removed:   dist/construct/backup Tag: LINUXIA .empty
Removed:   dist/construct/dbconf/default_db Tag: LINUXIA 2ndDayAir.dbm
Removed:            Ground.dbm NextDayAir.dbm access.dbm affiliate.dbm
Removed:            area.dbm banner.dbm cat.dbm country.dbm
Removed:            gift_certs.dbm inventory.dbm locale.dbm
Removed:            merchandising.dbm mv_metadata.dbm order_returns.dbm
Removed:            orderline.dbm pricing.dbm products.dbm
Removed:            recurring_items.dbm recurring_orders.dbm
Removed:            ship_addresses.dbm transactions.dbm userdb.dbm
Removed:            variable.dbm
Removed:   dist/construct/dbconf/mysql Tag: LINUXIA 2ndDayAir.dbm
Removed:            Ground.dbm NextDayAir.dbm access.dbm
Removed:            affiliate.mysql area.mysql banner.dbm cat.mysql
Removed:            country.mysql gift_certs.mysql inventory.mysql
Removed:            locale.dbm mv_metadata.dbm order_returns.mysql
Removed:            orderline.mysql recurring_items.mysql
Removed:            recurring_orders.mysql ship_addresses.mysql
Removed:            transactions.mysql userdb.mysql variable.dbm
Removed:   dist/construct/dbconf/pgsql Tag: LINUXIA 2ndDayAir.dbm
Removed:            Ground.dbm NextDayAir.dbm access.dbm
Removed:            affiliate.pgsql area.pgsql banner.dbm cat.pgsql
Removed:            country.pgsql gift_certs.pgsql inventory.pgsql
Removed:            locale.dbm mv_metadata.dbm orderline.pgsql
Removed:            products.pgsql recurring_items.pgsql
Removed:            recurring_orders.pgsql ship_addresses.pgsql
Removed:            transactions.pgsql userdb.pgsql variable.dbm
Removed:   dist/construct/etc Tag: LINUXIA profiles.login
Removed:            profiles.order
Removed:   dist/construct/images Tag: LINUXIA bg.gif clear.gif
Removed:            poweredby.gif
Removed:   dist/construct/images/affiliate Tag: LINUXIA hardhat.gif
Removed:   dist/construct/images/items Tag: LINUXIA
Removed:            gift_certificate_large.gif os28004.gif os28005.gif
Removed:            os28006.gif os28007.gif os28008.gif os28009.gif
Removed:            os28011.gif os28044.gif os28057a.gif os28057b.gif
Removed:            os28057c.gif os28062.gif os28064.gif os28065.gif
Removed:            os28066.gif os28068.gif os28068a.gif os28068b.gif
Removed:            os28069.gif os28070.gif os28072.gif os28073.gif
Removed:            os28074.gif os28075.gif os28076.gif os28077.gif
Removed:            os28080.gif os28081.gif os28082.gif os28084.gif
Removed:            os28085.gif os28086.gif os28087.gif os28108.gif
Removed:            os28109.gif os28110.gif os28111.gif os28112.gif
Removed:            os28113.gif os29000.gif
Removed:   dist/construct/images/navigation Tag: LINUXIA b1.gif
Removed:            b1_b.gif b2.gif b2_b.gif b3.gif b3_b.gif b4.gif
Removed:            b4_b.gif b5.gif b5_b.gif b6.gif b6_b.gif
Removed:            buy_now.gif checkout_button.gif
Removed:            continue_shopping.gif coupon_item.gif d.gif d1.gif
Removed:            d2.gif d3.gif default_a.gif go.gif go_b.gif
Removed:            header_handtools.gif header_ladders.gif
Removed:            header_measuringtools.gif
Removed:            header_paintingsupplies.gif
Removed:            header_safetyequipment.gif header_toolstorage.gif
Removed:            logout.gif logout_b.gif minime1.gif minime2.gif
Removed:            orangespacer.gif poweredby.gif
Removed:            recalculate_button.gif whitey.gif
Removed:   dist/construct/images/thumb Tag: LINUXIA os28004_b.gif
Removed:            os28005_b.gif os28006_b.gif os28007_b.gif
Removed:            os28008_b.gif os28009_b.gif os28011_b.gif
Removed:            os28044_b.gif os28057a_b.gif os28057b_b.gif
Removed:            os28057c_b.gif os28062_b.gif os28064_b.gif
Removed:            os28065_b.gif os28066_b.gif os28068_b.gif
Removed:            os28068a_b.gif os28068b_b.gif os28069_b.gif
Removed:            os28070_b.gif os28072_b.gif os28073_b.gif
Removed:            os28074_b.gif os28075_b.gif os28076_b.gif
Removed:            os28077_b.gif os28080_b.gif os28081_b.gif
Removed:            os28082_b.gif os28084_b.gif os28085_b.gif
Removed:            os28086_b.gif os28087_b.gif os28108_b.gif
Removed:            os28109_b.gif os28110_b.gif os28111_b.gif
Removed:            os28112_b.gif os28113_b.gif os29000_b.gif
Removed:   dist/construct/logs Tag: LINUXIA .empty
Removed:   dist/construct/orders Tag: LINUXIA .empty
Removed:   dist/construct/pages/admin/report_def Tag: LINUXIA
Removed:            Order%20Status.html Products%20to%20edit.html
Removed:   dist/construct/pages/admin/reports Tag: LINUXIA
Removed:            Order%20Status.html Products%20to%20edit.html
Removed:   dist/construct/products Tag: LINUXIA 2ndDayAir.csv
Removed:            2ndDayAirAM.csv 3DaySelect.csv 3DaySelectRes.csv
Removed:            450.csv Ground.csv GroundComm.csv GroundRes.csv
Removed:            NextDayAir.csv NextDayAirSaver.csv banner.txt
Removed:            gift_certs.txt locale.txt recurring_items.txt
Removed:            recurring_orders.txt salestax.asc shipping.asc
Removed:            ups_zone.asc
Removed:   dist/construct/session Tag: LINUXIA .empty
Removed:   dist/construct/special_pages Tag: LINUXIA badsearch.html
Removed:            canceled.html cc_not_valid.html confirmation.html
Removed:            failed.html interact.html missing.html
Removed:            needfield.html nomatch.html noproduct.html
Removed:            notfound.html order_security.html reconfig.html
Removed:            sec_faq.html security.html violation.html
Removed:   dist/construct/templates/regions Tag: LINUXIA
Removed:            LEFTONLY_BOTTOM NOLEFT_BOTTOM
Removed:   dist/construct/tmp Tag: LINUXIA .empty
Removed:   dist/construct/upload Tag: LINUXIA .empty
Removed:   dist/lib/UI/pages/admin Tag: LINUXIA advanced.html
Removed:            compedit.html flex_select_box.html genreport.html
Removed:            genstats.html genupload.html genxport.html
Removed:            page_new.html upload_other.html
Removed:   dist/lib/UI/usertag Tag: LINUXIA available_ups_internal
Removed:            available_www_shipping backup_file base_url button
Removed:            check_upload db_columns db_hash dbinfo
Removed:            directive_value dump_session e export_database
Removed:            field_label file_info file_navigator global_value
Removed:            grep_mm if_key_exists if_sql ifdef ifndef
Removed:            list_databases list_glob list_keys list_pages
Removed:            mm_value newer quick_table read_serial
Removed:            read_shipping read_ui_template return_to
Removed:            rotate_database rotate_file rotate_table send_help
Removed:            set_alias set_click setvar substitute title_bar
Removed:            unconfigure uneval unlink_file with
Removed:            write_relative_file write_shipping
Removed:   dist/simple Tag: LINUXIA catalog.cfg
Removed:   dist/simple/backup Tag: LINUXIA .empty
Removed:   dist/simple/config Tag: LINUXIA additional_fields
Removed:            additional_help postcopy_commands precopy_commands
Removed:   dist/simple/config/blue1 Tag: LINUXIA leftside logobar
Removed:   dist/simple/config/brown1 Tag: LINUXIA leftside logobar
Removed:   dist/simple/config/yellow1 Tag: LINUXIA leftside logobar
Removed:   dist/simple/etc Tag: LINUXIA area.recordnumber
Removed:            cat.recordnumber profiles.login profiles.order
Removed:            ship_notice
Removed:   dist/simple/html Tag: LINUXIA index.html
Removed:   dist/simple/images Tag: LINUXIA bg.gif poweredby.gif
Removed:   dist/simple/images/items Tag: LINUXIA poweredby.gif
Removed:   dist/simple/logs Tag: LINUXIA .empty
Removed:   dist/simple/mysql Tag: LINUXIA affiliate.mysql area.mysql
Removed:            cat.mysql inventory.mysql merchandising.mysql
Removed:            pricing.mysql products.mysql transactions.mysql
Removed:            userdb.mysql
Removed:   dist/simple/pages Tag: LINUXIA about.html account.html
Removed:            browse.html browse1.html canceled.html
Removed:            feedback.html flypage.html index.html login.html
Removed:            logout.html new_account.html news.html
Removed:            no_cookie.html privacy.html quantity.html
Removed:            results.html splash.html srchform.html
Removed:   dist/simple/pages/action Tag: LINUXIA get_password.html
Removed:   dist/simple/pages/multi Tag: LINUXIA b_address.html
Removed:            basket.html checkout.html final.html shipping.html
Removed:   dist/simple/pages/ord Tag: LINUXIA basket.html checkout.html
Removed:   dist/simple/pages/query Tag: LINUXIA check_orders.html
Removed:            order_detail.html
Removed:   dist/simple/pages/special Tag: LINUXIA feedback.html
Removed:            needfield.html
Removed:   dist/simple/pgsql Tag: LINUXIA area.pgsql cat.pgsql
Removed:            inventory.pgsql merchandising.pgsql pricing.pgsql
Removed:            products.pgsql transactions.pgsql userdb.pgsql
Removed:   dist/simple/products Tag: LINUXIA access.asc affiliate.txt
Removed:            area.txt cat.txt inventory.txt merchandising.txt
Removed:            orderline.txt pricing.txt products.txt route.txt
Removed:            state.txt transactions.txt variable.txt
Removed:   dist/simple/special_pages Tag: LINUXIA sec_faq.html
Removed:            security.html
Removed:   dist/simple/templates Tag: LINUXIA standalone standard
Removed:   dist/usertag Tag: LINUXIA button convert_date fcounter
Removed:            ups_query usertrack xml_generator
Removed:   eg       Tag: LINUXIA make_gnumeric.sh
Removed:   extensions/quickbooks/pages/admin Tag: LINUXIA
Removed:            export_coa.html export_items.html import_items.html
Removed:            index.html
Removed:   extensions/quickbooks/usertag Tag: LINUXIA
Removed:            export_quicken_coa export_quicken_items
Removed:            import_quicken_items
Removed:   lib/Vend Tag: LINUXIA ECML.pm
Removed:   lib/Vend/Misc Tag: LINUXIA Static.pm
Removed:   perl     Tag: LINUXIA Interchange.pm
Removed:   pod      Tag: LINUXIA mv_metadata.pod mvrpm.pod
Removed:   share/akopia/ui/admin Tag: LINUXIA b-configure2.gif
Removed:            b-help2.gif b-items2.gif b-orders2.gif b-pages2.gif
Removed:            b-regenerate2.gif b-statistics2.gif back.sm.gif
Removed:            bg.gif bluedot.gif cleardot.gif coinlogo.jpg
Removed:            curve_left.gif curve_right.gif delete.gif delsm.gif
Removed:            down.gif folder.gif folder.open.gif greendot.gif
Removed:            icon_config.gif icon_design.gif icon_error.gif
Removed:            icon_help.gif icon_item.gif icon_merch.gif
Removed:            icon_orders.gif icon_pages.gif icon_people.gif
Removed:            icon_regen.gif icon_regen_anim.gif icon_stats.gif
Removed:            index.gif layout.gif left.gif plus.gif red_logo.gif
Removed:            reddot.gif right.gif tallyman_logo.gif up.gif
Removed:            widgets.gif
Removed:   share/akopia/ui/help Tag: LINUXIA help_check.pl help_make.pl
Removed:   share/akopia/ui/help/images Tag: LINUXIA cleardot.gif
Removed:            curve.left.help.gif curve.right.help.gif
Removed:            help.background.gif
Removed:   share/akopia/ui/navigation Tag: LINUXIA A1.gif A1_b.gif
Removed:            A3.gif A3_b.gif B1.gif B10.gif B2.gif B2_b.gif
Removed:            B2_c.gif B3.gif B3_b.gif B3_c.gif B4.gif B4_b.gif
Removed:            B4_c.gif B5.gif B5_b.gif B5_c.gif B6.gif B6_b.gif
Removed:            B6_c.gif B7.gif B7_b.gif B7_c.gif B8.gif B8_b.gif
Removed:            B8_c.gif B9.gif B9_b.gif B9_c.gif akopia_logo.gif
Removed:            cellbackground.gif spacer1.gif spacer2.gif
Removed:            spacer3.gif spacer4.gif spacer_tall.gif
Removed:   win      Tag: LINUXIA tlink.exe
Log:
updated LINUXIA branch to 4.9 sources in order to use it as testbed again

Revision  Changes    Path
No                   revision



No                   revision



1.3.4.2   +1 -0      interchange/.cvsignore


rev 1.3.4.2, prev_rev 1.3.4.1
Index: .cvsignore
===================================================================
RCS file: /var/cvs/interchange/.cvsignore,v
retrieving revision 1.3.4.1
retrieving revision 1.3.4.2
diff -u -r1.3.4.1 -r1.3.4.2
--- .cvsignore	24 Oct 2000 18:28:21 -0000	1.3.4.1
+++ .cvsignore	25 Jan 2003 22:20:29 -0000	1.3.4.2
@@ -10,3 +10,4 @@
 .cpan.tried
 install-stamp
 *.tar.gz
+



1.40.4.17 +1187 -666 interchange/MANIFEST


rev 1.40.4.17, prev_rev 1.40.4.16
Index: MANIFEST
===================================================================
RCS file: /var/cvs/interchange/MANIFEST,v
retrieving revision 1.40.4.16
retrieving revision 1.40.4.17
diff -u -r1.40.4.16 -r1.40.4.17
--- MANIFEST	3 Apr 2001 08:07:37 -0000	1.40.4.16
+++ MANIFEST	25 Jan 2003 22:20:29 -0000	1.40.4.17
@@ -1,459 +1,1029 @@
 LICENSE
-MANIFEST
+MANIFEST			This list of files
 MANIFEST.SKIP
 Makefile.PL
-QuickStart
 README
 README.cvs
 README.debian
-README.rpm
+README.rpm-dist
+SPECS/interchange-init
+SPECS/interchange-logrotate
+SPECS/interchange-wrapper
 SPECS/interchange.spec
-UPGRADE_FROM_MV3
+UPGRADE
 WHATSNEW
+code/ActionMap/foo.am
+code/Filter/convert_date.filter
+code/Filter/date2time.filter
+code/Filter/encrypt.filter
+code/Filter/lc.filter
+code/Filter/linkdecode.filter
+code/Filter/next_sequential.filter
+code/SystemTag/accessories.coretag
+code/SystemTag/accounting.coretag
+code/SystemTag/area.coretag
+code/SystemTag/assign.coretag
+code/SystemTag/attr_list.coretag
+code/SystemTag/banner.coretag
+code/SystemTag/calc.coretag
+code/SystemTag/calcn.coretag
+code/SystemTag/cart.coretag
+code/SystemTag/catch.coretag
+code/SystemTag/cgi.coretag
+code/SystemTag/charge.coretag
+code/SystemTag/checked.coretag
+code/SystemTag/control.coretag
+code/SystemTag/control_set.coretag
+code/SystemTag/counter.coretag
+code/SystemTag/currency.coretag
+code/SystemTag/data.coretag
+code/SystemTag/default.coretag
+code/SystemTag/deliver.coretag
+code/SystemTag/description.coretag
+code/SystemTag/discount.coretag
+code/SystemTag/dump.coretag
+code/SystemTag/either.coretag
+code/SystemTag/error.coretag
+code/SystemTag/export.coretag
+code/SystemTag/field.coretag
+code/SystemTag/file.coretag
+code/SystemTag/filter.coretag
+code/SystemTag/flag.coretag
+code/SystemTag/fly_list.coretag
+code/SystemTag/fly_tax.coretag
+code/SystemTag/handling.coretag
+code/SystemTag/harness.coretag
+code/SystemTag/html_table.coretag
+code/SystemTag/image.tag
+code/SystemTag/import.coretag
+code/SystemTag/include.coretag
+code/SystemTag/index.coretag
+code/SystemTag/input_filter.coretag
+code/SystemTag/item_list.coretag
+code/SystemTag/levies.coretag
+code/SystemTag/levy_list.coretag
+code/SystemTag/log.coretag
+code/SystemTag/loop.coretag
+code/SystemTag/mail.coretag
+code/SystemTag/menu.coretag
+code/SystemTag/msg.coretag
+code/SystemTag/mvasp.coretag
+code/SystemTag/nitems.coretag
+code/SystemTag/onfly.coretag
+code/SystemTag/options.coretag
+code/SystemTag/order.coretag
+code/SystemTag/output_to.tag
+code/SystemTag/page.coretag
+code/SystemTag/parse_locale.coretag
+code/SystemTag/perl.coretag
+code/SystemTag/price.coretag
+code/SystemTag/process.coretag
+code/SystemTag/profile.coretag
+code/SystemTag/query.coretag
+code/SystemTag/read_cookie.coretag
+code/SystemTag/record.coretag
+code/SystemTag/region.coretag
+code/SystemTag/row.coretag
+code/SystemTag/salestax.coretag
+code/SystemTag/scratch.coretag
+code/SystemTag/scratchd.coretag
+code/SystemTag/search_region.coretag
+code/SystemTag/selected.coretag
+code/SystemTag/set.coretag
+code/SystemTag/set_cookie.coretag
+code/SystemTag/seti.coretag
+code/SystemTag/setlocale.coretag
+code/SystemTag/shipping.coretag
+code/SystemTag/shipping_desc.coretag
+code/SystemTag/soap.coretag
+code/SystemTag/sql.coretag
+code/SystemTag/strip.coretag
+code/SystemTag/subtotal.coretag
+code/SystemTag/tag.coretag
+code/SystemTag/time.coretag
+code/SystemTag/timed_build.coretag
+code/SystemTag/tmp.coretag
+code/SystemTag/tmpn.coretag
+code/SystemTag/total_cost.coretag
+code/SystemTag/tree.coretag
+code/SystemTag/try.coretag
+code/SystemTag/unpack.coretag
+code/SystemTag/update.coretag
+code/SystemTag/userdb.coretag
+code/SystemTag/value.coretag
+code/SystemTag/value_extended.coretag
+code/SystemTag/warnings.coretag
+code/UI_Tag/add_gpg_key.coretag
+code/UI_Tag/assume_identity.tag
+code/UI_Tag/auto_wizard.coretag
+code/UI_Tag/available_ups_internal.coretag
+code/UI_Tag/available_www_shipping.coretag
+code/UI_Tag/backup_database.coretag
+code/UI_Tag/backup_file.coretag
+code/UI_Tag/base_url.coretag
+code/UI_Tag/check_upload.coretag
+code/UI_Tag/content_editor.coretag
+code/UI_Tag/content_info.coretag
+code/UI_Tag/content_modify.coretag
+code/UI_Tag/cp.coretag
+code/UI_Tag/crypt.coretag
+code/UI_Tag/db_columns.coretag
+code/UI_Tag/db_hash.coretag
+code/UI_Tag/diff.coretag
+code/UI_Tag/diffmerge.coretag
+code/UI_Tag/directive_value.coretag
+code/UI_Tag/display.coretag
+code/UI_Tag/dump_session.coretag
+code/UI_Tag/export_database.coretag
+code/UI_Tag/file_info.coretag
+code/UI_Tag/file_navigator.coretag
+code/UI_Tag/filters.coretag
+code/UI_Tag/get_gpg_keys.coretag
+code/UI_Tag/global_value.coretag
+code/UI_Tag/grep_mm.coretag
+code/UI_Tag/if_mm.coretag
+code/UI_Tag/image_collate.coretag
+code/UI_Tag/import_fields.coretag
+code/UI_Tag/jsq.coretag
+code/UI_Tag/jsqn.coretag
+code/UI_Tag/list_databases.coretag
+code/UI_Tag/list_glob.coretag
+code/UI_Tag/list_keys.coretag
+code/UI_Tag/list_pages.coretag
+code/UI_Tag/menu_load.coretag
+code/UI_Tag/meta_record.coretag
+code/UI_Tag/mm_locale.coretag
+code/UI_Tag/mm_value.coretag
+code/UI_Tag/newer.coretag
+code/UI_Tag/quick_table.coretag
+code/UI_Tag/read_shipping.coretag
+code/UI_Tag/reconfig.coretag
+code/UI_Tag/reconfig_time.coretag
+code/UI_Tag/regenerate.coretag
+code/UI_Tag/return_to.coretag
+code/UI_Tag/rotate_table.coretag
+code/UI_Tag/row_edit.coretag
+code/UI_Tag/run_profile.coretag
+code/UI_Tag/su.coretag
+code/UI_Tag/substitute_file.coretag
+code/UI_Tag/tabbed_display.coretag
+code/UI_Tag/table_editor.coretag
+code/UI_Tag/uneval.coretag
+code/UI_Tag/unlink_file.coretag
+code/UI_Tag/update_order_status.tag
+code/UI_Tag/version.coretag
+code/UI_Tag/widget.coretag
+code/UI_Tag/write_relative_file.coretag
+code/UI_Tag/write_shipping.coretag
+code/UserTag/bar_button.tag
+code/UserTag/button.tag
+code/UserTag/component.tag
+code/UserTag/convert_date.tag
+code/UserTag/db_date.tag
+code/UserTag/delete_cart.tag
+code/UserTag/email.tag
+code/UserTag/email_raw.tag
+code/UserTag/env.tag
+code/UserTag/fedex_query.tag
+code/UserTag/formel.tag
+code/UserTag/fortune.tag
+code/UserTag/forum.tag
+code/UserTag/get_url.tag
+code/UserTag/history_scan.tag
+code/UserTag/load_cart.tag
+code/UserTag/loc.tag
+code/UserTag/page_meta.tag
+code/UserTag/rand.tag
+code/UserTag/save_cart.tag
+code/UserTag/summary.tag
+code/UserTag/table_organize.tag
+code/UserTag/title_bar.tag
+code/UserTag/ups_query.tag
+code/UserTag/usertrack.tag
+code/UserTag/var.tag
+code/Widget/gpg_keys.widget
+code/Widget/imagedir.widget
+code/Widget/imagehelper.widget
+code/Widget/uploadhelper.widget
 configure
+debian/400mod_interchange.info
+debian/CREDITS.debian
+debian/TODO
+debian/catalogs.cfg
+debian/changelog
+debian/control
+debian/copyright
+debian/docs
+debian/interchange-cat-foundation.config
+debian/interchange-cat-foundation.files
+debian/interchange-cat-foundation.postinst
+debian/interchange-cat-foundation.postrm
+debian/interchange-cat-foundation.prerm
+debian/interchange-cat-foundation.templates
+debian/interchange-ui.config
+debian/interchange-ui.files
+debian/interchange-ui.postinst
+debian/interchange-ui.postrm
+debian/interchange-ui.preinst
+debian/interchange-ui.prerm
+debian/interchange-ui.templates
+debian/interchange.cfg
+debian/interchange.conffiles
+debian/interchange.config
+debian/interchange.cron.daily
+debian/interchange.dirs
+debian/interchange.docs
+debian/interchange.files
+debian/interchange.init
+debian/interchange.logrotate
+debian/interchange.postinst
+debian/interchange.preinst
+debian/interchange.prerm
+debian/interchange.templates
+debian/interchange.wrapper
+debian/interchangeconfig
+debian/libapache-mod-interchange.doc-base
+debian/libapache-mod-interchange.docs
+debian/libapache-mod-interchange.files
+debian/makecat.cfg
+debian/makecat.wrapper
+debian/rules
 dist/catalog_after.cfg
 dist/catalog_before.cfg
-dist/construct/backup/.empty
-dist/construct/catalog.cfg
-dist/construct/config/additional_fields
-dist/construct/config/additional_help
-dist/construct/config/postcopy_commands
-dist/construct/config/precopy_commands
-dist/construct/dbconf/default_db/2ndDayAir.dbm
-dist/construct/dbconf/default_db/Ground.dbm
-dist/construct/dbconf/default_db/NextDayAir.dbm
-dist/construct/dbconf/default_db/access.dbm
-dist/construct/dbconf/default_db/affiliate.dbm
-dist/construct/dbconf/default_db/area.dbm
-dist/construct/dbconf/default_db/banner.dbm
-dist/construct/dbconf/default_db/cat.dbm
-dist/construct/dbconf/default_db/country.dbm
-dist/construct/dbconf/default_db/gift_certs.dbm
-dist/construct/dbconf/default_db/inventory.dbm
-dist/construct/dbconf/default_db/locale.dbm
-dist/construct/dbconf/default_db/merchandising.dbm
-dist/construct/dbconf/default_db/mv_metadata.dbm
-dist/construct/dbconf/default_db/order_returns.dbm
-dist/construct/dbconf/default_db/orderline.dbm
-dist/construct/dbconf/default_db/pricing.dbm
-dist/construct/dbconf/default_db/products.dbm
-dist/construct/dbconf/default_db/recurring_items.dbm
-dist/construct/dbconf/default_db/recurring_orders.dbm
-dist/construct/dbconf/default_db/ship_addresses.dbm
-dist/construct/dbconf/default_db/transactions.dbm
-dist/construct/dbconf/default_db/userdb.dbm
-dist/construct/dbconf/default_db/variable.dbm
-dist/construct/dbconf/mysql/2ndDayAir.dbm
-dist/construct/dbconf/mysql/Ground.dbm
-dist/construct/dbconf/mysql/NextDayAir.dbm
-dist/construct/dbconf/mysql/access.dbm
-dist/construct/dbconf/mysql/affiliate.mysql
-dist/construct/dbconf/mysql/area.mysql
-dist/construct/dbconf/mysql/banner.dbm
-dist/construct/dbconf/mysql/cat.mysql
-dist/construct/dbconf/mysql/country.mysql
-dist/construct/dbconf/mysql/gift_certs.mysql
-dist/construct/dbconf/mysql/inventory.mysql
-dist/construct/dbconf/mysql/locale.dbm
-dist/construct/dbconf/mysql/merchandising.mysql
-dist/construct/dbconf/mysql/mv_metadata.dbm
-dist/construct/dbconf/mysql/order_returns.mysql
-dist/construct/dbconf/mysql/orderline.mysql
-dist/construct/dbconf/mysql/pricing.mysql
-dist/construct/dbconf/mysql/products.mysql
-dist/construct/dbconf/mysql/recurring_items.mysql
-dist/construct/dbconf/mysql/recurring_orders.mysql
-dist/construct/dbconf/mysql/ship_addresses.mysql
-dist/construct/dbconf/mysql/transactions.mysql
-dist/construct/dbconf/mysql/userdb.mysql
-dist/construct/dbconf/mysql/variable.dbm
-dist/construct/dbconf/oracle/2ndDayAir.dbm
-dist/construct/dbconf/oracle/Ground.dbm
-dist/construct/dbconf/oracle/NextDayAir.dbm
-dist/construct/dbconf/oracle/access.dbm
-dist/construct/dbconf/oracle/affiliate.ora
-dist/construct/dbconf/oracle/area.ora
-dist/construct/dbconf/oracle/banner.dbm
-dist/construct/dbconf/oracle/cat.ora
-dist/construct/dbconf/oracle/country.ora
-dist/construct/dbconf/oracle/gift_certs.ora
-dist/construct/dbconf/oracle/inventory.ora
-dist/construct/dbconf/oracle/locale.dbm
-dist/construct/dbconf/oracle/merchandising.ora
-dist/construct/dbconf/oracle/mv_metadata.dbm
-dist/construct/dbconf/oracle/order_returns.ora
-dist/construct/dbconf/oracle/orderline.ora
-dist/construct/dbconf/oracle/pricing.ora
-dist/construct/dbconf/oracle/products.ora
-dist/construct/dbconf/oracle/recurring_items.ora
-dist/construct/dbconf/oracle/recurring_orders.ora
-dist/construct/dbconf/oracle/ship_addresses.ora
-dist/construct/dbconf/oracle/transactions.ora
-dist/construct/dbconf/oracle/userdb.ora
-dist/construct/dbconf/oracle/variable.dbm
-dist/construct/dbconf/pgsql/2ndDayAir.dbm
-dist/construct/dbconf/pgsql/Ground.dbm
-dist/construct/dbconf/pgsql/NextDayAir.dbm
-dist/construct/dbconf/pgsql/access.dbm
-dist/construct/dbconf/pgsql/affiliate.pgsql
-dist/construct/dbconf/pgsql/area.pgsql
-dist/construct/dbconf/pgsql/banner.dbm
-dist/construct/dbconf/pgsql/cat.pgsql
-dist/construct/dbconf/pgsql/country.pgsql
-dist/construct/dbconf/pgsql/gift_certs.pgsql
-dist/construct/dbconf/pgsql/inventory.pgsql
-dist/construct/dbconf/pgsql/locale.dbm
-dist/construct/dbconf/pgsql/merchandising.pgsql
-dist/construct/dbconf/pgsql/mv_metadata.dbm
-dist/construct/dbconf/pgsql/order_returns.pgsql
-dist/construct/dbconf/pgsql/orderline.pgsql
-dist/construct/dbconf/pgsql/pricing.pgsql
-dist/construct/dbconf/pgsql/products.pgsql
-dist/construct/dbconf/pgsql/recurring_items.pgsql
-dist/construct/dbconf/pgsql/recurring_orders.pgsql
-dist/construct/dbconf/pgsql/ship_addresses.pgsql
-dist/construct/dbconf/pgsql/transactions.pgsql
-dist/construct/dbconf/pgsql/userdb.pgsql
-dist/construct/dbconf/pgsql/variable.dbm
-dist/construct/etc/log_entry
-dist/construct/etc/log_transaction
-dist/construct/etc/mail_receipt
-dist/construct/etc/profiles.login
-dist/construct/etc/profiles.order
-dist/construct/etc/receipt.html
-dist/construct/etc/report
-dist/construct/etc/ship_notice
-dist/construct/html/index.html
-dist/construct/images/affiliate/hardhat.gif
-dist/construct/images/bg.gif
-dist/construct/images/clear.gif
-dist/construct/images/items/gift_certificate_large.gif
-dist/construct/images/items/os28004.gif
-dist/construct/images/items/os28005.gif
-dist/construct/images/items/os28006.gif
-dist/construct/images/items/os28007.gif
-dist/construct/images/items/os28008.gif
-dist/construct/images/items/os28009.gif
-dist/construct/images/items/os28011.gif
-dist/construct/images/items/os28044.gif
-dist/construct/images/items/os28057a.gif
-dist/construct/images/items/os28057b.gif
-dist/construct/images/items/os28057c.gif
-dist/construct/images/items/os28062.gif
-dist/construct/images/items/os28064.gif
-dist/construct/images/items/os28065.gif
-dist/construct/images/items/os28066.gif
-dist/construct/images/items/os28068.gif
-dist/construct/images/items/os28068a.gif
-dist/construct/images/items/os28068b.gif
-dist/construct/images/items/os28069.gif
-dist/construct/images/items/os28070.gif
-dist/construct/images/items/os28072.gif
-dist/construct/images/items/os28073.gif
-dist/construct/images/items/os28074.gif
-dist/construct/images/items/os28075.gif
-dist/construct/images/items/os28076.gif
-dist/construct/images/items/os28077.gif
-dist/construct/images/items/os28080.gif
-dist/construct/images/items/os28081.gif
-dist/construct/images/items/os28082.gif
-dist/construct/images/items/os28084.gif
-dist/construct/images/items/os28085.gif
-dist/construct/images/items/os28086.gif
-dist/construct/images/items/os28087.gif
-dist/construct/images/items/os28108.gif
-dist/construct/images/items/os28109.gif
-dist/construct/images/items/os28110.gif
-dist/construct/images/items/os28111.gif
-dist/construct/images/items/os28112.gif
-dist/construct/images/items/os28113.gif
-dist/construct/images/items/os29000.gif
-dist/construct/images/navigation/a1.gif
-dist/construct/images/navigation/a2.gif
-dist/construct/images/navigation/a3.gif
-dist/construct/images/navigation/b1.gif
-dist/construct/images/navigation/b1_b.gif
-dist/construct/images/navigation/b2.gif
-dist/construct/images/navigation/b2_b.gif
-dist/construct/images/navigation/b3.gif
-dist/construct/images/navigation/b3_b.gif
-dist/construct/images/navigation/b4.gif
-dist/construct/images/navigation/b4_b.gif
-dist/construct/images/navigation/b5.gif
-dist/construct/images/navigation/b5_b.gif
-dist/construct/images/navigation/b6.gif
-dist/construct/images/navigation/b6_b.gif
-dist/construct/images/navigation/b7.gif
-dist/construct/images/navigation/buy_now.gif
-dist/construct/images/navigation/c.gif
-dist/construct/images/navigation/checkout_button.gif
-dist/construct/images/navigation/continue_shopping.gif
-dist/construct/images/navigation/coupon_item.gif
-dist/construct/images/navigation/d.gif
-dist/construct/images/navigation/d1.gif
-dist/construct/images/navigation/d2.gif
-dist/construct/images/navigation/d3.gif
-dist/construct/images/navigation/default_a.gif
-dist/construct/images/navigation/default_b.gif
-dist/construct/images/navigation/go.gif
-dist/construct/images/navigation/go_b.gif
-dist/construct/images/navigation/header_handtools.gif
-dist/construct/images/navigation/header_ladders.gif
-dist/construct/images/navigation/header_measuringtools.gif
-dist/construct/images/navigation/header_paintingsupplies.gif
-dist/construct/images/navigation/header_safetyequipment.gif
-dist/construct/images/navigation/header_toolstorage.gif
-dist/construct/images/navigation/logout.gif
-dist/construct/images/navigation/logout_b.gif
-dist/construct/images/navigation/minime1.gif
-dist/construct/images/navigation/minime2.gif
-dist/construct/images/navigation/orangespacer.gif
-dist/construct/images/navigation/poweredby.gif
-dist/construct/images/navigation/recalculate_button.gif
-dist/construct/images/navigation/whitey.gif
-dist/construct/images/poweredby.gif
-dist/construct/images/smallamex.png
-dist/construct/images/smalldisc.png
-dist/construct/images/smallmc.png
-dist/construct/images/smallvisa.png
-dist/construct/images/thumb/gift_certificate.gif
-dist/construct/images/thumb/os28004_b.gif
-dist/construct/images/thumb/os28005_b.gif
-dist/construct/images/thumb/os28006_b.gif
-dist/construct/images/thumb/os28007_b.gif
-dist/construct/images/thumb/os28008_b.gif
-dist/construct/images/thumb/os28009_b.gif
-dist/construct/images/thumb/os28011_b.gif
-dist/construct/images/thumb/os28044_b.gif
-dist/construct/images/thumb/os28057a_b.gif
-dist/construct/images/thumb/os28057b_b.gif
-dist/construct/images/thumb/os28057c_b.gif
-dist/construct/images/thumb/os28062_b.gif
-dist/construct/images/thumb/os28064_b.gif
-dist/construct/images/thumb/os28065_b.gif
-dist/construct/images/thumb/os28066_b.gif
-dist/construct/images/thumb/os28068_b.gif
-dist/construct/images/thumb/os28068a_b.gif
-dist/construct/images/thumb/os28068b_b.gif
-dist/construct/images/thumb/os28069_b.gif
-dist/construct/images/thumb/os28070_b.gif
-dist/construct/images/thumb/os28072_b.gif
-dist/construct/images/thumb/os28073_b.gif
-dist/construct/images/thumb/os28074_b.gif
-dist/construct/images/thumb/os28075_b.gif
-dist/construct/images/thumb/os28076_b.gif
-dist/construct/images/thumb/os28077_b.gif
-dist/construct/images/thumb/os28080_b.gif
-dist/construct/images/thumb/os28081_b.gif
-dist/construct/images/thumb/os28082_b.gif
-dist/construct/images/thumb/os28084_b.gif
-dist/construct/images/thumb/os28085_b.gif
-dist/construct/images/thumb/os28086_b.gif
-dist/construct/images/thumb/os28087_b.gif
-dist/construct/images/thumb/os28108_b.gif
-dist/construct/images/thumb/os28109_b.gif
-dist/construct/images/thumb/os28110_b.gif
-dist/construct/images/thumb/os28111_b.gif
-dist/construct/images/thumb/os28112_b.gif
-dist/construct/images/thumb/os28113_b.gif
-dist/construct/images/thumb/os29000_b.gif
-dist/construct/logs/.empty
-dist/construct/orders/.empty
-dist/construct/pages/aboutus.html
-dist/construct/pages/account.html
-dist/construct/pages/admin/report_def/Order%20Status.html
-dist/construct/pages/admin/report_def/Products%20to%20edit.html
-dist/construct/pages/admin/reports/Order%20Status.html
-dist/construct/pages/admin/reports/Products%20to%20edit.html
-dist/construct/pages/affiliate/index.html
-dist/construct/pages/affiliate/login.html
-dist/construct/pages/browse.html
-dist/construct/pages/canceled.html
-dist/construct/pages/contact.html
-dist/construct/pages/customerservice.html
-dist/construct/pages/flypage.html
-dist/construct/pages/help.html
-dist/construct/pages/index.html
-dist/construct/pages/login.html
-dist/construct/pages/logout.html
-dist/construct/pages/new_account.html
-dist/construct/pages/ord/basket.html
-dist/construct/pages/ord/checkout.html
-dist/construct/pages/privacypolicy.html
-dist/construct/pages/process_return.html
-dist/construct/pages/quantity.html
-dist/construct/pages/query/check_orders.html
-dist/construct/pages/query/order_detail.html
-dist/construct/pages/query/order_return.html
-dist/construct/pages/recurring_add.html
-dist/construct/pages/recurring_orders.html
-dist/construct/pages/recurring_orders_added.html
-dist/construct/pages/recurring_orders_removed.html
-dist/construct/pages/results.html
-dist/construct/pages/results_big.html
-dist/construct/pages/returns.html
-dist/construct/pages/ship_addresses.html
-dist/construct/pages/ship_addresses_added.html
-dist/construct/pages/ship_addresses_removed.html
-dist/construct/pages/splash.html
-dist/construct/pages/stock-alert-added.html
-dist/construct/pages/stock-alert.html
-dist/construct/pages/swap_results.html
-dist/construct/products/2ndDayAir.csv
-dist/construct/products/2ndDayAirAM.csv
-dist/construct/products/3DaySelect.csv
-dist/construct/products/3DaySelectRes.csv
-dist/construct/products/450.csv
-dist/construct/products/Ground.csv
-dist/construct/products/GroundComm.csv
-dist/construct/products/GroundRes.csv
-dist/construct/products/NextDayAir.csv
-dist/construct/products/NextDayAirSaver.csv
-dist/construct/products/access.asc
-dist/construct/products/affiliate.txt
-dist/construct/products/area.txt
-dist/construct/products/banner.txt
-dist/construct/products/cat.txt
-dist/construct/products/country.txt
-dist/construct/products/gift_certs.txt
-dist/construct/products/inventory.txt
-dist/construct/products/locale.txt
-dist/construct/products/merchandising.txt
-dist/construct/products/mv_metadata.asc
-dist/construct/products/order_returns.txt
-dist/construct/products/orderline.txt
-dist/construct/products/pricing.txt
-dist/construct/products/products.txt
-dist/construct/products/recurring_items.txt
-dist/construct/products/recurring_orders.txt
-dist/construct/products/route.txt
-dist/construct/products/salestax.asc
-dist/construct/products/ship_addresses.txt
-dist/construct/products/shipping.asc
-dist/construct/products/state.txt
-dist/construct/products/transactions.txt
-dist/construct/products/ups_zone.asc
-dist/construct/products/userdb.txt
-dist/construct/products/variable.txt
-dist/construct/session/.empty
-dist/construct/special_pages/badsearch.html
-dist/construct/special_pages/canceled.html
-dist/construct/special_pages/cc_not_valid.html
-dist/construct/special_pages/confirmation.html
-dist/construct/special_pages/failed.html
-dist/construct/special_pages/interact.html
-dist/construct/special_pages/missing.html
-dist/construct/special_pages/needfield.html
-dist/construct/special_pages/nomatch.html
-dist/construct/special_pages/noproduct.html
-dist/construct/special_pages/notfound.html
-dist/construct/special_pages/order_security.html
-dist/construct/special_pages/reconfig.html
-dist/construct/special_pages/sec_faq.html
-dist/construct/special_pages/security.html
-dist/construct/special_pages/violation.html
-dist/construct/templates/cart
-dist/construct/templates/components/best_horizontal
-dist/construct/templates/components/best_vertical
-dist/construct/templates/components/cart
-dist/construct/templates/components/cart_display
-dist/construct/templates/components/cart_tiny
-dist/construct/templates/components/category_vertical
-dist/construct/templates/components/cross_horizontal
-dist/construct/templates/components/cross_vertical
-dist/construct/templates/components/promo_horizontal
-dist/construct/templates/components/promo_vertical
-dist/construct/templates/components/random_horizontal
-dist/construct/templates/components/random_vertical
-dist/construct/templates/components/upsell_horizontal
-dist/construct/templates/components/upsell_vertical
-dist/construct/templates/fullwidth
-dist/construct/templates/leftonly
-dist/construct/templates/leftright
-dist/construct/templates/regions/LEFTONLY_BOTTOM
-dist/construct/templates/regions/LEFTONLY_TOP
-dist/construct/templates/regions/LEFTRIGHT_BOTTOM
-dist/construct/templates/regions/LEFTRIGHT_TOP
-dist/construct/templates/regions/NOLEFT_BOTTOM
-dist/construct/templates/regions/NOLEFT_TOP
-dist/construct/templates/regions/SEL_ALL_BOTTOM
-dist/construct/templates/regions/SEL_ALL_TOP
-dist/construct/templates/regions/SEL_LEFT_BOTTOM
-dist/construct/templates/regions/SEL_LEFT_TOP
-dist/construct/templates/sel_all
-dist/construct/templates/sel_left
-dist/construct/tmp/.empty
-dist/construct/upload/.empty
 dist/error.log
 dist/etc/.empty
+dist/foundation/backup/.empty
+dist/foundation/catalog.cfg
+dist/foundation/config/additional_fields
+dist/foundation/config/additional_help
+dist/foundation/config/installsample
+dist/foundation/config/makedirs
+dist/foundation/config/postcopy_commands
+dist/foundation/config/precopy_commands
+dist/foundation/dbconf/default_db/2ndDayAir.dbm
+dist/foundation/dbconf/default_db/Ground.dbm
+dist/foundation/dbconf/default_db/NextDayAir.dbm
+dist/foundation/dbconf/default_db/access.dbm
+dist/foundation/dbconf/default_db/affiliate.dbm
+dist/foundation/dbconf/default_db/area.dbm
+dist/foundation/dbconf/default_db/cat.dbm
+dist/foundation/dbconf/default_db/component.dbm
+dist/foundation/dbconf/default_db/country.dbm
+dist/foundation/dbconf/default_db/default_db.cfg
+dist/foundation/dbconf/default_db/forum.dbm
+dist/foundation/dbconf/default_db/gift_certs.dbm
+dist/foundation/dbconf/default_db/inventory.dbm
+dist/foundation/dbconf/default_db/locale.dbm
+dist/foundation/dbconf/default_db/merchandising.dbm
+dist/foundation/dbconf/default_db/mv_metadata.dbm
+dist/foundation/dbconf/default_db/options.dbm
+dist/foundation/dbconf/default_db/order_returns.dbm
+dist/foundation/dbconf/default_db/orderline.dbm
+dist/foundation/dbconf/default_db/pricing.dbm
+dist/foundation/dbconf/default_db/products.dbm
+dist/foundation/dbconf/default_db/state.dbm
+dist/foundation/dbconf/default_db/survey.dbm
+dist/foundation/dbconf/default_db/transactions.dbm
+dist/foundation/dbconf/default_db/tree.dbm
+dist/foundation/dbconf/default_db/userdb.dbm
+dist/foundation/dbconf/default_db/variable.dbm
+dist/foundation/dbconf/locales/de_DE.cfg
+dist/foundation/dbconf/locales/default.cfg
+dist/foundation/dbconf/mysql/2ndDayAir.dbm
+dist/foundation/dbconf/mysql/Ground.dbm
+dist/foundation/dbconf/mysql/NextDayAir.dbm
+dist/foundation/dbconf/mysql/access.dbm
+dist/foundation/dbconf/mysql/affiliate.mysql
+dist/foundation/dbconf/mysql/area.mysql
+dist/foundation/dbconf/mysql/cat.mysql
+dist/foundation/dbconf/mysql/component.dbm
+dist/foundation/dbconf/mysql/country.mysql
+dist/foundation/dbconf/mysql/forum.mysql
+dist/foundation/dbconf/mysql/gift_certs.mysql
+dist/foundation/dbconf/mysql/inventory.mysql
+dist/foundation/dbconf/mysql/locale.dbm
+dist/foundation/dbconf/mysql/merchandising.mysql
+dist/foundation/dbconf/mysql/mv_metadata.dbm
+dist/foundation/dbconf/mysql/mysql.cfg
+dist/foundation/dbconf/mysql/options.mysql
+dist/foundation/dbconf/mysql/order_returns.mysql
+dist/foundation/dbconf/mysql/orderline.mysql
+dist/foundation/dbconf/mysql/pricing.mysql
+dist/foundation/dbconf/mysql/products.mysql
+dist/foundation/dbconf/mysql/state.mysql
+dist/foundation/dbconf/mysql/survey.dbm
+dist/foundation/dbconf/mysql/transactions.mysql
+dist/foundation/dbconf/mysql/tree.mysql
+dist/foundation/dbconf/mysql/userdb.mysql
+dist/foundation/dbconf/mysql/variable.dbm
+dist/foundation/dbconf/oracle/2ndDayAir.dbm
+dist/foundation/dbconf/oracle/Ground.dbm
+dist/foundation/dbconf/oracle/NextDayAir.dbm
+dist/foundation/dbconf/oracle/access.dbm
+dist/foundation/dbconf/oracle/affiliate.ora
+dist/foundation/dbconf/oracle/area.ora
+dist/foundation/dbconf/oracle/cat.ora
+dist/foundation/dbconf/oracle/component.dbm
+dist/foundation/dbconf/oracle/country.ora
+dist/foundation/dbconf/oracle/gift_certs.ora
+dist/foundation/dbconf/oracle/inventory.ora
+dist/foundation/dbconf/oracle/locale.dbm
+dist/foundation/dbconf/oracle/merchandising.ora
+dist/foundation/dbconf/oracle/mv_metadata.dbm
+dist/foundation/dbconf/oracle/options.ora
+dist/foundation/dbconf/oracle/oracle.cfg
+dist/foundation/dbconf/oracle/order_returns.ora
+dist/foundation/dbconf/oracle/orderline.ora
+dist/foundation/dbconf/oracle/pricing.ora
+dist/foundation/dbconf/oracle/products.ora
+dist/foundation/dbconf/oracle/state.ora
+dist/foundation/dbconf/oracle/survey.dbm
+dist/foundation/dbconf/oracle/transactions.ora
+dist/foundation/dbconf/oracle/tree.ora
+dist/foundation/dbconf/oracle/userdb.ora
+dist/foundation/dbconf/oracle/variable.dbm
+dist/foundation/dbconf/pgsql/2ndDayAir.dbm
+dist/foundation/dbconf/pgsql/Ground.dbm
+dist/foundation/dbconf/pgsql/NextDayAir.dbm
+dist/foundation/dbconf/pgsql/access.dbm
+dist/foundation/dbconf/pgsql/affiliate.pgsql
+dist/foundation/dbconf/pgsql/area.pgsql
+dist/foundation/dbconf/pgsql/cat.pgsql
+dist/foundation/dbconf/pgsql/component.dbm
+dist/foundation/dbconf/pgsql/country.pgsql
+dist/foundation/dbconf/pgsql/forum.pgsql
+dist/foundation/dbconf/pgsql/gift_certs.pgsql
+dist/foundation/dbconf/pgsql/inventory.pgsql
+dist/foundation/dbconf/pgsql/locale.dbm
+dist/foundation/dbconf/pgsql/merchandising.pgsql
+dist/foundation/dbconf/pgsql/mv_metadata.dbm
+dist/foundation/dbconf/pgsql/options.pgsql
+dist/foundation/dbconf/pgsql/order_returns.pgsql
+dist/foundation/dbconf/pgsql/orderline.pgsql
+dist/foundation/dbconf/pgsql/pgsql.cfg
+dist/foundation/dbconf/pgsql/pricing.pgsql
+dist/foundation/dbconf/pgsql/products.pgsql
+dist/foundation/dbconf/pgsql/state.pgsql
+dist/foundation/dbconf/pgsql/survey.dbm
+dist/foundation/dbconf/pgsql/transactions.pgsql
+dist/foundation/dbconf/pgsql/tree.pgsql
+dist/foundation/dbconf/pgsql/userdb.pgsql
+dist/foundation/dbconf/pgsql/variable.dbm
+dist/foundation/etc/area.recordnumber
+dist/foundation/etc/cat.recordnumber
+dist/foundation/etc/log_entry
+dist/foundation/etc/log_transaction
+dist/foundation/etc/mail_receipt
+dist/foundation/etc/order.number
+dist/foundation/etc/profiles.login
+dist/foundation/etc/profiles.order
+dist/foundation/etc/receipt.html
+dist/foundation/etc/report
+dist/foundation/etc/return.number
+dist/foundation/etc/rma.number
+dist/foundation/etc/ship_notice
+dist/foundation/html/index.html
+dist/foundation/images/affiliate/hardhat.gif
+dist/foundation/images/bg.gif
+dist/foundation/images/blueyellow/about.gif
+dist/foundation/images/blueyellow/banner.gif
+dist/foundation/images/blueyellow/bar_filler.gif
+dist/foundation/images/blueyellow/buynow.gif
+dist/foundation/images/blueyellow/cart.gif
+dist/foundation/images/blueyellow/checkout.gif
+dist/foundation/images/blueyellow/checkout_button.gif
+dist/foundation/images/blueyellow/continue_shopping.gif
+dist/foundation/images/blueyellow/gift_certificate_large.gif
+dist/foundation/images/blueyellow/go.gif
+dist/foundation/images/blueyellow/home.gif
+dist/foundation/images/blueyellow/littlebar.gif
+dist/foundation/images/blueyellow/login.gif
+dist/foundation/images/blueyellow/logo.gif
+dist/foundation/images/blueyellow/logo2.gif
+dist/foundation/images/blueyellow/logout.gif
+dist/foundation/images/blueyellow/placeorder.gif
+dist/foundation/images/blueyellow/poweredby.gif
+dist/foundation/images/blueyellow/recalculate_button.gif
+dist/foundation/images/blueyellow/savecart.gif
+dist/foundation/images/blueyellow/saverecur.gif
+dist/foundation/images/blueyellow/search.gif
+dist/foundation/images/blueyellow/sep.gif
+dist/foundation/images/blueyellow/service.gif
+dist/foundation/images/blueyellow/thumb.gif
+dist/foundation/images/blueyellow/yourimage.gif
+dist/foundation/images/computer.xls
+dist/foundation/images/construct.xls
+dist/foundation/images/download.png
+dist/foundation/images/fc.gif
+dist/foundation/images/fixedwidth/about.gif
+dist/foundation/images/fixedwidth/banner.gif
+dist/foundation/images/fixedwidth/bar_filler.gif
+dist/foundation/images/fixedwidth/buynow.gif
+dist/foundation/images/fixedwidth/cart.gif
+dist/foundation/images/fixedwidth/checkout.gif
+dist/foundation/images/fixedwidth/checkout_button.gif
+dist/foundation/images/fixedwidth/continue_shopping.gif
+dist/foundation/images/fixedwidth/go.gif
+dist/foundation/images/fixedwidth/home.gif
+dist/foundation/images/fixedwidth/littlebar.gif
+dist/foundation/images/fixedwidth/login.gif
+dist/foundation/images/fixedwidth/logo.gif
+dist/foundation/images/fixedwidth/logo2.gif
+dist/foundation/images/fixedwidth/logout.gif
+dist/foundation/images/fixedwidth/placeorder.gif
+dist/foundation/images/fixedwidth/poweredby.gif
+dist/foundation/images/fixedwidth/recalculate_button.gif
+dist/foundation/images/fixedwidth/savecart.gif
+dist/foundation/images/fixedwidth/saverecur.gif
+dist/foundation/images/fixedwidth/search.gif
+dist/foundation/images/fixedwidth/sep.gif
+dist/foundation/images/fixedwidth/service.gif
+dist/foundation/images/fixedwidth/thumb.gif
+dist/foundation/images/fixedwidth/yourimage.gif
+dist/foundation/images/fo.gif
+dist/foundation/images/foundation/about.gif
+dist/foundation/images/foundation/buynow.gif
+dist/foundation/images/foundation/cart.gif
+dist/foundation/images/foundation/checkout.gif
+dist/foundation/images/foundation/checkout_button.gif
+dist/foundation/images/foundation/go.gif
+dist/foundation/images/foundation/home.gif
+dist/foundation/images/foundation/littlebar.gif
+dist/foundation/images/foundation/login.gif
+dist/foundation/images/foundation/logo.gif
+dist/foundation/images/foundation/logo2.gif
+dist/foundation/images/foundation/logout.gif
+dist/foundation/images/foundation/placeorder.gif
+dist/foundation/images/foundation/poweredby.gif
+dist/foundation/images/foundation/recalculate_button.gif
+dist/foundation/images/foundation/savecart.gif
+dist/foundation/images/foundation/saverecur.gif
+dist/foundation/images/foundation/sep.gif
+dist/foundation/images/foundation/service.gif
+dist/foundation/images/foundation/thumb.gif
+dist/foundation/images/grayorange/about.gif
+dist/foundation/images/grayorange/banner.gif
+dist/foundation/images/grayorange/bar_filler.gif
+dist/foundation/images/grayorange/buynow.gif
+dist/foundation/images/grayorange/cart.gif
+dist/foundation/images/grayorange/checkout.gif
+dist/foundation/images/grayorange/checkout_button.gif
+dist/foundation/images/grayorange/continue_shopping.gif
+dist/foundation/images/grayorange/gift_certificate_large.gif
+dist/foundation/images/grayorange/go.gif
+dist/foundation/images/grayorange/home.gif
+dist/foundation/images/grayorange/littlebar.gif
+dist/foundation/images/grayorange/login.gif
+dist/foundation/images/grayorange/logo.gif
+dist/foundation/images/grayorange/logo2.gif
+dist/foundation/images/grayorange/logout.gif
+dist/foundation/images/grayorange/placeorder.gif
+dist/foundation/images/grayorange/poweredby.gif
+dist/foundation/images/grayorange/recalculate_button.gif
+dist/foundation/images/grayorange/savecart.gif
+dist/foundation/images/grayorange/saverecur.gif
+dist/foundation/images/grayorange/search.gif
+dist/foundation/images/grayorange/sep.gif
+dist/foundation/images/grayorange/service.gif
+dist/foundation/images/grayorange/thumb.gif
+dist/foundation/images/grayorange/yourimage.gif
+dist/foundation/images/grayscale/about.gif
+dist/foundation/images/grayscale/banner.gif
+dist/foundation/images/grayscale/bar_filler.gif
+dist/foundation/images/grayscale/buynow.gif
+dist/foundation/images/grayscale/cart.gif
+dist/foundation/images/grayscale/checkout.gif
+dist/foundation/images/grayscale/checkout_button.gif
+dist/foundation/images/grayscale/continue_shopping.gif
+dist/foundation/images/grayscale/gift_certificate_large.gif
+dist/foundation/images/grayscale/go.gif
+dist/foundation/images/grayscale/home.gif
+dist/foundation/images/grayscale/littlebar.gif
+dist/foundation/images/grayscale/login.gif
+dist/foundation/images/grayscale/logo.gif
+dist/foundation/images/grayscale/logo2.gif
+dist/foundation/images/grayscale/logout.gif
+dist/foundation/images/grayscale/placeorder.gif
+dist/foundation/images/grayscale/poweredby.gif
+dist/foundation/images/grayscale/recalculate_button.gif
+dist/foundation/images/grayscale/savecart.gif
+dist/foundation/images/grayscale/saverecur.gif
+dist/foundation/images/grayscale/search.gif
+dist/foundation/images/grayscale/sep.gif
+dist/foundation/images/grayscale/service.gif
+dist/foundation/images/grayscale/thumb.gif
+dist/foundation/images/grayscale/yourimage.gif
+dist/foundation/images/greens/about.gif
+dist/foundation/images/greens/banner.gif
+dist/foundation/images/greens/bar_filler.gif
+dist/foundation/images/greens/buynow.gif
+dist/foundation/images/greens/cart.gif
+dist/foundation/images/greens/checkout.gif
+dist/foundation/images/greens/checkout_button.gif
+dist/foundation/images/greens/continue_shopping.gif
+dist/foundation/images/greens/gift_certificate_large.gif
+dist/foundation/images/greens/go.gif
+dist/foundation/images/greens/home.gif
+dist/foundation/images/greens/littlebar.gif
+dist/foundation/images/greens/login.gif
+dist/foundation/images/greens/logo.gif
+dist/foundation/images/greens/logo2.gif
+dist/foundation/images/greens/logout.gif
+dist/foundation/images/greens/placeorder.gif
+dist/foundation/images/greens/poweredby.gif
+dist/foundation/images/greens/recalculate_button.gif
+dist/foundation/images/greens/savecart.gif
+dist/foundation/images/greens/saverecur.gif
+dist/foundation/images/greens/search.gif
+dist/foundation/images/greens/sep.gif
+dist/foundation/images/greens/service.gif
+dist/foundation/images/greens/thumb.gif
+dist/foundation/images/greens/yourimage.gif
+dist/foundation/images/items/yourimage.gif
+dist/foundation/images/purpleyellow/about.gif
+dist/foundation/images/purpleyellow/banner.gif
+dist/foundation/images/purpleyellow/bar_filler.gif
+dist/foundation/images/purpleyellow/buynow.gif
+dist/foundation/images/purpleyellow/cart.gif
+dist/foundation/images/purpleyellow/checkout.gif
+dist/foundation/images/purpleyellow/checkout_button.gif
+dist/foundation/images/purpleyellow/continue_shopping.gif
+dist/foundation/images/purpleyellow/gift_certificate_large.gif
+dist/foundation/images/purpleyellow/go.gif
+dist/foundation/images/purpleyellow/home.gif
+dist/foundation/images/purpleyellow/littlebar.gif
+dist/foundation/images/purpleyellow/login.gif
+dist/foundation/images/purpleyellow/logo.gif
+dist/foundation/images/purpleyellow/logo2.gif
+dist/foundation/images/purpleyellow/logout.gif
+dist/foundation/images/purpleyellow/placeorder.gif
+dist/foundation/images/purpleyellow/poweredby.gif
+dist/foundation/images/purpleyellow/recalculate_button.gif
+dist/foundation/images/purpleyellow/savecart.gif
+dist/foundation/images/purpleyellow/saverecur.gif
+dist/foundation/images/purpleyellow/search.gif
+dist/foundation/images/purpleyellow/sep.gif
+dist/foundation/images/purpleyellow/service.gif
+dist/foundation/images/purpleyellow/thumb.gif
+dist/foundation/images/purpleyellow/yourimage.gif
+dist/foundation/images/reports.xls
+dist/foundation/images/smallamex.png
+dist/foundation/images/smalldisc.png
+dist/foundation/images/smallmc.png
+dist/foundation/images/smallvisa.png
+dist/foundation/images/template.xls
+dist/foundation/images/thumb/thumb.gif
+dist/foundation/include/checkout/billing_address
+dist/foundation/include/checkout/initialization
+dist/foundation/include/checkout/login_form
+dist/foundation/include/checkout/mailing_status
+dist/foundation/include/checkout/new_browser_payment
+dist/foundation/include/checkout/old_browser_payment
+dist/foundation/include/checkout/payment_select
+dist/foundation/include/checkout/shipping_address
+dist/foundation/include/checkout/shopping_cart
+dist/foundation/include/checkout/tax_popup
+dist/foundation/include/forum/reply_form
+dist/foundation/include/forum/submit_form
+dist/foundation/pages/aboutus.html
+dist/foundation/pages/account.html
+dist/foundation/pages/admin/report_def/Order%20Status.html
+dist/foundation/pages/admin/report_def/Products%20to%20edit.html
+dist/foundation/pages/admin/reports/Order%20Status.html
+dist/foundation/pages/admin/reports/Products%20to%20edit.html
+dist/foundation/pages/advancedsearch.html
+dist/foundation/pages/affiliate/index.html
+dist/foundation/pages/affiliate/login.html
+dist/foundation/pages/browse.html
+dist/foundation/pages/canceled.html
+dist/foundation/pages/change_password.html
+dist/foundation/pages/contact.html
+dist/foundation/pages/customerservice.html
+dist/foundation/pages/deliver.html
+dist/foundation/pages/flypage.html
+dist/foundation/pages/forum/display.html
+dist/foundation/pages/forum/reply.html
+dist/foundation/pages/forum/submit.html
+dist/foundation/pages/help.html
+dist/foundation/pages/index.html
+dist/foundation/pages/login.html
+dist/foundation/pages/logout.html
+dist/foundation/pages/lost_password.html
+dist/foundation/pages/modular_modify.html
+dist/foundation/pages/new_account.html
+dist/foundation/pages/ord/basket.html
+dist/foundation/pages/ord/checkout.html
+dist/foundation/pages/privacypolicy.html
+dist/foundation/pages/process_return.html
+dist/foundation/pages/quantity.html
+dist/foundation/pages/query/check_orders.html
+dist/foundation/pages/query/get_password.html
+dist/foundation/pages/query/order_detail.html
+dist/foundation/pages/query/order_return.html
+dist/foundation/pages/query/unsub.html
+dist/foundation/pages/results.html
+dist/foundation/pages/results_big.html
+dist/foundation/pages/returns.html
+dist/foundation/pages/saved_carts.html
+dist/foundation/pages/ship_addresses.html
+dist/foundation/pages/ship_addresses_added.html
+dist/foundation/pages/ship_addresses_removed.html
+dist/foundation/pages/splash.html
+dist/foundation/pages/stock-alert-added.html
+dist/foundation/pages/stock-alert.html
+dist/foundation/pages/survey/graph.html
+dist/foundation/pages/survey/graph.png.html
+dist/foundation/pages/survey/standard.html
+dist/foundation/pages/swap_results.html
+dist/foundation/pages/test_order.html
+dist/foundation/products/2ndDayAir.csv
+dist/foundation/products/450.csv
+dist/foundation/products/Ground.csv
+dist/foundation/products/NextDayAir.csv
+dist/foundation/products/access.asc
+dist/foundation/products/affiliate.txt
+dist/foundation/products/area.txt
+dist/foundation/products/cat.txt
+dist/foundation/products/component.txt
+dist/foundation/products/country.txt
+dist/foundation/products/downloadable.txt
+dist/foundation/products/files.txt
+dist/foundation/products/forum.txt
+dist/foundation/products/gift_certs.txt
+dist/foundation/products/inventory.txt
+dist/foundation/products/locale.txt
+dist/foundation/products/merchandising.txt
+dist/foundation/products/mv_metadata.asc
+dist/foundation/products/options.txt
+dist/foundation/products/order_returns.txt
+dist/foundation/products/orderline.txt
+dist/foundation/products/pricing.txt
+dist/foundation/products/products.txt
+dist/foundation/products/route.txt
+dist/foundation/products/salestax.asc
+dist/foundation/products/shipping.asc
+dist/foundation/products/state.txt
+dist/foundation/products/survey.txt
+dist/foundation/products/transactions.txt
+dist/foundation/products/tree.txt
+dist/foundation/products/userdb.txt
+dist/foundation/products/variable.txt
+dist/foundation/special_pages/badsearch.html
+dist/foundation/special_pages/canceled.html
+dist/foundation/special_pages/cc_not_valid.html
+dist/foundation/special_pages/confirmation.html
+dist/foundation/special_pages/failed.html
+dist/foundation/special_pages/interact.html
+dist/foundation/special_pages/missing.html
+dist/foundation/special_pages/needfield.html
+dist/foundation/special_pages/nomatch.html
+dist/foundation/special_pages/noproduct.html
+dist/foundation/special_pages/notfound.html
+dist/foundation/special_pages/order_security.html
+dist/foundation/special_pages/reconfig.html
+dist/foundation/special_pages/sec_faq.html
+dist/foundation/special_pages/security.html
+dist/foundation/special_pages/violation.html
+dist/foundation/templates/blueyellow/regions/CATTOP_LEFTONLY_BOTTOM
+dist/foundation/templates/blueyellow/regions/CATTOP_LEFTONLY_TOP
+dist/foundation/templates/blueyellow/regions/CATTOP_LEFTRIGHT_BOTTOM
+dist/foundation/templates/blueyellow/regions/CATTOP_LEFTRIGHT_TOP
+dist/foundation/templates/blueyellow/regions/CATTOP_NOLEFT_BOTTOM
+dist/foundation/templates/blueyellow/regions/CATTOP_NOLEFT_TOP
+dist/foundation/templates/blueyellow/regions/LEFTONLY_BOTTOM
+dist/foundation/templates/blueyellow/regions/LEFTONLY_TOP
+dist/foundation/templates/blueyellow/regions/LEFTRIGHT_BOTTOM
+dist/foundation/templates/blueyellow/regions/LEFTRIGHT_TOP
+dist/foundation/templates/blueyellow/regions/NOLEFT_BOTTOM
+dist/foundation/templates/blueyellow/regions/NOLEFT_TOP
+dist/foundation/templates/blueyellow/theme.cfg
+dist/foundation/templates/components/affiliate_receptor
+dist/foundation/templates/components/best
+dist/foundation/templates/components/cart
+dist/foundation/templates/components/cart_display
+dist/foundation/templates/components/cart_tiny
+dist/foundation/templates/components/category_horizontal
+dist/foundation/templates/components/category_vert_toggle
+dist/foundation/templates/components/category_vertical
+dist/foundation/templates/components/category_vertical_tree
+dist/foundation/templates/components/cross
+dist/foundation/templates/components/fortune
+dist/foundation/templates/components/product_flyout
+dist/foundation/templates/components/product_tree
+dist/foundation/templates/components/promo
+dist/foundation/templates/components/random
+dist/foundation/templates/components/results_big
+dist/foundation/templates/components/results_buylist
+dist/foundation/templates/components/results_grid
+dist/foundation/templates/components/saved_carts_list_small
+dist/foundation/templates/components/search_box_small
+dist/foundation/templates/components/search_box_small_top
+dist/foundation/templates/components/upsell
+dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTONLY_BOTTOM
+dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTONLY_TOP
+dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTRIGHT_BOTTOM
+dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTRIGHT_TOP
+dist/foundation/templates/fixedwidth/regions/CATTOP_NOLEFT_BOTTOM
+dist/foundation/templates/fixedwidth/regions/CATTOP_NOLEFT_TOP
+dist/foundation/templates/fixedwidth/regions/LEFTONLY_BOTTOM
+dist/foundation/templates/fixedwidth/regions/LEFTONLY_TOP
+dist/foundation/templates/fixedwidth/regions/LEFTRIGHT_BOTTOM
+dist/foundation/templates/fixedwidth/regions/LEFTRIGHT_TOP
+dist/foundation/templates/fixedwidth/regions/NOLEFT_BOTTOM
+dist/foundation/templates/fixedwidth/regions/NOLEFT_TOP
+dist/foundation/templates/fixedwidth/theme.cfg
+dist/foundation/templates/foundation/cart
+dist/foundation/templates/foundation/regions/LEFTONLY_BOTTOM
+dist/foundation/templates/foundation/regions/LEFTONLY_TOP
+dist/foundation/templates/foundation/regions/LEFTRIGHT_BOTTOM
+dist/foundation/templates/foundation/regions/LEFTRIGHT_TOP
+dist/foundation/templates/foundation/regions/NOLEFT_BOTTOM
+dist/foundation/templates/foundation/regions/NOLEFT_TOP
+dist/foundation/templates/foundation/simple
+dist/foundation/templates/foundation/theme.cfg
+dist/foundation/templates/grayorange/regions/CATTOP_LEFTONLY_BOTTOM
+dist/foundation/templates/grayorange/regions/CATTOP_LEFTONLY_TOP
+dist/foundation/templates/grayorange/regions/CATTOP_LEFTRIGHT_BOTTOM
+dist/foundation/templates/grayorange/regions/CATTOP_LEFTRIGHT_TOP
+dist/foundation/templates/grayorange/regions/CATTOP_NOLEFT_BOTTOM
+dist/foundation/templates/grayorange/regions/CATTOP_NOLEFT_TOP
+dist/foundation/templates/grayorange/regions/LEFTONLY_BOTTOM
+dist/foundation/templates/grayorange/regions/LEFTONLY_TOP
+dist/foundation/templates/grayorange/regions/LEFTRIGHT_BOTTOM
+dist/foundation/templates/grayorange/regions/LEFTRIGHT_TOP
+dist/foundation/templates/grayorange/regions/NOLEFT_BOTTOM
+dist/foundation/templates/grayorange/regions/NOLEFT_TOP
+dist/foundation/templates/grayorange/theme.cfg
+dist/foundation/templates/grayscale/regions/CATTOP_LEFTONLY_BOTTOM
+dist/foundation/templates/grayscale/regions/CATTOP_LEFTONLY_TOP
+dist/foundation/templates/grayscale/regions/CATTOP_LEFTRIGHT_BOTTOM
+dist/foundation/templates/grayscale/regions/CATTOP_LEFTRIGHT_TOP
+dist/foundation/templates/grayscale/regions/CATTOP_NOLEFT_BOTTOM
+dist/foundation/templates/grayscale/regions/CATTOP_NOLEFT_TOP
+dist/foundation/templates/grayscale/regions/LEFTONLY_BOTTOM
+dist/foundation/templates/grayscale/regions/LEFTONLY_TOP
+dist/foundation/templates/grayscale/regions/LEFTRIGHT_BOTTOM
+dist/foundation/templates/grayscale/regions/LEFTRIGHT_TOP
+dist/foundation/templates/grayscale/regions/NOLEFT_BOTTOM
+dist/foundation/templates/grayscale/regions/NOLEFT_TOP
+dist/foundation/templates/grayscale/theme.cfg
+dist/foundation/templates/greens/regions/CATTOP_LEFTONLY_BOTTOM
+dist/foundation/templates/greens/regions/CATTOP_LEFTONLY_TOP
+dist/foundation/templates/greens/regions/CATTOP_LEFTRIGHT_BOTTOM
+dist/foundation/templates/greens/regions/CATTOP_LEFTRIGHT_TOP
+dist/foundation/templates/greens/regions/CATTOP_NOLEFT_BOTTOM
+dist/foundation/templates/greens/regions/CATTOP_NOLEFT_TOP
+dist/foundation/templates/greens/regions/LEFTONLY_BOTTOM
+dist/foundation/templates/greens/regions/LEFTONLY_TOP
+dist/foundation/templates/greens/regions/LEFTRIGHT_BOTTOM
+dist/foundation/templates/greens/regions/LEFTRIGHT_TOP
+dist/foundation/templates/greens/regions/NOLEFT_BOTTOM
+dist/foundation/templates/greens/regions/NOLEFT_TOP
+dist/foundation/templates/greens/theme.cfg
+dist/foundation/templates/leftonly
+dist/foundation/templates/leftright
+dist/foundation/templates/noleft
+dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTONLY_BOTTOM
+dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTONLY_TOP
+dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTRIGHT_BOTTOM
+dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTRIGHT_TOP
+dist/foundation/templates/purpleyellow/regions/CATTOP_NOLEFT_BOTTOM
+dist/foundation/templates/purpleyellow/regions/CATTOP_NOLEFT_TOP
+dist/foundation/templates/purpleyellow/regions/LEFTONLY_BOTTOM
+dist/foundation/templates/purpleyellow/regions/LEFTONLY_TOP
+dist/foundation/templates/purpleyellow/regions/LEFTRIGHT_BOTTOM
+dist/foundation/templates/purpleyellow/regions/LEFTRIGHT_TOP
+dist/foundation/templates/purpleyellow/regions/NOLEFT_BOTTOM
+dist/foundation/templates/purpleyellow/regions/NOLEFT_TOP
+dist/foundation/templates/purpleyellow/theme.cfg
+dist/foundation/templates/sampledata/reports/download/00352as.pdf
+dist/foundation/templates/sampledata/reports/download/11993ab.pdf
+dist/foundation/templates/sampledata/reports/download/22083da.pdf
+dist/foundation/templates/sampledata/reports/download/49503cg.pdf
+dist/foundation/templates/sampledata/reports/download/59330rt.pdf
+dist/foundation/templates/sampledata/reports/download/59402fw.pdf
+dist/foundation/templates/sampledata/reports/download/66548ch.pdf
+dist/foundation/templates/sampledata/reports/download/73358ee.pdf
+dist/foundation/templates/sampledata/reports/download/83491vp.pdf
+dist/foundation/templates/sampledata/reports/download/90773sh.pdf
+dist/foundation/templates/sampledata/reports/products/area.txt
+dist/foundation/templates/sampledata/reports/products/cat.txt
+dist/foundation/templates/sampledata/reports/products/inventory.txt
+dist/foundation/templates/sampledata/reports/products/merchandising.txt
+dist/foundation/templates/sampledata/reports/products/options.txt
+dist/foundation/templates/sampledata/reports/products/pricing.txt
+dist/foundation/templates/sampledata/reports/products/products.txt
+dist/foundation/templates/sampledata/reports/products/userdb.txt
+dist/foundation/templates/sampledata/tools/etc/after.cfg
+dist/foundation/templates/sampledata/tools/etc/before.cfg
+dist/foundation/templates/sampledata/tools/images/items/gift_cert.gif
+dist/foundation/templates/sampledata/tools/images/items/os28004.gif
+dist/foundation/templates/sampledata/tools/images/items/os28005.gif
+dist/foundation/templates/sampledata/tools/images/items/os28006.gif
+dist/foundation/templates/sampledata/tools/images/items/os28007.gif
+dist/foundation/templates/sampledata/tools/images/items/os28008.gif
+dist/foundation/templates/sampledata/tools/images/items/os28009.gif
+dist/foundation/templates/sampledata/tools/images/items/os28011.gif
+dist/foundation/templates/sampledata/tools/images/items/os28044.gif
+dist/foundation/templates/sampledata/tools/images/items/os28057a.gif
+dist/foundation/templates/sampledata/tools/images/items/os28057b.gif
+dist/foundation/templates/sampledata/tools/images/items/os28057c.gif
+dist/foundation/templates/sampledata/tools/images/items/os28062.gif
+dist/foundation/templates/sampledata/tools/images/items/os28064.gif
+dist/foundation/templates/sampledata/tools/images/items/os28065.gif
+dist/foundation/templates/sampledata/tools/images/items/os28066.gif
+dist/foundation/templates/sampledata/tools/images/items/os28068.gif
+dist/foundation/templates/sampledata/tools/images/items/os28068a.gif
+dist/foundation/templates/sampledata/tools/images/items/os28068b.gif
+dist/foundation/templates/sampledata/tools/images/items/os28069.gif
+dist/foundation/templates/sampledata/tools/images/items/os28070.gif
+dist/foundation/templates/sampledata/tools/images/items/os28072.gif
+dist/foundation/templates/sampledata/tools/images/items/os28073.gif
+dist/foundation/templates/sampledata/tools/images/items/os28074.gif
+dist/foundation/templates/sampledata/tools/images/items/os28075.gif
+dist/foundation/templates/sampledata/tools/images/items/os28076.gif
+dist/foundation/templates/sampledata/tools/images/items/os28077.gif
+dist/foundation/templates/sampledata/tools/images/items/os28080.gif
+dist/foundation/templates/sampledata/tools/images/items/os28081.gif
+dist/foundation/templates/sampledata/tools/images/items/os28082.gif
+dist/foundation/templates/sampledata/tools/images/items/os28084.gif
+dist/foundation/templates/sampledata/tools/images/items/os28085.gif
+dist/foundation/templates/sampledata/tools/images/items/os28086.gif
+dist/foundation/templates/sampledata/tools/images/items/os28087.gif
+dist/foundation/templates/sampledata/tools/images/items/os28108.gif
+dist/foundation/templates/sampledata/tools/images/items/os28109.gif
+dist/foundation/templates/sampledata/tools/images/items/os28110.gif
+dist/foundation/templates/sampledata/tools/images/items/os28111.gif
+dist/foundation/templates/sampledata/tools/images/items/os28112.gif
+dist/foundation/templates/sampledata/tools/images/items/os28113.gif
+dist/foundation/templates/sampledata/tools/images/items/os29000.gif
+dist/foundation/templates/sampledata/tools/images/thumb/gift_cert.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28004_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28005_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28006_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28007_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28008_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28009_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28011_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28044_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28057a_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28057b_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28057c_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28062_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28064_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28065_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28066_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28068_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28068a_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28068b_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28069_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28070_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28072_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28073_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28074_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28075_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28076_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28077_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28080_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28081_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28082_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28084_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28085_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28086_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28087_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28108_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28109_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28110_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28111_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28112_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os28113_b.gif
+dist/foundation/templates/sampledata/tools/images/thumb/os29000_b.gif
+dist/foundation/templates/sampledata/tools/products/affiliate.txt
+dist/foundation/templates/sampledata/tools/products/area.txt
+dist/foundation/templates/sampledata/tools/products/area_de_DE.txt
+dist/foundation/templates/sampledata/tools/products/cat.txt
+dist/foundation/templates/sampledata/tools/products/cat_de_DE.txt
+dist/foundation/templates/sampledata/tools/products/inventory.txt
+dist/foundation/templates/sampledata/tools/products/merchandising.txt
+dist/foundation/templates/sampledata/tools/products/options.txt
+dist/foundation/templates/sampledata/tools/products/orderline.txt
+dist/foundation/templates/sampledata/tools/products/pricing.txt
+dist/foundation/templates/sampledata/tools/products/products.txt
+dist/foundation/templates/sampledata/tools/products/products_de_DE.txt
+dist/foundation/templates/sampledata/tools/products/specs.txt
+dist/foundation/templates/sampledata/tools/products/transactions.txt
+dist/foundation/templates/sampledata/tools/products/userdb.txt
+dist/foundation/upload/.empty
+dist/foundation/upload/products.xls
 dist/interchange.cfg.dist
+dist/lib/UI/ContentEditor.pm
 dist/lib/UI/Primitive.pm
+dist/lib/UI/ichelp.txt
+dist/lib/UI/locales/README
+dist/lib/UI/locales/TODO
+dist/lib/UI/locales/da_DK.cfg
+dist/lib/UI/locales/de_DE.cfg
+dist/lib/UI/locales/default.cfg
+dist/lib/UI/locales/en_US.cfg
+dist/lib/UI/locales/es_ES.cfg
+dist/lib/UI/locales/he_IL.cfg
+dist/lib/UI/locales/ja_JP.cfg
+dist/lib/UI/locales/nl_NL.cfg
+dist/lib/UI/locales/pt_BR.cfg
+dist/lib/UI/locales/sv_SE.cfg
+dist/lib/UI/pages/admin/.access
+dist/lib/UI/pages/admin/.autoload
 dist/lib/UI/pages/admin/access.html
 dist/lib/UI/pages/admin/access_permissions.html
+dist/lib/UI/pages/admin/accounting/index.html
+dist/lib/UI/pages/admin/accounting/return.html
 dist/lib/UI/pages/admin/add_meta_option.html
-dist/lib/UI/pages/admin/advanced.html
 dist/lib/UI/pages/admin/affiliates.html
+dist/lib/UI/pages/admin/auto_wizard.html
 dist/lib/UI/pages/admin/bug_report.html
 dist/lib/UI/pages/admin/build_related.html
 dist/lib/UI/pages/admin/button_builder.html
-dist/lib/UI/pages/admin/compedit.html
-dist/lib/UI/pages/admin/config.html
+dist/lib/UI/pages/admin/commerce.html
+dist/lib/UI/pages/admin/content.html
+dist/lib/UI/pages/admin/content_components.html
+dist/lib/UI/pages/admin/content_editor.html
+dist/lib/UI/pages/admin/content_preview.html
+dist/lib/UI/pages/admin/content_publish.html
+dist/lib/UI/pages/admin/content_push.html
+dist/lib/UI/pages/admin/content_templates.html
 dist/lib/UI/pages/admin/customer.html
+dist/lib/UI/pages/admin/customer_all.html
 dist/lib/UI/pages/admin/customer_bill.html
 dist/lib/UI/pages/admin/customer_change_pass.html
+dist/lib/UI/pages/admin/customer_comments.html
+dist/lib/UI/pages/admin/customer_mailing.html
 dist/lib/UI/pages/admin/customer_pref.html
 dist/lib/UI/pages/admin/customer_select.html
 dist/lib/UI/pages/admin/customer_ship.html
 dist/lib/UI/pages/admin/customer_view.html
+dist/lib/UI/pages/admin/db_metaconfig.html
+dist/lib/UI/pages/admin/db_newview.html
+dist/lib/UI/pages/admin/dbconfig.html
+dist/lib/UI/pages/admin/dbconfig_save.html
 dist/lib/UI/pages/admin/dbdownload.html
 dist/lib/UI/pages/admin/dbinfo.html
+dist/lib/UI/pages/admin/direct_sql.html
 dist/lib/UI/pages/admin/do_upload.html
 dist/lib/UI/pages/admin/do_upload_page.html
 dist/lib/UI/pages/admin/do_view.html
+dist/lib/UI/pages/admin/edit_metaconfig.html
 dist/lib/UI/pages/admin/entry.html
 dist/lib/UI/pages/admin/entry_select.html
 dist/lib/UI/pages/admin/env_vars.html
 dist/lib/UI/pages/admin/error.html
 dist/lib/UI/pages/admin/error_item.html
 dist/lib/UI/pages/admin/export_table.html
+dist/lib/UI/pages/admin/file_transfer.html
 dist/lib/UI/pages/admin/flex_editor.html
+dist/lib/UI/pages/admin/flex_group.html
 dist/lib/UI/pages/admin/flex_select.html
-dist/lib/UI/pages/admin/flex_select_box.html
-dist/lib/UI/pages/admin/format_meta.html
 dist/lib/UI/pages/admin/fr_index.html
 dist/lib/UI/pages/admin/genconfig.html
-dist/lib/UI/pages/admin/genreport.html
-dist/lib/UI/pages/admin/genstats.html
+dist/lib/UI/pages/admin/generic.html
+dist/lib/UI/pages/admin/genfunction.html
 dist/lib/UI/pages/admin/gentable.html
-dist/lib/UI/pages/admin/genupload.html
-dist/lib/UI/pages/admin/genxport.html
+dist/lib/UI/pages/admin/gpg_key.html
 dist/lib/UI/pages/admin/group.html
 dist/lib/UI/pages/admin/group_edit.html
+dist/lib/UI/pages/admin/help.html
 dist/lib/UI/pages/admin/import_table.html
 dist/lib/UI/pages/admin/index.html
 dist/lib/UI/pages/admin/item.html
 dist/lib/UI/pages/admin/item_cross.html
 dist/lib/UI/pages/admin/item_edit.html
 dist/lib/UI/pages/admin/item_feature.html
+dist/lib/UI/pages/admin/item_group.html
 dist/lib/UI/pages/admin/item_inventory.html
+dist/lib/UI/pages/admin/item_option.html
+dist/lib/UI/pages/admin/item_option_phantom.html
 dist/lib/UI/pages/admin/item_price.html
 dist/lib/UI/pages/admin/item_up.html
 dist/lib/UI/pages/admin/layout.html
+dist/lib/UI/pages/admin/layout_auto.html
 dist/lib/UI/pages/admin/login.html
-dist/lib/UI/pages/admin/logout.html
+dist/lib/UI/pages/admin/menu_editor.html
+dist/lib/UI/pages/admin/menu_loader.html
 dist/lib/UI/pages/admin/merchandising.html
+dist/lib/UI/pages/admin/merge_meta.html
 dist/lib/UI/pages/admin/meta_editor.html
+dist/lib/UI/pages/admin/misc_order_number.html
 dist/lib/UI/pages/admin/order.html
 dist/lib/UI/pages/admin/order_status.html
+dist/lib/UI/pages/admin/order_status_alt.html
 dist/lib/UI/pages/admin/order_view.html
 dist/lib/UI/pages/admin/orderstats.html
-dist/lib/UI/pages/admin/page.html
-dist/lib/UI/pages/admin/page_edit.html
-dist/lib/UI/pages/admin/page_new.html
-dist/lib/UI/pages/admin/page_preview.html
-dist/lib/UI/pages/admin/page_save.html
+dist/lib/UI/pages/admin/page_metaconfig.html
+dist/lib/UI/pages/admin/page_upload.html
 dist/lib/UI/pages/admin/payment.html
+dist/lib/UI/pages/admin/pref_colors.html
+dist/lib/UI/pages/admin/pref_select.html
 dist/lib/UI/pages/admin/preferences.html
+dist/lib/UI/pages/admin/quick_question.html
 dist/lib/UI/pages/admin/quicklinks.html
 dist/lib/UI/pages/admin/reconfig.html
 dist/lib/UI/pages/admin/regen.html
@@ -461,10 +1031,15 @@
 dist/lib/UI/pages/admin/report.html
 dist/lib/UI/pages/admin/report_results.html
 dist/lib/UI/pages/admin/report_save.html
+dist/lib/UI/pages/admin/reports/order/.access
+dist/lib/UI/pages/admin/reports/order/.autoload
 dist/lib/UI/pages/admin/reports/order/ByAffiliate.html
 dist/lib/UI/pages/admin/reports/order/Detail.html
 dist/lib/UI/pages/admin/reports/order/Monthly.html
+dist/lib/UI/pages/admin/reports/traffic/.access
+dist/lib/UI/pages/admin/reports/traffic/.autoload
 dist/lib/UI/pages/admin/reports/traffic/ByAffiliate.html
+dist/lib/UI/pages/admin/search_replace.html
 dist/lib/UI/pages/admin/search_wizard.html
 dist/lib/UI/pages/admin/search_wizard2.html
 dist/lib/UI/pages/admin/search_wizard3.html
@@ -473,85 +1048,112 @@
 dist/lib/UI/pages/admin/ship_data.html
 dist/lib/UI/pages/admin/ship_edit.html
 dist/lib/UI/pages/admin/ship_range.html
+dist/lib/UI/pages/admin/show_session.html
 dist/lib/UI/pages/admin/sku_selector.html
+dist/lib/UI/pages/admin/special/.access
+dist/lib/UI/pages/admin/special/.autoload
 dist/lib/UI/pages/admin/special/key_violation.html
 dist/lib/UI/pages/admin/spread.html
 dist/lib/UI/pages/admin/spread_control.html
+dist/lib/UI/pages/admin/survey/index.html
+dist/lib/UI/pages/admin/survey/overall.html
+dist/lib/UI/pages/admin/survey/question.html
 dist/lib/UI/pages/admin/tablereport.html
 dist/lib/UI/pages/admin/tax.html
+dist/lib/UI/pages/admin/tax_simple.html
+dist/lib/UI/pages/admin/test_code.html
 dist/lib/UI/pages/admin/trafficstats.html
 dist/lib/UI/pages/admin/upload_config.html
 dist/lib/UI/pages/admin/upload_file.html
 dist/lib/UI/pages/admin/upload_image.html
-dist/lib/UI/pages/admin/upload_other.html
 dist/lib/UI/pages/admin/upload_pages.html
 dist/lib/UI/pages/admin/user_change_pass.html
 dist/lib/UI/pages/admin/user_edit.html
+dist/lib/UI/pages/admin/wizard/.access
+dist/lib/UI/pages/admin/wizard/.autoload
+dist/lib/UI/pages/admin/wizard/X_dump.html
+dist/lib/UI/pages/admin/wizard/X_test.html
+dist/lib/UI/pages/admin/wizard/demo_init.html
+dist/lib/UI/pages/admin/wizard/demo_zero.html
+dist/lib/UI/pages/admin/wizard/do_launch.html
+dist/lib/UI/pages/admin/wizard/do_save.html
+dist/lib/UI/pages/admin/wizard/guess_info.html
+dist/lib/UI/pages/admin/wizard/index.html
+dist/lib/UI/pages/admin/wizard/step_about.html
+dist/lib/UI/pages/admin/wizard/step_company.html
+dist/lib/UI/pages/admin/wizard/step_email.html
+dist/lib/UI/pages/admin/wizard/step_groupcontent.html
+dist/lib/UI/pages/admin/wizard/step_grouppolicy.html
+dist/lib/UI/pages/admin/wizard/step_index.html
+dist/lib/UI/pages/admin/wizard/step_launch.html
+dist/lib/UI/pages/admin/wizard/step_pay.html
+dist/lib/UI/pages/admin/wizard/step_pay_auth.html
+dist/lib/UI/pages/admin/wizard/step_pay_cyber.html
+dist/lib/UI/pages/admin/wizard/step_pay_itransact.html
+dist/lib/UI/pages/admin/wizard/step_pay_pgp.html
+dist/lib/UI/pages/admin/wizard/step_pay_signio.html
+dist/lib/UI/pages/admin/wizard/step_pay_skipjack.html
+dist/lib/UI/pages/admin/wizard/step_preview.html
+dist/lib/UI/pages/admin/wizard/step_products.html
+dist/lib/UI/pages/admin/wizard/step_security.html
+dist/lib/UI/pages/admin/wizard/step_ship.html
+dist/lib/UI/pages/admin/wizard/step_ship_country.html
+dist/lib/UI/pages/admin/wizard/step_ship_default.html
+dist/lib/UI/pages/admin/wizard/step_ship_fedex.html
+dist/lib/UI/pages/admin/wizard/step_ship_ups.html
+dist/lib/UI/pages/admin/wizard/step_style.html
+dist/lib/UI/pages/admin/wizard/step_style_logo.html
+dist/lib/UI/pages/admin/wizard/step_tax.html
+dist/lib/UI/pages/include/component_editor
+dist/lib/UI/pages/include/item_option_matrix
+dist/lib/UI/pages/include/item_option_modular
+dist/lib/UI/pages/include/item_option_simple
+dist/lib/UI/pages/include/menus/Accounting.txt
+dist/lib/UI/pages/include/menus/Admin.txt
+dist/lib/UI/pages/include/menus/Commerce.txt
+dist/lib/UI/pages/include/menus/Content.txt
+dist/lib/UI/pages/include/menus/ContentEdit.txt
+dist/lib/UI/pages/include/menus/Customers.txt
+dist/lib/UI/pages/include/menus/DbConfig.txt
+dist/lib/UI/pages/include/menus/Design.txt
+dist/lib/UI/pages/include/menus/Fixed.txt
+dist/lib/UI/pages/include/menus/Items.txt
+dist/lib/UI/pages/include/menus/Layout.txt
+dist/lib/UI/pages/include/menus/Legacy.txt
+dist/lib/UI/pages/include/menus/Merchandising.txt
+dist/lib/UI/pages/include/menus/Misc.txt
+dist/lib/UI/pages/include/menus/MiscFunction.txt
+dist/lib/UI/pages/include/menus/None.txt
+dist/lib/UI/pages/include/menus/OrderView.txt
+dist/lib/UI/pages/include/menus/Orders.txt
+dist/lib/UI/pages/include/menus/Quicklinks.txt
+dist/lib/UI/pages/include/menus/Reports.txt
+dist/lib/UI/pages/include/menus/Surveys.txt
+dist/lib/UI/pages/include/menus/Tables.txt
+dist/lib/UI/pages/include/menus/Top.txt
+dist/lib/UI/pages/include/menus/Wizard.txt
+dist/lib/UI/pages/include/menus/uiExport.txt
+dist/lib/UI/pages/include/meta/mv_metadata.asc
+dist/lib/UI/pages/include/order_delete_archive
+dist/lib/UI/pages/include/page_editor
+dist/lib/UI/pages/include/table_populator
+dist/lib/UI/pages/include/template_editor
+dist/lib/UI/pages/include/templates/ui_type1
+dist/lib/UI/pages/include/templates/ui_type2
+dist/lib/UI/pages/include/templates/ui_type3
+dist/lib/UI/pages/include/templates/ui_type5
+dist/lib/UI/pages/include/wizard_checklist
+dist/lib/UI/pages/include/wizard_profiles
+dist/lib/UI/profiles/Cancel
+dist/lib/UI/profiles/db_maintenance
+dist/lib/UI/profiles/file_maintenance
 dist/lib/UI/profiles/login
+dist/lib/UI/profiles/miscellaneous
 dist/lib/UI/profiles/order_button_build
+dist/lib/UI/profiles/process_filter
+dist/lib/UI/profiles/recompute_transaction
 dist/lib/UI/ui.cfg
-dist/lib/UI/usertag/available_ups_internal
-dist/lib/UI/usertag/available_www_shipping
-dist/lib/UI/usertag/backup_database
-dist/lib/UI/usertag/backup_file
-dist/lib/UI/usertag/base_url
-dist/lib/UI/usertag/button
-dist/lib/UI/usertag/check_upload
-dist/lib/UI/usertag/component
-dist/lib/UI/usertag/db_columns
-dist/lib/UI/usertag/db_hash
-dist/lib/UI/usertag/dbinfo
-dist/lib/UI/usertag/directive_value
-dist/lib/UI/usertag/display
-dist/lib/UI/usertag/dump_session
-dist/lib/UI/usertag/e
-dist/lib/UI/usertag/export_database
-dist/lib/UI/usertag/field_label
-dist/lib/UI/usertag/file_info
-dist/lib/UI/usertag/file_navigator
-dist/lib/UI/usertag/filters
-dist/lib/UI/usertag/global_value
-dist/lib/UI/usertag/grep_mm
-dist/lib/UI/usertag/if_key_exists
-dist/lib/UI/usertag/if_mm
-dist/lib/UI/usertag/if_sql
-dist/lib/UI/usertag/ifdef
-dist/lib/UI/usertag/ifndef
-dist/lib/UI/usertag/import_fields
-dist/lib/UI/usertag/list_databases
-dist/lib/UI/usertag/list_glob
-dist/lib/UI/usertag/list_keys
-dist/lib/UI/usertag/list_pages
-dist/lib/UI/usertag/mm_value
-dist/lib/UI/usertag/newer
-dist/lib/UI/usertag/quick_table
-dist/lib/UI/usertag/read_serial
-dist/lib/UI/usertag/read_shipping
-dist/lib/UI/usertag/read_ui_template
-dist/lib/UI/usertag/regenerate
-dist/lib/UI/usertag/related
-dist/lib/UI/usertag/return_to
-dist/lib/UI/usertag/rotate_database
-dist/lib/UI/usertag/rotate_file
-dist/lib/UI/usertag/rotate_table
-dist/lib/UI/usertag/row_edit
-dist/lib/UI/usertag/send_help
-dist/lib/UI/usertag/set_alias
-dist/lib/UI/usertag/set_click
-dist/lib/UI/usertag/setvar
-dist/lib/UI/usertag/substitute
-dist/lib/UI/usertag/title_bar
-dist/lib/UI/usertag/unconfigure
-dist/lib/UI/usertag/uneval
-dist/lib/UI/usertag/unlink_file
-dist/lib/UI/usertag/version
-dist/lib/UI/usertag/widget
-dist/lib/UI/usertag/with
-dist/lib/UI/usertag/write_relative_file
-dist/lib/UI/usertag/write_shipping
 dist/lib/UI/vars/UI_EDIT_LINK
-dist/lib/UI/vars/UI_STD_DBEDIT_HEAD
-dist/lib/UI/vars/UI_STD_DBEDIT_TABLE
 dist/lib/UI/vars/UI_STD_FILE_NAV
 dist/lib/UI/vars/UI_STD_FOOTER
 dist/lib/UI/vars/UI_STD_HEAD
@@ -573,49 +1175,47 @@
 dist/src/tlink.pl
 dist/src/vlink.c
 dist/src/vlink.pl
-dist/usertag/bar_button
-dist/usertag/button
-dist/usertag/convert_date
-dist/usertag/db_date
-dist/usertag/email
-dist/usertag/email_html
-dist/usertag/email_raw
-dist/usertag/fcounter
-dist/usertag/formel
-dist/usertag/get_url
-dist/usertag/loc
-dist/usertag/rand
-dist/usertag/reconfig
-dist/usertag/reconfig_time
-dist/usertag/reconfig_wait
-dist/usertag/summary
-dist/usertag/title_bar
-dist/usertag/ups_query
-dist/usertag/usertrack
-dist/usertag/var
-dist/usertag/xml_generator
 eg/compact
 eg/globalsub/authorizenet
+eg/globalsub/ccvs
 eg/globalsub/signio
+eg/globalsub/test_card
+eg/gpg_display
 eg/grant.sql
 eg/ifdef
-eg/make_gnumeric.sh
+eg/news_feature/README
+eg/news_feature/dbconf/default_db/news.dbm
+eg/news_feature/dbconf/mysql/news.mysql
+eg/news_feature/dbconf/oracle/news.ora
+eg/news_feature/dbconf/pgsql/news.pgsql
+eg/news_feature/pages/news.html
+eg/news_feature/products/news.txt
+eg/news_feature/templates/components/news
+eg/reset_order_number
+eg/survey_graph.tag
+eg/te
 eg/usertag/benchmark
 eg/usertag/sleep
-eg/usertag/table_organize
+extensions/ECML/Vend/ECML.pm
+extensions/ECML/ecml.coretag
+extensions/Interchange.pm
 extensions/quickbooks/README
 extensions/quickbooks/etc/trans_quickbooks
 extensions/quickbooks/ic_qb.pod
-extensions/quickbooks/pages/admin/export_coa.html
-extensions/quickbooks/pages/admin/export_items.html
-extensions/quickbooks/pages/admin/import_items.html
-extensions/quickbooks/pages/admin/index.html
+extensions/quickbooks/mv_metadata-additions.asc
+extensions/quickbooks/pages/admin/quickbooks/export_coa.html
+extensions/quickbooks/pages/admin/quickbooks/export_items.html
+extensions/quickbooks/pages/admin/quickbooks/get_orders.html
+extensions/quickbooks/pages/admin/quickbooks/import_items.html
+extensions/quickbooks/pages/admin/quickbooks/index.html
 extensions/quickbooks/qb.catalog.cfg
-extensions/quickbooks/usertag/export_quicken_coa
-extensions/quickbooks/usertag/export_quicken_items
-extensions/quickbooks/usertag/import_quicken_items
+extensions/quickbooks/qb_getord.pl
+extensions/quickbooks/usertag/export_quicken_coa.tag
+extensions/quickbooks/usertag/export_quicken_items.tag
+extensions/quickbooks/usertag/get_quicken_orders.tag
+extensions/quickbooks/usertag/import_quicken_items.tag
+extra/Business/Fedex.pm
 extra/Business/UPS.pm
-extra/File/CounterFile.pm
 extra/File/Spec.pm
 extra/File/Spec/OS2.pm
 extra/File/Spec/Unix.pm
@@ -623,234 +1223,155 @@
 extra/File/Spec/Win32.pm
 extra/HTML/Entities.pm
 extra/IniConf.pm
+extra/Tie/ShadowHash.pm
 extra/URI/URL.pm
 hints.pl
+lib/Vend/Accounting.pm
+lib/Vend/Accounting/SQL_Ledger.pm
 lib/Vend/Cart.pm
 lib/Vend/Config.pm
 lib/Vend/Control.pm
+lib/Vend/CounterFile.pm
 lib/Vend/Data.pm
 lib/Vend/DbSearch.pm
+lib/Vend/Dispatch.pm
 lib/Vend/Document.pm
-lib/Vend/ECML.pm
 lib/Vend/Error.pm
 lib/Vend/External.pm
+lib/Vend/Form.pm
 lib/Vend/Glimpse.pm
 lib/Vend/Imagemap.pm
 lib/Vend/Interpolate.pm
 lib/Vend/MakeCat.pm
-lib/Vend/Misc/Static.pm
+lib/Vend/Menu.pm
+lib/Vend/ModPerl.pm
 lib/Vend/Order.pm
 lib/Vend/Page.pm
 lib/Vend/Parse.pm
 lib/Vend/Parser.pm
+lib/Vend/Payment.pm
+lib/Vend/Payment/AuthorizeNet.pm
+lib/Vend/Payment/BoA.pm
+lib/Vend/Payment/CCVS.pm
+lib/Vend/Payment/CyberCash.pm
+lib/Vend/Payment/ECHO.pm
+lib/Vend/Payment/MCVE.pm
+lib/Vend/Payment/Signio.pm
+lib/Vend/Payment/Skipjack.pm
+lib/Vend/Payment/TCLink.pm
+lib/Vend/Payment/TestPayment.pm
+lib/Vend/Payment/WellsFargo.pm
+lib/Vend/Payment/iTransact.pm
+lib/Vend/RefSearch.pm
+lib/Vend/SOAP.pm
+lib/Vend/SOAP/Transport.pm
 lib/Vend/Scan.pm
 lib/Vend/Search.pm
 lib/Vend/Server.pm
 lib/Vend/Session.pm
 lib/Vend/SessionDB.pm
 lib/Vend/SessionFile.pm
+lib/Vend/Swish.pm
 lib/Vend/Table/Common.pm
 lib/Vend/Table/DBI.pm
 lib/Vend/Table/DB_File.pm
+lib/Vend/Table/Editor.pm
 lib/Vend/Table/GDBM.pm
 lib/Vend/Table/InMemory.pm
 lib/Vend/Table/LDAP.pm
-lib/Vend/Tagref.pm
+lib/Vend/Table/SDBM.pm
+lib/Vend/Table/Shadow.pm
 lib/Vend/Tags.pm
 lib/Vend/TextSearch.pm
 lib/Vend/Track.pm
 lib/Vend/UserDB.pm
 lib/Vend/Util.pm
-pdf/README
-pdf/icbackoffice.pdf
-pdf/iccattut.pdf
-pdf/icconfig.pdf
-pdf/icdatabase.pdf
-pdf/icinstall.pdf
-pdf/icintro.pdf
-pdf/ictemplates.pdf
-perl/Interchange.pm
-pod/README
-pod/icbackoffice.pod
-pod/iccattut.pod
-pod/icconfig.pod
-pod/icdatabase.pod
-pod/icinstall.pod
-pod/icintro.pod
-pod/ictemplates.pod
-pod/mv_metadata.pod
-pod/usertag.pod
+relocate.pl
 scripts/compile_link.PL
 scripts/config_prog.PL
 scripts/configdump.PL
 scripts/dump.PL
 scripts/expire.PL
 scripts/expireall.PL
+scripts/findtags.PL
+scripts/ic_mod_perl.PL
 scripts/interchange.PL
 scripts/localize.PL
 scripts/makecat.PL
+scripts/newcat.PL
 scripts/offline.PL
 scripts/restart.PL
 scripts/update.PL
-share/akopia/ui/admin/b-configure2.gif
-share/akopia/ui/admin/b-help2.gif
-share/akopia/ui/admin/b-items2.gif
-share/akopia/ui/admin/b-orders2.gif
-share/akopia/ui/admin/b-pages2.gif
-share/akopia/ui/admin/b-regenerate2.gif
-share/akopia/ui/admin/b-statistics2.gif
-share/akopia/ui/admin/back.sm.gif
-share/akopia/ui/admin/bg.gif
-share/akopia/ui/admin/bluedot.gif
-share/akopia/ui/admin/cleardot.gif
-share/akopia/ui/admin/coinlogo.jpg
-share/akopia/ui/admin/curve_left.gif
-share/akopia/ui/admin/curve_right.gif
-share/akopia/ui/admin/delete.gif
-share/akopia/ui/admin/delsm.gif
-share/akopia/ui/admin/down.gif
-share/akopia/ui/admin/folder.gif
-share/akopia/ui/admin/folder.open.gif
-share/akopia/ui/admin/greendot.gif
-share/akopia/ui/admin/icon_config.gif
-share/akopia/ui/admin/icon_design.gif
-share/akopia/ui/admin/icon_error.gif
-share/akopia/ui/admin/icon_help.gif
-share/akopia/ui/admin/icon_item.gif
-share/akopia/ui/admin/icon_merch.gif
-share/akopia/ui/admin/icon_orders.gif
-share/akopia/ui/admin/icon_pages.gif
-share/akopia/ui/admin/icon_people.gif
-share/akopia/ui/admin/icon_regen.gif
-share/akopia/ui/admin/icon_regen_anim.gif
-share/akopia/ui/admin/icon_stats.gif
-share/akopia/ui/admin/index.gif
-share/akopia/ui/admin/layout.gif
-share/akopia/ui/admin/left.gif
-share/akopia/ui/admin/plus.gif
-share/akopia/ui/admin/red_logo.gif
-share/akopia/ui/admin/reddot.gif
-share/akopia/ui/admin/right.gif
-share/akopia/ui/admin/tallyman_logo.gif
-share/akopia/ui/admin/up.gif
-share/akopia/ui/admin/widgets.gif
-share/akopia/ui/help/help.css
-share/akopia/ui/help/help_check.pl
-share/akopia/ui/help/help_make.pl
-share/akopia/ui/help/images/cleardot.gif
-share/akopia/ui/help/images/curve.left.help.gif
-share/akopia/ui/help/images/curve.right.help.gif
-share/akopia/ui/help/images/help.background.gif
-share/akopia/ui/help/src/404.html
-share/akopia/ui/help/src/access.main.html
-share/akopia/ui/help/src/access.permissions.html
-share/akopia/ui/help/src/admin.edit.user.html
-share/akopia/ui/help/src/affiliate.edit.html
-share/akopia/ui/help/src/affiliate.manager.html
-share/akopia/ui/help/src/affiliates.main.html
-share/akopia/ui/help/src/button.builder.html
-share/akopia/ui/help/src/change.password.html
-share/akopia/ui/help/src/create.new.affiliate.html
-share/akopia/ui/help/src/create.new.customer.html
-share/akopia/ui/help/src/crosssell.html
-share/akopia/ui/help/src/customer.edit.html
-share/akopia/ui/help/src/customer.html
-share/akopia/ui/help/src/customer.view.html
-share/akopia/ui/help/src/dbdownload.main.html
-share/akopia/ui/help/src/dbupload.main.html
-share/akopia/ui/help/src/edit.item.html
-share/akopia/ui/help/src/edit.page.html
-share/akopia/ui/help/src/env_vars.html
-share/akopia/ui/help/src/export.main.html
-share/akopia/ui/help/src/faq.html
-share/akopia/ui/help/src/flex.meta.html
-share/akopia/ui/help/src/flex.select.html
-share/akopia/ui/help/src/genconfig.main.html
-share/akopia/ui/help/src/genexport.main.html
-share/akopia/ui/help/src/gensql.main.html
-share/akopia/ui/help/src/genstats.main.html
-share/akopia/ui/help/src/gentable.html
-share/akopia/ui/help/src/glossary.main.html
-share/akopia/ui/help/src/group.main.html
-share/akopia/ui/help/src/help_template.txt
-share/akopia/ui/help/src/import.main.html
-share/akopia/ui/help/src/index.html
-share/akopia/ui/help/src/item.edit.html
-share/akopia/ui/help/src/item.editor.html
-share/akopia/ui/help/src/item.main.html
-share/akopia/ui/help/src/knar.main.html
-share/akopia/ui/help/src/layout.edit.html
-share/akopia/ui/help/src/layout.main.html
-share/akopia/ui/help/src/layoutdownload.main.html
-share/akopia/ui/help/src/layoutupload.main.html
-share/akopia/ui/help/src/license.html
-share/akopia/ui/help/src/logout.main.html
-share/akopia/ui/help/src/matrix.main.html
-share/akopia/ui/help/src/merch.build_related.html
-share/akopia/ui/help/src/merchandising.html
-share/akopia/ui/help/src/order.main.archived.html
-share/akopia/ui/help/src/order.main.pending.html
-share/akopia/ui/help/src/order.view.html
-share/akopia/ui/help/src/order_entry.main.html
-share/akopia/ui/help/src/orderstats.view.html
-share/akopia/ui/help/src/page.editor.html
-share/akopia/ui/help/src/payment.main.html
-share/akopia/ui/help/src/prefs.main.html
-share/akopia/ui/help/src/pricing.html
-share/akopia/ui/help/src/promotion.html
-share/akopia/ui/help/src/reconfig.html
-share/akopia/ui/help/src/regen.main.html
-share/akopia/ui/help/src/search_builder.html
-share/akopia/ui/help/src/shipping.data.html
-share/akopia/ui/help/src/shipping.edit.html
-share/akopia/ui/help/src/shipping.html
-share/akopia/ui/help/src/shipping.main.html
-share/akopia/ui/help/src/shipping.price.html
-share/akopia/ui/help/src/shipping.quantity.html
-share/akopia/ui/help/src/shipping.ups.html
-share/akopia/ui/help/src/shipping.weight.html
-share/akopia/ui/help/src/stats.order.html
-share/akopia/ui/help/src/stats.traffic.html
-share/akopia/ui/help/src/tax.main.html
-share/akopia/ui/help/src/upload.main.html
-share/akopia/ui/help/src/upsell.html
-share/akopia/ui/navigation/A1.gif
-share/akopia/ui/navigation/A1_b.gif
-share/akopia/ui/navigation/A2.gif
-share/akopia/ui/navigation/A2_b.gif
-share/akopia/ui/navigation/A3.gif
-share/akopia/ui/navigation/A3_b.gif
-share/akopia/ui/navigation/B1.gif
-share/akopia/ui/navigation/B10.gif
-share/akopia/ui/navigation/B2.gif
-share/akopia/ui/navigation/B2_b.gif
-share/akopia/ui/navigation/B2_c.gif
-share/akopia/ui/navigation/B3.gif
-share/akopia/ui/navigation/B3_b.gif
-share/akopia/ui/navigation/B3_c.gif
-share/akopia/ui/navigation/B4.gif
-share/akopia/ui/navigation/B4_b.gif
-share/akopia/ui/navigation/B4_c.gif
-share/akopia/ui/navigation/B5.gif
-share/akopia/ui/navigation/B5_b.gif
-share/akopia/ui/navigation/B5_c.gif
-share/akopia/ui/navigation/B6.gif
-share/akopia/ui/navigation/B6_b.gif
-share/akopia/ui/navigation/B6_c.gif
-share/akopia/ui/navigation/B7.gif
-share/akopia/ui/navigation/B7_b.gif
-share/akopia/ui/navigation/B7_c.gif
-share/akopia/ui/navigation/B8.gif
-share/akopia/ui/navigation/B8_b.gif
-share/akopia/ui/navigation/B8_c.gif
-share/akopia/ui/navigation/B9.gif
-share/akopia/ui/navigation/B9_b.gif
-share/akopia/ui/navigation/B9_c.gif
-share/akopia/ui/navigation/akopia_logo.gif
-share/akopia/ui/navigation/cellbackground.gif
-share/akopia/ui/navigation/spacer1.gif
-share/akopia/ui/navigation/spacer2.gif
-share/akopia/ui/navigation/spacer3.gif
-share/akopia/ui/navigation/spacer4.gif
-share/akopia/ui/navigation/spacer_tall.gif
+share/interchange/en_US/az.gif
+share/interchange/en_US/bg.gif
+share/interchange/en_US/box_checked.gif
+share/interchange/en_US/box_empty.gif
+share/interchange/en_US/delete.gif
+share/interchange/en_US/delsm.gif
+share/interchange/en_US/doc.gif
+share/interchange/en_US/down.gif
+share/interchange/en_US/folder.gif
+share/interchange/en_US/folder.open.gif
+share/interchange/en_US/forward.gif
+share/interchange/en_US/generic.gif
+share/interchange/en_US/graylogo.gif
+share/interchange/en_US/icfooter.gif
+share/interchange/en_US/iclogo.gif
+share/interchange/en_US/ico_download.gif
+share/interchange/en_US/ico_duck.gif
+share/interchange/en_US/ico_export.gif
+share/interchange/en_US/ico_folder.gif
+share/interchange/en_US/ico_import.gif
+share/interchange/en_US/ico_magnify.gif
+share/interchange/en_US/ico_pen.gif
+share/interchange/en_US/ico_upload.gif
+share/interchange/en_US/icon_config.gif
+share/interchange/en_US/icon_design.gif
+share/interchange/en_US/icon_error.gif
+share/interchange/en_US/icon_ic.gif
+share/interchange/en_US/icon_item.gif
+share/interchange/en_US/icon_merch.gif
+share/interchange/en_US/icon_orders.gif
+share/interchange/en_US/icon_pages.gif
+share/interchange/en_US/icon_people.gif
+share/interchange/en_US/icon_regen.gif
+share/interchange/en_US/icon_stats.gif
+share/interchange/en_US/index.gif
+share/interchange/en_US/interchange.css
+share/interchange/en_US/layout.gif
+share/interchange/en_US/left.gif
+share/interchange/en_US/logo.gif
+share/interchange/en_US/meta.png
+share/interchange/en_US/minus.gif
+share/interchange/en_US/photo.jpg
+share/interchange/en_US/plus.gif
+share/interchange/en_US/poweredby.gif
+share/interchange/en_US/right.gif
+share/interchange/en_US/smindex.gif
+share/interchange/en_US/specmeta.png
+share/interchange/en_US/text.gif
+share/interchange/en_US/tminus.gif
+share/interchange/en_US/tplus.gif
+share/interchange/en_US/transfer.gif
+share/interchange/en_US/unknown.gif
+share/interchange/en_US/up.gif
+share/interchange/ic.css
+share/interchange/ic1.css
+share/interchange/u/subtab_down_fill.gif
+share/interchange/u/subtab_down_left.gif
+share/interchange/u/subtab_down_right.gif
+share/interchange/u/subtab_fill.gif
+share/interchange/u/subtab_filllwr.gif
+share/interchange/u/subtab_left.gif
+share/interchange/u/subtab_right.gif
+share/interchange/u/tab_dark_left.gif
+share/interchange/u/tab_dark_right.gif
+share/interchange/u/tab_down_fill.gif
+share/interchange/u/tab_down_left.gif
+share/interchange/u/tab_down_right.gif
+share/interchange/u/tab_fill.gif
+share/interchange/u/tab_left.gif
+share/interchange/u/tab_light_left.gif
+share/interchange/u/tab_light_right.gif
+share/interchange/u/tab_right.gif
 test.pl



1.12.4.1  +6 -1      interchange/MANIFEST.SKIP


rev 1.12.4.1, prev_rev 1.12
Index: MANIFEST.SKIP
===================================================================
RCS file: /var/cvs/interchange/MANIFEST.SKIP,v
retrieving revision 1.12
retrieving revision 1.12.4.1
diff -u -r1.12 -r1.12.4.1
--- MANIFEST.SKIP	30 Sep 2000 20:53:55 -0000	1.12
+++ MANIFEST.SKIP	25 Jan 2003 22:20:30 -0000	1.12.4.1
@@ -19,13 +19,14 @@
 \.linux.warned
 \bCVS\b
 \bRCS\b
+^interchange-[0-9]+\..*
 ^lib/Business
 ^lib/File
 ^lib/HTML
 ^lib/IniConf.pm
 ^lib/URI
+^lib/Tie
 ^test(/|$)
-^pod/.*\.pdf
 ^bin(/|$)
 ^blib(/|$)
 ^catalogs/[^.].*
@@ -36,6 +37,7 @@
 ^dist/barry(/|$)
 ^dist/basic(/|$)
 ^dist/books(/|$)
+^dist/construct(/|$)
 ^dist/test(/|$)
 ^dist/etc/[^.]
 ^dist/lib/MiniMate(/|$)
@@ -49,9 +51,12 @@
 ^lib/src/config.status$
 ^lib/src/syscfg$
 ^pm_to_blib$
+^pod/README
+^pod/.*\.pdf
 ^pod/mvtags.pod$
 ^pod/QuickStart.pod$
 ^pod/mvrpm.pod$
+^pdf/README
 ^run(/|$)
 ^scripts/.*[a-z]$
 ^scripts/initp.PL$



1.23.4.16 +217 -247  interchange/Makefile.PL


rev 1.23.4.16, prev_rev 1.23.4.15
Index: Makefile.PL
===================================================================
RCS file: /var/cvs/interchange/Makefile.PL,v
retrieving revision 1.23.4.15
retrieving revision 1.23.4.16
diff -u -r1.23.4.15 -r1.23.4.16
--- Makefile.PL	15 Apr 2001 13:05:25 -0000	1.23.4.15
+++ Makefile.PL	25 Jan 2003 22:20:30 -0000	1.23.4.16
@@ -31,9 +31,7 @@
 my @remove_old;
 my $Lock_troubles;
 
-$VERSION = '4.6.5';
-
-# See if we have the CPAN module
+$VERSION = '4.9.7';
 
 my @os_hints;
 eval {
@@ -51,27 +49,7 @@
 use lib './lib';
 
 
-my $origdir;
-if ($changed_dir_initially) {
-	$origdir = cwd();
-}
-elsif($ENV{PWD}) {
-	## We will try
-	$origdir = $ENV{PWD};
-}
-else {
-	print <<EOF;
-We know this sounds dumb, but we need to know the current directory. Your
-system administratory appears to have set up your system so that you cannot
-search the directory path above you. Were you to ever change directory
-to /tmp or something, you couldn't even walk the tree back to your own
-directory.
-
-EOF
-
-	$origdir = my_prompt(qq{What is the directory you are in currently? });
-
-}
+my $origdir = cwd();
 
 # See if we have Term::ReadLine::Perl
 eval {
@@ -87,8 +65,11 @@
 
 my $term;
 if($TermRead) {
-	$term = new Term::ReadLine 'MakeFile';
-	$Prompt_sub = sub {
+	eval {
+		$term = new Term::ReadLine 'MakeFile';
+	};
+
+	! $@ and $Prompt_sub = sub {
 		my($prompt, $default) = @_;
 		$prompt .= "[$default] "
 			if defined $default && !$ENV{PERL_RL};
@@ -96,8 +77,6 @@
 	};
 }
 
-my $Windows = $^O =~ /win32/i ? 1 : 0;
-
 sub compare_file {
 	my($first,$second) = @_;
 	return 0 unless -s $first == -s $second;
@@ -179,10 +158,11 @@
 
  Interchange V$VERSION
  
-  Copyright (C) 1996-2001 Akopia, Inc. <info\@akopia.com>
-
+ Copyright (C) 1996-2003 Red Hat, Inc., and Interchange Development Group.
  Interchange is free under the terms of the GNU General Public License.
 
+ http://www.icdevgroup.org/
+
 EOF
 }
 
@@ -208,9 +188,6 @@
 
 	my @extra_lib_dirs;
 	my @extra_lib_files;
-	# We will use our own version of File::CounterFile always
-	push @extra_lib_dirs, 'File';
-	push @extra_lib_files, 'File/CounterFile.pm';
 
 	eval {
 		require IniConf;
@@ -236,29 +213,42 @@
 	}
 
 	eval {
+		require Tie::ShadowHash;
+	};
+	if ($@) {
+		push @extra_lib_dirs, 'Tie';
+		push @extra_lib_files, 'Tie/ShadowHash.pm';
+	}
+
+	eval {
+		require Business::Fedex;
+	};
+	if ($@) {
+		push @extra_lib_dirs, 'Business';
+		push @extra_lib_files, 'Business/Fedex.pm';
+	}
+
+	eval {
 		require Storable;
 	};
 	unless ($@) {
-				my $def = 's';
-		        print <<EOF if $MV::Default{storable};
+		my $def = 's';
+        print <<EOF if $MV::Default{storable};
 
 You appear to have Raphael Manfredi's Storable module installed.
-
-This module will significantly improve your DBM storage and
-fetch times.
+This module will significantly improve your DBM storage and fetch times.
 
 You can reply one of:
 
-		n -- Don't use Storable
-		s -- Use for sessions only, won't break existing databases
-		y -- Use for both sessions and databases
+	n -- Don't use Storable
+	s -- Use for sessions only, won't break existing databases
+	y -- Use for both sessions and databases
 
 It is recommended that all installations reply S unless there is a need for
 improved performance in Interchange DBM databases.
 
-If you reply YES and you use any GDBM or DB_File databases
-they will NEED TO BE REMADE for ALL CATALOGS using this
-Interchange server instance.
+If you reply YES and you use any GDBM or DB_File databases they will
+NEED TO BE REMADE for ALL CATALOGS using this Interchange server instance.
 EOF
 
 		if($ENV{MINIVEND_STORABLE_DB} || -f "$realdir/_db_storable" || -f "_db_storable") {
@@ -313,37 +303,28 @@
 }
 
 sub initialize {
-    my %X;
 #warn "Got to initialize\n";
-    $X{INSTALLDIRS}     = "perl";
-	$X{EXE_FILES}  = [qw(
-							scripts/compile_link
-							scripts/config_prog
-							scripts/configdump
-							scripts/dump
-							scripts/expire
-							scripts/expireall
-							scripts/localize
-							scripts/makecat
-							scripts/interchange
-							scripts/offline
-							scripts/restart
-							scripts/update
-						)];
-	$X{PL_FILES}  = {qw(
-							scripts/compile_link.PL scripts/compile_link
-							scripts/config_prog.PL scripts/config_prog
-							scripts/configdump.PL  scripts/configdump
-							scripts/dump.PL        scripts/dump
-							scripts/expire.PL      scripts/expire
-							scripts/expireall.PL   scripts/expireall
-							scripts/localize.PL    scripts/localize
-							scripts/makecat.PL     scripts/makecat
-							scripts/interchange.PL    scripts/interchange
-							scripts/offline.PL     scripts/offline
-							scripts/restart.PL     scripts/restart
-							scripts/update.PL      scripts/update
-						)};
+	my @scripts = map { "scripts/$_" } qw(
+		compile_link
+		config_prog
+		configdump
+		dump
+		expire
+		expireall
+		findtags
+		ic_mod_perl
+		interchange
+		localize
+		makecat
+		newcat
+		offline
+		restart
+		update
+	);
+	my %X;
+	$X{INSTALLDIRS}	= "perl";
+	$X{EXE_FILES}	= [ @scripts ];
+	$X{PL_FILES}	= { 'relocate.pl' => [ @scripts ] };
 
 	if(! $MV::Default{force} and ! $MV::Default{PREFIX}) {
 		if($> == 0) {
@@ -358,7 +339,7 @@
 		$MV::Default{RPMBUILDDIR} = $X{RPMBUILDDIR};
 	}
 
-	return %X if $MV::Default{nocopy};
+	return \%X if $MV::Default{nocopy};
 
     my $uid = $MV::Default{INTERCHANGE_USER};
     if(-f "_uid") {
@@ -368,10 +349,10 @@
         close UID;
     }
 
-#warn "Got past open UID file , uid=$uid user=$> Windows=$Windows\n";
+#warn "Got past open UID file , uid=$uid user=$>\n";
 
 	GETUID: {
-		if($> == 0 and ! $MV::Default{INTERCHANGE_USER} and ! $Windows) {
+		if($> == 0 and ! $MV::Default{INTERCHANGE_USER}) {
 			$uid = my_prompt(
 				qq{Interchange cannot be run as root. Which user should run Interchange? },
 				($uid || 'interch'),
@@ -386,7 +367,7 @@
 		elsif ($uid = $MV::Default{INTERCHANGE_USER}) {
 			# do nothing
 		}
-		elsif (! $Windows) {
+		else {
 			eval {
 				$uid = scalar getpwuid($>);
 			};
@@ -418,27 +399,29 @@
 
 	my $realdir;
 
+	$origdir =~ s:[\\/]\s*$::;
+	$origdir =~ s:^\s*::;
+
 	if(! $MV::Default{final}) {
 		&copyright_prompt();
 
 		# don't suggest install target same as software source directory
 		$MV::Default{PREFIX} = '' if
-			$MV::Default{PREFIX} =~ /^\Q$origdir/;
+			$MV::Default{PREFIX} eq $origdir;
 
 		{
 			$realdir = my_prompt(
 								"Where is your Interchange to be installed? ",
 								$MV::Default{PREFIX},
 								);
-			if ($realdir =~ /^\s*\Q$origdir/) {
+			$realdir =~ s:[\\/]\s*$::;
+			$realdir =~ s:^\s*::;
+			if ($realdir eq $origdir) {
 				warn "Can't install in software source directory!\n";
 				redo;
 			}
 		}
 		print "\n";
-		$realdir =~ s:[\\/]\s*$::;
-		$realdir =~ s:^\s*::;
-		$MV::Default{final} = $realdir if $Windows;
 	}
 	else {
 		$MV::Default{final} =~ s:[\\/]\s*$::;
@@ -447,7 +430,7 @@
 	}
 
 	die "Can't install in software source directory!\n" if
-		! $MV::Default{force} && $realdir =~ /^\Q$origdir/;
+		! $MV::Default{force} && $realdir eq $origdir;
 
 #warn "Got past realdir prompt\n" ; #if $X{RPMBUILDDIR};
 
@@ -456,67 +439,19 @@
 	$X{INSTALLARCHLIB}	= "$realdir";
 	$X{INSTALLPRIVLIB}	= "$realdir/lib";
 	if(! $MV::Default{final}) {
-		$X{INSTALLMAN1DIR}	= "$realdir/doc"
+		$X{INSTALLMAN1DIR}	= "$realdir/man"
 			if ! $MV::Default{INSTALLMAN1DIR};
-		$X{INSTALLMAN3DIR}	= "$realdir/doc"
+		$X{INSTALLMAN3DIR}	= "$realdir/man"
 			if ! $MV::Default{INSTALLMAN3DIR};
 	}
 
-	if (! -f 'pod/mvtags.pod') {
-		chdir 'lib'
-			or die "Cannot chdir to ./lib: $!\n";
-		system("$^X Vend/Tagref.pm > ../pod/mvtags.pod");
-		chdir '..'
-			or die "Cannot chdir back to ..: $!\n";
-	}
-	my @re_link  = qw( interchange bin/minivend );
-	my @re_dir  = qw( simple/download );
-	my @re_copy = qw(	
-						../pod/mvtags.pod simple/download/mvtags.pod
-						);
-
-#warn "Got past mvtags build\n" ; #if $X{RPMBUILDDIR};
-
-	if($Windows) {
-		mk_initp(\%X);
-		my ($in, $out);
-		my $ref = delete $X{PL_FILES};
-		if(! -d 'bin') {
-			File::Path::mkpath('bin');
-		}
-		my (@f);
-		while ( ($in, $out) = each %$ref) {
-			system "$^X $in";
-			if($?) {
-				die "Error making $in into $out: $!\n";
-			}
-			my $targ = $out;
-			$targ =~ s:.*/::;
-			File::Copy::copy($out, 'bin');
-			push @f, "bin/$targ";
-			system "pl2bat.bat $out";
-			if($?) {
-				warn "PL2BAT did not succeed for $out.\n";
-			}
-			else {
-				File::Copy::copy("$out.bat", 'bin');
-				push @f, "bin/$targ.bat";
-			}
-		}
-		# Check for extra needed libraries
-		extra_libs($realdir);
-		my $wanted = sub {
-				return unless -f $_;
-				push @f, $File::Find::name;
-		};
-		File::Find::find($wanted, 'lib');
-		for (@f) {
-			install_file('.', $realdir, $_);
-		}
-	}
-#warn "Got past Windows stuff\n" ; #if $X{RPMBUILDDIR};
+	my @re_link = qw( interchange bin/minivend );
+	my @re_dir  = qw();
+	my @re_copy = qw();
+
+	my $upgrade;
 	if($MV::Default{final}) {
-		$ = 0;
+		$^W = 0;
 		for(glob "_*") {
 			File::Copy::copy($_, $realdir);
 		}
@@ -530,27 +465,39 @@
 		# install share/ files from MANIFEST
 		chomp(my @sharefiles = grep m:^share/:, @files);
 		install_file('.', $realdir, $_) for @sharefiles;
-
-#warn "Got past install SHAREFILES\n" ; #if $X{RPMBUILDDIR};
-
-		# build context-sensitive admin help files
-		my $sourcedir = cwd();
-		BUILD_HELP_HTML: {
-			chdir "$realdir/share/akopia/ui/help" or last BUILD_HELP_HTML;
-			local $/;
-			open HELP_MAKE, "help_make.pl" or
-				warn("Unimportant: Unable to open help_make.pl\n"), last BUILD_HELP_HTML;
-			my $help_make = <HELP_MAKE>;
-			close HELP_MAKE;
-			print "Generating admin help HTML\n";
-			eval $help_make;
-			warn("Unimportant: Error generating admin help HTML\n") if $@;
+		# install code/ files from MANIFEST
+		chomp(my @codefiles = grep m:^code/:, @files);
+		install_file('.', $realdir, $_) for @codefiles;
+		# create symbolic links for images used for
+		# other languages either not yet translated
+		# or without embedded text
+		my @imgfiles = grep m:^share/interchange/en_US/:, @sharefiles;
+		my @loc;
+		@loc = map { s:.*/::; s/\.cfg$//; $_ } glob('dist/lib/UI/locales/*_*.cfg');
+		my $cwd = cwd();
+		my ($locale, $imgfile, $fname);
+		chdir("$realdir/share/interchange")
+			|| die "Couldn't enter directory $realdir/share/interchange: $!\n";
+
+		for $locale (@loc) {
+			unless (-d $locale) {
+				mkdir ($locale, 0777)
+					|| die "Couldn't create directory $realdir/share/interchange/$locale: $!\n";
+			}
+			for $imgfile (@imgfiles) {
+				$fname = basename($imgfile);
+				next if -f "$locale/$fname";
+				symlink ("../en_US/$fname", "$locale/$fname")
+					|| die "Couldn't create symlink $realdir/share/interchange/$locale/$fname: $!\n";
+			}
 		}
-		chdir $sourcedir;
+		chdir($cwd)
+			|| die "Couldn't enter directory $cwd: $!\n";
 
-#warn "Got past install Helpfiles\n" ; #if $X{RPMBUILDDIR};
+#warn "Got past install SHAREFILES\n" ; #if $X{RPMBUILDDIR};
 
 		# install dist/ files from MANIFEST
+		print "Installing dist/ files\n";
 		@files = grep m:^dist/:, @files;
 		chomp(@files);
 		@files = map { s:^dist/::; $_} @files;
@@ -559,7 +506,7 @@
 		chdir 'dist';
 		for (@re_dir) {
 			mkdir $_, 0777
-			 or @re_copy = ();
+				or @re_copy = ();
 		}
 		while ($_ = shift @re_copy ) {
 			my $from = $_;
@@ -568,6 +515,7 @@
 			File::Copy::copy($from, $to);
 		}
 		for (@files) {
+			$upgrade ||= -f "$realdir/$_";
 			install_file('.', $realdir, $_);
 		}
 		chdir '..';
@@ -670,20 +618,33 @@
 		}
 		if(@mods_to_get) {
 			my $mods = join "\n\t", @mods_to_get;
-			print <<EOF;
+			
+			if ($MV::Default{nocpaninstall}) {
+				print <<EOF;
+You do not appear to have all the required modules installed. You are missing:
+
+	$mods
+
+Please run src/cpan_local_install to install them.
+EOF
+  				exit ($MV::Default{force} ? 0 : 1);
+			} else {
+				print <<EOF;
 You do not appear to have all the required modules installed. You are missing:
 
 	$mods
 
 Trying to install now.
 EOF
+			}
+
 			chdir $realdir
 				or die "Couldn't change directory to $realdir: $!\n";
 			system $^X, 'src/cpan_local_install';
 			eval {
-					require Storable;
-					open JUNK, ">_session_storable"
-						and close JUNK;
+				require Storable;
+				open JUNK, ">_session_storable"
+					and close JUNK;
 			};
 			eval {
 				require Business::UPS;
@@ -701,17 +662,28 @@
 			}
 			system $^X, 'src/cpan_local_install', '-c';
 		}
+		if($upgrade) {
+		print <<EOF;
+
+Since this was an update, you are now ready to restart and ensure
+your catalogs run as expected. You do NOT need to re-run makecat,
+though you can always do that to make a new catalog. Never run
+makecat on an existing catalog.
+
+EOF
+		}
+		else {
 		print <<EOF;
 
 You are now ready to cd to $realdir and run 'bin/makecat'
 to set up your first catalog.
 
 EOF
+		}
 		exit;
 
 	}
 
-
 	# Check for extra needed libraries
 	extra_libs($realdir);
 
@@ -722,9 +694,9 @@
 
 sub regularize {
 	for (@_) {
-			s/[\\]\n//g;
-			s/\n\s+/ /g;
-			s/\s+$//g;
+		s/[\\]\n//g;
+		s/\n\s+/ /g;
+		s/\s+$//g;
 	}
 	wantarray ? @_ : $_[0];
 }
@@ -751,16 +723,16 @@
 VERBINST=0
 
 mv_install ::
-			\$(PERL) Makefile.PL force $uidparm final=\$(INSTALLARCHLIB)
+			\$(PERL) Makefile.PL force nocpaninstall=\$(NOCPANINSTALL) $uidparm final=\$(INSTALLARCHLIB)
 
-install :: all pure_install doc_install mv_install
+install :: all pure_install mv_install
 
 EOF
 	$new .= <<EOF;
 rpm_move ::
 		\$(PERL) Makefile.PL force=1 rpmbuilddir=$MV::Default{RPMBUILDDIR} final=\$(INSTALLARCHLIB)
 
-rpm_build :: all pure_install doc_install rpm_move
+rpm_build :: all pure_install rpm_move
 
 EOF
 	$_ = $self->MM::install;
@@ -768,84 +740,82 @@
 	$_;
 }
 
-	my %mv_specific = qw/
-						STORABLE 1 PREFIX 1 FORCE 1 FINAL 1 RPMBUILDDIR 1 INTERCHANGE_USER 1
-					  /;
-	my %delete;
-	use Getopt::Long;
-	my @saveargs = @ARGV;
-	my %optctl = (
-		'junk'			=> sub { 1 },
-		'<>'			=> sub {
-								my ($arg) = @_;
+sub MY::postamble {
+	return <<'EOF';
+UIDIR=dist/lib/UI
+UILCDIR=$(UIDIR)/locales
+
+localefiles:
+	@for langfile in $(UILCDIR)/*_*.cfg; do \
+		lang=`basename $$langfile .cfg`; \
+		mv $$langfile $$langfile.old; \
+		cat $(UILCDIR)/default.cfg >> $$langfile.old; \
+		if ! $(INSTALLBIN)/localize -n -m $$langfile.old -u $(UIDIR) -l $$lang `find $(UIDIR) -type f -not -empty` > $$langfile; then \
+		echo "Failed to generate locale file $$langfile"; \
+		mv $$langfile.old $$langfile; \
+		fi; \
+	done
+EOF
+}
+
+my %mv_specific = qw/
+	STORABLE 1 PREFIX 1 FORCE 1 FINAL 1 RPMBUILDDIR 1 INTERCHANGE_USER 1
+/;
+my %delete;
+use Getopt::Long;
+my @saveargs = @ARGV;
+my %optctl = (
+	'junk'			=> sub { 1 },
+	'<>'			=> sub {
+							my ($arg) = @_;
 	#warn "checking option $arg\n";
-								my ($opt, $val);
-								if($arg !~ /=/) {
-									$opt = $arg;
-									$val = 1;
-								}
-								else {
-									($opt, $val) = split /=/, $arg, 2;
-								}
-
-								$delete{$arg} = 1 if $mv_specific{uc $opt};
-									
-								$MV::Default{$opt} = $val;
-								return;
-							},
-	);
+							my ($opt, $val);
+							if($arg !~ /=/) {
+								$opt = $arg;
+								$val = 1;
+							}
+							else {
+								($opt, $val) = split /=/, $arg, 2;
+							}
 
-	my @options = ( qw/
-		junk
-		<>
-	/ );
-
-	Getopt::Long::config(qw/permute/);
-	GetOptions(\%optctl, @options)
-		or die "Bad option get\n";
-
-	if($MV::Default{PREFIX} and ! $changed_dir_initially) {
-		$origdir = cwd();
-	}
-
-#	use Data::Dumper;
-#	$Data::Dumper::Terse = $Data::Dumper::Indent = 2;
-#	print "ARGV: " . Dumper(\@ARGV);
-#	print "OPT: " . Dumper(\%MV::Default);
-
-	@ARGV = grep ! $delete{$_}, @saveargs;
-
-if($Windows) {
-	&initialize;
-}
-else {
-	WriteMakefile(
-		NAME       => "Interchange",
-		MAN3PODS => {
-						'pod/icbackoffice.pod'	=> 'blib/man3/icbackoffice.8',
-						'pod/iccattut.pod'		=> 'blib/man3/iccattut.8',
-						'pod/icconfig.pod'		=> 'blib/man3/icconfig.8',
-						'pod/icdatabase.pod'	=> 'blib/man3/icdatabase.8',
-						'pod/icinstall.pod'		=> 'blib/man3/icinstall.8',
-						'pod/icintro.pod'		=> 'blib/man3/icintro.8',
-						'pod/ictemplates.pod'	=> 'blib/man3/ictemplates.8',
-						'pod/mv_metadata.pod'	=> 'blib/man3/mv_metadata.8',
-						'pod/mvtags.pod'		=> 'blib/man3/mvtags.8',
+							$delete{$arg} = 1 if $mv_specific{uc $opt};
+
+							$MV::Default{$opt} = $val;
+							return;
 						},
-		DISTNAME => "interchange",
-		clean    => {
-					FILES=> "lib/IniConf.pm _uid _db_storable _session_storable lib/File/CounterFile.pm scripts/initp.pl scripts/compile_link scripts/config_prog scripts/configdump scripts/dump scripts/expire scripts/localize scripts/expireall scripts/makecat scripts/interchange scripts/offline scripts/restart scripts/update dist/simple/download/mvtags.pod",
-				   },
-
-		dist     => {
-						CI => "ci -l -t-Initial",
-						SUFFIX   => ".gz",
-						DIST_DEFAULT => 'all tardist',
-						COMPRESS => "gzip -9f",
-						ZIP_FLAGS => '-pr9',
-					},
-		VERSION_FROM => "scripts/interchange.PL",
-		EXE_FILES  => [],
-		CONFIGURE  => \&initialize,
-	);
-}
+);
+
+my @options = ( qw/
+	junk
+	<>
+/ );
+
+Getopt::Long::config(qw/permute/);
+GetOptions(\%optctl, @options)
+	or die "Bad option get\n";
+
+#use Data::Dumper;
+#$Data::Dumper::Terse = $Data::Dumper::Indent = 2;
+#print "ARGV: " . Dumper(\@ARGV);
+#print "OPT: " . Dumper(\%MV::Default);
+
+@ARGV = grep ! $delete{$_}, @saveargs;
+
+WriteMakefile(
+	NAME     => "Interchange",
+	DISTNAME => "interchange",
+	clean    => {
+				FILES => "lib/IniConf.pm _uid _db_storable _session_storable lib/File/CounterFile.pm scripts/initp.pl scripts/compile_link scripts/config_prog scripts/configdump scripts/dump scripts/expire scripts/localize scripts/expireall scripts/makecat scripts/ic_mod_perl scripts/interchange scripts/newcat scripts/offline scripts/restart scripts/update",
+			   },
+
+	dist     => {
+					CI => "ci -l -t-Initial",
+					SUFFIX   => ".gz",
+					DIST_DEFAULT => 'all tardist',
+					COMPRESS => "gzip -9f",
+					ZIP_FLAGS => '-pr9',
+				},
+	VERSION_FROM => "scripts/interchange.PL",
+	EXE_FILES  => [],
+	CONFIGURE  => \&initialize,
+);



1.14.4.9  +80 -141   interchange/README


rev 1.14.4.9, prev_rev 1.14.4.8
Index: README
===================================================================
RCS file: /var/cvs/interchange/README,v
retrieving revision 1.14.4.8
retrieving revision 1.14.4.9
diff -u -r1.14.4.8 -r1.14.4.9
--- README	15 Apr 2001 13:09:03 -0000	1.14.4.8
+++ README	25 Jan 2003 22:20:30 -0000	1.14.4.9
@@ -1,134 +1,108 @@
-Interchange V4.6.5
+-----------------------------------------------------------------------------
 
-Copyright (C) 1996-2001 Akopia, Inc. <info@akopia.com>
+                           I N T E R C H A N G E
 
-Originally based on Vend 0.2
-Copyright 1995 by Andrew M. Wilcox
+Interchange 4.9.7
 
-Portions from Vend 0.3
-Copyright 1995,1996 by Andrew M. Wilcox
+Copyright (C) 1996-2003 Red Hat, Inc., and Interchange Development Group.
 
-This program is free software; you can redistribute it and/or modify it
-under the terms of the GNU General Public License as published by the
-Free Software Foundation; either version 2 of the License, or (at your
-option) any later version.
+Originally based on Vend 0.2 and 0.3, copyright 1995-96 by Andrew M. Wilcox.
 
-This program is distributed in the hope that it will be useful, but
-WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
-or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
-for more details.
+This program is offered without warranty of any kind.
+See the file LICENSE for redistribution terms.
 
-You should have received a copy of the GNU General Public License along
-with this program; if not, write to the Free Software Foundation, Inc.,
-59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
+-----------------------------------------------------------------------------
 
+Interchange is a full-featured electronic catalog system with
+online ordering; real-time credit card processing hooks; high-end
+database access and retrieval with SQL support; product categorizing,
+merchandising, and discounting; basic customer relationship management;
+dynamic content presentation; content management; internationalization
+and localization support; real-time tax and shipping hooks; reporting;
+and web-based administration.
 
-Welcome to Interchange! This program is completely unsupported, without
-warranty of any kind. The author is interested in problems, suggestions,
-or comments, but does not have time to offer free individual support
-in most cases. See the Akopia website at http://www.akopia.com/
-for more information.
+Interchange absolutely REQUIRES Perl 5.6.0 or later on a Unix-like operating
+system.
 
--------------------------------------------------------------------
+-----------------------------------------------------------------------------
 
-                        I N T E R C H A N G E
+More information is in the following files and directories:
 
-Interchange is a full-featured electronic catalog system (commonly known
-as a shopping cart) with online ordering capability. It is a high-end
-database access and retrieval system with SQL support via the Perl DBI.
+LICENSE          The text of the GNU General Public License (GPL) under which
+                 Interchange is supplied.
 
-A full list of its features is available at:
+README.rpm-dist  Notes on using Interchange when installed from RPM packages.
 
-        http://www.akopia.com/
+README.debian    Notes on using Interchange when installed from Debian packages.
 
-IMPORTANT NOTE: Interchange absolutely REQUIRES Perl 5.005 or Perl 5.6.
+README.cvs       How to access the CVS repository to track ongoing development.
 
-The information you need is in the following files:
+WHATSNEW         Changes per version for this version family.
 
-    README     This file: Copyright info, roadmap to installation
-               and pointers to support system
+UPGRADE          Instructions on how to upgrade from an earlier Interchange
+                 version.
 
-    LICENSE    Your Interchange license -- please read.
-
-    QuickStart Document to help you install Interchange
-
-    WHATSNEW   Change information for all versions in this
-               version family.
-
-    MANIFEST   List of all core distribution files.
+-----------------------------------------------------------------------------
 
 Major files/directories in the distribution:
 
-    Makefile.PL The installation script.
-
-    dist/       The distribution files, exclusive of executable
-                files and modules. Includes:
+Makefile.PL    Script to create a Makefile, used for installation.
 
-                interchange.cfg.dist   Distribution interchange.cfg
-                construct/             The new catalog demo application
-                src/                   C and Perl code for CGI links
-                lib/                   User interface
-                usertag/               Some fairly-standard usertags
+dist/          The distribution files, exclusive of executable
+               files and modules. Includes:
 
-    extra/      Some not-always-needed Perl libraries.
+               interchange.cfg.dist   Distribution interchange.cfg
+               foundation/            Demo catalog skeleton, used by makecat
+               src/                   C and Perl code for CGI links
+               lib/                   Back-end administrative interface
+               code/                  Usertags and other customizable code
 
-    lib/        The library modules needed to run Interchange.
+extra/         Some not-always-needed Perl libraries.
 
-    pod/        Manual pages, viewable with perldoc.
+hints.pl       OS-specific configuration settings. None currently used.
 
-    scripts/    The executable files, relocated to bin/ in the run
-                directory.
+lib/           The library modules needed to run Interchange.
 
-    test.pl     The installation test script.
+scripts/       The executable files, relocated to bin/ in the install
+               directory.
 
--------------------------------------------------------------------
+relocate.pl    Script that adjusts paths in scripts/ for installation into
+               bin/.
 
-UNIX INSTALLATION
-------------------
-Here is the short version:
+test.pl        The installation test script.
 
-    gzip -dc interchange-4.6.*.tar.gz | tar xvf -
-    cd interchange-4.6.*
-    ./configure
+-----------------------------------------------------------------------------
 
-The 'configure' script is basically a shortcut for:
+                          I N S T A L L A T I O N
 
-    perl Makefile.PL
-    make
-    make test && make install
+You can install Interchange as root for a multi-user system-wide setup, or
+as an unprivileged user who will be the only one modifying Interchange files.
 
-Then you will need to make your first Interchange catalog. See the
-section 'DEMO' below.
+Here is the quick installation summary:
 
-Remember to check http://developer.akopia.com/ for documentation and
-help from other users if you have any trouble.
+gzip -dc interchange-4.9.?.tar.gz | tar xvf -
+cd interchange-4.9.?
+./configure
 
-PLEASE NOTE:
-After making configuration changes, make sure to restart the server.
-It won't take but a few seconds, and changes in configurable options
-don't take effect until it is done. You may even change a page and not
-see the effect until the server is restarted.
+The configure script asks where you'd like to install Interchange, and
+(against common practice) also install it.
 
-WINDOWS INSTALLATION
---------------------
-Interchange will not yet run reliably on Windows.
+The Interchange server doesn't do much if it isn't servicing one or more
+actual catalogs, so you next need to make your first Interchange catalog,
+as described in the next section.
 
--------------------------------------------------------------------
+-----------------------------------------------------------------------------
 
-                             D E M O
+                                 D E M O
 
-There is a demo application included called "construct".
+There is a demo catalog skeleton included called 'foundation'.
 
-To install the demo, go to the directory where you installed Interchange
-(default is "interchange" in your home directory, /usr/local/interchange
-for root installations, or /usr/lib/interchange for RPM installations)
-and run:
+To build your own catalog from the demo, go to the directory where you
+installed Interchange (default is "interchange" in your home directory,
+/usr/local/interchange for root installations, or /usr/lib/interchange
+for RPM installations) and run:
 
-    bin/makecat construct
-
-     or
-
-    bin/makecat any_id_you_pick
+bin/makecat
 
 Follow the prompts and after restarting the Interchange server you
 should be able to access the demo catalog.
@@ -137,62 +111,27 @@
 may not be available if you are not using an SQL database such as
 MySQL or PostgreSQL.
 
-Visit http://demo.akopia.com/ to see a live demo on our servers.
-
--------------------------------------------------------------------
-
-                     D O C U M E N T A T I O N
-
-The documentation is in several man pages and HTML files in the doc/
-subdirectory of the main Interchange directory.
-
-There is extended documentation available at
-http://developer.akopia.com/
-which includes user-annotated documentation, HTML versions of the manual,
-and a user-contributed code library.
-
--------------------------------------------------------------------
-
-                      A V A I L A B I L I T Y
-                              A N D
-                     C O M P A T I B I L I T Y
-
-Interchange 4 has been tested on Linux, FreeBSD, Solaris 2.x, and Digital
-UNIX/Tru64. Its predecessor Minivend 3 also reportedly runs on SCO, AIX,
-and other Unix ports. It should work on any UNIX or Win32 OS with Perl
-5.005 or higher.
-
-IMPORTANT NOTE FOR BSD USERS: Interchange has been known to segfault when
-reading sockets on Perl. This occurs more frequently on a busy system.
-The workaround is to set in minivend.cfg:
-
-    MaxServers   0
-    Housekeeping 1
+Visit http://demo.icdevgroup.org/ to try out a live demo.
 
-Windows does not support fork(), so the server runs in the foreground. There
-are other differences, and there may be portablity problems. Interchange is
-not yet tested to run on Windows; the canonical installation is UNIX.
+-----------------------------------------------------------------------------
 
--------------------------------------------------------------------
+                         D O C U M E N T A T I O N
 
-                    K N O W N   P R O B L E M S
+A documentation package is available, with documentation in many different
+formats. This and other information is available at the Interchange home on
+the web:
 
-BSDI, FreeBSD, NetBSD:
-    You will need to make sure the following are in effect
-    in minivend.cfg:
+http://www.icdevgroup.org/
 
-        MaxServers 0
-        Housekeeping 1
+-----------------------------------------------------------------------------
 
-    Expect lots of crashes if you don't do this.
+                         C O M P A T I B I L I T Y
 
-Apache with suEXEC:
-    VLINK/UNIX socket mode will not work well unless you do the
-    install as a normal user. If you are going to support multiple
-    users, you must use TLINK/INET mode.
+Interchange is regularly tested on Linux, FreeBSD, and Solaris. It
+has also been used on OpenBSD, Digital UNIX/Tru64, SCO, AIX, and other
+Unix variants. It should work on any Unix with Perl 5.005 or higher and
+the necessary Perl modules.
 
-Windows:
-    Interchange will not work properly with Windows. No strategy
-    has been yet developed for providing reliable operation on Windows.
+-----------------------------------------------------------------------------
 
--------------------------------------------------------------------
+(end)



1.2.4.6   +83 -77    interchange/README.cvs


rev 1.2.4.6, prev_rev 1.2.4.5
Index: README.cvs
===================================================================
RCS file: /var/cvs/interchange/README.cvs,v
retrieving revision 1.2.4.5
retrieving revision 1.2.4.6
diff -u -r1.2.4.5 -r1.2.4.6
--- README.cvs	7 Dec 2000 20:43:25 -0000	1.2.4.5
+++ README.cvs	25 Jan 2003 22:20:30 -0000	1.2.4.6
@@ -1,70 +1,46 @@
-=head1 NAME
+------------------------------------------------------------------------------
 
-Interchange CVS -- tracking the distribution
+                   Tracking Interchange development in CVS
 
-=head1 DESCRIPTION
+------------------------------------------------------------------------------
 
-If you don't want to wait for an official distribution, you can use
-anonymous CVS to follow the latest Interchange.
+If you don't want to wait for an official release, you can use anonymous
+CVS to follow the latest Interchange development.
 
-B<WARNING:> There may be bugs introduced at any time! Thoroughly test
-any changes before incorporating. Better yet, don't use CVS changes
-for anything but fixing present bugs, and run the latest release.
+WARNING: There may be bugs introduced at any time! Thoroughly test any
+changes before incorporating. Better yet, don't use CVS changes for
+anything but fixing present bugs, and run the latest release.
 
-=head1 USING THE CVS DISTRIBUTION
 
-The basic steps are:
+Check out a local copy
+----------------------
 
-=head2 Check out from CVS
-
-You need to have CVS installed on your system, to begin with. It comes
-as a default on most free Unix-like systems if you selected the
-development tools at install time.
+You need to have CVS installed on your system, to begin with. It
+comes pre-installed on most free Unix-like systems if you selected
+the development tools at install time. See http://www.cvshome.org/
+for download locations if you don't have it.
 
 If you are already an experienced CVS user, the information is:
 
-	CVSROOT   :pserver:anon_cvs@cvs.akopia.com:/anon_cvs/repository
-	password  anon_cvs
+	CVSROOT   :pserver:cvs@cvs.icdevgroup.org:/var/cvs
+	password  (none)
 	module    interchange
 
-If you are not experienced, it is still easy to get by following the
-few steps below.
-
-=over 4
-
-=item Set CVSROOT
-
-Using bash/ksh/sh, type at the shell prompt:
-
-	$ CVSROOT=:pserver:anon_cvs@cvs.akopia.com:/anon_cvs/repository
-	$ export CVSROOT
-
-If you use tcsh/csh, do:
-
-	% setenv CVSROOT :pserver:anon_cvs@cvs.akopia.com:/anon_cvs/repository
-
-=item Log in to CVS
-
-Before you can check out from the server, log in:
-
-	$ cvs login
-	password: anon_cvs
-
-=item Select a place to put it and check it out
-
-Your home directory or more probably a src/ subdirectory:
+If you are not experienced with CVS, it is still easy to get going by
+following these steps. First, choose a place to put the local copy you're
+going to check out. A good choice is somewhere in your home directory,
+probably a src/ subdirectory:
 
 	$ cd
 	$ mkdir src
 	$ cd src
-	$ cvs checkout -P interchange
+	$ cvs -z3 -d :pserver:cvs@cvs.icdevgroup.org:/var/cvs checkout -P interchange
 
-It will take a while -- if you are on a modem it may take quite a bit
-of time, as there are several megabytes of files to download.
+It will take a while, as there are several megabytes of files to download.
 
-=back
 
-=head2 Make an installation tar file
+Make a distribution tar file
+----------------------------
 
 If it is your first time installing Interchange from the CVS, you will want
 to make a distribution tar file:
@@ -74,42 +50,54 @@
 	Writing Makefile for Interchange
 	$ make tardist
 	/usr/local/bin/perl -I/YOUR/PERL/LIB -MExtUtils::Manifest=manicopy,maniread \
-	-e "manicopy(maniread(),'interchange-4.6.x', 'best');"
-	mkdir interchange-4.6.x
-	mkdir interchange-4.6.x/dist
+	-e "manicopy(maniread(),'interchange-4.9.x', 'best');"
+	mkdir interchange-4.9.x
+	mkdir interchange-4.9.x/dist
 	....
 	$ ls interch*
-	interchange-4.6.x.tar.gz
+	interchange-4.9.x.tar.gz
 
-=head2 Unpack and install
 
-Unpack the tar file and install as is normal. See the README and QuickStart
-files for help.
+Unpack and install
+------------------
 
-=head2 Checking for differences
+Unpack the tar file and install as normal. See the README file and other
+documentation for help. You should already be familiar with the Interchange
+developer website at:
 
-If you want to see how your current image compares to the repository, log in
-to CVS and run:
+	http://www.icdevgroup.org/
+
+Make sure you don't check out your CVS copy into $HOME/interchange
+and then install on top of it, since $HOME/interchange is the default
+install directory.
+
+
+Checking for differences
+------------------------
+
+If you want to see how your current image compares to the repository,
+cd into your checked out CVS copy and run:
 
 	cvs diff | more
 
-=head2 Updating
 
-To update the distribution, log into CVS as above, change to the distribution
-directory (i.e. src/interchange), then run:
+Updating
+--------
+
+To update the distribution, change to your checked out CVS directory
+(e.g. src/interchange), then run:
 
-	$ cd $HOME/src/interchange
-	$ cvs update
+	$ cvs update -Pd
 	U MANIFEST
 	U WHATSNEW
 	....
 
 In many cases, the major differences in the distribution will be easily
-updateable. You can copy any changed files directly to these
-library directories:
+updateable. You can copy any changed files directly to these library
+directories:
 
-	lib/Vend           (and all subdirectories)
-	lib/UI             (and all subdirectories)
+	lib/Vend    (and all subdirectories)
+	lib/UI      (and all subdirectories)
 
 You should check the files:
 
@@ -123,7 +111,9 @@
 diffs against the source files in scripts/*.PL, or do another install
 to a blank directory and do a diff to that.
 
-=head2 Keeping the catalog in sync
+
+Keeping the catalog in sync
+---------------------------
 
 If you are patterning your order methods after one of the template
 catalogs, you will want to check the products/*.txt and products/*.asc
@@ -132,19 +122,35 @@
 to merge the databases manually. In most cases, you can import them
 into a spreadsheet or database.
 
-=head1 Troubleshooting
 
-Some problems can occur due to the CVS image being dynamic.
+Troubleshooting
+---------------
 
-=head2 MANIFEST out of sync -- file not found
-
-If you get a complaint that a "file is not found" when trying to do 
-a C<make tardist> or C<make dist>, just do:
+If you get a complaint that a "file is not found" when trying to do a
+'make tardist' or 'make dist', that means your MANIFEST file is out of
+sync with the current codebase. Just do:
 
 	rm MANIFEST
 	make manifest
 
-=head2 Trying to run from the CVS directory
 
-If you install in the directory where your CVS image lives, you will have
-problems.
+More on CVS
+-----------
+
+If you plan to frequently use CVS, it is helpful to create a .cvsrc file
+in your home directory with commonly-used options such as these:
+
+	cvs -z3
+	diff -u
+	update -Pd
+	checkout -P
+
+This directs CVS to (1) automatically compress all data communicated
+between you and our server (saving bandwidth); (2) show context-sensitive
+diffs; (3) prune empty directories and create any new directories added
+to the repository since your checkout; and (4) prune empty directories
+during your checkouts.
+
+Please see the CVS website for complete documentation:
+
+	http://www.cvshome.org/



1.1.2.3   +25 -14    interchange/README.debian


rev 1.1.2.3, prev_rev 1.1.2.2
Index: README.debian
===================================================================
RCS file: /var/cvs/interchange/README.debian,v
retrieving revision 1.1.2.2
retrieving revision 1.1.2.3
diff -u -r1.1.2.2 -r1.1.2.3
--- README.debian	1 Apr 2001 13:46:33 -0000	1.1.2.2
+++ README.debian	25 Jan 2003 22:20:30 -0000	1.1.2.3
@@ -3,27 +3,38 @@
 
 This document contains information about the Interchange Debian packages.
 
-Status
-------
-
-The Interchange Debian packages are experimental and should not used
-on production systems. They may hose your installation. You have been
-warned! Please note that these packages contain several modifications 
-not (yet) approved by Akopia.
-
 Feedback
 --------
 
 Please send your comments and bug reports to Stefan Hornburg (Racke)
-<racke@linuxia.de>.
+<racke@linuxia.de>. He is the Interchange core developer responsible 
+for the Interchange Debian packages. 
 
 APT Sources
 ===========
 
-Interchange Debian packages for unstable (sid) are part of the Debian
-distribution.
+Interchange Debian packages for stable (woody), testing (sarge) 
+and unstable (sid) are part of the official Debian distribution.
+
+Up-to-date Interchange Debian packages for stable are available from:
+
+deb http://ftp.icdevgroup.org/interchange/debian interchange main
+deb-src http://ftp.icdevgroup.org/interchange/debian interchange main
 
-Interchange Debian packages for stable (potato) are available from:
+Debian Specific Changes
+=======================
+
+* all catalog configuration should we put into catalogs.cfg, so that 
+  /etc/interchange/interchange.cfg can upgraded easily 
+
+* any global usertags used locally should go into /etc/interchange/usertag
+  and they'll be included if they have the extension .tag
+
+Other Notes
+===========
 
-deb http://ftp.minivend.com/interchange/debian interchange main
-deb-src http://ftp.minivend.com/interchange/debian interchange main
+* if the selected Interchange user (default: interchange, may be changed
+  through debconf) doesn't exists at installation time, it will created.
+  Due to security reasons the shell for this user will be set to
+  /bin/false and the password for this user will be disabled. Use 
+  su -s /bin/sh if you need to become the Interchange user.



1.8.4.15  +1327 -275 interchange/WHATSNEW


rev 1.8.4.15, prev_rev 1.8.4.14
Index: WHATSNEW
===================================================================
RCS file: /var/cvs/interchange/WHATSNEW,v
retrieving revision 1.8.4.14
retrieving revision 1.8.4.15
diff -u -r1.8.4.14 -r1.8.4.15
--- WHATSNEW	15 Apr 2001 13:04:25 -0000	1.8.4.14
+++ WHATSNEW	25 Jan 2003 22:20:30 -0000	1.8.4.15
@@ -1,400 +1,1452 @@
-Interchange 4.6.5
+------------------------------------------------------------------------------
 
-* Fix two admin security holes, in do_view and page_save. Thanks to
-  Merlyn J. Pease <peasemj@bellatlantic.net> for reporting in bug #167.
+                  What's new in each version of Interchange
+                       (since the version 4.8 branch)
 
-* Several minor database field definition improvements.
+------------------------------------------------------------------------------
 
-* Clean up cruft in sample pricing table.
+Interchange 4.9.7 not yet released
 
-* Prevent admin/genconfig.html error.log entry about not being able to
-  display status file with NoAbsolute set.
 
-* Backport from 4.7 the error report if page couldn't be saved by
-  admin/page_save.
+Core
+----
 
-* Fix a couple of bugs with AlwaysSecure not working in an order link.
+* Allow [PREFIX-more-list] ... [/PREFIX-more-list] for nested loops.
 
-* Fix rounding problem with Shipping.
+* Support sparsely-populated quantity pricing tables.
 
-* Fix problem with FullURL.
+* Fix bug in field name ranges in CommonAdjust where q99..q101 was handled
+  as a Perl alphanumeric range q99, r00, r01, r02, etc. instead of
+  q99, q100, q101.
 
-* Add stub for test_column in Table/InMemory.pm.
-  Problem found by vasile_abo@wexim.com.
+Menu
+----
 
+* Add category-specific image links and toggles for the tree menu.
 
-Interchange 4.6.4
+  To enable this for toggles, do:
 
-* Added mod_interchange to the standard Interchange distribution.
-  It is the direct descendant of mod_minivend, created by Francis
-  J. Lacoste <francis.lacoste@iNsu.com> at iNsu Innovations Inc.
-  in 1999. With Francis's blessing, we're taking over maintenance of
-  the module. Thanks, Francis!
+  	  [menu
+	  		menu-type=tree
+			...
+			specific-image-toggle=N
+			]
 
-* Changed test.pl to use Errno.pm to derive socket test error messages.
-  Thanks to Patxi Larrayoz Elcano <larrayoz@retemail.es> for finding this.
+  Where N is the level (1 == 0) to which you wish to do this.
+
+  The image for a non-toggled category comes from the tree database field
+  img_up, for a toggled category from img_dn.
+
+  You can set the base URL for the images with:
+
+  		specific-image-base="__IMAGE_DIR__";
+
+  A trailing / is added if not already present.
+
+  If you wish to allow image anchors for links as well, put the image
+  name in the img_up field and add the parameter:
+
+  	       specific-image-link=1
+
+  If the image name is not present, the normal "name" field is used.
+
+  To enable all of this for the example product_tree component, you would
+  have a call of:
+
+	[menu tree-selector="[control tree_selector Products]"
+			link-class="[control link_class barlink]"
+			link-style="[control link_style]"
+			link-class-open="[control link_class_open]"
+			link-style-open="[control link_style_open font-size: larger;]"
+			link-class-closed="[control link_class_closed]"
+			link-style-closed="[control link_style_closed font-size: larger;]"
+			no-image="[control no_image]"
+			menu-type=tree
+			specific-image-toggle=1
+			specific-image-base="__IMAGE_DIR__/tree"
+			specific-image-link=1
+			reparse=0]
+
+
+UI
+--
+
+* Fix dependency of page editor on certain [if ...] conditions in page code.
+
+* Add "send help edit to ICDEVGROUP" function in the online help editor.
+
+* Change name of "Bottom" menu (which was on top) to "Fixed". 
+
+Payment
+-------
+
+* Add support for Verisign's PFProAPI.pm Perl module, which implements
+  Payflow Pro gateway communication without needing any external binary,
+  and thus no forking or temporary files for communication. Use PFProAPI
+  automatically if it is found at IC startup time, but fall back to pfpro
+  or pfpro-file if not. Upgrades should be transparent.
+
+Foundation
+----------
+
+* Make metadata correspond to current UI version.
+
+Debian
+------
+
+* Default traffic setting is low now.
+
+* Allow selection of traffic setting with debconf and interchangeconfig.
+
+* Specify unix and inet modes explicitly if user selects both. 
+
+* Check if /etc/init.d/interchange and /usr/sbin/interchangeconfig are 
+  executable in interchange-ui maintainer scripts.
+
+Miscellaneous
+-------------
+
+* Fix a bug that prevented the cgi-bin link program from being associated 
+  with the chosen owner and group. The patch was created and tested by Carl
+  Bailey.
+
+
+------------------------------------------------------------------------------
+
+
+Interchange 4.9.6, released 8-Jan-2003.
+
+
+Core
+----
+
+* Perl version 5.6.0 or newer is now a requirement to run Interchange.
+
+* Add new global directive TrustProxy, which allows the administrator to
+  designate certain IP addresses or hostnames as trusted proxies, whose
+  claims (via the HTTP_X_FORWARDED_FOR environment variable) about the
+  original requesting host will be believed.
+
+  When using a front-end proxy for Interchange, all requests appear to come
+  from that proxy, say 127.0.0.1 if on the same machine, which is effectively
+  the same as running WideOpen because sessions can be easily hijacked. This
+  offers a way to bring back a little discernment about what host we're
+  really dealing with.
+
+  Usage is identical to the RobotIP directive's, for example:
+
+  TrustProxy 127.0.0.1, 10.0.0.*
+
+  I'm not sure why anyone would want to do this, but it could also be used
+  with external HTTP proxies in general (which hopefully aren't lying), with
+  a simple 'TrustProxy *'.
+
+* Fix whitespace transform and tolerate leading whitespace on HTTP
+  header lines.
+
+* Avoid persistent storage to make [summary] safe in prefork mode.
+
+* Allow a database to spring into existence without a .txt file. TO
+  do this, you define the field names in the NAME paramter.
+
+      Database will_be_there  will_be_there.txt  __SQLDSN__
+      Database will_be_there  NAME   code  field1 field2
+      Database will_be_there  CREATE_EMPTY_TXT  1
+
+  All it does is create the .txt file (or whatever the name is) from
+  the value of NAME array. It does take delimiters into account.
+
+  You must be just a bit careful, since if you then remove the .txt
+  file it will of course recreate the table. Of course you should
+  take that into account when setting this non-default parameter.
+
+  This will allow some one-file configurations to be added to the
+  system.
+
+* Allow autonumber for the linked-table behavior of update_data. Before,
+  you couldn't autonumber because the determination of whether the data
+  would be set was whether the key value is present. This allows
+  you to set mv_data_qual=fieldname and have a non-empty value in
+  that field determine whether to insert or not.
+
+* Minor cleanup in Data.pm, including ensuring $obj->{DELIMITER} 
+  and $obj->{delimiter} match.
+
+* Avoid infinite loops in catalog configuration caused by includes.
+
+* Compile warnings in catalog usertags now show up in the logs instead
+  of "UserTag 'ugly_hack' code is not a subroutine reference".
+
+* Add new database configuration option PREFER_NULL. It accepts a list of
+  field names which should be set to NULL instead of an empty string
+  whenever possible:
+
+  Database  people  PREFER_NULL  age height
+
+  Probably most useful with numeric or date fields that are nullable, to
+  prevent import errors when trying to store '' into a numeric field. Also
+  for character fields that you'd rather have contain a NULL than '' to
+  comply with a CHECK or foreign key constraint.
+
+UserTags
+--------
+
+* Obsolete usertags dbinfo, e, if-key-exists, if_sql, reconfig_wait, 
+  rotate_file, with and write_page removed.
+
+Filters
+-------
+
+* Allow % in filter arguments. This could conceivably be a problem for
+  someone who had a filter ".%s" or something.
+
+Content Management
+------------------
+
+* Get restrict_allow settings right -- the default was not allowing the "var"
+  to be expanded in the image preview path. Should probably look at this
+  concept on a per-field basis, and set the default to "".
+
+Payment
+-------
+
+* Patch to display errors from payment modules in credit card header
+  on checkout page.
+
+Foundation
+----------
+
+* Multi-language support, configured by the LOCALES and DEFAULTLOCALE
+  variables.
+
+* Updated region templates.
+
+* New PayflowPro control variables MV_PAYMENT_PARTNER and MV_PAYMENT_VENDOR.
+
+* Payment routes use now generic MV_PAYMENT_* variables.
+
+* Test order page added.
+
+Shadow Database
+---------------
+
+* lookup_table option added
+
+* foreign method implemented
+
+* test_record calls underlying database now
+
+Installation
+------------
+
+* Debian packages support the selection of the GnuPG home directory 
+  during installation now.
+
+mod_interchange
+---------------
+
+* Fixed a weird bug where empty HTTP variables were being passed
+  under certain circumstances.
+
+* Fixed a bug reported by Jeff Dafoe.  The request information
+  enabled Interchange to show the correct page but prevented it
+  from storing the request in the session's history.  The problem
+  only showed itself when Interchange's [history-scan] tag was used.
+  As almost no page history was saved, [history-scan] sent the user
+  to the default page (usually index) most of the time. 
+
+
+------------------------------------------------------------------------------
+
+
+Interchange 4.9.5 released 2002-12-13 (minor bugfix release).
+
+
+Foundation
+----------
+
+* Add component files for new selectable results-list done by Ton.
+
+* Make proper patches to history-scan and barlink() to work with Randy
+  Moore's category_vert_toggle component.
+
+* Minor updates to category_vert_toggle component for HTML cleanup and 
+  performance improvement.
+
+Core
+----
+
+* Fixed problem with PreFork and mod_perl modes where Interchange children
+  kept order profile state between runs.
+
+* Make sure STDERR is selected in mod_perl mode in case some other mod_perl 
+  code uses select. 
+
+* Change default for MaxServers in "rpc" profile to zero. This is probably
+  best for the vast majority of servers running in PreFork mode.
+
+* Tolerate missing configdb database, issue warning only.
+
+* Tolerate people forgetting and putting , on the end of a parameter
+  when using line2options. A comma should never be the last character, I
+  would think, but you can choose to not use the filter if by some
+  bizarre chance it is needed.
+
+* A number of refinements and fixes to Menu module.
+
+	- Passing timed=1 to [menu ...] tag prevents putting session ID and
+	  count in URL, allowing timed-build to work well.
+
+	- first_line and last_line transforms allow you to specify a field
+	  to set to trigger the first line or the last line of the menu.
+	  This allows the current IC menu structures to work well with
+	  menus separated by space.
+
+	- logical_page feature allows a tab "up" indication in another
+	  menu, based on the page of the entry. This allows multi-level
+	  tabs to have an "up" indication on different menus.
+
+	- expand_values_form allows setting of ITL tag values even
+	  on multiple form values.  Honors [cgi ..], [value ..], and [var ..].
+
+    - Fix ordering of open paramter for trees -- it was broken by the new
+	  Vend::Util::vendUrl routine.
+
+* Simplify field_settor subroutines with prepared query and placeholders.
+  Prevents infamous DBD::Pg::do errors.
+
+* Form module -- add intrinsic "file" type, and allow setting of a
+  widget class directly without using "extra".
+
+* Other minor bugfixes too insignificant to mention.
+
+UserTags
+--------
+
+* min-rows option added to table-organize tag. Allows building small
+  result sets in one column (or however many columns needed to reach
+  min-rows).
+
+* Reworked [tree ...] tag to use DBI placeholders if supported.
+  While this doesn't seem to save too much CPU on a machine that
+  has the database and IC on the same machine, it should relieve
+  some network bandwidth on distributed setups.
+
+Installation
+------------
+
+* Various debian build patches.
+
+
+------------------------------------------------------------------------------
+
+
+Interchange 4.9.4 released 2002-12-02.
+
+* Fix problem with PreFork and mod_perl modes where Interchange children
+  kept order profile state between runs.
+
+* Tolerate people forgetting and putting , on the end of a parameter
+  when using line2options.
+
+Core
+----
+
+* The interchange script is now only used for configuration and
+  options. All code that previously resided there (notably the
+  dispatch(), respond(), update_data(), and do_order() routines)
+  has been relocated. Code that calls ::update_data, etc. should
+  NOT break, because we still use the modules in the script.
+  This caused the addition of Vend::Dispatch to hold many of
+  the routines.
+
+* Added new [deliver ....] tag that allows you to deliver some content
+  without worrying about [tag op=header] and page spacing issues. Adds 
+  new global variable $Vend::Sent which is authoritative notification
+  that all content is sent and that all further parsing of ITL
+  should stop.
+
+* Add mv_source parameter which sets an affiliate program source
+  and can be carried around in URLs when $Scratch->{mv_add_source}
+  is set. This solves the problem of AOL caching the page with
+  the source embedded, then forwarding the next request sans source.
+
+  From a suggestion by Dan <ic@concolor.org>.
+
+* Add new [menu ...] tag which can build simple, tree, and flyout
+  menus from a menu specification. See the UI.
+
+* Add robot tolerance facility, where mv_tmp_session is set when either
+  a RobotUA, RobotIP or RobotHost wildcard matches.
+
+  In interchange.cfg:
+
+      RobotUA   Inktomi, Scooter, Site*Sucker
+      RobotIP   209.135.65, 64.172.5.*
+      RobotHost *.googlebot.com
+
+  After that, it is all automatic. mv_tmp_session gets set to one, the
+  Scratch values mv_no_session_id and mv_no_count are set to one, and
+  normal pages don't get IDs put out by area.
+
+  What this will do for the user:
+
+        1. Allow those UAs to follow a URL.
+        2. Prevent useless session files from cluttering disk
+        3. Prevent session writes from inhibiting disk performance.
+
+* Added a (global) HostnameLookups directive to specify whether Interchange
+  should perform a DNS lookup to resolve the remote user's hostname from
+  their IP address.  The default is 'No'.  Hostnames are required for
+  facilities such as the RobotHost check to work.  If the web server is
+  configured to perform hostname resolution then this directive should remain
+  set to 'No'.
+
+* Add the oft-requested DirectoryIndex feature. 
+
+* Add new content management features. This allows Interchange to:
+
+    -- Accept Apache error redirects, i.e. handle 404 errors
+    -- Initially process page, process page after variables, and
+       process page before image substitution with configurable subroutines
+    -- Take puts for DAV-style publishing
+
+*   New "AcceptRedirect" directive. If "Yes", will look for REDIRECT_URL,
+    REDIRECT_QUERY_STRING, etc. and use those to provide the request.
+
+    This allows:
+
+        ErrorDocument 404 /cgi-bin/foundation
+
+    At that point, a request for /index.html that is not found will
+    be equivalent to /cgi-bin/foundation/index.html and will be
+    indistinguishable from the real page by the client.
+
+*   New Pragmas init_page, pre_page, post_page, which specify
+    Sub/GlobalSub routines to run at various points in page build.
+
+    init_page     Run before Variable substitution
+    pre_page      Run after Variable substitution, before interpolation
+    post_page     Run before Image substitution
+
+* Allow PUT operations. Add
+
+    [value-extended test=isput]       Check for a PUT
+    [value-extended put_contents=1]   Return PUT string
+    [value-extended put_ref=1]        Return ref to PUT string (scalar)
+
+  Some more DAV-type features can be done, I think, but they are not yet
+  scoped.
+
+* Remove min_string test from Search.pm, where it never really was used
+  or called due to mv_min_string default being 0.
+
+* Place mv_min_string check back in Glimpse where it was intended in the first
+  place.
+
+* Convert Mac line endings to Unix (as well as DOS).
+
+* Finally discovered what is going on with GPG and errors.
+
+  -- If PGP fails due to a system problem, like out of memory or
+     bad file permissions, it fails with a status that will cause
+     a real error which is in the lower 8 bits.
+
+  -- If PGP fails due to an internal problem like "key not found",
+     or no secret key ring, it will fail with system status set to
+     zero but the upper level status indicating its problem.
+
+     So a failed key will turn up as "File not found" in the
+     upper order bits, while a key *ring* not found will fail
+     with the same error in the lower status bits.
+
+  This patch is temporary, and at least tells you what $! is. I will
+  examine GPG's error messages and provide some simple ones like "key
+  not on keyring" and catch them to provide a better error.
+
+* Add general multiple-table update feature to Vend::Data::update_data.
+
+* Allow authoritative table name for constructed queries. Usage:
+
+    my $db = database_exists_ref($table);
+    my $tname = $db->name();
+
+    my $query = "select * from $tname";
+    $db->query($query);
+
+  This should allow REAL_NAME many more places.
+
+* New mv_cleanup operates like mv_click and mv_check, but operates
+  after a form processing action is done.
+
+* Added debug type to [log].
+
+* [userdb function=logout clear=1] will now restore the appropriate
+  ScratchDefault and ValuesDefault values instead of simply
+  deleting the scratches and values under its control.
+
+* Added check for no_increment so that mv_order_number can be set in
+  a route.
+
+* Fix bug where bad [nitems compare=...] could cause server error. Now
+  just silently causes bad compare.
+
+* Allow alternate values spaces with $CGI->{mv_values_space}. This allows
+  fill-in wizards, surveys, and such to not pollute the user's normal
+  values.
+
+  Use with caution -- if someone is in the practice of using $Values
+  to set catalog behavior (usually a poor idea) then it can cause
+  anomalies.
+
+* Clean up a few references to $Vend::Session->{values} which should
+  never be done anymore -- we had handled almost all of this previously.
+  It should always reference $::Values.
+
+Installation
+------------
+
+* "you are now ready to run makecat" is no longer displayed on upgrades.
+
+* Prevent test from failing on upgrades.
+
+Payment
+-------
+
+* Patch from Mark Johnson to Vend::Payment::Signio module whose explanation
+  we quote: 
+  If you send a garbage ORIGID, as IC does by default, it will attempt to
+  use that as the key for the transaction, without falling back on the data
+  you sent with it. Thus, it must explicitly not be used unless you have a
+  valid one which you want to use. This was why no credits were succeeding;
+  even though we were sending explicit new data, it ignored it and cried 
+  with the ever useful error "Not signed up for this tender type".
+
+* Added a Vend::Payment::TestPayment module to allow developers to test
+  their site's interaction with the Interchange Payment system, without
+  actually being connected to a real Payment Services Provider. 
+
+* Change AuthorizeNet.pm to more easily enable settlement of orders
+  done via AUTH_ONLY.
+
+* Prevent automatic try at credit card encryption if no EncryptKey
+  is present.
+
+Filters
+-------
+
+* Add new filter, "next_sequential". Allows selection of a next-sequential
+  value based on a field (and qualified by a field).   
+
+  [filter op="next_sequential.survey_q.sort"][cgi sort][/filter]
+
+  will:   
+
+    1. Return the existing value if present.
+    2. If existing value is blank, return max + 1 in the sort field,
+       i.e. equivalent to: 
+
+           SELECT sort FROM survey_q
+       ORDER BY sort DESC
+       LIMIT 1   
+
+  If another argument of a field name is passed, i.e. 
+
+    filter => 'next_sequential.survey_q.sort.sel',   
+
+  then you get: 
+
+       SELECT sort FROM survey_q
+       WHERE sel = '[cgi sel]'
+       ORDER BY sort DESC
+       LIMIT 1   
+
+  This allows a next-sequential numbering for things that need it.
+  Developed to support general-purpose survey UI for Ton's excellent
+  product rating system.
+
+* Fix bugs in option_format filter. It would turn commas into new options;
+  and alternate delimiters had no hope of working.
+
+* Add options2line and line2options filters, allowing you to specify
+  options in a textarea without comma separators and instead with one
+  option per line.
+
+Profiles
+--------
+
+* Add "future" profile comparator so that you can do:
+
+    appointment_date=future 1 day "Sorry, we need some lead time."
+
+  That allows you to check that a date value (ala the date widget) is
+  in the future.
+
+* Added "luhn" profile check for "LUHN-10"-encoded numbers.
+
+* Enhance unique profile check to allow specification of a foreign key
+  for uniqueness check.
+
+Foundation
+----------
+
+* Add several different color schemes instead of only the Foundation Red.
+  "blueyellow" is the new default.
+
+* Change logos and such to reflect ICDEVGROUP instead of Red Hat.
+
+* Add product_tree and product_flyout components to work with new
+  menu editor.
+
+* Change checkout display to work easier for DHTML browsers, old
+  browsers should see much the same thing.
+
+* Change order profiles and etc/log_transaction to do a more reliable
+  job of order checking. If your database has transactions (i.e. Postgres),
+  a failure in the log_transaction can cause a failure of the order.
+
+* Added auth_code and tracking_number to transactions table to support
+  charge settlement and shipping_tracking in the UI.
+
+* category_vert_toggle component reworked by Randy Moore.
+
+* new category_vertical_tree component by Rene Hertell.
+
+UserTags
+--------
+
+* Fixed problem in [button] tag to make sure that the current button being 
+  pressed is the only one whose mv_click_map_* variable gets set.
+
+  This works around the problem of a user clicking one button, using the
+  browser's Back button, then clicking on a different button, and both
+  mv_clicks execute instead of just the most recent one.
+
+* [history-scan ...] now escapes form parameters properly.
+
+* Extended stripping of line endings by [import-fields] to 
+  help people who import using files generated on non-Unix
+  operating systems.
+
+* Add [jsq] [/jsq] .. and [jsqn] [/jsqn] tags that build properly
+  JavaScript strings (jsq with variable substitution, jsqn without).
+
+* Add [tabbed-display] tag that shows DHTML tabbed panels.
+
+        [tabbed-display OPTIONS]
+            [tabbed-panel The title of one]
+            The contents of one
+            [/tabbed-panel]
+            [tabbed-panel The titel of two]
+            The contents of two
+            [/tabbed-panel]
+        [/tabbed-display]
+
+  It is pretty much that simple. It is documented, and an example is
+  on the pages/admin/genconfig.html page.
+
+* [table-editor ...] tag updated extensively. Added tabbed displays,
+  full templating of the display, user-includeable forms, almost all
+  features supported with metadata.
+
+* Many minor changes in metadata and preferences. Changed default
+  in some tables to tabbed display.
+
+* [update-order-status] tag added for shipping products. Also does
+  charge settlement if needed.
+
+* [xml-generator] removed.
+
+UI
+----
+
+* Extensive update to look and feel of the admin UI. The HTML design was
+  done by David and Hamish, core members from Zeald, Ltd. in New Zealand.
+  There are no more BGCOLOR references, and only a couple of <font ..>
+  tags. All has been switched to CSS.
+
+* Remove icmenu database. That work now done by lib/UI/pages/include/menus/*.
+
+* Major update to [table-editor ...] which so much of the UI is based
+  around. 
+
+    -- Tabbed displays
+    -- Insert spreadsheet linked via foreign key
+    -- Insert custom form widgets for form processing use,
+           a "recompute transaction" included for an example
+    -- Control over styles and classes for table columns
+        -- Completely templateable
+
+* Add the suggested feature from Dan Browning -- a great idea --
+  a spreadsheet of a linked table within the table editor.
+
+  Adds the options:
+
+    link_table               Table to link in
+
+    link_key                 Key field to link to
+
+    link_fields              Columns to display
+
+    link_sort                How to order the linked rows
+                             (probably should add link_query here)
+
+    link_view                The view for spreasheet meta
+
+    link_label               How to label the thing (default
+                             is something like "Settings in
+                             link_table linked by link_key"
+
+    link_before              Where to plop the thing, input
+                             a column name in the main table to
+                             put it before
+
+    link_extra               Class, style, or other data for
+                             the table cells in the spreadsheet
+
+
+   To make it even better, multiple link tables are allowed,
+   so you could do:
+
+       [table-editor
+            link-table.0=options
+            link-table.1=pricing
+            link-key.0=sku
+            link-key.1=price_group
+        ]
+
+   To test, try this little test-snippet in a default foundation
+   from the latest CVS.
+
+    [table-editor
+        table=products
+        item_id="os28004"
+        link-table=options
+        link-key=sku
+        link-fields="sku price description"
+        link-sort="price desc"
+        link-before="weight"
+    ]
+
+* Complete rework of content editor. Improvements too many to name.
+
+    - "Edit page", "Edit menu", even "edit component" links are inserted when
+      you are logged in as admin.
+
+    - Complete cleanup of page/template/component parsing code, now perhaps
+      someone besides Mike could understand it. 8-)
+
+    - File navigator only now used for pages, not for templates/components,
+      retains context.
+
+    - Hooks are there for doing an entire edit session then pushing new content all
+      at once. Theoreticially, you could create an entire new site, browse it
+      and test it without the public seeing it, and then push one button to
+      publish it all. I say theoretically because I haven't done it yet, but
+      it should be there soon.
+
+    - Preview now holds true for browsing catalog.
+
+    - Now can create and edit pages that have no template wrapper.
+
+    - Add page to clone (push) sets of components to like sets of pages, i.e.
+      edit one to get the components like you want them and then select the
+      pages that that setup should be copied to.
+
+    - Closed all Bugzillas relating to it.
+       -- New pages not creating properly
+       -- Unable to edit in subdirectories
+       -- Templates not written properly
+
+    - TODO:
+
+        -- Allow alternate DSN for staging database tables.
+        -- Document this puppy, finally.
+        -- Change templates so that left-side/right-side components interchange,
+           and so that most class=content components can go vertical.
+        -- Vet the new [menu][/menu] component so that left-hand side
+           menu can be directory/location sensitive.
+        -- Build in the "use the index.html page in the current directory
+           as the template" functionality.
  
-* Fix problem with MV_DEFAULT_SEARCH_FILE. Found by Joshua Scott
-  <josh@bluebonnet.net>.
+* Improve spreadsheet.
+
+    -- Any meta widget can be used.
+    -- No possiblity of data crossover with embedded nulls.
+    -- Remove need for "Change display" with improved meta edit (will
+       add temporary view selector soon).
+    -- Better display (I think).
+    -- Better consistency of display for data and new record, etc.
+    -- Fields can use meta, go to textarea, have text field all selectable
+       from spreadsheet meta control.
+
+* Add cheesy mail list manager, a common thing to ask. Supported by unsubscribe
+  function and a batch download mode for large mailings....probably should
+  create some online help.
+
+* Ability to employ database entries in filters supported by profile 
+  "process_filter" now.
+
+* Major update to order status update program. Now can batch ship by
+  checking boxes, sequence ship, settle transactions previously done
+  via auth_only with realtime payment gateway, and more.
+
+* Many, many, minor bug fixes and improvements.
+
+Swish Search
+------------
+
+* Added module to search indexes with Swish.
+
+* To use, you must add to interchange.cfg:
+
+        Require module Vend::Swish
+        AddDirective Swish hash
+        Variable swish Vend::Swish
+
+* The search is called with st=swish (same as mv_searchtype=swish).
+
+* The fields to return are configurable, and default to;
+
+        rf=code score title url mod_date filesize
+        fn=code score title url mod_date filesize
+
+  These correspond to:
+
+                        code            swishreccount
+                        score           swishrank
+                        url                     swishdocpath
+                        title           swishtitle
+                        filesize        swishdocsize
+                        mod_date        swishlastmodified
+
+mod_interchange
+---------------
+
+* Implemented a proper (automatic) URILevels mechanism and removed
+  the URILevels configuration directive.  This also fixes a bug,
+  reported by Philip Hempel in the interchange-users mail list,
+  where [PT] redirects were not being handled correctly.
+
+Forum
+-----
+
+* Add "forum" feature to foundation. Allows commenting on products and
+  also as a byproduct arbitrary blog-style forums.
+
+  This is a complete forum display:
+
+        [forum top=THREAD_ID /]
+
+  You can get more complex than that. There is an illustration of the
+  templated version in the pages/forum/display.html page.
+
+  Disabled by default for DBM and Oracle. No database def is
+  supplied for Oracle.
+
+  With Postgres and MySQL, the forum is displayed in the flypage
+  automatically by default. The thread doesn't exist until the
+  first comment is made, at which time we create a top-level thread
+  named for the SKU.
+
+  An email notification goes out with new comments if that is
+  enabled.
+
+  There is some scoring logic for display, but no way to assign
+  scores yet (except by editing the database directly).
 
-* Fixed bug with encrypted-password users not being logged in after
-  new account creation. Reported by tamas.kohegyi@unforgettable.com.
+  The reply and submit pages use include files from include/forum.
 
-* Add CGIWRAP workaround. Remove bogus PATH_INFO that is prepended to
-  SCRIPT_NAME.
+  Arbitrary forums need to be enabled by setting the artid equal
+  to the code. If the artid is 0, as is the default on a random
+  submit, no display will be done. (The enabling is done automatically
+  for products by passing the product=1 parameter in the URL and
+  finding the product in the database.)
 
-* Add unusable password hash for group ':backup' in access.asc. It was
-  possible to access the admin interface with this username and no password.
 
-* Disallow login attempts with group names, usernames with invalid
-  characters, and blank usernames or passwords.
+------------------------------------------------------------------------------
 
-* Fix index statement problem for order_returns in PostgreSQL, found by
-  <lmorley@flexihost.com>.
 
+Interchange 4.9.3 released only as nightly builds.
 
-Interchange 4.6.3
 
-* Fixed a bad bug that kept product options from working right. A bugfix
-  in 4.6.2 uncovered a worse bug due to swapped parameters in a subroutine
-  call in Data.pm. Thanks to Marc Infield <marc@geronimo.com> for pointing
-  this out quickly.
+------------------------------------------------------------------------------
 
 
-Interchange 4.6.2
+Interchange 4.9.2 released 2002-08-12.
 
-* [loop list=`$Scratch->{ary}`] now accepts a prebuilt array reference to
-  loop over. Must be in the form returned by $db->query(), i.e. the list
-  array (of arrays), an optional field hash ref giving the field name to
-  index pointers, and an optional array ref giving the field names in
-  order. Thanks to Kaare Rasmussen for the suggestion.
 
-* Fixed bad bug in History, saving mv_credit_card_number in session. Oops.
+Core
+----
+
+* New ability to run Interchange entirely inside Apache and mod_perl.
+  See POD documentation inside scripts/ic_mod_perl.PL for details.
+
+* Add new Jobs and Cron facility:
+
+  - While we don't keep the time, and a scheduler will have to set the
+    execution time, it allows ITL to be run without the hassles of having
+    to deal with HTTP.
+  - Use $Vend::Cfg->{Cron} for setup.
+  - Emails either to command line address or $Vend::Cfg->{Cron}{email}
+    (only if the cron job supplies output). Uses the $Vend::Cfg->{Cron}
+    variables subject, from, reply_to and extra_headers.
+  - Logs to $Vend::Cfg->{Cron}{log}
+    (only if the cron job supplies output).
+  - Can add session dump when $Vend::Cfg->{Cron}{add_session}.
+  - Base directory set by $Vend::Cfg->{Cron}{base_directory}, defaults
+    to etc/cron. If $Vend::Cfg->{Cron}{use_global} is set, 
+    the same directory in $Global::ConfDir is scanned too.
+  - The macros $Vend::Cfg->{initialize} and $Vend::Cfg->{autoload} are
+    executed once resp. before each job.
+ 
+* Add First and Last links to more-list, with ability to customize via
+  [first-anchor] and [last-anchor] containers.
+
+* Bye bye Wizard. Suggest anyone who wants it resurrect it and
+  make it work properly...
+
+* Add new menu editor and menu system. It is based around Vend::Menu
+  and the new tag [menu ...], which builds various types of DHTMl and
+  standard HTML menus based on browser type.
+
+  The menu editor can edit simple menus or tree-based menus.
+  All UI menus use this. A simple menu component (i.e. a link list)
+  and a tree-based list are provided for Foundation.
+
+* New support for database-native sequences for MySQL, PostgreSQL, and Oracle:
+
+  - To do a minimal sequenced table, all you need to do is:
+
+    Database  sequenced sequenced.txt __DBIDSN__
+    Database  sequenced AUTO_SEQUENCE sequenced_seq
+
+  - The parameter passed to AUTO_SEQUENCE (in the above, "sequenced") will
+    be used as the sequence name for Postgres and Oracle (and presumably
+    others that emulate them).
+
+    For MySQL, the same technique that Stefan introduced is used, with an
+    AUTO_INCREMENT field. The value in AUTO_SEQUENCE is just a non-false
+    value. The behavior depends on the definition of
+    $capability->{LAST_SEQUENCE_FUNCTION}.
+
+    If MySQL is the DB in use,
+
+    $key = $s->autonumber();
+
+    returns nothing and the key will be later found with
+
+    $key = $s->last_sequence_value($key);
+
+    and returned in $db->set_slice, etc. ($db->set_row also uses this, but
+    the key value is never returned. You can get it with
+    $db->last_sequence_value if you need it.)
+
+    If PostgreSQL/Oracle is used, the key is returned with
+
+    $key = $s->autonumber();
+
+    and is just parroted back with
+
+    $key = $s->last_sequence_value($key);
+
+    If the table is being created, the sequence will be created as well. If
+    it exists, it will not be dropped. If the "code" or key field is not
+    set with a COLUMN_DEF, the field type to be used will be found in
+    $capability->{SEQUENCE_KEY}.
+
+    Capablility entries used:
+
+    SEQUENCE_CREATE         Query to create a sequence on table creation.
+    SEQUENCE_QUERY          Query to get next value in sequence.
+    SEQUENCE_KEY            Type definition for key field when AUTO_SEQUENCE
+                            table is created.
+    SEQUENCE_VALUE_FUNCTION Query to get current value of sequence.
+    SEQUENCE_LAST_FUNCTION  Query to get key when MySQL behavior is wanted.
+
+  - Can automatically drop existing sequence if:
+
+    Database sometable AUTO_SEQUENCE_DROP 1
+
+* Add BASE_CAPABILITY configuration parameter to allow testing of a new
+  SQL database type with settings based on one of the known types. If
+  behavior is different in particulars, that capability can be modified
+  in the config file.
+
+* In Vend::Config, fix incompatibility in Perl 5.005-style regex that
+  causes rejection of certain Locale settings.
+
+* Remove unnecessary CGI variable mappings at end of Vend::Config.
+
+* Fix call to [item-tag object name].
+
+* Add Filter alias e = encode_entites.
+
+
+Extensions
+----------
+
+* Various Quickbooks updates:
+
+  - Fixed: When an auto-created user orders from the same company as an
+    existing Quickbooks customer, it overwrites the customer.
+
+  - Save the auto-created user id (e.g. U00001) and use it in the Customer
+    Name as a unique identifier, just as logged-in users.
+
+  - New variables for easy customization of export features via Admin UI,
+    documented via item-specific meta referenced in the documentation.
+
+  - Fixed: "INTL" showing up without country (now matches US or USA).
+
+  - Put the company name on a separate line in Ship-to and Bill-to
+    addresses. Now utilizing all 5 lines.
+
+  - Item name updates:
+    - Length filter now customizable via QB_ITEM_LENGTH
+    - Default is 30 (backwards compatible)
+    - Item name taken from 'title' first, if any, then 'description' second.
+
+  - Optionally cause Quickbooks invoice number to be blank, to keep
+    Quickbook's invoice number progression unmodified.
+  
+  - Accompanying documentation.
+
+Utilities/EG
+-------------
+
+* eg/te -- jon's great tabbed file editor.
+
+    Add some new options:
+
+    -f to handle files without field names on first line of file.
+    -n to number rows in comments.
+
+    -s for starting value support (really only vi).
+
+        te -s os28004 <file>
+
+        Jumps to first occurrence of "os28004" in <file>. Option -i ignores case
+        in the search.
+
+    Allow setting of persistent options in environment variable TE_OPTIONS.
+
+    Handle -i and -s with mixed-case search term (lowercase it first).
+
+    Don't escape " in search term, as it doesn't seem special.
+
+Payment
+-------
+
+* Support for TrustCommerce added. Written, tested, and donated by
+  Dan Helfman of TrustCommerce <dan@trustcommerce.com>. Thanks, Dan!
+
+* Support for the Mainstreet Credit Verification Engine (MCVE) added.
+  Written, tested, and donated by Tom Friedel <tom@readyink.com>.
+  Thanks, Tom!
  
-* Fixed bug in secure/non-secure host comparison, thanks to Murray Gibbins,
-  Stefan Hornburg, and Hans-Joachim Leidinger.
+* Support for ECHO added. Written, tested, and donated by
+  Michael Lehmkuhl <michael@electricpulp.com>.  Ported from globalsub to 
+  Vend::Payment by Dan Browning <db@kavod.com>.  Thanks Michael!
+
+UI
+--
+
+* [import_fields]: Performance enhancement: use set_slice() to update all 
+  fields in a record at once when importing files.
   
-* Add MV_USERPROFILE to the list of recognized cookies, allowing a
-  cookie-based admin login. Providing the password is saved in a cookie
-  (perhaps with no expiration time?) then this will allow multiple-order
-  entry by running the login process again.
-   
-* Fixed up the DisplayErrors auto-response to be localized. Not many people
-  use this, but trying to localize all error messages.
 
-* Fixed bug in ui_date_widget, generated month name for "Feb 30" which turned
-  into March.
+------------------------------------------------------------------------------
+
+
+Interchange 4.9.1 released 2002-07-22
+
+
+Core
+----
+
+* The great tag breakout!
+
+    - Almost all tags are now UserTag definitions. The exceptions are:
+
+        and bounce goto if label or unless
+
+    - New TagDir directive (default is VENDROOT/code) sets the
+      directory (or directories) which are searched for code definitions
+      set by UserTag and CodeDef.
 
-* Patch supplied by Hans-Joachim Leidinger <jojo@buchonline.net> prevents
-  blank credit card info from being encrypted.
+    - New TagGroup directive establishes groups of ITL tags which can
+      be included.
 
-* Fixed bug #106, hang at install time if specified Interchange user ID
-  doesn't exist.
+        TagGroup :crufty "banner default ecml html_table onfly sql"
 
-* Fixed problem in Search.pm where coordinated search of op=rm would not
-  match on words only.
+      The default groups include :core, which contains all of the
+      ITL tags defined in 4.8/early 4.9. The groups are defined
+      in $Vend::Cfg::StdTags and can be undefined if desired
+      with "TagGroup :group".
 
-* Fixed recent bug that prevented cached DBI connections.
+    - New TagInclude directive allows inclusion of tags (or groups
+      of tags). If a tag is defined as a core tag (with a .coretag
+      or .tag or .ct extension) and is not included, it will not
+      be compiled and placed in the tag map. This is for all catalogs,
+      so if *any* catalog uses a tag it must be included.
 
-* Fixed a couple of hard-coded mv_metadata references in admin pages
-  preventing renaming of __UI_META_TABLE__.
+      Examples:
 
-* Fix problem with ProductFiles resolution in loops. The Vend::OnlyProducts
-  setting was confused after the on-the-fly update.
+        # Include the base tags
+        TagInclude :core
 
-* Convert '[' characters to &#91; in [value-extended] to prevent reparsing
-  of Interchange tags from user data.
+        # Not the commerce tags
+        TagInclude !:commerce
 
-* Fixed problem with fly-list not accepting base parameter as per docs.
-  Found by Victor Nolton.
+        # But make sure item-list is included even though
+        # it is in :commerce
+        TagInclude item-list
 
-* Added Stefan Hornburg's patch for table image background paths.
-  Set pragma substitute_table_image to enable this.
+        ## Double negatives are honored
+        TagGroup    :foo "bar !baz buz"
+        ## With the group above, the below is equivalent
+        ## to TagInclude !bar baz !buz
+        TagInclude !:foo
 
-* Improved makecat error message when problems occur reading config file.
+    - New CodeDef directive allows the setting of filters, order checks,
+      FormAction, ActionMap, ItemAction, and LocaleChange.
 
-* Made NoAbsolute default to Yes in interchange.cfg, which gives better
-  default security for newly-built catalogs.
+            ## filters
+            CodeDef  mixedcase Filter
+            CodeDef  mixedcase Routine <<EOR
+            sub {
+                my $val = shift;
+                ## [filter mixedcase]mixed case[/filter]
+                ## outputs "MiXeD CaSe"
+                $val =~ s/(.)(.)/\u$1\l$2/g;
+                return $val;
+            }
+            EOR
 
-* Various minor HTML corrections. Thanks to Paul <porl@namee.com.au> and
-  Mediabang.
+            ## order checks
+            CodeDef  mixedcase OrderCheck
+            CodeDef  foo  Routine <<EOR
+            sub {
+                my ($ref, $var, $val) = @_;
+                return (1,$var) if $val eq 'bar';
+                return (0,$var, "foo must be bar");
+            }
+            EOR
 
-* Fixed in-stock notification problem on flypage.html and stock-alert.html.
+       All work in catalog.cfg; LocaleChange and ItemAction are not
+       global. FormAction, ActionMap, and ItemAction directives
+       are equivalent to their CodeDef equivalents.
 
-* RPM only: Fixed logrotate.d file to prevent cascading log rotation like
-  error.log.1.gz.1.gz etc. Thanks to Murray Gibbins for diagnosis & fix.
+* New Vend::Form module implements display tag and widget creation.
+  Passes all known tests, and runs accessories/widgets (apparently)
+  flawlessly in foundation, barry, simple, and the UI.
 
+* Add new HIDE_FIELD capability to DbSearch. It provides automatic
+  hiding of records accessed via search (and NOT query).
 
-Interchange 4.6.1
+ -When the following configuration is added:
 
-* Added MS Excel import/export capability.
+    Database products HIDE_FIELD inactive
 
-* Added new SessionType "NFS", which forces fcntl_lock/fcntl_unlock in
-  SessionFile.pm (bug #76).
+ -It adds automatically the qualification to every search:
 
-* Report missing DBDs at startup time by working around DBI bug that causes
-  $@ to be eaten (bug #75).
+    WHERE inactive != 1
 
-* Miscellaneous bugfixes, thanks to Jean-Philippe Bouchard:
-  - Fixed Data.pm bug that caused flypage problems (bug #60).
-  - Fixed spreadsheet edit auto export bug (bug #59).
+ -To use, you should have a field of char(1) or int type.
 
-* Link program fixes, thanks to minivend@delionsweb.net:
-  - Fixed tlink.pl LINK_PORT problem (bug #61).
-  - Fixed compile_link 'nosuid' option failure (bug #66).
+    Database products COLUMN_DEF "inactive=int default 0"
 
-* Construct Something changes:
-  - Fixed stock alert price problem (bug #57).
-  - Fixed 'title' vs. 'description' field issues. Thanks to Steve Gertz.
+ -This has the side-effect of hiding fields with NULL in the
+  field, so be careful. You should probably set "default 0"
+  as shown above.
 
-* Fixed [selected] and [checked] tags to be more uniform and to support
-  case-sensitive and $CGI comparisons. Documented in Tagref.pm. Also,
-  "multiple" and "default" args can no longer be positional -- no big loss.
+ -Works for DBM types too.
 
-* Fixed bug that kept [item-subtotal noformat=1] from being recognized.
+ -Does NOT work for TextSearch.
 
-* [item-exec routine] now picks up $Values, etc. before a [calc] is run.
+ -If you want to show all records, you can pass mv_no_hide=1
+  in the search parameters. Obviously, this makes this not a
+  security feature.
 
-* Order.pm: routes now use a "from" parameter which sets the email From: 
-  header.
+* Clear the following intermittent error:
 
-* Fixes to Util.pm:
-  - Prevent sprintf() from screwing up numbers in certain locales.
-  - [include] now can interpret [L] if locale=1 parameter is added.
+    CGI mapping error: multipart/form-data sent incorrectly
 
-* Server.pm -- we can now accept ISINDEX queries (for what it is worth).
+  Some browsers, like Opera, use non-word characters like '+' in
+  form-data MIME boundaries, causing the regex matches to fail.
 
-* Scan.pm -- fix non-interpolated tags in search profiles.
+* New function Vend::Util::logOnce which ignores repeated identical
+  log messages (works only in the scope of the current Interchange
+  page)
 
-* Database tables can now reside in different directories with the 
-  DIR option to the Database config parameter.
+* Remove last remnants of mv_raw_searchspec.
 
-* Fixed typo ('error' vs. 'errors') in Order.pm preventing no-items
-  error from being seen at checkout (bug #82). Thanks to Bas Bezemer.
+* Remove HTML-embedded tag syntax
 
-* Removed some duplicated image files, reducing package size by ~ 200 KB.
+* Remove Vend::ECML, move to extensions/ directory.
 
-* Fixed scoping problem with override from user image upload.
+* Allow customization of links in more-list, like this:
+  [link-template]<a href="$URL$" target="_top">$ANCHOR$</a>[/link-template]
 
-* Allow internationalization of error messages in UserDB.
+* Add utility functions Vend::Data::product_row and product_row_hash,
+  which do the same thing as product_field, but return the whole row
+  instead of just one field.
 
-* interchange.PL: Fixed bad call to Vend::Imagemap::action_map, must be
-  just the action_map since autouse is in force. Thanks to Jeff Carnahan.
 
-* Fixed bugs in or-ed searches in DbSearch, fixed mv_search_relate bugs.
+UI
+--
 
-* Fixed problem with nu parameter getting out of sync in mv_sql_query.
+* Major changes to the content editing scheme.
 
-* Added 3 usertags: benchmark, sleep, and table_organize (in eg/).
+    - Requires a CSS/Javascript 1.3 compliant browser. Tested on
+      Mozilla 0.9.8, MSIE 5.51, Opera 6.0tp2. All work pretty well;
+      Mozilla is a bit slow, Opera doesn't have CSS widths down.
 
-* Filled in some missing timestamp fields in construct demo store data,
-  which was causing PostgreSQL 7 data imports to fail.
+    - Page editor has a quasi-visual layout that should be much more
+      intuitive. Support for a "PAGE_PICTURE" file in the templates
+      allows visual links to the editor page.
 
+    - Components, templates, and pages are now all editable.
+      Template and component editors need to be brought up to speed
+      with the page editor, but work fairly well.
 
-Interchange 4.6.0
+    - Added new lib/UI/ContentEditor.pm module which implements
+      this stuff in conjunction with lib/UI/pages/include/*_editor.
+      A bit of a JavaScript dependency nightmare on the generated
+      attribute editors, but I may get this more canned as time goes on.
 
-* Minor final changes
+    - Let's get this on record -- this content editiing WILL NOT
+      UNDER ANY CIRCUMSTANCES EVER WORK ON NETSCAPE 4. Do not ask,
+      though I know the people who monitor this stuff won't.
 
+* Added Mike's cool new "auto_wizard" which builds a wizard from a
+  file like in the example. It will be the method to provide scripted
+  content addition.
 
-Interchange 4.5.8 beta release
+* More table-editor updates -- added notable option, and
+  all_opts option which allows building the options in
+  Perl and then doing:
 
-* Documentation overhaul -- PDFs now available
-* Various bugfixes
-* Oracle support improved
-* 'Construct' catalog improvements
-* Authorize.net support
+        [table-editor all-opts=`\%opts`]
 
+* Look for major updates on the table editor to make it
+  completely templateable.
 
-Interchange 4.5.7 beta release
+* Fix problem with $Tag->display() called with null table, affecting
+  "wizard" mode.
 
+* Add a "admin/test_code.html" page for testing short snippets
+  of ITL without having to create a test page.
 
-Interchange 4.5.6 changes -- complete overhaul of UI
+* Make the table populator JavaScript honor the db tables the
+  particular admin user is supposed to see.
 
-* Everything renamed to "interchange". interchange.cfg, interchange.pid,
-  etc. If you keep minivend.cfg as the configuration file, the PID file
-  will be minivend.pid. There should be a good level of backward
-  compatibility.
+* [import-fields replace=1] -- added option to replace items in the database
 
-* "construct" is now the default demo -- a "foundation" demo will be
-  added later.
+* Add su facility for catalog superuser to switch users to another
+  user id, using new UI_Tag su as follows:
 
-	-- Improved graphics and layout over older demos.
-	-- Split ship addresses for items
-	-- Shipping notices integrated
-	-- Recurring order facility (doesn't yet work).
-	-- PO with credit limit
-	-- Merchandising cross-sells by category or item.
-	-- "Others who bought this"
+    [su username=miltonbear]
 
-  The HTML rendering is kind of slow on Netscape, any help with that
-  would be appreciated.
+    1. Stringifies current session after checking that su user is valid
+    2. Writes a random string to "$Global::ConfDir/tmp/$Session->{id}"
+    3. Issues a cookie hashing the above two
+    4. Inits a new session, putting in the login info
+    5. Writes $Session->{su} with session string
 
-* The user interface (UI) was reorganized to make it easier to understand
-  and use.
+    [su exit=1]
 
-  -- All functions should now be available via menu, quicklinks should
-     not be necessary.
-  -- Most database table lists are HTML lists with links instead of
-     the button approach.
-  -- Administration console with information helpful for debug.
+    1. Reads random string from "$Global::ConfDir/tmp/$Session->{id}"
+    2. Hashes that with session and verifies with cookie
+    3. Safe evals session string
+    4. Retrieves session username/admin info
 
-UI:
+    [su create_user=1 username=bobby password=howdy verify=howdy]
 
-* Orders 
-  -- list-based
-  -- shipping status notices
-  -- automatic check of archive box when status=shipped
-  -- list-based delete and archive operations
-  -- lists are sortable on multiple fields
-  -- status display for individual line items
-  -- change size of list with Knar UI_SZ_LIST_ORDER
+    Allows combined creation of new user and switching to that user. 
+    Any options you would pass to userdb tag can be given to su usertag, 
+    to tweak account creation. If user already exists, it's silently switched to.
 
-* Customers
-  -- list-based
-  -- list-based delete and deactivate operations
-  -- lists are sortable on multiple fields
-  -- status display for individual line items
-  -- change size of list with Knar UI_SZ_LIST_CUSTOMER
+  MMsu profile is called on admin/customer.html to run the switch.
 
-* Item editor
-  -- Select list of items to delete or edit in sequence
-  -- Now have different "views" for merchandising, pricing, inventory, etc.
-  -- checkbox-based deletes
-  -- item fields to display set with UI_ITEM_FIELDS
-  -- separator fields set with UI_ITEM_BREAK
-  -- cross_category field added to merchandising table
+  When you "log out", you are reverting to the previous user, and you
+  can go no further back. So if you go from superuser->adminuser, then
+  adminuser->regular user, there is no way back to superuser without
+  logging in again.
 
-* Content
-  -- Templates easier to create
-  -- Editor allows change of template
+* Continuing work on meta_display and Vend::Form.
 
-* Layout
-  -- button builder does on-the-fly items
-  -- fixed bugs in search builder
+    - Relocated date and option widgets
+    - Prepared for breaking out image widgets to code/Widget
+    - Fixed various bugs in widgets
+    - Code simplification in Primitive.pm
+    - Fix widget.coretag to not call UI::Primitive routine
+    - Redo option_format filtering
 
-* Merchandising
-  -- new menu, includes affiliate stuff
+* Display server hostname on the information page (genconfig).
 
-* Reporting
-  -- Fixed cast problem with PostGres reports
-  -- More consistent look/feel for reports
+* Unused usertags component, set-alias and set-click removed.
 
-* Administration
-  -- New information screen that should help with diagnosing trouble
-  -- Table select/edit now consistent with other editors
-  -- Selector rows can be sorted via column, forward and reverse
-  -- Table display properties can be easily edited
 
-Core:
+Payment
+-------
 
-* Database update forms (mv_todo=set) now can set fields in multiple
-  tables when there is a common key.
+* Support for Wells Fargo added
 
-* Changed SpecialPage defaults for "search", "order", and "checkout"
-  to reflect longstanding defaults in demo catalogs.
 
-* Fixed bug in fixed-field (PriceField) pricing, introduced sometime
-  in Minivend 4.
+Accounting
+----------
 
-* Added GUESS_NUMERIC parameter to databases, which operates by checking
-  field types in SQL and by looking at the import data on DBM. You can
-  see this in operation in the UPS tables "Ground", etc.
+* Vend::Accounting module added, along with example module for SQL_Ledger.
+  This is the basis for a start of a defined accounting system interface.
 
-* Removed auto-index of key field if POSTCREATE statement exists.
+  Some intended functions:
+    NOTE: AS = Accounting Software, i.e. SQL-Ledger, IC = Interchange
 
-* Added some more better auto-numbering support. Still not ready
-  for the UI.
+    1. Assign customer number
+    2. Change customer information based on input, limit to fields customer
+       should have control over
+    3. Add sales transaction (IC)
+    4. Feed back sales transaction from AS side for account status
+    5. Enter payments (IC --> AS), with credit-cards used to pay invoices
+    6. Reconcile AS account status with IC, i.e. ship status
+    7. Cancel order (IC)
+    8. Ship portion or all of order (IC)
+    9. Mark order complete
 
-* Found bug in Vend::Table::DBI->inc_field that caused a quoted value
-  when really was a number.
+    Input on other functions needed is appreciated.
 
-* CSV imports now are fully as functional as others, can do indexing, numeric
-  guess, etc.
+PROPOSED:
 
-* Added "value" widget type for [accessories ...].
+* Set of modules selectable by route handle:
 
-* Added [tmp var]scratch setting[/tmp] and [scratchd var] tags to
-  purge Scratch when setting/accessing variables. This can improve
-  session write speed if setting a large value which will only be
-  used in the current page.
+    Vend::Account::SQL_Ledger (exists)
+    Vend::Account::QuickBooks (proposed)
+    Vend::Account::Compiere (proposed)
+    Vend::Account::[fill-in-the-blank]
 
-* Added "tabbed" filter, and some other Filters. Now you can add
-  your own filters persistently with:
+* Use a usertag [account] (a la [charge]) to interface functions.
 
-	Sub <<EOS
-	sub somesub { 
-		$Filter{foo_to_bar} = sub {
-			my $value = shift;
-			$value =~ s/foo/bar/g;
-			return $value;
-		};
-	}
-	EOS
-	
-	or just in the current page
+* Use a profile primitive, "&account=label function" ala "&charge="
+  to do some accounting functions in profiles, notably getting an
+  order number or customer number
 
-	[perl]
-		$Filter{foo_to_bar_tmp} = sub {
-			my $value = shift;
-			$value =~ s/foo/bar/g;
-			return $value;
-		};
-		return;
-    [/perl]
+* Allow either COMMIT or no-COMMIT operation, with tradeoffs
 
-  Thanks to Stefan Hornburg for suggestion.
+* Define accounting system parameters via Route, and build
+  in accounting functions into Route so that they can be
+  a predicate for order success.
+
+* Define two transitional state tables for handshaking:
+
+    orderstatus -- status of orders, i.e.
+            pending,transmitted,received,shipped,complete
+
+    accountstatus -- record of payments and orders for account statement
+
+
+Foundation demo
+---------------
+
+* use [if variable MV_DEMO_MODE] instead of the more cumbersome
+  [if type=explicit compare="__MV_DEMO_MODE__"].
+
+* add global INTERCHANGE_URL and INTERCHANGE_EMAIL variables to be used
+  for the Interchange developer website & email contact points, instead
+  of hard-coded stuff
+
+* standardize on the short form "Interchange" for the application name.
+
+* update a few URLs, etc.
+
+* Remove history-scan tag from catalog.cfg; it is now in code/UserTag.
+
+* Remove no_html_parse pragma, for which code has already been deleted.
+
+* Moved payment routes to the top of the Route stack. Technically they
+  should not be below the default route, and though it works in the
+  standard foundation setup, it caused lots of failures when people
+  tried to customize their order routing.
+
+* (Oracle) Add missing Database xxx UPPERCASE 1 settings. Thanks to
+  Jonathan Lee <jonalee740304@yahoo.com> for reporting.
+
+* Get rid of weird tax rate popup notice when updating account
+  info, which is especially strange when you've never had anything
+  in your cart ...
+
+* Change catalog.cfg to highlight etc/after.cfg.
+
+
+UserTags
+--------
+
+* [fedex-query] -- Stop dying if there's a problem with FedEx express
+  lookups, which kept even ground rate lookups from being done during
+  the first request when the Business::Fedex object is first created.
+
+  Instead, just log the error but continue on with possible ground lookup.
+
+  (This situation resulted in the oddity of the shipping rate displaying
+  as $0.00 on the checkout page, but still getting added into the total cost
+  and displaying in the shipping rate pulldown select box just fine.)
+  
+* interchange.cfg: Remove now-redundant include of usertag/*.tag.
 
-* Fixed SpecialPage handling of salestax.asc, thanks to Jeff Carnahan.
+* [db-columns] -- Add ability to get back an array instead of a joined string
+  to $Tag->list_databases,$Tag->list_keys,$Tag->db_columns,
 
-* Fixed _postcode() routine in Order.pm, thanks to Brett Harrison.
+* [email] -- Add enhancement made by Jurgen Botz to use send_mail program
+  so that Net::SMTP can send the email tag. Thanks Jurgen!
 
-* Fixed longstanding problem with demo catalog whereby the UserDB
-  defined the username field as "user" but it was actually named
-  "username" in the database. Changed UserDB default to "username", because
-  "user" is a reserved word in some SQL databases (i.e. Postgres).
+* [history_scan] -- Count option added, which guarantees that the
+  returned link is at least count # of clicks back in the page history.
 
-* UserDB: Removed mv_credit_card_info from B_FIELDS so that it would not
-  be saved in UserDB.
+* [image] -- descriptionsfields and exists_only options added.
 
-* Added [counter ...] tag, with some additional capabilities over
-  the old [fcounter ...] tag. Kept fcounter around in UserTag for
-  compatibility with older catalogs.
 
-* Added image copying for shared image directories (the admin).
+Build
+-----
 
+* Removed stale POD documentation from main interchange repository; for
+  some time now, docs source has been in SDF format in docs repository
+  and available in separate docs package.
 
-Interchange 4.5.5 beta release
+* Keep test from giving warning about not being able to stat
+  "code" directory.
 
+* Big changes to RPM specfile:
 
-Interchange 4.5.3 beta release
+  - Allow non-root RPM builds.
+  - Don't add interch user on build machine.
+  - Don't automatically start Interchange after installing RPM.
+  - Remove unneeded .empty files used in CVS to avoid pruning
+    important but empty directories.
+  - Make admin UI images owned by root.
+  - Don't allow Interchange RPMs to own /usr/share/man/man[18] system
+    directories.
+  - Start using RPM dependencies for Perl CPAN modules. Users who
+    install directly from CPAN will have to use --nodeps.
+  - Start daemon in UNIX mode only by default.
+  - Build foundation-demo RPM with MV_DEMO_MODE set.
+  - On uninstall, remove autogenerated /usr/lib/interchange/etc/varnames
+  - Start using Red Hat standard /sbin/service instead of directly
+    running /etc/rc.d/init.d/interchange.
+  - Add standard 'reload' function as alias for restart.
+  - Quell /sbin/service stop errors.
+  - Let user see if we turn off old IC server before install/upgrade.
+  - Make packages architecture-dependent, to save lots of hassles.
+  - Stop checking for /home/httpd, but use a define for webdir
+    that can easily be changed if needed.
 
 
-Interchange 4.5.0 changes -- the start of the Tallyman merge.
+------------------------------------------------------------------------------
 
-* Many, many, changes and improvments to the user interface.
-  Minimate is broken out again and made separate; the UI should
-  have all of its functionality. See the UI online help for changes.
-* LDAP support. You can now keep data in LDAP servers, with 
-  normal Minivend Database connectivity. Searchable, too!
-  Put in catalog.cfg:
 
-	Database  variable variable.txt LDAP:some.servername.com
-	Database  variable BIND_DN      cn=fragermk, o=catalogs, c=minivend
-	Database  variable BASE_DN      o=catalogs, c=minivend
-	Database  variable BIND_PW      secret
+Interchange 4.9.0 "released" only via CVS
 
-  Programmed by Mike Frager with a bit of help from Mike Heins.
 
-* VariableDatabase now takes effect at the time of the call in catalog.cfg.
-  This means you can edit your Variable settings in a database, reconfigure,
-  and then use the values farther down in the configuration file.
+------------------------------------------------------------------------------
 
-* Order.pm: fixed multiple problems in precedence for order profiles.
-  Thanks to Ton Verhagen. Also added "isbn" profile check written
-  by Ton Verhagen.
-* Interpolate.pm: Fixed bug in error message generation -- thanks to Dan
-  Busarow.
-* Config.pm: Fixed default declaration of "HOT" for memory databases,
-  now should work properly as default database.
-* Other changes much too numerous to mention. This will be the last
-  version of this changes document; there are too many.
+(end)



1.2.4.2   +27 -23    interchange/configure


rev 1.2.4.2, prev_rev 1.2.4.1
Index: configure
===================================================================
RCS file: /var/cvs/interchange/configure,v
retrieving revision 1.2.4.1
retrieving revision 1.2.4.2
diff -u -r1.2.4.1 -r1.2.4.2
--- configure	26 Oct 2000 23:22:22 -0000	1.2.4.1
+++ configure	25 Jan 2003 22:20:30 -0000	1.2.4.2
@@ -1,19 +1,20 @@
 #!/bin/sh
 
+# $Id: configure,v 1.2.4.2 2003/01/25 22:20:30 racke Exp $
+
+ICVERSION='4.9.7'
+
 cat <<EOF
 
- Akopia Interchange Version 4.6.x Configuration
+ Interchange Version $ICVERSION Configuration
 
- Copyright 1996-2000 Akopia, Inc, <support@akopia.com>
+ Copyright 1996-2003 Red Hat, Inc. and Interchange Development Group
 
- Interchange was originally based on Vend 0.2
- Copyright 1995 Andrew M. Wilcox <awilcox@maine.com>
- 
- Portions from Vend 0.3
- Copyright 1995, 1996 Andrew M. Wilcox <awilcox@maine.com>
+ Interchange was originally based on Vend 0.2 and 0.3
+ Copyright 1995, 1996 Andrew M. Wilcox <amw@wilcoxsolutions.com>
 
- Distributed under the GNU General Public License, see
- the file Copying for license information.
+ Distributed under the GNU General Public License.
+ See the file LICENSE for license information.
 
 EOF
 
@@ -53,7 +54,7 @@
 	while true
 	do
 		if test -n "$PERL"
-		then VER=`$PERL -e '((print $]), exit 1) if $] !~ /^5\.\d+/; print $]'`
+		then VER=`$PERL -e '((print $]), exit 1) unless $] >= 5.006 or $^V; printf "%vd", $^V'`
 		else false
 		fi
 		if [ $? -eq 0 ]
@@ -66,19 +67,23 @@
 				TESTPERL=perl5
 				break
 			else
-				echo $VER
-				VER=""
-				echo "Perl version not high enough or Perl not found."
+				if [ -n "$VER" ]
+				then
+					echo "Found Perl $VER as $PERL"
+					echo "Interchange $ICVERSION requires Perl version 5.6.0 or newer!"
+					VER=""
+				else
+					echo "Perl not found! Perl 5.6.0 or newer is required to run Interchange $ICVERSION."
+				fi
 			fi
 		fi
 	
 		echo
-		echo "I need to know where the Perl 5 interpreter resides."
-		echo "It was not 'perl' or 'perl5', or it was not in your"
-		echo "path.  Please enter a fully-qualified path name,"
-		echo "or just press ENTER to exit.. (what did I say?)"
+		echo "I need to know where the Perl interpreter resides (version 5.6.0 or higher)."
+		echo "It was not 'perl' or 'perl5', or it was not in your path. Please enter a full"
+		echo "path name, or just press <enter> to quit."
 		echo
-		echo $F "Where is your Perl 5, please? $E"
+		echo $F "Where is your Perl, please? $E"
 		read PERL
 		if test -z "$PERL"
 		then exit 1
@@ -94,12 +99,11 @@
 
 if test ! -f .cpan.tried
 then
-echo
-echo "If you get a CPAN error, rerun the configuration and it"
-echo "should go away."
-echo
+	echo
+	echo "If you get a CPAN error, rerun the configuration and it should go away."
+	echo
 fi
 
-$PERL Makefile.PL
+$PERL Makefile.PL $*
 make
 make test && make install



1.2.4.2   +1 -1      interchange/hints.pl


rev 1.2.4.2, prev_rev 1.2.4.1
Index: hints.pl
===================================================================
RCS file: /var/cvs/interchange/hints.pl,v
retrieving revision 1.2.4.1
retrieving revision 1.2.4.2
diff -u -r1.2.4.1 -r1.2.4.2
--- hints.pl	3 Jan 2001 23:13:01 -0000	1.2.4.1
+++ hints.pl	25 Jan 2003 22:20:30 -0000	1.2.4.2
@@ -8,7 +8,7 @@
 	my $condition;
 	my $routine;
 
-	$condition = sub { $^O =~ /bsd/i };
+	$condition = sub { $^O =~ /nolongernecessary/i };
 	$routine = sub {
 		my $fn = 'interchange.cfg.dist';
 		rename $fn, "$fn.bak";



1.4.4.2   +9 -2      interchange/test.pl


rev 1.4.4.2, prev_rev 1.4.4.1
Index: test.pl
===================================================================
RCS file: /var/cvs/interchange/test.pl,v
retrieving revision 1.4.4.1
retrieving revision 1.4.4.2
diff -u -r1.4.4.1 -r1.4.4.2
--- test.pl	18 Feb 2001 19:54:23 -0000	1.4.4.1
+++ test.pl	25 Jan 2003 22:20:30 -0000	1.4.4.2
@@ -5,6 +5,11 @@
 $cur_dir = cwd();
 $failed = 0;
 
+if($^O =~ /cygwin|win32/) {
+	print "no tests supported on Windows platform.\n";
+	exit;
+}
+
 die "Must be in build directory\n" unless -d 'blib';
 die "No tests defined for Windows\n" if $^O =~ /win32/i;
 
@@ -17,13 +22,15 @@
 print CONFIG <<EOF;
 Catalog  test $ENV{MINIVEND_ROOT} /test
 TcpMap $ENV{MINIVEND_PORT} -
+TagDir 0
+TagDir etc
 EOF
 
 open(CONFIG, ">$ENV{MINIVEND_ROOT}/catalog.cfg")
 	or die "open: $!\n";
 
-print CONFIG <<EOF;
-MailOrderTo info\@akopia.com
+print CONFIG <<'EOF';
+MailOrderTo  info@icdevgroup.org
 VendURL      http:/test
 SecureURL    http:/test
 Database     products products.asc DEFAULT



No                   revision



No                   revision



1.3.2.1   +0 -0      interchange/README.rpm-dist


rev 1.3.2.1, prev_rev 1.3
Index: README.rpm-dist
===================================================================
RCS file: /var/cvs/interchange/README.rpm-dist,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



2.5.2.1   +0 -0      interchange/UPGRADE


rev 2.5.2.1, prev_rev 2.5
Index: UPGRADE
===================================================================
RCS file: /var/cvs/interchange/UPGRADE,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



2.1.2.1   +1 -1      interchange/relocate.pl


rev 2.1.2.1, prev_rev 2.1
Index: relocate.pl
===================================================================
RCS file: /var/cvs/interchange/relocate.pl,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1
--- relocate.pl	27 Jun 2002 18:56:43 -0000	2.1
+++ relocate.pl	25 Jan 2003 22:20:30 -0000	2.1.2.1
@@ -1,7 +1,7 @@
 #!/usr/bin/perl -w
 
 # relocate.pl
-# $Id: relocate.pl,v 2.1 2002/06/27 18:56:43 jon Exp $
+# $Id: relocate.pl,v 2.1.2.1 2003/01/25 22:20:30 racke Exp $
 #
 # Rewrite pathnames or other values that need to be hardcoded in
 # files. Take a commented line, remove the leading hash character,



No                   revision



No                   revision



1.1.2.9   +442 -348  interchange/SPECS/interchange.spec


rev 1.1.2.9, prev_rev 1.1.2.8
Index: interchange.spec
===================================================================
RCS file: /var/cvs/interchange/SPECS/interchange.spec,v
retrieving revision 1.1.2.8
retrieving revision 1.1.2.9
diff -u -r1.1.2.8 -r1.1.2.9
--- interchange.spec	15 Apr 2001 13:11:04 -0000	1.1.2.8
+++ interchange.spec	25 Jan 2003 22:20:31 -0000	1.1.2.9
@@ -1,49 +1,65 @@
-%define interchange_version		4.6.5
-%define interchange_rpm_release	1
-%define interchange_package		interchange
-%define interchange_user		interch
-%define build_cats				construct
-
-# Relevant differences between Red Hat 6 and Red Hat 7 file layout:
-# /home/httpd -> /var/www
-# /usr/man    -> /usr/share/man
-# /usr/doc    -> /usr/share/doc
-
-%define webdir %( if [ -d /var/www ]; then echo -n '/var/www' ; else echo -n '/home/httpd' ; fi )
-
-# This is obviously a terrible oversimplification of whether a system
-# is Red Hat 7 or not, but it's worked so far.
-%define interchange_rpm_subrelease %( if [ "%webdir" = "/var/www" ]; then echo -n rh7 ; else echo -n rh6 ; fi )
-
-Name: %interchange_package
-Version: %interchange_version
-Release: %{interchange_rpm_release}.%interchange_rpm_subrelease
-Summary: Interchange is a powerful database access and HTML templating daemon focused on ecommerce.
-Vendor: Akopia, Inc.
-Copyright: GNU General Public License
-URL: http://developer.akopia.com/
-Packager: Akopia <info@akopia.com>
-Source: http://ftp.minivend.com/interchange/interchange-%{interchange_version}.tar.gz
-Group: Applications/Internet
-Distribution: Red Hat Linux Applications CD
-Provides: %interchange_package
-Obsoletes: %interchange_package
+%define ic_user				interch
+%define ic_group			interch
 
-BuildRoot: /var/tmp/interchange
+%define filelist %{_tmppath}/%{name}-%{version}.filelist
+%define webdir /var/www
+
+
+Summary: Interchange web application platform
+Name: interchange
+Version: 4.9.7
+Release: 1
+Vendor: Interchange Development Group
+Group: System Environment/Daemons
+BuildRoot: %{_tmppath}/%{name}-%{version}-buildroot
+URL: http://www.icdevgroup.org/
+Packager: Jon Jensen <jon@redhat.com>
+Source0: http://www.icdevgroup.org/pub/interchange/interchange-%{version}.tar.gz
+Source1: interchange-wrapper
+Source2: interchange-init
+Source3: interchange-logrotate
+License: GPL
+Prereq: /sbin/chkconfig, /sbin/service, /usr/sbin/useradd, /usr/sbin/groupadd
+Requires: perl >= 5.005
+Requires: perl-Business-UPS
+Requires: perl-Digest-MD5
+Requires: perl-MIME-Base64
+Requires: perl-Safe-Hole
+Requires: perl-SQL-Statement
+Requires: perl-Storable
+Requires: perl-URI
+Requires: perl-libnet
+Requires: perl-libwww-perl
+BuildPrereq: perl >= 5.005
 
 %description
-Interchange is the most powerful free ecommerce system available today.
-Its features and power rival costly commercial systems.
+Interchange is a complete web application platform focused on
+ecommerce, dynamic data presentation, and content management.
 
-%define warning_file %{_docdir}/%{interchange_package}-%{version}/WARNING_YOU_ARE_MISSING_SOMETHING
 
+%package foundation
+Summary: A template store for Interchange
+Group: System Environment/Daemons
+Requires: interchange = %{version}-%{release}
+
+%description foundation
+The Foundation Store is a full-featured ecommerce catalog you can
+adapt to build your own store.
 
-%prep
 
+%package foundation-demo
+Summary: A prebuilt demonstration store for Interchange
+Group: System Environment/Daemons
+Prereq: interchange = %{version}-%{release}
 
-%setup
+%description foundation-demo
+This demo is a prebuilt installation of the Foundation Store that
+makes it easy to test drive Interchange's ecommerce features.
 
 
+%prep
+%setup -q
+
 %build
 
 if test -z "$RPM_BUILD_ROOT" -o "$RPM_BUILD_ROOT" = "/"
@@ -51,233 +67,139 @@
 	echo "RPM_BUILD_ROOT has stupid value"
 	exit 1
 fi
-rm -rf $RPM_BUILD_ROOT
-mkdir -p $RPM_BUILD_ROOT
+%__rm -rf $RPM_BUILD_ROOT
+%__mkdir_p $RPM_BUILD_ROOT
 
-if test -n "$RPM_RUN_BASE"
-then
-	RUNBASE=$RPM_RUN_BASE
-else
-	RUNBASE=/var/run
-fi
-
-if test -n "$RPM_LOG_BASE"
-then
-	LOGBASE=$RPM_LOG_BASE
-else
-	LOGBASE=/var/log
-fi
+ETCBASE=%{_sysconfdir}
+RUNBASE=%{_localstatedir}/run
+LOGBASE=%{_localstatedir}/log
+LIBBASE=%{_localstatedir}/lib
+CACHEBASE=%{_localstatedir}/cache
+ICBASE=%{_libdir}/interchange
 
-if test -n "$RPM_LIB_BASE"
-then
-	LIBBASE=$RPM_LIB_BASE
-else
-	LIBBASE=/var/lib
-fi
-
-if test -n "$RPM_ETC_BASE"
-then
-	ETCBASE=$RPM_ETC_BASE
-else
-	ETCBASE=/etc
-fi
-
-# Create an interch user if one doesn't already exist (on build machine).
-if [ -n "$RPM_BUILD_ROOT" ] && [ -z "`grep '^%{interchange_user}:' /etc/passwd`" ]
-then
-	if [ -n "`grep ^%{interchange_user}: /etc/group`" ]
-	then
-		GROUPOPT='-g %{interchange_user}'
-	else
-		GROUPOPT=
-	fi
-	useradd -M -r -d $LIBBASE/interchange -s /bin/bash -c "Interchange server" $GROUPOPT %interchange_user
-fi
-
-perl Makefile.PL \
+# Install Interchange
+%__perl Makefile.PL \
 	rpmbuilddir=$RPM_BUILD_ROOT \
-	INTERCHANGE_USER=%interchange_user \
-	PREFIX=$RPM_BUILD_ROOT/%{_prefix}/lib/interchange \
-	INSTALLMAN1DIR=$RPM_BUILD_ROOT/%{_mandir}/man1 \
-	INSTALLMAN3DIR=$RPM_BUILD_ROOT/%{_mandir}/man8 \
+	INTERCHANGE_USER=%ic_user \
+	PREFIX=$RPM_BUILD_ROOT$ICBASE \
+	INSTALLMAN1DIR=$RPM_BUILD_ROOT%{_mandir}/man1 \
+	INSTALLMAN3DIR=$RPM_BUILD_ROOT%{_mandir}/man8 \
 	force=1
-make > /dev/null
-make test
-make install
-gzip $RPM_BUILD_ROOT%{_mandir}/man*/* 2>/dev/null
-mkdir -p $RPM_BUILD_ROOT/%{_prefix}/lib/interchange/build
-cp extra/HTML/Entities.pm $RPM_BUILD_ROOT/%{_prefix}/lib/interchange/build
-cp extra/IniConf.pm $RPM_BUILD_ROOT/%{_prefix}/lib/interchange/build
-cp -a eg extensions $RPM_BUILD_ROOT/%{_prefix}/lib/interchange
-chown -R root.root $RPM_BUILD_ROOT
-cd $RPM_BUILD_ROOT/%{_prefix}/lib/interchange
-export PERL5LIB=$RPM_BUILD_ROOT/%{_prefix}/lib/interchange/lib
-export MINIVEND_ROOT=$RPM_BUILD_ROOT/%{_prefix}/lib/interchange
-perl -pi -e 's:^\s+LINK_FILE\s+=>.*:	LINK_FILE => "/var/run/interchange/socket",:' bin/compile_link
-bin/compile_link -build src
-
+%__make
+%__make test
+%__make NOCPANINSTALL=1 install
+
+# Copy over extra stuff that usually stays in source directory
+%__mkdir_p $RPM_BUILD_ROOT$ICBASE/build
+%__cp -p extra/HTML/Entities.pm $RPM_BUILD_ROOT$ICBASE/build
+%__cp -p extra/IniConf.pm $RPM_BUILD_ROOT$ICBASE/build
+%__cp -R -p eg extensions $RPM_BUILD_ROOT$ICBASE
+
+# Tell Perl where to find IC libraries during build time
+export PERL5LIB=$RPM_BUILD_ROOT$ICBASE/lib
+export MINIVEND_ROOT=$RPM_BUILD_ROOT$ICBASE
+
+# Fix paths of link file in compile script
+cd $RPM_BUILD_ROOT$ICBASE
+%__perl -pi -e "s:^(\s+)LINK_FILE(\s+)=>.*:\$1LINK_FILE\$2=> \"$RUNBASE/interchange/socket\",:" bin/compile_link
 
-ETCDIRS="rc.d/init.d logrotate.d"
-LIBDIRS="interchange"
-ICDIRS="$RPM_BUILD_ROOT$RUNBASE/interchange $RPM_BUILD_ROOT$LOGBASE/interchange"
-
-for i in $ETCDIRS
-do
-	mkdir -p $RPM_BUILD_ROOT$ETCBASE/$i
-done
-
-for i in $LIBDIRS
-do
-	mkdir -p $RPM_BUILD_ROOT$LIBBASE/$i
-done
-
-for i in $ICDIRS
-do
-	mkdir -p $i
-	if test -z "$RPM_BUILD_DIR"
-	then
-		chown %{interchange_user}.%interchange_user $i
-		chmod 751 $i
-	fi
-done
-
-mkdir -p $RPM_BUILD_ROOT$ETCBASE/rc.d/init.d
-mkdir -p $RPM_BUILD_ROOT/usr/sbin
-
-cat > $RPM_BUILD_ROOT$ETCBASE/rc.d/init.d/interchange <<EOF
-#!/bin/sh
-#
-# Startup script for Interchange
-# http://developer.akopia.com/
-#
-# chkconfig: 345 96 4
-# description: Interchange is a database access and HTML templating system focused on ecommerce
-# processname: interchange
-# pidfile: $RUNBASE/interchange/interchange.pid
-# config: $ETCBASE/interchange.cfg
-# config: $LIBBASE/interchange/*/catalog.cfg
-
-
-# Source function library.
-. /etc/rc.d/init.d/functions
-
-# Handle /usr/local
-PATH=\$PATH:/usr/local/bin
-
-# See how we were called.
-case "\$1" in
-  start)
-	echo -n "Starting interchange: "
-	daemon interchange
-	echo
-	touch /var/lock/subsys/interchange
-	;;
-  stop)
-	echo -n "Shutting down interchange: "
-	killproc interchange
-	echo
-	rm -f /var/lock/subsys/interchange
-	rm -f $RUNBASE/interchange/interchange.pid
-	;;
-  status)
-	status interchange
-	;;
-  restart)
-	\$0 stop
-	\$0 start
-	;;
-  *)
-	echo "Usage: \$0 {start|stop|restart|status}"
-	exit 1
-esac
-
-exit 0
-EOF
-
-cat > $RPM_BUILD_ROOT/etc/logrotate.d/interchange <<EOF
-/var/log/interchange/*log {
-        rotate 4
-        weekly
-        compress
-}
-EOF
-
-cat > $RPM_BUILD_ROOT/usr/sbin/interchange <<EOF
-#!/bin/sh
-
-RUNSTRING="/usr/lib/interchange/bin/interchange -q \\
-	-configfile $ETCBASE/interchange.cfg \\
-	-pidfile $RUNBASE/interchange/interchange.pid \\
-	-logfile $LOGBASE/interchange/error.log \\
-	ErrorFile=$LOGBASE/interchange/error.log \\
-	PIDfile=$RUNBASE/interchange/interchange.pid \\
-	-confdir $RUNBASE/interchange \\
-	SocketFile=$RUNBASE/interchange/socket"
-
-USER=\`whoami\`
-if test \$USER = "root"
-then 
-	exec su %interchange_user -c "\$RUNSTRING \$*"
-else
-	exec \$RUNSTRING \$*
-fi
-EOF
+# Build link program
+bin/compile_link -build src
 
-chmod +x $RPM_BUILD_ROOT$ETCBASE/rc.d/init.d/interchange $RPM_BUILD_ROOT/usr/sbin/interchange
+%__mkdir_p $RPM_BUILD_ROOT$LIBBASE/interchange
+%__mkdir_p $RPM_BUILD_ROOT$RUNBASE/interchange
+%__mkdir_p $RPM_BUILD_ROOT$LOGBASE/interchange
+%__mkdir_p $RPM_BUILD_ROOT$CACHEBASE/interchange
+
+# Install wrapper script
+%__mkdir_p $RPM_BUILD_ROOT%{_sbindir}
+%__install -m755 %{SOURCE1} $RPM_BUILD_ROOT%{_sbindir}/interchange
+
+# Install SysV-style system startup/shutdown script
+%__mkdir_p $RPM_BUILD_ROOT$ETCBASE/rc.d/init.d
+%__install -m755 %{SOURCE2} $RPM_BUILD_ROOT$ETCBASE/rc.d/init.d/interchange
+
+# Install log rotation script
+%__mkdir_p $RPM_BUILD_ROOT$ETCBASE/logrotate.d
+%__install -m644 %{SOURCE3} $RPM_BUILD_ROOT$ETCBASE/logrotate.d/interchange
 
+# Build the demo catalog
+HOST=RPM_CHANGE_HOST
+BASEDIR=%{_localstatedir}/lib/interchange
+LOGDIR=%{_localstatedir}/log/interchange
+CACHEDIR=%{_localstatedir}/cache/interchange
 DOCROOT=%{webdir}/html
 CGIDIR=%{webdir}/cgi-bin
-SERVERCONF=/etc/httpd/conf/httpd.conf
 CGIBASE=/cgi-bin
-HOST=RPM_CHANGE_HOST
-BASEDIR=/var/lib/interchange
-
-for i in %build_cats
+HTTPDCONF=%{_sysconfdir}/httpd/conf/httpd.conf
+for i in foundation
 do 
-	mkdir -p $RPM_BUILD_ROOT$CGIDIR
-	mkdir -p $RPM_BUILD_ROOT$DOCROOT/$i/images
-	mkdir -p $RPM_BUILD_ROOT$BASEDIR/$i
+	%__mkdir_p $RPM_BUILD_ROOT$CGIDIR
+	%__mkdir_p $RPM_BUILD_ROOT$DOCROOT/$i/images
+	%__mkdir_p $RPM_BUILD_ROOT$BASEDIR/$i
 	bin/makecat \
 		-F \
-		--cgibase=$CGIBASE \
+		--relocate=$RPM_BUILD_ROOT \
+		--nocfg \
+		--norunning \
+		--demotype=$i \
+		--catalogname=$i \
 		--basedir=$BASEDIR \
+		--catroot=$BASEDIR/$i \
 		--documentroot=$DOCROOT \
+		--samplehtml=$DOCROOT/$i \
+		--sampleurl=http://$HOST/$i \
+		--imagedir=$DOCROOT/$i/images \
+		--imageurl=/$i/images \
 		--sharedir=$DOCROOT \
-		--shareurl=/ \
-		--interchangeuser=%interchange_user \
-		--interchangegroup=%interchange_user \
-		--serverconf=$SERVERCONF \
-		--vendroot=/usr/lib/interchange \
-		--catroot=$BASEDIR/$i \
+		--shareurl= \
 		--cgidir=$CGIDIR \
-		--relocate=$RPM_BUILD_ROOT \
-		--servername=$HOST \
+		--cgibase=$CGIBASE \
 		--cgiurl=$CGIBASE/$i \
-		--demotype=$i \
-		--mailorderto=%{interchange_user}@$HOST \
-		--catuser=%interchange_user \
+		--interchangeuser=%ic_user \
+		--interchangegroup=%ic_group \
 		--permtype=user \
-		--samplehtml=$DOCROOT/$i \
-		--imagedir=$DOCROOT/$i/images \
-		--imageurl=/$i/images \
+		--serverconf=$HTTPDCONF \
+		--vendroot=$ICBASE \
 		--linkmode=UNIX \
-		--sampleurl=http://$HOST/$i \
-		--catalogname=$i
+		--servername=$HOST \
+		--catuser=%ic_user \
+		--mailorderto=%{ic_user}@$HOST \
+		cachedir=$CACHEDIR/$i \
+		logdir=$LOGDIR/$i \
+		demomode=1
 done
 
-find $RPM_BUILD_ROOT/var/lib/interchange -type d | xargs chmod 755
-find $RPM_BUILD_ROOT/%{_prefix}/lib/interchange/bin -type f | xargs chmod 755
+# Remove admin UI images now that they're in the HTML doc root
+%__rm -rf $RPM_BUILD_ROOT$ICBASE/share/interchange
 
-for i in %build_cats
-do
-	touch $RPM_BUILD_ROOT/var/log/interchange/$i.error.log
-	ln -s ../../../log/interchange/$i.error.log $RPM_BUILD_ROOT/var/lib/interchange/$i/error.log
-done
-mv interchange.cfg $RPM_BUILD_ROOT/etc/interchange.cfg
-ln -s /etc/interchange.cfg .
-rm -f error.log
-ln -s /var/log/interchange/error.log .
-chmod +r $RPM_BUILD_ROOT/etc/interchange.cfg
+# Clean up empty placeholder files used to keep CVS from pruning away
+# otherwise empty directories
+find $RPM_BUILD_ROOT -type f -name .empty \( -size 0b -o -size 1b \) -exec %__rm -f \{\} \;
+
+# Put interchange.cfg in /etc instead of IC software directory
+%__mv interchange.cfg.dist $RPM_BUILD_ROOT$ETCBASE/interchange.cfg
+%__ln_s $ETCBASE/interchange.cfg
+
+# Put global error log in /var/log/interchange instead of IC software directory
+RPMICLOG=$LOGBASE/interchange/error.log
+%__rm -f error.log
+%__ln_s $RPMICLOG
+touch $RPM_BUILD_ROOT$RPMICLOG
+
+# Make a symlink from docroot area into /usr/share/doc/interchange-x.x.x.
+%__ln_s %{_docdir}/interchange-%{version} $RPM_BUILD_ROOT$DOCROOT/interchange/doc
+
+# I don't know of a way to exclude a subdirectory from one of the directories
+# listed in the %files section, so I have to use this monstrosity to generate
+# a list of all directories in /usr/lib/interchange except the foundation demo
+# directory and pass the list to %files below.
+DIRDEPTH=`echo $ICBASE | sed 's:[^/]::g' | awk '{print length + 1}'`
+cd $RPM_BUILD_ROOT
+find . -path .$ICBASE/foundation -prune -mindepth $DIRDEPTH -maxdepth $DIRDEPTH \
+	-o -print | %__grep "^\.$ICBASE" | sed 's:^\.::' | \
+	%__sed 's:^\(/usr/lib/interchange/etc\):%attr(-, %{ic_user}, %{ic_group}) \1:' \
+	> %filelist
 
 
 %install
@@ -285,157 +207,329 @@
 
 %pre
 
-if test -x /etc/rc.d/init.d/interchange
-then
-	/etc/rc.d/init.d/interchange stop > /dev/null 2>&1
-	#echo "Giving interchange a couple of seconds to exit nicely"
-	sleep 5
-fi
+/sbin/service interchange stop >/dev/null 2>&1 || :
 
-# Create an interch user if one doesn't already exist (on install machine).
-if [ -n "`grep ^%{interchange_user}: /etc/group`" ]
-then
-	GROUPOPT='-g %{interchange_user}'
-else
-	GROUPOPT=
-fi
-useradd -M -r -d /var/lib/interchange -s /bin/bash -c "Interchange server" $GROUPOPT %interchange_user 2> /dev/null || true 
+# Create interch user/group if they don't already exist
+/usr/sbin/groupadd -g 52 %ic_group 2>/dev/null || :
+/usr/sbin/useradd -u 52 -g %ic_group -c "Interchange server" -s /bin/bash \
+	-r -d %{_localstatedir}/lib/interchange %ic_user 2>/dev/null || :
+
+
+%files foundation
+
+%defattr(-, root, root)
+%{_libdir}/interchange/foundation
 
 
-%files
+%files -f %filelist
+
+%defattr(-, %{ic_user}, %{ic_group})
+
+%dir %{_localstatedir}/run/interchange
+%dir %{_localstatedir}/cache/interchange
+%dir %{_localstatedir}/log/interchange
+%dir %{_localstatedir}/lib/interchange
+%config(noreplace) %verify(not size mtime md5) %{_sysconfdir}/interchange.cfg
+
+%defattr(-, root, root)
 
-%doc QuickStart
 %doc LICENSE
 %doc README
-%doc README.rpm
+%doc README.rpm-dist
 %doc README.cvs
-%doc UPGRADE_FROM_MV3
+%doc UPGRADE
 %doc WHATSNEW
-%doc pdf/icbackoffice.pdf
-%doc pdf/icconfig.pdf
-%doc pdf/icdatabase.pdf
-%doc pdf/icinstall.pdf
-%doc pdf/icintro.pdf
-%doc pdf/ictemplates.pdf
-%config(noreplace) /etc/interchange.cfg
-%config(noreplace) /etc/logrotate.d/interchange
-%config /etc/rc.d/init.d/interchange
-%{webdir}/cgi-bin/construct
-%{webdir}/html/construct
-%{webdir}/html/akopia
-/var/lib/interchange/construct
-%{_prefix}/sbin/interchange
-%{_prefix}/lib/interchange
-%{_mandir}/man1
-%{_mandir}/man8
-%dir /var/lib/interchange
-/var/log/interchange
-/var/run/interchange
+%config(noreplace) %{_sysconfdir}/logrotate.d/interchange
+%config %{_sysconfdir}/rc.d/init.d/interchange
+%{_sbindir}/interchange
+%dir %{_libdir}/interchange
+%{webdir}/html/interchange
+%{_mandir}/*/*
+
+
+%files foundation-demo
+
+%defattr(-, %{ic_user}, %{ic_group})
+%{_localstatedir}/lib/interchange/foundation
+%{_localstatedir}/log/interchange/foundation
+%{_localstatedir}/cache/interchange/foundation
+%{webdir}/html/foundation
+%{webdir}/cgi-bin/foundation
 
 
 %post
 
-# Make Interchange start/stop automatically with the operating system.
-/sbin/chkconfig --add interchange
-
-# Change permissions so that the user that will run the Interchange daemon
-# owns all database files.
-chown -R %{interchange_user}.%interchange_user /var/lib/interchange
-chown -R %{interchange_user}.%interchange_user /var/log/interchange
-chown -R %{interchange_user}.%interchange_user /var/run/interchange
-
-for i in %build_cats
-do
-	ln -s %{webdir}/html/$i/images /var/lib/interchange/$i
-	chown %{interchange_user}.%interchange_user %{webdir}/cgi-bin/$i
-	chmod 4755 %{webdir}/cgi-bin/$i
-done
+# Create the error log if it doesn't exist
+if [ ! -f %{_localstatedir}/log/interchange/error.log ]; then
+    touch %{_localstatedir}/log/interchange/error.log
+    %__chown %{ic_user}.%{ic_group} %{_localstatedir}/log/interchange/error.log
+fi
 
-# Set the hostname
-HOST=`hostname`
-perl -pi -e "s/RPM_CHANGE_HOST/$HOST/g"	/var/lib/interchange/*/catalog.cfg /var/lib/interchange/*/products/variable.txt %{webdir}/html/construct/index.html
+# Optionally set Interchange to start/stop with the operating system.
+#/sbin/chkconfig --add interchange
 
 # Get to a place where no random Perl libraries should be found
 cd /usr
 
-status=`perl -e "require HTML::Entities and print 1;" 2>/dev/null`
+# Install private copies of key CPAN modules if necessary
+status=`%__perl -e "require HTML::Entities and print 1;" 2>/dev/null`
 if test "x$status" != x1
 then
-	mkdir -p %{_prefix}/lib/interchange/lib/HTML 2>/dev/null
-	cp %{_prefix}/lib/interchange/build/Entities.pm %{_prefix}/lib/interchange/lib/HTML 2>/dev/null
+	%__mkdir_p %{_libdir}/interchange/lib/HTML 2>/dev/null
+	%__cp -p %{_libdir}/interchange/build/Entities.pm %{_libdir}/interchange/lib/HTML 2>/dev/null
 fi
 
-status=`perl -e "require IniConf and print 1;" 2>/dev/null`
+status=`%__perl -e "require IniConf and print 1;" 2>/dev/null`
 if test "x$status" != x1
 then
-	cp %{_prefix}/lib/interchange/build/IniConf.pm %{_prefix}/lib/interchange/lib 2>/dev/null
+	%__cp -p %{_libdir}/interchange/build/IniConf.pm %{_libdir}/interchange/lib 2>/dev/null
 fi
 
-status=`perl -e "require Storable and print 1;" 2>/dev/null`
+# Storable is technically optional; be careful in case user
+# installed with --nodeps
+status=`%__perl -e "require Storable and print 1;" 2>/dev/null`
 if test "x$status" != x1
 then
-	rm -f %{_prefix}/lib/interchange/_*storable
+	%__rm -f %{_libdir}/interchange/_*storable
 fi
 
-missing=
-for i in MD5 MIME::Base64 URI::URL SQL::Statement Safe::Hole
-do
-	status=`perl -e "require $i and print 1;" 2>/dev/null`
-	if test "x$status" != x1
-	then
-		missing="$missing $i"
-	fi
-done
 
-if test -n "$missing"
+%post foundation-demo
+
+HOST=`hostname`
+
+i=foundation
+%__perl -pi -e "s/RPM_CHANGE_HOST/$HOST/g" \
+	%{_localstatedir}/lib/interchange/$i/catalog.cfg \
+	%{_localstatedir}/lib/interchange/$i/products/*.txt \
+	%{_localstatedir}/lib/interchange/$i/products/*.asc \
+	%{_localstatedir}/lib/interchange/$i/config/* \
+	%{webdir}/html/$i/index.html
+
+# Add Catalog directive to interchange.cfg
+ICCFG=%{_sysconfdir}/interchange.cfg
+catline="`%__grep -i \"^#*[ \t]*Catalog[ \t][ \t]*$i[ \t]\" $ICCFG`"
+if [ -z "$catline" ]; then
+	catline="Catalog  $i  /var/lib/interchange/$i  /cgi-bin/$i"
+	%__perl -pi -e "next if ! /^\s*#\s*Catalog\s/i or \$done; s,\$,\n$catline,; ++\$done" $ICCFG
+fi
+
+# Add the new catalog to the running Interchange daemon
+if [ -n "`/sbin/service interchange status 2>/dev/null | %__grep -i 'interchange.*is running'`" ]
 then
-	{
-		echo ""
-		echo "Missing Perl modules:"
-		echo ""
-		echo "$missing"
-		echo ""
-		echo "Interchange catalogs will work without them, but the admin interface"
-		echo "will not. You need to install them for the UI to work."
-		echo ""
-		echo "Try:"
-		echo ""
-		echo 'perl -MCPAN -e "install Bundle::Interchange"'
-		echo ""
-	} > %warning_file
+	echo "$catline" | %{_sbindir}/interchange --add=$i > /dev/null 2>&1
 fi
 
 
 %preun
 
-# Stop Interchange if running
-if test -x /etc/rc.d/init.d/interchange
-then
-	/etc/rc.d/init.d/interchange stop > /dev/null
+if [ $1 = 0 ]; then
+	# Stop Interchange if running
+	/sbin/service interchange stop >/dev/null 2>&1
+
+	# Remove autostart of interchange
+	/sbin/chkconfig --del interchange 2>/dev/null
+
+	# Remove non-user data
+	%__rm -rf %{_localstatedir}/run/interchange/*
+	%__rm -rf %{_localstatedir}/cache/interchange/*
+	%__rm -rf %{_libdir}/interchange/lib/HTML
+	%__rm -rf %{_libdir}/interchange/etc/varnames
 fi
 
-# Remove autostart of interchange
-if test $1 = 0
-then
-	/sbin/chkconfig --del interchange
+
+%preun foundation-demo
+
+if [ $1 = 0 ]; then
+	i=foundation
+
+	# Remove catalog from running Interchange
+	if [ -n "`/sbin/service interchange status 2>/dev/null | %__grep -i 'interchange.*is running'`" ]
+	then
+		%{_sbindir}/interchange --remove=$i > /dev/null 2>&1
+	fi
+
+	# Remove Catalog directive from interchange.cfg
+	if [ -e %{_sysconfdir}/interchange.cfg ]; then
+		%__perl -pi -e "s/^\s*Catalog\s+$i\s[^\n]+\n//i" %{_sysconfdir}/interchange.cfg
+	fi
+
+	# Remove leftover machine-generated files
+	%__rm -rf %{_localstatedir}/cache/interchange/$i/tmp/*
+	%__rm -rf %{_localstatedir}/cache/interchange/$i/session/*
+	%__rm -rf %{_localstatedir}/log/interchange/$i/orders/*
+	%__rm -rf %{_localstatedir}/log/interchange/$i/logs/*
+	%__rm -rf %{_localstatedir}/lib/interchange/$i/products/*.db
+	%__rm -rf %{_localstatedir}/lib/interchange/$i/products/*.gdbm
+	%__rm -rf %{_localstatedir}/lib/interchange/$i/products/products.txt.*
+	%__rm -rf %{_localstatedir}/lib/interchange/$i/products/*.autonumber
+	%__rm -rf %{_localstatedir}/lib/interchange/$i/products/*.numeric
+	%__rm -rf %{_localstatedir}/lib/interchange/$i/etc/status.$i
 fi
 
-# Remove non-user data
-rm -rf /var/run/interchange/*
-rm -rf /var/lib/interchange/*/images
-rm -rf %{_prefix}/lib/interchange/lib/HTML
-rm -f %warning_file
-rm -f /var/log/interchange/error.log
-
-# Remove construct demo stuff -- we'd rather not do this, but
-# Red Hat's certification tests require no files be left over
-DEMOCATDIR=/var/lib/interchange/construct
-rm -rf $DEMOCATDIR/tmp/* $DEMOCATDIR/session/* $DEMOCATDIR/logs/*
-rm -f $DEMOCATDIR/products/*.gdbm $DEMOCATDIR/products/Ground.csv.numeric $DEMOCATDIR/products/products.txt.*
-rm -f $DEMOCATDIR/etc/status.construct
+
+%clean
+
+%__rm -f %filelist
+[ "$RPM_BUILD_ROOT" != "/" ] && %__rm -rf $RPM_BUILD_ROOT
 
 
 %changelog
+* Mon Jul 22 2002 Jon Jensen <jon@redhat.com> 4.9.1-1
+- Update Vendor etc. to Interchange Development Group.
+- Also remove *.gdbm from foundation-demo products directory on uninstall.
+
+* Mon Jun 17 2002 Jon Jensen <jon@redhat.com>
+- Quell /sbin/service stop errors
+- Re-add main filelist omitted by oversight
+- On uninstall, remove autogenerated /usr/lib/interchange/etc/varnames
+- Stop duplicating admin UI share images in HTML doc root
+- Minor tweaks for 4.9 series
+
+* Tue May 07 2002 Jon Jensen <jon@redhat.com> 4.8.6-1
+- Turn off autostart
+- Pass on message if shutting down running Interchange daemon
+- Use macros for executables where possible
+- Stop gzipping manpages to allow default RPM compression
+  (bzip2 on recent Red Hat Linux)
+
+* Tue Apr 30 2002 Jon Jensen <jon@redhat.com> 4.8.4-9
+- Check package count in uninstall scripts.
+- Add Prereqs for system tools used
+- Let useradd and groupadd fail gracefully, rather than assuming interch
+  user will appear in /etc/passwd or /etc/group
+
+* Mon Apr 29 2002 Jon Jensen <jon@redhat.com>
+- Request uid and gid to be 52, Red Hat's assigned numbers for Interchange.
+- Start IC daemon in UNIX mode only by default.
+- Build foundation-demo with MV_DEMO_MODE set by default.
+- Back out Stronghold index.html patch.
+- Adapt a few more Gary-isms (manpage filelist, NOCPANINSTALL setting).
+
+* Fri Feb 15 2002 Jon Jensen <jon@redhat.com> 4.8.4-8
+- Keep foundation demo's Catalog directive out of interchange.cfg for
+  the base Interchange package; add it separately after installation.
+- Drop unneeded interchange.cfg.dist.
+- Quell some minor uninstall noise.
+
+* Wed Feb 13 2002 Gary Benson <gbenson@redhat.com> 4.8.4-7
+- made the init script more consistent with other RHL packages.
+
+* Wed Feb 13 2002 Gary Benson <gbenson@redhat.com>
+- don't ship an empty logfile in the brpm
+- use _sysconfdir and _localstatedir instead of /etc and /var
+
+* Tue Feb 12 2002 Gary Benson <gbenson@redhat.com>
+- replace ic_version, ic_rpm_release, etc. with version, release, etc.
+- remove cat_name definition, since "Foundation" appears multiple times.
+- tidy summaries and reflow descriptions.
+- remove provides self, obsoletes self and buildarch devilry.
+- change groups to System Environment/Daemons.
+- add versioned subpackage dependencies.
+- split init scripts and logrotate config into separate files.
+
+* Wed Jan 30 2002 Jon Jensen <jon@redhat.com> 4.8.4-6
+- Allow non-root RPM builds (required some changes to makecat as well).
+- Don't add interch user on build machine.
+- Allow easy en/disabling of daemon autostart with defined parameter
+  and default to off to prevent any surprises.
+- Start using Red Hat standard /sbin/service instead of directly running
+  /etc/rc.d/init.d/interchange.
+- Remove unneeded .empty files used in CVS to avoid pruning important but
+  empty directories.
+- Make admin UI images owned by root.
+- Don't include /usr/share/man/man[18] system directories in RPMs.
+- Start using RPM dependencies for Perl CPAN modules. Users who install
+  directly from CPAN will have to use --nodeps.
+- Make main interchange package architecture-dependent, because it includes
+  precompiled vlink and tlink CGIs, and we shouldn't require a C compiler
+  on the install machine if users run makecat later.
+- Stop checking for /home/httpd, but use a define for webdir that can
+  easily be changed if needed.
+
+* Wed Sep 19 2001 Jon Jensen <jon@redhat.com>
+- Add Prereq: interchange to interchange-foundation-demo because the demo
+  installs files owned by the interch user, which gets created when the base
+  package is installed. This way the order the RPMs are given on the command
+  line won't cause trouble.
+
+* Fri Jul 27 2001 Jon Jensen <jon@redhat.com>
+- Make a symlink to /usr{/share}/doc/interchange-x.x.x in
+  /var/www/html/interchange/doc.
+
+* Sat Jul 14 2001 Jon Jensen <jon@redhat.com>
+- Add some files to list for replacing RPM_CHANGE_HOST to real hostname.
+
+* Wed Jun 20 2001 Jon Jensen <jon@redhat.com>
+- Make /usr/lib/interchange/etc owned by interch.interch for makecat.cfg
+  and reconfig and whatever else needs it.
+
+* Thu Jun 14 2001 Jon Jensen <jon@redhat.com>
+- Bring back prebuilt demo, but as a separate package called
+  interchange-foundation-demo. It's helpful to have prebuilt CGI binaries
+  for emaciated OS installations without a C compiler.
+- Handle admin images moved to /var/www/html/interchange.
+
+* Fri May 25 2001 Jon Jensen <jon@redhat.com>
+- Use new split confdir/rundir option to keep important things in
+  /var/run/interchange from getting erased at OS boot time.
+- Add usertrack and catalog error.log to log rotation.
+
+* Tue May 15 2001 Jon Jensen <jon@redhat.com>
+- Quiet restart notice when removing foundation RPM.
+- Correct bad --add option when adding foundation to running Interchange.
+- Move session and temporary files to /var/cache/interchange per LSB.
+- Allow makecat to handle logdir location rather than manually symlinking.
+- Remove admin images when foundation is uninstalled (need to find a better
+  way to deal with this in the future).
+ 
+* Sat May 12 2001 Jon Jensen <jon@redhat.com>
+- Deal with 'useradd' not being in path.
+- Remove some superfluous chowning and chmodding.
+- Show messages from /usr/sbin/interchange; quiet only from rc.d script.
+- Make all Interchange global files owned by root for security -- that way
+  even catalog admin users can't change files if checks are bypassed.
+  Since one must be root to install the RPM at all and to add files to
+  /var/www, this doesn't seem unreasonable. You can still start and stop
+  the server as the interch user. It does mean that you have to be root to
+  run makecat. To allow makecat as interch user, chown interch.interch on
+  these files and directories:
+    /etc/interchange.cfg
+    /var/lib/interchange
+    /usr/lib/interchange/etc/makecat.cfg
+    /var/www/cgi-bin (or copy the link manually)
+    /var/www/html (or add HTML & images manually)
+  And I think that would do it.
+- Make demo package quiet during install.
+- Cleaner delete during uninstall of main package.
+- Safer delete during uninstall of foundation package -- during install
+  stamp the catalog directory with a file and later skip the delete step
+  if that file is not found.
+- Fix a few typos, add some comments.
+
+* Tue Mar 27 2001 Jon Jensen <jon@redhat.com>
+- Fix error.log symlink.
+- Specify that socket.ipc goes in /var/run/interchange
+- Work with Red Hat Linux 6 or 7 from same RPM file.
+- Move to noarch RPM builds. The downside is that we're compiling vlink for
+  foundation *after* install ... This should be ok if we can fall back to
+  the Perl vlink if compile fails.
+
+* Fri Feb 23 2001 Jon Jensen <jon@redhat.com>
+- Check for existing foundation catalog before install (can't count on RPM
+  checks since Interchange is building the catalog after skeleton install)
+- Completely uninstall new locally-built foundation instance
+
+* Tue Feb 20 2001 Jon Jensen <jon@redhat.com>
+- build separate packages for Interchange server and foundation demo
+- run makecat on foundation at install time, rather than build time
+  - this shaves around 500 kB from the RPM package size
+  - don't need to know web directory at build time now, which brings us
+    very close to a single RPM for both RH 6 and 7 platforms; docs are
+    now the only difference left
+- clean up RPM build root after build
+- update text throughout to reflect Red Hat acquisition of Akopia
+
 * Sat Jan  6 2001 Jon Jensen <jon@akopia.com>
 - purge global error.log and most of construct demo when uninstalling
   to satisfy Red Hat's RPM certification requirements



No                   revision



No                   revision



2.2.2.1   +0 -0      interchange/SPECS/interchange-init


rev 2.2.2.1, prev_rev 2.2
Index: interchange-init
===================================================================
RCS file: /var/cvs/interchange/SPECS/interchange-init,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/SPECS/interchange-logrotate


rev 2.1.2.1, prev_rev 2.1
Index: interchange-logrotate
===================================================================
RCS file: /var/cvs/interchange/SPECS/interchange-logrotate,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.2.2.1   +0 -0      interchange/SPECS/interchange-wrapper


rev 2.2.2.1, prev_rev 2.2
Index: interchange-wrapper
===================================================================
RCS file: /var/cvs/interchange/SPECS/interchange-wrapper,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/code/ActionMap/foo.am


rev 1.1.2.1, prev_rev 1.1
Index: foo.am
===================================================================
RCS file: /var/cvs/interchange/code/ActionMap/foo.am,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/code/Filter/convert_date.filter


rev 1.1.2.1, prev_rev 1.1
Index: convert_date.filter
===================================================================
RCS file: /var/cvs/interchange/code/Filter/convert_date.filter,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/Filter/date2time.filter


rev 1.1.2.1, prev_rev 1.1
Index: date2time.filter
===================================================================
RCS file: /var/cvs/interchange/code/Filter/date2time.filter,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/Filter/encrypt.filter


rev 1.1.2.1, prev_rev 1.1
Index: encrypt.filter
===================================================================
RCS file: /var/cvs/interchange/code/Filter/encrypt.filter,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/Filter/lc.filter


rev 1.1.2.1, prev_rev 1.1
Index: lc.filter
===================================================================
RCS file: /var/cvs/interchange/code/Filter/lc.filter,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/Filter/linkdecode.filter


rev 1.1.2.1, prev_rev 1.1
Index: linkdecode.filter
===================================================================
RCS file: /var/cvs/interchange/code/Filter/linkdecode.filter,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +1 -1      interchange/code/Filter/next_sequential.filter


rev 1.1.2.1, prev_rev 1.1
Index: next_sequential.filter
===================================================================
RCS file: /var/cvs/interchange/code/Filter/next_sequential.filter,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- next_sequential.filter	14 Oct 2002 21:35:02 -0000	1.1
+++ next_sequential.filter	25 Jan 2003 22:20:31 -0000	1.1.2.1
@@ -1,4 +1,4 @@
-## $Id: next_sequential.filter,v 1.1 2002/10/14 21:35:02 mheins Exp $
+## $Id: next_sequential.filter,v 1.1.2.1 2003/01/25 22:20:31 racke Exp $
 CodeDef next_sequential Filter
 CodeDef next_sequential Routine <<EOR
 sub {



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/code/SystemTag/accessories.coretag


rev 1.1.2.1, prev_rev 1.1
Index: accessories.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/accessories.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/SystemTag/accounting.coretag


rev 1.2.2.1, prev_rev 1.2
Index: accounting.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/accounting.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/code/SystemTag/area.coretag


rev 1.2.2.1, prev_rev 1.2
Index: area.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/area.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/assign.coretag


rev 1.1.2.1, prev_rev 1.1
Index: assign.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/assign.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.4.2.1   +0 -0      interchange/code/SystemTag/attr_list.coretag


rev 1.4.2.1, prev_rev 1.4
Index: attr_list.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/attr_list.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/code/SystemTag/banner.coretag


rev 1.2.2.1, prev_rev 1.2
Index: banner.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/banner.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/calc.coretag


rev 1.1.2.1, prev_rev 1.1
Index: calc.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/calc.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/calcn.coretag


rev 1.1.2.1, prev_rev 1.1
Index: calcn.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/calcn.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/cart.coretag


rev 1.1.2.1, prev_rev 1.1
Index: cart.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/cart.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.4.2.1   +0 -0      interchange/code/SystemTag/catch.coretag


rev 1.4.2.1, prev_rev 1.4
Index: catch.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/catch.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/cgi.coretag


rev 1.1.2.1, prev_rev 1.1
Index: cgi.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/cgi.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/charge.coretag


rev 1.1.2.1, prev_rev 1.1
Index: charge.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/charge.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/SystemTag/checked.coretag


rev 1.3.2.1, prev_rev 1.3
Index: checked.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/checked.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/control.coretag


rev 1.1.2.1, prev_rev 1.1
Index: control.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/control.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/control_set.coretag


rev 1.1.2.1, prev_rev 1.1
Index: control_set.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/control_set.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/SystemTag/counter.coretag


rev 1.2.2.1, prev_rev 1.2
Index: counter.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/counter.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +2 -3      interchange/code/SystemTag/currency.coretag


rev 1.2.2.1, prev_rev 1.2
Index: currency.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/currency.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1
--- currency.coretag	23 Jan 2003 19:18:47 -0000	1.2
+++ currency.coretag	25 Jan 2003 22:20:32 -0000	1.2.2.1
@@ -1,11 +1,10 @@
 UserTag currency            Order        convert noformat
 UserTag currency            hasEndTag
 UserTag currency            Interpolate
-UserTag currency            addAttr
 UserTag currency            PosNumber    2
 UserTag currency            Routine      <<EOR
 sub {
-	my($convert,$noformat,$opt,$amount) = @_;
-	return Vend::Util::currency($amount, $noformat, $convert, $opt);
+	my($convert,$noformat,$amount) = @_;
+	return Vend::Util::currency($amount, $noformat, $convert);
 }
 EOR



1.1.2.1   +0 -0      interchange/code/SystemTag/data.coretag


rev 1.1.2.1, prev_rev 1.1
Index: data.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/data.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/default.coretag


rev 1.1.2.1, prev_rev 1.1
Index: default.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/default.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.4.2.1   +1 -1      interchange/code/SystemTag/deliver.coretag


rev 1.4.2.1, prev_rev 1.4
Index: deliver.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/deliver.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1
--- deliver.coretag	14 Jan 2003 02:25:50 -0000	1.4
+++ deliver.coretag	25 Jan 2003 22:20:32 -0000	1.4.2.1
@@ -1,7 +1,7 @@
 UserTag deliver Order type
 UserTag deliver HasEndTag
 UserTag deliver addAttr
-UserTag deliver Version $Revision: 1.4 $
+UserTag deliver Version $Revision: 1.4.2.1 $
 UserTag deliver Routine <<EOR
 sub {
 	my ($type, $opt, $body) = @_;



1.1.2.1   +0 -0      interchange/code/SystemTag/description.coretag


rev 1.1.2.1, prev_rev 1.1
Index: description.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/description.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/discount.coretag


rev 1.1.2.1, prev_rev 1.1
Index: discount.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/discount.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/dump.coretag


rev 1.1.2.1, prev_rev 1.1
Index: dump.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/dump.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/either.coretag


rev 1.1.2.1, prev_rev 1.1
Index: either.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/either.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/error.coretag


rev 1.1.2.1, prev_rev 1.1
Index: error.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/error.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/export.coretag


rev 1.1.2.1, prev_rev 1.1
Index: export.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/export.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/field.coretag


rev 1.1.2.1, prev_rev 1.1
Index: field.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/field.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/file.coretag


rev 1.1.2.1, prev_rev 1.1
Index: file.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/file.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/filter.coretag


rev 1.1.2.1, prev_rev 1.1
Index: filter.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/filter.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/flag.coretag


rev 1.1.2.1, prev_rev 1.1
Index: flag.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/flag.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/fly_list.coretag


rev 1.1.2.1, prev_rev 1.1
Index: fly_list.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/fly_list.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/fly_tax.coretag


rev 1.1.2.1, prev_rev 1.1
Index: fly_tax.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/fly_tax.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/handling.coretag


rev 1.1.2.1, prev_rev 1.1
Index: handling.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/handling.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/harness.coretag


rev 1.1.2.1, prev_rev 1.1
Index: harness.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/harness.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/html_table.coretag


rev 1.1.2.1, prev_rev 1.1
Index: html_table.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/html_table.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/SystemTag/image.tag


rev 1.2.2.1, prev_rev 1.2
Index: image.tag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/image.tag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/import.coretag


rev 1.1.2.1, prev_rev 1.1
Index: import.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/import.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/SystemTag/include.coretag


rev 1.2.2.1, prev_rev 1.2
Index: include.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/include.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/index.coretag


rev 1.1.2.1, prev_rev 1.1
Index: index.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/index.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/input_filter.coretag


rev 1.1.2.1, prev_rev 1.1
Index: input_filter.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/input_filter.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/item_list.coretag


rev 1.1.2.1, prev_rev 1.1
Index: item_list.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/item_list.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/levies.coretag


rev 1.1.2.1, prev_rev 1.1
Index: levies.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/levies.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/levy_list.coretag


rev 1.1.2.1, prev_rev 1.1
Index: levy_list.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/levy_list.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/log.coretag


rev 1.1.2.1, prev_rev 1.1
Index: log.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/log.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/loop.coretag


rev 1.1.2.1, prev_rev 1.1
Index: loop.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/loop.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/mail.coretag


rev 1.1.2.1, prev_rev 1.1
Index: mail.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/mail.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/menu.coretag


rev 1.1.2.1, prev_rev 1.1
Index: menu.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/menu.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/msg.coretag


rev 1.1.2.1, prev_rev 1.1
Index: msg.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/msg.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/mvasp.coretag


rev 1.1.2.1, prev_rev 1.1
Index: mvasp.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/mvasp.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/nitems.coretag


rev 1.1.2.1, prev_rev 1.1
Index: nitems.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/nitems.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/onfly.coretag


rev 1.1.2.1, prev_rev 1.1
Index: onfly.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/onfly.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/options.coretag


rev 1.1.2.1, prev_rev 1.1
Index: options.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/options.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/SystemTag/order.coretag


rev 1.3.2.1, prev_rev 1.3
Index: order.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/order.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/output_to.tag


rev 1.1.2.1, prev_rev 1.1
Index: output_to.tag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/output_to.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/page.coretag


rev 1.1.2.1, prev_rev 1.1
Index: page.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/page.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/parse_locale.coretag


rev 1.1.2.1, prev_rev 1.1
Index: parse_locale.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/parse_locale.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/perl.coretag


rev 1.1.2.1, prev_rev 1.1
Index: perl.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/perl.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/SystemTag/price.coretag


rev 1.2.2.1, prev_rev 1.2
Index: price.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/price.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/code/SystemTag/process.coretag


rev 1.4.2.1, prev_rev 1.4
Index: process.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/process.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/profile.coretag


rev 1.1.2.1, prev_rev 1.1
Index: profile.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/profile.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/query.coretag


rev 1.1.2.1, prev_rev 1.1
Index: query.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/query.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/read_cookie.coretag


rev 1.1.2.1, prev_rev 1.1
Index: read_cookie.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/read_cookie.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/record.coretag


rev 1.1.2.1, prev_rev 1.1
Index: record.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/record.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/region.coretag


rev 1.1.2.1, prev_rev 1.1
Index: region.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/region.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/row.coretag


rev 1.1.2.1, prev_rev 1.1
Index: row.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/row.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +1 -1      interchange/code/SystemTag/salestax.coretag


rev 1.3.2.1, prev_rev 1.3
Index: salestax.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/salestax.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1
--- salestax.coretag	23 Jan 2003 19:18:47 -0000	1.3
+++ salestax.coretag	25 Jan 2003 22:20:32 -0000	1.3.2.1
@@ -6,6 +6,6 @@
 UserTag salestax            Routine <<EOR
 sub {
 	my($cart, $noformat, $opt) = @_;
-	return currency( salestax($cart, $opt), $noformat, undef, $opt);
+	return currency( salestax($cart, $opt), $noformat);
 }
 EOR



1.1.2.1   +0 -0      interchange/code/SystemTag/scratch.coretag


rev 1.1.2.1, prev_rev 1.1
Index: scratch.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/scratch.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/scratchd.coretag


rev 1.1.2.1, prev_rev 1.1
Index: scratchd.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/scratchd.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/search_region.coretag


rev 1.1.2.1, prev_rev 1.1
Index: search_region.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/search_region.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/SystemTag/selected.coretag


rev 1.3.2.1, prev_rev 1.3
Index: selected.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/selected.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/set.coretag


rev 1.1.2.1, prev_rev 1.1
Index: set.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/set.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/set_cookie.coretag


rev 1.1.2.1, prev_rev 1.1
Index: set_cookie.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/set_cookie.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/seti.coretag


rev 1.1.2.1, prev_rev 1.1
Index: seti.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/seti.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/setlocale.coretag


rev 1.1.2.1, prev_rev 1.1
Index: setlocale.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/setlocale.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/shipping.coretag


rev 1.1.2.1, prev_rev 1.1
Index: shipping.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/shipping.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/shipping_desc.coretag


rev 1.1.2.1, prev_rev 1.1
Index: shipping_desc.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/shipping_desc.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/soap.coretag


rev 1.1.2.1, prev_rev 1.1
Index: soap.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/soap.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/sql.coretag


rev 1.1.2.1, prev_rev 1.1
Index: sql.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/sql.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/strip.coretag


rev 1.1.2.1, prev_rev 1.1
Index: strip.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/strip.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +2 -3      interchange/code/SystemTag/subtotal.coretag


rev 1.2.2.1, prev_rev 1.2
Index: subtotal.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/subtotal.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1
--- subtotal.coretag	23 Jan 2003 19:18:47 -0000	1.2
+++ subtotal.coretag	25 Jan 2003 22:20:32 -0000	1.2.2.1
@@ -1,11 +1,10 @@
 UserTag subtotal            Order        name noformat
 UserTag subtotal            attrAlias    cart name
-UserTag subtotal            addAttr
 UserTag subtotal            InvalidateCache
 UserTag subtotal            PosNumber    2
 UserTag subtotal            Routine <<EOR
 sub {
-	my($cart, $noformat, $opt) = @_;
-	return currency( subtotal($cart), $noformat, undef, $opt);
+	my($cart, $noformat) = @_;
+	return currency( subtotal($cart), $noformat);
 }
 EOR



1.1.2.1   +0 -0      interchange/code/SystemTag/tag.coretag


rev 1.1.2.1, prev_rev 1.1
Index: tag.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/tag.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/time.coretag


rev 1.1.2.1, prev_rev 1.1
Index: time.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/time.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/timed_build.coretag


rev 1.1.2.1, prev_rev 1.1
Index: timed_build.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/timed_build.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/tmp.coretag


rev 1.1.2.1, prev_rev 1.1
Index: tmp.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/tmp.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/tmpn.coretag


rev 1.1.2.1, prev_rev 1.1
Index: tmpn.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/tmpn.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +2 -3      interchange/code/SystemTag/total_cost.coretag


rev 1.2.2.1, prev_rev 1.2
Index: total_cost.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/total_cost.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1
--- total_cost.coretag	23 Jan 2003 19:18:47 -0000	1.2
+++ total_cost.coretag	25 Jan 2003 22:20:32 -0000	1.2.2.1
@@ -2,10 +2,9 @@
 UserTag total-cost          attrAlias    cart name
 UserTag total-cost          InvalidateCache
 UserTag total-cost          PosNumber    2
-UserTag total-cost          addAttr
 UserTag total-cost          Routine <<EOR
 sub {
-	my($cart, $noformat, $opt) = @_;
-	return currency( total_cost($cart), $noformat, undef, $opt);
+	my($cart, $noformat) = @_;
+	return currency( total_cost($cart), $noformat);
 }
 EOR



1.4.2.1   +0 -0      interchange/code/SystemTag/tree.coretag


rev 1.4.2.1, prev_rev 1.4
Index: tree.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/tree.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/try.coretag


rev 1.1.2.1, prev_rev 1.1
Index: try.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/try.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/unpack.coretag


rev 1.1.2.1, prev_rev 1.1
Index: unpack.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/unpack.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/update.coretag


rev 1.1.2.1, prev_rev 1.1
Index: update.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/update.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/userdb.coretag


rev 1.1.2.1, prev_rev 1.1
Index: userdb.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/userdb.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/value.coretag


rev 1.1.2.1, prev_rev 1.1
Index: value.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/value.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/SystemTag/value_extended.coretag


rev 1.1.2.1, prev_rev 1.1
Index: value_extended.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/value_extended.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/SystemTag/warnings.coretag


rev 1.3.2.1, prev_rev 1.3
Index: warnings.coretag
===================================================================
RCS file: /var/cvs/interchange/code/SystemTag/warnings.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/code/UI_Tag/add_gpg_key.coretag


rev 1.2.2.1, prev_rev 1.2
Index: add_gpg_key.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/add_gpg_key.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/assume_identity.tag


rev 1.1.2.1, prev_rev 1.1
Index: assume_identity.tag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/assume_identity.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.8.2.1   +0 -0      interchange/code/UI_Tag/auto_wizard.coretag


rev 1.8.2.1, prev_rev 1.8
Index: auto_wizard.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/auto_wizard.coretag,v
retrieving revision 1.8
retrieving revision 1.8.2.1
diff -u -r1.8 -r1.8.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/available_ups_internal.coretag


rev 1.1.2.1, prev_rev 1.1
Index: available_ups_internal.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/available_ups_internal.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/available_www_shipping.coretag


rev 1.1.2.1, prev_rev 1.1
Index: available_www_shipping.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/available_www_shipping.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/backup_database.coretag


rev 1.1.2.1, prev_rev 1.1
Index: backup_database.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/backup_database.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/backup_file.coretag


rev 1.2.2.1, prev_rev 1.2
Index: backup_file.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/backup_file.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/base_url.coretag


rev 1.1.2.1, prev_rev 1.1
Index: base_url.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/base_url.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/check_upload.coretag


rev 1.1.2.1, prev_rev 1.1
Index: check_upload.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/check_upload.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/UI_Tag/content_editor.coretag


rev 1.3.2.1, prev_rev 1.3
Index: content_editor.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/content_editor.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/content_info.coretag


rev 1.2.2.1, prev_rev 1.2
Index: content_info.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/content_info.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/content_modify.coretag


rev 1.1.2.1, prev_rev 1.1
Index: content_modify.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/content_modify.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/cp.coretag


rev 1.2.2.1, prev_rev 1.2
Index: cp.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/cp.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/crypt.coretag


rev 1.1.2.1, prev_rev 1.1
Index: crypt.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/crypt.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/db_columns.coretag


rev 1.2.2.1, prev_rev 1.2
Index: db_columns.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/db_columns.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/db_hash.coretag


rev 1.2.2.1, prev_rev 1.2
Index: db_hash.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/db_hash.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/diff.coretag


rev 1.1.2.1, prev_rev 1.1
Index: diff.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/diff.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/diffmerge.coretag


rev 1.1.2.1, prev_rev 1.1
Index: diffmerge.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/diffmerge.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/directive_value.coretag


rev 1.1.2.1, prev_rev 1.1
Index: directive_value.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/directive_value.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.9.2.1   +0 -0      interchange/code/UI_Tag/display.coretag


rev 1.9.2.1, prev_rev 1.9
Index: display.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/display.coretag,v
retrieving revision 1.9
retrieving revision 1.9.2.1
diff -u -r1.9 -r1.9.2.1



1.4.2.1   +0 -0      interchange/code/UI_Tag/dump_session.coretag


rev 1.4.2.1, prev_rev 1.4
Index: dump_session.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/dump_session.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/export_database.coretag


rev 1.1.2.1, prev_rev 1.1
Index: export_database.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/export_database.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/file_info.coretag


rev 1.1.2.1, prev_rev 1.1
Index: file_info.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/file_info.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.8.2.1   +0 -0      interchange/code/UI_Tag/file_navigator.coretag


rev 1.8.2.1, prev_rev 1.8
Index: file_navigator.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/file_navigator.coretag,v
retrieving revision 1.8
retrieving revision 1.8.2.1
diff -u -r1.8 -r1.8.2.1



1.3.2.1   +0 -0      interchange/code/UI_Tag/filters.coretag


rev 1.3.2.1, prev_rev 1.3
Index: filters.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/filters.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/get_gpg_keys.coretag


rev 1.2.2.1, prev_rev 1.2
Index: get_gpg_keys.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/get_gpg_keys.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/global_value.coretag


rev 1.2.2.1, prev_rev 1.2
Index: global_value.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/global_value.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/grep_mm.coretag


rev 1.1.2.1, prev_rev 1.1
Index: grep_mm.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/grep_mm.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/if_mm.coretag


rev 1.2.2.1, prev_rev 1.2
Index: if_mm.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/if_mm.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/image_collate.coretag


rev 1.2.2.1, prev_rev 1.2
Index: image_collate.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/image_collate.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.6.2.1   +1 -1      interchange/code/UI_Tag/import_fields.coretag


rev 1.6.2.1, prev_rev 1.6
Index: import_fields.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/import_fields.coretag,v
retrieving revision 1.6
retrieving revision 1.6.2.1
diff -u -r1.6 -r1.6.2.1
--- import_fields.coretag	12 Jan 2003 18:28:45 -0000	1.6
+++ import_fields.coretag	25 Jan 2003 22:20:35 -0000	1.6.2.1
@@ -1,6 +1,6 @@
 UserTag import_fields Order table
 UserTag import_fields addAttr
-UserTag import_fields Version $Revision: 1.6 $
+UserTag import_fields Version $Revision: 1.6.2.1 $
 UserTag import_fields Routine <<EOR
 sub {
 	my($table, $opt) = @_;



1.3.2.1   +0 -0      interchange/code/UI_Tag/jsq.coretag


rev 1.3.2.1, prev_rev 1.3
Index: jsq.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/jsq.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/jsqn.coretag


rev 1.2.2.1, prev_rev 1.2
Index: jsqn.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/jsqn.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/list_databases.coretag


rev 1.2.2.1, prev_rev 1.2
Index: list_databases.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/list_databases.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/list_glob.coretag


rev 1.1.2.1, prev_rev 1.1
Index: list_glob.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/list_glob.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/list_keys.coretag


rev 1.2.2.1, prev_rev 1.2
Index: list_keys.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/list_keys.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/list_pages.coretag


rev 1.1.2.1, prev_rev 1.1
Index: list_pages.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/list_pages.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/UI_Tag/menu_load.coretag


rev 1.3.2.1, prev_rev 1.3
Index: menu_load.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/menu_load.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/meta_record.coretag


rev 1.2.2.1, prev_rev 1.2
Index: meta_record.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/meta_record.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/mm_locale.coretag


rev 1.1.2.1, prev_rev 1.1
Index: mm_locale.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/mm_locale.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/mm_value.coretag


rev 1.1.2.1, prev_rev 1.1
Index: mm_value.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/mm_value.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/newer.coretag


rev 1.1.2.1, prev_rev 1.1
Index: newer.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/newer.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/quick_table.coretag


rev 1.1.2.1, prev_rev 1.1
Index: quick_table.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/quick_table.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/read_shipping.coretag


rev 1.1.2.1, prev_rev 1.1
Index: read_shipping.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/read_shipping.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/reconfig.coretag


rev 1.2.2.1, prev_rev 1.2
Index: reconfig.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/reconfig.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/reconfig_time.coretag


rev 1.1.2.1, prev_rev 1.1
Index: reconfig_time.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/reconfig_time.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/UI_Tag/regenerate.coretag


rev 1.3.2.1, prev_rev 1.3
Index: regenerate.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/regenerate.coretag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/return_to.coretag


rev 1.1.2.1, prev_rev 1.1
Index: return_to.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/return_to.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/rotate_table.coretag


rev 1.1.2.1, prev_rev 1.1
Index: rotate_table.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/rotate_table.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.5.2.1   +0 -0      interchange/code/UI_Tag/row_edit.coretag


rev 1.5.2.1, prev_rev 1.5
Index: row_edit.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/row_edit.coretag,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/run_profile.coretag


rev 1.1.2.1, prev_rev 1.1
Index: run_profile.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/run_profile.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.4.2.1   +0 -0      interchange/code/UI_Tag/su.coretag


rev 1.4.2.1, prev_rev 1.4
Index: su.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/su.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/substitute_file.coretag


rev 1.1.2.1, prev_rev 1.1
Index: substitute_file.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/substitute_file.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/tabbed_display.coretag


rev 1.2.2.1, prev_rev 1.2
Index: tabbed_display.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/tabbed_display.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.14.2.1  +0 -0      interchange/code/UI_Tag/table_editor.coretag


rev 1.14.2.1, prev_rev 1.14
Index: table_editor.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/table_editor.coretag,v
retrieving revision 1.14
retrieving revision 1.14.2.1
diff -u -r1.14 -r1.14.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/uneval.coretag


rev 1.2.2.1, prev_rev 1.2
Index: uneval.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/uneval.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UI_Tag/unlink_file.coretag


rev 1.1.2.1, prev_rev 1.1
Index: unlink_file.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/unlink_file.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.6.2.1   +1 -1      interchange/code/UI_Tag/update_order_status.tag


rev 1.6.2.1, prev_rev 1.6
Index: update_order_status.tag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/update_order_status.tag,v
retrieving revision 1.6
retrieving revision 1.6.2.1
diff -u -r1.6 -r1.6.2.1
--- update_order_status.tag	14 Jan 2003 00:20:17 -0000	1.6
+++ update_order_status.tag	25 Jan 2003 22:20:35 -0000	1.6.2.1
@@ -1,6 +1,6 @@
 UserTag update-order-status Order order_number
 UserTag update-order-status addAttr
-UserTag update-order-status Version $Id: update_order_status.tag,v 1.6 2003/01/14 00:20:17 mheins Exp $
+UserTag update-order-status Version $Id: update_order_status.tag,v 1.6.2.1 2003/01/25 22:20:35 racke Exp $
 UserTag update-order-status Routine <<EOR
 sub {
 	my ($on, $opt) = @_;



1.4.2.1   +0 -0      interchange/code/UI_Tag/version.coretag


rev 1.4.2.1, prev_rev 1.4
Index: version.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/version.coretag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/widget.coretag


rev 1.2.2.1, prev_rev 1.2
Index: widget.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/widget.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/write_relative_file.coretag


rev 1.2.2.1, prev_rev 1.2
Index: write_relative_file.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/write_relative_file.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/code/UI_Tag/write_shipping.coretag


rev 1.2.2.1, prev_rev 1.2
Index: write_shipping.coretag
===================================================================
RCS file: /var/cvs/interchange/code/UI_Tag/write_shipping.coretag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/code/UserTag/bar_button.tag


rev 1.1.2.1, prev_rev 1.1
Index: bar_button.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/bar_button.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.7.2.1   +1 -1      interchange/code/UserTag/button.tag


rev 1.7.2.1, prev_rev 1.7
Index: button.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/button.tag,v
retrieving revision 1.7
retrieving revision 1.7.2.1
diff -u -r1.7 -r1.7.2.1
--- button.tag	13 Jan 2003 23:11:00 -0000	1.7
+++ button.tag	25 Jan 2003 22:20:36 -0000	1.7.2.1
@@ -2,7 +2,7 @@
 UserTag button addAttr
 UserTag button attrAlias value text
 UserTag button hasEndTag
-UserTag button Version $Id: button.tag,v 1.7 2003/01/13 23:11:00 mheins Exp $
+UserTag button Version $Id: button.tag,v 1.7.2.1 2003/01/25 22:20:36 racke Exp $
 UserTag button Documentation <<EOD
 
 =pod



1.5.2.1   +0 -0      interchange/code/UserTag/component.tag


rev 1.5.2.1, prev_rev 1.5
Index: component.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/component.tag,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/convert_date.tag


rev 1.1.2.1, prev_rev 1.1
Index: convert_date.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/convert_date.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/db_date.tag


rev 1.1.2.1, prev_rev 1.1
Index: db_date.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/db_date.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/delete_cart.tag


rev 1.1.2.1, prev_rev 1.1
Index: delete_cart.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/delete_cart.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/UserTag/email.tag


rev 1.3.2.1, prev_rev 1.3
Index: email.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/email.tag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/code/UserTag/email_raw.tag


rev 1.2.2.1, prev_rev 1.2
Index: email_raw.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/email_raw.tag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/env.tag


rev 1.1.2.1, prev_rev 1.1
Index: env.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/env.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/code/UserTag/fedex_query.tag


rev 1.3.2.1, prev_rev 1.3
Index: fedex_query.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/fedex_query.tag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.6.2.1   +0 -0      interchange/code/UserTag/formel.tag


rev 1.6.2.1, prev_rev 1.6
Index: formel.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/formel.tag,v
retrieving revision 1.6
retrieving revision 1.6.2.1
diff -u -r1.6 -r1.6.2.1



1.2.2.1   +0 -0      interchange/code/UserTag/fortune.tag


rev 1.2.2.1, prev_rev 1.2
Index: fortune.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/fortune.tag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.3.2.1   +0 -0      interchange/code/UserTag/forum.tag


rev 1.3.2.1, prev_rev 1.3
Index: forum.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/forum.tag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.3.2.1   +0 -0      interchange/code/UserTag/get_url.tag


rev 1.3.2.1, prev_rev 1.3
Index: get_url.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/get_url.tag,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.8.2.1   +0 -0      interchange/code/UserTag/history_scan.tag


rev 1.8.2.1, prev_rev 1.8
Index: history_scan.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/history_scan.tag,v
retrieving revision 1.8
retrieving revision 1.8.2.1
diff -u -r1.8 -r1.8.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/load_cart.tag


rev 1.1.2.1, prev_rev 1.1
Index: load_cart.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/load_cart.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/loc.tag


rev 1.1.2.1, prev_rev 1.1
Index: loc.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/loc.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/page_meta.tag


rev 1.1.2.1, prev_rev 1.1
Index: page_meta.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/page_meta.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/rand.tag


rev 1.1.2.1, prev_rev 1.1
Index: rand.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/rand.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/save_cart.tag


rev 1.1.2.1, prev_rev 1.1
Index: save_cart.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/save_cart.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UserTag/summary.tag


rev 1.2.2.1, prev_rev 1.2
Index: summary.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/summary.tag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.5.2.1   +0 -0      interchange/code/UserTag/table_organize.tag


rev 1.5.2.1, prev_rev 1.5
Index: table_organize.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/table_organize.tag,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/title_bar.tag


rev 1.1.2.1, prev_rev 1.1
Index: title_bar.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/title_bar.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/code/UserTag/ups_query.tag


rev 1.2.2.1, prev_rev 1.2
Index: ups_query.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/ups_query.tag,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/code/UserTag/usertrack.tag


rev 1.1.2.1, prev_rev 1.1
Index: usertrack.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/usertrack.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.4.2.1   +0 -0      interchange/code/UserTag/var.tag


rev 1.4.2.1, prev_rev 1.4
Index: var.tag
===================================================================
RCS file: /var/cvs/interchange/code/UserTag/var.tag,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/code/Widget/gpg_keys.widget


rev 1.1.2.1, prev_rev 1.1
Index: gpg_keys.widget
===================================================================
RCS file: /var/cvs/interchange/code/Widget/gpg_keys.widget,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/Widget/imagedir.widget


rev 1.1.2.1, prev_rev 1.1
Index: imagedir.widget
===================================================================
RCS file: /var/cvs/interchange/code/Widget/imagedir.widget,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/Widget/imagehelper.widget


rev 1.1.2.1, prev_rev 1.1
Index: imagehelper.widget
===================================================================
RCS file: /var/cvs/interchange/code/Widget/imagehelper.widget,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/code/Widget/uploadhelper.widget


rev 1.1.2.1, prev_rev 1.1
Index: uploadhelper.widget
===================================================================
RCS file: /var/cvs/interchange/code/Widget/uploadhelper.widget,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/debian/400mod_interchange.info


rev 1.2.2.1, prev_rev 1.2
Index: 400mod_interchange.info
===================================================================
RCS file: /var/cvs/interchange/debian/400mod_interchange.info,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.5.2.1   +0 -0      interchange/debian/CREDITS.debian


rev 1.5.2.1, prev_rev 1.5
Index: CREDITS.debian
===================================================================
RCS file: /var/cvs/interchange/debian/CREDITS.debian,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



2.7.2.1   +0 -0      interchange/debian/interchange-cat-foundation.config


rev 2.7.2.1, prev_rev 2.7
Index: interchange-cat-foundation.config
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-cat-foundation.config,v
retrieving revision 2.7
retrieving revision 2.7.2.1
diff -u -r2.7 -r2.7.2.1



2.0.4.1   +0 -0      interchange/debian/interchange-cat-foundation.files


rev 2.0.4.1, prev_rev 2.0
Index: interchange-cat-foundation.files
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-cat-foundation.files,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.11.2.1  +0 -0      interchange/debian/interchange-cat-foundation.postinst


rev 2.11.2.1, prev_rev 2.11
Index: interchange-cat-foundation.postinst
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-cat-foundation.postinst,v
retrieving revision 2.11
retrieving revision 2.11.2.1
diff -u -r2.11 -r2.11.2.1



1.2.4.1   +0 -0      interchange/debian/interchange-cat-foundation.postrm


rev 1.2.4.1, prev_rev 1.2
Index: interchange-cat-foundation.postrm
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-cat-foundation.postrm,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1



2.2.4.1   +0 -0      interchange/debian/interchange-cat-foundation.prerm


rev 2.2.4.1, prev_rev 2.2
Index: interchange-cat-foundation.prerm
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-cat-foundation.prerm,v
retrieving revision 2.2
retrieving revision 2.2.4.1
diff -u -r2.2 -r2.2.4.1



2.9.2.1   +0 -0      interchange/debian/interchange-cat-foundation.templates


rev 2.9.2.1, prev_rev 2.9
Index: interchange-cat-foundation.templates
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-cat-foundation.templates,v
retrieving revision 2.9
retrieving revision 2.9.2.1
diff -u -r2.9 -r2.9.2.1



2.3.4.1   +0 -0      interchange/debian/interchange-ui.config


rev 2.3.4.1, prev_rev 2.3
Index: interchange-ui.config
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-ui.config,v
retrieving revision 2.3
retrieving revision 2.3.4.1
diff -u -r2.3 -r2.3.4.1



1.3.2.1   +0 -0      interchange/debian/interchange-ui.postrm


rev 1.3.2.1, prev_rev 1.3
Index: interchange-ui.postrm
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-ui.postrm,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.5.2.1   +0 -0      interchange/debian/interchange-ui.preinst


rev 1.5.2.1, prev_rev 1.5
Index: interchange-ui.preinst
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-ui.preinst,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.3.4.1   +0 -0      interchange/debian/interchange-ui.prerm


rev 1.3.4.1, prev_rev 1.3
Index: interchange-ui.prerm
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-ui.prerm,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1



2.2.4.1   +0 -0      interchange/debian/interchange-ui.templates


rev 2.2.4.1, prev_rev 2.2
Index: interchange-ui.templates
===================================================================
RCS file: /var/cvs/interchange/debian/interchange-ui.templates,v
retrieving revision 2.2
retrieving revision 2.2.4.1
diff -u -r2.2 -r2.2.4.1



1.1.2.3   +26 -13    interchange/debian/interchange.preinst


rev 1.1.2.3, prev_rev 1.1.2.2



1.2.4.1   +0 -0      interchange/debian/interchange.prerm


rev 1.2.4.1, prev_rev 1.2
Index: interchange.prerm
===================================================================
RCS file: /var/cvs/interchange/debian/interchange.prerm,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1



2.8.2.1   +0 -0      interchange/debian/interchangeconfig


rev 2.8.2.1, prev_rev 2.8
Index: interchangeconfig
===================================================================
RCS file: /var/cvs/interchange/debian/interchangeconfig,v
retrieving revision 2.8
retrieving revision 2.8.2.1
diff -u -r2.8 -r2.8.2.1



1.2.2.1   +0 -0      interchange/debian/libapache-mod-interchange.doc-base


rev 1.2.2.1, prev_rev 1.2
Index: libapache-mod-interchange.doc-base
===================================================================
RCS file: /var/cvs/interchange/debian/libapache-mod-interchange.doc-base,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.4.4.2   +58 -64    interchange/dist/catalog_after.cfg


rev 1.4.4.2, prev_rev 1.4.4.1
Index: catalog_after.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/catalog_after.cfg,v
retrieving revision 1.4.4.1
retrieving revision 1.4.4.2
diff -u -r1.4.4.1 -r1.4.4.2
--- catalog_after.cfg	10 Jan 2001 01:33:01 -0000	1.4.4.1
+++ catalog_after.cfg	25 Jan 2003 22:20:38 -0000	1.4.4.2
@@ -1,9 +1,58 @@
-#ifdef @UI
+AutoVariable <<EOF
+	DefaultShipping
+	DescriptionField
+	ImageDir
+	ImageDirSecure
+	MailOrderTo
+	PriceField
+	ProductFiles
+	ProductDir
+	SecureURL
+	VendURL
+EOF
+
+ifdef @UI
 UserDB ui database   access
 UserDB ui crypt      1
 UserDB ui time_field last_login
 UserDB ui admin 1
 UserDB default admin 0
+
+#AdminSub <<EOR
+#add_gpg_key
+#backup_database
+#backup_file
+#check_upload
+#db_columns
+#db_hash
+#directive_value
+#dump_session
+#export_database
+#file_navigator
+#global_value
+#grep_mm
+#if_mm
+#import_fields
+#list_databases
+#list_glob
+#list_keys
+#list_pages
+#mm_value
+#read_shipping
+#read_ui_template
+#regenerate
+#rotate_file
+#row_edit
+#substitute_file
+#uneval
+#unlink_file
+#version
+#widget
+#with
+#write_relative_file
+#write_shipping
+#EOR
+
 ParseVariables Yes
 
 ActionMap ui_download <<EOR
@@ -13,28 +62,13 @@
 	$CGI->{mv_nextpage} =~ s:^ui_download/::;
 	$CGI->{mv_nextpage} .= $Session->{extension};
 	if($Tag->if_mm('files', $CGI->{mv_nextpage}) ) {
-		$Document->header("Content-type: application/octet-stream");
-		$Document->hot(1);
-		HTML ( $Tag->file($CGI->{mv_nextpage}) );
-		$status = 0;
-	}
-	else {
-		$Scratch->{ui_error} = "Not authorized for file $CGI->{mv_nextpage}";
-		$CGI->{mv_nextpage} = '__UI_BASE__/error';
-		$status = 1;
-	}
-	return $status;
-}
-EOR
-
-ActionMap ui_edit <<EOR
-sub {
-	my $deliverable = shift;
-	my $status;
-	$CGI->{mv_nextpage} =~ s:^ui_download/::;
-	$CGI->{mv_nextpage} .= $Session->{extension};
-	if($Tag->if_mm('files', $CGI->{mv_nextpage}) ) {
-		$Document->header("Content-type: application/octet-stream");
+		# Take care of MSIE brain damage
+		if($Session->{browser} =~ /msie/i) {
+			$Document->header("Content-type: application/x-foolmsie");
+		}
+		else {
+			$Document->header("Content-type: application/octet-stream");
+		}
 		$Document->hot(1);
 		HTML ( $Tag->file($CGI->{mv_nextpage}) );
 		$status = 0;
@@ -48,44 +82,4 @@
 }
 EOR
 
-ActionMap ui_dbdownload <<EOR
-sub {
-	my $deliverable = shift;
-	my $status;
-	my ($db, $dbname, @columns, @keys, @values);
-
-	$CGI->{mv_nextpage} =~ s:^ui_dbdownload/::;
-	$dbname = $CGI->{mv_nextpage};
-
-	if($Tag->if_mm({function => 'export', table => $dbname})) {
-		$Document->header("Content-type: application/octet-stream");
-		$Document->hot(1);
-
-		# get a list of accessible columns
-		@columns = split(/\0/, 
-			$Tag->db_columns({name => $dbname, joiner => "\0"}));
-		HTML (join ("\t", @columns), "\n");
-
-		# get a list of accessible keys
-		@keys = split(/\n/,
-			$Tag->list_keys($dbname));
-
-		# put out anything
-		foreach my $key (@keys) {
-			undef @values;
-			foreach my $col (@columns) {
-				push (@values, $Tag->data($dbname, $col, $key));
-			}
-			HTML (join("\t", @values), "\n");
-		}
-		$status = 0;
-	}
-	else {
-		$Scratch->{ui_error} = "Not authorized for table $dbname";
-		$CGI->{mv_nextpage} = '__UI_BASE__/error';
-		$status = 1;
-	}
-	return $status;
-}
-EOR
-#endif
+endif



1.17.4.9  +56 -149   interchange/dist/catalog_before.cfg


rev 1.17.4.9, prev_rev 1.17.4.8
Index: catalog_before.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/catalog_before.cfg,v
retrieving revision 1.17.4.8
retrieving revision 1.17.4.9
diff -u -r1.17.4.8 -r1.17.4.9
--- catalog_before.cfg	2 Jan 2001 08:05:50 -0000	1.17.4.8
+++ catalog_before.cfg	25 Jan 2003 22:20:38 -0000	1.17.4.9
@@ -1,36 +1,25 @@
 ParseVariables Yes
 
-#ifdef @UI_BASE
+ifdef @UI_BASE
 Variable UI_BASE @@UI_BASE@@
-#endif
+endif
 
-#ifndef UI_BASE
+ifndef UI_BASE
 Variable UI_BASE admin
-#endif
+endif
 
-#ifdef @UI
-Variable UI_AFFILIATE_TABLE affiliate
+ifdef @LockType ne 'none'
+Variable UI_LOCKING 1
+endif
+
+Variable INTERCHANGE_EMAIL interchange@icdevgroup.org
+Variable INTERCHANGE_URL http://www.icdevgroup.org/
+
+ifdef @UI
+Variable UI_ABOUT_LOGIN_URL http://www.icdevgroup.org/
+Variable UI_ABOUT_NORMAL_URL http://www.icdevgroup.org/
 Variable UI_ACCESS_TABLE   access
 Variable UI_BOTTOMIMG      poweredby.gif
-Variable UI_C_ALINK        #FF0000
-Variable UI_C_BG           #FFFFFF
-Variable UI_C_HEADERTXT    #333333
-Variable UI_C_INTBLOCK     #CCCC99
-Variable UI_C_INTBLOCKBAR  #73f2d9
-Variable UI_C_LINK         #0000FF
-Variable UI_C_TITLEBARBG   #6699FF
-Variable UI_C_TITLEBARCONT #000000
-Variable UI_C_TITLEBARTXT  #FFFFFF
-Variable UI_C_TOPBLOCKBAR  #336699
-Variable UI_C_TXT          #000000
-Variable UI_C_MENUTEXT     #000066
-Variable UI_C_MENUBG       #FFFFFF
-Variable UI_C_MENUTITLE    #000066
-Variable UI_C_MENUBARBG    #000066
-Variable UI_C_MENUBARTXT   #FFFFAA
-Variable UI_C_VLINK        #0000CC
-Variable UI_C_CONTRAST     #FF0000
-Variable UI_HELP_BASE_URL  http://localhost/ui/help
 Variable UI_HELP_HEIGHT    480
 Variable UI_HELP_WIDTH     650
 Variable UI_LEFT_WIDTH     150
@@ -38,14 +27,12 @@
 Variable UI_MAIN_WIDTH     600
 Variable UI_META_TABLE     mv_metadata
 Variable UI_PRODUCT_DIR    products
-Variable UI_PRODUCT_TABLE  products
-Variable UI_ITEM_DESCRIPTION  description
 Variable UI_PAGE_DIR       pages
 Variable UI_OVERALL_WIDTH  750
-Variable UI_P_ALINK        #EE0000
+Variable UI_P_ALINK        #CC3333
 Variable UI_P_BG           #FFFFFF
-Variable UI_P_LINK         #0000EE
-Variable UI_P_VLINK        #0000FF
+Variable UI_P_LINK         #CC3333
+Variable UI_P_VLINK        #FF3333
 Variable UI_RIGHT_WIDTH    450
 Variable UI_SZ_LIST_CUSTOMER 50
 Variable UI_SZ_LIST_ORDER    50
@@ -53,117 +40,23 @@
 Variable UI_T_PROPERTIES   cellpadding=3 cellspacing=0 width=90% border=0
 Variable UI_T_ROW_EVEN     #EEEEEE
 Variable UI_T_ROW_ODD      #FFFFFF
+Variable UI_TOP_BG		   #CC0000
 
-Variable UI_SUBMENU_None <<EOV
-code	next_line	indicator	depends_on	page	form	name
-1		!nevairbe				<font size="-1"><b>Welcome to Akopia Interchange</b></font>
-EOV
-
-Variable UI_SUBMENU_Merchandising <<EOV
-code	next_line	indicator	depends_on	page	form	name
-1				__UI_BASE__/merchandising		Product Merchandising
-2				__UI_BASE__/affiliates		Affiliates
-3				__UI_BASE__/build_related		Generate "others who ..."
-4	1		affiliates	__UI_BASE__/flex_editor	page_title=Create new affiliate&mv_data_table=[var UI_AFFILIATE_TABLE]&help_name=create.new.affiliate&item_id=new&ui_return_to=__UI_BASE__/affiliates&icon_name=admin/icon_people.gif	Create new affiliate
-EOV
-
-Variable UI_SUBMENU_Reports <<EOV
-code	next_line	indicator	depends_on	page	form	name
-1				__UI_BASE__/orderstats		Orders
-2				__UI_BASE__/trafficstats		Traffic
-[if-mm super]3				__UI_BASE__/tablereport		Custom
-[/if-mm]
-EOV
-
-Variable UI_SUBMENU_Orders <<EOV
-code	next_line	indicator	depends_on	page	form	name
-1		!showarchive		__UI_BASE__/order	showpending=1	Pending Orders
-2		showarchive		__UI_BASE__/order	showarchive=1	Archived Orders
-3				__UI_BASE__/entry		Enter Order
-EOV
-
-Variable UI_SUBMENU_Items <<EOV
-code	next_line	indicator	depends_on	page	form	name
-1				__UI_BASE__/item		Item list
-9				__UI_BASE__/item_edit	item_id=new	&nbsp;&nbsp;&nbsp;&nbsp;Create new item
-2			item_id			&nbsp;&nbsp;&nbsp;sku: [cgi item_id]
-3	1		item_id	__UI_BASE__/item_edit	item_id=[cgi item_id]&ui_sequence_edit=[cgi ui_sequence_edit]&item_id_left=[cgi item_id_left]	Edit
-4			item_id	__UI_BASE__/item_price	item_id=[cgi item_id]&ui_sequence_edit=[cgi ui_sequence_edit]&item_id_left=[cgi item_id_left]	Pricing
-5			item_id	__UI_BASE__/item_up	item_id=[cgi item_id]&ui_sequence_edit=[cgi ui_sequence_edit]&item_id_left=[cgi item_id_left]	Up-sell
-6			item_id	__UI_BASE__/item_cross	item_id=[cgi item_id]&ui_sequence_edit=[cgi ui_sequence_edit]&item_id_left=[cgi item_id_left]	Cross-sell
-7			item_id	__UI_BASE__/item_feature	item_id=[cgi item_id]&ui_sequence_edit=[cgi ui_sequence_edit]&item_id_left=[cgi item_id_left]	Promotion
-8			item_id	__UI_BASE__/item_inventory	item_id=[cgi item_id]&ui_sequence_edit=[cgi ui_sequence_edit]&item_id_left=[cgi item_id_left]	Inventory
-EOV
-
-Variable UI_SUBMENU_Content <<EOV
-code	next_line	indicator	depends_on	page	form	name
-1				__UI_BASE__/page		Page Edit
-2				__UI_BASE__/genupload		File Transfer
-EOV
-
-Variable UI_SUBMENU_Design <<EOV
-code	next_line	indicator	depends_on	page	form	name
-1				__UI_BASE__/layout		Site layout
-2				__UI_BASE__/search_wizard		Search Builder
-3				__UI_BASE__/button_builder		Button Builder
-4				__UI_BASE__/regenerate		Generate Static
-5				__UI_BASE__/genupload		File Transfer
-6				__UI_BASE__/page		Page Edit
-EOV
-
-Variable UI_SUBMENU_Customers <<EOV
-code	next_line	indicator	exclude_on	depends_on	page	form	name
-1		showactive			__UI_BASE__/customer	showactive=1	Active Customers
-2		showinactive			__UI_BASE__/customer	showinactive=1	Inactive Customers
-3					__UI_BASE__/flex_editor	page_title=Create new customer&mv_data_table=userdb&help_name=create.new.customer&item_id=new&ui_return_to=__UI_BASE__/customer	Create new customer
-4	1		deletecustomer	customer	__UI_BASE__/customer_ship	customer=[cgi customer]	Shipping
-5			deletecustomer	customer	__UI_BASE__/customer_bill	customer=[cgi customer]	Billing
-6			deletecustomer	customer	__UI_BASE__/customer_pref	customer=[cgi customer]	Preferences
-7			deletecustomer	customer	__UI_BASE__/entry	customer=[cgi customer]	Enter Order
-EOV
-
-#Variable UI_SUBMENU_Admin <<EOV
-#code	next_line	indicator	depends_on	page	form	name
-#1				__UI_BASE__/tax	ui_page_charges=1	Charges
-#2				__UI_BASE__/preferences		Preferences
-#3				__UI_BASE__/flex_select	mv_data_table=variable&page_title=Knar editor&ui_meta_specific=1&help_name=knar.main&ui_description_fields=code&ui_return_to=__UI_BASE__/preferences	Knar
-#4				__UI_BASE__/gentable	ui_page_tables=1	Tables
-#5			ui_changes_made	__UI_BASE__/reconfig		&nbsp;&nbsp;&nbsp;Apply Changes
-#6	1		ui_page_tables	__UI_BASE__/flex_select	ui_page_tables=1&mv_data_table=[cgi mv_data_table]	Edit
-#7			ui_page_tables	__UI_BASE__/import_table	ui_page_tables=1&mv_data_table=[cgi mv_data_table]	Import Data
-#8			ui_page_tables	__UI_BASE__/export_table	ui_page_tables=1&mv_data_table=[cgi mv_data_table]	Export Data
-#9			ui_page_tables	__UI_BASE__/spread	ui_page_tables=1&mv_data_table=[cgi mv_data_table]	Spreadsheet
-#10			ui_page_tables	__UI_BASE__/flex_editor	ui_page_tables=1&mv_data_table=[cgi mv_data_table]&item_id=new	New Entry
-#11			ui_page_tables	__UI_BASE__/gentable	ui_page_tables=1&	&nbsp;&nbsp;&nbsp;&nbsp;Re-select Table
-#12	1		ui_page_charges	__UI_BASE__/tax		Tax
-#13			ui_page_charges	__UI_BASE__/ship	ui_page_charges=1	Shipping
-#14			ui_page_charges	__UI_BASE__/payment	ui_page_charges=1	Payment
-#EOV
-
-Variable UI_SUBMENU_Admin <<EOV
-code	next_line	indicator	exclude_on	depends_on	page	form	name
-1					__UI_BASE__/genconfig		Info
-2					__UI_BASE__/tax		Tax
-3					__UI_BASE__/ship		Shipping
-4					__UI_BASE__/payment		Payment
-5					__UI_BASE__/access		Access
-6					__UI_BASE__/preferences		Preferences
-7					__UI_BASE__/flex_select	mv_data_table=variable&page_title=Knar editor&ui_meta_specific=1&help_name=knar.main&ui_description_fields=code&ui_return_to=__UI_BASE__/preferences Variable	Knar
-8					__UI_BASE__/gentable		Tables
-9					__UI_BASE__/reconfig	ui_changes_made	&nbsp;&nbsp;&nbsp;Apply Changes
-10	1		no_dbmenu	mv_data_table	__UI_BASE__/flex_select	mv_data_table=[cgi mv_data_table]	Edit
-11			no_dbmenu	mv_data_table	__UI_BASE__/import_table	mv_data_table=[cgi mv_data_table]	Import Data
-12			no_dbmenu	mv_data_table	__UI_BASE__/export_table	mv_data_table=[cgi mv_data_table]	Export Data
-13			no_dbmenu	mv_data_table	__UI_BASE__/spread	mv_data_table=[cgi mv_data_table]	Spreadsheet
-14			no_dbmenu	mv_data_table	__UI_BASE__/flex_editor	mv_data_table=[cgi mv_data_table]&item_id=new	New Entry
-15			no_dbmenu	mv_data_table	__UI_BASE__/gentable		&nbsp;&nbsp;&nbsp;&nbsp;Re-select Table
-16	1			access_menu	__UI_BASE__/access		Users
-17				access_menu	__UI_BASE__/group		Groups
-EOV
-#endif
+Variable UI_ITEM_TABLES    products pricing inventory merchandising options:sku
+
+Database ichelp ichelp.txt  TAB
+Database ichelp PRELOAD     lib/UI/ichelp.txt
+Database ichelp PRELOAD_EMPTY_ONLY 1
+Database ichelp HIDE_EDIT   1
+Database ichelp AUTO_EXPORT __UI_LOCKING__
+
+endif
 
 ParseVariables No
 
+Variable  MV_DEFAULT_SEARCH_FILE  products
+Variable  MV_DEFAULT_SEARCH_TABLE products
+
 Sub <<EOR
 sub bar_link {
 	my $base = shift || 'cat';
@@ -172,6 +65,7 @@
 		and $extra = $1;
 	my $ref = shift;
 	my $code = $ref->[0];
+
 	my $record =  tag_data($base, 'n/a', $code, { hash => 1 });
 	return $ref->[0] unless $record;
 
@@ -179,6 +73,7 @@
 	my $anchor;
 	my $highlight;
 	my $first;
+	my $expand;
 
 	LINK: {
 		if($record->{link_type} eq 'external') {
@@ -218,17 +113,18 @@
 				push @out, "sf=$col";
 				push @out, "se=$string";
 			}
-			push @out, qq{va=link_image=$record->{banner_image}};
-			push @out, qq{va=link_banner=$record->{banner_text}};
+			push @out, $record->{search}
+				if $record->{search} =~ /^\s*\w\w=/;
+
+			push @out, qq{va=banner_image=$record->{banner_image}} if ($record->{banner_image});
+			push @out, qq{va=banner_text=$record->{banner_text}} if ($record->{banner_text});
 			$options{arg} = join "\n", @out;
 			$url = $Tag->area(\%options);
 		}
 		elsif	($record->{link_type} eq 'complex') {
 			$record->{search} =~ s/[\r\n+]/\n/g;
-			$record->{search} .= qq{\nva=link_banner=$record->{banner_text}}
-				if $record->{banner_text};
-			$record->{search} .= qq{\nva=link_image=$record->{banner_image}}
-				if $record->{banner_image};
+			$record->{search} .= qq{\nva=banner_text=$record->{banner_text}} if ($record->{banner_text});
+			$record->{search} .= qq{\nva=banner_image=$record->{banner_image}} if ($record->{banner_image});
 			$url = $Tag->area('scan', $record->{search});
 		}
 		else {
@@ -237,36 +133,47 @@
 	}
 
 	ANCHOR: {
+		my $display_text = $record->{banner_text} || $record->{name};
+		$display_text =~ s/"/&quot;/g;
 		if($record->{display_type} eq 'url') {
 			$anchor = "";
 		}
 		elsif ($record->{display_type} eq 'name') {
-			$anchor = "$record->{name}";
+			$anchor = $display_text;
 		}
 		elsif ($record->{display_type} eq 'icon') {
-			$anchor = qq{<img src="$record->{image}" alt="$record->{name}"};
+			$anchor = qq{<img src="$record->{image}" alt="$display_text"};
 			$anchor .= " $record->{image_prop}"
 				if $record->{image_prop};
 			$anchor .= '>';
-			$anchor .= $record->{name};
+			$anchor .= $display_text;
 		}
 		elsif ($record->{display_type} eq 'image') {
-			$anchor = qq{<img src="$record->{image}" alt="$record->{name}"};
+			$anchor = qq{<img src="$record->{image}" alt="$display_text"};
 			$anchor .= " $record->{image_prop}"
 				if $record->{image_prop};
 			$anchor .= '>';
 		}
 		else {
-			$anchor = "$record->{name}";
+			$anchor = $display_text;
 		}
 	}
 	return $url if ! $anchor;
 	return $anchor if ! $url;
+	EXPAND: {
+		if ($url =~ /\?/) {
+			$expand = "&expand=$code";
+		}
+		else {
+			$expand = "?expand=$code";
+		}
+	}		
 	my $tmpl = $record->{link_template}
 			 || $extra
 			 || $Variable->{BAR_LINK_TEMPLATE}
-			 || q{<A HREF="$URL$" CLASS="barlink">$ANCHOR$</A>};
+			 || q{<A HREF="$URL$" class=barlink>$ANCHOR$</A>};
 	$record->{ANCHOR} = $anchor;
+	$record->{EXPAND} = $expand;
 	$record->{URL} = $url;
 	$tmpl =~ s!{HIGHLIGHT}(.*?){/HIGHLIGHT}! $highlight ? $1 : '' !gise;
 	$tmpl =~ s/\$(\w+)\$/$record->{$1}/g;



1.3.4.3   +125 -37   interchange/dist/interchange.cfg.dist


rev 1.3.4.3, prev_rev 1.3.4.2
Index: interchange.cfg.dist
===================================================================
RCS file: /var/cvs/interchange/dist/interchange.cfg.dist,v
retrieving revision 1.3.4.2
retrieving revision 1.3.4.3
diff -u -r1.3.4.2 -r1.3.4.3
--- interchange.cfg.dist	16 Jan 2001 21:37:53 -0000	1.3.4.2
+++ interchange.cfg.dist	25 Jan 2003 22:20:38 -0000	1.3.4.3
@@ -1,63 +1,151 @@
-#Catalog   construct /var/lib/interchange/catalogs/construct /cgi-bin/construct
+#========================================================================#
 
-# Set to 1 to include UI
-Variable   UI   1
+# interchange.cfg
+# See 'icconfig' document for details.
 
-# Set to "low" or "high" to get different server parameters
-Variable   TRAFFIC    low
-#Variable   TRAFFIC    high
+#========================================================================#
+
+# These settings all affect other configuration directives below.
+
+AutoVariable Windows LockType
+
+# Set to 1 to include back-end administration interface.
+Variable  UI  1
+
+# Set to "low", "high", or "rpc" to get different server parameters.
+Variable  TRAFFIC  low
+
+# Set to 1 to send extra debugging info to file /tmp/icdebug
+# and get a dump of global and catalog data structures.
+#Variable  DEBUG  1
+
+#========================================================================#
+
+# Set up individual catalogs here.
+
+#Catalog  store  /var/lib/interchange/store  /cgi-bin/store
+
+#========================================================================#
+
+# Require an external module
+
+# This one tests the realtime payment gateway code, uncomment to test.
+## Require module Vend::Payment::TestPayment
+
+#========================================================================#
+
+# Disable old C-style meta-directives like #ifdef, #endif, and #include.
+ConfigParseComments No
 
 Environment  MOD_PERL
 
-# Prevent arbitrary [file ...] and [include ...] among other things
-NoAbsolute  Yes
+# Prevent arbitrary [file ...] and [include ...] among other things.
+NoAbsolute Yes
+
+#========================================================================#
 
-#Uncomment to log to debug file /tmp/icdebug
-#Variable   DEBUG     1
+ifdef @DEBUG
 
-# You can set the Variable DEBUG above then tail -f the DebugFile
-# You can also see Interchange and catalog data structures
-#ifdef @DEBUG
 Message Sending debug to /tmp/icdebug.
 DebugFile /tmp/icdebug
+
+# A few simple tests ...
 GlobalSub sub test_global_sub { return 'Test of global subroutine OK.' }
-Variable  TEST_VARIABLE Test of global variable OK.
-#endif
+Variable  TEST_VARIABLE  Test of global variable OK.
+
+# Dump global and catalog data structures to a text file at startup time.
+# See {ConfDir}/interchange.structure and {CatRoot}/{CatName}.structure.
+DumpStructure Yes
+
+# This logs DBI calls to your DebugFile.
+# It's commented out by default because it generates a lot of messages.
+#DataTrace 1
+
+endif
 
-#ifdef TRAFFIC =~ /low/i
+#========================================================================#
+
+ifdef TRAFFIC =~ /low/i
 Message Low traffic settings.
 HouseKeeping 3
 MaxServers   5
 PIDcheck     300
-#endif
+endif
 
-#ifdef TRAFFIC =~ /high/i
+ifdef TRAFFIC =~ /high/i
 Message High traffic settings.
 HouseKeeping 2
 MaxServers   10
 PIDcheck     120
-#endif
+endif
 
-# No real downside to adding this....
-Mall       Yes
+ifdef TRAFFIC =~ /rpc/i
+Message RPC traffic settings.
+PreFork             Yes
+StartServers        5
+MaxServers          0
+MaxRequestsPerChild 100
+HouseKeeping        2
+PIDcheck            120
+endif
+
+#========================================================================#
+
+# Set this so cookies are issued only for the current catalog, not for
+# the whole base domain.
+Mall  Yes
 
-# Additional Safe operations to untrap beyond the standard
-# "ftfile sort"
+# Additional Safe operations to untrap beyond the standard "ftfile sort".
 SafeUntrap  rand
 
 TcpMap 7786 -
 
-# Uses value of UI variable above
-#ifdef UI
-Message Calling UI....
-Variable UI_TAG_TITLE_BAR 1
-#include lib/UI/ui.cfg
-#endif
-
-#### Now including individual usertag files
-
-#include usertag/*
-
-
-### Include if you want non-English error messages. Not complete.
-# #include locale.error
+# Include back office administration UI if variable set above.
+ifdef UI
+Message -i -n Calling UI...
+include lib/UI/ui.cfg
+endif
+
+## This is only needed if you use Net::SMTP instead of
+## sendmail or clones
+Variable MV_SMTPHOST smtp
+
+# FreeBSD's stock Perl build dumps core if you set $0, so let's not touch it
+ifdef DOLLAR_ZERO_BUG or $^O =~ /freebsd/
+Message Running FreeBSD; disabling $0 set
+Variable MV_DOLLAR_ZERO 0
+endif
+
+# Include individual usertags.
+include usertag/*.tag
+
+# Include if you want non-English error messages. Not complete.
+# include locale.error
+
+RobotUA <<EOR
+    ATN_Worldwide, AltaVista, Arachnoidea, Aranha, Architext, Ask, Atomz,
+    BackRub, Builder, CMC, Contact, Digital*Integrity, Directory, EZResult,
+    Excite, Ferret, Fireball, Google, Gromit, Gulliver, Harvest, Hubater,
+    H?m?h?kki, INGRID, IncyWincy, Jack, KIT*Fireball, Kototoi, LWP, Lycos,
+    MegaSheep, Mercator, Nazilla, NetMechanic, NetResearchServer, NetScoop,
+    ParaSite, Refiner, RoboDude, Rover, Rutgers, Scooter, Slurp, Spyder,
+    T-H-U-N-D-E-R-S-T-O-N-E, Toutatis, Tv*Merc, Valkyrie, Voyager, WIRE,
+    Walker, Wget, WhizBang, Wire, Wombat, Yahoo, Yandex, ZyBorg, appie,
+    asterias, bot, contact, crawl, collector, fido, find, gazz, grabber,
+    griffon, archiver, legs, marvin, mirago, moget, newscan, seek, speedy,
+    spider, suke, tarantula, agent, topiclink, whowhere, winona, worm, xtreme,
+EOR
+
+RobotIP <<EOR
+    202.9.155.123,      204.152.191.41,         208.146.26.19,
+    208.146.26.233,     209.185.141.209,        209.185.141.211,
+    209.202.148.36,     209.202.148.41,         216.200.130.207,
+    216.35.103.6?,      216.35.103.70,
+EOR
+
+RobotHost <<EOR
+    *.crawler*.com,     *.excite.com,           *.googlebot.com,
+    *.infoseek.com,     *.inktomi.com,          *.inktomisearch.com,
+    *.lycos.com,        *.pa-x.dec.com,         add-url.altavista.com,
+    westinghouse-rsl-com-usa.NorthRoyalton.cw.net,
+EOR



No                   revision



No                   revision



2.2.2.1   +0 -0      interchange/dist/etc/varnames


rev 2.2.2.1, prev_rev 2.2
Index: varnames
===================================================================
RCS file: /var/cvs/interchange/dist/etc/varnames,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



No                   revision



No                   revision



2.15.2.1  +0 -5      interchange/dist/foundation/catalog.cfg


rev 2.15.2.1, prev_rev 2.15
Index: catalog.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/catalog.cfg,v
retrieving revision 2.15
retrieving revision 2.15.2.1
diff -u -r2.15 -r2.15.2.1
--- catalog.cfg	25 Jan 2003 21:24:16 -0000	2.15
+++ catalog.cfg	25 Jan 2003 22:20:41 -0000	2.15.2.1
@@ -81,11 +81,6 @@
 include dbconf/oracle/oracle.cfg
 endif
 
-ifdef SQLITE
-DatabaseDefault NO_ASCII_INDEX 1
-include dbconf/sqlite/sqlite.cfg
-endif
-
 # Default DBM if nothing else defined
 ifndef SOME_DATABASE
 include dbconf/default_db/default_db.cfg



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/backup/.empty


<<.empty: empty>>


No                   revision



No                   revision



2.4.2.1   +18 -10    interchange/dist/foundation/config/additional_fields


rev 2.4.2.1, prev_rev 2.4
Index: additional_fields
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/config/additional_fields,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1
--- additional_fields	25 Jan 2003 21:24:16 -0000	2.4
+++ additional_fields	25 Jan 2003 22:20:41 -0000	2.4.2.1
@@ -11,7 +11,7 @@
 tools	reports	none
 
 SOMESQL
-Set to 1 if you want to use MySQL, PostgreSQL, Oracle, or SQLite
+Set to 1 if you want to use MySQL, PostgreSQL, Oracle, or DB2
 	1	0
 
 {SOMESQL}MYSQL
@@ -68,7 +68,7 @@
 
 {SOMESQL and ! '__MVC_MYSQL__' and ! '__MVC_PGSQL__'}ORACLE
 Set to 1 if you want to use Oracle
-0	1
+1	0
 
 {ORACLE}SQLDSN
 DBI DSN to use
@@ -90,17 +90,25 @@
 Field name suffix for Oracle
 _field
 
-{SOMESQL and ! '__MVC_MYSQL__' and ! '__MVC_PGSQL__' and ! '__MVC_ORACLE__'}SQLITE
-Set to 1 if you want to use SQLite
-1	0
+{SOMESQL and ! '__MVC_MYSQL__' and ! '__MVC_PGSQL__' and ! '__MVC_ORACLE__'}DB2
+Set to 1 if you want to use DB2
+	1	0
 
-{SQLITE}SQLDB
-Database file to use (will be created)
-__MVC_CATROOT__/products/sqlite.db
+{DB2}SQLDB
+Database to use (will be created)
+test___MVC_CATALOGNAME__	interch
 
-{SQLITE}SQLDSN
+{DB2}SQLDSN
 DBI DSN to use
-dbi:SQLite:__MVC_SQLDB__
+dbi:DB2:__MVC_SQLDB__
+
+{DB2}SQLUSER
+Username for DB2 (if any)
+	__MVC_CATALOGNAME__	__MVC_CATUSER__	interch
+
+{DB2}SQLPASS
+Password for DB2 (if any)
+	pass
 
 SUPERUSER
 Account name that will control this catalog



2.1.2.1   +0 -0      interchange/dist/foundation/config/additional_help


rev 2.1.2.1, prev_rev 2.1
Index: additional_help
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/config/additional_help,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.4.1   +0 -0      interchange/dist/foundation/config/installsample


rev 2.1.4.1, prev_rev 2.1
Index: installsample
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/config/installsample,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.5.2.1   +0 -0      interchange/dist/foundation/config/makedirs


rev 2.5.2.1, prev_rev 2.5
Index: makedirs
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/config/makedirs,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/config/postcopy_commands


rev 2.0.4.1, prev_rev 2.0
Index: postcopy_commands
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/config/postcopy_commands,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/config/precopy_commands


rev 2.1.2.1, prev_rev 2.1
Index: precopy_commands
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/config/precopy_commands,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/2ndDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: 2ndDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/2ndDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/Ground.dbm


rev 2.0.4.1, prev_rev 2.0
Index: Ground.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/Ground.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/NextDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: NextDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/NextDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/access.dbm


rev 2.0.4.1, prev_rev 2.0
Index: access.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/access.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/affiliate.dbm


rev 2.0.4.1, prev_rev 2.0
Index: affiliate.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/affiliate.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/area.dbm


rev 2.0.4.1, prev_rev 2.0
Index: area.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/area.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/cat.dbm


rev 2.0.4.1, prev_rev 2.0
Index: cat.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/cat.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/component.dbm


rev 2.0.4.1, prev_rev 2.0
Index: component.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/component.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/country.dbm


rev 2.0.4.1, prev_rev 2.0
Index: country.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/country.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/default_db.cfg


rev 2.0.4.1, prev_rev 2.0
Index: default_db.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/default_db.cfg,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/default_db/forum.dbm


rev 1.1.2.1, prev_rev 1.1
Index: forum.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/forum.dbm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/gift_certs.dbm


rev 2.0.4.1, prev_rev 2.0
Index: gift_certs.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/gift_certs.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/inventory.dbm


rev 2.0.4.1, prev_rev 2.0
Index: inventory.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/inventory.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/locale.dbm


rev 2.0.4.1, prev_rev 2.0
Index: locale.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/locale.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/merchandising.dbm


rev 2.0.4.1, prev_rev 2.0
Index: merchandising.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/merchandising.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/mv_metadata.dbm


rev 2.0.4.1, prev_rev 2.0
Index: mv_metadata.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/mv_metadata.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/options.dbm


rev 2.0.4.1, prev_rev 2.0
Index: options.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/options.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/order_returns.dbm


rev 2.0.4.1, prev_rev 2.0
Index: order_returns.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/order_returns.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/orderline.dbm


rev 2.0.4.1, prev_rev 2.0
Index: orderline.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/orderline.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/pricing.dbm


rev 2.0.4.1, prev_rev 2.0
Index: pricing.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/pricing.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/products.dbm


rev 2.0.4.1, prev_rev 2.0
Index: products.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/products.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/state.dbm


rev 2.0.4.1, prev_rev 2.0
Index: state.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/state.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/default_db/survey.dbm


rev 1.1.2.1, prev_rev 1.1
Index: survey.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/survey.dbm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/transactions.dbm


rev 2.0.4.1, prev_rev 2.0
Index: transactions.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/transactions.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/default_db/tree.dbm


rev 1.1.2.1, prev_rev 1.1
Index: tree.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/tree.dbm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/userdb.dbm


rev 2.0.4.1, prev_rev 2.0
Index: userdb.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/userdb.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/default_db/variable.dbm


rev 2.0.4.1, prev_rev 2.0
Index: variable.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/default_db/variable.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/locales/de_DE.cfg


rev 1.1.2.1, prev_rev 1.1
Index: de_DE.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/locales/de_DE.cfg,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/dbconf/locales/default.cfg


rev 1.2.2.1, prev_rev 1.2
Index: default.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/locales/default.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/2ndDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: 2ndDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/2ndDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/Ground.dbm


rev 2.0.4.1, prev_rev 2.0
Index: Ground.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/Ground.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/NextDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: NextDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/NextDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/access.dbm


rev 2.0.4.1, prev_rev 2.0
Index: access.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/access.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/affiliate.mysql


rev 2.1.2.1, prev_rev 2.1
Index: affiliate.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/affiliate.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/area.mysql


rev 2.1.2.1, prev_rev 2.1
Index: area.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/area.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/cat.mysql


rev 2.1.2.1, prev_rev 2.1
Index: cat.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/cat.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/component.dbm


rev 2.0.4.1, prev_rev 2.0
Index: component.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/component.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/country.mysql


rev 2.2.2.1, prev_rev 2.2
Index: country.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/country.mysql,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/forum.mysql


rev 1.2.2.1, prev_rev 1.2
Index: forum.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/forum.mysql,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/gift_certs.mysql


rev 2.1.2.1, prev_rev 2.1
Index: gift_certs.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/gift_certs.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/inventory.mysql


rev 2.1.2.1, prev_rev 2.1
Index: inventory.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/inventory.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/locale.dbm


rev 2.0.4.1, prev_rev 2.0
Index: locale.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/locale.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/merchandising.mysql


rev 2.1.2.1, prev_rev 2.1
Index: merchandising.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/merchandising.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/mv_metadata.dbm


rev 2.0.4.1, prev_rev 2.0
Index: mv_metadata.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/mv_metadata.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/mysql.cfg


rev 2.2.2.1, prev_rev 2.2
Index: mysql.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/mysql.cfg,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/options.mysql


rev 2.2.2.1, prev_rev 2.2
Index: options.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/options.mysql,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/order_returns.mysql


rev 2.1.2.1, prev_rev 2.1
Index: order_returns.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/order_returns.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/orderline.mysql


rev 2.3.2.1, prev_rev 2.3
Index: orderline.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/orderline.mysql,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/pricing.mysql


rev 2.1.2.1, prev_rev 2.1
Index: pricing.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/pricing.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/products.mysql


rev 2.1.2.1, prev_rev 2.1
Index: products.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/products.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/state.mysql


rev 2.1.2.1, prev_rev 2.1
Index: state.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/state.mysql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/survey.dbm


rev 1.1.2.1, prev_rev 1.1
Index: survey.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/survey.dbm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.5.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/transactions.mysql


rev 2.5.2.1, prev_rev 2.5
Index: transactions.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/transactions.mysql,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/tree.mysql


rev 1.3.2.1, prev_rev 1.3
Index: tree.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/tree.mysql,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/dbconf/mysql/userdb.mysql


rev 2.3.2.1, prev_rev 2.3
Index: userdb.mysql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/userdb.mysql,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/mysql/variable.dbm


rev 2.0.4.1, prev_rev 2.0
Index: variable.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/mysql/variable.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/2ndDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: 2ndDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/2ndDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/Ground.dbm


rev 2.0.4.1, prev_rev 2.0
Index: Ground.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/Ground.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/NextDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: NextDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/NextDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/access.dbm


rev 2.0.4.1, prev_rev 2.0
Index: access.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/access.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/affiliate.ora


rev 2.0.4.1, prev_rev 2.0
Index: affiliate.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/affiliate.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/area.ora


rev 2.0.4.1, prev_rev 2.0
Index: area.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/area.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/cat.ora


rev 2.0.4.1, prev_rev 2.0
Index: cat.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/cat.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/component.dbm


rev 2.0.4.1, prev_rev 2.0
Index: component.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/component.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/dbconf/oracle/country.ora


rev 2.2.2.1, prev_rev 2.2
Index: country.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/country.ora,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/gift_certs.ora


rev 2.0.4.1, prev_rev 2.0
Index: gift_certs.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/gift_certs.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/inventory.ora


rev 2.0.4.1, prev_rev 2.0
Index: inventory.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/inventory.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/locale.dbm


rev 2.0.4.1, prev_rev 2.0
Index: locale.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/locale.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/merchandising.ora


rev 2.0.4.1, prev_rev 2.0
Index: merchandising.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/merchandising.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/mv_metadata.dbm


rev 2.0.4.1, prev_rev 2.0
Index: mv_metadata.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/mv_metadata.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/dbconf/oracle/options.ora


rev 2.2.2.1, prev_rev 2.2
Index: options.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/options.ora,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/oracle.cfg


rev 2.1.4.1, prev_rev 2.1
Index: oracle.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/oracle.cfg,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/order_returns.ora


rev 2.0.4.1, prev_rev 2.0
Index: order_returns.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/order_returns.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/oracle/orderline.ora


rev 2.1.2.1, prev_rev 2.1
Index: orderline.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/orderline.ora,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/pricing.ora


rev 2.0.4.1, prev_rev 2.0
Index: pricing.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/pricing.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/products.ora


rev 2.0.4.1, prev_rev 2.0
Index: products.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/products.ora,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/oracle/state.ora


rev 2.1.2.1, prev_rev 2.1
Index: state.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/state.ora,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/oracle/survey.dbm


rev 1.1.2.1, prev_rev 1.1
Index: survey.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/survey.dbm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.4.2.1   +0 -0      interchange/dist/foundation/dbconf/oracle/transactions.ora


rev 2.4.2.1, prev_rev 2.4
Index: transactions.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/transactions.ora,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1



1.3.2.1   +1 -1      interchange/dist/foundation/dbconf/oracle/tree.ora


rev 1.3.2.1, prev_rev 1.3
Index: tree.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/tree.ora,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1
--- tree.ora	23 Jan 2003 18:01:22 -0000	1.3
+++ tree.ora	25 Jan 2003 22:20:43 -0000	1.3.2.1
@@ -13,7 +13,7 @@
 Database  tree  COLUMN_DEF   "parent_fld=varchar(20)"
 Database  tree  COLUMN_DEF   "msort=varchar(8)"
 Database  tree  COLUMN_DEF   "extended=varchar2(4000)"
-Database  tree  COLUMN_DEF   "inactive=int default 0 not null"
+Database  tree  COLUMN_DEF   "inactive=int not null default 0"
 Database  tree  COLUMN_DEF   "member=varchar(1)"
 Database  tree  INDEX        parent_fld
 Database  tree  INDEX        mgroup



2.2.2.1   +0 -0      interchange/dist/foundation/dbconf/oracle/userdb.ora


rev 2.2.2.1, prev_rev 2.2
Index: userdb.ora
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/userdb.ora,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/oracle/variable.dbm


rev 2.0.4.1, prev_rev 2.0
Index: variable.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/oracle/variable.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/2ndDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: 2ndDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/2ndDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/Ground.dbm


rev 2.0.4.1, prev_rev 2.0
Index: Ground.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/Ground.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/NextDayAir.dbm


rev 2.0.4.1, prev_rev 2.0
Index: NextDayAir.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/NextDayAir.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/access.dbm


rev 2.0.4.1, prev_rev 2.0
Index: access.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/access.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/affiliate.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: affiliate.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/affiliate.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/area.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: area.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/area.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/cat.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: cat.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/cat.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/component.dbm


rev 2.0.4.1, prev_rev 2.0
Index: component.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/component.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/country.pgsql


rev 2.1.2.1, prev_rev 2.1
Index: country.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/country.pgsql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/forum.pgsql


rev 1.1.2.1, prev_rev 1.1
Index: forum.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/forum.pgsql,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/gift_certs.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: gift_certs.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/gift_certs.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/inventory.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: inventory.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/inventory.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/locale.dbm


rev 2.0.4.1, prev_rev 2.0
Index: locale.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/locale.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/merchandising.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: merchandising.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/merchandising.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/mv_metadata.dbm


rev 2.0.4.1, prev_rev 2.0
Index: mv_metadata.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/mv_metadata.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/options.pgsql


rev 2.2.2.1, prev_rev 2.2
Index: options.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/options.pgsql,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/order_returns.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: order_returns.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/order_returns.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.3.2.1   +4 -4      interchange/dist/foundation/dbconf/pgsql/orderline.pgsql


rev 2.3.2.1, prev_rev 2.3
Index: orderline.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/orderline.pgsql,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1
--- orderline.pgsql	23 Jan 2003 19:05:50 -0000	2.3
+++ orderline.pgsql	25 Jan 2003 22:20:44 -0000	2.3.2.1
@@ -18,11 +18,11 @@
 Database  orderline  COLUMN_DEF   "subtotal=varchar(12) NOT NULL"
 Database  orderline  COLUMN_DEF   "shipping=varchar(12)"
 Database  orderline  COLUMN_DEF   "taxable=varchar(3)"
-Database  orderline  COLUMN_DEF   "size=varchar(255)"
-Database  orderline  COLUMN_DEF   "color=varchar(255)"
-Database  orderline  COLUMN_DEF   "options=text"
+Database  orderline  COLUMN_DEF   "size=varchar(30)"
+Database  orderline  COLUMN_DEF   "color=varchar(30)"
+Database  orderline  COLUMN_DEF   "options=varchar(255)"
 Database  orderline  COLUMN_DEF   "order_date=varchar(32) NOT NULL"
 Database  orderline  COLUMN_DEF   "update_date=timestamp"
-Database  orderline  COLUMN_DEF   "status=varchar(64)"
+Database  orderline  COLUMN_DEF   "status=varchar(32)"
 Database  orderline  COLUMN_DEF   "parent=varchar(9)"
 Database  orderline  INDEX         store_id order_number



2.1.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/pgsql.cfg


rev 2.1.4.1, prev_rev 2.1
Index: pgsql.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/pgsql.cfg,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/pricing.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: pricing.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/pricing.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/products.pgsql


rev 2.1.2.1, prev_rev 2.1
Index: products.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/products.pgsql,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/state.pgsql


rev 2.0.4.1, prev_rev 2.0
Index: state.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/state.pgsql,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/survey.dbm


rev 1.1.2.1, prev_rev 1.1
Index: survey.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/survey.dbm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.5.2.1   +29 -32    interchange/dist/foundation/dbconf/pgsql/transactions.pgsql


rev 2.5.2.1, prev_rev 2.5
Index: transactions.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/transactions.pgsql,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1
--- transactions.pgsql	23 Jan 2003 19:05:50 -0000	2.5
+++ transactions.pgsql	25 Jan 2003 22:20:44 -0000	2.5.2.1
@@ -9,7 +9,7 @@
 Database  transactions  COLUMN_DEF   "code=VARCHAR(14) NOT NULL PRIMARY KEY"
 Database  transactions  COLUMN_DEF   "store_id=VARCHAR(9)"
 Database  transactions  COLUMN_DEF   "order_number=VARCHAR(14) NOT NULL"
-Database  transactions  COLUMN_DEF   "session=VARCHAR(64) NOT NULL"
+Database  transactions  COLUMN_DEF   "session=VARCHAR(32) NOT NULL"
 Database  transactions  COLUMN_DEF   "username=VARCHAR(20) DEFAULT '' NOT NULL"
 Database  transactions  COLUMN_DEF   "shipmode=VARCHAR(255)"
 Database  transactions  COLUMN_DEF   "nitems=VARCHAR(9) NOT NULL"
@@ -18,45 +18,42 @@
 Database  transactions  COLUMN_DEF   "handling=VARCHAR(12)"
 Database  transactions  COLUMN_DEF   "salestax=VARCHAR(12)"
 Database  transactions  COLUMN_DEF   "total_cost=VARCHAR(16) NOT NULL"
-Database  transactions  COLUMN_DEF   "fname=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "lname=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "company=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "address1=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "address2=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "city=VARCHAR(128) NOT NULL"
-Database  transactions  COLUMN_DEF   "state=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "zip=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "country=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "phone_day=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "phone_night=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "fax=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "email=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "b_fname=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "b_lname=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "b_company=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "b_address1=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "b_address2=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "b_city=VARCHAR(128)"
-Database  transactions  COLUMN_DEF   "b_state=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "b_zip=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "b_country=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "b_phone=VARCHAR(32)"
-Database  transactions  COLUMN_DEF   "payment_method=varchar(255)"
-Database  transactions  COLUMN_DEF   "avs=varchar(255)"
+Database  transactions  COLUMN_DEF   "fname=VARCHAR(30)"
+Database  transactions  COLUMN_DEF   "lname=VARCHAR(30)"
+Database  transactions  COLUMN_DEF   "company=VARCHAR(30)"
+Database  transactions  COLUMN_DEF   "address1=VARCHAR(64)"
+Database  transactions  COLUMN_DEF   "address2=VARCHAR(64)"
+Database  transactions  COLUMN_DEF   "city=VARCHAR(30) NOT NULL"
+Database  transactions  COLUMN_DEF   "state=VARCHAR(10)"
+Database  transactions  COLUMN_DEF   "zip=VARCHAR(10)"
+Database  transactions  COLUMN_DEF   "country=VARCHAR(10)"
+Database  transactions  COLUMN_DEF   "phone_day=VARCHAR(20)"
+Database  transactions  COLUMN_DEF   "phone_night=VARCHAR(20)"
+Database  transactions  COLUMN_DEF   "fax=VARCHAR(20)"
+Database  transactions  COLUMN_DEF   "email=VARCHAR(42)"
+Database  transactions  COLUMN_DEF   "b_fname=VARCHAR(30)"
+Database  transactions  COLUMN_DEF   "b_lname=VARCHAR(30)"
+Database  transactions  COLUMN_DEF   "b_company=VARCHAR(30)"
+Database  transactions  COLUMN_DEF   "b_address1=VARCHAR(64)"
+Database  transactions  COLUMN_DEF   "b_address2=VARCHAR(64)"
+Database  transactions  COLUMN_DEF   "b_city=VARCHAR(30)"
+Database  transactions  COLUMN_DEF   "b_state=VARCHAR(10)"
+Database  transactions  COLUMN_DEF   "b_zip=VARCHAR(10)"
+Database  transactions  COLUMN_DEF   "b_country=VARCHAR(10)"
+Database  transactions  COLUMN_DEF   "b_phone=VARCHAR(20)"
+Database  transactions  COLUMN_DEF   "payment_method=varchar(128)"
+Database  transactions  COLUMN_DEF   "avs=varchar(32)"
 Database  transactions  COLUMN_DEF   "order_id=varchar(32)"
 Database  transactions  COLUMN_DEF   "auth_code=varchar(32)"
 Database  transactions  COLUMN_DEF   "tracking_number=varchar(64)"
 Database  transactions  COLUMN_DEF   "order_date=varchar(32) NOT NULL"
 Database  transactions  COLUMN_DEF   "update_date=timestamp"
-Database  transactions  COLUMN_DEF   "archived=varchar(1) DEFAULT ''"
-Database  transactions  COLUMN_DEF   "deleted=varchar(1) DEFAULT ''"
-Database  transactions  COLUMN_DEF   "complete=varchar(1) DEFAULT ''"
+Database  transactions  COLUMN_DEF   "archived=CHAR(1) DEFAULT ''"
+Database  transactions  COLUMN_DEF   "deleted=CHAR(1) DEFAULT ''"
+Database  transactions  COLUMN_DEF   "complete=CHAR(1) DEFAULT ''"
 Database  transactions  COLUMN_DEF   "status=VARCHAR(32)"
 Database  transactions  COLUMN_DEF   "parent=VARCHAR(9)"
 Database  transactions  COLUMN_DEF   "comments=text"
 Database  transactions  COLUMN_DEF   "currency_locale=varchar(32)"
 Database  transactions  INDEX         store_id
 Database  transactions  INDEX         order_number
-Database  transactions  INDEX         order_date
-Database  transactions  INDEX         archived
-Database  transactions  INDEX         deleted



1.2.2.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/tree.pgsql


rev 1.2.2.1, prev_rev 1.2
Index: tree.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/tree.pgsql,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



2.4.2.1   +25 -25    interchange/dist/foundation/dbconf/pgsql/userdb.pgsql


rev 2.4.2.1, prev_rev 2.4
Index: userdb.pgsql
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/userdb.pgsql,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1
--- userdb.pgsql	23 Jan 2003 19:05:50 -0000	2.4
+++ userdb.pgsql	25 Jan 2003 22:20:44 -0000	2.4.2.1
@@ -6,41 +6,41 @@
 Database  userdb  PASS         __SQLPASS__
 endif
 Database  userdb  DEFAULT_TYPE  VARCHAR(255)
-Database  userdb  COLUMN_DEF   "username=VARCHAR(20) NOT NULL PRIMARY KEY"
+Database  userdb  COLUMN_DEF   "code=VARCHAR(20) NOT NULL PRIMARY KEY"
 Database  userdb  COLUMN_DEF   "password=VARCHAR(20)"
 Database  userdb  COLUMN_DEF   "acl=text"
 Database  userdb  COLUMN_DEF   "mod_time=varchar(20)"
 Database  userdb  COLUMN_DEF   "s_nickname=text"
-Database  userdb  COLUMN_DEF   "company=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "fname=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "lname=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "address1=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "address2=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "address3=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "city=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "state=VARCHAR(32)"
-Database  userdb  COLUMN_DEF   "zip=VARCHAR(32)"
-Database  userdb  COLUMN_DEF   "country=VARCHAR(32)"
-Database  userdb  COLUMN_DEF   "phone_day=VARCHAR(32)"
+Database  userdb  COLUMN_DEF   "company=VARCHAR(30)"
+Database  userdb  COLUMN_DEF   "fname=VARCHAR(30)"
+Database  userdb  COLUMN_DEF   "lname=VARCHAR(30)"
+Database  userdb  COLUMN_DEF   "address1=VARCHAR(64)"
+Database  userdb  COLUMN_DEF   "address2=VARCHAR(64)"
+Database  userdb  COLUMN_DEF   "address3=VARCHAR(64)"
+Database  userdb  COLUMN_DEF   "city=VARCHAR(30)"
+Database  userdb  COLUMN_DEF   "state=VARCHAR(10)"
+Database  userdb  COLUMN_DEF   "zip=VARCHAR(10)"
+Database  userdb  COLUMN_DEF   "country=VARCHAR(10)"
+Database  userdb  COLUMN_DEF   "phone_day=VARCHAR(20)"
 Database  userdb  COLUMN_DEF   "mv_shipmode=VARCHAR(255)"
 Database  userdb  COLUMN_DEF   "b_nickname=text"
-Database  userdb  COLUMN_DEF   "b_fname=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "b_lname=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "b_address1=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "b_address2=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "b_address3=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "b_city=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "b_state=VARCHAR(32)"
-Database  userdb  COLUMN_DEF   "b_zip=VARCHAR(32)"
-Database  userdb  COLUMN_DEF   "b_country=VARCHAR(32)"
-Database  userdb  COLUMN_DEF   "b_phone=VARCHAR(32)"
+Database  userdb  COLUMN_DEF   "b_fname=VARCHAR(30)"
+Database  userdb  COLUMN_DEF   "b_lname=VARCHAR(30)"
+Database  userdb  COLUMN_DEF   "b_address1=VARCHAR(64)"
+Database  userdb  COLUMN_DEF   "b_address2=VARCHAR(64)"
+Database  userdb  COLUMN_DEF   "b_address3=VARCHAR(64)"
+Database  userdb  COLUMN_DEF   "b_city=VARCHAR(30)"
+Database  userdb  COLUMN_DEF   "b_state=VARCHAR(10)"
+Database  userdb  COLUMN_DEF   "b_zip=VARCHAR(10)"
+Database  userdb  COLUMN_DEF   "b_country=VARCHAR(10)"
+Database  userdb  COLUMN_DEF   "b_phone=VARCHAR(20)"
 Database  userdb  COLUMN_DEF   "mv_credit_card_type=VARCHAR(16)"
 Database  userdb  COLUMN_DEF   "mv_credit_card_exp_month=VARCHAR(2)"
 Database  userdb  COLUMN_DEF   "mv_credit_card_exp_year=VARCHAR(4)"
 Database  userdb  COLUMN_DEF   "p_nickname=text"
-Database  userdb  COLUMN_DEF   "email=VARCHAR(128)"
-Database  userdb  COLUMN_DEF   "fax=VARCHAR(32)"
-Database  userdb  COLUMN_DEF   "phone_night=VARCHAR(32)"
+Database  userdb  COLUMN_DEF   "email=VARCHAR(42)"
+Database  userdb  COLUMN_DEF   "fax=VARCHAR(20)"
+Database  userdb  COLUMN_DEF   "phone_night=VARCHAR(20)"
 Database  userdb  COLUMN_DEF   "fax_order=VARCHAR(2)"
 Database  userdb  COLUMN_DEF   "address_book=TEXT"
 Database  userdb  COLUMN_DEF   "accounts=TEXT"



2.0.4.1   +0 -0      interchange/dist/foundation/dbconf/pgsql/variable.dbm


rev 2.0.4.1, prev_rev 2.0
Index: variable.dbm
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/dbconf/pgsql/variable.dbm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/etc/area.recordnumber


rev 2.0.4.1, prev_rev 2.0
Index: area.recordnumber
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/area.recordnumber,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/cat.recordnumber


rev 2.0.4.1, prev_rev 2.0
Index: cat.recordnumber
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/cat.recordnumber,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/log_entry


rev 2.0.4.1, prev_rev 2.0
Index: log_entry
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/log_entry,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.6.2.1   +0 -0      interchange/dist/foundation/etc/log_transaction


rev 2.6.2.1, prev_rev 2.6
Index: log_transaction
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/log_transaction,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/etc/mail_receipt


rev 2.1.2.1, prev_rev 2.1
Index: mail_receipt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/mail_receipt,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/order.number


rev 2.0.4.1, prev_rev 2.0
Index: order.number
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/order.number,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/profiles.login


rev 2.0.4.1, prev_rev 2.0
Index: profiles.login
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/profiles.login,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/etc/profiles.order


rev 2.1.2.1, prev_rev 2.1
Index: profiles.order
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/profiles.order,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/receipt.html


rev 2.0.4.1, prev_rev 2.0
Index: receipt.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/receipt.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/report


rev 2.0.4.1, prev_rev 2.0
Index: report
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/report,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/return.number


rev 2.0.4.1, prev_rev 2.0
Index: return.number
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/return.number,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/rma.number


rev 2.0.4.1, prev_rev 2.0
Index: rma.number
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/rma.number,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/etc/ship_notice


rev 2.0.4.1, prev_rev 2.0
Index: ship_notice
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/etc/ship_notice,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.5.2.1   +0 -0      interchange/dist/foundation/html/index.html


rev 2.5.2.1, prev_rev 2.5
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/html/index.html,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/images/bg.gif


<<bg.gif: GIF image data, version 89a, 5 x 5,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/computer.xls


<<computer.xls: Microsoft Office Document>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/construct.xls


<<construct.xls: Microsoft Office Document>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/download.png


<<download.png: PNG image data, 140 x 26, 8-bit colormap, interlaced>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fc.gif


<<fc.gif: GIF image data, version 89a, 20 x 22,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fo.gif


<<fo.gif: GIF image data, version 89a, 27 x 22,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/reports.xls


<<reports.xls: Microsoft Office Document>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/smallamex.png


<<smallamex.png: PNG image data, 36 x 23, 8-bit colormap, non-interlaced>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/smalldisc.png


<<smalldisc.png: PNG image data, 36 x 22, 8-bit colormap, interlaced>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/smallmc.png


<<smallmc.png: PNG image data, 36 x 23, 8-bit colormap, non-interlaced>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/smallvisa.png


<<smallvisa.png: PNG image data, 36 x 23, 8-bit colormap, non-interlaced>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/template.xls


<<template.xls: Microsoft Office Document>>


No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/images/affiliate/hardhat.gif


<<hardhat.gif: GIF image data, version 89a, 150 x 50,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/about.gif


<<about.gif: GIF image data, version 89a, 88 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/banner.gif


<<banner.gif: GIF image data, version 89a, 600 x 73,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/bar_filler.gif


<<bar_filler.gif: GIF image data, version 89a, 163 x 21,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/buynow.gif


<<buynow.gif: GIF image data, version 89a, 52 x 13,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/cart.gif


<<cart.gif: GIF image data, version 89a, 101 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/checkout.gif


<<checkout.gif: GIF image data, version 89a, 102 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/checkout_button.gif


<<checkout_button.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/continue_shopping.gif


<<continue_shopping.gif: GIF image data, version 89a, 118 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/gift_certificate_large.gif


<<gift_certificate_large.gif: GIF image data, version 89a, 134 x 33,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/go.gif


<<go.gif: GIF image data, version 89a, 45 x 15,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/home.gif


<<home.gif: GIF image data, version 89a, 60 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/littlebar.gif


<<littlebar.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/login.gif


<<login.gif: GIF image data, version 89a, 68 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/logo.gif


<<logo.gif: GIF image data, version 89a, 136 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/logo2.gif


<<logo2.gif: GIF image data, version 89a, 165 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/logout.gif


<<logout.gif: GIF image data, version 89a, 84 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/placeorder.gif


<<placeorder.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 117 x 28,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/recalculate_button.gif


<<recalculate_button.gif: GIF image data, version 89a, 80 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/savecart.gif


<<savecart.gif: GIF image data, version 89a, 96 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/saverecur.gif


<<saverecur.gif: GIF image data, version 89a, 147 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/search.gif


<<search.gif: GIF image data, version 89a, 44 x 14,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/sep.gif


<<sep.gif: GIF image data, version 89a, 3 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/service.gif


<<service.gif: GIF image data, version 89a, 76 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 100,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/blueyellow/yourimage.gif


<<yourimage.gif: GIF image data, version 89a, 120 x 150,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/about.gif


<<about.gif: GIF image data, version 89a, 88 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/banner.gif


<<banner.gif: GIF image data, version 89a, 600 x 73,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/bar_filler.gif


<<bar_filler.gif: GIF image data, version 89a, 163 x 21,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/buynow.gif


<<buynow.gif: GIF image data, version 89a, 52 x 13,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/cart.gif


<<cart.gif: GIF image data, version 89a, 101 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/checkout.gif


<<checkout.gif: GIF image data, version 89a, 102 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/checkout_button.gif


<<checkout_button.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/continue_shopping.gif


<<continue_shopping.gif: GIF image data, version 89a, 118 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/go.gif


<<go.gif: GIF image data, version 89a, 45 x 15,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/home.gif


<<home.gif: GIF image data, version 89a, 60 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/littlebar.gif


<<littlebar.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/login.gif


<<login.gif: GIF image data, version 89a, 68 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/logo.gif


<<logo.gif: GIF image data, version 89a, 136 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/logo2.gif


<<logo2.gif: GIF image data, version 89a, 165 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/logout.gif


<<logout.gif: GIF image data, version 89a, 84 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/placeorder.gif


<<placeorder.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 117 x 28,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/recalculate_button.gif


<<recalculate_button.gif: GIF image data, version 89a, 80 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/savecart.gif


<<savecart.gif: GIF image data, version 89a, 96 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/saverecur.gif


<<saverecur.gif: GIF image data, version 89a, 147 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/search.gif


<<search.gif: GIF image data, version 89a, 44 x 14,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/sep.gif


<<sep.gif: GIF image data, version 89a, 3 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/service.gif


<<service.gif: GIF image data, version 89a, 76 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 100,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/fixedwidth/yourimage.gif


<<yourimage.gif: GIF image data, version 89a, 120 x 150,>>


No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/about.gif


<<about.gif: GIF image data, version 89a, 88 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/buynow.gif


<<buynow.gif: GIF image data, version 89a, 52 x 13,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/cart.gif


<<cart.gif: GIF image data, version 89a, 101 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/checkout.gif


<<checkout.gif: GIF image data, version 89a, 102 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/checkout_button.gif


<<checkout_button.gif: GIF image data, version 89a, 90 x 25,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/go.gif


<<go.gif: GIF image data, version 89a, 45 x 15,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/home.gif


<<home.gif: GIF image data, version 89a, 60 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/littlebar.gif


<<littlebar.gif: GIF image data, version 89a, 1 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/login.gif


<<login.gif: GIF image data, version 89a, 68 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/logo.gif


<<logo.gif: GIF image data, version 89a, 136 x 60,>>


2.1.2.1   +0 -0      interchange/dist/foundation/images/foundation/logo2.gif


<<logo2.gif: GIF image data, version 89a, 165 x 60,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/logout.gif


<<logout.gif: GIF image data, version 89a, 84 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/placeorder.gif


<<placeorder.gif: GIF image data, version 89a, 90 x 25,>>


2.1.2.1   +0 -0      interchange/dist/foundation/images/foundation/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 117 x 28,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/recalculate_button.gif


<<recalculate_button.gif: GIF image data, version 89a, 80 x 18,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/savecart.gif


<<savecart.gif: GIF image data, version 89a, 96 x 18,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/saverecur.gif


<<saverecur.gif: GIF image data, version 89a, 147 x 18,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/sep.gif


<<sep.gif: GIF image data, version 89a, 3 x 25,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/service.gif


<<service.gif: GIF image data, version 89a, 76 x 20,>>


2.0.4.1   +0 -0      interchange/dist/foundation/images/foundation/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 80,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/about.gif


<<about.gif: GIF image data, version 89a, 88 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/banner.gif


<<banner.gif: GIF image data, version 89a, 600 x 73,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/bar_filler.gif


<<bar_filler.gif: GIF image data, version 89a, 163 x 21,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/buynow.gif


<<buynow.gif: GIF image data, version 89a, 52 x 13,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/cart.gif


<<cart.gif: GIF image data, version 89a, 101 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/checkout.gif


<<checkout.gif: GIF image data, version 89a, 102 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/checkout_button.gif


<<checkout_button.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/continue_shopping.gif


<<continue_shopping.gif: GIF image data, version 89a, 118 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/gift_certificate_large.gif


<<gift_certificate_large.gif: GIF image data, version 89a, 134 x 33,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/go.gif


<<go.gif: GIF image data, version 89a, 45 x 15,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/home.gif


<<home.gif: GIF image data, version 89a, 60 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/littlebar.gif


<<littlebar.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/login.gif


<<login.gif: GIF image data, version 89a, 68 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/logo.gif


<<logo.gif: GIF image data, version 89a, 136 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/logo2.gif


<<logo2.gif: GIF image data, version 89a, 165 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/logout.gif


<<logout.gif: GIF image data, version 89a, 84 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/placeorder.gif


<<placeorder.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 117 x 28,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/recalculate_button.gif


<<recalculate_button.gif: GIF image data, version 89a, 80 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/savecart.gif


<<savecart.gif: GIF image data, version 89a, 96 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/saverecur.gif


<<saverecur.gif: GIF image data, version 89a, 147 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/search.gif


<<search.gif: GIF image data, version 89a, 44 x 14,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/sep.gif


<<sep.gif: GIF image data, version 89a, 3 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/service.gif


<<service.gif: GIF image data, version 89a, 76 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 100,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayorange/yourimage.gif


<<yourimage.gif: GIF image data, version 89a, 120 x 150,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/about.gif


<<about.gif: GIF image data, version 89a, 88 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/banner.gif


<<banner.gif: GIF image data, version 89a, 600 x 73,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/bar_filler.gif


<<bar_filler.gif: GIF image data, version 89a, 163 x 21,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/buynow.gif


<<buynow.gif: GIF image data, version 89a, 52 x 13,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/cart.gif


<<cart.gif: GIF image data, version 89a, 101 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/checkout.gif


<<checkout.gif: GIF image data, version 89a, 102 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/checkout_button.gif


<<checkout_button.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/continue_shopping.gif


<<continue_shopping.gif: GIF image data, version 89a, 118 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/gift_certificate_large.gif


<<gift_certificate_large.gif: GIF image data, version 89a, 134 x 33,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/go.gif


<<go.gif: GIF image data, version 89a, 45 x 15,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/home.gif


<<home.gif: GIF image data, version 89a, 60 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/littlebar.gif


<<littlebar.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/login.gif


<<login.gif: GIF image data, version 89a, 68 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/logo.gif


<<logo.gif: GIF image data, version 89a, 136 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/logo2.gif


<<logo2.gif: GIF image data, version 89a, 165 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/logout.gif


<<logout.gif: GIF image data, version 89a, 84 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/placeorder.gif


<<placeorder.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 117 x 28,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/recalculate_button.gif


<<recalculate_button.gif: GIF image data, version 89a, 80 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/savecart.gif


<<savecart.gif: GIF image data, version 89a, 96 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/saverecur.gif


<<saverecur.gif: GIF image data, version 89a, 147 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/search.gif


<<search.gif: GIF image data, version 89a, 44 x 14,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/sep.gif


<<sep.gif: GIF image data, version 89a, 3 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/service.gif


<<service.gif: GIF image data, version 89a, 76 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 100,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/grayscale/yourimage.gif


<<yourimage.gif: GIF image data, version 89a, 120 x 150,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/about.gif


<<about.gif: GIF image data, version 89a, 88 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/banner.gif


<<banner.gif: GIF image data, version 89a, 600 x 73,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/bar_filler.gif


<<bar_filler.gif: GIF image data, version 89a, 163 x 21,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/buynow.gif


<<buynow.gif: GIF image data, version 89a, 52 x 13,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/cart.gif


<<cart.gif: GIF image data, version 89a, 101 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/checkout.gif


<<checkout.gif: GIF image data, version 89a, 102 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/checkout_button.gif


<<checkout_button.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/continue_shopping.gif


<<continue_shopping.gif: GIF image data, version 89a, 118 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/gift_certificate_large.gif


<<gift_certificate_large.gif: GIF image data, version 89a, 134 x 33,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/go.gif


<<go.gif: GIF image data, version 89a, 45 x 15,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/home.gif


<<home.gif: GIF image data, version 89a, 60 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/littlebar.gif


<<littlebar.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/login.gif


<<login.gif: GIF image data, version 89a, 68 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/logo.gif


<<logo.gif: GIF image data, version 89a, 136 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/logo2.gif


<<logo2.gif: GIF image data, version 89a, 165 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/logout.gif


<<logout.gif: GIF image data, version 89a, 84 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/placeorder.gif


<<placeorder.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 117 x 28,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/recalculate_button.gif


<<recalculate_button.gif: GIF image data, version 89a, 80 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/savecart.gif


<<savecart.gif: GIF image data, version 89a, 96 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/saverecur.gif


<<saverecur.gif: GIF image data, version 89a, 147 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/search.gif


<<search.gif: GIF image data, version 89a, 44 x 14,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/sep.gif


<<sep.gif: GIF image data, version 89a, 3 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/service.gif


<<service.gif: GIF image data, version 89a, 76 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 100,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/greens/yourimage.gif


<<yourimage.gif: GIF image data, version 89a, 120 x 150,>>


No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/images/items/yourimage.gif


<<yourimage.gif: GIF image data, version 89a, 325 x 325,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/about.gif


<<about.gif: GIF image data, version 89a, 88 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/banner.gif


<<banner.gif: GIF image data, version 89a, 600 x 73,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/bar_filler.gif


<<bar_filler.gif: GIF image data, version 89a, 163 x 21,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/buynow.gif


<<buynow.gif: GIF image data, version 89a, 52 x 13,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/cart.gif


<<cart.gif: GIF image data, version 89a, 101 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/checkout.gif


<<checkout.gif: GIF image data, version 89a, 102 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/checkout_button.gif


<<checkout_button.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/continue_shopping.gif


<<continue_shopping.gif: GIF image data, version 89a, 118 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/gift_certificate_large.gif


<<gift_certificate_large.gif: GIF image data, version 89a, 134 x 33,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/go.gif


<<go.gif: GIF image data, version 89a, 45 x 15,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/home.gif


<<home.gif: GIF image data, version 89a, 60 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/littlebar.gif


<<littlebar.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/login.gif


<<login.gif: GIF image data, version 89a, 68 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/logo.gif


<<logo.gif: GIF image data, version 89a, 136 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/logo2.gif


<<logo2.gif: GIF image data, version 89a, 165 x 60,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/logout.gif


<<logout.gif: GIF image data, version 89a, 84 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/placeorder.gif


<<placeorder.gif: GIF image data, version 89a, 90 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 117 x 28,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/recalculate_button.gif


<<recalculate_button.gif: GIF image data, version 89a, 80 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/savecart.gif


<<savecart.gif: GIF image data, version 89a, 96 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/saverecur.gif


<<saverecur.gif: GIF image data, version 89a, 147 x 18,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/search.gif


<<search.gif: GIF image data, version 89a, 44 x 14,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/sep.gif


<<sep.gif: GIF image data, version 89a, 3 x 25,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/service.gif


<<service.gif: GIF image data, version 89a, 76 x 20,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 100,>>


1.1.2.1   +0 -0      interchange/dist/foundation/images/purpleyellow/yourimage.gif


<<yourimage.gif: GIF image data, version 89a, 120 x 150,>>


No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/images/thumb/thumb.gif


<<thumb.gif: GIF image data, version 89a, 80 x 80,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/include/checkout/billing_address


rev 1.1.2.1, prev_rev 1.1
Index: billing_address
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/billing_address,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/include/checkout/initialization


rev 1.2.2.1, prev_rev 1.2
Index: initialization
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/initialization,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/include/checkout/login_form


rev 1.1.2.1, prev_rev 1.1
Index: login_form
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/login_form,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/include/checkout/mailing_status


rev 1.1.2.1, prev_rev 1.1
Index: mailing_status
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/mailing_status,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/include/checkout/new_browser_payment


rev 1.2.2.1, prev_rev 1.2
Index: new_browser_payment
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/new_browser_payment,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/include/checkout/old_browser_payment


rev 1.1.2.1, prev_rev 1.1
Index: old_browser_payment
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/old_browser_payment,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/include/checkout/payment_select


rev 1.1.2.1, prev_rev 1.1
Index: payment_select
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/payment_select,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/include/checkout/shipping_address


rev 1.2.2.1, prev_rev 1.2
Index: shipping_address
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/shipping_address,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/include/checkout/shopping_cart


rev 1.1.2.1, prev_rev 1.1
Index: shopping_cart
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/shopping_cart,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/include/checkout/tax_popup


rev 1.1.2.1, prev_rev 1.1
Index: tax_popup
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/checkout/tax_popup,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/include/forum/reply_form


rev 1.1.2.1, prev_rev 1.1
Index: reply_form
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/forum/reply_form,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/include/forum/submit_form


rev 1.1.2.1, prev_rev 1.1
Index: submit_form
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/include/forum/submit_form,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



2.2.2.1   +0 -0      interchange/dist/foundation/pages/aboutus.html


rev 2.2.2.1, prev_rev 2.2
Index: aboutus.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/aboutus.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.5.2.1   +0 -0      interchange/dist/foundation/pages/account.html


rev 2.5.2.1, prev_rev 2.5
Index: account.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/account.html,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/pages/advancedsearch.html


rev 2.2.2.1, prev_rev 2.2
Index: advancedsearch.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/advancedsearch.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/pages/browse.html


rev 2.2.2.1, prev_rev 2.2
Index: browse.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/browse.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/pages/canceled.html


rev 2.2.2.1, prev_rev 2.2
Index: canceled.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/canceled.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/change_password.html


rev 2.0.4.1, prev_rev 2.0
Index: change_password.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/change_password.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/pages/contact.html


rev 2.2.2.1, prev_rev 2.2
Index: contact.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/contact.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/customerservice.html


rev 2.1.2.1, prev_rev 2.1
Index: customerservice.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/customerservice.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/deliver.html


rev 2.0.4.1, prev_rev 2.0
Index: deliver.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/deliver.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.3.2.1   +0 -0      interchange/dist/foundation/pages/flypage.html


rev 2.3.2.1, prev_rev 2.3
Index: flypage.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/flypage.html,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/help.html


rev 2.0.4.1, prev_rev 2.0
Index: help.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/help.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/index.html


rev 2.1.2.1, prev_rev 2.1
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/index.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/pages/login.html


rev 2.3.2.1, prev_rev 2.3
Index: login.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/login.html,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/logout.html


rev 2.1.2.1, prev_rev 2.1
Index: logout.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/logout.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/lost_password.html


rev 2.0.4.1, prev_rev 2.0
Index: lost_password.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/lost_password.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/modular_modify.html


rev 2.0.4.1, prev_rev 2.0
Index: modular_modify.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/modular_modify.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/pages/new_account.html


rev 2.2.2.1, prev_rev 2.2
Index: new_account.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/new_account.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/privacypolicy.html


rev 2.0.4.1, prev_rev 2.0
Index: privacypolicy.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/privacypolicy.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/process_return.html


rev 2.0.4.1, prev_rev 2.0
Index: process_return.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/process_return.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/quantity.html


rev 2.0.4.1, prev_rev 2.0
Index: quantity.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/quantity.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.6.2.1   +0 -0      interchange/dist/foundation/pages/results.html


rev 2.6.2.1, prev_rev 2.6
Index: results.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/results.html,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1



2.5.2.1   +0 -0      interchange/dist/foundation/pages/results_big.html


rev 2.5.2.1, prev_rev 2.5
Index: results_big.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/results_big.html,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/returns.html


rev 2.1.2.1, prev_rev 2.1
Index: returns.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/returns.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/saved_carts.html


rev 2.1.2.1, prev_rev 2.1
Index: saved_carts.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/saved_carts.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/ship_addresses.html


rev 2.0.4.1, prev_rev 2.0
Index: ship_addresses.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/ship_addresses.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/ship_addresses_added.html


rev 2.0.4.1, prev_rev 2.0
Index: ship_addresses_added.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/ship_addresses_added.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/ship_addresses_removed.html


rev 2.0.4.1, prev_rev 2.0
Index: ship_addresses_removed.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/ship_addresses_removed.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/pages/splash.html


rev 2.2.2.1, prev_rev 2.2
Index: splash.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/splash.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/stock-alert-added.html


rev 2.0.4.1, prev_rev 2.0
Index: stock-alert-added.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/stock-alert-added.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.3.2.1   +0 -0      interchange/dist/foundation/pages/stock-alert.html


rev 2.3.2.1, prev_rev 2.3
Index: stock-alert.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/stock-alert.html,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/swap_results.html


rev 2.1.2.1, prev_rev 2.1
Index: swap_results.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/swap_results.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/pages/test_order.html


rev 1.1.2.1, prev_rev 1.1
Index: test_order.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/test_order.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/pages/admin/report_def/Order%20Status.html


rev 2.0.4.1, prev_rev 2.0
Index: Order%20Status.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/admin/report_def/Order%20Status.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/admin/report_def/Products%20to%20edit.html


rev 2.0.4.1, prev_rev 2.0
Index: Products%20to%20edit.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/admin/report_def/Products%20to%20edit.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/pages/admin/reports/Order%20Status.html


rev 2.0.4.1, prev_rev 2.0
Index: Order%20Status.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/admin/reports/Order%20Status.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/admin/reports/Products%20to%20edit.html


rev 2.0.4.1, prev_rev 2.0
Index: Products%20to%20edit.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/admin/reports/Products%20to%20edit.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/pages/affiliate/index.html


rev 2.0.4.1, prev_rev 2.0
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/affiliate/index.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/affiliate/login.html


rev 2.1.2.1, prev_rev 2.1
Index: login.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/affiliate/login.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/pages/forum/display.html


rev 1.1.2.1, prev_rev 1.1
Index: display.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/forum/display.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/pages/forum/reply.html


rev 1.2.2.1, prev_rev 1.2
Index: reply.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/forum/reply.html,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/pages/forum/submit.html


rev 1.2.2.1, prev_rev 1.2
Index: submit.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/forum/submit.html,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/pages/ord/basket.html


rev 2.0.4.1, prev_rev 2.0
Index: basket.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/ord/basket.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.10.2.1  +0 -0      interchange/dist/foundation/pages/ord/checkout.html


rev 2.10.2.1, prev_rev 2.10
Index: checkout.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/ord/checkout.html,v
retrieving revision 2.10
retrieving revision 2.10.2.1
diff -u -r2.10 -r2.10.2.1



No                   revision



No                   revision



2.1.2.1   +0 -0      interchange/dist/foundation/pages/query/check_orders.html


rev 2.1.2.1, prev_rev 2.1
Index: check_orders.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/query/check_orders.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/pages/query/get_password.html


rev 2.3.2.1, prev_rev 2.3
Index: get_password.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/query/get_password.html,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/pages/query/order_detail.html


rev 2.0.4.1, prev_rev 2.0
Index: order_detail.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/query/order_detail.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/pages/query/order_return.html


rev 2.1.2.1, prev_rev 2.1
Index: order_return.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/query/order_return.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/pages/query/unsub.html


rev 1.1.2.1, prev_rev 1.1
Index: unsub.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/query/unsub.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/foundation/pages/survey/graph.html


rev 1.1.2.1, prev_rev 1.1
Index: graph.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/survey/graph.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/pages/survey/graph.png.html


rev 1.1.2.1, prev_rev 1.1
Index: graph.png.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/survey/graph.png.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/pages/survey/standard.html


rev 1.2.2.1, prev_rev 1.2
Index: standard.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/pages/survey/standard.html,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/products/2ndDayAir.csv


rev 2.0.4.1, prev_rev 2.0
Index: 2ndDayAir.csv
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/2ndDayAir.csv,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/450.csv


rev 2.0.4.1, prev_rev 2.0
Index: 450.csv
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/450.csv,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/Ground.csv


rev 2.0.4.1, prev_rev 2.0
Index: Ground.csv
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/Ground.csv,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/NextDayAir.csv


rev 2.0.4.1, prev_rev 2.0
Index: NextDayAir.csv
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/NextDayAir.csv,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/products/access.asc


rev 2.1.2.1, prev_rev 2.1
Index: access.asc
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/access.asc,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/affiliate.txt


rev 2.0.4.1, prev_rev 2.0
Index: affiliate.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/affiliate.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/area.txt


rev 2.0.4.1, prev_rev 2.0
Index: area.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/area.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/cat.txt


rev 2.0.4.1, prev_rev 2.0
Index: cat.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/cat.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/component.txt


rev 2.0.4.1, prev_rev 2.0
Index: component.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/component.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/products/country.txt


rev 2.1.2.1, prev_rev 2.1
Index: country.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/country.txt,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/downloadable.txt


rev 2.0.4.1, prev_rev 2.0
Index: downloadable.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/downloadable.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/files.txt


rev 2.0.4.1, prev_rev 2.0
Index: files.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/files.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/foundation/products/forum.txt


rev 1.1.2.1, prev_rev 1.1
Index: forum.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/forum.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/gift_certs.txt


rev 2.0.4.1, prev_rev 2.0
Index: gift_certs.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/gift_certs.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/inventory.txt


rev 2.0.4.1, prev_rev 2.0
Index: inventory.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/inventory.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/products/locale.txt


rev 2.1.2.1, prev_rev 2.1
Index: locale.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/locale.txt,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/merchandising.txt


rev 2.0.4.1, prev_rev 2.0
Index: merchandising.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/merchandising.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.27.2.1  +0 -0      interchange/dist/foundation/products/mv_metadata.asc


rev 2.27.2.1, prev_rev 2.27
Index: mv_metadata.asc
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/mv_metadata.asc,v
retrieving revision 2.27
retrieving revision 2.27.2.1
diff -u -r2.27 -r2.27.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/options.txt


rev 2.0.4.1, prev_rev 2.0
Index: options.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/options.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/order_returns.txt


rev 2.0.4.1, prev_rev 2.0
Index: order_returns.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/order_returns.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/orderline.txt


rev 2.0.4.1, prev_rev 2.0
Index: orderline.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/orderline.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/pricing.txt


rev 2.0.4.1, prev_rev 2.0
Index: pricing.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/pricing.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/products.txt


rev 2.0.4.1, prev_rev 2.0
Index: products.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/products.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/route.txt


rev 2.0.4.1, prev_rev 2.0
Index: route.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/route.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/salestax.asc


rev 2.0.4.1, prev_rev 2.0
Index: salestax.asc
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/salestax.asc,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/shipping.asc


rev 2.0.4.1, prev_rev 2.0
Index: shipping.asc
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/shipping.asc,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.3.2.1   +0 -0      interchange/dist/foundation/products/state.txt


rev 2.3.2.1, prev_rev 2.3
Index: state.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/state.txt,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/products/survey.txt


rev 1.1.2.1, prev_rev 1.1
Index: survey.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/survey.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/products/transactions.txt


rev 2.2.2.1, prev_rev 2.2
Index: transactions.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/transactions.txt,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/products/tree.txt


rev 1.3.2.1, prev_rev 1.3
Index: tree.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/tree.txt,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/products/userdb.txt


rev 2.0.4.1, prev_rev 2.0
Index: userdb.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/userdb.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.21.2.1  +0 -1      interchange/dist/foundation/products/variable.txt


rev 2.21.2.1, prev_rev 2.21
Index: variable.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/products/variable.txt,v
retrieving revision 2.21
retrieving revision 2.21.2.1
diff -u -r2.21 -r2.21.2.1
--- variable.txt	25 Jan 2003 21:24:18 -0000	2.21
+++ variable.txt	25 Jan 2003 22:21:03 -0000	2.21.2.1
@@ -93,7 +93,6 @@
 SHIP_FLAT_DOM_RATE	5	Shipping
 SHIP_FLAT_INTL_RATE	10	Shipping
 SQLDSN	__MVC_SQLDSN__	Database
-SQLITE	__MVC_SQLITE__	Database
 SQLPASS	__MVC_SQLPASS__	Database
 SQLUSER	__MVC_SQLUSER__	Database
 STYLE	__MVC_STYLE__	Template



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/badsearch.html


rev 2.0.4.1, prev_rev 2.0
Index: badsearch.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/badsearch.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/canceled.html


rev 2.0.4.1, prev_rev 2.0
Index: canceled.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/canceled.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/cc_not_valid.html


rev 2.0.4.1, prev_rev 2.0
Index: cc_not_valid.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/cc_not_valid.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/confirmation.html


rev 2.0.4.1, prev_rev 2.0
Index: confirmation.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/confirmation.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/failed.html


rev 2.0.4.1, prev_rev 2.0
Index: failed.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/failed.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/special_pages/interact.html


rev 2.2.2.1, prev_rev 2.2
Index: interact.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/interact.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/special_pages/missing.html


rev 2.1.2.1, prev_rev 2.1
Index: missing.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/missing.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/needfield.html


rev 2.0.4.1, prev_rev 2.0
Index: needfield.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/needfield.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/nomatch.html


rev 2.0.4.1, prev_rev 2.0
Index: nomatch.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/nomatch.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/special_pages/noproduct.html


rev 2.1.2.1, prev_rev 2.1
Index: noproduct.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/noproduct.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/special_pages/notfound.html


rev 2.1.2.1, prev_rev 2.1
Index: notfound.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/notfound.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/special_pages/order_security.html


rev 2.1.2.1, prev_rev 2.1
Index: order_security.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/order_security.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/reconfig.html


rev 2.0.4.1, prev_rev 2.0
Index: reconfig.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/reconfig.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/special_pages/sec_faq.html


rev 2.0.4.1, prev_rev 2.0
Index: sec_faq.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/sec_faq.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/foundation/special_pages/security.html


rev 2.1.2.1, prev_rev 2.1
Index: security.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/security.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/special_pages/violation.html


rev 2.1.2.1, prev_rev 2.1
Index: violation.html
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/special_pages/violation.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



No                   revision



No                   revision



2.3.2.1   +0 -0      interchange/dist/foundation/templates/leftonly


rev 2.3.2.1, prev_rev 2.3
Index: leftonly
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/leftonly,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.4.2.1   +0 -0      interchange/dist/foundation/templates/leftright


rev 2.4.2.1, prev_rev 2.4
Index: leftright
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/leftright,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/templates/noleft


rev 2.3.2.1, prev_rev 2.3
Index: noleft
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/noleft,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/theme.cfg


rev 1.2.2.1, prev_rev 1.2
Index: theme.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/theme.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTRIGHT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTRIGHT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTRIGHT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/CATTOP_LEFTRIGHT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/CATTOP_NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/CATTOP_NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/CATTOP_NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/CATTOP_NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/LEFTRIGHT_BOTTOM


rev 1.3.2.1, prev_rev 1.3
Index: LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/LEFTRIGHT_BOTTOM,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.5.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/LEFTRIGHT_TOP


rev 1.5.2.1, prev_rev 1.5
Index: LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/LEFTRIGHT_TOP,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/blueyellow/regions/NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/blueyellow/regions/NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



No                   revision



No                   revision



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/affiliate_receptor


rev 2.2.2.1, prev_rev 2.2
Index: affiliate_receptor
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/affiliate_receptor,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/best


rev 2.2.2.1, prev_rev 2.2
Index: best
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/best,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.9.2.1   +0 -0      interchange/dist/foundation/templates/components/cart


rev 2.9.2.1, prev_rev 2.9
Index: cart
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/cart,v
retrieving revision 2.9
retrieving revision 2.9.2.1
diff -u -r2.9 -r2.9.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/templates/components/cart_display


rev 2.3.2.1, prev_rev 2.3
Index: cart_display
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/cart_display,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/cart_tiny


rev 2.2.2.1, prev_rev 2.2
Index: cart_tiny
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/cart_tiny,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/category_horizontal


rev 2.2.2.1, prev_rev 2.2
Index: category_horizontal
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/category_horizontal,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



1.5.2.1   +0 -0      interchange/dist/foundation/templates/components/category_vert_toggle


rev 1.5.2.1, prev_rev 1.5
Index: category_vert_toggle
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/category_vert_toggle,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/templates/components/category_vertical


rev 2.3.2.1, prev_rev 2.3
Index: category_vertical
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/category_vertical,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/templates/components/category_vertical_tree


rev 1.1.2.1, prev_rev 1.1
Index: category_vertical_tree
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/category_vertical_tree,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/cross


rev 2.2.2.1, prev_rev 2.2
Index: cross
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/cross,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/fortune


rev 2.2.2.1, prev_rev 2.2
Index: fortune
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/fortune,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/components/product_flyout


rev 1.2.2.1, prev_rev 1.2
Index: product_flyout
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/product_flyout,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/components/product_tree


rev 1.4.2.1, prev_rev 1.4
Index: product_tree
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/product_tree,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



2.6.2.1   +0 -0      interchange/dist/foundation/templates/components/promo


rev 2.6.2.1, prev_rev 2.6
Index: promo
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/promo,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/random


rev 2.2.2.1, prev_rev 2.2
Index: random
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/random,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/templates/components/results_big


rev 1.1.2.1, prev_rev 1.1
Index: results_big
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/results_big,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/templates/components/results_buylist


rev 1.1.2.1, prev_rev 1.1
Index: results_buylist
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/results_buylist,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/templates/components/results_grid


rev 1.1.2.1, prev_rev 1.1
Index: results_grid
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/results_grid,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/saved_carts_list_small


rev 2.2.2.1, prev_rev 2.2
Index: saved_carts_list_small
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/saved_carts_list_small,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/templates/components/search_box_small


rev 2.3.2.1, prev_rev 2.3
Index: search_box_small
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/search_box_small,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/templates/components/search_box_small_top


rev 2.3.2.1, prev_rev 2.3
Index: search_box_small_top
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/search_box_small_top,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/components/upsell


rev 2.2.2.1, prev_rev 2.2
Index: upsell
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/components/upsell,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/theme.cfg


rev 1.2.2.1, prev_rev 1.2
Index: theme.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/theme.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTONLY_TOP


rev 1.3.2.1, prev_rev 1.3
Index: CATTOP_LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTONLY_TOP,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTRIGHT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTRIGHT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTRIGHT_TOP


rev 1.3.2.1, prev_rev 1.3
Index: CATTOP_LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_LEFTRIGHT_TOP,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_NOLEFT_TOP


rev 1.3.2.1, prev_rev 1.3
Index: CATTOP_NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/CATTOP_NOLEFT_TOP,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/LEFTONLY_TOP


rev 1.3.2.1, prev_rev 1.3
Index: LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/LEFTONLY_TOP,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/LEFTRIGHT_BOTTOM


rev 1.3.2.1, prev_rev 1.3
Index: LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/LEFTRIGHT_BOTTOM,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/LEFTRIGHT_TOP


rev 1.3.2.1, prev_rev 1.3
Index: LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/LEFTRIGHT_TOP,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/fixedwidth/regions/NOLEFT_TOP


rev 1.3.2.1, prev_rev 1.3
Index: NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/fixedwidth/regions/NOLEFT_TOP,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/templates/foundation/cart


rev 2.0.4.1, prev_rev 2.0
Index: cart
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/cart,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/foundation/simple


rev 2.0.4.1, prev_rev 2.0
Index: simple
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/simple,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.4.2.1   +0 -0      interchange/dist/foundation/templates/foundation/theme.cfg


rev 2.4.2.1, prev_rev 2.4
Index: theme.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/theme.cfg,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1



No                   revision



No                   revision



2.2.2.1   +0 -0      interchange/dist/foundation/templates/foundation/regions/LEFTONLY_BOTTOM


rev 2.2.2.1, prev_rev 2.2
Index: LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/regions/LEFTONLY_BOTTOM,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.6.2.1   +0 -0      interchange/dist/foundation/templates/foundation/regions/LEFTONLY_TOP


rev 2.6.2.1, prev_rev 2.6
Index: LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/regions/LEFTONLY_TOP,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1



2.3.2.1   +0 -0      interchange/dist/foundation/templates/foundation/regions/LEFTRIGHT_BOTTOM


rev 2.3.2.1, prev_rev 2.3
Index: LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/regions/LEFTRIGHT_BOTTOM,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.6.2.1   +0 -0      interchange/dist/foundation/templates/foundation/regions/LEFTRIGHT_TOP


rev 2.6.2.1, prev_rev 2.6
Index: LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/regions/LEFTRIGHT_TOP,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/foundation/regions/NOLEFT_BOTTOM


rev 2.2.2.1, prev_rev 2.2
Index: NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/regions/NOLEFT_BOTTOM,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.5.2.1   +0 -0      interchange/dist/foundation/templates/foundation/regions/NOLEFT_TOP


rev 2.5.2.1, prev_rev 2.5
Index: NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/foundation/regions/NOLEFT_TOP,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/theme.cfg


rev 1.2.2.1, prev_rev 1.2
Index: theme.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/theme.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTRIGHT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTRIGHT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTRIGHT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/CATTOP_LEFTRIGHT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/CATTOP_NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/CATTOP_NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/CATTOP_NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/CATTOP_NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/LEFTRIGHT_BOTTOM


rev 1.3.2.1, prev_rev 1.3
Index: LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/LEFTRIGHT_BOTTOM,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.5.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/LEFTRIGHT_TOP


rev 1.5.2.1, prev_rev 1.5
Index: LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/LEFTRIGHT_TOP,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayorange/regions/NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayorange/regions/NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/theme.cfg


rev 1.2.2.1, prev_rev 1.2
Index: theme.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/theme.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTRIGHT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTRIGHT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTRIGHT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/CATTOP_LEFTRIGHT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/CATTOP_NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/CATTOP_NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/CATTOP_NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/CATTOP_NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/LEFTRIGHT_BOTTOM


rev 1.3.2.1, prev_rev 1.3
Index: LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/LEFTRIGHT_BOTTOM,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.5.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/LEFTRIGHT_TOP


rev 1.5.2.1, prev_rev 1.5
Index: LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/LEFTRIGHT_TOP,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/grayscale/regions/NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/grayscale/regions/NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/greens/theme.cfg


rev 1.2.2.1, prev_rev 1.2
Index: theme.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/theme.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTRIGHT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTRIGHT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTRIGHT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/CATTOP_LEFTRIGHT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/CATTOP_NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/CATTOP_NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/CATTOP_NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/CATTOP_NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/LEFTRIGHT_BOTTOM


rev 1.3.2.1, prev_rev 1.3
Index: LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/LEFTRIGHT_BOTTOM,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.5.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/LEFTRIGHT_TOP


rev 1.5.2.1, prev_rev 1.5
Index: LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/LEFTRIGHT_TOP,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/greens/regions/NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/greens/regions/NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/theme.cfg


rev 1.2.2.1, prev_rev 1.2
Index: theme.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/theme.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTRIGHT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTRIGHT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTRIGHT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_LEFTRIGHT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: CATTOP_NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: CATTOP_NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/CATTOP_NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/LEFTONLY_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: LEFTONLY_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/LEFTONLY_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/LEFTONLY_TOP


rev 1.4.2.1, prev_rev 1.4
Index: LEFTONLY_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/LEFTONLY_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.3.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/LEFTRIGHT_BOTTOM


rev 1.3.2.1, prev_rev 1.3
Index: LEFTRIGHT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/LEFTRIGHT_BOTTOM,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.5.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/LEFTRIGHT_TOP


rev 1.5.2.1, prev_rev 1.5
Index: LEFTRIGHT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/LEFTRIGHT_TOP,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



1.2.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/NOLEFT_BOTTOM


rev 1.2.2.1, prev_rev 1.2
Index: NOLEFT_BOTTOM
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/NOLEFT_BOTTOM,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/foundation/templates/purpleyellow/regions/NOLEFT_TOP


rev 1.4.2.1, prev_rev 1.4
Index: NOLEFT_TOP
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/purpleyellow/regions/NOLEFT_TOP,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/00352as.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 00352as.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/00352as.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/11993ab.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 11993ab.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/11993ab.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/22083da.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 22083da.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/22083da.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/49503cg.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 49503cg.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/49503cg.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/59330rt.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 59330rt.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/59330rt.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/59402fw.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 59402fw.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/59402fw.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/66548ch.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 66548ch.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/66548ch.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/73358ee.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 73358ee.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/73358ee.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/83491vp.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 83491vp.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/83491vp.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/download/90773sh.pdf


rev 2.0.4.1, prev_rev 2.0
Index: 90773sh.pdf
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/download/90773sh.pdf,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/area.txt


rev 2.0.4.1, prev_rev 2.0
Index: area.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/area.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/cat.txt


rev 2.0.4.1, prev_rev 2.0
Index: cat.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/cat.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/inventory.txt


rev 2.0.4.1, prev_rev 2.0
Index: inventory.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/inventory.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/merchandising.txt


rev 2.0.4.1, prev_rev 2.0
Index: merchandising.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/merchandising.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/options.txt


rev 2.0.4.1, prev_rev 2.0
Index: options.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/options.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/pricing.txt


rev 2.0.4.1, prev_rev 2.0
Index: pricing.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/pricing.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/products.txt


rev 2.0.4.1, prev_rev 2.0
Index: products.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/products.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/reports/products/userdb.txt


rev 2.2.2.1, prev_rev 2.2
Index: userdb.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/reports/products/userdb.txt,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/etc/after.cfg


rev 2.0.4.1, prev_rev 2.0
Index: after.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/etc/after.cfg,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/etc/before.cfg


<<before.cfg: empty>>


No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/gift_cert.gif


<<gift_cert.gif: GIF image data, version 89a, 134 x 33,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28004.gif


<<os28004.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28005.gif


<<os28005.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28006.gif


<<os28006.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28007.gif


<<os28007.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28008.gif


<<os28008.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28009.gif


<<os28009.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28011.gif


<<os28011.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28044.gif


<<os28044.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28057a.gif


<<os28057a.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28057b.gif


<<os28057b.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28057c.gif


<<os28057c.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28062.gif


<<os28062.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28064.gif


<<os28064.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28065.gif


<<os28065.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28066.gif


<<os28066.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28068.gif


<<os28068.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28068a.gif


<<os28068a.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28068b.gif


<<os28068b.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28069.gif


<<os28069.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28070.gif


<<os28070.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28072.gif


<<os28072.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28073.gif


<<os28073.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28074.gif


<<os28074.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28075.gif


<<os28075.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28076.gif


<<os28076.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28077.gif


<<os28077.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28080.gif


<<os28080.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28081.gif


<<os28081.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28082.gif


<<os28082.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28084.gif


<<os28084.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28085.gif


<<os28085.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28086.gif


<<os28086.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28087.gif


<<os28087.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28108.gif


<<os28108.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28109.gif


<<os28109.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28110.gif


<<os28110.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28111.gif


<<os28111.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28112.gif


<<os28112.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os28113.gif


<<os28113.gif: GIF image data, version 89a, 120 x 150,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/items/os29000.gif


<<os29000.gif: GIF image data, version 89a, 120 x 150,>>


No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/gift_cert.gif


<<gift_cert.gif: GIF image data, version 89a, 134 x 33,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28004_b.gif


<<os28004_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28005_b.gif


<<os28005_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28006_b.gif


<<os28006_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28007_b.gif


<<os28007_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28008_b.gif


<<os28008_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28009_b.gif


<<os28009_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28011_b.gif


<<os28011_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28044_b.gif


<<os28044_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28057a_b.gif


<<os28057a_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28057b_b.gif


<<os28057b_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28057c_b.gif


<<os28057c_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28062_b.gif


<<os28062_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28064_b.gif


<<os28064_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28065_b.gif


<<os28065_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28066_b.gif


<<os28066_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28068_b.gif


<<os28068_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28068a_b.gif


<<os28068a_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28068b_b.gif


<<os28068b_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28069_b.gif


<<os28069_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28070_b.gif


<<os28070_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28072_b.gif


<<os28072_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28073_b.gif


<<os28073_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28074_b.gif


<<os28074_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28075_b.gif


<<os28075_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28076_b.gif


<<os28076_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28077_b.gif


<<os28077_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28080_b.gif


<<os28080_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28081_b.gif


<<os28081_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28082_b.gif


<<os28082_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28084_b.gif


<<os28084_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28085_b.gif


<<os28085_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28086_b.gif


<<os28086_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28087_b.gif


<<os28087_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28108_b.gif


<<os28108_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28109_b.gif


<<os28109_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28110_b.gif


<<os28110_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28111_b.gif


<<os28111_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28112_b.gif


<<os28112_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os28113_b.gif


<<os28113_b.gif: GIF image data, version 89a, 80 x 80,>>


2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/images/thumb/os29000_b.gif


<<os29000_b.gif: GIF image data, version 89a, 80 x 80,>>


No                   revision



No                   revision



2.1.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/affiliate.txt


rev 2.1.2.1, prev_rev 2.1
Index: affiliate.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/affiliate.txt,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/area.txt


rev 2.0.4.1, prev_rev 2.0
Index: area.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/area.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/area_de_DE.txt


rev 1.1.2.1, prev_rev 1.1
Index: area_de_DE.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/area_de_DE.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/cat.txt


rev 2.0.4.1, prev_rev 2.0
Index: cat.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/cat.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/cat_de_DE.txt


rev 1.1.2.1, prev_rev 1.1
Index: cat_de_DE.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/cat_de_DE.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/inventory.txt


rev 2.1.2.1, prev_rev 2.1
Index: inventory.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/inventory.txt,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/merchandising.txt


rev 2.1.2.1, prev_rev 2.1
Index: merchandising.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/merchandising.txt,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/options.txt


rev 2.0.4.1, prev_rev 2.0
Index: options.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/options.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/orderline.txt


rev 2.0.4.1, prev_rev 2.0
Index: orderline.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/orderline.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/pricing.txt


rev 2.0.4.1, prev_rev 2.0
Index: pricing.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/pricing.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/products.txt


rev 2.2.2.1, prev_rev 2.2
Index: products.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/products.txt,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



1.1.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/products_de_DE.txt


rev 1.1.2.1, prev_rev 1.1
Index: products_de_DE.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/products_de_DE.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/specs.txt


rev 2.0.4.1, prev_rev 2.0
Index: specs.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/specs.txt,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.5.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/transactions.txt


rev 2.5.2.1, prev_rev 2.5
Index: transactions.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/transactions.txt,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



2.2.2.1   +0 -0      interchange/dist/foundation/templates/sampledata/tools/products/userdb.txt


rev 2.2.2.1, prev_rev 2.2
Index: userdb.txt
===================================================================
RCS file: /var/cvs/interchange/dist/foundation/templates/sampledata/tools/products/userdb.txt,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/foundation/upload/.empty


<<.empty: empty>>


2.0.4.1   +0 -0      interchange/dist/foundation/upload/products.xls


<<products.xls: Microsoft Office Document>>


No                   revision



No                   revision



1.21.4.8  +94 -397   interchange/dist/lib/UI/Primitive.pm


rev 1.21.4.8, prev_rev 1.21.4.7
Index: Primitive.pm
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/Primitive.pm,v
retrieving revision 1.21.4.7
retrieving revision 1.21.4.8
diff -u -r1.21.4.7 -r1.21.4.8
--- Primitive.pm	2 Feb 2001 09:25:14 -0000	1.21.4.7
+++ Primitive.pm	25 Jan 2003 22:21:12 -0000	1.21.4.8
@@ -1,8 +1,10 @@
-#!/usr/bin/perl
+# UI::Primitive - Interchange configuration manager primitives
 
-# Copyright (C) 1998-2000 Akopia, Inc. <info@akopia.com>
+# $Id: Primitive.pm,v 1.21.4.8 2003/01/25 22:21:12 racke Exp $
 
-# Author: Michael J. Heins <heins@akopia.com>
+# Copyright (C) 1998-2002 Red Hat, Inc. <interchange@redhat.com>
+
+# Author: Michael J. Heins <mikeh@perusion.net>
 # Former maintainer: Stefan Hornburg <racke@linuxia.de>
 
 # This file is free software; you can redistribute it and/or modify it
@@ -23,7 +25,7 @@
 
 package UI::Primitive;
 
-$VERSION = substr(q$Revision: 1.21.4.7 $, 10);
+$VERSION = substr(q$Revision: 1.21.4.8 $, 10);
 $DEBUG = 0;
 
 use vars qw!
@@ -33,14 +35,19 @@
 	!;
 
 use File::Find;
-use File::CounterFile;
-use Text::ParseWords;
 use Exporter;
 use strict;
 use Vend::Util qw/errmsg/;
 $DECODE_CHARS = qq{&[<"\000-\037\177-\377};
 
-@EXPORT = qw( ui_check_acl ui_acl_enabled ) ;
+@EXPORT = qw(
+		list_glob
+		list_images
+		list_pages
+		meta_record
+		ui_acl_enabled
+		ui_check_acl
+	);
 
 =head1 NAME
 
@@ -60,128 +67,57 @@
 $ui_safe->untrap(@{$Global::SafeUntrap});
 
 sub is_super {
-#::logDebug("called is_super");
+	return 1
+		if  $Vend::Cfg->{RemoteUser}
+		and $Vend::Cfg->{RemoteUser} eq $CGI::remote_user;
 	return 0 if ! $Vend::Session->{logged_in};
-#::logDebug("is_super: logged in");
 	return 0 if ! $Vend::username;
 	return 0 if $Vend::Cfg->{AdminUserDB} and ! $Vend::admin;
-#::logDebug("is_super: have username");
 	my $db = Vend::Data::database_exists_ref(
 						$Vend::Cfg->{Variable}{UI_ACCESS_TABLE} || 'access'
 						);
 	return 0 if ! $db;
-#::logDebug("is_super: access db exists");
 	$db = $db->ref();
 	my $result = $db->field($Vend::username, 'super');
-#::logDebug("is_super: result=$result");
 	return $result;
 }
 
 sub is_logged {
-#::logDebug("is_logged check");
+	return 1
+		if  $Vend::Cfg->{RemoteUser}
+		and $Vend::Cfg->{RemoteUser} eq $CGI::remote_user;
 	return 0 if ! $Vend::Session->{logged_in};
-#::logDebug("is_logged logged_in=ok");
 	return 0 unless $Vend::admin or ! $Vend::Cfg->{AdminUserDB};
-#::logDebug("is_logged admin=ok");
 	return 1;
 }
 
 my %wrap_dest;
 my $compdb;
 
-sub ui_wrap {
-	my $path = shift;
-	if($CGI::values{ui_destination}) {
-		my $sub = $wrap_dest{$CGI::values{ui_destination}} || return 1;
-		return $sub->($path);
-	}
-	$Vend::Cfg->{VendURL} .= '/ui_wrap';
-	$UI::Editing = \&resolve_var;
-	$compdb = ::database_exists_ref($::Variable->{UI_COMPONENT_TABLE} ||= 'component');
-	$path =~ s:([^/]+)::;
-	$Vend::RedoAction = 1;
-	my $snoop = $1;
-	return $snoop;
-}
-
-sub wrap_edit {
-	package Vend::Interpolate;
-	my $name = shift;
-#::logGlobal("entering wrap_edit $name");
-	my $ref;
-	if ($compdb->record_exists($name)) {
-		$ref = $compdb->row_hash($name);
-	}
-	else {
-		return $::Variable->{$name} if ! $::Variable->{$name};
-		$ref = { variable => $::Variable->{$name} };
-	}
-	if ($ref->{variable} =~ s/^(\s*\[)include(\s+)/$1 . 'file' . $2/e) {
-		$ref->{variable} = ::interpolate_html($ref->{variable});
-	}
-	my $edit_link;
-	my $url = $Vend::Cfg->{VendURL};
-	$url =~ s!/ui_wrap$!$::Variable->{UI_BASE} || $Global::Variable->{UI_BASE} || 'admin'!e;
-	$url .= "/";
-	if(not $edit_link = $::Variable->{UI_EDIT_LINK}) {
-		my $url = Vend::Interpolate::tag_area(
-						"$::Variable->{UI_BASE}/compedit",
-						$name,
-						);
-		$url =~ s:/ui_wrap/:/:;
-		$edit_link = <<EOF;
-<A HREF="$url" target="_blank"><u>edit</u></A>
-EOF
-		chop $edit_link;
-	}
-	my $out = <<EOF;
-[calc] \$C_stack = [] unless \$C_stack;
-		push \@\$C_stack, \$Scratch->{ui_component} || '';
-		\$Scratch->{ui_component} = q{$name}; return; [/calc]
-EOF
-	chop $out;
-
-	for( qw/preedit preamble variable postamble postedit/ ) {
-		$out .= $ref->{$_};
-	}
-	$out .= qq{[calc] \$Scratch->{ui_component} = pop \@\$C_stack; return; [/calc]};
-	$out =~ s:\[comment\]\s*\$EDIT_LINK\$\s*\[/comment\]:$edit_link:;
-#::logGlobal("returning wrap_edit $out");
-	return $out;
-}
-
-sub resolve_var {
-	my ($name, $ref) = @_;
-	if ($compdb) {
-		return wrap_edit($name);
-	}
-	return $ref->{$name} if $ref and defined $ref->{$name};
-	return $::Variable->{$name};
-}
-
 sub ui_acl_enabled {
 	my $try = shift;
 	my $table;
 	$Global::SuperUserFunction = \&is_super;
-	my $default = defined $Global::Variable->{UI_ACL}
-				 ? (! $Global::Variable->{UI_ACL})
-				 : 1;
+	my $default = defined $Global::Variable->{UI_SECURITY_OVERRIDE}
+				? $Global::Variable->{UI_SECURITY_OVERRIDE}
+				: 0;
+	if ($Vend::superuser) {
+		return $Vend::UI_entry = { super => 1 };
+	}
 	$table = $::Variable->{UI_ACCESS_TABLE} || 'access';
 	$Vend::WriteDatabase{$table} = 1;
 	my $db = Vend::Data::database_exists_ref($table);
 	return $default unless $db;
 	$db = $db->ref() unless $Vend::Interpolate::Db{$table};
 	my $uid = $try || $Vend::username || $CGI::remote_user;
-#::logDebug("ACL enabled try uid=$uid");
 	if(! $uid or ! $db->record_exists($uid) ) {
 		return 0;
 	}
-#::logDebug("ACL enabled record exists uid=$uid");
 	my $ref = $db->row_hash($uid)
 		or die "Bad database record for $uid.";
-#::logDebug("ACL enabled, table_control=$ref->{table_control}");
 	if($ref->{table_control}) {
 		$ref->{table_control_ref} = $ui_safe->reval($ref->{table_control});
+		ref $ref->{table_control_ref} or delete $ref->{table_control_ref};
 	}
 	return $ref if $try;
 	$Vend::UI_entry = $ref;
@@ -190,7 +126,6 @@
 sub get_ui_table_acl {
 	my ($table, $user, $keys) = @_;
 	$table = $::Values->{mv_data_table} unless $table;
-#::logDebug("Call get_ui_table_acl: " . Vend::Util::uneval_it(\@_));
 	my $acl_top;
 	if($user and $user ne $Vend::username) {
 		if ($Vend::UI_acl{$user}) {
@@ -209,7 +144,6 @@
 	}
 	else {
 		unless ($acl_top = $Vend::UI_entry) {
-#::logDebug("Call get_ui_table_acl: acl_top=" . ::uneval($acl_top));
 			return undef unless ref($acl_top = ui_acl_enabled());
 		}
 	}
@@ -219,7 +153,6 @@
 
 sub ui_acl_grep {
 	my ($acl, $name, @entries) = @_;
-#::logDebug("Call ui_acl_grep: " . ::uneval(\@_));
 	my $val;
 	my %ok;
 	@ok{@entries} = @entries;
@@ -233,7 +166,6 @@
 			for(@entries) {
 
 				my $v = ::tag_data($t, $val, $_);
-#::logDebug("ui_acl_grep owner: t=$t f=$val k=$_ v=$v u=$u");
 				$ok{$_} = $v eq $u;
 			}
 	}
@@ -268,30 +200,19 @@
 sub ui_extended_acl {
 	my ($item, $string) = @_;
 	$string = " $string ";
-#::logDebug("extended acl string='$string'");
 	my ($name, $sub) = split /=/, $item, 2;
-#::logDebug("extended acl: name=$name sub=$sub");
-#::logDebug("extended acl trying /[\s,]!${name}\[,\s]/");
 	return 0 if $string =~ /[\s,]!$name(?:[,\s])/;
-#::logDebug("extended acl passed /[\s,]!${name}\[,\s]/");
-#::logDebug("extended acl trying /[\s,]${name}\[,\s]/");
 	return 1 if $string =~ /[\s,]$name(?:[,\s])/;
-#::logDebug("extended acl passed /[\s,]${name}\[,\s]/");
 	my (@subs) = split //, $sub;
 	for(@subs) {
-#::logDebug("extended acl trying /[\s,]!$name=[^,\s]*$sub/");
 		return 0 if $string =~ /[\s,]!$name=[^,\s]*$sub/;
-#::logDebug("extended acl passed /[\s,]!$name=[^,\s]*$sub/");
-#::logDebug("extended acl trying /[\s,]$name=[^,\s]*$sub/");
 		return 0 unless $string =~ /[\s,]$name=[^,\s]*$sub/;
-#::logDebug("extended acl passed /[\s,]$name=[^,\s]*$sub/");
 	}
 	return 1;
 }
 
 sub ui_check_acl {
 	my ($item, $string) = @_;
-#::logDebug("checking item=$item");
 	return ui_extended_acl(@_) if $item =~ /=/;
 	$string = " $string ";
 	return 0 if $string =~ /[\s,]!$item[=,\s]/;
@@ -357,6 +278,9 @@
   		}
 
 		my @fields = grep /\S/, split /[,\s\0]+/, $CGI->{mv_data_fields};
+		push @fields, $CGI->{mv_blob_field}
+			if $CGI->{mv_blob_field};
+
 		for(@fields) {
 			$CGI->{$_} =~ s/\[/&#91;/g unless $mml_enable;
 			$CGI->{$_} =~ s/\</&lt;/g unless $html_enable;
@@ -386,10 +310,8 @@
 sub list_keys {
 	my $table = shift;
 	my $opt = shift;
-#::logDebug("list-keys $table");
 	$table = $::Values->{mv_data_table}
 		unless $table;
-#::logDebug("list-keys $table");
 	my @keys;
 	my $record;
 	if(! ($record = $Vend::UI_entry) ) {
@@ -399,11 +321,8 @@
 	my $acl;
 	my $keys;
 	if($record) {
-#::logDebug("list_keys: record=$record");
 		$acl = get_ui_table_acl($table);
-#::logDebug("list_keys table=$table: acl=$acl");
 		if($acl and $acl->{yes_keys}) {
-#::logDebug("list_keys table=$table: yes.keys enabled");
 			@keys = grep /\S/, split /\s+/, $acl->{yes_keys};
 		}
 	}
@@ -416,7 +335,6 @@
 			return ::errmsg('--not listed, too large--');
 		}
 		my $query = "select $keyname from $table order by $keyname";
-#::logDebug("list_keys: query=$query");
 		$keys = $db->query(
 						{
 							query => $query,
@@ -439,10 +357,8 @@
 				@keys = sort @keys;
 			}
 		}
-#::logDebug("list_keys: query=returned " . ::uneval(\@keys));
 	}
 	if($acl) {
-#::logDebug("list_keys acl: ". ::uneval($acl));
 		@keys = UI::Primitive::ui_acl_grep( $acl, 'keys', @keys);
 	}
 	my $joiner = $opt->{joiner} || "\n";
@@ -489,13 +405,20 @@
 }
 
 sub list_images {
-	my ($base) = @_;
+	my ($base, $suf) = @_;
 	return undef unless -d $base;
-	my $suf = '\.(GIF|gif|JPG|JPEG|jpg|jpeg|png|PNG)';
+#::logDebug("passed suf=$suf");
+	$suf = '\.(GIF|gif|JPG|JPEG|jpg|jpeg|png|PNG)'
+		unless $suf;
 	my @names;
+	my $regex;
+	eval {
+		$regex = qr{$suf$}o;
+	};
+	return undef if $@;
 	my $wanted = sub {
 					return undef unless -f $_;
-					return undef unless /$suf$/o;
+					return undef unless $_ =~ $regex;
 					my $n = $File::Find::name;
 					$n =~ s:^$base/?::;
 					push(@names, $n);
@@ -524,13 +447,11 @@
 	my ($keep, $suf, $base) = @_;
 	$suf = $Vend::Cfg->{StaticSuffix} if ! $suf;
 	$base = Vend::Util::catfile($Vend::Cfg->{VendRoot}, $base) if $base;
-	$base = $Vend::Cfg->{PageDir} if ! $base;
+	$base ||= $Vend::Cfg->{PageDir};
 	my @names;
+	$suf = quotemeta($suf);
+#::logDebug("Finding, ext=$suf base=$base");
 	my $wanted = sub {
-					if(-d $_ and $Vend::Cfg->{AdminPage}{$_}) {
-						$File::Find::prune = 1;
-						return;
-					}
 					return undef unless -f $_;
 					return undef unless /$suf$/;
 					my $n = $File::Find::name;
@@ -539,6 +460,7 @@
 					push(@names, $n);
 				};
 	find($wanted, $base);
+#::logDebug("Found files: " . join (",", @names));
 	return sort @names;
 }
 
@@ -578,12 +500,11 @@
 
 	my $motion = $options->{Motion} || 'save';
 
-#::logDebug( "rotate $base with options dir=$dir motion=$motion from >> " . ::uneval($options));
+	$options->{max} = 10 if ! defined $options->{max};
 
 	$dir =~ s:/+$::;
 
 	if("\L$motion" eq 'save' and ! -f "$dir/$base+") {
-			require File::Copy;
 			File::Copy::copy("$dir/$base", "$dir/$base+")
 				or die "copy $dir/$base to $dir/$base+: $!\n";
 	}
@@ -611,11 +532,14 @@
 
 	$base = "$dir/$base";
 
-#::logDebug( "rotate $base with options dir=$dir motion=$motion from >> " . ::uneval($options));
 
 	my $base_exists = -f $base;
 	push @forward, $base if $base_exists;
 
+	if (@forward > $options->{max}) {
+		$#forward = $options->{max};
+	}
+
 	for(reverse sort @forward) {
 		next unless -f $_;
 		rename $_, $_ . $add or die "rename $_ => $_+: $!\n";
@@ -626,6 +550,11 @@
 	@backward = sort @backward;
 
 	unshift @backward, $base;
+
+	if (@backward > $options->{max}) {
+		$#backward = $options->{max};
+	}
+
 	my $i;
 	for($i = 0; $i < $#backward; $i++) {
 		rename $backward[$i+1], $backward[$i]
@@ -639,284 +568,52 @@
 	return 1;
 }
 
-my @t = localtime();
 
-my (@years) = ( $t[5] + 1899 .. $t[5] + 1910 );
-my (@months);
-my (@days);
-
-for(1 .. 12) {
-	$t[4] = $_ - 1;
-	$t[5] = 1;
-	push @months, [sprintf("%02d", $_), POSIX::strftime("%B", @t)];
-}
-
-for(1 .. 31) {
-	push @days, [sprintf("%02d", $_), $_];
-}
-
-sub date_widget {
-	my($name, $val) = @_;
-	if($val =~ /\D/) {
-		$val = Vend::Interpolate::filter_value('date_change', $val);
-	}
-	@t = localtime();
-	$val = POSIX::strftime("%Y%m%d", @t) if not $val;
-	my $sel = 0;
-	my $out = qq{<SELECT NAME="$name">};
-	my $o;
-	for(@months) {
-		$o = qq{<OPTION VALUE="$_->[0]">$_->[1]};
-		($out .= $o, next) unless ! $sel and $val;
-		$o =~ s/>/ SELECTED>/ && $sel++
-			if substr($val, 4, 2) eq $_->[0];
-		$out .= $o;
-	}
-	$sel = 0;
-	$out .= qq{</SELECT>};
-	$out .= qq{<INPUT TYPE=hidden NAME="$name" VALUE="/">};
-	$out .= qq{<SELECT NAME="$name">};
-	for(@days) {
-		$o = qq{<OPTION VALUE="$_->[0]">$_->[1]};
-		($out .= $o, next) unless ! $sel and $val;
-		$o =~ s/>/ SELECTED>/ && $sel++
-			if substr($val, 6, 2) eq $_->[0];
-		$out .= $o;
-	}
-	$sel = 0;
-	$out .= qq{</SELECT>};
-	$out .= qq{<INPUT TYPE=hidden NAME="$name" VALUE="/">};
-	$out .= qq{<SELECT NAME="$name">};
-	for(@years) {
-		$o = qq{<OPTION>$_};
-		($out .= $o, next) unless ! $sel and $val;
-		$o =~ s/>/ SELECTED>/ && $sel++
-			if substr($val, 0, 4) eq $_;
-		$out .= $o;
-	}
-	$out .= qq{</SELECT>};
-}
-
-sub imagehelper_widget {
-    my ($name, $val, $path) = @_;
-
-    if ($val) {
-        qq{<A HREF="$path/$val">$val</A>&nbsp;<INPUT TYPE=hidden NAME=mv_data_file_field VALUE="$name">
-<INPUT TYPE=hidden NAME=mv_data_file_path VALUE="$path">
-<INPUT TYPE=hidden NAME=mv_data_file_oldfile VALUE="$val">
-<INPUT TYPE=file NAME="$name" VALUE="$val">};      
-    } else {
-        qq{<INPUT TYPE=hidden NAME=mv_data_file_field VALUE="$name">
-<INPUT TYPE=hidden NAME=mv_data_file_path VALUE="$path">
-<INPUT TYPE=hidden NAME=mv_data_file_oldfile VALUE="">
-<INPUT TYPE=file NAME="$name">};
-    }
-}
-
-my $base_entry_value;
-
-sub meta_display {
-	my ($table,$column,$key,$value,$meta_db,$query,$o) = @_;
-
-#::logDebug("metadisplay: t=$table c=$column k=$key v=$value md=$meta_db");
-	my $metakey;
-	$meta_db = $::Variable->{UI_META_TABLE} || 'mv_metadata' if ! $meta_db;
-	$o = {} if ! ref $o;
-#::logDebug("metadisplay: t=$table c=$column k=$key v=$value opt=" . ::uneval_it($o));
-	my $meta = Vend::Data::database_exists_ref($meta_db)
+sub meta_record {
+	my ($item, $view, $mdb) = @_;
+
+#::logDebug("meta_record: item=$item view=$view mdb=$mdb");
+	return undef unless $item;
+
+	if(! ref ($mdb)) {
+		my $mtable = $mdb || $::Variable->{UI_META_TABLE} || 'mv_metadata';
+#::logDebug("meta_record mtable=$mtable");
+		$mdb = Vend::Data::database_exists_ref($mtable)
 		or return undef;
-	$meta = $meta->ref();
-	if($column eq $meta->config('KEY')) {
-		$base_entry_value = $value =~ /::/ ? $table : $value;
-	}
-#::logDebug("metadisplay: got meta ref=$meta");
-	my $tag = '';
-	if($o->{arbitrary}) {
-		$tag = "$o->{arbitrary}::";
-	}
-	my (@tries) = "$tag${table}::$column";
-	if($key) {
-		# Don't think we need table::key combo anymore....
-		# unshift @tries, "$tag${table}::${column}::$key", "$tag${table}::$key";
-		unshift @tries, "$tag${table}::${column}::$key";
-	}
-	if($tag and $o->{fallback}) {
-		push @tries, "${table}::${column}::$key", "${table}::${column}";
-	}
-
-	my $sess = $Vend::Session->{mv_metadata} || {};
-	for $metakey (@tries) {
-#::logDebug("enter metadisplay record $metakey");
-		my $record;
-		unless ( $record = $sess->{$metakey} and ref $record ) {
-			next unless $meta->record_exists($metakey);
-			$record = $meta->row_hash($metakey);
-		}
-		if($query) {
-			return $record->{query};
-		}
-#::logDebug("metadisplay record: " . Vend::Util::uneval_it($record));
-		my $opt;
-		if($record->{options} and $record->{options} =~ /^[\w:]+$/) {
-			PASS: {
-				my $passed = $record->{options};
-#::logDebug("passed = '$passed'");
-
-				if($passed eq 'tables') {
-					$record->{passed} = "=--none--," . list_tables({ joiner => ',' });
-				}
-				elsif($passed eq 'filters') {
-					$record->{passed} = $Vend::Interpolate::Tag->filters(1),
-				}
-				elsif($passed =~ /^columns(::(\w*))?$/) {
-					my $total = $1;
-					my $tname = $2 || $record->{db} || $table;
-					$tname = $base_entry_value if $total eq '::';
-#::logDebug("tname='$tname' total=$total");
-					my $db = $Vend::Database{$tname};
-					$record->{passed} = join (',', "=--none--", $db->columns())
-						if $db;
-				}
-				elsif($passed =~ /^keys(::(\w+))?$/) {
-					my $tname = $2 || $record->{db} || $table;
-					$record->{passed} = "=--none--," . list_keys($tname, { joiner => ',' });
-				}
-			}
-		}
-		if($record->{pre_filter}) {
-			$value = Vend::Interpolate::filter_value($record->{pre_filter}, $value);
-		}
-		if($record->{lookup}) {
-			my $fld = $record->{field} || $record->{lookup};
-			my $key = $record->{lookup};
-			LOOK: {
-				my $dbname = $record->{db} || $table;
-				my $db = Vend::Data::database_exists_ref($dbname);
-				last LOOK unless $db;
-				my $query;
-				if ($record->{lookup_key}) {
-					$query = "select DISTINCT $record->{lookup_key}, $fld FROM $dbname ORDER BY $fld";
-				} else {
-					$query = "select DISTINCT $key, $fld FROM $dbname ORDER BY $fld";
-				}
-				my $ary = $db->query($query);
-				last LOOK unless ref($ary);
-				if(! scalar @$ary) {
-					push @$ary, ["=--no current values--"];
-				}
-				undef $record->{type} unless $record->{type} =~ /multi|combo/;
-				my $sub;
-				if($record->{lookup_exclude}) {
-					eval {
-						$sub = sub { $_[0] !~ m{$record->{lookup_exclude}}o };
-					};
-					if ($@) {
-						::logError(errmsg(
-										"Bad lookup pattern m{%s}: %s",
-										$record->{exclude},
-										$@,
-									));
-						$sub = \&CORE::length;
-					}
-				}
-				$sub = sub { length(@_) } if ! $sub;
-				$record->{passed} = join ",", grep $sub->($_),
-									map
-										{ $_->[1] =~ s/,/&#44;/g; $_->[0] . "=" . $_->[1]}
-									@$ary;
-				if($record->{options}) {
-					$record->{passed} =
-						join ",", $record->{options}, $record->{passed};
-				}
-				$record->{passed} = "=--no current values--"
-					if ! $record->{passed};
-			}
-		}
-		elsif ($record->{type} eq 'date') {
-			my $w = date_widget($column, $value);
-			$w .= qq{<INPUT TYPE=hidden NAME="ui_filter:$column" VALUE="date_change">};
-			return $w unless $o->{template};
-			return ($w, $record->{label}, $record->{help}, $record->{help_url});
-		}
-		elsif ($record->{type} eq 'imagedir') {
-			my $dir = $record->{'outboard'} || $column;
-			my @files = list_images($dir);
-			$record->{type} = 'combo';
-			$record->{passed} = join ",",
-									map { s/,/&#44;/g; $_} @files;
-		}
-		elsif ($record->{type} eq 'imagehelper') {
-            my $w = imagehelper_widget($column, $value, $record->{outboard});
-			return ($w, $record->{label}, $record->{help}, $record->{help_url});			
-        }
-		for(qw/append prepend/) {
-			next unless $record->{$_};
-			$record->{$_} = Vend::Util::resolve_links($record->{$_});
-			$record->{$_} =~ s/_UI_VALUE_/$value/g;
-			$record->{$_} =~ /_UI_URL_VALUE_/
-				and do {
-					my $tmp = $value;
-					$tmp =~ s/(\W)/sprintf '%%%02x', ord($1)/eg;
-					$record->{$_} =~ s/_UI_URL_VALUE_/$tmp/g;
-				};
-			$record->{$_} =~ s/_UI_TABLE_/$table/g;
-			$record->{$_} =~ s/_UI_COLUMN_/$column/g;
-			$record->{$_} =~ s/_UI_KEY_/$key/g;
-		}
-		for(qw/height width/) {
-			$record->{$_} = $o->{$_}
-				if defined $o->{$_};
-		}
-		if($record->{height}) {
-			if($record->{type} =~ /multi/i) {
-				$record->{type} = "MULTIPLE SIZE=$record->{height}";
-			}
-			elsif ($record->{type} =~ /textarea/i) {
-				my $width = $record->{width} || 80;
-				$record->{type} = "textarea_" . $record->{height} . '_' . $width;
-			}
+	}
+#::logDebug("meta_record has an item=$item and mdb=$mdb");
+
+	my $record;
+	if($view) {
+		$record = $mdb->row_hash("${view}::$item");
+	}
+	$record = $mdb->row_hash($item) if ! $record;
+#::logDebug("meta_record  record=$record");
+
+	return undef if ! $record;
+
+	# Get additional settings from extended field, which is a serialized
+	# hash
+	my $hash;
+	if($record->{extended}) {
+		$hash = Vend::Util::get_option_hash($record->{extended});
+		if(ref $hash eq 'HASH') {
+			@$record{keys %$hash} = values %$hash;
 		}
-		elsif ($record->{width}) {
-			if($record->{type} =~ /textarea/) {
-				$record->{type} = "textarea_2_" . $record->{width};
-			}
-			elsif($record->{type} =~ /text/) {
-				$record->{type} = "text_$record->{width}";
-			}
-			elsif($record->{type} =~ /radio|check/) {
-				$record->{type} =~ s/(left|right)[\s_]*\d*/$1 $record->{width}/;
-			}
+		else {
+			undef $hash;
 		}
+	}
+
 
-		$opt = {
-			attribute	=> ($record->{'attribute'}	|| $column),
-			table		=> ($record->{'db'}			|| $meta_db),
-			rows 		=> ($o->{rows} || $record->{height}),
-			cols 		=> ($o->{cols} || $record->{width}),
-			column		=> ($record->{'field'}		|| 'options'),
-			name		=> ($o->{'name'} || $record->{'name'} || $column),
-			outboard	=> ($record->{'outboard'}	|| $metakey),
-			passed		=> ($record->{'passed'}		|| undef),
-			type		=> ($o->{type} || $record->{'type'}		|| undef),
-			prepend		=> ($record->{'prepend'}	|| undef),
-			append		=> ($record->{'append'}		|| undef),
-		};
-#::logDebug("going to display for $opt->{name} type=$opt->{type}");
-		my $w = Vend::Interpolate::tag_accessories(
-				undef, undef, $opt, { $column => $value } );
-		my $filter;
-#::logDebug("filters: o=$o->{filter} r=$record->{filter}");
-		if($filter = ($o->{filter} || $record->{filter})) {
-			$w .= qq{<INPUT TYPE=hidden NAME="ui_filter:$column" VALUE="};
-			$w .= $filter;
-			$w .= '">';
-		}
-#::logDebug("template=$o->{template}");
-		return $w unless $o->{template};
-#::logDebug("supposed to return template: widget=$w record=" . ::uneval_it($record));
-		return ($w, $record->{label}, $record->{help}, $record->{help_url});
+	# Allow view settings to be placed in the extended area
+	if($view and $hash and $hash->{view}) {
+		my $view_hash = $record->{view}{$view};
+		ref $view_hash
+			and @$record{keys %$view_hash} = values %$view_hash;
 	}
-	return undef;
+#::logDebug("return meta_record=" . ::uneval($record) );
+	return $record;
 }
 
 1;



1.8.4.2   +58 -67    interchange/dist/lib/UI/ui.cfg


rev 1.8.4.2, prev_rev 1.8.4.1
Index: ui.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/ui.cfg,v
retrieving revision 1.8.4.1
retrieving revision 1.8.4.2
diff -u -r1.8.4.1 -r1.8.4.2
--- ui.cfg	20 Oct 2000 10:18:24 -0000	1.8.4.1
+++ ui.cfg	25 Jan 2003 22:21:12 -0000	1.8.4.2
@@ -1,95 +1,86 @@
-# Copyright (C) 2000 Akopia Corp. <heins@akopia.com>
+# Set global defaults for UI images location
+Variable UI_IMAGE_DIR /interchange/
+Variable UI_IMAGE_DIR_SECURE /interchange/
 
-# Author: Michael J. Heins, Akopia Corp. <heins@akopia.com>
-
-# This file is free software; you can redistribute it and/or modify it
-# under the terms of the GNU General Public License as published by the
-# Free Software Foundation; either version 2, or (at your option) any
-# later version.
-
-# This file is distributed in the hope that it will be
-# useful, but WITHOUT ANY WARRANTY; without even the implied warranty
-# of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-# General Public License for more details.
-
-# You should have received a copy of the GNU General Public License
-# along with this file; see the file COPYING.  If not, write to the Free
-# Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
-
-Variable UI_IMG /akopia/ui/
 # Set the base for the UI pages
 Variable UI_BASE admin
+Variable UI_HELP_TABLE ichelp
+#Variable UI_HELP_URL http://other-help-host/...
 
-# localized strings
-#ifdef UI_LOCALE_DE
-#include lib/UI/locales/de_DE.cfg
-#endif
-
-#ifdef UI_LOCALE_FR
-#include lib/UI/locales/fr_FR.cfg
-#endif
-
-#ifdef UI_LOCALE_IT
-#include lib/UI/locales/it_IT.cfg
-#endif
-
-#ifdef UI_LOCALE_RU
-#include lib/UI/locales/ru_RU.cfg
-#endif
+Variable UI_STATE_TABLE   state
+Variable UI_COUNTRY_TABLE country
 
+# This one is MV because used internally as well
+Variable MV_OPTION_TABLE options
 
-UserTag UI_initlocale Routine <<EOR
-sub {
-	package Vend::Config;
+# Load individual locale settings.
+# Comment this out to remove language selection box from login page.
+include lib/UI/locales/*_*.cfg
 
-	sub parse_deflocparse {	
-		# preserve locale information for UI
-		$C->{Locale_repository} = {} unless $C->{Locale_repository};
-		foreach my $key (keys %$Global::Locale_repository)
-		  {	
-    	    $C->{Locale_repository}{"MM_$key"} = 
-			         $Global::Locale_repository->{$key};
-	      }	
-	}
-}
-EOR
-
-AddDirective MM_InitLocale deflocparse default
+# Set up for default locale
+Locale en_US MV_LANG_NAME English
 
 # instruct Interchange to use this directory as alternative
 # for searching Interchange pages
 TemplateDir lib/UI/pages
 
-## This tag is here to initialize the imports
+# This tag is here to initialize the imports
+UserTag reconfigure Order table file
 UserTag reconfigure Routine <<EOR
 use UI::Primitive;
+use Vend::Table::Editor;
 *ui_check_acl = \&UI::Primitive::ui_check_acl;
 *ui_acl_enabled = \&UI::Primitive::ui_acl_enabled;
 *get_ui_table_acl = \&UI::Primitive::get_ui_table_acl;
 sub {
-	Vend::Util::logData("$Global::ConfDir/reconfig", $CGI::script_name)
+	my ($table, $file) = @_;
+	my $recon = $CGI::script_name;
+	if($table and $file) {
+		$recon .= " $table $file";
+	}
+	Vend::Util::logData("$Global::RunDir/reconfig", $recon)
 			and return "SUCCESS";
 	return "FAILED";
 }
 EOR
 
-Variable UI_MENU_CONTENT <<EOV
-code	img_dn	img_up	img_sel	page	url	alt	name
-[if-mm advanced order]2	B2.gif	B2_b.gif	B2_b.gif	__UI_BASE__/order		Order administration	Orders
-[/if-mm][if-mm advanced userdb]3	B3.gif	B3_b.gif	B3_b.gif	__UI_BASE__/customer		Customer administration	Customers
-[/if-mm][if-mm advanced items]4	B4.gif	B4_b.gif	B4_b.gif	__UI_BASE__/item		Item management	Items
-[/if-mm][if-mm advanced content]5	B5.gif	B5_b.gif	B5_b.gif	__UI_BASE__/page		Content edit	Content
-[/if-mm][if-mm advanced layout]6	B6.gif	B6_b.gif	B6_b.gif	__UI_BASE__/layout		Site design	Design
-[/if-mm][if-mm advanced items]7	B7.gif	B7_b.gif	B7_b.gif	__UI_BASE__/merchandising		merchandising	Merchandising
-[/if-mm][if-mm advanced stats]8	B8.gif	B8_b.gif	B8_b.gif	__UI_BASE__/genreport		Statistics and reports	Reports
-[/if-mm][if-mm advanced admin]9	B9.gif	B9_b.gif	B9_b.gif	__UI_BASE__/genconfig		System administration	Admin
-[/if-mm]
-EOV
+GlobalSub <<EOS
+sub admin_links {
+	return unless $Vend::admin;
+	my $tmpd = $Vend::Cfg->{ScratchDir};
+	$tmpd .= "/previews/$Vend::SessionID";
+	$Vend::Cfg->{PreviewDir} = $tmpd if -d $tmpd;
+	$::Variable->{ADL_SUFFIX} = $Vend::Cfg->{HTMLsuffix};
+	$::Variable->{ADL_PAGE} = $::Variable->{ADL_PAGE_TEMPLATE} || <<EOF;
+[page href="admin/content_editor" form="
+			ui_name=[var MV_PAGE 1][var ADL_SUFFIX]
+			ui_type=page
+		"][loc]edit[/loc]&nbsp;[loc]page[/loc]</A>
+EOF
+
+	$::Variable->{ADL_COMPONENT} = $::Variable->{ADL_COMPONENT_TEMPLATE} || <<EOF;
+[page href="admin/content_editor" form="
+			ui_name=[contol component]
+			ui_type=component
+		"][loc]edit[/loc]&nbsp;[control component]</A>
+EOF
+
+	$::Variable->{ADL_MENU} = $::Variable->{ADL_MENU_TEMPLATE} || <<EOF;
+<a class="[control link_class]"
+	href="[area
+			href=admin/menu_editor
+			form=|
+				qmenu_name=[either][control menu_name][or][var MV_PAGE 1][/either]
+			|
+		]">[loc]edit[/loc]&nbsp;[loc]menu[/loc]</A>
+EOF
+	return;
 
+}
+EOS
 
 # user tags
-#include lib/UI/usertag/*
-#include lib/UI/vars/*
+include lib/UI/vars/*
 Profiles lib/UI/profiles/*
 
-Message ...UI is loaded....
+Message ...UI is loaded...



No                   revision



No                   revision



2.8.2.1   +2 -2      interchange/dist/lib/UI/ContentEditor.pm


rev 2.8.2.1, prev_rev 2.8
Index: ContentEditor.pm
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/ContentEditor.pm,v
retrieving revision 2.8
retrieving revision 2.8.2.1
diff -u -r2.8 -r2.8.2.1
--- ContentEditor.pm	22 Jan 2003 15:26:59 -0000	2.8
+++ ContentEditor.pm	25 Jan 2003 22:21:12 -0000	2.8.2.1
@@ -2,7 +2,7 @@
 #
 # UI::ContentEditor - Interchange page/component edit
 # 
-# $Id: ContentEditor.pm,v 2.8 2003/01/22 15:26:59 mheins Exp $
+# $Id: ContentEditor.pm,v 2.8.2.1 2003/01/25 22:21:12 racke Exp $
 #
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -23,7 +23,7 @@
 
 package UI::ContentEditor;
 
-$VERSION = substr(q$Revision: 2.8 $, 10);
+$VERSION = substr(q$Revision: 2.8.2.1 $, 10);
 $DEBUG = 0;
 
 use POSIX qw/strftime/;



2.5.2.1   +0 -0      interchange/dist/lib/UI/ichelp.txt


rev 2.5.2.1, prev_rev 2.5
Index: ichelp.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/ichelp.txt,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



No                   revision



No                   revision



1.7.2.1   +0 -0      interchange/dist/lib/UI/locales/README


rev 1.7.2.1, prev_rev 1.7
Index: README
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/README,v
retrieving revision 1.7
retrieving revision 1.7.2.1
diff -u -r1.7 -r1.7.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/locales/TODO


rev 1.2.2.1, prev_rev 1.2
Index: TODO
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/TODO,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



2.12.2.1  +0 -0      interchange/dist/lib/UI/locales/da_DK.cfg


rev 2.12.2.1, prev_rev 2.12
Index: da_DK.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/da_DK.cfg,v
retrieving revision 2.12
retrieving revision 2.12.2.1
diff -u -r2.12 -r2.12.2.1



2.32.2.1  +0 -0      interchange/dist/lib/UI/locales/de_DE.cfg


rev 2.32.2.1, prev_rev 2.32
Index: de_DE.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/de_DE.cfg,v
retrieving revision 2.32
retrieving revision 2.32.2.1
diff -u -r2.32 -r2.32.2.1



2.24.2.1  +0 -0      interchange/dist/lib/UI/locales/default.cfg


rev 2.24.2.1, prev_rev 2.24
Index: default.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/default.cfg,v
retrieving revision 2.24
retrieving revision 2.24.2.1
diff -u -r2.24 -r2.24.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/locales/en_US.cfg


rev 1.1.2.1, prev_rev 1.1
Index: en_US.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/en_US.cfg,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/dist/lib/UI/locales/es_ES.cfg


rev 1.3.2.1, prev_rev 1.3
Index: es_ES.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/es_ES.cfg,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.4.2.1   +0 -0      interchange/dist/lib/UI/locales/he_IL.cfg


rev 1.4.2.1, prev_rev 1.4
Index: he_IL.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/he_IL.cfg,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/locales/ja_JP.cfg


rev 1.2.2.1, prev_rev 1.2
Index: ja_JP.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/ja_JP.cfg,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



2.16.2.1  +0 -0      interchange/dist/lib/UI/locales/nl_NL.cfg


rev 2.16.2.1, prev_rev 2.16
Index: nl_NL.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/nl_NL.cfg,v
retrieving revision 2.16
retrieving revision 2.16.2.1
diff -u -r2.16 -r2.16.2.1



1.4.2.1   +0 -0      interchange/dist/lib/UI/locales/pt_BR.cfg


rev 1.4.2.1, prev_rev 1.4
Index: pt_BR.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/pt_BR.cfg,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.12.2.1  +0 -0      interchange/dist/lib/UI/locales/sv_SE.cfg


rev 1.12.2.1, prev_rev 1.12
Index: sv_SE.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/locales/sv_SE.cfg,v
retrieving revision 1.12
retrieving revision 1.12.2.1
diff -u -r1.12 -r1.12.2.1



No                   revision



No                   revision



1.9.4.1   +46 -35    interchange/dist/lib/UI/pages/admin/access.html


rev 1.9.4.1, prev_rev 1.9
Index: access.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/access.html,v
retrieving revision 1.9
retrieving revision 1.9.4.1
diff -u -r1.9 -r1.9.4.1
--- access.html	5 Oct 2000 12:15:37 -0000	1.9
+++ access.html	25 Jan 2003 22:21:13 -0000	1.9.4.1
@@ -1,23 +1,25 @@
-[calc] $CGI->{no_dbmenu} = 1; $CGI->{access_menu} = 1; return [/calc]
-[set page_title]Administrator Accounts[/set]
+[calc]
+	$CGI->{no_dbmenu} = 1;
+	$CGI->{access_menu} = 1;
+	return;
+[/calc]
+[set page_title][L]Administrator Accounts[/L][/set]
 [set ui_class]Admin[/set]
 [set page_perm]access=l[/set]
 [set help_name]access.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 
 @_UI_STD_HEAD_@
-[if scratch ui_message]
-<P>
-<BLOCKQUOTE>
-	[scratch ui_message][set ui_message][/set]
-</BLOCKQUOTE>
-<P>
-&nbsp;
-[/if]
 
+[calc]
+	$Config->{NoSearch} =~ s/\baccess\b//;
+	$Config->{NoSearch} =~ s/^\|//;
+	$Config->{NoSearch} =~ s/\|$//;
+	return;
+[/calc]
 
 <form action="[area ui]" method=POST name=accessform>
-<farm action="/cgi-bin/test-cgi" name=accessform>
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="__UI_BASE__/user_edit">
 <INPUT TYPE=hidden NAME=ui_hide_key VALUE="1">
@@ -31,14 +33,14 @@
 <center>
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 [if-mm advanced access=c]
 
 <tr>
-<td colspan=2 bgcolor="__UI_C_INTBLOCK__">
+<td colspan=2 class=rnorm>
 
-[button text="Create new administrator" src="@_UI_IMG_@admin/create.gif"]
+[button text="[L]Create new user[/L]"]
 mv_nextpage=__UI_BASE__/user_edit
 user_id=NEW
 ui_hide_key=0
@@ -48,35 +50,35 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 [/if-mm]
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_LEFT_WIDTH__>
+<td class=rnorm width=__UI_LEFT_WIDTH__>
 
 [if-mm advanced access=e]
-	[button name=mv_junk value="Edit administrator" src="@_UI_IMG_@admin/edit.gif"][/button]<p>
+	[button name=mv_junk value="[L]Edit user[/L]"][/button]<p>
 [/if-mm]
 
 [if-mm advanced perm=v]
-[button value="Show permissions" src="@_UI_IMG_@admin/show.gif"]
+[button value="[L]Show permissions[/L]"]
 mv_nextpage=__UI_BASE__/access_permissions
 ui_return_to=@@MV_PAGE@@
 [/button]<p>
 [/if-mm]
 
 [if-mm advanced access=e]
-[button value="Change password" src="@_UI_IMG_@admin/change_password.gif"]
+[button value="[L]Change password[/L]"]
 mv_nextpage=__UI_BASE__/user_change_pass
 ui_hide_key=0
 [/button]
 <p>[/if-mm]
 
 [if-mm advanced access=d]
-[button text="Delete administrator"
+[button text="[L]Delete user[/L]"
 		form=accessform
-		confirm="Are you sure you want to delete this administrator?"
+		confirm="[L]Are you sure you want to delete this administrator?[/L]"
 		]
 mv_todo=return
 mv_nextpage=@@MV_PAGE@@
@@ -84,53 +86,62 @@
 [perl table="__UI_ACCESS_TABLE__"]
 	my $db = $Db{__UI_ACCESS_TABLE__};
 	if(! $db) {
-		$Scratch->{ui_message} = "Bad access table __UI_ACCESS_TABLE__";
+		$Scratch->{ui_message} = errmsg("Bad access table '%s'", '__UI_ACCESS_TABLE__');
 		return;
 	}
 	unless ( $db->delete_record($CGI->{user_id}) ) {
 		$Scratch->{ui_message} =
-			"Failed to delete administrator $CGI->{user_id} from table __UI_ACCESS_TABLE__";
+			errmsg("Failed to delete administrator %s from table %s", $CGI->{user_id}, '__UI_ACCESS_TABLE__');
 		return;
 	}
 	$Scratch->{ui_message} =
-			"Deleted administrator $CGI->{user_id} from table __UI_ACCESS_TABLE__";
-	return;
+			errmsg("Deleted administrator %s from table %s", $CGI->{user_id},
+  '__UI_ACCESS_TABLE__');
+	return ;
 [/perl]
 [/button]
 [/if-mm]
 
+[if-mm super]
+[button text="[L]Switch to user[/L]" form=accessform]
+mv_todo=return
+mv_nextpage=@@MV_PAGE@@
+mv_click=MMsu
+admin=1
+user=[cgi user_id]
+dest=admin/index
+[/button]
+[/if-mm]
+
 </td>
 
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_RIGHT_WIDTH__>
+<td class=rnorm width=__UI_RIGHT_WIDTH__>
 <select name="user_id" size=10>
 [loop search="
 		fi=access
 		st=db
+		ml=1000
 		co=yes
 		sf=username
 		se=:
 		bs=yes
 		ne=1
-		tf=name
+		tf=name,username
+		to=f
 	"]
   <option value="[loop-code]">[loop-code] -- [loop-data access name][if-loop-data access super]*[/if-loop-data]
 [/loop]
-</select>&nbsp;<B>* superuser</B>
+</select>&nbsp;<B>* [L]Site Administrator[/L]</B>
 </td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>
 
 <p>
-
-[button text="Back"]
-mv_todo=back
-mv_nextpage=index
-[/button]
 
 </form>
 



1.7.4.2   +144 -125  interchange/dist/lib/UI/pages/admin/access_permissions.html


rev 1.7.4.2, prev_rev 1.7.4.1
Index: access_permissions.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/access_permissions.html,v
retrieving revision 1.7.4.1
retrieving revision 1.7.4.2
diff -u -r1.7.4.1 -r1.7.4.2
--- access_permissions.html	7 Dec 2000 18:05:33 -0000	1.7.4.1
+++ access_permissions.html	25 Jan 2003 22:21:13 -0000	1.7.4.2
@@ -10,13 +10,22 @@
 [bounce page="__UI_BASE__/access"]
 [/if]
 
-[seti page_title]Edit Permissions: [cgi user_id][/seti]
+[seti page_title][L]Edit Permissions[/L]: [cgi user_id][/seti]
 [set ui_class]Admin[/set]
 [set page_perm]access=v[/set]
 [set help_name]access.permissions[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 
 [set process_perm]
+[flag type=write table="__UI_ACCESS_TABLE__"]
+[tmp ui_owner][db-hash
+				table="__UI_ACCESS_TABLE__"
+				column="table_control"
+				key="[cgi user_id]"][/tmp]
+[calc] $Scratch->{ui_owner} .= ";" if $Scratch->{ui_owner} =~ /\S/; return; [/calc]
+<!-- [calc]
+	$tc = [scratch ui_owner] '';
+[/calc] -->
 [perl]
 	my @filters = grep /^ui_filter:/, keys %$CGI;
 	foreach my $key (@filters) {
@@ -37,85 +46,93 @@
 	$CGI->{yes_tables} =~ s/\w+=(?:\s+|$)//g;
 	$CGI->{yes_tables} =~ s/(\w+)=vecdix(\s+|$)/$1$2/g;
 
+	$CGI->{owner_field} =~ s/\0//g;
+	$CGI->{owner_field} =~ s/,$//;
+	my (%of) = split /[=,]/, $CGI->{owner_field};
+
+	for(keys %of) {
+		if($of{$_} !~ /\S/) {
+			next unless defined $tc->{$_};
+			delete $tc->{$_}{owner_field};
+		}
+		else {
+			$tc->{$_}{owner_field} = $of{$_};
+		}
+	}
+
+	$CGI->{table_control} = $Tag->uneval( { ref => $tc } );
+	$CGI->{owner_field} =~ s/\w+=(?:\s+|$)//g;
+	$CGI->{owner_field} =~ s/(\w+)=vecdix(\s+|$)/$1$2/g;
+
 	$CGI->{no_tables} =~ s/\0/ /g;
 	
 	$CGI->{mv_todo} = 'set';
-	$CGI->{mv_nextpage} = '@@MV_PAGE@@';# unless $CGI->{mv_nextpage};
 	return;
 [/perl]
 [/set]
 
 @_UI_STD_HEAD_@
-[if scratch ui_message]
-<P>
-<BLOCKQUOTE>
-	[scratch ui_message][set ui_message][/set]
-</BLOCKQUOTE>
-<P>
-&nbsp;
-[/if]
-
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
-[if scratch ui_failure]
-	<FONT COLOR=RED>Failed: [scratch ui_failure][set ui_failure][/set]</FONT><BR>
-[/if]
-
+[output name=top_of_form]
 <FORM METHOD=POST ACTION="[area ui]">
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
 <INPUT TYPE=hidden NAME=mv_doit VALUE="set">
 <INPUT TYPE=hidden NAME=mv_click VALUE="process_perm">
-<INPUT TYPE=hidden NAME=mv_nextpage VALUE="[cgi ui_return_to]">
+<INPUT TYPE=hidden NAME=mv_nextpage VALUE="[either][cgi ui_return_to][or]__UI_BASE__/access[/either]">
 <INPUT TYPE=hidden NAME=user_id VALUE="[cgi user_id]">
 <INPUT TYPE=hidden NAME=username VALUE="[cgi user_id]">
 <INPUT TYPE=hidden NAME=mv_data_table VALUE="[value mv_data_table]">
 <INPUT TYPE=hidden NAME=mv_data_key VALUE="username">
 <INPUT TYPE=hidden NAME=mv_update_empty VALUE="1">
-<INPUT TYPE=hidden NAME=mv_data_fields VALUE="username yes_functions no_tables yes_tables">
+<INPUT TYPE=hidden NAME=mv_data_fields VALUE="username yes_functions no_tables yes_tables table_control">
 <INPUT TYPE=hidden NAME="mv_data_function" VALUE="update">
+[output name=""]
 
-
-<table __UI_T_PROPERTIES__>
-
-<tr>
-<td colspan=6 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
-</tr>
-
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>&nbsp;</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>View list</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>View detail</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Create</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Edit</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Delete</td>
+[tabbed-display
+	js-prefix="perm_"
+	width=800
+	height=800
+	]
+[tabbed-panel Editor Functions]
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+
+<tr class=rhead>
+<td class=rhead valign=top>&nbsp;</td>
+<td class=rhead valign=top>[L]View list[/L]</td>
+<td class=rhead valign=top>[L]View detail[/L]</td>
+<td class=rhead valign=top>[L]Create[/L]</td>
+<td class=rhead valign=top>[L]Edit[/L]</td>
+<td class=rhead valign=top>[L]Delete[/L]</td>
 </tr>
 
 [seti tables][list-databases][/seti]
 [perl tables="__UI_META_TABLE__ __UI_ACCESS_TABLE__"]
 
 	my @permissions = (
-        item		=> 'Item editor',
-        page		=> 'Page editor',
-        cat			=> 'Category editor',
-        tax			=> 'Tax editor',
-        shipping	=> 'Shipping editor',
-        payment		=> 'Payment editor',
-        affiliate	=> 'Affiliates editor',
-        itemtype	=> 'Item type editor',
-        pagetype	=> 'Page type editor',
-        grouptype	=> 'Group type editor',
-        matrix		=> 'Matrix editor',
-        knar		=> 'Knar editor',
-        access		=> 'Administrator Permissions',
-        group		=> 'Access Group editor',
-        perm		=> 'Permission editor',
-        layout		=> 'Layout editor',
+        item		=> '[L]Item editor[/L]',
+        page		=> '[L]Page editor[/L]',
+        cat			=> '[L]Category editor[/L]',
+        tax			=> '[L]Tax editor[/L]',
+        shipping	=> '[L]Shipping editor[/L]',
+        payment		=> '[L]Payment editor[/L]',
+        affiliate	=> '[L]Affiliates editor[/L]',
+        itemtype	=> '[L]Item type editor[/L]',
+        pagetype	=> '[L]Page type editor[/L]',
+        grouptype	=> '[L]Group type editor[/L]',
+        matrix		=> '[L]Matrix editor[/L]',
+        knar		=> '[L]Knar editor[/L]',
+        access		=> '[L]Administrator Permissions[/L]',
+        group		=> '[L]Access Group editor[/L]',
+        perm		=> '[L]Permission editor[/L]',
+        layout		=> '[L]Layout editor[/L]',
 	);
 	my %extra = qw/userdb 1 order 1/;
 	my $current = tag_data('__UI_ACCESS_TABLE__', 'yes_functions', $CGI->{user_id});
 	my $out = '';
 	my @ary = grep /\S/, split /[\s,\0]+/, $current;
-	my @some = qw/l v e c d/;
+	my @some = qw/l v c e d/;
 	my @more = qw/a u p/;
 	my @all = (@some, @more);
 	my %all;
@@ -141,27 +158,29 @@
 #DEBUG
 #	$out .= <<EOF;
 #<tr>
-#<td colspan=6 bgcolor=__UI_C_INTBLOCK__ valign=top>
+#<td colspan=6 class=rownorm valign=top>
 #$string
 #</td>
 #EOF
 
 	my $perm;
 	my $title;
+	my $inc = 0;
 	while( $perm = shift @permissions) {
 		$title = shift @permissions;
 		my $ref = $permref->{$perm} || {};
+		my $class = $inc++ % 2 ? 'rownorm' : 'rowalt';
 		$out .= <<EOF;
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
+<tr class=$class>
+<td class=$class valign=top>
 <b>$title</b>
 <input type=hidden value="$perm=" name="yes_functions">
 </td>
 EOF
 		for(@some) {
 			$out .= <<EOF;
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
-<INPUT type=checkbox value=$_ name="yes_functions"$ref->{$_}>
+<td class=$class valign=top>
+<INPUT type=checkbox class=s3 value=$_ name="yes_functions"$ref->{$_}>
 </td>
 EOF
 		}
@@ -169,35 +188,28 @@
 	}
 	my $ref = $permref->{order};
 	$out .= <<EOF;
-<tr>
-<td colspan=6 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
 </table>
- 
-<br>
+[/tabbed-panel]
 
-<table __UI_T_PROPERTIES__>
+[tabbed-panel Other Functions]
 
-<tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
-</tr>
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
-<b>Order manager:</b>
+<td class=rownorm valign=top>
+<b>[L]Order manager[/L]:</b>
 <INPUT type=hidden value="order=" name="yes_functions">
-<li><INPUT type=checkbox value=l name="yes_functions"$ref->{l}> View list
-<li><input type=checkbox value=v name="yes_functions"$ref->{v}> View single
-<li><input type=checkbox value=d name="yes_functions"$ref->{d}> Delete
-<li><input type=checkbox value=e name="yes_functions"$ref->{e}> Edit
-<li><input type=checkbox value=c name="yes_functions"$ref->{c}> Input new
-<li><input type=checkbox value=a name="yes_functions"$ref->{a}> Archive
-<li><input type=checkbox value=u name="yes_functions"$ref->{u}> Un-archive
+<li><INPUT type=checkbox value=l name="yes_functions"$ref->{l}> [L]View list[/L]
+<li><input type=checkbox value=v name="yes_functions"$ref->{v}> [L]View single[/L]
+<li><input type=checkbox value=d name="yes_functions"$ref->{d}> [L]Delete[/L]
+<li><input type=checkbox value=e name="yes_functions"$ref->{e}> [L]Edit[/L]
+<li><input type=checkbox value=c name="yes_functions"$ref->{c}> [L]Input new[/L]
+<li><input type=checkbox value=a name="yes_functions"$ref->{a}> [L]Archive[/L]
+<li><input type=checkbox value=u name="yes_functions"$ref->{u}> [L]Un-archive[/L]
 <INPUT type=hidden value="," name="yes_functions">
 <p>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top ROWSPAN=2>
+<td class=rownorm valign=top ROWSPAN=2>
 EOF
 	@permissions = (
 		orderstats		=> 'Order statistics utility',
@@ -206,15 +218,19 @@
 		stats			=> 'Stats menu',
 		techadmin		=> 'Technical Admin menu',
 		sitedesign		=> 'Site Design menu',
-		config			=> 'Apply changes',
+		reconfig		=> 'Apply changes',
+		delete_files	=> 'Delete owned files',
 		dbupload		=> 'Database importer',
 		dbdownload		=> 'Database exporter',
 		layupload		=> 'Layout importer',
 		laydownload		=> 'Layout exporter',
+		gentable		=> 'List tables',
 		gensql			=> 'Direct SQL utility',
+		dbconfig		=> 'Database configuration',
+		files			=> 'Modify Files',
 	);
 	while($perm = shift @permissions ) {
-		$title = shift @permissions;
+		$title = errmsg(shift @permissions);
 		my $on = defined $permref->{$perm} ? ' CHECKED' : '';
 		$out .= <<EOF;
 <li><INPUT type=checkbox value="$perm," name="yes_functions"$on> <b>$title</b>
@@ -227,15 +243,15 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
-<b>Administrator Permissions:</b>
+<td class=rownorm valign=top>
+<b>[L]Customer Edit Permissions[/L]:</b>
 <INPUT type=hidden value="userdb=" name="yes_functions">
-<li><INPUT type=checkbox value=l name="yes_functions"$ref->{l}> View list
-<li><input type=checkbox value=v name="yes_functions"$ref->{v}> View single
-<li><input type=checkbox value=d name="yes_functions"$ref->{d}> Delete
-<li><input type=checkbox value=e name="yes_functions"$ref->{e}> Edit
-<li><input type=checkbox value=c name="yes_functions"$ref->{c}> Input new
-<li><input type=checkbox value=p name="yes_functions"$ref->{p}> Mail password
+<li><INPUT type=checkbox value=l name="yes_functions"$ref->{l}> [L]View list[/L]
+<li><input type=checkbox value=v name="yes_functions"$ref->{v}> [L]View single[/L]
+<li><input type=checkbox value=d name="yes_functions"$ref->{d}> [L]Delete[/L]
+<li><input type=checkbox value=e name="yes_functions"$ref->{e}> [L]Edit[/L]
+<li><input type=checkbox value=c name="yes_functions"$ref->{c}> [L]Input new[/L]
+<li><input type=checkbox value=p name="yes_functions"$ref->{p}> [L]Mail password[/L]
 <INPUT type=hidden value="," name="yes_functions">
 <p>
 </td>
@@ -244,46 +260,37 @@
 	return $out;
 [/perl]
 
-<tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
-</tr>
-
 </table>
 
-<p>
+[/tabbed-panel]
 
-<table cellpadding=3 cellspacing=0 width=100%>
+[tabbed-panel Table Permissions]
 
-<tr>
-<td colspan=8 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
-</tr>
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
 
 <tr>
-<td colspan=8 bgcolor=__UI_C_INTBLOCK__ ALIGN=center><B>Table Permissions</B></td>
+<td colspan=9 class=rhead ALIGN=center><B>[L]Table Permissions[/L]</B></td>
 </tr>
 
 <tr>
-<td colspan=8 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td class=rhead valign=top>&nbsp;</td>
+<td class=rhead valign=top>[L]HIDE[/L]</td>
+<td class=rhead valign=top>[L]View[/L]</td>
+<td class=rhead valign=top>[L]Edit[/L]</td>
+<td class=rhead valign=top>[L]Create[/L]</td>
+<td class=rhead valign=top>[L]Delete[/L]</td>
+<td class=rhead valign=top>[L]Import[/L]</td>
+<td class=rhead valign=top>[L]Export[/L]</td>
+<td class=rhead valign=top>[L]Owner field[/L]</td>
 </tr>
 
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>&nbsp;</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>HIDE</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>View</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Edit</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Create</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Delete</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Import</td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>Export</td>
-</tr>
-
-
 [perl]
 
 	my $current = tag_data('__UI_ACCESS_TABLE__', 'yes_tables', $CGI->{user_id})
 					|| $Scratch->{tables};
 	$current =~ s/\s+/ /g;
 	my $no = tag_data('__UI_ACCESS_TABLE__', 'no_tables', $CGI->{user_id});
+
 	$no =~ s/\s+/ /g;
 	#Log("no = $no");
 	my (@no) = split /\s+/, $no;
@@ -329,49 +336,61 @@
 
 	my $perm;
 	my $title;
+	my $inc = 0;
 	while( $perm = shift @permissions) {
 		$title = shift @permissions;
+		my $class = $inc++ % 2 ? 'rownorm' : 'rowalt';
 		my $ref = $permref->{$perm} || {};
 		$out .= <<EOF;
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
+<tr class=$class>
+<td class=$class valign=top>
 <b>$title</b>
 <input type=hidden value="$perm=" name="yes_tables">
 </td>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
-<INPUT type=checkbox value="$perm" name="no_tables"$no{$perm}>
+<td class=$class valign=top>
+<INPUT type=checkbox class=s3 value="$perm" name="no_tables"$no{$perm}>
 </td>
 EOF
 		for(@all) {
 			$out .= <<EOF;
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
+<td class=$class valign=top>
 <INPUT type=checkbox value=$_ name="yes_tables"$ref->{$_}>
 </td>
 EOF
 		}
+
+		my $of = '';
+		if($tc->{$perm}) {
+			$of = $tc->{$perm}{owner_field};
+		}
+		$out .= <<EOF;
+<td class=$class valign=top>
+<INPUT type=hidden value="$perm=" name="owner_field">
+<INPUT type=text value="$of" name="owner_field" size=10>
+<INPUT type=hidden value="," name="owner_field">
+</td>
+EOF
 		$out =~ s!(<.td>\s*)$!<input type=hidden value="," name="yes_tables">$1</tr>!;
 	}
 	#$Scratch->{string} = $string;
 	return $out;
 	[/perl]
 
-<tr>
-<td colspan=8 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
-</tr>
-
 </table>
+[/tabbed-panel]
+[/tabbed-display]
 
-<input type=submit value="Ok">
-
-[button text="Cancel"]
-mv_todo=back
-mv_nextpage=[either][value-extended name=ui_return_to index=0][or]__UI_BASE__/access[/either]
-mv_data_table=[cgi mv_data_table]
-[/button]
-
-<BR>
+[output name=top_buttons]
+	<input type=submit value="[L]Ok[/L]" class=s3 style="font-weight: bold; width: 40px; text-align: center">
+	<input type=submit name=mv_click value="[L]Cancel[/L]" class=s3>
+
+[output name=bottom_buttons]
+	<input type=submit value="[L]Ok[/L]" class=s3 style="font-weight: bold; width: 40px; text-align: center">
+	<input type=submit name=mv_click value="[L]Cancel[/L]" class=s3>
 
+[output name=bottom_of_form]
 </form>
+[output name=""]
 @_UI_STD_FOOTER_@
 
 <!-- page: @@MV_PAGE@@ -->



1.1.2.3   +13 -320   interchange/dist/lib/UI/pages/admin/add_meta_option.html


rev 1.1.2.3, prev_rev 1.1.2.2
Index: add_meta_option.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/add_meta_option.html,v
retrieving revision 1.1.2.2
retrieving revision 1.1.2.3
diff -u -r1.1.2.2 -r1.1.2.3
--- add_meta_option.html	5 Dec 2000 11:01:05 -0000	1.1.2.2
+++ add_meta_option.html	25 Jan 2003 22:21:13 -0000	1.1.2.3
@@ -41,16 +41,9 @@
 	[bounce page="__UI_BASE__/error"]
 [/if-mm]
 
-[calc]
-	$CGI->{ui_meta_view} = 'optadd';
-	$Scratch->{ui_override_table} = $CGI->{mv_data_table} = '__UI_META_TABLE__';
-	$CGI->{ui_hide_key} = 1;
-	$CGI->{ui_data_fields} = 'code options';
-	return;
-[/calc]
-
-@_UI_STD_DBEDIT_HEAD_@
+[comment] BEGIN former UI_STD_DBEDIT_HEAD [/comment]
 
+[tmp table_perm][cgi mv_data_table][/tmp]
 [set ui_class]Admin[/set]
 [set help_name]meta.edit[/set]
 [set icon_name][/set]
@@ -61,317 +54,17 @@
 @_UI_STD_HEAD_@
 <!-- ----- BEGIN REAL STUFF ----- -->
 
-[if scratch ui_failure]
-	<FONT COLOR=RED>Failed:
-	[scratch ui_failure][set ui_failure][/set]</FONT><BR>
-[/if]
-
-<FORM METHOD=POST ACTION="[area process]">
-<INPUT TYPE=hidden NAME=mv_doit VALUE="set">
-<INPUT TYPE=hidden NAME=mv_click VALUE="process_filter">
-<INPUT TYPE=hidden NAME=mv_click VALUE="enable_it">
-<INPUT TYPE=hidden NAME=mv_nextpage VALUE="[either][cgi ui_nextpage][or]__UI_BASE__/flex_select[/either]">
-<INPUT TYPE=hidden NAME=mv_data_table VALUE="[value mv_data_table]">
-<INPUT TYPE=hidden NAME=ui_meta_specific VALUE="[cgi ui_meta_specific]">
-<INPUT TYPE=hidden NAME=ui_hide_key VALUE="[cgi ui_hide_key]">
-<INPUT TYPE=hidden NAME=ui_display_only VALUE="[cgi ui_display_only]">
-<INPUT TYPE=hidden NAME=ui_meta_view VALUE="[cgi ui_meta_view]">
-<INPUT TYPE=hidden NAME=item_id_left VALUE="[cgi item_id_left]">
-<INPUT TYPE=hidden NAME=ui_sequence_edit VALUE="[cgi ui_sequence_edit]">
-<INPUT TYPE=hidden NAME=mv_data_key VALUE="[value ui_data_key_name]">
-<INPUT TYPE=hidden NAME=mv_data_decode VALUE="[value mv_data_decode]">
-[calc]
-	$ui_img = q{@_UI_IMG_@};
-	unless ($CGI->{ui_return_to}) {
-		$CGI->{ui_return_to} = "[var MV_PAGE global]\0item_id=$Scratch->{arg}";
-	}
-	@inst = split /\0/, $CGI->{ui_return_to};
-	my $out;
-	for(@inst) {
-		s/"/&quot;/g;
-		$out .= <<EOF;
-<INPUT TYPE=hidden NAME=ui_return_to VALUE="$_">
-EOF
-	}
-	return $out;
-[/calc]
-<INPUT TYPE=hidden NAME=mv_update_empty VALUE="1">
-
-[if-key-exists table="[value mv_data_table]" key="[scratch arg]"]
-<INPUT TYPE=hidden NAME="mv_data_function" VALUE="update">
-[else]
-<INPUT TYPE=hidden NAME="mv_data_function" VALUE="insert">
-[/else]
-[/if-key-exists]
-
-<table width="60%" border="" cellspacing="0" cellpadding="0" bordercolor="__UI_C_TITLEBARBG__">
-<tr>
-  <td>
-
-<table cellspacing=0 cellmargin=0 width="100%" cellpadding="2" align="center" border="0">
-
-<tr bgcolor="__UI_C_TITLEBARBG__"> 
-<td align=right colspan=2><img src="@_UI_IMG_@admin/bg.gif" width=1 height=3 alt=x></td>
-</tr>
-
-[comment]
-Display an extra Ok/Cancel button pair if there are more than
-4 rows of input, so user doesn't have to scroll to bottom of page.
-[/comment]
-[perl]
-      my $linecount = (split / /, $CGI->{ui_data_fields}) - 1;
-      my $out = '';
-      $out .= <<'EOF' if $linecount > 4;
-<TR BGCOLOR="__UI_T_ROW_EVEN__">
-<td>&nbsp;</td>
-<td align=left>
-<B><INPUT TYPE=submit NAME=mv_click VALUE="Ok">
-</B>
-&nbsp;
-<INPUT TYPE=submit NAME=mv_click VALUE="Cancel">
-</TD>
-</TR>
-
-<tr BGCOLOR="__UI_C_TITLEBARBG__">
-<td colspan=2><img src="${ui_img}admin/bg.gif" width=1 height=3 alt=x></td>
-</tr>
-
-EOF
-[/perl]
-
-[mvasp tables="[list-databases] __UI_META_TABLE__ __UI_ACCESS_TABLE__"]
-<%
-	my $table	= $Values->{mv_data_table};
-	my $mtable	= q{__UI_META_TABLE__} || 'mv_metadata';
-	my $db		= $Db{$table};
-	my $mdb		= $Db{$mtable};
-	my %break;
-	my %break_label;
-	if($CGI->{ui_break_before}) {
-		my @tmp = grep /\S/, split /[\s,\0]+/, $CGI->{ui_break_before};
-		@break{@tmp} = @tmp;
-		if($CGI->{ui_break_before_label}) {
-			@tmp = grep /\S/, split /\s*[,\0]\s*/, $CGI->{ui_break_before_label};
-			for(@tmp) {
-				my ($br, $lab) = split /\s*=\s*/, $_;
-				$break_label{$br} = $lab;
-			}
-		}
-	}
-	if(!$db) {
-		return "<TR><TD>Broken table '$table'</TD></TR>";
-	}
-
-	my %display_only;
-	if($CGI->{ui_display_only}) {
-		my @do = split /[\0,\s]+/, $CGI->{ui_display_only};
-		for(@do) {
-			$display_only{$_} = 1;
-			$CGI->{ui_data_fields} =~ s/\b$_\b//;
-		}
-	}
-
-	my $key		= $CGI->{item_id};
-	my $keycol  = $db->config('KEY');
-	my $passed_fields = $Values->{ui_data_fields};
-	my @extra_cols;
-	my %ok_col;
-	while($passed_fields =~ s/(\w+:+\S+)//) {
-		push @extra_cols, $1;
-	}
-	my (@cols)  = split /\s+/, $Tag->db_columns( {
-										name	=> $table,
-										columns	=> $passed_fields,
-										passed_order => 1,
-									});
-
-	if($Values->{ui_data_fields}) {
-		for(@cols, @extra_cols) {
-			unless (/^(\w+):+(\S+)/) {
-				$ok_col{$_} = 1;
-				next;
-			}
-			my $t = $1;
-			my $c = $2;
-			next unless $Tag->db_columns( { name	=> $t, columns	=> $c, });
-			$ok_col{$_} = 1;
-		}
-		@cols = grep $ok_col{$_}, split /\s+/, $Values->{ui_data_fields};
-	}
-
-	my $super = $Tag->if_mm('super');
-
-	my $refkey = $key;
-
-	if($db->record_exists($key)) {
-#Log("Should work. key=$key table=$table");
-	}
-	elsif($db->config('AUTO_NUMBER')) {
-		$CGI->{$Values->{ui_data_key_name}} = '';
-		undef $key;
-	}
-	else {
-		$CGI->{$Values->{ui_data_key_name}} = $key;
-		undef $key;
-	}
-	foreach my $col (@cols) {
-		if($CGI->{ui_hide_key} and $col eq $keycol) {
-			$Document->write(<<EOF);
-<INPUT TYPE=hidden NAME="$col" VALUE="$Scratch->{arg}">
-EOF
-			next;
-		}
-
-		my $do = $display_only{$col};
-		
-		my $currval;
-		if($col =~ /(\w+):+(\S+)/) {
-			$t = $1;
-			$c = $2;
-			$Scratch->{mv_data_enable} .= " $t "
-				unless $do or $Scratch->{mv_data_enable} =~ /\b$t\b/;
-		}
-		else {
-			$t = $table;
-			$c = $col;
-		}
-
-		my $type;
-		if($do) {
-			my $k = defined $key ? $key : $refkey;
-			$currval = tag_data($t, $c, $k);
-			$type = 'value';
-#Log("hit display_only for $col, t=$t, c=$c, k=$k, currval=$currval");
-		}
-		elsif($CGI->{$col} and !defined($key) || !tag_data($t, $c, $key) ) {
-			$currval = $CGI->{$col};
-		}
-		else {
-			$currval = delete $Scratch->{"ui_preload:$t:$c"} || undef;
-		}
-
-		my $meta = '';
-		my $display = $Tag->display({
-										table => $t,
-										column => $c,
-										name => $col,
-										key => $key,
-										type => $type,
-										default => $currval,
-										arbitrary => $CGI->{ui_meta_view},
-										fallback => 1,
-										template => q(
-<TR BGCOLOR="__UI_T_ROW_EVEN__">
-   <td align=left width=150> 
-     <font color="__UI_C_TEXT__" size="-1"><b>$LABEL$</b>~META~
-   </td>
-   <td valign=TOP> 
-     <table cellspacing=0 cellmargin=0 width="100%">
-       <tr> 
-         <td width="60%"> 
-           <FONT SIZE="-1">$WIDGET$</FONT>
-         </td>
-         <td><FONT SIZE="-1"><i>$HELP$</i>{HELPURL}<BR><A HREF="$HELP_URL$">help</A>{/HELPURL}</FONT></td>
-       </tr>
-     </table>
-   </td>
- </tr>
-),
-									});
-		if($super and ($Variable->{UI_META_LINK} || $Values->{ui_meta_force}) ) {
-			$meta .= '<BR><FONT SIZE=1>';
-			# Get global variables
-			my $base = $Tag->var('UI_BASE', 1);
-			my $page = $Tag->var('MV_PAGE', 1);
-			$meta .= $Tag->page(
-							{	href => "$base/meta_editor",
-								form => qq{
-										item_id=${t}::$c
-										ui_return_to=$page
-										ui_return_to=item_id=$Scratch->{arg}
-										ui_return_to=ui_return_table=$t
-										}
-							});
-			$meta .= 'meta</A>';
-			$meta .= '<br>' . $Tag->page(
-							{	href => "$base/meta_editor",
-								form => qq{
-										item_id=${t}::${c}::$key
-										mv_data_table=$mtable
-										ui_hide_key=1
-										ui_meta_view=metaconfig
-										ui_return_to=$page
-										ui_return_to=item_id=$Scratch->{arg}
-										ui_return_to=ui_return_table=$t
-										}
-							}) . 'item-specific meta</A></FONT>'
-				if $CGI->{ui_meta_specific};
-			$meta .= '</FONT>';
-		}
-        #unless ($label) {
-            #$Document->write ($display);
-            #next;
-        #}
-		$Document->write(<<EOF) if $break{$col};
-<TR BGCOLOR="__UI_T_ROW_ODD__">
-	<TD COLSPAN=2><B>$break_label{$col}</B><IMG SRC="${ui_img}admin/bg.gif" WIDTH=1 HEIGHT=1 alt=x></TD>
-</TR>
-EOF
-		$display =~ s/\~META\~/$meta/g;
-		$Document->write($display);
-	}
-%>
-[/mvasp]
-
-<INPUT TYPE=hidden NAME=mv_data_fields VALUE="[cgi ui_data_fields]">
-
-<tr>
-<td colspan=2 BGCOLOR="__UI_C_TITLEBARBG__"><img src="@_UI_IMG_@admin/bg.gif" height=3 alt=x></td>
-</tr>
-
-<TR BGCOLOR="__UI_T_ROW_EVEN__">
-<td>&nbsp;</td>
-<td align=left>
-<B>[button text="Ok"]
-[return-to click]
-mv_todo=set
-mv_data_table=[cgi mv_data_table]
-[/button]</B>
-&nbsp;
-&nbsp;
-[button text="Cancel"]
-mv_todo=return
-[return-to click]
-[/button]
-[if-mm tables =x]
-<small>
-&nbsp;
-&nbsp;
-&nbsp;
-&nbsp;
-&nbsp;
-	[if !value ui_too_large]
-	[if-mm super]
-	<INPUT TYPE=checkbox NAME=mv_auto_export CHECKED VALUE="[value mv_data_table]">
-		Auto-export
-	[else]
-	<INPUT TYPE=hidden NAME=mv_auto_export VALUE="[value mv_data_table]">
-	[/else]
-	[/if-mm]
-	[/if]
-[/if-mm]
-</small>
-</td>
-</tr>
-
-<tr>
-<td colspan=2 BGCOLOR="__UI_C_TITLEBARBG__"><img src="@_UI_IMG_@admin/bg.gif" height=3 alt=x></td>
-</tr>
-
-</table>
-</td></tr></table>
-
-</form>
+[table-editor
+	table="[either]__UI_META_TABLE__[or]mv_metadata[/either]"
+	key="[cgi item_id]"
+	ui_data_fields="code options"
+	no-table-meta=1
+	label.options="Specials"
+	widget.options="option_format"
+	help.options="Add a promotion type by placing the key in the left column, and some descriptive text in the right-hand column."
+	tabbed=0
+	cgi=1
+	][/table-editor]
 
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->



1.10.4.10 +32 -28    interchange/dist/lib/UI/pages/admin/affiliates.html


rev 1.10.4.10, prev_rev 1.10.4.9
Index: affiliates.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/affiliates.html,v
retrieving revision 1.10.4.9
retrieving revision 1.10.4.10
diff -u -r1.10.4.9 -r1.10.4.10
--- affiliates.html	5 Nov 2000 12:54:09 -0000	1.10.4.9
+++ affiliates.html	25 Jan 2003 22:21:13 -0000	1.10.4.10
@@ -10,11 +10,12 @@
 [/if-mm]
 [/comment]
 
+
 [set ui_class]Merchandising[/set]
 [set page_title]Affiliates manager[/set]
 [set table_perm]1[/set]
 [set help_name]affiliate.manager[/set]
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
 [calc]
         $CGI->{affiliates} = 1;
         return;
@@ -37,7 +38,7 @@
 <INPUT TYPE=submit VALUE="Limit with search">
 </FORM>
 [if cgi ui_text_qualification]
-<H3>Entries containing "[cgi ui_text_qualification]"</H3>
+<H3>[msg arg.0="[cgi ui_text_qualification]"]Entries containing "%s"[/msg]</H3>
 [/if]
 [search-region more=1 arg="
 		[if cgi ui_text_qualification]
@@ -48,7 +49,7 @@
 			tf=[cgi ui_sort_field]
 			to=[cgi ui_sort_option]
 		[else]
-			tf=name
+			tf=description
 		[/else]
 		[/if]
 		st=db
@@ -70,45 +71,49 @@
 	}
 	return;
 [/calc]
-[seti key][dbinfo table=__UI_AFFILIATE_TABLE__ attrib=KEY][/seti]
 <TABLE border=0 CELLSPACING=0 width="90%">
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<TR BGCOLOR="__UI_C_TITLEBARBG__">
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
-	return "ui_sort_field=$Scratch->{key}\n" . sortrev($Scratch->{key});
-	`]Code</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
+<tr class=rspacer><td colspan=8></td></tr>
+<tr class=rmarq>
+<td>[page
+					extra=rmarq
+					href=@@MV_PAGE@@
+					form=`
+							return "ui_sort_field=affiliate\n" . sortrev('affiliate');
+					`]Code</td>
+<td>[page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=name\n" . sortrev('name');
-	`]Name</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">Linkback and entry URLs</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Reports</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
-	return "ui_sort_field=active\n" . sortrev('active');
-	`]Active</TH>
+	` extra=rmarq]Name</td>
+<td class=rmarq>Linkback and entry URLs</td>
+<td align=center class=rmarq>Reports</td>
+	<td align=center class=rmarq>
+	[page href=@@MV_PAGE@@ extra=rmarq
+		form=`
+			return "ui_sort_field=active\n" . sortrev('active');
+		`]Active</a>
+	</td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=5></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=5></td></tr>
+<tr class=rspacer><td colspan=5></td></tr>
 [/on-match]
 [search-list]
-<TR [item-alternate 2]BGCOLOR="__UI_T_ROW_EVEN__"[else]BGCOLOR="__UI_T_ROW_ODD__"[/else][/item-alternate]>
+<TR [item-alternate 2]class=rnorm[else]class=ralt[/else][/item-alternate]>
 <TD VALIGN=top>[page
 				href=__UI_BASE__/flex_editor
 				form="
 					item_id=[item-code]
-					page_title=Edit affiliate -- [item-data __UI_AFFILIATE_TABLE__ name]
-					page_banner=Edit affiliate: <B>[item-data __UI_AFFILIATE_TABLE__ name]</B>
+					page_title=Edit affiliate -- [item-data affiliate name]
+					page_banner=Edit affiliate: <B>[item-data affiliate name]</B>
 					mv_data_table=__UI_AFFILIATE_TABLE__
-					icon_name=admin/icon_people.gif
+					icon_name=icon_people.gif
 					ui_return_to=__UI_BASE__/affiliates
 					help_name=affiliate.edit
 				"][item-code]</A></TD>
-<TD VALIGN=top>[item-data __UI_AFFILIATE_TABLE__ name]</TD>
-<TD VALIGN=top><font size=-1>linkback:&nbsp;<A href="[item-data __UI_AFFILIATE_TABLE__ url]">[item-data __UI_AFFILIATE_TABLE__ url]</A><br>
+<TD VALIGN=top>[item-data affiliate name]</TD>
+<TD VALIGN=top><span style="font-size: small">linkback:&nbsp;<A href="[item-data affiliate url]">[item-data affiliate url]</A><br>
 entry:&nbsp;[calc]
 	my $url = $Config->{VendURL};
 	$url .=  q{?mv_pc=[item-code]};
 	return qq{<A HREF="$url">$url</A>};
-[/calc]</font>
+[/calc]</span>
 </TD>
 <TD ALIGN=CENTER VALIGN=TOP>[page href="__UI_BASE__/reports/order/ByAffiliate"
 				form="
@@ -120,7 +125,7 @@
 				start_date=[tag time]%Y%m[/tag]
 				affiliate=[item-code]
 				"]Traffic</A></td>
-<TD ALIGN=CENTER VALIGN=top>[if-item-data __UI_AFFILIATE_TABLE__ active]Yes[else]No[/else][/if-item-data]
+<TD ALIGN=CENTER VALIGN=top>[if-item-data affiliate active]Yes[else]No[/else][/if-item-data]
 </TD>
 </tr>
 [/search-list]
@@ -133,8 +138,7 @@
 </td>
 </tr>
 [/no-match]
-<tr bgcolor="#000000" height=1><td colspan=5></td></tr>
-<tr bgcolor="#FFFFFF" height=8><td colspan=5></td></tr>
+<tr class=rborder height=1><td colspan=5></td></tr>
 [more-list]
 <tr>
 <td colspan=5 align=center>



1.1.2.2   +2 -2      interchange/dist/lib/UI/pages/admin/bug_report.html


rev 1.1.2.2, prev_rev 1.1.2.1
Index: bug_report.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/bug_report.html,v
retrieving revision 1.1.2.1
retrieving revision 1.1.2.2
diff -u -r1.1.2.1 -r1.1.2.2
--- bug_report.html	14 Oct 2000 14:47:56 -0000	1.1.2.1
+++ bug_report.html	25 Jan 2003 22:21:13 -0000	1.1.2.2
@@ -1,11 +1,11 @@
 [set page_title]Bug report[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [set page_perm]bug[/set]
 @@UI_STD_HEAD@@
 
 If you are uncertain of the genesis of this problem, 
 please highlight the following text and then press SHIFT-DELETE. Once you
-have done that, <A HREF="http://developer.akopia.com/bugs/enter_bug.cgi">login to Bugzilla</A>
+have done that, <A HREF="http://interchange.redhat.com/bugs/enter_bug.cgi">login to Bugzilla</A>
 and enter a bug report, using SHIFT-INSERT to place the text in the 
 Description section.
 <FORM>



1.3.4.2   +15 -4     interchange/dist/lib/UI/pages/admin/build_related.html


rev 1.3.4.2, prev_rev 1.3.4.1
Index: build_related.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/build_related.html,v
retrieving revision 1.3.4.1
retrieving revision 1.3.4.2
diff -u -r1.3.4.1 -r1.3.4.2
--- build_related.html	14 Oct 2000 14:47:56 -0000	1.3.4.1
+++ build_related.html	25 Jan 2003 22:21:13 -0000	1.3.4.2
@@ -2,8 +2,9 @@
 [set ui_class]Merchandising[/set]
 [set page_perm]regen[/set]
 [set help_name]merch.build_related[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 
+[flag type=write table=merchandising]
 <!-- ----- BEGIN REAL STUFF ----- -->
 
 @_UI_STD_HEAD_@
@@ -11,10 +12,10 @@
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width="__UI_LEFT_WIDTH__" valign=top colspan=2>
+<td class=rnorm width="__UI_LEFT_WIDTH__" valign=top colspan=2>
 
 [calc]
 	%sku = (
@@ -69,6 +70,16 @@
 			}
 		}
 	}
+
+	for(keys %sku) {
+		delete $sku{$_} if ! $_;
+	}
+
+	my @count = keys %sku;
+
+	return errmsg("No order history found.")
+		if ! @count;
+
 	my $mdb = $Db{merchandising};
 	for(sort keys %sku) {
 		my $val = $Tag->uneval( { ref => $sku{$_} } );
@@ -82,7 +93,7 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.10.4.1  +32 -33    interchange/dist/lib/UI/pages/admin/button_builder.html


rev 1.10.4.1, prev_rev 1.10
Index: button_builder.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/button_builder.html,v
retrieving revision 1.10
retrieving revision 1.10.4.1
diff -u -r1.10 -r1.10.4.1
--- button_builder.html	23 Sep 2000 17:55:32 -0000	1.10
+++ button_builder.html	25 Jan 2003 22:21:13 -0000	1.10.4.1
@@ -1,7 +1,7 @@
 [set page_title]Button builder[/set]
 [set ui_class]Design[/set]
 [set help_name]button.builder[/set]
-[set icon_name]admin/icon_pages.gif[/set]
+[set icon_name]icon_pages.gif[/set]
 [set mv_no_session_id][/set]
 [set empty_basket]
 	[calc]
@@ -13,8 +13,7 @@
 <!-- ----- BEGIN REAL STUFF ----- -->
 
 [if scratch ui_failure]
-	<FONT COLOR=RED>Failed:
-	[scratch ui_failure][set ui_failure][/set]</FONT><BR>
+	<blockquote class=cerror>Failed: [scratchd ui_failure]</blockquote>
 [/if]
 
 <P>
@@ -34,11 +33,11 @@
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td colspan=2  bgcolor=__UI_C_INTBLOCK__>
+<td colspan=2  class=rnorm>
 
 <B>Build an order button or link</B>
 
@@ -48,14 +47,14 @@
 [scratch item_result]
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Type</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <SELECT NAME=item_button>
 <OPTION VALUE=0>Link
 <OPTION VALUE=1 [selected item_button 1]>Button
@@ -68,10 +67,10 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Item code</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 [perl]
 	my $table = $Config->{ProductFiles}[0];
 	$Scratch->{keypos} = $Config->{Database}{$table}{KEYINDEX} || '0';
@@ -99,10 +98,10 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Specific Quantity</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <INPUT NAME=item_quantity> <I>(Separate multiple quantities by commas)</I>
 
@@ -114,10 +113,10 @@
 	return unless scalar @$ary > 1;
 	my $out = <<'EOF';
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 A specific database
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <SELECT NAME=item_db>
 EOF
 	for(@$ary) {
@@ -131,10 +130,10 @@
 [/calc]
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Separate line?</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <SELECT NAME=item_separate>
 	<OPTION VALUE=0> No
@@ -148,10 +147,10 @@
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Group items?</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <SELECT NAME=item_group>
 	<OPTION VALUE=""> No
@@ -161,10 +160,10 @@
 </tr>
 [loop prefix=macro list=`join "\n", @{$Config->{UseModifier}};`]
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>[macro-code] (if any)</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <SELECT NAME=item_modifier_[macro-code]>
 <OPTION VALUE=""> --none specified--
 [calc]
@@ -190,10 +189,10 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Affiliate code</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <select name="affiliate">
 <option value=""> --no affiliate --
 [loop search="
@@ -213,23 +212,23 @@
 
 [if config OnFly]
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Description</B>
 <BR>
-<font size="-1"><i>(on-the-fly only)</i></font>
+<span style="font-size: smaller; font-style: italic;"><i>(on-the-fly only)</span>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input name="description" size=50>
 </td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Price</B>
 <BR>
-<font size="-1"><i>(on-the-fly only)</i></font>
+<span style="font-size: smaller; font-style: italic;">(on-the-fly only)</span>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input name="price" size=8>
 </td>
 </tr>
@@ -241,10 +240,10 @@
 	for(@{$Config->{UseModifier}}) {
 		$out .= <<EOF;
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>$_ (if any)</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <INPUT NAME=item_modifier_$_>
  <I>(Separate multiple values by commas)</I>
 </SELECT>
@@ -256,16 +255,16 @@
 [/calc]
 [/comment]
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <B>Action</B>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <INPUT TYPE=submit VALUE=Build>
 </td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.10.4.4  +126 -59   interchange/dist/lib/UI/pages/admin/customer.html


rev 1.10.4.4, prev_rev 1.10.4.3
Index: customer.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer.html,v
retrieving revision 1.10.4.3
retrieving revision 1.10.4.4
diff -u -r1.10.4.3 -r1.10.4.4
--- customer.html	25 Jan 2001 18:45:04 -0000	1.10.4.3
+++ customer.html	25 Jan 2003 22:21:13 -0000	1.10.4.4
@@ -1,23 +1,23 @@
-[calc]
+@_UI_STD_INIT_@[calc]
 	if ( $CGI->{showactive} ) {
 		delete $Values->{showinactive};
 		$Values->{showactive} = 1;
 		$Scratch->{active_sense} = 'ne';
-		$Scratch->{active_img} = 'admin/right.gif';
+		$Scratch->{active_img} = 'right.gif';
 		$Scratch->{active_nm} = 'deactivate';
 	}
 	elsif($CGI->{showinactive}) {
 		delete $Values->{showactive};
 		$Values->{showinactive} = 1;
 		$Scratch->{active_sense} = 'eq';
-		$Scratch->{active_img} = 'admin/left.gif';
+		$Scratch->{active_img} = 'left.gif';
 		$Scratch->{active_nm} = 'activate';
 	}
 	elsif(! $Values->{showactive} and ! $Values->{showinactive}) {
 		delete $Values->{showinactive};
 		$Values->{showactive} = 1;
 		$Scratch->{active_sense} = 'ne';
-		$Scratch->{active_img} = 'admin/right.gif';
+		$Scratch->{active_img} = 'right.gif';
 		$Scratch->{active_nm} = 'deactivate';
 	}
 	return;
@@ -26,11 +26,13 @@
 [value name=mv_data_table set=userdb hide=1]
 [if-mm !tables]
 [set ui_error]
-	Not authorized for customer administration. Contact administrator?
+	[L]Not authorized for customer administration. Contact administrator?[/L]
 [/set]
 [bounce page="__UI_BASE__/error"]
 [/if-mm]
 
+[tmp can_delete][if-mm advanced userdb=d]1[/if-mm][/tmp]
+
 [set ui_class]Customers[/set]
 [set page_perm]userdb[/set]
 
@@ -40,8 +42,8 @@
 	$Config->{NoSearch} = '';
 	my $db = $Db{userdb};
 	if(! $db) {
-		$Scratch->{error_message} = "<FONT CLASS=error>Error: no userdb database.</FONT><BR>";
-		$Scratch->{ui_location} = "__UI_BASE__/error";
+		$Scratch->{ui_error} = errmsg('no %s database', 'userdb');
+		$Scratch->{ui_location} = $Tag->area("__UI_BASE__/error");
 		return;
 	}
 
@@ -54,7 +56,7 @@
 		$value = 1;
 		$action_col = 'inactive';
 	}
-	elsif($CGI->{deletecustomer}) {
+	elsif($CGI->{deletecustomer} and $Scratch->{can_delete}) {
 		$delete = 1;
 	}
 	elsif($CGI->{viewcustomer} and ! $CGI->{viewnext}) {
@@ -84,9 +86,9 @@
 	}
 	if(@errors) {
 		my $plural = @errors > 1 ? 's' : '';
-		return "<FONT CLASS=error>Error$plural:<UL><LI>" .
+		return "<span class=cerror>Error$plural:<UL><LI>" .
 				join ("<LI>", @errors)                    .
-				"</UL></FONT><BR>";
+				"</UL></span><BR>";
 	}
 	if($CGI->{viewnext}) {
 		#Log("viewnext");
@@ -128,16 +130,48 @@
 	return;
 [/perl]
 
+[calc]
+	if ($CGI->{mv_like_spec}) {
+		my @f = split /\0/, $CGI->{mv_like_field};
+		my @s = split /\0/, $CGI->{mv_like_spec};
+		my @q = 'ra=yes';
+		my $found;
+		for(my $i = 0; $i < @f; $i++) {
+			next unless length $s[$i];
+			$found++;
+			push @q, "lf=$f[$i]";
+			push @q, "ls=$s[$i]";
+		}
+		if($found) { $CGI->{ui_text_qualification} = join "\n", @q; }
+		else	   { $CGI->{ui_text_qualification} = "" }
+	}
+	return if $CGI->{ui_text_qualification};
+	return unless
+	  $Variable->{CUSTOMER_VIEW_LARGE} or $Config->{Database}{transactions}{LARGE};
+	$Scratch->{ui_location} = $Tag->area( {
+									
+									href => '__UI_BASE__/flex_select',
+									form => q(
+										mv_data_table=userdb
+										page_title=Customer select
+										page_banner=Customer select
+										ui_searchpage=__UI_BASE__/customer
+									),
+								},
+								);
+	return;
+[/calc]
+
 [if scratch ui_location]
 [bounce href=`delete $Scratch->{ui_location}`]
 [/if]
 
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
 [seti page_title]
 	[if value showinactive]
-	Customers: Inactive Customers
+	[L]Customers[/L]: [L]Inactive Customers[/L]
 	[else]
-	Customers: Active Customers
+	[L]Customers[/L]: [L]Active Customers[/L]
 	[/else]
 	[/if]
 [/seti]
@@ -146,29 +180,28 @@
 
 @_UI_STD_HEAD_@
 
-
-[if scratch ui_message]
-<BLOCKQUOTE>
-[scratch ui_message]
-</BLOCKQUOTE>
-[set ui_message][/set]
-[/if]
-</font>
-
 <!-- ----- BEGIN REAL STUFF ----- -->
 
 <!-- ----- Show the active/inactive buttons ----- -->
 
+
+[output name=search_box]
 <FORM ACTION="[area @@MV_PAGE@@]">
-<SMALL><INPUT TYPE=text NAME=ui_text_qualification VALUE="">
-[button text="Search for customer"]
-mv_nextpage=@@MV_PAGE@@
-[/button]
+<INPUT TYPE=text NAME=ui_text_qualification VALUE="" class=s3>
+<input type=submit value="[L]Search for customer[/L]" class=s3>
 </form>
-</SMALL>
+
+[output name=""]
+
 <!-- ----- Show the customer list box ----- -->
 [if cgi ui_text_qualification]
-<H4>Entries containing "[cgi ui_text_qualification]"</H3>
+[calc]
+	return if $CGI->{mv_like_spec};
+	$Scratch->{page_banner} ||= $Scratch->{page_title};
+	my $val = $Tag->filter('encode_entities', $CGI->{ui_text_qualification});
+	$Scratch->{page_banner} .= ' -- ' . errmsg( 'entries containing "%s"', $val);
+	return;
+[/calc]
 [/if]
 <FORM ACTION="[process]">
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="@@MV_PAGE@@">
@@ -178,8 +211,11 @@
 		ml=__UI_SZ_LIST_CUSTOMER__
 		md=1
 		st=db
-		[if cgi ui_text_qualification]
+		[if cgi mv_like_spec]
+		    [cgi ui_text_qualification]
+		[elsif cgi ui_text_qualification]
 		    se=[cgi ui_text_qualification]
+		[/elsif]
 		[else]
 		    co=yes
 		    sf=inactive
@@ -211,46 +247,52 @@
 	}
 	return;
 [/calc]
-<TABLE border=0 __UI_T_PROPERTIES__>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<TR BGCOLOR="__UI_C_TITLEBARBG__">
-	<th>&nbsp;</th>
-	<TH ALIGN=left><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
+<br>
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+<tr class=rhead>
+	<td>actions</td>
+	<td class=rhead>[page extra=rhead href=@@MV_PAGE@@ form=`
 	$qual = '';
 	if($CGI->{ui_text_qualification}) {
 		$qual .= "ui_text_qualification=$CGI->{ui_text_qualification}";
 	}
     return "ui_sort_field=username\n" . sortrev('username');
-    `]ID</a></TH>
-	<TH ALIGN=left><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
+    `][L]ID[/L]</a></td>
+	<td class=rhead>[page extra=rhead href=@@MV_PAGE@@ form=`
     return "$qual\nui_sort_field=lname,fname\n" . sortrev('lname');
-    `]Name</A></TH>
-	<TH ALIGN=left><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
+    `][L]Name[/L]</A></td>
+	<td class=rhead>[page extra=rhead href=@@MV_PAGE@@ form=`
     return "$qual\nui_sort_field=company,lname\n" . sortrev('company');
-    `]Company</A></TH>
-	<TH ALIGN=left><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
-    return "$qual\nui_sort_field=country,state,city\n" . sortrev('country');
-    `]Location</A></TH>
+    `][L]Company[/L]</A></td>
+	<td class=rhead>
+		[page
+			href=@@MV_PAGE@@
+			extra=rhead
+			form=`
+				return "$qual\nui_sort_field=country,state,city\n" . sortrev('country');
+			`][L]Location[/L]</A></td>
 </TR>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=8></td></tr>
-
 [search-list]
-<TR [item-alternate 2]BGCOLOR="__UI_T_ROW_EVEN__"[else]BGCOLOR="__UI_T_ROW_ODD__"[/else][/item-alternate]>
+<TR [item-alternate 2]class=rownorm[else]class=rowalt[/else][/item-alternate]>
 
 	<TD><INPUT TYPE=checkbox NAME=customer VALUE="[item-code]">
 [page href="@@MV_PAGE@@"
+	extra="title=[scratch active_nm]"
 	form="
 		[scratch active_nm]=1
 		customer=[item-code]
-	"]<IMG SRC="@_UI_IMG_@[scratch active_img]" HEIGHT=10 WIDTH=11 ALT="[scratch active_nm] [item-code]" BORDER=0></A>
+	"]<IMG SRC="[scratch active_img]" HEIGHT=10 WIDTH=11 ALT="[scratch active_nm] [item-code]" BORDER=0></A>
+[if scratch can_delete]
 <A HREF="[area
 	href='@@MV_PAGE@@'
 	form='
 		deletecustomer=1
 		customer=[item-code]
 	']"
-	onClick="return confirm('Are you sure you want to delete customer [item-code]?')"><IMG src="@_UI_IMG_@admin/delsm.gif" ALT="DELETE [item-code]" BORDER=0></A>
+	onClick="return confirm('Are you sure you want to delete customer [item-code]?')"
+	title=delete
+><IMG src="delsm.gif" ALT="DELETE [item-code]" BORDER=0></A>
+[/if]
 </td><td>
 [page href=__UI_BASE__/customer_view
 			  form="
@@ -270,34 +312,59 @@
 [no-match]
 <TR>
 	<TD COLSPAN=4>
-	No [if value showinactive]in[/if]active customers.
+[if value showinactive]
+    [L]No inactive customers.[/L]
+[else]
+	[L]No active customers.[/L]
+[/else]
+[/if]
 	</td>
 </tr>
 [/no-match]
 [more-list]
 <TR>
 	<TD COLSPAN=4>
-	Customers [matches] of [value mv_search_match_count]: [more]
+	[msg arg.0="[matches]" arg.1="[value mv_search_match_count]"]Customers %s of %s[/msg]: [more]
 	</td>
 </tr>
 [/more-list]
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=8><td colspan=8></td></tr>
 
 </table>
-[if-mm advanced userdb=d]
-[button form=batch text="Delete checked customers"
- confirm='Are you sure you want to delete the checked customers?']deletecustomer=1
+<br>
+[on-match]
+[output name=bottom_buttons]
+[if scratch can_delete]
+[button extra="class=s3" form=batch text="[L]Delete checked customers[/L]"
+ confirm='[L]Are you sure you want to delete the checked customers?[/L]']deletecustomer=1
 [/button]
-[/if-mm]
-&nbsp;&nbsp;&nbsp;[button form=batch text=`
-			my $tmp = "$Scratch->{active_nm} checked customers";
+[/if]
+&nbsp;&nbsp;&nbsp;[button form=batch extra="class=s3" text=`
+			my $tmp = errmsg("$Scratch->{active_nm} checked customers");
 			return "\u$tmp";
 			`]
 [scratch active_nm]=1[/button]
-</FORM>
+[output name=""]
+[/on-match]
+
+[if-mm advanced userdb=e]
+[output name=top_buttons]
+	<form action="[area @@MV_PAGE@@]">
+	<input type=hidden name=mv_action value=refresh>
+	<input type=hidden name=mv_click value=MMsu>
+	<span class=s3>Switch to a user:</span> <select name=user class=s3>
+						[search-list]
+						<option>[item-code]
+						[/search-list]
+					  </select><input type=submit value="[L]Switch[/L]" class=s3>
+	</form>
+[output name=""]
+[/if-mm]
+
 [/search-region]
 
+[output name=bottom_of_form]
+</FORM>
+[output name=""]
 
 <!-- ----- END REAL STUFF ----- -->
 



1.1.4.1   +18 -5     interchange/dist/lib/UI/pages/admin/customer_bill.html


rev 1.1.4.1, prev_rev 1.1
Index: customer_bill.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_bill.html,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- customer_bill.html	14 Sep 2000 07:51:37 -0000	1.1
+++ customer_bill.html	25 Jan 2003 22:21:13 -0000	1.1.4.1
@@ -5,34 +5,47 @@
 	if(! $CGI->{item_id} and $Session->{arg}) {
 		$CGI->{item_id} = $CGI->{customer} = $Session->{arg};
 	}
+	$CGI->{customer} = $CGI->{item_id} if ! $CGI->{customer};
 	return if ! $CGI->{item_id};
 	if(! $CGI->{mv_data_table}) {
 		$CGI->{ui_hide_key} = 1;
 		$CGI->{mv_data_table} = 'userdb';
 	}
 	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = 'username company b_fname b_lname b_address1 b_address2 b_city b_state b_zip b_country email phone_day phone_night';
-					
+		$CGI->{ui_data_fields} = 'username b_company b_fname b_lname b_address1 b_address2 b_city b_state b_zip b_country email b_phone phone_day phone_night';
+		$CGI->{ui_display_only} = 'email phone_day phone_night';
+	}
+	if(! $CGI->{mv_blob_field}) {
+		$CGI->{mv_blob_title} = '<B>Accounts book</B>';
+		$CGI->{mv_blob_field} = 'accounts';
+		$CGI->{mv_blob_label} = 'b_city';
+		$CGI->{mv_blob_pointer} = 'b_nickname';
 	}
 	if(! $CGI->{ui_break_before}) {
 		$CGI->{ui_break_before} = 'b_address1 email';
 	}
+	if(! $CGI->{ui_return_to}) {
+		$CGI->{ui_return_to} = join "\0",
+									'__UI_BASE__/customer_view',
+									"customer=$CGI->{item_id}",
+								;
+
+	}
 	return;
 [/calc]
 [if !cgi item_id]
 	[bounce page="__UI_BASE__/customer"]
 [/if]
-@_UI_STD_DBEDIT_HEAD_@
 
 [set ui_class]Customers[/set]
 [seti page_title]Customer billing information -- [cgi item_id][/seti]
 [seti page_banner]Customer billing information: <B>[page href="__UI_BASE__/customer_view" form="customer=[cgi customer]"][cgi customer]</A></B>[/seti]
 [set help_name]customer.edit[/set]
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
+[table-editor cgi=1 no-table-meta=1 output_map=1]
 
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->



1.8.4.1   +16 -15    interchange/dist/lib/UI/pages/admin/customer_change_pass.html


rev 1.8.4.1, prev_rev 1.8
Index: customer_change_pass.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_change_pass.html,v
retrieving revision 1.8
retrieving revision 1.8.4.1
diff -u -r1.8 -r1.8.4.1
--- customer_change_pass.html	25 Sep 2000 17:24:32 -0000	1.8
+++ customer_change_pass.html	25 Jan 2003 22:21:13 -0000	1.8.4.1
@@ -3,24 +3,24 @@
 [set ui_class]Customers[/set]
 [set page_perm]userdb=e[/set]
 [set help_name]access.main[/set]
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
 [set no_old_needed][/set]
 @_UI_STD_HEAD_@
 
 [if session failure]
 <P>
 &nbsp;
-<BLOCKQUOTE>
-<FONT COLOR=RED>Failure:</FONT> [data session failure][data base=session field=failure value=""]
-</BLOCKQUOTE>
+<blockquote class=cerror>
+	Failure: [data session failure][data base=session field=failure value=""]
+</blockquote>
 <P>
 &nbsp;
 [/if]
 
 [if scratch ui_message]
 <P>
-<BLOCKQUOTE>
-	[scratch ui_message][set ui_message][/set]
+<BLOCKQUOTE class=cmessage>
+	[scratchd ui_message]
 </BLOCKQUOTE>
 <P>
 &nbsp;
@@ -39,6 +39,7 @@
 [/set]
 
 <form action="[area ui]" method="post">
+<input type=hidden name=mv_session_id value="[data session id]">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE=__UI_BASE__/customer_view>
 <INPUT TYPE=hidden NAME=mv_arg VALUE="[loop-code]">
@@ -50,43 +51,43 @@
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 User name
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 	<input type=hidden name=mv_data_function value="update">
 	<input type=hidden name=username value="[loop-code]">[loop-code]
 </td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 New password
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <INPUT TYPE=password NAME=password VALUE="" SIZE=20>
 </td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 Verify password
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <INPUT TYPE=password SIZE=20 NAME=verify VALUE="">
 </td>
 </tr>
 
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.1.4.1   +46 -7     interchange/dist/lib/UI/pages/admin/customer_pref.html


rev 1.1.4.1, prev_rev 1.1
Index: customer_pref.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_pref.html,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- customer_pref.html	14 Sep 2000 07:51:37 -0000	1.1
+++ customer_pref.html	25 Jan 2003 22:21:13 -0000	1.1.4.1
@@ -5,34 +5,73 @@
 	if(! $CGI->{item_id} and $Session->{arg}) {
 		$CGI->{item_id} = $CGI->{customer} = $Session->{arg};
 	}
+	$CGI->{customer} = $CGI->{item_id} if ! $CGI->{customer};
 	return if ! $CGI->{item_id};
 	if(! $CGI->{mv_data_table}) {
 		$CGI->{ui_hide_key} = 1;
 		$CGI->{mv_data_table} = 'userdb';
 	}
 	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = 'username company fname lname fax_order mv_shipmode dealer project_id credit_limit inactive email_copy mail_list email phone_day phone_night fax db_acl file_acl';
+		$CGI->{ui_data_fields} = '
+				=General
+				
+				username
+				company
+				fname lname
+				fax_order
+				mv_shipmode
+				inactive
+
+				=Dealer Status
+
+				dealer
+				price_level
+				project_id
+				credit_limit
+
+				=Email Preferences
+
+				email
+				email_copy
+				mail_list
+
+				=Contact Info
+
+				phone_day
+				phone_night
+				fax
+
+				=Permissions
+
+				db_acl
+				file_acl';
+		$CGI->{ui_display_only} = 'company fname lname phone_day';
 					
 	}
-	if(! $CGI->{ui_break_before}) {
-		$CGI->{ui_break_before} = 'dealer email_copy email db_acl';
+	if(! $CGI->{ui_return_to}) {
+		$CGI->{ui_return_to} = join "\0",
+									'__UI_BASE__/customer_view',
+									"customer=$CGI->{item_id}",
+								;
+
 	}
 	return;
 [/calc]
 [if !cgi item_id]
 	[bounce page="__UI_BASE__/customer"]
 [/if]
-@_UI_STD_DBEDIT_HEAD_@
 
 [set ui_class]Customers[/set]
 [seti page_title]Customer preferences -- [cgi item_id][/seti]
 [seti page_banner]Customer preferences: <B>[page href="__UI_BASE__/customer_view" form="customer=[cgi customer]"][cgi customer]</A></B>[/seti]
 [set help_name]customer.edit[/set]
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
+[table-editor cgi=1 output_map=1 form-name=customer_pref]
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@
+[return-to click]
+-->



1.2.4.1   +16 -17    interchange/dist/lib/UI/pages/admin/customer_select.html


rev 1.2.4.1, prev_rev 1.2
Index: customer_select.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_select.html,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- customer_select.html	23 Sep 2000 17:55:32 -0000	1.2
+++ customer_select.html	25 Jan 2003 22:21:13 -0000	1.2.4.1
@@ -19,7 +19,7 @@
 	$Config->{NoSearch} = '';
 	my $db = $Db{userdb};
 	if(! $db) {
-		$Scratch->{error_message} = "<FONT CLASS=error>Error: no userdb database.</FONT><BR>";
+		$Scratch->{error_message} = "<span class=cerror>Error: no userdb database.</span><BR>";
 		$Scratch->{ui_location} = "__UI_BASE__/error";
 		return;
 	}
@@ -63,9 +63,9 @@
 	}
 	if(@errors) {
 		my $plural = @errors > 1 ? 's' : '';
-		return "<FONT CLASS=error>Error$plural:<UL><LI>" .
+		return "<span class=cerror>Error$plural:<UL><LI>" .
 				join ("<LI>", @errors)                    .
-				"</UL></FONT><BR>";
+				"</UL></span><BR>";
 	}
 	if($CGI->{viewnext}) {
 		#Log("viewnext");
@@ -112,7 +112,7 @@
 [bounce href=`delete $Scratch->{ui_location}`]
 [/if]
 
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
 [seti page_title]
 	[if value showinactive]
 	Customers: Inactive customers
@@ -128,30 +128,29 @@
 
 
 [if scratch message]
-<BLOCKQUOTE>
-[scratch message]
-</BLOCKQUOTE>
-[set message][/set]
+	<blockquote class=cmessage>
+		[scratchd message]
+	</blockquote>
 [/if]
-</font>
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
 <!-- ----- Show the active/inactive buttons ----- -->
 
-<form action="[area __UI_BASE__/customer]" method=POST>
+<form action="[process href=@@MV_PAGE@@]" method=POST>
+<input type=hidden name=mv_session_id value="[data session id]">
 <INPUT TYPE=hidden NAME=mv_action VALUE=return>
 
 <input type=hidden name=inactive value="false">
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 [if value showinactive]
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_MAIN_WIDTH__ colspan=2>
+<td class=rnorm width=__UI_MAIN_WIDTH__ colspan=2>
 [button name="showactive" text="Show active customers"][/button]
 [set active_sense]eq[/set]
 </td>
@@ -159,7 +158,7 @@
 [else]
 [value name=showinactive set=""]
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_MAIN_WIDTH__ colspan=2>
+<td class=rnorm width=__UI_MAIN_WIDTH__ colspan=2>
 <input type=submit name="showinactive" value="Show inactive customers">
 [set active_sense]ne[/set]
 </td>
@@ -168,13 +167,13 @@
 [/if]
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rnorm><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <!-- ----- Show the operation buttons ----- -->
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_LEFT_WIDTH__>
+<td class=rnorm width=__UI_LEFT_WIDTH__>
 
 [button name="viewcustomer" text="View customer"][/button]<br>
 
@@ -217,7 +216,7 @@
 <input type=submit name="xload" value="Export customers">
 [/comment]
 </td>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_RIGHT_WIDTH__>
+<td class=rnorm width=__UI_RIGHT_WIDTH__>
 <SMALL>Specific customer <INPUT TYPE=text NAME=customer VALUE="">
 [button text="Start list here"]
 [calc]
@@ -255,7 +254,7 @@
 </td></tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 </table>
 



1.1.4.1   +19 -5     interchange/dist/lib/UI/pages/admin/customer_ship.html


rev 1.1.4.1, prev_rev 1.1
Index: customer_ship.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_ship.html,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- customer_ship.html	14 Sep 2000 07:49:28 -0000	1.1
+++ customer_ship.html	25 Jan 2003 22:21:13 -0000	1.1.4.1
@@ -5,6 +5,7 @@
 	if(! $CGI->{item_id} and $Session->{arg}) {
 		$CGI->{item_id} = $CGI->{customer} = $Session->{arg};
 	}
+	$CGI->{customer} = $CGI->{item_id} if ! $CGI->{customer};
 	return if ! $CGI->{item_id};
 	if(! $CGI->{mv_data_table}) {
 		$CGI->{ui_hide_key} = 1;
@@ -12,26 +13,39 @@
 	}
 	if(! $CGI->{ui_data_fields}) {
 		$CGI->{ui_data_fields} = 'username company fname lname address1 address2 city state zip country email phone_day phone_night';
+		$CGI->{ui_display_only} = 'email phone_night';
+	}
+	if(! $CGI->{mv_blob_field}) {
+		$CGI->{mv_blob_title} = '<B>Address book</B>';
+		$CGI->{mv_blob_field} = 'address_book';
+		$CGI->{mv_blob_label} = 'city';
+		$CGI->{mv_blob_pointer} = 's_nickname';
 	}
 	if(! $CGI->{ui_break_before}) {
 		$CGI->{ui_break_before} = 'address1 email';
 	}
+	if(! $CGI->{ui_return_to}) {
+		$CGI->{ui_return_to} = join "\0",
+									'__UI_BASE__/customer_view',
+									"customer=$CGI->{item_id}",
+								;
+
+	}
 	return;
 [/calc]
 [if !cgi item_id]
 	[bounce page="__UI_BASE__/customer"]
 [/if]
-@_UI_STD_DBEDIT_HEAD_@
 
 [set ui_class]Customers[/set]
-[seti page_title]Customer shipping information -- [cgi customer][/seti]
-[seti page_banner]Customer shipping information: <B>[page href="__UI_BASE__/customer_view" form="customer=[cgi customer]"][cgi customer]</A></B>[/seti]
+[seti page_title][L]Customer shipping information[/L] -- [cgi customer][/seti]
+[seti page_banner][L]Customer shipping information[/L]: <B>[page href="__UI_BASE__/customer_view" form="customer=[cgi customer]"][cgi customer]</A></B>[/seti]
 [set help_name]customer.edit[/set]
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
+[table-editor cgi=1 no-table-meta=1 output-map=1]
 
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->



1.8.4.1   +369 -222  interchange/dist/lib/UI/pages/admin/customer_view.html


rev 1.8.4.1, prev_rev 1.8
Index: customer_view.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_view.html,v
retrieving revision 1.8
retrieving revision 1.8.4.1
diff -u -r1.8 -r1.8.4.1
--- customer_view.html	23 Sep 2000 17:55:32 -0000	1.8
+++ customer_view.html	25 Jan 2003 22:21:13 -0000	1.8.4.1
@@ -1,14 +1,14 @@
-[set page_title]Customer manager: View customer[/set]
+[tmp page_title][L]Customer manager[/L]: [L]View customer[/L] [cgi customer][/tmp]
 [set ui_class]Customers[/set]
-[set page_banner]View customer[/set]
+[set page_banner][L]View customer[/L][/set]
 [set help_name]customer.view[/set]
-[set icon_name]admin/icon_people.gif[/set]
+[set icon_name]icon_people.gif[/set]
+
 @_UI_STD_HEAD_@
+
 [calc]
 	delete $Scratch->{ui_bounce};
-	#Log("got here, customer=$CGI->{customer}, arg=$CGI->{mv_arg}");
-	return if $CGI->{customer};
-	$CGI->{customer} = $CGI->{mv_arg} 
+	$CGI->{customer} ||= $CGI->{mv_arg} 
 		or $Scratch->{ui_bounce} = '__UI_BASE__/customer';
 	return;
 [/calc]
@@ -17,239 +17,386 @@
 [/if]
 
 <!-- ----- BEGIN REAL STUFF ----- -->
-[update values]
-[loop list="[value-extended customer]"]
-
-<table border=0 __UI_T_PROPERTIES__>
-<tr>
-<td colspan=6 bgcolor=__UI_C_TITLEBARBG__><img src="@_UI_IMG_@admin/bg.gif" height=1></td>
-</tr>
-
-<tr>
-<td colspan=6 align=left bgcolor=__UI_C_INTBLOCK__>
-<table>
-<tr><td align=right>
-<b>Customer Username: </td><td>[loop-code]</b></td>
-</tr><tr>
-<td align=right><b>Customer: </td><td>
-<A HREF="[area
-				href=__UI_BASE__/customer_pref
-				form=|
-					customer=[cgi customer]
-				|
-		]"><u>[loop-data userdb fname] [loop-data userdb lname]</u></A>
-		</b>
-</td>
-</tr>
-</table>
-</td>
-</tr>
-
-<tr>
-<td colspan=2 valign=top>
-
-<!-- ----- Customer information ----- -->
-
-<form>
-
-<table border=0>
-<tr><td align=right>
-<font size=2><b> Company: </b></font>
-</td><td><font size=2>[loop-data userdb company]</font></td></tr>
-
-<tr><td align=right>
-<font size=2><b> Home phone: </b></font>
-</td><td><font size=2>[loop-data userdb phone_night]</font></td></tr>
-
-<tr><td align=right>
-<font size=2><b> Work phone: </b></font>
-</td><td><font size=2>[loop-data userdb phone_day]</font></td></tr>
-
-<tr><td align=right>
-<font size=2><b> Email: </b></font>
-</td><td><font size=2> <a href="mailto:[loop-data userdb email]"><U>[loop-data userdb email]</U></a></font></td></tr>
-<tr><td align=right>
-<font size=2><b> Payment type: </b></font>
-</td><td><font size=2>[display arbitrary=custview table=userdb column=fax_order key="[loop-code]"]</a></font></tr>
-
-[if-loop-data userdb project_id]
-<tr><td align=right>
-<font size=2><b>PO Number:</b></font>&nbsp;
-</td><td><font size=2>[loop-data userdb project_id]</font></td></tr>
-[/if-loop-data]
-
-[if-loop-data userdb fax]
-<tr><td align=right>
-<font size=2><b>FAX number:</b></font>&nbsp;
-</td><td><font size=2>[loop-data userdb fax]</font></td></tr>
-[/if-loop-data]
 
-<tr><td align=right>
-<font size=2><b>Dealer:</b></font>&nbsp;
-</td><td><font size=2>[display arbitrary=custview table=userdb column=dealer key="[loop-code]"]</font></td></tr>
+[perl tables=country]### pre-open database for calcs below[/perl] 
 
-
-<tr><td align=right>
-<font size=2><b>Wants email copy:</b></font>&nbsp;
-</td><td><font size=2>[display arbitrary=custview table=userdb column=email_copy key="[loop-code]"]</font></td></tr>
-
-<tr><td align=right>
-<font size=2><b>Mail lists:</b></font>&nbsp;
-</td><td><font size=2>[loop-data userdb mail_list]</font></td></tr>
-
-</table>
-</form>
-
-</td><td valign=top colspan=4>
-[set bill_address]
-[loop-data userdb b_fname] [loop-data userdb b_lname]<br>
-[loop-data userdb b_address1]<br>
-[if-loop-data userdb b_address2]
-[loop-data userdb b_address2]<br>
-[/if-loop-data]
-[loop-data userdb b_city], [loop-data userdb b_state] [loop-data userdb b_zip]<br>
-[/set]
-
-[set ship_address]
-[loop-data userdb fname] [loop-data userdb lname]<br>
-[loop-data userdb address1]<br>
-[if-loop-data userdb address2]
-[loop-data userdb address2]<br>
-[/if-loop-data]
-[loop-data userdb city], [loop-data userdb state] [loop-data userdb zip]<br>
-[/set]
-
-<font size=2>
-<p>
-[if-loop-data userdb username]
-<A HREF="[area
-				href=__UI_BASE__/customer_bill
-				form=|
-					customer=[loop-data userdb username]
-				|
-		]"><b><u>Bill To</u>:</b></A>
-[else]
-		<b>Bill To:</b>
-[/else]
-[/if-loop-data]
-<blockquote>
-[if-loop-data userdb b_address1]
-[scratch bill_address]
+[query list=1
+		prefix=loop
+		sql="select * from userdb where username = '[cgi customer]'"]
+<table width="100%" border="0" cellspacing="0" cellpadding="0">
+   <tr> 
+      <td> 
+         <table width="100%" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+            <tr> 
+               <td width="25%" nowrap class="block4bold">User Name: &nbsp; [loop-code]</a></td>
+               <td width="25%" nowrap class="block4bold">
+			   	Account Status: &nbsp;
+					[filter uc]
+					[if-loop-param inactive]
+					[L]inactive[/L]
+					[else]
+					[L]active[/L]
+					[/else]
+					[/if-loop-param]
+					[/filter]
+					
+				</td>
+               <td width="25%" nowrap class="block4bold">
+			   		
+					Total Sales: &nbsp;
+				[query arrayref=totals sql=|
+										SELECT total_cost,status
+										FROM  transactions
+					                    WHERE username = '[loop-code]'
+										|][/query]
+					[calc]
+						my $q = $Tmp->{totals};
+						my $ary;
+						return 'no orders' unless $q and defined $q->[0];
+						my $total = 0;
+						for(@$q) {
+							next if $_->[1] eq 'canceled';
+							$total += $_->[0];
+						}
+						return $Tag->currency({ body => $total } );
+					[/calc]
+				</td>
+                <td width="25%" nowrap class="block4bold">
+			   		Last login: &nbsp; <span class="maincontent">
+						[if-loop-param !mod_time]
+						Never
+						[else]
+						[time time="[loop-param mod_time]"]%b %e, %Y %l:%M %P[/time]
+						[/else]
+						[/if-loop-param]
+					</span>
+				</td>
+            </tr>
+         </table>
+      </td>
+   </tr>
+   <tr> 
+      <td height="6"><img src="bg.gif" width="1" height="6"></td>
+   </tr>
+   <tr> 
+      <td> 
+         <table width="100%" border="0" cellspacing="0" cellpadding="0">
+            <tr> 
+               <!-- CUSTOMER DETAILS -->
+               <td width="33%" valign="top"> 
+                  <table width="100%" height="200" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+                     <tr> 
+               
+                        <td height="1%" class="block4"><a href="[area href='admin/customer_view' form='customer=[loop-param username]']">Customer Details</a></td>
+                     </tr>
+                     <tr> 
+                        <td height="99%" valign="top" class="block4"> 
+                           <table width="100%" border="0" cellspacing="0" cellpadding="1">
+                              <tr> 
+                                 <td width="30%" class="block4bold">Customer:</td>
+                                 <td width="70%" class="maincontent"><a href="[area href='admin/customer_view' form='customer=[loop-param username]']">[loop-param fname] [loop-param lname]</a> 
+                                 </td>
+                              </tr>
+                              <tr> 
+                                 <td class="block4bold"> [L]Company[/L]:</td>
+                                 <td class="maincontent">[loop-param company]</td>
+                              </tr>
+                              <tr> 
+                                 <td nowrap class="block4bold">[L]Home phone[/L]:</td>
+                                 <td class="maincontent">[loop-param phone_night]</td>
+                              </tr>
+                              <tr> 
+                                 <td nowrap class="block4bold"> [L]Work phone[/L]:</td>
+                                 <td class="maincontent">[loop-param phone_night]</td>
+                              </tr>
+                              <tr> 
+                                 <td class="block4bold">[L]Email[/L]:</td>
+                                 <td class="maincontent"><a href="mailto:[loop-param email]">[loop-param email]</a></td>
+                              </tr>
+                              <tr> 
+                                 <td nowrap class="block4bold">[L]Payment type[/L]:</td>
+                                 <td class="maincontent">[loop-param payment_method]</td>
+                              </tr>
+			[if variable CUSTOMER_VIEW_DEALER]
+							  <tr>
+                                 <td nowrap class="block4bold">[L]Dealer[/L]:</td>
+                                 <td class="maincontent">
+								 	[page href=admin/customer_pref
+										  form="
+										  	customer=[loop-code]
+											start_at=dealer
+										  "][if-loop-param dealer]Yes[else]No[/else][/if-loop-param]</a>
+										  </td>
+							  </tr>
+							  <tr>
+                                 <td nowrap class="block4bold">[L]Price Level[/L]:</td>
+                                 <td class="maincontent">
+								 	[page href=admin/customer_pref
+										  form="
+										  	customer=[loop-code]
+											start_at=price_level
+										  "][display type=display table=userdb col=price_level key="[loop-code]"]</a>
+										  </td>
+							  </tr>
+		  [/if]
+                              <tr> 
+                                 <td height="15" colspan="2" class="block4bold"><img src="bg.gif" width="1" height="1"></td>
+                              </tr>
+                           </table>
+                        </td>
+                     </tr>
+                  </table>
+               </td>
+               <td width="3"><img src="bg.gif" width="3" height="1"></td>
+               <!-- BILLING DETAILS -->
+               <td width="33%" valign="top"> 
+                  <table width="100%" height="200" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+                     <tr> 
+                        <td height="1%" class="block4"><a href="[area
+						
+								href="admin/customer_bill"
+								form="
+									customer=[loop-code]
+									item_id=[loop-code]
+								"
+						]">[L]Billing Details[/L]</a></td>
+                     </tr>
+                     <tr> 
+                        <td height="99%" valign="top" class="block4"> 
+[if-loop-param b_address1]
+	[loop prefix=bill list="[loop-code]"]
+                           <table width="100%" border="0" cellspacing="0" cellpadding="1">
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Name[/L]:</td>
+                                 <td width="70%" class="maincontent"><A HREF="[area
+				href=__UI_BASE__/customer_view
+				arg="[loop-param username]"
+		]"><u>[loop-param b_fname] [loop-param b_lname]</A>
+                                 </td>
+                              </tr>
+							  [if-bill-data userdb b_company]
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Company[/L]:</td>
+                                 <td width="70%" class="maincontent">
+								 	[loop-param b_company]
+                                 </td>
+                              </tr>
+							  [/if-bill-data]
+                              <tr> 
+                                 <td valign="top" class="block4bold">[L]Address[/L]:</td>
+                                 <td class="maincontent">
+								 [loop-param b_address1]
+								 [if-bill-data userdb b_address2]
+								 <br>
+								 [loop-param b_address2]
+								 [/if-bill-data]
+								 </td>
+                              </tr>
+							  [if-bill-data userdb b_country =~ /^US|^CA/]
+                              <tr> 
+                                 <td class="block4bold">[L]City, State, Zip[/L]:</td>
+                                 <td class="maincontent">[loop-param b_city], [loop-param state]  [loop-param zip]</td>
+                              </tr>
+							  [else]
+                              <tr> 
+                                 <td class="block4bold">[L]City[/L]:</td>
+                                 <td class="maincontent">[loop-param b_city]</td>
+                              </tr>
+							  		[if-bill-param b_state]
+                              <tr> 
+                                 <td class="block4bold">[L]State[/L]:</td>
+                                 <td class="maincontent">[loop-param b_state]</td>
+                              </tr>
+								    [/if-bill-data]
+							  		[if-bill-param b_zip]
+                              <tr> 
+                                 <td class="block4bold">[L]Postal code[/L]:</td>
+                                 <td class="maincontent">[loop-param b_zip]</td>
+                              </tr>
+								    [/if-bill-data]
+							  [/else]
+							  [/if-bill-data]
+                              <tr> 
+                                 <td class="block4bold">[L]Country[/L]:</td>
+                                 <td class="maincontent">[data table=country col=name key="[loop-param b_country]"]</td>
+                              </tr>
+                              <tr> 
+                                 <td height="15" colspan="2" class="block4bold"><img src="bg.gif" width="1" height="1"></td>
+                              </tr>
+                           </table>
+		[/loop]
 [else]
-[scratch ship_address]
+						<i>[L]Same as shipping address[/L]</i>
 [/else]
-[/if-loop-data]
-</blockquote>
-
-<A HREF="[area
-				href=__UI_BASE__/customer_ship
-				form=|
-					customer=[cgi customer]
-				|
-		]"><b><u>Ship To</u>:</b></A>
-<br>
-<blockquote>
-[scratch ship_address]
-</blockquote>
-</font>
-
-[set bill_address][/set]
-[set ship_address][/set]
-</td></tr>
-
-<tr>
-<td colspan=6 bgcolor=__UI_C_TITLEBARBG__><img src="@_UI_IMG_@admin/bg.gif" height=1></td>
-</tr>
-
-<tr>
-<td width="20%" bgcolor=__UI_C_INTBLOCK__>
-	<B>Order number</B>
-</td>
-<td width="20%" bgcolor=__UI_C_INTBLOCK__>
-	<B>Order date</B>
-</td>
-<td bgcolor=__UI_C_INTBLOCK__>
-	<B>Order Total</B>
-</td>
-<td bgcolor=__UI_C_INTBLOCK__>
-	<B>Status</B>
-</td>
-</tr>
-[query list=1
-		st=db
-		table=transactions 
-		sql="select
-			  order_number, order_date, salestax, shipping, total_cost, status
-			  FROM transactions 
-			  WHERE username = '[loop-code]'
-			  ORDER BY order_date
-			  "
-			  ]
-<tr>
-<td>
-	<A HREF="[area __UI_BASE__/order_view [sql-code]]"><U>[sql-code]</U></A>
-</td>
-<td>
-	[sql-pos 1]
-</td>
-<td>
-	[sql-pos 4]
-</td>
-<td>
-<A HREF="[area
-			href=__UI_BASE__/order_status
-			form="
-				order=[sql-code]
-			"]"><U>[sql-pos 5]</U></A>
-</td>
-</tr>
+[/if-loop-param]
+                        </td>
+                     </tr>
+                  </table>
+               </td>
+               <td width="3"><img src="bg.gif" width="3" height="1"></td>
+               <!-- SHIPPING DETAILS -->
+               <td width="34%" valign="top"> 
+                  <table width="100%" height="200" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+                     <tr> 
+                        <td height="1%" class="block4"><a href="[area
+						
+								href="admin/customer_ship"
+								form="
+									customer=[loop-code]
+									item_id=[loop-code]
+								"
+						]">[L]Shipping Details[/L]</a></td>
+                     </tr>
+                     <tr> 
+                        <td height="99%" valign="top" class="block4"> 
+                           <table width="100%" border="0" cellspacing="0" cellpadding="1">
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Name[/L]:</td>
+                                 <td width="70%" class="maincontent"><A HREF="[area
+				href=__UI_BASE__/customer_view
+				arg="[loop-code]"
+		]"><u>[loop-param fname] [loop-param lname]</A>
+                                 </td>
+                              </tr>
+							  [if-loop-param company]
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Company[/L]:</td>
+                                 <td width="70%" class="maincontent">
+								 	[loop-param company]
+                                 </td>
+                              </tr>
+							  [/if-loop-param]
+                              <tr> 
+                                 <td valign="top" class="block4bold">[L]Address[/L]:</td>
+                                 <td class="maincontent">
+								 [loop-param address1]
+								 [if-loop-param address2]
+								 <br>
+								 [loop-param address2]
+								 [/if-loop-param]
+								 </td>
+                              </tr>
+							  [if-loop-param country =~ /^US|^CA/]
+                              <tr> 
+                                 <td class="block4bold">[L]City, State, Zip[/L]:</td>
+                                 <td class="maincontent">[loop-param city], [loop-param state]  [loop-param zip]</td>
+                              </tr>
+							  [else]
+                              <tr> 
+                                 <td class="block4bold">[L]City[/L]:</td>
+                                 <td class="maincontent">[loop-param city]</td>
+                              </tr>
+							  		[if-loop-param state]
+                              <tr> 
+                                 <td class="block4bold">[L]State[/L]:</td>
+                                 <td class="maincontent">[loop-param state]</td>
+                              </tr>
+								    [/if-loop-param]
+							  		[if-loop-param zip]
+                              <tr> 
+                                 <td class="block4bold">[L]Postal code[/L]:</td>
+                                 <td class="maincontent">[loop-param zip]</td>
+                              </tr>
+								    [/if-loop-param]
+							  [/else]
+							  [/if-loop-param]
+                              <tr> 
+                                 <td class="block4bold">[L]Country[/L]:</td>
+                                 <td class="maincontent">[data table=country col=name key="[loop-param country]"]</td>
+                              </tr>
+                              <tr> 
+                                 <td height="15" colspan="2" class="block4bold"><img src="bg.gif" width="1" height="1"></td>
+                              </tr>
+                           </table>
+                        </td>
+                     </tr>
+                  </table>
+               </td>
+            </tr>
+         </table>
+      </td>
+   </tr>
+   <tr> 
+      <td height=6><img src="bg.gif" width=1 height=6></td>
+   </tr>
+   <tr> 
+      <td> 
+         <!-- CUSTOMERS ORDER GRID -->
+         <table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+            <tr> 
+               <td width="14%" class=rhead style="padding: 5px">[L]Status[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px">[L]Order Number[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px">[L]Order Date[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px; text-align: left">[L]Shipped to[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px; text-align: right">[L]Number of items[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px; text-align: right">[L]Subtotal[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px; text-align: right">[L]Total[/L]</td>
+            </tr>
+[query list=1 sql="select * from transactions where username = '[loop-code]'"]
+            <tr class="[sql-alternate 2]rowalt[else]rownorm[/else][/sql-alternate]"> 
+               <td style="padding: 5px">[page href="admin/order_status"
+			   							 form="order=[loop-code]"
+									]
+                [display    table=transactions
+                            column=status
+                            key="[sql-code]"
+                            arbitrary=order_view
+                ]</A>
+               <td style="padding: 5px">
+			   	[page href='__UI_BASE__/order_view' form='order=[sql-code]'][sql-code]</a>
+			   	</td>
+               <td style="padding: 5px">[convert-date fmt="%b %e, %Y %H:%M"][sql-param order_date][/convert-date]</td>
+               <td align=left style="padding: 5px">
+			   	[loop-param city], [loop-param state] [loop-param country]
+               </td>
+               <td align=right style="padding: 5px">[sql-param nitems]</td>
+               <td align=right style="padding: 5px">[currency][sql-param subtotal][/currency]</td>
+			   <td align=right style="padding: 5px">[currency][sql-param total_cost][/currency]</td>
+            </tr>
 [/query]
-<tr>
-<td colspan=6 bgcolor=__UI_C_TITLEBARBG__><img src="@_UI_IMG_@admin/bg.gif" height=1></td>
-</tr>
-
+         </table>
+      </td>
+   </tr>
 </table>
-<SMALL>
-<form action="[area __UI_BASE__/customer]" method=post>
+
+[seti page_banner][L]View Customer[/L]:
+					[if-loop-param company]
+						[loop-param company]
+					[else][loop-param fname] [loop-param lname][/else]
+					[/if-loop-param]
+				[/seti]
+
+[output name=bottom_buttons]
+<form action="[area __UI_BASE__/order]" method=post>
+<input type=hidden name=mv_session_id value="[data session id]">
 <input type=hidden name=mv_action value=back>
-<input type=hidden name=customer value="[loop-data userdb username]">
+<input type=hidden name=order value="[loop-data transactions order_number]">
+<input type=hidden name=archive value=false>
 <input type=hidden name=viewnext value=1>
-
-[button text="Back"]
+[set [L]Return[/L]]
 viewnext=
-viewcustomer=
-[/button]
+vieworder=
+[/set]
+<input type=submit name=mv_click value="[L]Return[/L]" class=s3>
+<input type=submit name="vieworder" value="[L]View next order[/L]" class=s3>
 
-[button text="Enter order"]
-mv_nextpage=__UI_BASE__/entry
-mv_todo=return
-[/button] 
-
-[if-mm advanced userdb=e]
-[if-loop-data userdb inactive]
-[button name="activate" text="Activate customer"][/button]
+[if-loop-data transactions archived]
+<input type=submit name="unarchiveorder" value="[L]Un-archive order and view next[/L]" class=s3>
 [else]
-[button name="deactivate" text="Deactivate customer"
-	confirm="Are you sure you want to deactivate this customer?"][/button]
+<input type=submit name="archiveorder" value="[L]Archive order and view next[/L]" class=s3>
 [/else]
 [/if-loop-data]
-
-[button text="Change password"]
-user_id=[loop-code]
-mv_nextpage=__UI_BASE__/customer_change_pass
-[/button]
+[if-mm advanced order=d]
+<input type=submit name="deleteorder" value="[L]Delete order and view next[/L]" 
+ onClick="return confirm('[L]Are you sure you want to delete this order?[/L]')" class=s3>
 [/if-mm]
+</form>
 
-[if-mm advanced userdb=d]
-<input type=submit name="deletecustomer" value="Delete customer" 
- onClick="return confirm('Are you sure you want to delete this customer?')">
-[/if-mm]
+[output]
 
-</form>
-</SMALL>
+[/query]
 
-[/loop]
 <!-- ----- END REAL STUFF ----- -->
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Id: customer_view.html,v 1.8.4.1 2003/01/25 22:21:13 racke Exp $ -->



1.11.4.2  +26 -41    interchange/dist/lib/UI/pages/admin/dbdownload.html


rev 1.11.4.2, prev_rev 1.11.4.1
Index: dbdownload.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/dbdownload.html,v
retrieving revision 1.11.4.1
retrieving revision 1.11.4.2
diff -u -r1.11.4.1 -r1.11.4.2
--- dbdownload.html	26 Nov 2000 23:45:08 -0000	1.11.4.1
+++ dbdownload.html	25 Jan 2003 22:21:13 -0000	1.11.4.2
@@ -1,7 +1,7 @@
-[set page_title]Database export[/set]
+[set page_title][L]Database export[/L][/set]
 [set ui_class]Admin[/set]
 [set help_name]dbdownload.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [set page_perm]dbdownload[/set]
 [set exported_tables][/set]
 [if cgi ui_do_export]
@@ -13,63 +13,46 @@
 			 grep /\S/, split /[,\s\0]+/, $CGI->{ui_do_export};
 	[/calc] -->
 [/if]
+
 @_UI_STD_HEAD_@
 
 [if scratch exported_tables]
 <BLOCKQUOTE>
-	[backup-database
+	[msg arg.0='[backup-database
 		compress="[cgi ui_compress]"
-		gnumeric="[cgi ui_gnumeric]"
 		xls="[cgi ui_export_xls]"
+		max_xls_string="[cgi ui_export_max_xls_string]"
 		tables="[scratch exported_tables]"
-	] tables backed up.
+	]']%s tables backed up.[/msg]
 </BLOCKQUOTE>
 [/if]
 
 [set mv_deliver][/set]
 
-[if file backup/DBDOWNLOAD.all.gz]
-<BLOCKQUOTE>
-	[calc] $Scratch->{mv_deliver} .= ' backup/DBDOWNLOAD.all.gz'; return; [/calc]
-	[page href="ui/backup/DBDOWNLOAD.all.gz"
-			form="
-				mv_data_file=backup/DBDOWNLOAD.all.gz
-				mv_todo=deliver
-			"]Download compressed gnumeric file ([file-info name="backup/DBDOWNLOAD.all.gz" date=1])</A><BR>
-</BLOCKQUOTE>
-[/if]
 
-[if file backup/DBDOWNLOAD.all]
-	[calc] $Scratch->{mv_deliver} .= ' backup/DBDOWNLOAD.all'; return; [/calc]
-	[page href="ui/backup/DBDOWNLOAD.all"
-			form="
-				mv_data_file=backup/DBDOWNLOAD.all
-				mv_todo=deliver
-			"]Download gnumeric file ([file-info name="backup/DBDOWNLOAD.all" date=1])</A><BR>
-[/if]
 [if file backup/DBDOWNLOAD.xls]
 	[calc] $Scratch->{mv_deliver} .= ' backup/DBDOWNLOAD.xls'; return; [/calc]
 	[page href="ui/backup/DBDOWNLOAD.xls"
 			form="
 				mv_data_file=backup/DBDOWNLOAD.xls
 				mv_todo=deliver
-			"]Download XLS file ([file-info name="backup/DBDOWNLOAD.xls" date=1])</A><BR>
+			"][L]Download XLS file[/L] ([file-info name="backup/DBDOWNLOAD.xls" date=1])</A><BR>
 [/if]
 
 [if scratch ui_error]
-	<B>Errors on last operation:</B>
+	<B>[L]Errors on last operation[/L]:</B>
 	[scratch ui_error][set ui_error][/set]
 [/if]
 
-<form ACTION="[area @@MV_PAGE@@]" method="post">
+<form ACTION="[area @@MV_PAGE@@]" method="POST" NAME=dbdownload>
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" height=1></td>
+<td class=rborder><img src="bg.gif" height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rborder>
 &nbsp;
 <p>
 
@@ -86,27 +69,29 @@
 	<BR>
 [/loop]
 </blockquote>
+<A HREF="javascript:checkAll(document.dbdownload, 'ui_do_export', 1)">Uncheck all</A><BR>
+<A HREF="javascript:checkAll(document.dbdownload, 'ui_do_export', 0)">Check all</A>
 </td>
 <td valign=top>
 	<B>Options:</B><BR><BR>
 	<BLOCKQUOTE>
 	<INPUT TYPE=checkbox NAME=ui_compress VALUE=on [checked ui_compress on]> Compress (if available)<BR>
-	<INPUT TYPE=radio VALUE=0 NAME=ui_gnumeric  [if !value ui_gnumeric]
-												CHECKED
-												[/if]
-												>
-		No Gnumeric output<BR>
-
-	<INPUT TYPE=radio NAME=ui_gnumeric VALUE=on [checked ui_gnumeric on]>
-		Gnumeric simple text format<BR>
-	<INPUT TYPE=radio NAME=ui_gnumeric VALUE=compressed [checked ui_gnumeric compressed]>
-		Gnumeric simple text format, compressed
 	[if type=explicit compare="[version extended=1 modtest='Spreadsheet::WriteExcel']"]
-	<BR><INPUT TYPE=checkbox VALUE=1 NAME=ui_export_xls> Create XLS spreadsheet
+	<BR><INPUT TYPE=checkbox VALUE=1 NAME=ui_export_xls [checked name=ui_export_xls value=1]> Create XLS spreadsheet
+	<SELECT NAME=ui_export_max_xls_string>
+[loop lr=1 option=ui_export_max_xls_string cgi=1 list="
+0	Max string length 255
+1024	1024 (compatible with some)
+4096	4096 (compatible with some)
+16384	16384 (compatible with some)
+"]
+<OPTION VALUE="[loop-code]"> [loop-pos 1]
+[/loop]
+	</SELECT>
 	[/if]
 	</BLOCKQUOTE>
 	<p>
-	<input type=submit name="do_download" value="Perform export">
+	<input type=submit name="do_download" value="[L]Perform export[/L]">
 	</td>
 </tr>
 </table>
@@ -115,7 +100,7 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.2.4.1   +58 -55    interchange/dist/lib/UI/pages/admin/dbinfo.html


rev 1.2.4.1, prev_rev 1.2
Index: dbinfo.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/dbinfo.html,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- dbinfo.html	23 Sep 2000 17:55:32 -0000	1.2
+++ dbinfo.html	25 Jan 2003 22:21:13 -0000	1.2.4.1
@@ -1,26 +1,20 @@
 [tmp page_perm]techadmin[/tmp]
-[tmp page_title]Administration: [data session arg] table information[/tmp]
-[tmp page_banner]<i>[calc]$Config->{CatalogName}[/calc]</i> table information [if session arg]([data session arg])[/if][/tmp]
+[tmp page_title][L]Administration[/L]: [cgi name=mv_data_table filter=entities keep=1] [L]table information[/L][/tmp]
+[tmp page_banner]<i>[calc]$Config->{CatalogName}[/calc]</i> [L]table information[/L] [if cgi mv_data_table]([cgi name=mv_data_table filter=entities keep=1])[/if][/tmp]
 [set ui_class]Admin[/set]
 [tmp help_name]genconfig.main[/tmp]
-[tmp icon_name]admin/icon_config.gif[/tmp]
+[tmp icon_name]icon_config.gif[/tmp]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
 <center>
-<table __UI_T_PROPERTIES__>
-
-<tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-<tr><td align=left bgcolor=__UI_C_INTBLOCK__>
-<TABLE border=0 width="100%">
+<table width="100%" border=0 cellpadding=2 cellspacing=0 class=rseparator>
 
 [perl tables="[list-databases] __UI_META_TABLE__"]
 	my @tables;
-	if($Session->{arg}) {
-		@tables = split /[\s,\0]+/, $Session->{arg};
+	if($CGI->{mv_data_table}) {
+		@tables = split /[\s,\0]+/, $CGI->{mv_data_table};
 	}
 	else {
 		@tables = sort keys %{$Config->{Database}};
@@ -49,7 +43,7 @@
 	@ignore{@ignore} = @ignore;
 
 	my %typemap = (
-		1	=> 'DBM/Memory, default delimiter',
+		1	=> 'DBM/Memory, auto-detect delimiter',
 		2	=> 'DBM/Memory, LINE delimiter',
 		3	=> 'DBM/Memory, %% delimiter',
 		4	=> 'DBM/Memory, CSV delimiter',
@@ -59,22 +53,35 @@
 		8	=> 'DBI/SQL',
 		9	=> 'LDAP',
 	);
+	my $tcount = 0;
 	for (@tables) {
 		my $tname = $_;
+		my $rclass = ($tcount++ % 2) ? 'rownorm' : 'rowalt';
 		my $tinfo = '';
 		if($mdb and $mdb->record_exists($tname) ) {
 			$tinfo = $mdb->field($tname, 'label');
 			if($tinfo) {
-				$tinfo = "<br>($tinfo)";
+				$tinfo .= "<br>($tinfo)";
 			}
 		}
+
 		my $ref = $Config->{Database}{$_};
 		my $class = $ref->{Class};
 		my $file  = $ref->{file};
 		my $dfile = ($class eq 'DBI' ? $ref->{db_file_extended} : $ref->{db_file});
 		my $dfn   = $dfile;
 		$dfile =~ s:^$Config->{ProductDir}/::o;
-		my $dir   = $ref->{dir} || $Config->{ProductDir};
+		my $dir   = $ref->{DIR} || $Config->{ProductDir};
+		my %delim_map = (
+			"|" => 'PIPE',
+			"\t" => 'TAB',
+			"\n" => 'LINE',
+		);
+
+		my $delim;
+		$delim = $ref->{delimiter};
+		$delim   = $delim_map{$delim} || $delim;
+
 		my $type  = $typemap{$ref->{type}};
 
 		$type .= " DSN=$ref->{DSN}" if $ref->{DSN};
@@ -88,34 +95,43 @@
 		$dfile .= "</TT>";
 		my $obj   = $ref->{Object};
 		$out .= <<EOF;
-<TR>
-	<TH VALIGN=TOP ALIGN=RIGHT width="15%">
-	$tname$tinfo
-	</TH>
-	<td VALIGN=TOP>
-		<TABLE border=1 width="100%">
-		<tr>
-			<th valign=top align=left>Type</th>
-			<td>$type</td>
-		</tr>
-		<tr>
-			<th valign=top align=left width="30%">Class</th>
-			<td>$class</td>
+		<tr class=rhead>
+			<td valign=TOP align=center class=rhead colspan=2>
+			<b>$tname$tinfo</b>
+			</td>
 		</tr>
-		<tr>
-			<th valign=top align=left width="30%">Directory</th>
-			<td>$dir</td>
-		</tr>
-		<tr>
-			<th valign=top align=left width="30%">Text File</th>
-			<td>$file</td>
+		<tr class=rownorm>
+			<th valign=top align=left class=clabel>Type</th>
+			<td class=cdata>$type</td>
+		</tr>
+		<tr class=rownorm>
+			<th valign=top align=left width="30%" class=clabel>Class</th>
+			<td class=cdata>$class</td>
+		</tr>
+		<tr class=rownorm>
+			<th valign=top align=left width="30%" class=clabel>Directory</th>
+			<td class=cdata>$dir</td>
+		</tr>
+		<tr class=rownorm>
+			<th valign=top align=left width="30%" class=clabel>Text File</th>
+			<td class=cdata>$file</td>
+		</tr>
+		<tr class=rownorm>
+			<th valign=top align=left width="30%" class=clabel>DB File</th>
+			<td class=cdata>$dfile</td>
 		</tr>
+EOF
+
+		$out .= <<EOF if $delim;
 		<tr>
-			<th valign=top align=left width="30%">DB File</th>
-			<td>$dfile</td>
+			<th valign=top align=left width="30%">Delimiter</th>
+			<td>$delim</td>
 		</tr>
-		<tr>
-			<th colspan=2>Other</th>
+EOF
+
+		$out .= <<EOF;
+		<tr class=rhead>
+			<td colspan=2 class=rhead>Parameters</th>
 		</tr>
 EOF
 		for(sort keys %{$ref}) {
@@ -123,9 +139,9 @@
 			my $key = $_;
 			my $r = $ref->{$_};
 			my $o = <<EOF;
-		<tr>
-			<th valign=top align=left width="30%">$_</th>
-			<td>
+		<tr class=rownorm>
+			<td valign=top align=left width="30%" class=clabel>$_</td>
+			<td class=cdata>
 EOF
 			if(! defined $r) {
 				$o .= "undef";
@@ -162,9 +178,6 @@
 		}
 
 		$out .= <<EOF;
-		</table>
-	</TD>
-</TR>
 EOF
 
 	}
@@ -172,16 +185,6 @@
 [/perl]
 
 </TABLE>
-
-</td></tr>
-
-<tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-</table>
-</center>
-
 
 <!-- ----- END REAL STUFF ----- -->
 



1.2.4.1   +4 -3      interchange/dist/lib/UI/pages/admin/do_upload.html


rev 1.2.4.1, prev_rev 1.2
Index: do_upload.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/do_upload.html,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- do_upload.html	6 Aug 2000 20:16:59 -0000	1.2
+++ do_upload.html	25 Jan 2003 22:21:13 -0000	1.2.4.1
@@ -1,5 +1,6 @@
+@_UI_STD_INIT_@
 [if-mm function="!files" name="[value ui_upload_fn]"]
-[seti ui_error] Not allowed to upload [value ui_upload_fn].[/seti]
+[seti ui_error] [msg arg.0="[value ui_upload_fn]"]Not allowed to upload %s.[/msg][/seti]
 [bounce page=__UI_BASE__/error]
 [/if-mm]
 
@@ -28,8 +29,8 @@
 							outfile="[value ui_upload_fn]"
 						]
 					|]
-[bounce href="[either][return-to url][or][area __UI_BASE__/genupload][/either]"]
+[bounce href="[either][return-to url][or][area __UI_BASE__/file_transfer][/either]"]
 [else]
-[seti ui_error] Error writing file [value ui_upload_fn].[/seti]
+[seti ui_error][msg arg.0="[value ui_upload_fn]"]Error writing file %s.[/msg][/seti]
 [bounce page=__UI_BASE__/error]
 [/else][/if]



1.2.4.3   +32 -19    interchange/dist/lib/UI/pages/admin/do_view.html


rev 1.2.4.3, prev_rev 1.2.4.2
Index: do_view.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/do_view.html,v
retrieving revision 1.2.4.2
retrieving revision 1.2.4.3
diff -u -r1.2.4.2 -r1.2.4.3
--- do_view.html	17 Apr 2001 08:34:18 -0000	1.2.4.2
+++ do_view.html	25 Jan 2003 22:21:13 -0000	1.2.4.3
@@ -1,19 +1,19 @@
-[seti total_junk][perl]
+@_UI_STD_INIT_@[tmp total_junk][set violation]Failed to run security checks.[/set][perl tables="__UI_ACCESS_TABLE__ __UI_META_TABLE__"]
 	delete $Scratch->{violation};
 	$_ = delete $Session->{arg};
-	$Scratch->{violation} = 'Must be logged in.'
+	$Scratch->{violation} = errmsg('Must be logged in.')
 		unless $Session->{logged_in};
-	$Scratch->{violation} = 'Must be logged in as admin.'
+	$Scratch->{violation} = errmsg('Must be logged in as admin.')
 		unless $Session->{admin};
-	$Scratch->{violation} = 'No .. allowed in file name.'
+	$Scratch->{violation} = errmsg('No .. allowed in file name.')
 		if m{\.\./};
-	$Scratch->{violation} = 'No | allowed.'
+	$Scratch->{violation} = errmsg('No | allowed.')
 		if m{\|};
-	$Scratch->{violation} = 'No whitespace allowed.'
+	$Scratch->{violation} = errmsg('No whitespace allowed.')
 		if m{\s};
-	$Scratch->{violation} = 'No drive letters!'
+	$Scratch->{violation} = errmsg('No drive letters!')
 		if m{^\s*[a-zA-Z]:/};
-	$Scratch->{violation} = 'No absolute file paths allowed.'
+	$Scratch->{violation} = errmsg('No absolute file paths allowed.')
 		if s{^/}{};
 	if($Scratch->{violation}) {
 			Log (<<EOF);
@@ -25,29 +25,42 @@
 	$Session->{username}
 	$Session->{host}
 EOF
+		return;
 	}
 	else {
 		$Scratch->{file_to_view} = $_;
 	}
-	if(/\.gif$/i) {
-		$Scratch->{content_type} = 'image/gif';
-	}
-	elsif(/\.jpe?g$/i) {
-		$Scratch->{content_type} = 'image/jpeg';
-	}
-	elsif(/\.png$/i) {
-		$Scratch->{content_type} = 'image/png';
+
+	delete $Scratch->{alternate_view};
+	if(
+		/:/
+		and $Tag->if_mm('super')
+		and $Config->{SessionType} eq 'File'
+		and $sd = $Config->{SessionDatabase}
+		and $sd =~ s:^$Config->{VendRoot}/::
+		and $_ =~ m{^$sd/././(.*)}
+		and $check = $1
+		and $check !~ /\.lock$/
+		) 
+	{
+		$Scratch->{alternate_view} = "[dump-session name='$check']";
+		$Scratch->{content_type} = 'text/plain';
+		delete $Scratch->{file_to_view};
 	}
 	else {
-		$Scratch->{content_type} = 'text/plain';
+		$Scratch->{content_type} = $Tag->filter('mime_type', $_);
+		$Scratch->{content_type} = $CGI->{content_type} || "text/plain"
+			if $Scratch->{content_type} eq 'application/octet-stream'
+			or $Scratch->{content_type} eq 'text/html';
 	}
 	return;
 [/perl][if scratch violation]
 [seti ui_error][scratch violation] -- logged.[/seti]
 [bounce page="__UI_BASE__/error"]
 [else]
-[tag op=header interpolate=1]Content-Type: [scratch content_type][set content_type][/set][/tag]
+[comment][calc]Debug("Setting content-type to $Scratch->{content_type}"); return; [/calc][/comment]
+[tag op=header interpolate=1]Content-Type: [scratchd content_type][/tag]
 [/else]
 [/if]
-[/seti][file name="[scratch file_to_view]" type="[value download_conversion]"
+[/tmp][scratchd name=alternate_view interpolate=1][file name="[scratch file_to_view]" type="[value download_conversion]"
 ][goto end=1 abort=1]



1.8.4.3   +97 -115   interchange/dist/lib/UI/pages/admin/entry.html


rev 1.8.4.3, prev_rev 1.8.4.2
Index: entry.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/entry.html,v
retrieving revision 1.8.4.2
retrieving revision 1.8.4.3
diff -u -r1.8.4.2 -r1.8.4.3
--- entry.html	20 Oct 2000 18:08:23 -0000	1.8.4.2
+++ entry.html	25 Jan 2003 22:21:13 -0000	1.8.4.3
@@ -1,7 +1,7 @@
-[set page_title]Order Entry[/set]
+[set page_title][L]Order Entry[/L][/set]
 [set ui_class]Orders[/set]
 [set help_name]order_entry.main[/set]
-[set icon_name]admin/icon_orders.gif[/set]
+[set icon_name]icon_orders.gif[/set]
 [seti meta_header]
 <SCRIPT>    // JavaScript Form Validation Demo    // by Paul Colton
     function check_tax(form) {
@@ -38,31 +38,31 @@
 	<COL WIDTH="1%">
 	<COL WIDTH="18%">
 	<THEAD>
-		<tr bgcolor="000000" height=1><td colspan=7></td></tr>
-		<TR BGCOLOR=__UI_C_TITLEBARBG__ VALIGN=TOP>
-			<TH BGCOLOR=__UI_C_TITLEBARBG__ WIDTH="10%">
-				<P><FONT COLOR=__UI_C_TITLEBARTXT__><FONT SIZE="-1" FACE="helvetica, sans-serif">SKU</FONT></FONT></P>
+		<tr class=rborder height=1><td colspan=7></td></tr>
+		<TR class=rmarq VALIGN=TOP>
+			<TH class=rmarq WIDTH="10%">
+				[L]SKU[/L]
 			</TH>
-			<TH BGCOLOR=__UI_C_TITLEBARBG__ WIDTH="1%">&nbsp;</TH>
-			<TH BGCOLOR=__UI_C_TITLEBARBG__ WIDTH="40%">
-				<P><FONT COLOR=__UI_C_TITLEBARTXT__><FONT SIZE="-1" FACE="helvetica, sans-serif">Description</FONT></FONT></P>
+			<TH class=rmarq WIDTH="1%">&nbsp;</TH>
+			<TH class=rmarq WIDTH="40%">
+				[L]Description[/L]
 			</TH>
-			<TH BGCOLOR=__UI_C_TITLEBARBG__ WIDTH="13%">
-				<P><FONT COLOR=__UI_C_TITLEBARTXT__><FONT SIZE="-1" FACE="helvetica, sans-serif">Quantity</FONT></FONT></P>
+			<TH class=rmarq WIDTH="13%">
+				[L]Quantity[/L]
 			</TH>
-			<TH ALIGN=RIGHT BGCOLOR=__UI_C_TITLEBARBG__ WIDTH="17%">
-				<P><FONT COLOR=__UI_C_TITLEBARTXT__><FONT SIZE="-1" FACE="helvetica, sans-serif">Price</FONT></FONT></P>
+			<TH ALIGN=RIGHT class=rmarq WIDTH="17%">
+				[L]Price[/L]
 			</TH>
-			<TH BGCOLOR=__UI_C_TITLEBARBG__ WIDTH="1%">&nbsp;</TH>
-			<TH ALIGN=RIGHT BGCOLOR=__UI_C_TITLEBARBG__ WIDTH="18%">
-				<P><FONT COLOR=__UI_C_TITLEBARTXT__><FONT SIZE="-1" FACE="helvetica, sans-serif">Extension</FONT></FONT></P>
+			<TH class=rmarq WIDTH="1%">&nbsp;</TH>
+			<TH ALIGN=RIGHT class=rmarq WIDTH="18%">
+				[L]Extension[/L]
 			</TH>
 		</TR>
-		<tr bgcolor="000000" height=1><td colspan=7></td></tr>
+		<tr class=rborder height=1><td colspan=7></td></tr>
 	</THEAD>
 	<TBODY>
-<TR BGCOLOR=__UI_C_INTBLOCK__>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP align=center>
+<TR class=rnorm>
+	<TD class=rnorm VALIGN=TOP align=center>
 	[search-region prefix=sku]
 	[if value mv_search_match_count]
 	<small>
@@ -80,104 +80,91 @@
 	[/if]
 	[/search-region]
 	</TD>
-	<TH BGCOLOR=__UI_C_INTBLOCK__ WIDTH="2">&nbsp;</TH>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ ALIGN=CENTER VALIGN=TOP MARGINWIDTH=12 MARGINHEIGHT=12>
+	<TH class=rnorm WIDTH="2">&nbsp;</TH>
+	<TD class=rnorm ALIGN=CENTER VALIGN=TOP MARGINWIDTH=12 MARGINHEIGHT=12>
 	<INPUT NAME=mv_searchspec
 			onChange="this.form.action='[process-search]'; this.form.submit()">
 	</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP ALIGN=CENTER>
+	<TD class=rnorm VALIGN=TOP ALIGN=CENTER>
 	<INPUT TYPE=text NAME="mv_order_quantity" onChange="this.form.submit()" SIZE=3>
 
 	</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP ALIGN=RIGHT>
+	<TD class=rnorm VALIGN=TOP ALIGN=RIGHT>
 		&nbsp;
 	</TD>
-	<TH BGCOLOR=__UI_C_INTBLOCK__ WIDTH="2">&nbsp;</TH>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP ALIGN=RIGHT>
+	<TH class=rnorm WIDTH="2">&nbsp;</TH>
+	<TD class=rnorm VALIGN=TOP ALIGN=RIGHT>
 		&nbsp;
 	</TD>
 </TR>
-<TR><TD ALIGN=CENTER COLSPAN=7><IMG SRC="clear.gif" WIDTH="1" ALT="" HEIGHT="1" BORDER="0"></TR>
+<TR><TD ALIGN=CENTER COLSPAN=7><IMG SRC="bg.gif" WIDTH="1" ALT="" HEIGHT="1" BORDER="0"></TR>
 
 [item-list]
-<TR BGCOLOR=__UI_C_INTBLOCK__>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP align=center>
+<TR class=rnorm>
+	<TD class=rnorm VALIGN=TOP align=center>
 	<FONT SIZE="-2"><INPUT TYPE=checkbox NAME="[quantity-name]"
 			   onClick="this.form.action='[process-target]',
 			   			this.form.submit()"
 			   VALUE=0>remove</FONT>&nbsp;&nbsp;&nbsp;[item-code]</TD>
-	<TH BGCOLOR=__UI_C_INTBLOCK__ WIDTH="2">&nbsp;</TH>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP MARGINWIDTH=12 MARGINHEIGHT=12>
+	<TH class=rnorm WIDTH="2">&nbsp;</TH>
+	<TD class=rnorm VALIGN=TOP MARGINWIDTH=12 MARGINHEIGHT=12>
 	[page [item-code]][item-description]</A>
 	[if-item-field weight]&nbsp;&nbsp;&nbsp;
 	<SMALL>WEIGHT: [summary amount=`[item-quantity] * [item-field weight]`]</SMALL>
 	[/if-item-field]
 	&nbsp;&nbsp;&nbsp;
-	[if-item-field related]
-	[if !ordered [item-field related]]
-	<TABLE CELLPADDING=0 CELLSPACING=0 WIDTH="100%">
-	[loop arg="[item-field related]" prefix=related]
-		[related-change 1][condition]1[/condition]
-		<TR><TD COLSPAN=2 BGCOLOR=__UI_C_TITLEBARBG__><FONT COLOR=__UI_C_TITLEBARTXT__>Other items to suggest:</TD>
-		</TR>
-		[/related-change 1]
-		[if !ordered [related-code]]
-		<TR>
-		<TD><FONT SIZE="1"><INPUT TYPE=checkbox NAME="mv_order_item"
-			onClick="this.form.action='[process-target]',
-					this.form.submit()"
-			VALUE="[related-code]"></TD>
-		<TD><FONT SIZE="1">[related-field title]</TD>
-		</TR>	
-		[/if]
-	[/loop]
-	</TABLE>
-	[/if]
-	[/if-item-field]<FONT SIZE=1>[item-accessories size][item-accessories color]</FONT>	
+	[if-item-data options o_enable]
+	<br>
+	<table>
+	[table-organize cols=2]
+	[item-options td=1]
+	[/table-organize]
+	</table>
+	[/if-item-data]
 	</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP ALIGN=CENTER>
+	<TD class=rnorm VALIGN=TOP ALIGN=CENTER>
 	<INPUT TYPE=text NAME="[quantity-name]" VALUE="[item-quantity]" SIZE=3>
 
 	</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP ALIGN=RIGHT>
+	<TD class=rnorm VALIGN=TOP ALIGN=RIGHT>
 		[discount-price]
 		[if discount [item-code]]
-		<BR><FONT COLOR=__CONTRAST__ SIZE=-2>Item is discounted
+		<BR><FONT COLOR=__CONTRAST__ SIZE=-2>[L]Item is discounted[/L]
 			[item-discount]
 			</FONT>
 		[/if]
 	</TD>
-	<TH BGCOLOR=__UI_C_INTBLOCK__ WIDTH="2">&nbsp;</TH>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ VALIGN=TOP ALIGN=RIGHT>
+	<TH class=rnorm WIDTH="2">&nbsp;</TH>
+	<TD class=rnorm VALIGN=TOP ALIGN=RIGHT>
 		[item-subtotal]
 	</TD>
 </TR>
-<TR><TD ALIGN=CENTER COLSPAN=7><IMG SRC="clear.gif" WIDTH="1" ALT="" HEIGHT="1" BORDER="0"></TR>
+<TR><TD ALIGN=CENTER COLSPAN=7><IMG SRC="bg.gif" WIDTH="1" ALT="" HEIGHT="1" BORDER="0"></TR>
 [/item-list]
 <TR>
 <TD COLSPAN=4 ROWSPAN=5 ALIGN=LEFT VALIGN=CENTER>
 &nbsp;&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit
 	onClick="this.form.action='[process-target]'"
-	VALUE="Enter / Recalculate">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<FONT SIZE="-1">[summary format="<B>Shipping weight:</B> %s" total=1]</FONT></TD>
+	VALUE="[L]Enter / Recalculate[/L]">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<FONT SIZE="-1">[summary format="<B>[L]Shipping weight[/L]:</B> %s" total=1]</FONT></TD>
 <TR>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL><B>Subtotal</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL>&nbsp;</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ ALIGN=RIGHT VALIGN=RIGHT><SMALL><B>[subtotal]</TD>
+	<TD class=rnorm><SMALL><B>[L]Subtotal[/L]</TD>
+	<TD class=rnorm><SMALL>&nbsp;</TD>
+	<TD class=rnorm ALIGN=RIGHT VALIGN=RIGHT><SMALL><B>[subtotal]</TD>
 </TR>
 <TR>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL>Shipping</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL>&nbsp;</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ ALIGN=RIGHT VALIGN=RIGHT><SMALL>[shipping]</TD>
+	<TD class=rnorm><SMALL>[L]Shipping[/L]</TD>
+	<TD class=rnorm><SMALL>&nbsp;</TD>
+	<TD class=rnorm ALIGN=RIGHT VALIGN=RIGHT><SMALL>[shipping]</TD>
 </TR>
 <TR>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL>Tax</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL>&nbsp;</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ ALIGN=RIGHT VALIGN=RIGHT><SMALL>[salestax]</TD>
+	<TD class=rnorm><SMALL>[L]Tax[/L]</TD>
+	<TD class=rnorm><SMALL>&nbsp;</TD>
+	<TD class=rnorm ALIGN=RIGHT VALIGN=RIGHT><SMALL>[salestax]</TD>
 </TR>
 <TR>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL><B>TOTAL</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__><SMALL>&nbsp;</TD>
-	<TD BGCOLOR=__UI_C_INTBLOCK__ ALIGN=RIGHT VALIGN=RIGHT><SMALL><B>[total-cost]</TD>
+	<TD class=rnorm><SMALL><B>[L]TOTAL[/L]</TD>
+	<TD class=rnorm><SMALL>&nbsp;</TD>
+	<TD class=rnorm ALIGN=RIGHT VALIGN=RIGHT><SMALL><B>[total-cost]</TD>
 </TR>
 </TBODY>
 </TABLE>
@@ -190,16 +177,13 @@
 [/if]
 <INPUT TYPE=hidden NAME=mv_doit          VALUE=refresh>
 <INPUT TYPE=hidden NAME=mv_nextpage      VALUE="@@MV_PAGE@@">
-[comment]
-<!-- Order routes in catalog.cfg -->
-<!-- Checkout profile in etc/order.profiles -->
-[/comment]
+[comment] checkout_profile in etc/profiles.order [/comment]
 <INPUT TYPE=hidden NAME=mv_order_profile VALUE=checkout_profile>
-<INPUT TYPE=hidden NAME=mv_order_route   VALUE="log_entry main copy_user">
+[comment] Order routes in catalog.cfg [/comment]
 
 <br>
-<TABLE border=0 WIDTH=600><TR><TD BGCOLOR="__UI_C_TITLEBARBG__">
-<FONT COLOR="__UI_C_TITLEBARTXT__"><B>Shipping Address</B></FONT>
+<TABLE border=0 WIDTH=600><TR><TD class=rmarq>
+[L]Shipping Address[/L]
 </TD></TR></TABLE>
 
 [calc]
@@ -254,24 +238,24 @@
 <TABLE WIDTH="90%" cellpadding=3 border=0>
 <TR>
 	<TD ALIGN=RIGHT>
-	Customer ID</TD>
+	[L]Customer ID[/L]</TD>
 	<TD>
 		<INPUT TYPE=text NAME=customer_id VALUE="[value customer_id]" size=30>
-		<INPUT TYPE=checkbox NAME=new_customer_id VALUE=1 [if !value customer_id]CHECKED[else]onClick="this.form.customer_id.value=''; this.form.submit()"[/else][/if]>New customer
+		<INPUT TYPE=checkbox NAME=new_customer_id VALUE=1 [if !value customer_id]CHECKED[else]onClick="this.form.customer_id.value=''; this.form.submit()"[/else][/if]>[L]New customer[/L]
 	</TD>
 </TR>
 
 <TR>
 	<TD ALIGN=RIGHT>
-	[error name=fname std_label="First Name" required=1]</TD>
+	[error name=fname std_label="[L]First Name[/L]" required=1]</TD>
 	<TD>
 		<INPUT TYPE=text NAME=fname VALUE="[value name=fname default="[loop-data userdb fname]"]" size=30>
-	[error name=lname std_label=Last required=1]&nbsp;<INPUT TYPE=text NAME=lname VALUE="[value name=lname default="[loop-data userdb lname]"]" size=30>
+	[error name=lname std_label="[L]Last Name[/L]" required=1]&nbsp;<INPUT TYPE=text NAME=lname VALUE="[value name=lname default="[loop-data userdb lname]"]" size=30>
 	</TD>
 </TR>
 
 <TR>
-	<TD ALIGN=RIGHT>[error name=address1 std_label=Address required=1]</TD>
+	<TD ALIGN=RIGHT>[error name=address1 std_label=[L]Address[/L] required=1]</TD>
 	<TD ALIGN=LEFT>
 		<INPUT TYPE=text NAME=address1 VALUE="[value name=address1 default="[loop-data userdb address1]"]" size=60>
 	</TD>
@@ -286,7 +270,7 @@
 
 <TR>
 	<TD ALIGN=RIGHT>
-		[error name=city std_label="City" required=1]
+		[error name=city std_label="[L]City[/L]" required=1]
 	</TD>
 	<TD>
 	<TABLE>
@@ -295,14 +279,14 @@
 			<INPUT TYPE=text NAME=city VALUE="[value name=city default="[loop-data userdb city]"]" size=20>
 		</TD>
 		<TD>
-			[error name=state std_label="State/Province" required=1]
+			[error name=state std_label="[L]State/Province[/L]" required=1]
 		</TD>
 		<TD>
 			<INPUT onChange="check_tax(this.form)"
 				TYPE=text NAME=state VALUE="[value name=state default="[loop-data userdb state]"]" size=3>
 		</TD>
 		<TD>
-			[error name=zip std_label="Zip/Postal Code" required=1]
+			[error name=zip std_label="[L]Zip/Postal Code[/L]" required=1]
 		</TD>
 		<TD>
 			<INPUT TYPE=text NAME=zip VALUE="[value name=zip default="[loop-data userdb zip]"]" size=10>
@@ -313,7 +297,7 @@
 </TR>
 
 <TR>
-	<TD ALIGN=RIGHT><B>[error name=email std_label="Email Address" required=1]</B></TD>
+	<TD ALIGN=RIGHT><B>[error name=email std_label="[L]Email Address[/L]" required=1]</B></TD>
 	<TD ALIGN=LEFT>
 		<INPUT TYPE=text NAME=email VALUE="[value name=email default="[loop-data userdb email]"]" size=42>
 	</TD>
@@ -322,15 +306,15 @@
 
 <TR>
 		<TD ALIGN=RIGHT>
-		<B>Country</B>
+		<B>[L]Country[/L]</B>
 		</TD>
 		<TD>
 		[value name=country set="[value name=country default='[loop-data userdb country]']" hide=1]
 		[if value country =~ /(^$|US|CA)/]
 		<SELECT NAME=country onChange="this.form.submit()">
-			<OPTION VALUE="US"> United States
-			<OPTION [selected country CA] VALUE="CA"> Canada
-			<OPTION VALUE="JP"> Other (select to change)
+			<OPTION VALUE="US"> [L]United States[/L]
+			<OPTION [selected country CA] VALUE="CA"> [L]Canada[/L]
+			<OPTION VALUE="JP"> [L]Other (select to change)[/L]
 		</SELECT>
 		[else]
 		<SELECT onChange="this.form.submit()" NAME=country>
@@ -339,12 +323,12 @@
 		[/loop]
 		</SELECT>
 		[/else]
-		[/if] <FONT SIZE="1"><B>(will update display)</B></FONT>
+		[/if] <FONT SIZE="1"><B>[L](will update display)[/L]</B></FONT>
 		</TD>
 </TR>
 
 <TR>	
-	<TD ALIGN=RIGHT>[error name=phone_day std_label="Daytime Phone" required=1]</TD>
+	<TD ALIGN=RIGHT>[error name=phone_day std_label="[L]Daytime Phone[/L]" required=1]</TD>
 	<TD>
 	<TABLE>
 	<TR>
@@ -352,7 +336,7 @@
 		<INPUT TYPE=text NAME=phone_day VALUE="[value name=phone_day default="[loop-data userdb phone_day]"]" size=16>
 		</TD>
 		<TD ALIGN=RIGHT>
-		[error name=phone_night std_label="Evening Phone" required=0]
+		[error name=phone_night std_label="[L]Evening Phone[/L]" required=0]
 		</TD>
 		<TD>
 		<INPUT TYPE=text NAME=phone_night VALUE="[value name=phone_night default="[loop-data userdb phone_night]"]" size=16>
@@ -361,13 +345,13 @@
 	</TABLE>
 </TR>
 
-[set Find]
+[set [L]Find[/L]]
 mv_nextpage=__UI_BASE__/entry_select
 mv_change_frame=select
 mv_todo=back
 [/set]
 
-[set Clear]
+[set [L]Clear[/L]]
 customer_id=
 customer=NEW
 mv_todo=return
@@ -377,14 +361,14 @@
 <TR>
 	<TD>&nbsp;</TD>
 	<TD>
-	<B><INPUT TYPE=submit NAME=mv_click VALUE=Find>
-	<INPUT TYPE=submit NAME=mv_click VALUE=Clear></B>
+	<B><INPUT TYPE=submit NAME=mv_click VALUE=[L]Find[/L]>
+	<INPUT TYPE=submit NAME=mv_click VALUE=[L]Clear[/L]></B>
 	 </TD>
 </TR>
 <TR>
 	<TD>&nbsp;</TD>
 	<TD>
-		<SMALL><I><B>Bold</B> fields needed to process the order</I></SMALL>
+		<SMALL><I>[msg arg.0="<B>" arg.1="</B>"]%sBold%s fields needed to process the order[/msg]</I></SMALL>
 	</TD>
 </TR>
 
@@ -397,8 +381,8 @@
 [/item-list]
 [if !scratch only_downloadable]
 <P>
-<TABLE WIDTH=600><TR><TD BGCOLOR="__UI_C_TITLEBARBG__">
-<FONT COLOR=__UI_C_TITLEBARTXT__><B>Choose your shipping method</B></FONT>
+<TABLE WIDTH=600><TR><TD class=rmarq>
+[L]Choose your shipping method[/L]
 </TD></TR></TABLE>
 
 <P>
@@ -412,13 +396,13 @@
 		]
     </SELECT>
 </TD>
-<TD ALIGN=RIGHT><INPUT TYPE=submit VALUE="Update"></TD>
+<TD ALIGN=RIGHT><INPUT TYPE=submit VALUE="[L]Update[/L]"></TD>
 </TR>
 
 <TR>
 <TD COLSPAN=2 ALIGN=CENTER>
 [if session ship_message]
-<BR><B>Note:</B> [data session ship_message]<BR>
+<BR><B>[L]Note:[/L]</B> [data session ship_message]<BR>
 [/if]
 </TD>
 </TR></TABLE>
@@ -426,8 +410,8 @@
 
 
 [if variable CREDIT_CARDS_ACCEPTED =~ /\S/]
-<TABLE WIDTH=600><TR><TD BGCOLOR="__UI_C_TITLEBARBG__">
-<FONT COLOR=__UI_C_TITLEBARTXT__>[error std_label="<B>Credit Card Information</B>" name=mv_credit_card_valid]</FONT>
+<TABLE WIDTH=600><TR><TD class=rmarq>
+[error std_label="<B>Credit Card Information</B>" name=mv_credit_card_valid]
 </TD></TR></TABLE>
 
 <P>  
@@ -513,8 +497,8 @@
 	<I>I will pay by COD ([handling cod] extra charge will be added)</I><BR>
 [/if]
 <br>
-<TABLE WIDTH=__UI_MAIN_WIDTH__><TR><TD BGCOLOR="__UI_C_TITLEBARBG__">
-<FONT COLOR="__UI_C_TITLEBARTXT__"><B>Billing Address (if different)</B></FONT>
+<TABLE WIDTH=__UI_MAIN_WIDTH__><TR><TD class=rmarq>
+Billing Address (if different)
 </TD></TR></TABLE>
 
 <TABLE border=0>
@@ -559,12 +543,8 @@
 
 </TABLE><br>
 
-[set Place Order!]
-mv_todo=submit
-[/set]
-
-<TABLE WIDTH=600><TR><TD BGCOLOR="__UI_C_TITLEBARBG__">
-<FONT COLOR="__UI_C_TITLEBARTXT__"><B>Email preferences</B></FONT>
+<TABLE WIDTH=600><TR><TD class=rmarq>
+Email preferences
 </TD></TR></TABLE>
 
 <TABLE>
@@ -589,11 +569,13 @@
 </TABLE>
 
 <CENTER>
-[set Place Order]
-mv_todo=submit
+[set [L]Place Order[/L]]
+	mv_todo=submit
+	mv_nextpage=admin/order
+	[value name=mv_order_route set="log_entry main copy_user" hide=1]
 [/set]
 
-<INPUT name=mv_click TYPE=submit VALUE="Place Order">
+<INPUT name=mv_click TYPE=submit VALUE="[L]Place Order[/L]">
 </CENTER>
 
 <P>



1.5.4.1   +7 -6      interchange/dist/lib/UI/pages/admin/entry_select.html


rev 1.5.4.1, prev_rev 1.5
Index: entry_select.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/entry_select.html,v
retrieving revision 1.5
retrieving revision 1.5.4.1
diff -u -r1.5 -r1.5.4.1
--- entry_select.html	23 Sep 2000 17:55:32 -0000	1.5
+++ entry_select.html	25 Jan 2003 22:21:13 -0000	1.5.4.1
@@ -1,6 +1,6 @@
 [set page_perm]userdb[/set]
 [set ui_class]Orders[/set]
-[set icon_name]admin/icon_orders.gif[/set]
+[set icon_name]icon_orders.gif[/set]
 [set page_title] Select Customer [/set]
 
 @_UI_STD_HEAD_@
@@ -18,29 +18,30 @@
 <!-- ----- BEGIN REAL STUFF ----- -->
 
 <form action="[process]" method=POST>
+<input type=hidden name=mv_session_id value="[data session id]">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=return>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="__UI_BASE__/entry">
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <!-- ----- Show the operation buttons ----- -->
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_LEFT_WIDTH__>
+<td class=rnorm width=__UI_LEFT_WIDTH__>
 
 <input type=submit value="Select"><br>
 
 <br>
 
 </td>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_RIGHT_WIDTH__>
+<td class=rnorm width=__UI_RIGHT_WIDTH__>
 
 <!-- ----- Show the customer list box ----- -->
 
@@ -90,7 +91,7 @@
 </td></tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 </table>
 



1.6.4.1   +2 -2      interchange/dist/lib/UI/pages/admin/env_vars.html


rev 1.6.4.1, prev_rev 1.6
Index: env_vars.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/env_vars.html,v
retrieving revision 1.6
retrieving revision 1.6.4.1
diff -u -r1.6 -r1.6.4.1
--- env_vars.html	14 Sep 2000 07:46:48 -0000	1.6
+++ env_vars.html	25 Jan 2003 22:21:13 -0000	1.6.4.1
@@ -1,7 +1,7 @@
-[set page_title]Environment Variables[/set]
+[set page_title][L]Environment Variables[/L][/set]
 [set ui_class]Admin[/set]
 [set help_name]env_vars[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->



1.13.4.1  +47 -9     interchange/dist/lib/UI/pages/admin/error.html


rev 1.13.4.1, prev_rev 1.13
Index: error.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/error.html,v
retrieving revision 1.13
retrieving revision 1.13.4.1
diff -u -r1.13 -r1.13.4.1
--- error.html	23 Sep 2000 17:55:32 -0000	1.13
+++ error.html	25 Jan 2003 22:21:13 -0000	1.13.4.1
@@ -2,38 +2,76 @@
 [set ui_class]None[/set]
 [set page_perm][/set]
 [set no_login_required]1[/set]
-[seti page_title]Error: [scratch ui_error][/seti]
+[seti page_title][L]Error[/L]: [scratch ui_error][/seti]
 [set help_name]item.error[/set]
-[set icon_name]admin/icon_error.gif[/set]
+[set icon_name]icon_error.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
+[tmp loginhint][msg arg.0="[page __UI_BASE__/login]<U><B>" arg.1="</b></U></A>"]Maybe you need to %slog in%s?[/msg][/tmp]
 <table __UI_T_PROPERTIES__>
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
+[if session ui_error]
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
+class=rnorm>
 &nbsp;
 <p>
 
-The following error occurred:
+[L]The following error occurred:[/L]
 <p>
 <BLOCKQUOTE>
-<b>[scratch ui_error]</b>[set ui_error][/set]
+<b>[calc] delete $Session->{ui_error} [/calc]</b>
 </BLOCKQUOTE>
 <p>
-Please correct and try again.
+[L]Please correct and try again.[/L]
 <p>
-<i>Maybe you need to [page __UI_BASE__/login]<U><B>log in</b></U></A>?</I>
+<i>[scratch loginhint]</i>
 &nbsp;
 </td>
 </tr>
+[/if]
 
+[if scratch ui_error]
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+	<td class=rnorm>
+		&nbsp;
+		<p>
+
+		[L]The following error occurred:[/L]
+		<blockquote class=cerror>
+			[scratchd ui_error]
+		</blockquote>
+		[L]Please correct and try again.[/L]
+		&nbsp;
+	</td>
+</tr>
+[/if]
+
+
+[if scratch violation]
+<tr>
+	<td class=rnorm>
+		&nbsp;
+		<p>
+
+		[L]The following violation occurred:[/L]
+			<blockquote class=cerror>
+				[scratchd violation]
+			</blockquote>
+		[L]Please correct and try again.[/L]
+		<p>
+			<i>[scratch loginhint]</i>
+	&nbsp;
+	</td>
+</tr>
+[/if]
+
+<tr>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.7.4.1   +4 -4      interchange/dist/lib/UI/pages/admin/error_item.html


rev 1.7.4.1, prev_rev 1.7
Index: error_item.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/error_item.html,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- error_item.html	23 Sep 2000 17:55:32 -0000	1.7
+++ error_item.html	25 Jan 2003 22:21:13 -0000	1.7.4.1
@@ -3,7 +3,7 @@
 [set ui_class]None[/set]
 [set page_banner]Error[/set]
 [set help_name]item.edit.error[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 
 @_UI_STD_HEAD_@
 
@@ -11,11 +11,11 @@
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
+class=rnorm>
 &nbsp;
 <p>
 
@@ -30,7 +30,7 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.9.4.3   +42 -47    interchange/dist/lib/UI/pages/admin/export_table.html


rev 1.9.4.3, prev_rev 1.9.4.2
Index: export_table.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/export_table.html,v
retrieving revision 1.9.4.2
retrieving revision 1.9.4.3
diff -u -r1.9.4.2 -r1.9.4.3
--- export_table.html	26 Nov 2000 23:53:53 -0000	1.9.4.2
+++ export_table.html	25 Jan 2003 22:21:13 -0000	1.9.4.3
@@ -1,17 +1,11 @@
-[if cgi mv_data_table]
-[if-mm function=!export table="[cgi mv_data_table]"]
-[set ui_error]Not allowed to export table '[cgi mv_data_table]'.[/seti]
-[bounce page="__UI_BASE__/error"]
-[/if-mm]
-[/if]
-[set page_title]Individual Table Export[/set]
+[set page_title][L]Individual Table Export[/L][/set]
+[set table_perm]=x[/set]
 [set ui_class]Admin[/set]
-[set table_perm]1[/set]
 [set help_name]export.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
-[page __UI_BASE__/dbdownload]Multiple table export[/page]<BR>
+[page __UI_BASE__/dbdownload][L]Multiple table export[/L]</a><BR>
 
 [seti user_tables][loop list="[list-databases]"][if-mm function=export table="[loop-code]"][loop-code]
 [/if-mm][/loop][/seti]
@@ -25,7 +19,7 @@
 	for(@tables) {
 		#Log("table $_");
 		unless (ref $Db{$_}) {
-			Log("bad table $_");
+			Log("bad table %s", $_);
 			next;
 		}
 		$tables{$_} = [ $Db{$_}->columns() ];
@@ -169,9 +163,9 @@
 		Sorting: [value ui_sort_field]:[value ui_sort_option][/if]
 		[/quick-table]
 	[else]
-	<FONT SIZE=5 COLOR=RED>
+	<blockquote class=cerror>
 		Database export error: [data session last_error]
-	</FONT>
+	</blockquote>
 	[/else]
 	[/if]
 [/if]
@@ -182,20 +176,21 @@
 [/if]
 
 <form action="[area @@MV_PAGE@@]" method="POST" ENCTYPE="multipart/form-data">
+<input type=hidden name=mv_session_id value="[data session id]">
 <INPUT TYPE=hidden NAME=mv_action     VALUE=return>
 <INPUT TYPE=hidden NAME=ui_return_to VALUE="__UI_BASE__/genconfig">
 
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
-Table to export
+<td class=rnorm>
+[L]Table to export[/L]
 </td>
-<td bgcolor="__UI_C_INTBLOCK__">
+<td class=rnorm>
 <select name="mv_data_table" onChange="populateTable(
 			this.form.mv_data_table.options,
 			this.form.ui_sort_field.options,
@@ -210,39 +205,39 @@
 
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
-Export as<BR>
+<td class=rnorm>
+[L]Export as[/L]<BR>
 </td>
-<td bgcolor="__UI_C_INTBLOCK__">
+<td class=rnorm>
         <SELECT NAME="mv_data_export_type">
-            <OPTION VALUE=""> Current type
-            <OPTION VALUE="DEFAULT"> System default
-            <OPTION VALUE="TAB"> TAB delimited
-            <OPTION VALUE="CSV"> CSV
-            <OPTION VALUE="PIPE"> PIPE separated
+            <OPTION VALUE=""> [L]Current type[/L]
+            <OPTION VALUE="DEFAULT"> [L]System default[/L]
+            <OPTION VALUE="TAB"> [L]TAB delimited[/L]
+            <OPTION VALUE="CSV"> [L]CSV[/L]
+            <OPTION VALUE="PIPE"> [L]PIPE separated[/L]
             <OPTION VALUE="%%"> %%/%%%
-            <OPTION VALUE="LINE"> Line mode
+            <OPTION VALUE="LINE"> [L]Line mode[/L]
         </SELECT>
 </td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
-	Export to file<br>
-	<small><I>(leave empty for default file)</I></small>
+<td class=rnorm>
+	[L]Export to file[/L]<br>
+	<small><I>([L]leave empty for default file[/L])</I></small>
 </td>
-<td bgcolor="__UI_C_INTBLOCK__">
+<td class=rnorm>
  <INPUT NAME=mv_data_file SIZE=40>
 </td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
-Sort by column
+<td class=rnorm>
+[L]Sort by column[/L]
 </td>
-<td bgcolor="__UI_C_INTBLOCK__">
+<td class=rnorm>
 	<SELECT NAME=ui_sort_field>
-		<OPTION VALUE=""> unsorted
+		<OPTION VALUE=""> [L]unsorted[/L]
 		[loop list=|
 						[db-columns name="[value mv_data_table]"]
 					|]
@@ -253,28 +248,28 @@
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
-	Sort options<BR>
+<td class=rnorm>
+	[L]Sort options[/L]<BR>
 </td>
-<td bgcolor="__UI_C_INTBLOCK__">
+<td class=rnorm>
 	<SELECT NAME=ui_sort_option>
-		<OPTION VALUE=""> default (alpha)
-		<OPTION VALUE="r"> reverse
-		<OPTION VALUE="n"> numeric
-		<OPTION VALUE="rn"> reverse numeric
-		<OPTION VALUE="f"> case-insensitive
-		<OPTION VALUE="rf"> case-insensitive, reverse
+		<OPTION VALUE=""> [L]default (alpha)[/L]
+		<OPTION VALUE="r"> [L]reverse[/L]
+		<OPTION VALUE="n"> [L]numeric[/L]
+		<OPTION VALUE="rn"> [L]reverse numeric[/L]
+		<OPTION VALUE="f"> [L]case-insensitive[/L]
+		<OPTION VALUE="rf"> [L]case-insensitive[/L], [L]reverse[/L]
 	</SELECT>
 </td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" colspan=2>
+<td class=rnorm colspan=2>
 
 <center>
-<INPUT TYPE=submit NAME=mv_click VALUE="Export">
+<INPUT TYPE=submit NAME=mv_click VALUE="[L]Export[/L]">
 </center>
-[set Export]
+[set [L]Export[/L]]
 ui_export_database=1
 [/set]
 
@@ -282,7 +277,7 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.8.4.2   +71 -18    interchange/dist/lib/UI/pages/admin/flex_editor.html


rev 1.8.4.2, prev_rev 1.8.4.1
Index: flex_editor.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/flex_editor.html,v
retrieving revision 1.8.4.1
retrieving revision 1.8.4.2
diff -u -r1.8.4.1 -r1.8.4.2
--- flex_editor.html	12 Oct 2000 12:47:55 -0000	1.8.4.1
+++ flex_editor.html	25 Jan 2003 22:21:14 -0000	1.8.4.2
@@ -1,41 +1,94 @@
-[if cgi ui_return_table]
-	[calc] $CGI->{mv_data_table} = delete $CGI->{ui_return_table}; return; [/calc]
-[/if]
-[seti page_title]
+[strip interpolate=1]
+@_UI_STD_INIT_@
+[calc]
+	$CGI->{mv_data_table} = delete $CGI->{mv_return_table}
+		if $CGI->{mv_return_table};
+	return;
+[/calc]
+[tmp page_title]
+	[either]
+		[loc][cgi page_title][/loc]
+	[or]
+		[L]Table Edit[/L]: [cgi mv_data_table]
+	[/either]
+[/tmp]
+[tmp page_banner]
 	[either]
+		[cgi page_banner]
+	[or]
+		[if cgi mv_data_table ne __UI_META_TABLE__]
+		[if-mm super]
+		[L]Select for table edit[/L]:
+		 [cgi mv_data_table]
+		[if cgi ui_meta_view]
+		 (<b>[page href="__UI_BASE__/db_metaconfig"
+				 form='
+				 ui_table=[cgi mv_data_table]
+				 ui_view=[cgi ui_meta_view]
+				 start_at=extended.ui_data_fields
+		 '][cgi ui_meta_view]</b> [L]view[/L]</A>)
+		 [/if]
+		 (<b>[page href="__UI_BASE__/db_metaconfig"
+				 form='
+				 ui_table=[cgi mv_data_table]
+				 start_at=extended.ui_data_fields
+				 '][L]standard view[/L]</A>)
+		[/if-mm]
+		 [/if]
+	[or]
 		[cgi page_title]
 	[or]
-		Table Edit: [cgi mv_data_table]
+		[L]Select for table edit[/L]: [cgi mv_data_table]
 	[/either]
-[/seti]
+[/tmp]
 [seti table_perm][cgi mv_data_table]=v[/seti]
 [seti help_name][either][cgi help_name][or]flex.meta[/either][/seti]
-[seti icon_name][either][cgi icon_name][or]admin/icon_config.gif[/either][/seti]
+[seti icon_name][either][cgi icon_name][or]icon_config.gif[/either][/seti]
+[if !scratch ui_class][seti ui_class][either][cgi ui_class][or]Admin[/either][/seti][/if]
 [flag type=write table="[cgi mv_data_table]"]
 
 [if cgi ui_new_item]
-	[calc]
-		$CGI->{item_id} = q{[counter file="__UI_PRODUCT_DIR__/[cgi mv_data_table].autonumber" start=new0000]};
+	[loop list="__MV_ITEM_TABLES__"]
+		[flag type=write table="[loop-code]"]
+	[/loop]
+	[perl tables="[cgi mv_data_table]"]
+		my $db = $Db{$CGI->{mv_data_table}} or return;
+		unless ($db->config('AUTO_SEQUENCE')) {
+			$db->config('AUTO_NUMBER', '000001')
+				unless $db->config('AUTO_NUMBER');
+			$CGI->{item_id} = $db->autonumber();
+		}
+		if ($CGI->{ui_clone_id}) {
+			$CGI->{ui_clone_tables} = '__UI_CLONE_TABLES__' || '__UI_ITEM_TABLES__';
+			my $db = $Db{$CGI->{mv_data_table}} or return;
+			return unless $db->record_exists($CGI->{ui_clone_id});
+			my $ref = $db->row_hash($CGI->{ui_clone_id});
+			$CGI->{ $db->config('KEY') } = $CGI->{item_id}
+				if defined $CGI->{item_id};
+			@{$CGI}{ keys %$ref } = values %$ref;
+		}
 		return;
-	[/calc]
+	[/perl]
 [/if]
 
-@_UI_STD_DBEDIT_HEAD_@
-@_UI_STD_HEAD_@
-@_UI_STD_DBEDIT_TABLE_@
+[/strip]@_UI_STD_HEAD_@
+
+[tmp tmp_item_id][cgi item_id][/tmp]
+[table-editor cgi=1 output_map="[scratch ui_style_edit]" ui_style="[scratch ui_style_edit]"]
 
 <A HREF="[area href=admin/flex_editor
 				form='
-					item_id=[cgi item_id]
-					[return-to click]
+					item_id=[scratch tmp_item_id]
 					mv_data_table=[value mv_data_table]
 					page_title=Edit [value mv_data_table]: [cgi item_id]
 					help_name=genedit
+					ui_return_stack=1
+					ui_data_fields_all=1
 					ui_no_meta_display=1
 					ui_hide_key=1
-					icon_name=admin/icon_config.gif
-					']">No meta display</A>
+					icon_name=icon_config.gif
+					']">[L]No meta display[/L]</A>
 
 @_UI_STD_FOOTER_@
 
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Id: flex_editor.html,v 1.8.4.2 2003/01/25 22:21:14 racke Exp $ -->



1.16.4.3  +465 -205  interchange/dist/lib/UI/pages/admin/flex_select.html


rev 1.16.4.3, prev_rev 1.16.4.2
Index: flex_select.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/flex_select.html,v
retrieving revision 1.16.4.2
retrieving revision 1.16.4.3
diff -u -r1.16.4.2 -r1.16.4.3
--- flex_select.html	27 Nov 2000 01:20:30 -0000	1.16.4.2
+++ flex_select.html	25 Jan 2003 22:21:14 -0000	1.16.4.3
@@ -1,3 +1,4 @@
+
 <!-- [if cgi mv_more_ip]
 [calc]
 	for( qw/
@@ -26,32 +27,51 @@
 	[either]
 		[cgi page_title]
 	[or]
-		Select for table edit: [cgi mv_data_table]
+		[L]Select for table edit[/L]: [cgi mv_data_table]
 	[/either]
 [/tmp]
+[tmp page_secure][either]@@UI_SECURE@@[or]__UI_SECURE__[/either][/tmp]
 [tmp page_banner]
 	[either]
 		[cgi page_banner]
 	[or]
 		[cgi page_title]
 	[or]
-		[loop list="[cgi mv_data_table]"]
-		Select for table edit:
-		[page href="__UI_BASE__/flex_editor"
-				 form='
-				 mv_data_table=__UI_META_TABLE__
-				 ui_meta_view=dbconfig
-				 ui_data_fields=code name height field options help help_url display_filter
-				 ui_break_before=height display_filter
-				 page_title=Change display information: [loop-code]
-				 ui_return_to=__UI_BASE__/gentable
-				 item_id=[loop-code]
-		 '][loop-code]</A>
-		[/loop]
+		[L]Select for table edit[/L]:
+		<a href="[area
+					href="__UI_BASE__/db_metaconfig"
+					secure="[scratch page_secure]"
+					form=|
+						 ui_table=[cgi mv_data_table]
+						 start_at=height
+					|
+				]"
+				title="[cgi mv_data_table] [L]edit properties[/L], standard [L]view[/L]"
+				class=rtitle>[cgi mv_data_table]</A>
+		[if cgi ui_meta_view]
+		(<a href="[area
+					href="__UI_BASE__/db_metaconfig"
+					secure="[scratch page_secure]"
+					form=|
+						 ui_view=[cgi ui_meta_view]
+						 ui_table=[cgi mv_data_table]
+						 start_at=height
+					|
+				]"
+				title="[cgi mv_data_table] [L]edit properties[/L], [cgi ui_meta_view] [L]view[/L]"
+				class=rtitle>[cgi ui_meta_view] [L]view[/L]</A>)
+		[/if]
 	[/either]
 [/tmp]
 [tmp help_name][either][cgi help_name][or]flex.select[/either][/tmp]
-[tmp icon_name][either][cgi icon_name][or]admin/icon_config.gif[/either][/tmp]
+[tmp icon_name][either][cgi icon_name][or]icon_config.gif[/either][/tmp]
+
+[if cgi mv_return_table]
+	[calc]
+		$CGI->{mv_data_table} = delete $CGI->{mv_return_table};
+		return;
+	[/calc]
+[/if]
 
 [if cgi ui_return_table]
 	[calc]
@@ -61,59 +81,41 @@
 [/if]
 
 [if-mm function="!tables" table="[cgi mv_data_table]"]
-[bounce page="__UI_BASE__/error"]
+[tmp errorurl][area href="__UI_BASE__/error" secure="[either]@@UI_SECURE@@[or]__UI_SECURE__[/either]"][/tmp]
+[bounce href="[scratch errorurl]"]
 [/if-mm]
 
 <!-- sequence_edit: [cgi ui_sequence_edit] -->
 <!-- item_id_left: [cgi item_id_left] -->
 [perl tables="[cgi mv_data_table] __UI_META_TABLE__"]
 	delete $Scratch->{ui_location};
-	if($CGI->{ui_sequence_edit}) {
-		my $doit;
-		if($CGI->{item_id_left} =~ s/^(.*?),//) {
-			$CGI->{item_id} = $1;
-			$doit = 1;
-		}
-		elsif ($CGI->{item_id_left}) {
-			$CGI->{item_id} = delete $CGI->{item_id_left};
-			delete $CGI->{ui_sequence_edit};
-			$doit = 1;
-		}
-		else {
-			delete $CGI->{item_id};
-			delete $CGI->{ui_sequence_edit};
-		}
-		return unless $doit;
-		$Scratch->{ui_location}
-				= $Tag->area( {
-						href => '__UI_BASE__/flex_editor',
-						form => qq{
-							mv_data_table=$CGI->{mv_data_table}
-							item_id=$CGI->{item_id}
-							item_id_left=$CGI->{item_id_left}
-							ui_sequence_edit=$CGI->{ui_sequence_edit}
-							ui_return_to=__UI_BASE__/flex_select
-							ui_return_to=mv_data_table=$CGI->{mv_data_table}
-							ui_return_to=ui_sequence_edit=$CGI->{ui_sequence_edit}
-							ui_page_banner=Edit next key $CGI->{item_id}
-						},
-					});
+	$Scratch->{ui_class} = $CGI->{ui_class}
+		if $CGI->{ui_class}
+		&&  $CGI->{ui_class} =~ /^\w+$/;
+
+	my $tab = $CGI->{mv_data_table} or return;
+	if($tab =~ s/\.(txt|asc)$/_$1/) {
+		$tab =~ s:.*/::;
+	}
+	my $db = $Db{$tab};
+	if(! $db) {
+		$Scratch->{ui_error} = errmsg('no %s database', $tab);
+		$Scratch->{ui_location} = $Tag->area({href=>"__UI_BASE__/error",
+            secure=>$Scratch->{page_secure}});
 		return;
 	}
 
+	delete $Scratch->{tmp_large};
+	if( $Variable->{UI_LARGE_TABLE} =~ /\b$tab\b/ or $db->config('LARGE') ) {
+		$Scratch->{tmp_large} = 1;
+	}
+
 	return unless $CGI->{item_id};
 	return unless delete $CGI->{deleterecords};
 	return unless $Tag->if_mm('tables', '=d');
 
 	delete $Scratch->{ui_location};
 	$Config->{NoSearch} = '';
-	my $tab = $CGI->{mv_data_table} or return;
-	my $db = $Db{$tab};
-	if(! $db) {
-		$Scratch->{error_message} = "<FONT CLASS=error>Error: no <B>$tab</B> database.</FONT><BR>";
-		$Scratch->{ui_location} = "__UI_BASE__/error";
-		return;
-	}
 
 	for(grep $_, @{$CGI_array->{item_id}}) {
 		$db->delete_record($_)
@@ -121,29 +123,13 @@
 	}
 	if(@errors) {
 		my $plural = @errors > 1 ? 's' : '';
-		return "<FONT CLASS=error>Error$plural:<UL><LI>" .
+		return "<span CLASS=error>Error$plural:<UL><LI>" .
 				join ("<LI>", @errors)                    .
-				"</UL></FONT><BR>";
+				"</UL></span><BR>";
 	}
 	return;
 [/perl]
 
-[comment]
-[calc]
-	### Why was I doing this?
-	my $out = '';
-	my $page;
-	delete $Scratch->{ui_location};
-	return unless $CGI->{ui_return_to};
-	($page, @env) = split /\0/, $CGI->{ui_return_to};
-	$Scratch->{ui_location} = $Tag->area({
-									href => $page,
-									form => join "\n", @env,
-								});
-	return;
-[/calc]
-[/comment]
-
 <!-- ui_location: [scratch ui_location] -->
 [if scratch ui_location]
 [bounce href=`delete $Scratch->{ui_location}`]
@@ -155,10 +141,9 @@
 @_UI_STD_HEAD_@
 [update values]
 <!-- ----- BEGIN REAL STUFF ----- -->
-<FORM ACTION="[area @@MV_PAGE@@]" METHOD=post>
-<table>
-<tr>
-<td>
+
+[if !scratch tmp_large]
+	[tmp extra_title]
 		[loop list="[cgi mv_data_table]"]
 		 	[if-loop-data __UI_META_TABLE__ name]
 		 	<B>[loop-data __UI_META_TABLE__ name]</B>
@@ -167,159 +152,382 @@
 		 	&nbsp;&nbsp;&nbsp;<small><A HREF="[loop-data __UI_META_TABLE__ help_url]">help</A></small>
 			[/if-loop-data]
 		 	[if-loop-data __UI_META_TABLE__ help]
-		 	<BR><i>[loop-data __UI_META_TABLE__ name]</i>
+		 	<i>[loop-data __UI_META_TABLE__ name]</i>
 			[/if-loop-data]
 		[/loop]
-</td>
-<td>
-<input NAME=ui_text_qualification size=16> <INPUT TYPE=submit VALUE="Limit with search">
-</td>
-</tr>
-</table>
+	[/tmp]
+	[calc]
+		$Scratch->{page_title} .= $Scratch->{extra_title};
+		return;
+	[/calc]
+
+[output name=search_box]
+<FORM ACTION="[area href="[either][cgi ui_searchpage][or]@@MV_PAGE@@[/either]"]" METHOD=GET>
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
+<INPUT TYPE=hidden NAME=mv_data_table    VALUE="[cgi mv_data_table]">
+<INPUT TYPE=hidden NAME=mv_action        VALUE=back>
+<INPUT TYPE=hidden NAME=ui_show_fields VALUE="[cgi ui_show_fields]">
+<span class=s3>[L]Limit with search[/L]:</span> <input NAME=ui_text_qualification size=16 class=s2> 
+</FORM>
+[output]
+[/if]
+
 [if scratch ui_failure]
-<P>
-<BLOCKQUOTE>
-<FONT COLOR="__CONTRAST__">[scratch ui_failure][set ui_failure][/set]</FONT>
-</BLOCKQUOTE>
-<P>
-&nbsp;
+<blockquote class=cerror>
+	[scratchd ui_failure]
+</blockquote>
 [/if]
+
 [if scratch ui_message]
-<P>
-<BLOCKQUOTE>
-<FONT COLOR="__CONTRAST__">[scratch ui_message][set ui_message][/set]</FONT>
-</BLOCKQUOTE>
-<P>
-&nbsp;
+	<blockquote class=cmessage>
+		[scratchd ui_message]
+	</blockquote>
 [/if]
 
+[if-mm !super]
+[tmp ui_owner][db-hash
+				table="__UI_ACCESS_TABLE__"
+				column="table_control::[cgi mv_data_table]::owner_field"
+				key="[data session username]"][/tmp]
+[/if-mm]
+
+[set tmp_nomatch_message]<B>[L]No records[/L].</b>[/set]
+[set tmp_like_spec][/set]
 [perl tables="[cgi mv_data_table] __UI_META_TABLE__"]
-	my $ref = $Db{$CGI->{mv_data_table}};
-	my $mref = $Db{__UI_META_TABLE__};
+	my $tab = $CGI->{mv_data_table};
+	my $ref = $Db{$tab};
+	my $meta = $Tag->meta_record($CGI->{mv_data_table}, $CGI->{ui_meta_view});
 	
 	if (! $ref) {
 		$Scratch->{keypos} = 0;
 		return;
 	}
-	elsif (! $mref) {
+	elsif (! $meta) {
 		$Scratch->{keypos} = 0;
 	}
 
-	my $meta;
-	if($mref and $mref->record_exists($CGI->{mv_data_table}) ) {
-		$meta = $mref->row_hash($CGI->{mv_data_table});
-	}
-	else {
-		$meta = {};
+	if( $tab ne $ref->config('name')) {
+		## Probably transient database
+		$CGI->{mv_data_table_real} = $tab = $ref->config('name');
 	}
+
+	$meta ||= {};
+
 	if($CGI->{ui_flex_key}) {
 		$Scratch->{keypos} = $CGI->{ui_flex_key};
 	}
 	else {
-		$Scratch->{keyname} = $ref->config('KEY');
 		$Scratch->{keypos} = $ref->config('KEY_INDEX');
 	}
+	$Scratch->{keyname} = $ref->config('KEY');
 
+	$CGI->{ui_show_fields} ||= $meta->{ui_show_fields} || $meta->{field};
+	$CGI->{ui_meta_specific} ||= $meta->{ui_meta_specific};
 	$Config->{NoSearch} = '';
 	$ui_text_qualification = $CGI->{ui_text_qualification};
-	if ($ui_text_qualification and $CGI->{ui_text_qualification} =~ /=/ ) {
-		my ($f, $s) = split /\s*=\s*/, $CGI->{ui_text_qualification} , 2;
-		$CGI->{ui_text_qualification} = "co=1\nop=eq\nse=$s\nsf=$f";
+	if ($ui_text_qualification and $CGI->{ui_text_qualification} =~ /[<!=>\^]/ ) {
+		if($Scratch->{ui_owner}) {
+			$CGI->{ui_text_qualification} = <<EOF;
+co=1
+st=db
+sf=$Scratch->{ui_owner}
+se=$Session->{username}
+op=eq
+nu=0
+os=0
+su=0
+bs=0
+EOF
+		}
+		else {
+			$CGI->{ui_text_qualification} = "co=1\n";
+		}
+
+		my @entries = split /\s+(and|or)\s+/i,  $ui_text_qualification;
+		my $or;
+		for(@entries) {
+			if(/^or$/i) {
+				$or = 1;
+				$CGI->{ui_text_qualification} .= "os=1\n";
+				next;
+			}
+			elsif(/^and$/i) {
+				$or = 0;
+				$CGI->{ui_text_qualification} .= "os=0\n";
+				next;
+			}
+			my ($f, $op, $s) = split /\s*([<=!>\^]+)\s*/, $_, 2;
+			$op = "eq" if $op eq "==";
+			$op = "rm" if $op eq "=";
+			if($op eq '^') {
+				$op = 'rm';
+				$CGI->{ui_text_qualification} .= "bs=1\nsu=1\n";
+			}
+			else {
+				$CGI->{ui_text_qualification} .= "bs=0\nsu=0\n";
+			}
+			if(length($s) > 1) {
+				$CGI->{ui_text_qualification} .= "se=$s\nsf=$f\nop=$op\n";
+			}
+			else {
+				$CGI->{ui_text_qualification} .= "se=.\nsf=$f\nop=rn\n";
+			}
+			if($op =~ /[<>]/ and $s =~ /^[\d.]+$/) {
+				$CGI->{ui_text_qualification} .= "nu=1\n";
+			}
+			else {
+				$CGI->{ui_text_qualification} .= "nu=0\n";
+			}
+		}
+		if(defined $or) {
+			$CGI->{ui_text_qualification} .= $or ? "os=1\n" : "os=0\n";
+		}
+
+		$out_message = errmsg('Entries matching "%s"', $ui_text_qualification);
 	}
 	elsif ($ui_text_qualification) {
 		$CGI->{ui_text_qualification} = "se=$CGI->{ui_text_qualification}";
+		$out_message = errmsg('Entries matching "%s"', $ui_text_qualification);
+		if($Scratch->{ui_owner}) {
+			$CGI->{ui_text_qualification} = <<EOF;
+co=1
+sf=$Scratch->{ui_owner}
+se=$Session->{username}
+op=eq
+sf=:*
+se=$CGI->{ui_text_qualification}
+EOF
+		}
+	}
+	elsif ( $CGI->{mv_like_field} ) {
+		my @f = split /\0/, $CGI->{mv_like_field};
+		my @s = split /\0/, $CGI->{mv_like_spec};
+		my @q = 'ra=yes';
+		my $found;
+		for(my $i = 0; $i < @f; $i++) {
+			next unless length $s[$i];
+			$found++;
+			push @q, "lf=$f[$i]";
+			push @q, "ls=$s[$i]";
+		}
+		if($found) { $CGI->{ui_text_qualification} = join "\n", @q; }
+		else	   { $CGI->{ui_text_qualification} = "" }
+	}
+	elsif($Scratch->{ui_owner}) {
+		$CGI->{ui_text_qualification} = <<EOF;
+co=1
+sf=$Scratch->{ui_owner}
+se=$Session->{username}
+op=eq
+EOF
+	}
+	elsif ($Scratch->{tmp_large}) {
+#Debug("It is large.");
+		my $keylabel = $Tag->display({
+							table => $tab,
+							name => 'item_id',
+							column => $Scratch->{keyname},
+							template => 1,
+						});
+		my $url = $Tag->area( { href => '__UI_BASE__/flex_editor' } );
+		$Scratch->{'[L]Edit[/L]'} = <<EOF;
+	mv_nextpage=__UI_BASE__/flex_editor
+	mv_todo=return
+	item_id=[cgi goto_id]
+EOF
+		$Scratch->{tmp_nomatch_message} = <<EOF;
+Record to edit: <INPUT TYPE=text NAME=goto_id> <INPUT NAME=mv_click TYPE=submit VALUE="[L]Edit[/L]">
+EOF
+		$Scratch->{tmp_like_spec} = 1;
+		$CGI->{ui_text_qualification} = "";
 	}
 	else {
 		$CGI->{ui_text_qualification} = "ra=yes";
 	}
-	$CGI->{ui_sort_field} = $meta->{lookup} || $Scratch->{keyname}
-		if ! $CGI->{ui_sort_field};
+
+	if($meta->{ui_sort_combined} =~ /\S/) {
+		$meta->{ui_sort_field} = $meta->{ui_sort_combined};
+		$meta->{ui_sort_option} = '';
+	}
+
+	$CGI->{ui_sort_field}	||= $meta->{ui_sort_field}
+							||  $meta->{lookup}
+							||  $Scratch->{keyname};
+	$CGI->{ui_sort_option}	||= $meta->{ui_sort_option};
+	$CGI->{ui_sort_option}	=~ s/[\0,\s]+//g;
 	$CGI->{ui_list_size} = $meta->{height}
 		if ! $CGI->{ui_list_size};
-	if(! ($CGI->{ui_show_fields} = $meta->{field}) ) {
-		$CGI->{ui_show_fields} = '*';
-		$CGI->{ui_description_fields} = join ",", $ref->columns();
+
+	if(! $CGI->{ui_show_fields} ) {
+		$CGI->{ui_show_fields} = 
+			$CGI->{ui_description_fields}
+				= join ",", $ref->columns();
 	}
 	else {
-		$CGI->{ui_show_fields} =~ s/[\0,\s]+/,/g;
-		$CGI->{ui_description_fields} = $CGI->{ui_show_fields};
+		my $i = 0;
+		my $show = $CGI->{ui_show_fields};
+		$show =~ s/(\w+)(?:\((.*?)\))?/ ($filter_show[$i++] = $2), $1/eg;
+#Log("filter_show: " . $Tag->uneval( { ref => \@filter_show } ));
+		$show =~ s/[\0,\s]+/,/g;
+		$CGI->{ui_description_fields} = $show;
+	}
+
+	@cols = grep $ref->column_exists($_), 
+				split /,/, $CGI->{ui_description_fields};
+
+	my %limit_field;
+
+	$CGI->{ui_limit_fields} =~ s/[\0,\s]+/ /g;
+	$CGI->{ui_limit_fields} =~ s/^\s+//;
+	$CGI->{ui_limit_fields} =~ s/\s+$//;
+
+	my (@limit_field) = split " ", $CGI->{ui_limit_fields};
+
+#Log("show_field: " . $Tag->uneval( { ref => \@cols } ));
+#Log("cols ary:   " . $Tag->uneval( { ref => \@cols } ));
+#Log("limit_fields ary: " . $Tag->uneval( { ref => \@limit_field } ));
+	if(@limit_field) {
+#Log("limit_fields ary: " . $Tag->uneval( { ref => \@limit_field } ));
+		@limit_field{@limit_field} = ();
+#Log("limit_fields: " . $Tag->uneval( { ref => \%limit_field } ));
+		@cols = grep ! exists($limit_field{$_}), @cols;
+#Log("cols ary:   " . $Tag->uneval( { ref => \@cols } ));
 	}
-	@cols = split /[\s,\0]+/, $CGI->{ui_description_fields};
+
+	unshift(@cols, $Scratch->{keyname})
+		if $cols[0] ne $Scratch->{keyname};
+
 	for(@cols) {
 		$numeric{$_} = 1 if $ref->numeric($_);
 	}
 
+	$CGI->{ui_description_fields} = join ",", @cols;
+
+	unless ($CGI->{ui_sort_option}) { 
+		 $CGI->{ui_sort_option} = 'n'
+				if $ref->numeric($CGI->{ui_sort_field}); 
+	} 
+
+	my $fi = $CGI->{mv_data_table_real} || $CGI->{mv_data_table};
+	$Scratch->{sparams} = $Scratch->{tmp_like_spec} ? '' : <<EOF;
+
+	fi=$fi
+	st=db
+	$CGI->{ui_text_qualification}
+	su=1
+	md=1
+	ml=$CGI->{ui_list_size}
+	tf=$CGI->{ui_sort_field}
+	to=$CGI->{ui_sort_option}
+	rf=$CGI->{ui_description_fields}
+
+EOF
+	$Scratch->{page_banner} .= $out_message;
+	$Scratch->{page_title} .= $out_message;
 	return;
 [/perl]
+</FORM>
 
-[if cgi ui_show_fields]
-	[tmp sparams]
-			fi=[cgi mv_data_table]
-			st=db
-			[cgi ui_text_qualification]
-			su=1
-			md=1
-			ml=[cgi ui_list_size]
-			tf=[cgi ui_sort_field]
-			to=[cgi ui_sort_option]
-			rf=[cgi ui_show_fields]
-	[/tmp]
-[else]
-	[tmp sparams]
-		fi=[cgi mv_data_table]
-		st=db
-		[cgi ui_text_qualification]
-		md=1
-		tf=[scratch keypos]
-		rf=[scratch keypos]
-	[/tmp]
-[/else]
-[/if]
-
-<INPUT TYPE=hidden NAME=mv_data_table    VALUE="[cgi mv_data_table]">
-<INPUT TYPE=hidden NAME=ui_page_title    VALUE="[cgi ui_page_title]">
-<INPUT TYPE=hidden NAME=ui_page_title    VALUE="[cgi ui_page_banner]">
-<INPUT TYPE=hidden NAME=ui_meta_specific VALUE="[cgi ui_meta_specific]">
-<INPUT TYPE=hidden NAME=ui_return_to     VALUE="@@MV_PAGE@@">
-<INPUT TYPE=hidden NAME=ui_return_to     VALUE="mv_data_table=[cgi mv_data_table]">
-<INPUT TYPE=hidden NAME=ui_return_to     VALUE="ui_sequence_edit=1">
-<INPUT TYPE=hidden NAME=mv_action        VALUE=back>
-<TABLE CELLSPACING=1 cellmargin=3>
-<TR BGCOLOR="__UI_C_TITLEBARBG__">
-[loop list="[cgi ui_description_fields]"]
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">
-	[loop-change 1][condition]1[/condition]&nbsp;&nbsp;&nbsp;&nbsp;[/loop-change 1]
-	<A HREF="[area href='@@MV_PAGE@@'
-					form=`
-						my $f = '[loop-code]';
-						my $o = '';
-						$o .= 'r'
-							if $CGI->{ui_sort_field} eq $f
-									and
-								$CGI->{ui_sort_option} !~ /r/;
-						$o .= 'n' if $numeric{$f};
-						return qq(
-							ui_text_qualification=$ui_text_qualification
-							mv_data_table=$CGI->{mv_data_table}
-							ui_sort_field=$f
-							ui_sort_option=$o
-						);
-					`
-				]">[loop-code]</TH>
-[/loop]
-</tr>
-[search-region more=1 arg="[scratch sparams]"]
-[search-list]
-<TR [item-alternate 2]BGCOLOR="__UI_T_ROW_EVEN__"[else]BGCOLOR="__UI_T_ROW_ODD__"[/else][/item-alternate]>
-
-<TD><INPUT TYPE=checkbox NAME=item_id VALUE="[item-code]">&nbsp;&nbsp;[page href=__UI_BASE__/flex_editor form=|
-									mv_data_table=[cgi mv_data_table]
-									ui_page_title=[cgi ui_page_title]
-									ui_page_title=[cgi ui_page_banner]
-									ui_meta_specific=[cgi ui_meta_specific]
-									ui_return_to=@@MV_PAGE@@
-									ui_return_to=mv_data_table=[cgi mv_data_table]
-									item_id=[item-code]
+[tmpn tmp_ncols][/tmpn]
+<!-- tq: [scratch sparams] -->
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+	<FORM ACTION="[area href="[either][cgi ui_searchpage][or]@@MV_PAGE@@[/either]"]" METHOD=GET>
+	<INPUT TYPE=hidden NAME=mv_data_table    VALUE="[cgi mv_data_table]">
+	[if cgi ui_meta_view]
+	[return-to]
+	<!-- got a return-to -->
+	[else]
+	<!-- got no return-to -->
+	<INPUT TYPE=hidden NAME=ui_meta_specific VALUE="[cgi ui_meta_specific]">
+	<INPUT TYPE=hidden NAME=ui_page_title    VALUE="[cgi ui_page_title]">
+	<INPUT TYPE=hidden NAME=ui_page_banner   VALUE="[cgi ui_page_banner]">
+	<INPUT TYPE=hidden NAME=ui_limit_fields VALUE="[cgi ui_limit_fields]">
+	<INPUT TYPE=hidden NAME=ui_show_fields VALUE="[cgi ui_show_fields]">
+	<INPUT TYPE=hidden NAME=ui_return_to     VALUE="@@MV_PAGE@@">
+	<INPUT TYPE=hidden NAME=ui_return_to     VALUE="mv_data_table=[cgi mv_data_table]">
+	<INPUT TYPE=hidden NAME=ui_return_to     VALUE="ui_sequence_edit=1">
+	[/else]
+	[/if]
+	<INPUT TYPE=hidden NAME=mv_action        VALUE=back>
+	<tr class=rhead>
+	<td class=rhead>&nbsp;</td>
+	[loop list="[cgi ui_description_fields]"]
+	<td class=rhead>
+    <table align="left" class=rhead cellspacing=2 cellpadding=0>
+    <tr>
+      <td align="right" valign="center">
+		<A HREF="[area href='__UI_BASE__/flex_group'
+						form='
+							mv_data_table=[cgi mv_data_table]
+							ui_meta_view=[cgi ui_meta_view]
+							mv_arg=[loop-code]
+						'
+					]"
+			title="[msg arg.0='[loop-code]']Select group by %s[/msg]"
+				><img src="smindex.gif" border=0></a>
+      </td>
+      <td align="left" valign="center" class=rhead>
+	  [calc]
+			my $f = '[loop-code]';
+			my $o = '';
+			my $msg;
+			my $rmsg;
+			if ($CGI->{ui_sort_field} eq $f and $CGI->{ui_sort_option} !~ /r/) {
+				$o .= 'r';
+				$msg = "sort by %s (%s)";
+				$rmsg = errmsg('reverse');
+			}
+			else {
+				$msg = "sort by %s";
+			}
+			$o .= 'n' if $numeric{$f};
+			$Scratch->{tmp_sort_msg} = errmsg($msg, $f, $rmsg);
+			$Scratch->{tmp_url} = $Tag->area( {
+											href => '@@MV_PAGE@@',
+											form => qq(
+									ui_text_qualification=$ui_text_qualification
+									mv_data_table=$CGI->{mv_data_table}
+									ui_meta_view=$CGI->{ui_meta_view}
+									ui_sort_field=$f
+									ui_sort_option=$o
+											),
+											});
+			return;
+		[/calc]
+		<a href="[scratch tmp_url]"
+			class=rhead
+			title="[scratch tmp_sort_msg]">[either][data table="__UI_META_TABLE__" column=label key="[cgi mv_data_table]::[loop-code]"][or][loop-code][/either]</A>
+      </td>
+    </tr>
+    </table>	
+	</td>
+	[/loop]
+	</tr>
+	[tmp tmp_url]
+		mv_data_table=[cgi mv_data_table]
+		ui_page_title=[cgi ui_page_title]
+		ui_meta_view=[cgi ui_meta_view]
+		ui_page_banner=[cgi ui_page_banner]
+		ui_meta_specific=[cgi ui_meta_specific]
+		[if cgi ui_return_to]
+		[and !cgi ui_return_stack]
+			[return-to formlink]
+		[else]
+			ui_return_to=@@MV_PAGE@@
+		[/else]
+		[/if][/tmp]
+	[search-region more=1
+		form="
+			ui_meta_specific=[cgi ui_meta_specific]
+			ui_meta_view=[cgi ui_meta_view]
+		" arg="[scratch sparams]"]
+	[search-list]
+	<tr [item-alternate 2]class=rownorm[else]class=rowalt[/else][/item-alternate]>
+
+	<td width="30"><INPUT TYPE=checkbox NAME=item_id VALUE="[item-code]"></td>
+	<td>[page href=__UI_BASE__/flex_editor form=|
+								[scratch tmp_url]
+							item_id=[item-code]
 						|][item-code]</A></TD>
 [item-sub show_line]
 sub {
@@ -328,9 +536,20 @@
 	return unless $line;
 	shift (@$line);
 	my $out = '';
+	my $i = 1;
 	for(@$line) {
+		my $filter = $filter_show[$i] || '';
+		$filter .= ' encode_entities' unless $filter =~ /\b(?:encode_)?entities\b/;
+
+		my $extra = '';
+		$extra .= " $1" while $filter =~ s/(v?align=\w+)//i;
+
+#Log("$i filter = $filter");
+
+		$_ = $Tag->filter($filter, $_);
 		s/\[/&#91;/g;
-		$out .= "<TD>" . $Tag->filter('entities', $_) . "</TD>";
+		$out .= "<TD$extra>$_</TD>";
+		$i++;
 	}
 	return $out . "\n";
 }
@@ -340,49 +559,90 @@
 [/search-list]
 [no-match]
 <tr>
-<td colspan=6 align=center>
-<B>Nothing matched.</B>
+<td colspan="[scratch tmp_ncols]" align=left>
+[scratchd tmp_nomatch_message]
 </td>
 </tr>
+[if scratch tmp_like_spec]
+	<tr>
+	<td colspan="[scratch tmp_ncols]" align=left>
+	[L]Or enter a query by example to select a set of records.[/L]
+	[L]Each input will match on the <i>beginning</i> text in the field.[/L]
+	</td>
+	</tr>
+	[loop list="[cgi ui_description_fields]"]
+	<TD>
+		<input type=hidden name=mv_like_field value="[loop-code]">
+		<input type=text name=mv_like_spec size=10>
+	</td>
+	[/loop]
+	<tr>
+	<td colspan="[scratch tmp_ncols]" align=left>
+	<input type=submit value="[L]Find[/L]">
+	</td>
+	</tr>
+[/if]
 [/no-match]
 [more-list]
 <tr>
 <td colspan=6 align=center>
-More rows: [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
+[L]More rows[/L]: [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
 </td>
 </tr>
 [/more-list]
 </table>
 
-[button text="Edit checked records in sequence"]
-ui_sequence_edit=[calc]
-	$CGI->{item_id_left} = $CGI->{item_id};
-	$CGI->{item_id_left} =~ s/\0+/,/g;
-	if($CGI->{item_id_left} =~ s/^(.*?),//) {
-		$CGI->{item_id} = $1;
-		return 1;
-	}
-	else {
-		delete $CGI->{item_id_left};
-		return '';
-	}
-[/calc]
+[on-match]
+[if !cgi ui_meta_view]
+
+[output name=top_buttons]
+[button text="[L]Edit checked records in sequence[/L]" extra=" class=s2"]
+ui_sequence_edit=1
+mv_nextpage=__UI_BASE__/flex_editor
+mv_todo=return
+[/button]
+
+[output name=bottom_buttons]
+[button text="[L]Edit checked records in sequence[/L]" extra=" class=s2"]
+ui_sequence_edit=1
 mv_nextpage=__UI_BASE__/flex_editor
 mv_todo=return
 [/button]
 
+[output]
+[/if]
+
+[if-mm function="tables" table="[cgi mv_data_table]=d"]
+
+[output name=top_buttons]
 &nbsp;&nbsp;&nbsp;&nbsp;
+[button text="[L]Delete checked records[/L]"
+		extra="class=s2"
+		confirm="[L]Are you sure you want to delete the checked records?[/L]"]
+[flag type=write table="[cgi mv_data_table]"]
+deleterecords=1
+mv_click=db_maintenance
+[/button]
 
-[button text="Delete checked records"
-		confirm="Are you sure you want to delete the checked records?"]
+[output name=bottom_buttons]
+&nbsp;&nbsp;&nbsp;&nbsp;
+[button text="[L]Delete checked records[/L]"
+		extra="class=s2"
+		confirm="[L]Are you sure you want to delete the checked records?[/L]"]
 [flag type=write table="[cgi mv_data_table]"]
 deleterecords=1
-mv_todo=back
-mv_nextpage=@@MV_PAGE@@
+mv_click=db_maintenance
 [/button]
+[output]
+
+[/if-mm]
+
+[/on-match]
 </FORM>
 [/search-region]
 <!-- ----- END REAL STUFF ----- -->
 
+[update values]
+
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ Revision: $Id: flex_select.html,v 1.16.4.3 2003/01/25 22:21:14 racke Exp $ -->



1.1.4.1   +1 -0      interchange/dist/lib/UI/pages/admin/fr_index.html


rev 1.1.4.1, prev_rev 1.1
Index: fr_index.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/fr_index.html,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- fr_index.html	19 Aug 2000 15:54:04 -0000	1.1
+++ fr_index.html	25 Jan 2003 22:21:14 -0000	1.1.4.1
@@ -1,3 +1,4 @@
+@_UI_STD_INIT_@
 <html>
 [if !session logged_in]
 [bounce page="__UI_BASE__/login"]



1.15.4.6  +407 -90   interchange/dist/lib/UI/pages/admin/genconfig.html


rev 1.15.4.6, prev_rev 1.15.4.5
Index: genconfig.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/genconfig.html,v
retrieving revision 1.15.4.5
retrieving revision 1.15.4.6
diff -u -r1.15.4.5 -r1.15.4.6
--- genconfig.html	15 Apr 2001 13:39:57 -0000	1.15.4.5
+++ genconfig.html	25 Jan 2003 22:21:14 -0000	1.15.4.6
@@ -1,143 +1,426 @@
 [tmp page_perm]files[/tmp]
-[tmp page_title]Administration: [calc]$Config->{CatalogName}[/calc][/tmp]
+[tmp page_title][L]Administration[/L]: [calc]$Config->{CatalogName}[/calc][/tmp]
 [set ui_class]Admin[/set]
 [tmp help_name]genconfig.main[/tmp]
-[tmp icon_name]admin/icon_config.gif[/tmp]
+[tmp icon_name]icon_config.gif[/tmp]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
-<center>
-<table __UI_T_PROPERTIES__>
+<div style="margin-left: 5%">
+
+[if !scratch ui_old_browser]
+[tabbed-display
+	ui-style=1
+	panel-prepend="<table cellpadding=3 cellspacing=0>"
+	panel-append="</table>"
+	start-at-index="[cgi start_at_index]"
+	panel-shade=f
+	panel-width="[either][cgi panel_width][or]800[/either]"
+	panel-height="[either][cgi panel_height][or]500[/either]"
+	tab-width=160]
+[tabbed-panel [L]Catalog Information[/L]]
+
+<TR>
+	<td class=rhead>
+	[L]Catalog URL[/L]
+	</th>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[calc]$url=$Scratch->{ui_catalog_url};$url=~s%/index[^/]*%%;return qq{<A HREF="$url">$url}[/calc]</A></TD>
+</TR>
 
-<tr><td align=left bgcolor=__UI_C_INTBLOCK__>
-<TABLE border=0>
 <TR>
-  <TD BGCOLOR=__UI_C_TOPBLOCKBAR__ COLSPAN=3><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1><CENTER>Catalog Information</CENTER></TD>
+	<td class=rhead>
+	[L]Secure URL[/L]
+	</td>
+	<TD class=clabel>&nbsp; &nbsp;</TD>
+	<TD class=cdata>[calc]return qq{<A HREF="$Config->{SecureURL}">$Config->{SecureURL}}[/calc]</A></TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Catalog URL
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[calc]return qq{<A HREF="$Config->{VendURL}">$Config->{VendURL}}[/calc]</A></TD>
+	<td class=rhead>
+	[L]Location of Error Logs[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>
+		[L]Global[/L]: [version extended=1 global_error=1]<br>
+		[L]Local[/L]: [version extended=1 local_error=1]
+	</TD>
 </TR>
 
+
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Secure URL
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[calc]return qq{<A HREF="$Config->{SecureURL}">$Config->{SecureURL}}[/calc]</A></TD>
+	<td class=rhead>
+	[L]Active sessions[/L]
+	[if cgi list_sessions]<br><i>
+	([L]last[/L]
+	[calc] int (
+					$::Variable->{ACTIVE_SESSION_MINUTES}
+					|| ( ($Config->{SessionExpire} || 60) / 60)
+				)
+				 [/calc] [L]minutes[/L])</I>
+	[/if]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>
+	[if cgi list_sessions]
+		[loop list="[dump-session find=1]"]
+				<A HREF="[area
+								href='__UI_BASE__/show_session'
+								form='show_session=[loop-code]'
+					]"
+					>[loop-code]</A> &nbsp;
+				(<A HREF="[area
+								href='__UI_BASE__/show_session'
+								form='show_session=[loop-code]'
+					]"
+					TARGET="_blank"
+					>in new window</A>)<BR>
+			[/loop]
+		 
+	[else]
+		[page href="@@MV_PAGE@@" form="list_sessions=1"][L]Show active sessions[/L]</A>
+		<br>
+		<i>([L]last[/L]
+		[calc] int (
+					$::Variable->{ACTIVE_SESSION_MINUTES}
+					|| ( ($Config->{SessionExpire} || 60) / 60)
+				)
+				 [/calc] [L]minutes[/L])</I>
+
+	[/else]
+	[/if]
+	[if cgi show_session]
+		<P><B>[L]Showing session[/L]: [cgi show_session]</B>
+<XMP style="font-size: small">
+[dump-session name="[cgi show_session]"]
+</XMP>
+	[/if]
+	</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Location of Error Logs
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>
-		Global: [version extended=1 global_error=1]<br>
-		Local: [version extended=1 local_error=1]
+	<td class=rhead>
+	[L]Last order number[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>
+		[calc]
+			my $cfn = $Variable->{MV_ORDER_COUNTER_FILE} || 'etc/order.number';
+			$Values->{new_order_number} = $Tag->file($cfn);
+			$Values->{new_order_number} =~ s/.*\n([A-Za-z0-9]+).*$/$1/s;
+			return;
+		[/calc]
+		[page __UI_BASE__/misc_order_number][value new_order_number]</A>
+	</TD>
+</TR>
+
+[/tabbed-panel]
+[tabbed-panel[L]Interchange Server Information[/L]]
+
+<TR>
+	<td class=rhead>
+	[L]Interchange version[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Server hostname[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 hostname=1]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Interchange PID[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 pid=1]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Interchange SUID User[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 uid=1]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Server mode[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 mode=1]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Last time server restarted[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[calc] scalar localtime([file-info conf=1 name="interchange.pid" time=1])[/calc]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Last time changes applied[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[file name=`"etc/status.$Config->{CatalogName}"`] ([page __UI_BASE__/reconfig @@MV_PAGE@@][L]apply now[/L]</A>)</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[msg arg.0='<A HREF="[area __UI_BASE__/env_vars]">' arg.1="</A>"]%sEnvironment%s variables passed[/msg]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 env=1]</TD>
+</TR>
+
+[/tabbed-panel]
+[tabbed-panel [L]Perl Information[/L]]
+
+<TR>
+	<td class=rhead>
+	<A HREF="[area href="@@MV_PAGE@@"
+		form="
+			more_perl=1
+			start_at_index=2
+			panel_width=1000
+			panel_height=800
+		"]">[L]Perl Version[/L]</A>
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>Perl [version extended=1 perl=1 perl_config="[cgi more_perl]"]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Optional Module Information[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>
+		<table>
+		[table-organize columns=2 columnize=1 td='width="50%"']
+		<td>[version extended=1 modules=1 joiner="</td><td>"]</TD>
+		[/table-organize]
+		</table>
+	</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Safe operations untrapped[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 safe=1]</TD>
+</TR>
+
+<TR>
+  <TD COLSPAN=3>&nbsp;</TD>
+</TR>
+
+[/tabbed-panel]
+[tabbed-panel [L]Database Information[/L]]
+
+<TR>
+	<td class=rhead>
+	[L]Database Interfaces[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>
+		[version extended=1 db=1]
+	</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Database Tables[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>	
+		<table width="400">
+		[table-organize cols=3 columnize=1]
+			[loop list="[list-databases]"]
+		<TD>
+				<A HREF="[area href=admin/dbinfo form='mv_data_table=[loop-code]']">[loop-code]</A><br>
 		</TD>
+			[/loop]
+		[/table-organize]
+		</table>
+	</TD>
 </TR>
+[/tabbed-panel]
+[/tabbed-display]
 
+[/if]
 
+[if scratch ui_old_browser]
+<table>
+<tr><td align=left class=rnorm>
+<TABLE __UI_T_PROPERTIES__>
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Active sessions
+  <TD class=rmarq COLSPAN=3 align=center>[L]Catalog Information[/L]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Catalog URL[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[calc]$url=$Scratch->{ui_catalog_url};$url=~s%/index[^/]*%%;return qq{<A HREF="$url">$url}[/calc]</A></TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Secure URL[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[calc]return qq{<A HREF="$Config->{SecureURL}">$Config->{SecureURL}}[/calc]</A></TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Location of Error Logs[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>
+		[L]Global[/L]: [version extended=1 global_error=1]<br>
+		[L]Local[/L]: [version extended=1 local_error=1]
+	</TD>
+</TR>
+
+
+<TR>
+	<td class=rhead>
+	[L]Active sessions[/L]
 	[if cgi list_sessions]<br><small><i>
-	(last
+	([L]last[/L]
 	[calc] int (
 					$::Variable->{ACTIVE_SESSION_MINUTES}
 					|| ( ($Config->{SessionExpire} || 60) / 60)
 				)
-				 [/calc] minutes)</I></small>
+				 [/calc] [L]minutes[/L])</I></small>
 	[/if]
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[if cgi list_sessions][loop list="[dump-session find=1]"]<A HREF="[area
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[if cgi list_sessions][loop list="[dump-session find=1]"]<A HREF="[area
 														href='@@MV_PAGE@@'
 														form='show_session=[loop-code]'
 														]">[loop-code]</A><BR>[/loop]
 	[else]
-		[page href="@@MV_PAGE@@" form="list_sessions=1"]Show active sessions</A>
+		[page href="@@MV_PAGE@@" form="list_sessions=1"][L]Show active sessions[/L]</A>
 		<br>
-		<small><i>(last
+		<small><i>([L]last[/L]
 		[calc] int (
 					$::Variable->{ACTIVE_SESSION_MINUTES}
 					|| ( ($Config->{SessionExpire} || 60) / 60)
 				)
-				 [/calc] minutes)</I></small>
+				 [/calc] [L]minutes[/L])</I></small>
 
 	[/else]
 	[/if]
 	[if cgi show_session]
-		<P><B>Showing session: [cgi show_session]</B>
-		<FONT SIZE=-1>
-<PRE>
+		<P><B>[L]Showing session[/L]: [cgi show_session]</B>
+<XMP style="font-size: small">
 [dump-session name="[cgi show_session]"]
-</PRE>
-		</FONT>
+</XMP>
 	[/if]
-		</TD>
+	</TD>
 </TR>
 
 <TR>
+	<td class=rhead>
+	[L]Last order number[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>
+		[calc]
+			my $cfn = $Variable->{MV_ORDER_COUNTER_FILE} || 'etc/order.number';
+			$Values->{new_order_number} = $Tag->file($cfn);
+			$Values->{new_order_number} =~ s/.*\n([A-Za-z0-9]+).*$/$1/s;
+			return;
+		[/calc]
+		[page __UI_BASE__/misc_order_number][value new_order_number]</A>
+	</TD>
+</TR>
+
+
+<TR>
   <TD COLSPAN=3>&nbsp;</TD>
 </TR>
 
 <TR>
-  <TD BGCOLOR=__UI_C_TOPBLOCKBAR__ COLSPAN=3><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1><CENTER>Interchange Server Information</CENTER></TD>
+  <TD class=rmarq COLSPAN=3 align=center>[L]Interchange Server Information[/L]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Interchange version
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD> [version]</A></TD>
+	<td class=rhead>
+	[L]Interchange version[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Interchange PID
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[version extended=1 pid=1]</TD>
+	<td class=rhead>
+	[L]Server hostname[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 hostname=1]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Interchange SUID User
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[version extended=1 uid=1]</TD>
+	<td class=rhead>
+	[L]Interchange PID[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 pid=1]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Last time server restarted
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[calc] scalar localtime([file-info conf=1 name="interchange.pid" time=1])[/calc]</TD>
+	<td class=rhead>
+	[L]Interchange SUID User[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 uid=1]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Last time changes applied
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[file name=`"etc/status.$Config->{CatalogName}"`] ([page __UI_BASE__/reconfig @@MV_PAGE@@]apply now</A>)</TD>
+	<td class=rhead>
+	[L]Server mode[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 mode=1]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	<A HREF="[area __UI_BASE__/env_vars]">Environment</A> variables passed
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[version extended=1 env=1]</TD>
+	<td class=rhead>
+	[L]Last time server restarted[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[calc] scalar localtime([file-info conf=1 name="interchange.pid" time=1])[/calc]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Last time changes applied[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[file name=`"etc/status.$Config->{CatalogName}"`] ([page __UI_BASE__/reconfig @@MV_PAGE@@][L]apply now[/L]</A>)</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[msg arg.0='<A HREF="[area __UI_BASE__/env_vars]">' arg.1="</A>"]%sEnvironment%s variables passed[/msg]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 env=1]</TD>
 </TR>
 
 <TR>
@@ -145,32 +428,66 @@
 </TR>
 
 <TR>
-  <TD BGCOLOR=__UI_C_TOPBLOCKBAR__ COLSPAN=3><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1><CENTER>Perl Information</CENTER></TD>
+  <TD class=rmarq COLSPAN=3 align=center>[L]Perl Information[/L]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	<A HREF="[area href="@@MV_PAGE@@" form="more_perl=1"]">Perl Version</A>
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>Perl [version extended=1 perl=1 perl_config="[cgi more_perl]"]
-	</TD>
+	<td class=rhead>
+	<A HREF="[area href="@@MV_PAGE@@" form="more_perl=1"]">[L]Perl Version[/L]</A>
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>Perl [version extended=1 perl=1 perl_config="[cgi more_perl]"]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Optional Module Information
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD> [version extended=1 modules=1]</A></TD>
+	<td class=rhead>
+	[L]Optional Module Information[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 modules=1]</TD>
 </TR>
 
 <TR>
-	<TH VALIGN=TOP ALIGN=RIGHT>
-	Safe operations untrapped
-	</TH>
-	<TD>&nbsp; &nbsp;</TD>
-	<TD>[version extended=1 safe=1]</TD>
+	<td class=rhead>
+	[L]Safe operations untrapped[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 safe=1]</TD>
+</TR>
+
+<TR>
+  <TD COLSPAN=3>&nbsp;</TD>
+</TR>
+
+<TR>
+  <TD class=rmarq COLSPAN=3 align=center>[L]Database Information[/L]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Database Interfaces[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>[version extended=1 db=1]</TD>
+</TR>
+
+<TR>
+	<td class=rhead>
+	[L]Database Tables[/L]
+	</td>
+	<td class=clabel>&nbsp; &nbsp;</TD>
+	<td class=cdata>	<small>
+	<blockquote><div align=left>
+		[loop list="[list-databases]"]
+			<A HREF="[area __UI_BASE__/dbinfo [loop-code]]">[loop-code]</A><br>
+		[/loop]
+	</div></blockquote>
+	</small>
+</TD>
+</TR>
+
+<TR>
+  <TD class=rborder COLSPAN=3><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></TD>
 </TR>
 
 <TR>
@@ -213,8 +530,8 @@
 </td></tr>
 
 </table>
-</center>
-
+</div>
+[/if]
 
 <!-- ----- END REAL STUFF ----- -->
 



1.11.4.3  +204 -56   interchange/dist/lib/UI/pages/admin/gentable.html


rev 1.11.4.3, prev_rev 1.11.4.2
Index: gentable.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/gentable.html,v
retrieving revision 1.11.4.2
retrieving revision 1.11.4.3
diff -u -r1.11.4.2 -r1.11.4.3
--- gentable.html	10 Jan 2001 01:32:33 -0000	1.11.4.2
+++ gentable.html	25 Jan 2003 22:21:14 -0000	1.11.4.3
@@ -1,36 +1,60 @@
-[set page_perm]files[/set]
-[set page_title]Configuration[/set]
+[set page_perm]gentable[/set]
+[set page_title][L]Table Manager[/L][/set]
 [set ui_class]Admin[/set]
-[set help_name]genconfig.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set help_name]gentable[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
-<center>
-<TABLE width="90%" border=0 callpadding=0 cellspacing=0>
-<tr bgcolor="#000000" height=1><td></td></tr>
-<TR BGCOLOR="#__UI_C_TOPBLOCKBAR__">
-<TD VALIGN="top" width="20%">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-Database tables
-</font>
-</td></tr>
-<tr bgcolor="#000000" height=1><td></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td></td></tr>
-
-
-<tr><td align=left bgcolor=__UI_C_INTBLOCK__>
-
 <!-- touch metatable [data __UI_META_TABLE__ test test] -->
-<table border=0 cellspacing=0 cellmargin=0 cellpadding=0>
+[perl tables="__UI_META_TABLE__"]
+	my $db = $Db{__UI_META_TABLE__};
+	my $q = "select code from __UI_META_TABLE__ where type = 'table'";
+	my $ary = $db->query($q);
+	for(@$ary) {
+		my($code) = @$_; 
+		my ($view,$tab) = split /:+/, $code, 2;
+		if(! $tab) {
+			$tab = $view;
+			undef $view;
+		}
+		## $db->set_field($code, 'lookup', $tab);
+		## $db->set_field($code, 'attribute', $view);
+		## push @out, "set code=$code tab=$tab view=$view lookup=$tab attribute=$view";
+		next unless $view;
+		$views{$tab} ||= [];
+		push @{$views{$tab}}, $view;
+	}
+	for(keys %views) {
+		my $ary = $views{$_};
+		@$ary = sort @$ary;
+	}
+	return;
+[/perl]
+
+<table width="100%" border=0 cellspacing=0 cellpadding=0>
+  <tr>
+		<td>
+			<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+			  <tr class=rhead> 
 [loop list="[list-databases]"]
 [loop-sub db_action]
 sub {
 #Log("args=" . $Tag->uneval({ ref => \@_ }));
 	my $name = shift;
+	return if $admin{$name};
 	my $rec = shift;
 	my $tab = $rec->[0];
+	if(! $admin_done++) {
+		# Set up hidden tables
+		%admin = map { ($_, 1) } split /[\s.\0]+/, $Variable->{UI_ADMIN_TABLES};
+		# To build the links to hidden tables
+		$Scratch->{ui_tmp_admin} = join " ", sort keys %admin;
+	}
+
+	return '' if $admin{$tab};
+
 #Log("name=$name tab=$tab");
 	$name = $tab if ! $name;
 	my $url = "$Config->{VendURL}/__UI_BASE__";
@@ -41,72 +65,196 @@
 	};
 	my $ref = {
 		upload => { 
-						img => '@_UI_IMG_@admin/up.gif',
-						url => "$url/upload_file?mv_arg=" .
-								$froot->(join "/",
-											($Config->{Database}{$tab}{dir} || $Config->{ProductDir}),
-											$Config->{Database}{$tab}{file}
-										)
-								. '&ui_return_to=@@MV_PAGE@@',
-					},
-		view => { 
-						img => '@_UI_IMG_@admin/index.gif',
-						url => "$url/do_view?mv_arg=" .
-								$froot->(join "/",
+						img => 'ico_upload.gif',
+						url => $Tag->area(
+									'__UI_BASE__/upload_file',
+									$froot->(join "/",
 											($Config->{Database}{$tab}{dir} || $Config->{ProductDir}),
 											$Config->{Database}{$tab}{file}
 										),
+									{
+										form => 'ui_return_to=@@MV_PAGE@@'
+									}
+								),
+									
 					},
 		download => { 
-						img => '@_UI_IMG_@admin/down.gif',
-						url => "$Config->{VendURL}/ui_dbdownload/$tab",
+						img => 'ico_download.gif',
+						url => $Tag->area( 
+									{
+										href => 'ui_download/' .
+										  $froot->(
+										  	join "/",
+												(	$Config->{Database}{$tab}{dir}
+													||
+													$Config->{ProductDir}
+												),
+												$Config->{Database}{$tab}{file}
+											 ),
+										 form => 'filler=1',
+										 add_dot_html => 0,
+									},
+								),
 					},
 		import => { 
-						img => '@_UI_IMG_@admin/left.gif',
-						url => "$url/import_table?mv_data_table=$tab",
+						img => 'ico_import.gif',
+						url => $Tag->area(
+									{
+										href => '__UI_BASE__/import_table',
+										form => "mv_data_table=$tab",
+									}
+									),
 					},
 		export => { 
-						img => '@_UI_IMG_@admin/right.gif',
-						url => "$url/export_table?mv_data_table=$tab",
+						img => 'ico_export.gif',
+						url => $Tag->area(
+									{
+										href => '__UI_BASE__/export_table',
+										form => "mv_data_table=$tab",
+									}
+									),
+					},
+		config => { 
+						img => 'icon_config.gif',
+						url => $Tag->area(
+									{
+										href => '__UI_BASE__/dbconfig',
+										form => "mv_data_table=$tab",
+									}
+									),
 					},
 		edit => { 
-						img => '@_UI_IMG_@admin/layout.gif',
-						url => "$url/flex_select?mv_data_table=$tab",
+						img => 'layout.gif',
+						url => $Tag->area(
+									{
+										href => '__UI_BASE__/flex_select',
+										form => "mv_data_table=$tab",
+									}
+									),
 					},
 	};
 	my $out = '';
+	my @litems = (
+				$title_thing || '[L]Table name[/L] ([L]description[/L]) -- [L]click to edit[/L]',
+				'[L]views[/L]',
+				'[L]import[/L]',
+				'[L]export[/L]',
+				'[L]upload[/L]',
+				'[L]download[/L]',
+			);
+	if ($Variable->{UI_DBCONFIG}) {
+		push @litems, '[L]config[/L]';
+	}
+	
 	if(! $dblist_done_one++) {
-		$out .= '<tr>';
-		for(qw/edit import export view upload download /, "Table name (description)") {  # Add "report"
-			$out .= qq{<td bgcolor="__UI_C_TITLEBARBG__" align=center><font size="-1" color="__UI_C_TITLEBARTXT__">$_</td>};
+		$out .= '<tr class=rhead>';
+		my $i = 0;
+		for(@litems) {  # Add "report"
+			my $align = $i++ == 0 ? 'left' : 'center';
+			$out .= qq{<td class=rhead align=$align>$_</td>};
 		}
 		$out .= "</tr>";
 	}
-	$out .= '<tr>';
-	for(qw/edit import export view upload download /) {  # Add "report"
+
+	my $class;
+	if($dblist_done_one % 2) {
+		$class = 'rownorm';
+	}
+	else {
+		$class = 'rowalt';
+	}
+
+	my $desc = tag_data('__UI_META_TABLE__', 'name', $name);
+	my $totdesc = $name;
+	$totdesc .= " ($desc)" if $desc;
+	my $titdesc = errmsg('edit table %s', $totdesc);
+	$titdesc = $Tag->filter('encode_entities', $titdesc);
+	
+	my $mainwidth = $Variable->{UI_DBCONFIG} ? '30%' : '40%';
+
+	my $mref = $ref->{edit};
+	$out .= <<EOF;
+<tr class=$class>
+	<td class=$class width="$mainwidth">
+		<a href="$mref->{url}" title="$titdesc" class=$class>$totdesc</a>
+	</td>
+EOF
+
+	$out .= <<EOF;
+	<td class=$class width="20%">
+EOF
+	if(my $ary = $views{$name}) {
+		for(sort @$ary) {
+			my $tit = errmsg("edit %s with view %s", $tab, $_);
+			my $url = $Tag->area(
+								{
+									href => '__UI_BASE__/flex_select',
+									form => qq{
+												mv_data_table=$tab
+												ui_meta_view=$_
+											},
+								}
+							);
+			$out .= qq{<a href="$url" title="$tit">$_</a> };
+		}
+	}
+	else {
+		$out .= '&nbsp;';
+	}
+
+	$out .= "\n\t</td>\n";
+	my @mitems = (qw/import export upload download/);
+
+	if($Variable->{UI_DBCONFIG}) {
+		push @mitems, 'config';
+	}
+
+	for(@mitems) {  # Add "report"
 		my $line = $ref->{$_};
-		$out .= <<EOF;
-<td ALIGN=center><A HREF="$line->{url}"><img src="$line->{img}" border=0 alt="$_ $tab" align=top></A></td>
+		if($_ eq 'config' and $Config->{Database}{$tab}{type} > 7) {
+			$out .= qq{<td class=$class align=center width="12%">&nbsp;</td>};
+		}
+		else {
+			$out .= <<EOF;
+<td class=$class align=center width="12%"><a href="$line->{url}" title="$_ $tab"><img src="$line->{img}" border=0 alt="$_ $tab" title="$_ $tab" align=top></A></td>
 EOF
+		}
 	}
-	$out .= qq{<td>&nbsp;<FONT SIZE="+1">$name</FONT>};
-	my $desc = tag_data('__UI_META_TABLE__', 'name', $name);
-	$out .= qq{ ($desc)} if $desc;
-	$out .= q{</td></tr>};
+	$out .= q{</tr>};
 	return $out;
 }
 [/loop-sub]
 [loop-exec db_action][loop-data __UI_META_TABLE__ label][/loop-exec]
 [/loop]
-</table>
 
-</td></tr>
-
-<tr bgcolor="#000000" height=1><td></td></tr>
+[if-mm super]
+[calc]
+	%admin = ();
+	undef $dblist_done_one;
+	$title_thing = q{[L]Hidden Admin Tables[/L]};
+	return;
+[/calc]
 
 </table>
-</center>
+</td>
+</tr>
+</table>
 
+<table width="100%" border=0 cellspacing=0 cellpadding=0>
+  <tr>
+		<td>
+			<br><br>
+			<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+			  <tr class=rhead> 
+[loop list="[scratch ui_tmp_admin]"]
+[loop-exec db_action][loop-data __UI_META_TABLE__ label][/loop-exec]
+[/loop]
+[/if-mm]
+
+</table>
+</td>
+</tr>
+</table>
 
 <!-- ----- END REAL STUFF ----- -->
 



1.10.4.2  +20 -21    interchange/dist/lib/UI/pages/admin/group.html


rev 1.10.4.2, prev_rev 1.10.4.1
Index: group.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/group.html,v
retrieving revision 1.10.4.1
retrieving revision 1.10.4.2
diff -u -r1.10.4.1 -r1.10.4.2
--- group.html	20 Oct 2000 10:18:25 -0000	1.10.4.1
+++ group.html	25 Jan 2003 22:21:14 -0000	1.10.4.2
@@ -1,9 +1,9 @@
-[calc] $CGI->{no_dbmenu} = 1; $CGI->{access_menu} = 1; return [/calc]
-[set page_title]Admin Group Manager[/set]
+[calc]$Config->{NoSearch} = ''; $CGI->{no_dbmenu} = 1; $CGI->{access_menu} = 1; return [/calc]
+[set page_title][L]Administration Group Manager[/L][/set]
 [set ui_class]Admin[/set]
 [set page_perm]group=l[/set]
 [set help_name]group.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 
 @_UI_STD_HEAD_@
 [if scratch ui_message]
@@ -16,29 +16,30 @@
 [/if]
 
 <form action="[area ui]" method=POST>
+<input type=hidden name=mv_session_id value="[data session id]">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="__UI_BASE__/group_edit">
 <INPUT TYPE=hidden NAME=ui_hide_key VALUE="1">
 
-<table __UI_T_PROPERTIES__>
+<table cellpadding=3 cellspacing=0 width="70%">
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
-[set Create new group]
+[set [L]Create new group[/L]]
 mv_nextpage=__UI_BASE__/group_edit
 group_id=NEW
 ui_hide_key=0
 [/set]
 
-[set Show permissions]
+[set [L]Show permissions[/L]]
 user_id=[cgi group_id]
 mv_nextpage=__UI_BASE__/access_permissions
 ui_return_to=@@MV_PAGE@@
 [/set]
 
 
-[set Delete group]
+[set [L]Delete group[/L]]
 mv_nextpage=@@MV_PAGE@@
 [flag type=write table="__UI_ACCESS_TABLE__"]
 [if-mm advanced access=d]
@@ -64,26 +65,26 @@
 [/set]
 
 <tr>
-<td colspan=2 bgcolor="__UI_C_INTBLOCK__">
-<input type="submit" name="mv_click" value="Create new group">
+<td colspan=2 class=rnorm>
+<input type="submit" name="mv_click" value="[L]Create new group[/L]">
 </td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width=150>
-<input type="submit" value="Edit group"><br>
-<input type="submit" name="mv_click" value="Show permissions"><p>
+<td class=rnorm width=150>
+<input type="submit" value="[L]Edit group[/L]"><br><br>
+<input type="submit" name="mv_click" value="[L]Show permissions[/L]"><p>
 [if-mm advanced access=d]
-<input type="submit" name="mv_click" value="Delete group" 
- onClick="return confirm('Are you sure you want to delete this group?')">
+<input type="submit" name="mv_click" value="[L]Delete group[/L]" 
+ onClick="return confirm('[L]Are you sure you want to delete this group?[/L]')">
 [/if-mm]
 </td>
 
-<td bgcolor="__UI_C_INTBLOCK__" width=450>
+<td class=rnorm width=450>
 <select name="group_id" size=10>
 [loop search="fi=access/st=db/co=yes/sf=username/se=:/bs=yes/tf=name"]
   <option value="[loop-code]">[loop-data access name]
@@ -93,19 +94,17 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
 </table>
 
 <p>
 
-[set Back]
+[set [L]Back[/L]]
 mv_todo=back
 mv_nextpage=index
 [/set]
-
-<input type=submit name="mv_click" value="Back">
 
 </form>
 



1.6.4.2   +38 -30    interchange/dist/lib/UI/pages/admin/group_edit.html


rev 1.6.4.2, prev_rev 1.6.4.1
Index: group_edit.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/group_edit.html,v
retrieving revision 1.6.4.1
retrieving revision 1.6.4.2
diff -u -r1.6.4.1 -r1.6.4.2
--- group_edit.html	20 Oct 2000 10:18:25 -0000	1.6.4.1
+++ group_edit.html	25 Jan 2003 22:21:14 -0000	1.6.4.2
@@ -4,9 +4,10 @@
 [set ui_class]Admin[/set]
 [set page_perm]group=v[/set]
 [set help_name]group.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [calc]
 	$CGI->{mv_data_table} = $Values->{mv_data_table} = '__UI_ACCESS_TABLE__'; 
+	$Config->{NoSearch} = '';
 	return;
 [/calc]
 
@@ -21,6 +22,7 @@
 [/if]
 [loop list="[cgi group_id]"]
 <form action="[area ui]" method="post">
+<input type=hidden name=mv_session_id value="[data session id]">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE=__UI_BASE__/group>
 <INPUT TYPE=hidden NAME=mv_data_table VALUE="[value mv_data_table]">
@@ -28,28 +30,28 @@
 <INPUT TYPE=hidden NAME=mv_update_empty VALUE="1">
 <INPUT TYPE=hidden NAME=mv_data_fields VALUE="username name">
 
-<table __UI_T_PROPERTIES__>
+<table cellpadding=3 cellspacing=0 width="80%" align=center>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
 <input type="hidden" name="group_id" value="1001">
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Group name</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input type=text size=40 name=name maxlength=100 value="[filter entities][loop-data __UI_ACCESS_TABLE__ name][/filter]">
 </td>
 </tr>
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Group ID</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 [if cgi ui_hide_key]
 	<input type=hidden name=mv_data_function value="update">
 	<input type=hidden name=username value="[loop-code]">[loop-code]
@@ -67,38 +69,44 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td colspan=2 class=rspacer><img src="bg.gif" width=600 height=1></td>
 </tr>
 
-</table>
+<tr class=rnorm>
+	<td>&nbsp;</td>
+	<td>
+
+	[if-mm advanced access=e]
+		[set Ok]
+		[calc]
+			$CGI->{username} =~ s/\W+//g;
+			$CGI->{username} =~ s/^/:/;
+			return;
+		[/calc]
+		mv_todo=set
+		[/set]
+		<input type=submit name="mv_click" value="Ok">
+		<input type=submit value="Cancel">
+	[else]
+		[set Back]
+		mv_todo=back
+		[/set]
+		<input type=submit value="Back">
+	[/else]
+	[/if-mm]
+</td>
+</tr>
 
-<p>
+<tr>
+<td colspan=2 class=rborder><img src="bg.gif" width=600 height=1></td>
+</tr>
 
-[if-mm advanced access=e]
-	[set Ok]
-	[calc]
-		$CGI->{username} =~ s/\W+//g;
-		$CGI->{username} =~ s/^/:/;
-		return;
-	[/calc]
-	mv_todo=set
-	[/set]
-	<input type=submit name="mv_click" value="Ok">
-	<input type=submit value="Cancel">
-[else]
-	[set Back]
-	mv_todo=back
-	[/set]
-	<input type=submit value="Back">
-[/else]
-[/if-mm]
+</table>
 
 
 </form>
 
 [/loop]
-
-</form>
 
 @_UI_STD_FOOTER_@
 



1.9.4.4   +98 -30    interchange/dist/lib/UI/pages/admin/import_table.html


rev 1.9.4.4, prev_rev 1.9.4.3
Index: import_table.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/import_table.html,v
retrieving revision 1.9.4.3
retrieving revision 1.9.4.4
diff -u -r1.9.4.3 -r1.9.4.4
--- import_table.html	27 Nov 2000 01:27:37 -0000	1.9.4.3
+++ import_table.html	25 Jan 2003 22:21:14 -0000	1.9.4.4
@@ -1,8 +1,9 @@
-[set page_title]Individual Table Import[/set]
+[if-mm super][flag type=write table="ichelp"][/if-mm]
+[set page_title][L]Table Import[/L][/set]
 [set table_perm]=i[/set]
 [set help_name]import.main[/set]
 [set ui_class]Admin[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
@@ -17,14 +18,16 @@
 		return;
 	[/calc]
 [/if]
+
+
 [if type=explicit compare="[value-extended
 							name=upload_file
 							test=isfile]"]
 	[title-bar]
 	[if cgi ui_import_convert]
-		Importing multiple tables:
+		[L]Importing multiple tables:[/L]
 	[else]
-		Import of table [cgi mv_data_file]:
+		[msg arg.0="[cgi mv_data_table]"]Import of table %s:[/msg]
 	[/else]
 	[/if]
 	[calc]
@@ -58,21 +61,24 @@
 	[value-extended
 		name=upload_file
 		outfile="upload/[cgi ui_upload_filename]"
-		yes="Upload succeeded"
-		no="Upload FAILED"
+		yes="[L]Upload succeeded[/L]"
+		no="[L]Upload FAILED[/L]"
 		]
 	<P>
 	[if type=!file term="upload/[cgi ui_upload_filename]"]
-		<B>Import file [cgi ui_upload_filename] not found!!!</B>
+		<B>[msg arg.0="[cgi ui_upload_filename]"]Import file %s not found!!![/msg]</B>
 	[elsif cgi ui_upload_ext eq add]
 	[import-fields
 					add=1
+					autonumber="[cgi ui_autonumber]"
 					convert="[cgi ui_import_convert]"
 					delete="[cgi ui_allow_delete]"
+					filter_field="[cgi ui_filter_field]"
 					dir=backup
 					file="upload/[cgi ui_upload_filename]"
 					move=1
 					multiple="[cgi ui_allow_multiple]"
+					transactions="[cgi ui_import_transactions]"
 					quiet="[cgi ui_import_quiet]"
 					table="[cgi mv_data_table]"
 	]
@@ -85,8 +91,26 @@
 					file="upload/[cgi ui_upload_filename]"
 					move=1
 					multiple="[cgi ui_allow_multiple]"
+					transactions="[cgi ui_import_transactions]"
 					quiet="[cgi ui_import_quiet]"
 					table="[cgi mv_data_table]"
+					filter_field="[cgi ui_filter_field]"
+	]
+	[/elsif]
+	[elsif cgi ui_upload_ext eq cleanse]
+	[import-fields
+	                add=1
+					convert="[cgi ui_import_convert]"
+					cleanse=1
+					delete="[cgi ui_allow_delete]"
+					dir=backup
+					file="upload/[cgi ui_upload_filename]"
+					move=1
+					multiple="[cgi ui_allow_multiple]"
+					transactions="[cgi ui_import_transactions]"
+					quiet="[cgi ui_import_quiet]"
+					table="[cgi mv_data_table]"
+					filter_field="[cgi ui_filter_field]"
 	]
 	[/elsif]
 	[/if]
@@ -98,47 +122,91 @@
 	return;
 [/calc]
 <form action="[area @@MV_PAGE@@]" method="POST" ENCTYPE="multipart/form-data">
+<input type=hidden name=mv_session_id value="[data session id]">
 <INPUT TYPE=hidden NAME=mv_action     VALUE=return>
-<INPUT TYPE=hidden NAME=ui_return_to VALUE="__UI_BASE__/genxport">
+<INPUT TYPE=hidden NAME=ui_return_to VALUE="__UI_BASE__/gentable">
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+	<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+
+<tr class=rnorm>
+	<td class=clabel>Table Name</td>
+	<td class=cdata>
+		
+		<select name="mv_data_table">
+		[loop
+			list="[list-databases extended=i]"
+			option=mv_data_table
+		]<option value="[loop-code]">[loop-code][/loop]
+		</select>
+	</td>
+</tr>
+<tr class=rnorm>
+	<td class=clabel>Import from File</td>
+	<td class=cdata>
+	<input type=file name=upload_file>
+	<BR>
+	<input type="submit" value="[L]Import[/L]">
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
-<input type=file name=upload_file>
-<BR>
-<input type="submit" value="Import">
+	<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+
+<tr class=rnorm>
+	<td colspan=2 valign=top>
 <br>
-<hr>
 <SELECT NAME=ui_upload_ext>
-	<OPTION VALUE=add> Add new items if present
-	<OPTION VALUE=update> Ignore new items
-</SELECT>&nbsp;&nbsp;&nbsp;<INPUT TYPE=checkbox NAME=ui_allow_delete VALUE=1> Allow delete
+	<OPTION VALUE=add> [L]Add new items if present[/L]
+	<OPTION VALUE=cleanse> [L]Replace existing items[/L]
+	<OPTION VALUE=update> [L]Ignore new items[/L]
+</SELECT>&nbsp;&nbsp;&nbsp;<SMALL><INPUT TYPE=checkbox NAME=ui_allow_delete VALUE=1> [L]Allow delete[/L]
+&nbsp;&nbsp;<INPUT TYPE=checkbox NAME=ui_autonumber VALUE=1 CHECKED> [L]Autonumber if no key[/L]
+<INPUT TYPE=checkbox NAME=ui_import_transactions VALUE=1> [L]Use transactions[/L]</SMALL>
 <BR><select NAME=ui_import_convert>
-		<OPTION VALUE=0> Single table
-		<OPTION VALUE=1> Gnumeric simple tex
+		<OPTION VALUE=0> [L]Single table[/L]
+		<OPTION VALUE=1> [L]Gnumeric simple tex[/L]
 		[if type=explicit compare="[version modtest='Spreadsheet::ParseExcel' extended=1]"]
-		<OPTION VALUE=2> XLS Spreadsheet
+		<OPTION VALUE=2> [L]XLS Spreadsheet[/L]
 		[/if]
 		</select>
 
-<BR><INPUT TYPE=radio NAME=ui_import_quiet VALUE=0 [checked name=ui_import_quiet value=0]> Show summary/add record/delete record messages
-<BR><INPUT TYPE=radio NAME=ui_import_quiet VALUE=1 [checked name=ui_import_quiet value=1 default=1]> Show summary messages only
-<BR><INPUT TYPE=radio NAME=ui_import_quiet VALUE=2 [checked name=ui_import_quiet value=2]> Show *no* messages
+<BR><INPUT TYPE=radio NAME=ui_import_quiet VALUE=0 [checked name=ui_import_quiet value=0]> [L]Show summary/add record/delete record messages[/L]
+<BR><INPUT TYPE=radio NAME=ui_import_quiet VALUE=1 [checked name=ui_import_quiet value=1 default=1]> [L]Show summary messages only[/L]
+<BR><INPUT TYPE=radio NAME=ui_import_quiet VALUE=2 [checked name=ui_import_quiet value=2]> [L]Show *no* messages[/L]
 </td>
-<td bgcolor="__UI_C_INTBLOCK__">
+	
+	<td valign=top>
+		<b>Field filters</b><br>
+		<textarea name=ui_filter_field cols=30 rows=3>[data
+												table="mv_metadata"
+												field="extended.filter_field"
+												serial=1
+												key="[cgi mv_data_table]"]</textarea>
+		<br>
+		<i>
+			Specified one per line:
+			<blockquote>
+<pre>
+	fieldname1=filter
+	fieldname2=filter1 filter2 
+</pre>
+			</blockquote>
+			If multiple tables, must specify table as well:
+			<blockquote>
+<pre>
+	table1:fieldname1=filter
+	table2:fieldname2=filter1 filter2 
+</pre>
+			</blockquote>
+		</i>
+	</td>
 
-<select name="mv_data_table">
-[loop list="[list-databases extended=i]" option=mv_data_table]<option value="[loop-code]"> [loop-code]
-[/loop]
-</select>
-</td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.22.4.13 +73 -166   interchange/dist/lib/UI/pages/admin/index.html


rev 1.22.4.13, prev_rev 1.22.4.12
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/index.html,v
retrieving revision 1.22.4.12
retrieving revision 1.22.4.13
diff -u -r1.22.4.12 -r1.22.4.13
--- index.html	9 Feb 2001 20:10:41 -0000	1.22.4.12
+++ index.html	25 Jan 2003 22:21:14 -0000	1.22.4.13
@@ -1,3 +1,6 @@
+[if !global Windows]
+[index table=ichelp export_only=1]
+[/if]
 [strip interpolate=1]
 [if-mm !logged_in]
 	[bounce page="__UI_BASE__/login"]
@@ -13,7 +16,7 @@
 [set page_title]Interchange Administration[/set]
 [tmp ui_no_title]1[/tmp]
 [set icon_name][/set]
-[set help_name]index[/set]
+[set help_name]home[/set]
 [set ui_class]None[/set]
 
 [seti meta_header]
@@ -58,14 +61,16 @@
 
 [/strip]
 @_UI_STD_HEAD_@
-<table width="100%" border="0" cellspacing="0" cellpadding="0" height="320" width=700 bgcolor="#eeeeee">
+<table width="100%" border=0 cellspacing=0 cellpadding=0 height=320 width=700 bgcolor="#eeeeee">
 <tr>
-<td valign=top>
+<td valign=top style="
+		border: 2px solid #996633;
+">
 <br><br><br>
 <div align=center>
-<table width="90%" border="1" cellspacing=0 cellpadding="0" bordercolorlight="#6699FF" bordercolordark="#6699FF">
-<tr>
-<td bgcolor="#FFFFFF">
+<table width="90%" border="1" cellspacing=0 cellpadding="0" bgcolor="#FFFFFF">
+<tr class=ralt>
+<td>
 <br>						
 <div align=center>
 <table border=0 cellspacing=3 cellpadding=2>
@@ -86,8 +91,8 @@
 <H1>Admin interface will not work properly.</H1>
 Please install needed Perl modules:
 <small>
-<blockquote>
-	<FONT COLOR="__UI_C_CONTRAST__">$imp</FONT>
+<blockquote class=cerror>
+	$imp
 </blockquote>
 <blockquote>
 	$minor
@@ -115,174 +120,76 @@
 	return $out;
 [/calc]
 
-[if-mm advanced order]
-<tr>
-<td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_orders.gif">
-</td>
-<td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/order]">Orders</a></font>
-</b>
-</font>
-</td>
-<td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-View and manage incoming orders, archive and access past orders 
-</font>
-</td>
-</tr>
-[/if-mm]
-
-[if-mm advanced page]
-<tr>
-<td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_pages.gif">
-</td>
-<td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/page]">Content</a></font>
-</b>
-</font>
-</td>
-<td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-Create, edit, upload and download pages 
-</font>
-</td>
-</tr>
-[/if-mm]
-
-[if-mm advanced userdb]
-<tr>
-<td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_people.gif">
-</td>
-<td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/customer]">Customers</a></font>
-</b>
-</font>
-</font>
-</td>
-<td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-View and manage customer information and order history 
-</font>
-</td>
-</tr>
-[/if-mm]
-
-[if-mm advanced sitedesign]
-<tr>
-<td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_design.gif">
-</td>
-<td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/layout]">Design</a></font>
-</b>
-</font>
-</td>
-<td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-Organize site navigation, manage site layout 
-</font>
-</td>
-</tr>
-[/if-mm]
+[perl tables="__UI_META_TABLE__ mv_metadata"]
+	delete $Scratch->{merge_complete};
+	delete $Scratch->{do_merge};
+	my $tab = q{__UI_META_TABLE__} || 'mv_metadata';
+	my $db = $Db{$tab}
+		or do {
+			$Scratch->{merge_complete}
+				= errmsg("Cannot merge: no meta table '%s'", $tab);
+			return;
+		};
+
+	my $newver = $Tag->version();
+	$Scratch->{newver} = $newver;
+	my $compnew = $newver;
+	$compnew =~ s/\D+//g;
+
+	my $curver = 0;
+	if($db->record_exists('ui-version')) {
+		$curver = $db->field("ui-version", 'label');
+	}
+
+	$Scratch->{curver} = $curver;
+	my $compcur = $curver;
+	$compcur =~ s/\D+//g;
 
-[if-mm advanced item]
-</tr>
-<td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_item.gif">
-</td>
-<td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/item]">Items</a></font>
-</b>
-</font>
-</td>
-<td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-Add and edit items displayed for sale on the site 
-</font>
-</td>
-</tr>
-[/if-mm]
-
-[if-mm advanced stats]
-<tr>
-<td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_stats.gif">
-</td>
-<td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/orderstats]">Reporting</a></font>
-</b>
-</font>
-</td>
-<td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-View statistics on orders and site traffic, create custom reports 
-</font>
-</td>
-</tr>
-[/if-mm]
-</tr>
-
-[if-mm advanced item]
-<tr>
-<td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_merch.gif">
-</td>
-<td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/merchandising]">Merchandising</a></font>
-</b>
-</font>
-</td>
-<td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-Set up quantity pricing, up-sell, promotions, and affiliates 
-</font>
-</td>
-[/if-mm]
+	if ($curver eq $newver) {
+		## All is copasetic
+	}
+	elsif($compcur gt $compnew) {
+		## I guess this is OK
+	}
+	else {
+		return qq{
+<TR>
+<TD COLSPAN=3>
+<blockquote class=titlebox>
+UI update appears to have been done and metadata has not
+been updated for this catalog...
+	<blockquote>
+		[page href=admin/merge_meta extra=class=titlebox]Merge Metadata</a>
+	</blockquote>
+</blockquote>
+</TD>
+</TR>
+		};
+	}
+	return;
+[/perl]
 
-[if-mm advanced techadmin]
+[menu
+	  name=Top
+	  superuser=super
+	  inactive=inactive
+	  localize=name,description
+	  ui_security=depends_on
+	  lr=1]
 <tr>
 <td valign="top">
-<font color="#000066">
-<img src="@_UI_IMG_@admin/icon_config.gif">
+	  {IMG_ICON?}
+<img src="{IMG_ICON}">
+	  {/IMG_ICON?}
 </td>
 <td valign="top">
-<b>
-<font face="Arial, Helvetica, sans-serif">
-&nbsp;<a href="[area __UI_BASE__/genconfig]">Administration</a></font>
-</b>
-</font>
+&nbsp;<a href="{HREF}">{NAME}</a>
 </td>
 <td valign="top">
-<font size="-1" face="Arial, Helvetica, sans-serif">
-Administrator and developer-oriented tools 
-</font>
+{DESCRIPTION}
 </td>
 </tr>
-[/if-mm]
+[/menu]
 
 </table>
 </div>



1.18.4.7  +436 -103  interchange/dist/lib/UI/pages/admin/item.html


rev 1.18.4.7, prev_rev 1.18.4.6
Index: item.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item.html,v
retrieving revision 1.18.4.6
retrieving revision 1.18.4.7
diff -u -r1.18.4.6 -r1.18.4.7
--- item.html	27 Oct 2000 09:28:44 -0000	1.18.4.6
+++ item.html	25 Jan 2003 22:21:14 -0000	1.18.4.7
@@ -1,35 +1,57 @@
 [if !cgi mv_data_table]
+[or cgi ui_scrub_table]
 [calc]
 	$CGI->{mv_data_table} = $Values->{mv_data_table} = $Config->{ProductFiles}[0];
 	return;
 [/calc]
 [/if]
+[set ui_class]Items[/set]
+[tmp page_title][L]Item editor[/L][/tmp]
+[if-mm super]
+[tmp page_banner]
+		[page href="__UI_BASE__/db_metaconfig"
+				secure="[scratch page_secure]"
+				form='
+						 ui_return_to=__UI_BASE__/index
+						 ui_table=[cgi mv_data_table]
+						 ui_view=item_select
+						 start_at=height
+				'][L]Item editor[/L]</A>
+[/tmp]
+[/if-mm]
+[set table_perm]__ProductFiles_0__=v[/set]
+[set help_name]item.editor[/set]
+[set icon_name]icon_item.gif[/set]
+@_UI_STD_HEAD_@
 
 
+[comment]
 <!-- sequence_edit: [cgi ui_sequence_edit] -->
 <!-- item_id_left: [cgi item_id_left] -->
+[/comment]
+
 [if cgi deleterecords]
 [if-mm function="!tables" table="[cgi mv_data_table]"]
+[set ui_error][msg arg.0="[cgi mv_data_table]"]Not allowed to delete from %s.[/msg][/set]
 [bounce page="__UI_BASE__/error"]
 [else]
 <!-- flag write for delete: [flag type=write table="[cgi mv_data_table]"] -->
+[tmp extra_tables][loop list=`
+	my @tab = grep /\S/, split /[\s,\0]+/,  q{__UI_ITEM_TABLES__};
+	my %seen;
+	for (@tab) {
+		s/:.*//;
+		next if $seen{$_}++;
+	}
+	return join " ", @tab;
+	`][if-mm tables [loop-code]=d][loop-code] [flag type=write table="[loop-code]"][/if-mm][/loop][/tmp]
 [/else]
 [/if-mm]
 [/if]
 
-[perl tables="[cgi mv_data_table] __UI_META_TABLE__"]
+[perl tables="[cgi mv_data_table] [scratch extra_tables] __UI_META_TABLE__"]
 	delete $Scratch->{ui_location};
-    $Scratch->{description_field} = $Config->{DescriptionField};
-	my $tab = $CGI->{mv_data_table} or return;
-
-	my $db = $Db{$tab};
-	if(! ref $db) {
-		$Scratch->{error_message} = "<FONT CLASS=error>Error: no <B>$tab</B> database.</FONT><BR>";
-		$Scratch->{ui_location} = "__UI_BASE__/error";
-		return;
-	}
-    $Values->{ui_data_key_name} = $db->config('KEY');
-    $Values->{ui_data_key_numeric} = $db->config('NUMERIC')->{$db->config('KEY')};
+	my $dest = $CGI->{ui_sequence_destination} || '__UI_BASE__/item_edit';
 	if($CGI->{ui_sequence_edit}) {
 		my $doit;
 		if($CGI->{item_id_left} =~ s/^(.*?),//) {
@@ -48,7 +70,7 @@
 		return unless $doit;
 		$Scratch->{ui_location}
 				= $Tag->area( {
-						href => '__UI_BASE__/item_edit',
+						href => $dest,
 						form => qq{
 							item_id=$CGI->{item_id}
 							item_id_left=$CGI->{item_id_left}
@@ -58,70 +80,252 @@
 		return;
 	}
 
-	return unless $CGI->{item_id};
-	return unless delete $CGI->{deleterecords};
-	return unless $Tag->if_mm('tables', '=d');
+[/perl]
+
+[if scratch ui_location]
+	[bounce href=`delete $Scratch->{ui_location}`]
+[/if]
+
+<!-- ----- BEGIN REAL STUFF ----- -->
+[output name=search_box]
+<FORM ACTION="[area @@MV_PAGE@@]">
+<INPUT NAME=ui_text_qualification type=text class=s3>
+<INPUT TYPE=submit VALUE="[L]Limit with search[/L]" class=s3>
+</FORM>
+
+[output name=""]
+[if-mm !super]
+[tmp ui_owner][db-hash
+				table="__UI_ACCESS_TABLE__"
+				column="table_control::[cgi mv_data_table]::owner_field"
+				key="[data session username]"][/tmp]
+[/if-mm]
+
+[perl tables="[cgi mv_data_table] __UI_META_TABLE__"]
+	my $tab = $CGI->{mv_data_table};
+	my $view = $CGI->{ui_meta_view} || 'item_select';
+	my $ref = $Db{$tab};
+	my $meta = $Tag->meta_record($tab, $view);
+#Debug("Meta record: " . uneval($meta));
+	if (! $ref) {
+		$Scratch->{keypos} = 0;
+		return;
+	}
+	elsif (! $meta) {
+		$Scratch->{keypos} = 0;
+	}
+
+	$meta ||= {};
+
+	if($CGI->{ui_flex_key}) {
+		$Scratch->{keypos} = $CGI->{ui_flex_key};
+	}
+	else {
+		$Scratch->{keyname} = $ref->config('KEY');
+		$Scratch->{keypos} = $ref->config('KEY_INDEX');
+	}
 
-	delete $Scratch->{ui_location};
 	$Config->{NoSearch} = '';
+	$ui_text_qualification = $CGI->{ui_text_qualification}
+		and $CGI->{changed_qual} = 1;
+	if ($ui_text_qualification and $CGI->{ui_text_qualification} =~ /[<!=>\^]/ ) {
+		if($Scratch->{ui_owner}) {
+			$CGI->{ui_text_qualification} = <<EOF;
+co=1
+sf=$Scratch->{ui_owner}
+se=$Session->{username}
+op=eq
+nu=0
+os=0
+su=0
+bs=0
+EOF
+		}
+		else {
+			$CGI->{ui_text_qualification} = "co=1\n";
+		}
+
+		my @entries = split /\s+(and|or)\s+/i,  $ui_text_qualification;
+		my $or;
+		for(@entries) {
+			if(/^or$/i) {
+				$or = 1;
+				$CGI->{ui_text_qualification} .= "os=1\n";
+				next;
+			}
+			elsif(/^and$/i) {
+				$or = 0;
+				$CGI->{ui_text_qualification} .= "os=0\n";
+				next;
+			}
+			my ($f, $op, $s) = split /\s*([<=!>\^]+)\s*/, $_, 2;
+			$op = "eq" if $op eq "==";
+			$op = "rm" if $op eq "=";
+			if($op eq '^') {
+				$op = 'rm';
+				$CGI->{ui_text_qualification} .= "bs=1\nsu=1\n";
+			}
+			else {
+				$CGI->{ui_text_qualification} .= "bs=0\nsu=0\n";
+			}
+			$CGI->{ui_text_qualification} .= "se=$s\nsf=$f\nop=$op\n";
+			if($op =~ /[<>]/ and $s =~ /^[\d.]+$/) {
+				$CGI->{ui_text_qualification} .= "nu=1\n";
+			}
+			else {
+				$CGI->{ui_text_qualification} .= "nu=0\n";
+			}
+		}
+		if(defined $or) {
+			$CGI->{ui_text_qualification} .= $or ? "os=1\n" : "os=0\n";
+		}
+
+		$out_message = errmsg('entries matching "%s"', $ui_text_qualification);
+	}
+	elsif ($ui_text_qualification) {
+		$CGI->{ui_text_qualification} = "se=$CGI->{ui_text_qualification}";
+		$out_message = errmsg('entries matching "%s"', $ui_text_qualification);
+		if($Scratch->{ui_owner}) {
+			$CGI->{ui_text_qualification} = <<EOF;
+co=1
+sf=$Scratch->{ui_owner}
+se=$Session->{username}
+op=eq
+sf=:*
+se=$CGI->{ui_text_qualification}
+EOF
+		}
+	}
+	elsif($Scratch->{ui_owner}) {
+		$CGI->{ui_text_qualification} = <<EOF;
+co=1
+sf=$Scratch->{ui_owner}
+se=$Session->{username}
+op=eq
+EOF
+	}
+	else {
+		$CGI->{ui_text_qualification} = "ra=yes";
+	}
 
-	for(grep $_, @{$CGI_array->{item_id}}) {
-		$db->delete_record($_)
-			or push @errors, $@;
-	}
-	if(@errors) {
-		my $plural = @errors > 1 ? 's' : '';
-		return "<FONT CLASS=error>Error$plural:<UL><LI>" .
-				join ("<LI>", @errors)                    .
-				"</UL></FONT><BR>";
+	if($meta->{ui_sort_combined} =~ /\S/) {
+		$meta->{ui_sort_field} = $meta->{ui_sort_combined};
+		$meta->{ui_sort_option} = '';
+	}
+
+	if ($CGI->{ui_sort_field}) {
+		$CGI->{changed_qual} = 1;
+		delete $Scratch->{item_special_sort};
+	}
+	elsif(! $Scratch->{item_special_sort}) {
+		$CGI->{ui_sort_field}	||= $meta->{ui_sort_field}
+								||  $meta->{lookup}
+								||  $Scratch->{keyname};
+		$CGI->{ui_sort_option} ||= $meta->{ui_sort_option};
+		$CGI->{ui_sort_option}	=~ s/[\0,\s]+//g;
 	}
+
+	$CGI->{ui_list_size} = $meta->{height}
+		if ! $CGI->{ui_list_size};
+	$CGI->{ui_show_fields} ||= $meta->{ui_show_fields} || $meta->{field};
+#Debug("CGI->{ui_show_fields}=$CGI->{ui_show_fields}");
+	if(! $CGI->{ui_show_fields}) {
+		$CGI->{ui_show_fields} = '*';
+		$CGI->{ui_description_fields} = join ",", $ref->columns();
+	}
+	else {
+		my $i = 0;
+		$CGI->{ui_show_fields} =~
+			s/(\w+)(?:\((.*?)\))?/ ($filter_show[$i++] = $2), $1/eg;
+#Debug("filter_show: " . $Tag->uneval( { ref => \@filter_show } ));
+		$CGI->{ui_show_fields} =~ s/[\0,\s]+$//g;
+		$CGI->{ui_show_fields} =~ s/^[\0,\s]+//g;
+		$CGI->{ui_show_fields} =~ s/[\0,\s]+/,/g;
+		$CGI->{ui_description_fields} = $CGI->{ui_show_fields};
+	}
+
+	$meta->{ui_special_add} ||= $meta->{outboard};
+	# Set in item editor area
+	@special = grep /\S/, split /[,\0]+/, $meta->{ui_special_add}
+		if ($meta->{ui_special_add} ||= $meta->{outboard});
+	unless (@special) {
+		@special = (
+			'Qty price;pricing:q5:r',
+			'Up-sell;merchandising:upsell_to:r',
+			'Cross-sell;merchandising:cross_sell:r',
+			'Promo;merchandising:featured:r',
+			'Inventory;inventory:quantity:r',
+			);
+	}
+	@special = grep $_ !~ /^none$/i, @special;
+
+	$Scratch->{ui_show_special} = join ("\n", '', @special, '');
+	@cols = grep /\S/, split /[\s,\0]+/, $CGI->{ui_description_fields};
+	for(@cols) {
+		$numeric{$_} = 1 if $ref->numeric($_);
+	}
+	$CGI->{changed_qual} = 1 if delete $Scratch->{item_list_clicked};
+
+	$Scratch->{ui_text_qualification} = $out_message;
 	return;
 [/perl]
 
-[if scratch ui_location]
-	[bounce href=`delete $Scratch->{ui_location}`]
+[if scratch ui_text_qualification]
+[calc]
+	return if $CGI->{mv_like_spec};
+	$Scratch->{page_banner} ||= $Scratch->{page_title};
+	$Scratch->{page_banner} .= ' -- ' . $Scratch->{ui_text_qualification};
+	return;
+[/calc]
 [/if]
 
-[set ui_class]Items[/set]
-[set page_title]Item editor[/set]
-[set table_perm]__UI_PRODUCT_TABLE__=v[/set]
-[set help_name]item.editor[/set]
-[set icon_name]admin/icon_item.gif[/set]
-@_UI_STD_HEAD_@
-
+<!-- existing item_sparams: '[scratch item_sparams]'
+		tq: '[cgi ui_text_qualification]' -->
 
-<!-- ----- BEGIN REAL STUFF ----- -->
-[if scratch ui_message]
-<BLOCKQUOTE>
-	[scratchd ui_message]
-</BLOCKQUOTE>
-<p>
-&nbsp;
+[if cgi changed_qual]
+[then]
+	[set item_list_clicked][/set]
+	[seti item_sparams]
+			fi=[cgi mv_data_table]
+			st=db
+			[cgi ui_text_qualification]
+			nh=[cgi showinactive]
+			su=1
+			md=1
+			ml=[cgi ui_list_size]
+			tf=[cgi ui_sort_field]
+			to=[cgi ui_sort_option]
+			rf=[cgi ui_show_fields]
+	[/seti]
+[/then]
+[elsif !scratch item_sparams]
+	[seti item_sparams]
+			fi=[cgi mv_data_table]
+			st=db
+			ra=yes
+			md=1
+			nh=[cgi showinactive]
+			ml=[cgi ui_list_size]
+			tf=[cgi ui_sort_field]
+			to=[cgi ui_sort_option]
+			rf=[cgi ui_show_fields]
+	[/seti]
+[/elsif]
+[else]
+	[set item_list_clicked]1[/set]
+	<span class=cmessage>([L]click Items again to reset list[/L])</span>
+[/else]
 [/if]
 
-<FORM ACTION="[area @@MV_PAGE@@]">
-<INPUT NAME=ui_text_qualification>
-<INPUT TYPE=submit VALUE="Limit with search">
-</FORM>
-[if cgi ui_text_qualification]
-<H3>Entries containing "[cgi ui_text_qualification]"</H3>
+<!-- existing item_sparams: '[scratch item_sparams]'
+		tq: '[cgi ui_text_qualification]' -->
+
+[if cgi ui_special_sort]
+[seti item_special_sort][cgi ui_special_sort][/seti]
 [/if]
-[search-region more=1 arg="
-		[if cgi ui_text_qualification]
-		se=[cgi ui_text_qualification]
-		su=yes
-		[else]ra=yes[/else][/if]
-		[if cgi ui_sort_field]
-			tf=[cgi ui_sort_field]
-			to=[cgi ui_sort_option]
-		[else]
-			tf=[scratch description_field]
-		[/else]
-		[/if]
-		st=db
-		sp=@@MV_PAGE@@
-		ml=__UI_SZ_LIST_ITEMS__
-"][on-match]
+
+[search-region more=1 sort="[scratch item_special_sort]" arg="[scratch item_sparams]"]
+[on-match]
 [calc] 
 	my $so   = $CGI->{ui_sort_option};
 	my $fld  = $CGI->{ui_sort_field};
@@ -130,7 +334,7 @@
 		my ($f, $n) = @_;
 		my $out = 'ui_sort_option=';
 		$out .= 'n' if $n;
-		return $out unless ($fld eq $f) || ($f eq 'description');
+		return $out unless ($fld eq $f) || ($f eq '__DescriptionField__');
 		return $out if $so =~ /r/;
 		return $out . 'r';
 	}
@@ -139,53 +343,173 @@
 
 <FORM ACTION="[area __UI_BASE__/item_edit]" METHOD=POST>
 <INPUT TYPE=hidden NAME=mv_action VALUE=back>
-<TABLE border=0 CELLSPACING=0 width="90%">
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<TR BGCOLOR="__UI_C_TITLEBARBG__">
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
-	return "ui_sort_field=$Values->{ui_data_key_name}\n" . sortrev($Values->{ui_data_key_name}, $Values->{ui_data_key_numeric});
-	`]SKU</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
-	return "ui_sort_field=$Scratch->{description_field}\n" . sortrev($Scratch->{description_field});
-	`]Description</TH>
-<TH ALIGN=RIGHT><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
-	return "ui_sort_field=price\n" . sortrev('price', 1);
-	`]Price</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Qty pricing</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Up-sell</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Cross-sell</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Promotion</TH>
-<TH ALIGN=right><FONT COLOR="__UI_C_TITLEBARTXT__">Inventory</TH>
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
 
+<tr class=rhead><TD>&nbsp;</TD>
+[loop list="[cgi ui_description_fields]"]
+<th[loop-calc]
+			my $extra = '';
+			while ($filter_show[ [loop-increment] - 1] =~ m/\b(v?align\s*=\w+)/gi) {
+				$extra .= " $1";
+			}
+			return $extra || ' ALIGN=LEFT';
+		[/loop-calc] class=rhead>
+
+    <table align="left">
+    <tr>
+      <td align="right" valign="center">
+	<A HREF="[area
+		href='__UI_BASE__/item_group'
+		form='mv_arg=[loop-code]
+		mv_data_table=[cgi mv_data_table]
+		']"><IMG ALT="select by [loop-code]" SRC="smindex.gif" BORDER=0></A>
+
+      </td>
+      <td align="left" valign="center" class=rhead>
+	<A HREF="[area href='@@MV_PAGE@@'
+					form=`
+						my $f = '[loop-code]';
+						my $o = '';
+						$o .= 'r'
+							if $CGI->{ui_sort_field} eq $f
+									and
+								$CGI->{ui_sort_option} !~ /r/;
+						$o .= 'n' if $numeric{$f};
+						return qq(
+							ui_text_qualification=$ui_text_qualification
+							mv_data_table=$CGI->{mv_data_table}
+							ui_sort_field=$f
+							ui_sort_option=$o
+						);
+					`
+				]" class=rhead>[either][data table="__UI_META_TABLE__" column=label key="[cgi mv_data_table]::[loop-code]"][or][loop-code][/either]</A>
+      </td>
+    </tr>
+    </table>	
+  </th>
+[/loop]
+[calc]
+	my $out = '';
+	for(@special) {
+		my $display = $_;
+		$display =~ s/\s*;\s*(.*)//;
+		$display = errmsg($display);
+		my $sort = $1; 
+		if($sort) {
+			my $cgi = $CGI->{ui_special_sort};
+			$cgi =~ s/(.*:.*):(\w+)$/$1/;
+			my $cgiopt = $1;
+			$sort =~ s/(.*:.*):(\w+)$/$1/;
+			my $sortopt = $2;
+			if($cgi eq $sort) {
+				$cgiopt =~ tr/nrx//cds;
+				%toggle = ( qw/
+								rn n
+								nr n
+								n  rn
+								x  r
+								r  x
+							/);
+				$toggle{''} = 'r';
+				$sortopt = $toggle{$cgiopt};
+			}
+			my $url = $Tag->page({
+						href => '@@MV_PAGE@@',
+						extra => 'class=rhead',
+						form => "
+									ui_text_qualification=$ui_text_qualification
+									mv_data_table=$CGI->{mv_data_table}
+									ui_special_sort=$sort:$sortopt
+								",
+							    });
+			$display = "$url$display</A>";
+		}
+		$out .= <<EOF;
+<td class=rhead ALIGN=CENTER><small class=rhead>$display</small></td>
+EOF
+	}
+	return $out;
+[/calc]
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=8></td></tr>
 [/on-match]
 [search-list]
-<TR [item-alternate 2]BGCOLOR="__UI_T_ROW_EVEN__"[else]BGCOLOR="__UI_T_ROW_ODD__"[/else][/item-alternate]>
-<TD><INPUT TYPE=checkbox NAME=item_id VALUE="[item-code]"> [page href=__UI_BASE__/item_edit form="item_id=[item-code]"][item-code]</A></TD>
-<TD>[filter 30][item-description][/filter]</TD>
-<TD ALIGN=RIGHT>[item-price]</TD>
+<tr class=[item-alternate 2]rowalt[else]rownorm[/else][/item-alternate]>
+
+<TD><INPUT TYPE=checkbox NAME=item_id VALUE="[item-code]"></TD><TD>[page href=__UI_BASE__/item_edit form="item_id=[item-code]"][item-code]</A></TD>
+[item-sub show_line]
+sub {
+	my $extra = shift;
+	$extra =~ s/^[\s%]+//;
+	$extra =~ s/[\s%]+$//;
+	my (%extra) = split /\n%%\n/, $extra;
+	my $line = shift;
+	return unless $line;
+	shift (@$line);
+	my $out = '';
+	my $i = 1;
+	for(@$line) {
+		my $extra = '';
+		my $filter = $filter_show[$i] || 'entities';
+		$extra .= " $1" while $filter =~ s/(v?align=\w+)//i;
+#Log("$i filter = $filter");
+		$_ = $Tag->filter($filter, $_);
+		s/\[/&#91;/g;
+		$out .= "<TD$extra>$_</TD>";
+		$i++;
+	}
+	for(@special) {
+#Log("Special='$_'");
+		my $item = $_;
+		$item =~ s/\s*;.*//;
+#Log("Special='$item'");
+		$out .= $extra{$item};
+	}
+	return $out . "\n";
+}
+[/item-sub]
+[item-exec show_line]
+Options
+%%
+<TD ALIGN=CENTER>[page href=__UI_BASE__/item_option form="
+	item_id=[item-code]
+"][if-item-data options o_enable][L]Yes[/L][else][L]No[/L][/else][/if-item-data]</A>
+</TD>
+%%
+Qty price
+%%
 <TD ALIGN=CENTER>[page href=__UI_BASE__/item_price form="
 	item_id=[item-code]
-"][if-item-data pricing sku]Yes[else]No[/else][/if-item-data]</A>
+"][if-item-data pricing sku][L]Yes[/L][else][L]No[/L][/else][/if-item-data]</A>
 </TD>
+%%
+Up-sell
+%%
 <TD ALIGN=CENTER>[page href=__UI_BASE__/item_up form="
 	item_id=[item-code]
-"][if-item-data merchandising upsell_to]Yes[else]No[/else][/if-item-data]</a>
+"][if-item-data merchandising upsell_to][L]Yes[/L][else][L]No[/L][/else][/if-item-data]</a>
 </TD>
+%%
+Cross-sell
+%%
 <TD ALIGN=CENTER>[page href=__UI_BASE__/item_cross form="
 	item_id=[item-code]
-"][either][if-item-data merchandising cross_category]Yes[/if-item-data][or][if-item-data merchandising cross_sell]Yes[/if-item-data][or]No[/either]</a>
+"][either][if-item-data merchandising cross_category][L]Yes[/L][/if-item-data][or][if-item-data merchandising cross_sell][L]Yes[/L][/if-item-data][or][L]No[/L][/either]</a>
 </TD>
+%%
+Promo
+%%
 <TD ALIGN=CENTER>[page href=__UI_BASE__/item_feature form="
 	item_id=[item-code]
-"][if-item-data merchandising featured]Yes[else]No[/else][/if-item-data]</a>
+"][if-item-data merchandising featured][L]Yes[/L][else][L]No[/L][/else][/if-item-data]</a>
 </TD>
-<TD ALIGN=right>[page href=__UI_BASE__/item_inventory form="
+%%
+Inventory
+%%
+<TD ALIGN=center>[page href=__UI_BASE__/item_inventory form="
 	item_id=[item-code]
 "][if-item-data inventory quantity ne ''][item-data inventory quantity][else]N/A[/else][/if-item-data]</a>
 </TD>
+[/item-exec]
 </tr>
 
 [/search-list]
@@ -193,22 +517,26 @@
 <tr>
 <td colspan=6 align=left>
 <br>
-<B>Nothing matched.</B>
+<B>[L]Nothing matched[/L].</B>
 <br><br>
 </td>
 </tr>
 [/no-match]
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=8><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 [more-list]
 <tr>
 <td colspan=8 align=center>
-More items: [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
+[L]More items[/L]: [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
 </td>
 </tr>
 [/more-list]
 </table>
-[button text="Edit checked items in sequence"]
+
+[/search-region]
+
+[output name="bottom_buttons"]
+
+[button text="[L]Edit checked items in sequence[/L]" extra="class=s3"]
 ui_sequence_edit=[calc]
 	$CGI->{item_id_left} = $CGI->{item_id};
 	$CGI->{item_id_left} =~ s/\0+/,/g;
@@ -228,17 +556,22 @@
 
 &nbsp;&nbsp;&nbsp;&nbsp;
 
-[button text="Delete checked items"
-		confirm="Are you sure you want to delete the checked items?"]
+[button text="[L]Delete checked items[/L]" extra="class=s3"
+		confirm="Are you sure you want to delete the checked items\n__UI_ITEM_TABLES__?"
+]
 [flag type=write table="[cgi mv_data_table]"]
 deleterecords=1
+ui_delete_tables=__UI_ITEM_TABLES__
+mv_click=db_maintenance
 mv_todo=back
 mv_nextpage=@@MV_PAGE@@
 [/button]
-</FORM>
+<INPUT TYPE=hidden NAME=mv_data_table VALUE="[cgi mv_data_table]">
 
-[/search-region]
+[output name="bottom_of_form"]
+</FORM>
+[output name=""]
 <!-- ----- END REAL STUFF ----- -->
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ Revision: $Id: item.html,v 1.18.4.7 2003/01/25 22:21:14 racke Exp $ -->



1.2.4.5   +13 -26    interchange/dist/lib/UI/pages/admin/item_cross.html


rev 1.2.4.5, prev_rev 1.2.4.4
Index: item_cross.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_cross.html,v
retrieving revision 1.2.4.4
retrieving revision 1.2.4.5
diff -u -r1.2.4.4 -r1.2.4.5
--- item_cross.html	27 Nov 2000 01:11:32 -0000	1.2.4.4
+++ item_cross.html	25 Jan 2003 22:21:14 -0000	1.2.4.5
@@ -7,45 +7,32 @@
 		$CGI->{mv_data_table} = 'merchandising';
 	}
 	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = 'sku __UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__ cross_sell cross_category blurb_begin blurb_end';
-		$CGI->{ui_display_only} = '__UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__';
+		$CGI->{ui_data_fields} = 'sku __ProductFiles_0__:__DescriptionField__ cross_sell cross_category blurb_begin blurb_end';
+		$CGI->{ui_display_only} = '__ProductFiles_0__:__DescriptionField__';
 	}
 	if(! $CGI->{ui_break_before}) {
 		$CGI->{ui_break_before} = 'blurb_begin';
 	}
-	my @args = (
-		 '__UI_BASE__/item_edit',
-		 "item_id=$CGI->{item_id}",
-		 "item_id_left=$CGI->{item_id_left}",
-		 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
-	);
-	$CGI->{ui_return_to} = join "\0", @args;
+	if(! $CGI->{ui_return_to}) {
+		my @args = (
+			 '__UI_BASE__/item_edit',
+			 "item_id=$CGI->{item_id}",
+			 "item_id_left=$CGI->{item_id_left}",
+			 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
+		);
+		$CGI->{ui_return_to} = join "\0", @args;
+	}
 	return;
 [/calc]
-@_UI_STD_DBEDIT_HEAD_@
 
 [seti page_title]Cross-selling: [cgi item_id][/seti]
 [seti page_banner]Cross-selling: edit item <B>[page href="__UI_BASE__/item_edit" form="item_id=[cgi item_id]"][cgi item_id]</A></B>[/seti]
 [set help_name]crosssell[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
-
-[if-mm super]
-<A HREF="[area href=admin/flex_editor
-				form='
-					item_id=[cgi item_id]
-					mv_data_table=__UI_PRODUCT_TABLE__
-					page_title=Edit items: [cgi item_id]
-					help_name=inventory.edit
-					ui_no_meta_display=1
-					ui_hide_key=1
-					ui_return_to=admin/item
-					icon_name=admin/icon_item.gif
-					']">No meta display</A>
-[/if-mm]
+[table-editor cgi=1 output_map=1]
 
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->



1.12.4.6  +54 -54    interchange/dist/lib/UI/pages/admin/item_edit.html


rev 1.12.4.6, prev_rev 1.12.4.5
Index: item_edit.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_edit.html,v
retrieving revision 1.12.4.5
retrieving revision 1.12.4.6
diff -u -r1.12.4.5 -r1.12.4.6
--- item_edit.html	2 Nov 2000 10:03:45 -0000	1.12.4.5
+++ item_edit.html	25 Jan 2003 22:21:14 -0000	1.12.4.6
@@ -1,79 +1,79 @@
 [calc]
 	$CGI->{mv_data_table} = $Config->{ProductFiles}[0];
-	if ($CGI->{item_id} eq 'new') {
-		$CGI->{ui_new_item} = 1;
-	}
-	else {
-		$CGI->{ui_hide_key} = 1 unless $CGI->{item_id} eq 'new';
-	}
-	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = $Variable->{UI_ITEM_FIELDS}
-				|| 'sku description category comment price image weight size color';
-	}
-	if(! $CGI->{ui_break_before}) {
-		$CGI->{ui_break_before} = $Variable->{UI_ITEM_BREAK}
-				|| 'image size';
-	}
-	if(! $CGI->{ui_break_before_label}) {
-		$CGI->{ui_break_before_label} = $Variable->{UI_ITEM_BREAK_LABEL};
-	}
-	my @args = (
-		 '__UI_BASE__/item',
-		 "item_id_left=$CGI->{item_id_left}",
-		 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
-	);
-	$CGI->{ui_return_to} = join "\0", @args;
+	$CGI->{ui_hide_key} = 1 unless $CGI->{ui_new_item};
+	$CGI->{ui_return_to} ||= '__UI_BASE__/item';
+	$Tag->tmpn('tmp_item_id');
+	$Scratch->{tmp_item_id} = $CGI->{item_id} || $CGI->{item_id_left};
+	$Scratch->{tmp_item_id} =~ s/\0.*//
+		or $Scratch->{tmp_item_id} =~ s/,.*//;
 	return;
 [/calc]
+
 [if cgi ui_new_item]
-	[calc]
-		$CGI->{item_id} = q{[counter file="__UI_PRODUCT_DIR__/__UI_PRODUCT_DIR__.autonumber" start=new0000]};
+	[loop list="__MV_ITEM_TABLES__"]
+		[flag type=write table="[loop-code]"]
+	[/loop]
+	[perl tables="[cgi mv_data_table]"]
+		my $db = $Db{$CGI->{mv_data_table}} or return;
+		if ($CGI->{ui_clone_id}) {
+			$CGI->{ui_clone_tables} = '__UI_CLONE_TABLES__' || '__UI_ITEM_TABLES__';
+			my $db = $Db{$CGI->{mv_data_table}} or return;
+			return unless $db->record_exists($CGI->{ui_clone_id});
+			my $ref = $db->row_hash($CGI->{ui_clone_id});
+			$CGI->{ $db->config('KEY') } = $CGI->{item_id}
+				if defined $CGI->{item_id};
+			@{$CGI}{ keys %$ref } = values %$ref;
+		}
 		return;
-	[/calc]
+	[/perl]
 [/if]
-[perl tables="[cgi mv_data_table]"]
-my $tab = $CGI->{mv_data_table};
-my $db = $Db{$tab};
-
-if(! ref $db) {
-	$Scratch->{error_message} = "<FONT CLASS=error>Error: no <B>$tab</B> database.</FONT><BR>";
-	$Scratch->{ui_location} = "__UI_BASE__/error";
-	return;
-}
-if ($CGI->{ui_new_item} && $db->config('AUTO_INCREMENT')) {
-	$CGI->{item_id} = '';
-}
-[/perl]
 
-[if scratch ui_location]
-	[bounce href=`delete $Scratch->{ui_location}`]
-[/if]
+[set ui_class]Items[/set]
+[seti page_title][L]Item editor[/L]: [scratch tmp_item_id][/seti]
+[set help_name]edit.item[/set]
+[set icon_name]icon_item.gif[/set]
 
-@_UI_STD_DBEDIT_HEAD_@
+[tmp edit_item_msg]
+[if cgi ui_new_item]
+	[msg]New item[/msg]
+[else]
+	[msg arg.0="<B>[scratch tmp_item_id]</B>"]edit item %s[/msg]
+[/else]
+[/if]
+[/tmp]
 
-[seti page_title]Item editor: [cgi item_id][/seti]
-[seti page_banner]Item editor: edit item <B>[cgi item_id]</B>[/seti]
-[set help_name]edit.item[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[if-mm super]
+[tmp page_banner][page href="__UI_BASE__/db_metaconfig"
+				 form='
+				 ui_table=[cgi mv_data_table]
+				 ui_view=[cgi ui_meta_view]
+				 ui_return_to=__UI_BASE__/item
+				 mv_return_table=[cgi mv_data_table]
+				 start_at=extended.ui_data_fields
+		 '][L]Item editor[/L]</A> [scratch edit_item_msg]
+[/tmp]
+[else]
+[tmp page_banner][L]Item editor[/L]: [msg arg.0="<B>[cgi item_id]</B>"]edit item %s[/msg][/tmp]
+[/else]
+[/if-mm]
 
 @_UI_STD_HEAD_@
 <P>
-[related table=`$Config->{ProductFiles}[0]`]
-@_UI_STD_DBEDIT_TABLE_@
+[table-editor cgi=1 output_map="[scratch ui_style_edit]" ui_style="[scratch ui_style_edit]"]
 
 [if-mm super]
 <A HREF="[area href=admin/flex_editor
 				form='
 					item_id=[cgi item_id]
-					mv_data_table=__UI_PRODUCT_TABLE__
-					page_title=Edit items: [cgi item_id]
+					mv_data_table=__ProductFiles_0__
+					page_title=[L]Edit items[/L]: [cgi item_id]
 					help_name=inventory.edit
 					ui_no_meta_display=1
 					ui_hide_key=1
 					ui_return_to=__UI_BASE__/item
-					icon_name=admin/icon_item.gif
-					']">No meta display</A>
+					icon_name=icon_item.gif
+					']">[L]No meta display[/L]</A>
 [/if-mm]
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 1.12.4.6 $ -->



1.2.4.5   +13 -27    interchange/dist/lib/UI/pages/admin/item_feature.html


rev 1.2.4.5, prev_rev 1.2.4.4
Index: item_feature.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_feature.html,v
retrieving revision 1.2.4.4
retrieving revision 1.2.4.5
diff -u -r1.2.4.4 -r1.2.4.5
--- item_feature.html	27 Nov 2000 01:03:50 -0000	1.2.4.4
+++ item_feature.html	25 Jan 2003 22:21:14 -0000	1.2.4.5
@@ -7,19 +7,21 @@
 		$CGI->{mv_data_table} = 'merchandising';
 	}
 	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = 'sku __UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__ featured blurb_begin blurb_end timed_promotion start_date finish_date';
-		$CGI->{ui_display_only} = '__UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__';
+		$CGI->{ui_data_fields} = 'sku __ProductFiles_0__:__DescriptionField__ featured blurb_begin blurb_end timed_promotion start_date finish_date';
+		$CGI->{ui_display_only} = '__ProductFiles_0__:__DescriptionField__';
 	}
 	if(! $CGI->{ui_break_before}) {
 		$CGI->{ui_break_before} = 'blurb_begin timed_promotion';
 	}
-	my @args = (
-		 '__UI_BASE__/item_edit',
-		 "item_id=$CGI->{item_id}",
-		 "item_id_left=$CGI->{item_id_left}",
-		 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
-	);
-	$CGI->{ui_return_to} = join "\0", @args;
+	if(! $CGI->{ui_return_to}) {
+		my @args = (
+			 '__UI_BASE__/item_edit',
+			 "item_id=$CGI->{item_id}",
+			 "item_id_left=$CGI->{item_id_left}",
+			 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
+		);
+		$CGI->{ui_return_to} = join "\0", @args;
+	}
 	return;
 [/calc]
 [perl tables="merchandising"]
@@ -33,30 +35,14 @@
 	return;
 [/perl]
 
-@_UI_STD_DBEDIT_HEAD_@
-
 [seti page_title]Promotion: [cgi item_id][/seti]
 [seti page_banner]Promotion: edit item <B>[page href="__UI_BASE__/item_edit" form="item_id=[cgi item_id]"][cgi item_id]</A></B>[/seti]
 [set help_name]promotion[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
-
-[if-mm super]
-<A HREF="[area href=admin/flex_editor
-				form='
-					item_id=[cgi item_id]
-					mv_data_table=__UI_PRODUCT_TABLE__
-					page_title=Edit items: [cgi item_id]
-					help_name=inventory.edit
-					ui_no_meta_display=1
-					ui_hide_key=1
-					ui_return_to=admin/item
-					icon_name=admin/icon_item.gif
-					']">No meta display</A>
-[/if-mm]
+[table-editor cgi=1 output-map=1]
 
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->



1.2.4.4   +12 -18    interchange/dist/lib/UI/pages/admin/item_inventory.html


rev 1.2.4.4, prev_rev 1.2.4.3
Index: item_inventory.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_inventory.html,v
retrieving revision 1.2.4.3
retrieving revision 1.2.4.4
diff -u -r1.2.4.3 -r1.2.4.4
--- item_inventory.html	27 Nov 2000 00:58:08 -0000	1.2.4.3
+++ item_inventory.html	25 Jan 2003 22:21:14 -0000	1.2.4.4
@@ -6,45 +6,39 @@
 		$CGI->{ui_hide_key} = 1;
 		$CGI->{mv_data_table} = 'inventory';
 	}
-	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = '__UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__ [db-columns name=inventory]';
-		$CGI->{ui_display_only} = '__UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__';
+	if(! $CGI->{ui_return_to}) {
+		my @args = (
+			 '__UI_BASE__/item_edit',
+			 "item_id=$CGI->{item_id}",
+			 "item_id_left=$CGI->{item_id_left}",
+			 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
+		);
+		$CGI->{ui_return_to} = join "\0", @args;
 	}
-	if(! $CGI->{ui_break_before}) {
-		$CGI->{ui_break_before} = 'account';
-	}
-	my @args = (
-		 '__UI_BASE__/item_edit',
-		 "item_id=$CGI->{item_id}",
-		 "item_id_left=$CGI->{item_id_left}",
-		 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
-	);
-	$CGI->{ui_return_to} = join "\0", @args;
 	return;
 [/calc]
-@_UI_STD_DBEDIT_HEAD_@
 
 [seti page_title]Inventory: [cgi item_id][/seti]
 [seti page_banner]Inventory: edit item <B>[page href="__UI_BASE__/item_edit" form="item_id=[cgi item_id]"][cgi item_id]</A></B>[/seti]
 [set help_name]item.editor[/set]
 [set table_perm]inventory[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
+[table-editor cgi=1 output-map=1]
 
 [if-mm super]
 <A HREF="[area href=admin/flex_editor
 				form='
 					item_id=[cgi item_id]
-					mv_data_table=__UI_PRODUCT_TABLE__
+					mv_data_table=__ProductFiles_0__
 					page_title=Edit items: [cgi item_id]
 					help_name=inventory.edit
 					ui_no_meta_display=1
 					ui_hide_key=1
 					ui_return_to=admin/item
-					icon_name=admin/icon_item.gif
+					icon_name=icon_item.gif
 					']">No meta display</A>
 [/if-mm]
 



1.2.4.4   +37 -30    interchange/dist/lib/UI/pages/admin/item_price.html


rev 1.2.4.4, prev_rev 1.2.4.3
Index: item_price.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_price.html,v
retrieving revision 1.2.4.3
retrieving revision 1.2.4.4
diff -u -r1.2.4.3 -r1.2.4.4
--- item_price.html	27 Nov 2000 00:55:40 -0000	1.2.4.3
+++ item_price.html	25 Jan 2003 22:21:14 -0000	1.2.4.4
@@ -2,50 +2,57 @@
 	[bounce page="__UI_BASE__/item"]
 [/if]
 [calc]
+	if($CGI->{merchandising}) {
+		$Scratch->{mv_logical_page} = 'admin/merchandising';
+		$Scratch->{ui_class} = 'Merchandising';
+	}
+	else {
+		$Scratch->{ui_class} = 'Items';
+	}
 	if(! $CGI->{mv_data_table}) {
 		$CGI->{ui_hide_key} = 1;
 		$CGI->{mv_data_table} = 'pricing';
 	}
 	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = '__UI_PRODUCT_TABLE__:price __UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__ [db-columns name=pricing]';
-		$CGI->{ui_display_only} = '__UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__';
+		@cols = split /\s+/, q{[db-columns name=pricing]};
+		@cols = grep $_ ne 'sku' && $_ ne 'price_group', @cols;
+		my $colstring = join "\n", @cols;
+		$CGI->{ui_data_fields} = qq{
+
+=Base Pricing
+
+price_group
+sku
+__ProductFiles_0__:__DescriptionField__
+__ProductFiles_0__:price
+__ProductFiles_0__:wholesale
+
+=Quantity Pricing
+
+$colstring
+};
+		$CGI->{ui_display_only} = '__ProductFiles_0__:__DescriptionField__';
 	}
-	if(! $CGI->{ui_break_before}) {
-		$CGI->{ui_break_before} = 'price_group q2';
+	if(! $CGI->{ui_return_to}) {
+		my @args = (
+			 '__UI_BASE__/item_edit',
+			 "item_id=$CGI->{item_id}",
+			 "item_id_left=$CGI->{item_id_left}",
+			 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
+		);
+		$CGI->{ui_return_to} = join "\0", @args;
 	}
-	my @args = (
-		 '__UI_BASE__/item_edit',
-		 "item_id=$CGI->{item_id}",
-		 "item_id_left=$CGI->{item_id_left}",
-		 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
-	);
-	$CGI->{ui_return_to} = join "\0", @args;
 	return;
 [/calc]
-@_UI_STD_DBEDIT_HEAD_@
 
-[seti page_title]Pricing: [cgi item_id][/seti]
-[seti page_banner]Pricing: edit item <B>[page href="__UI_BASE__/item_edit" form="item_id=[cgi item_id]"][cgi item_id]</A></B>[/seti]
+[seti page_title][L]Pricing[/L]: [cgi item_id][/seti]
+[seti page_banner][L]Pricing[/L]: [msg arg.0='<B>[page href="__UI_BASE__/item_edit" form="item_id=[cgi item_id]"][cgi item_id]</A></B>']edit item %s[/msg][/seti]
 [set help_name]pricing[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
-
-[if-mm super]
-<A HREF="[area href=admin/flex_editor
-				form='
-					item_id=[cgi item_id]
-					mv_data_table=__UI_PRODUCT_TABLE__
-					page_title=Edit items: [cgi item_id]
-					help_name=inventory.edit
-					ui_no_meta_display=1
-					ui_hide_key=1
-					ui_return_to=admin/item
-					icon_name=admin/icon_item.gif
-					']">No meta display</A>
-[/if-mm]
+[table-editor cgi=1 output-map=1]
 
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->



1.2.4.4   +15 -28    interchange/dist/lib/UI/pages/admin/item_up.html


rev 1.2.4.4, prev_rev 1.2.4.3
Index: item_up.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_up.html,v
retrieving revision 1.2.4.3
retrieving revision 1.2.4.4
diff -u -r1.2.4.3 -r1.2.4.4
--- item_up.html	27 Nov 2000 00:40:03 -0000	1.2.4.3
+++ item_up.html	25 Jan 2003 22:21:14 -0000	1.2.4.4
@@ -7,45 +7,32 @@
 		$CGI->{mv_data_table} = 'merchandising';
 	}
 	if(! $CGI->{ui_data_fields}) {
-		$CGI->{ui_data_fields} = 'sku __UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__ upsell_to';
-		$CGI->{ui_display_only} = '__UI_PRODUCT_TABLE__:__UI_ITEM_DESCRIPTION__';
+		$CGI->{ui_data_fields} = 'sku __ProductFiles_0__:__DescriptionField__ upsell_to';
+		$CGI->{ui_display_only} = '__ProductFiles_0__:__DescriptionField__';
 	}
 	if(! $CGI->{ui_break_before}) {
 		$CGI->{ui_break_before} = 'upsell_to';
 	}
-	my @args = (
-		 '__UI_BASE__/item_edit',
-		 "item_id=$CGI->{item_id}",
-		 "item_id_left=$CGI->{item_id_left}",
-		 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
-	);
-	$CGI->{ui_return_to} = join "\0", @args;
+	if(! $CGI->{ui_return_to}) {
+		my @args = (
+			 '__UI_BASE__/item_edit',
+			 "item_id=$CGI->{item_id}",
+			 "item_id_left=$CGI->{item_id_left}",
+			 "ui_sequence_edit=$CGI->{ui_sequence_edit}",
+		);
+		$CGI->{ui_return_to} = join "\0", @args;
+	}
 	return;
 [/calc]
-@_UI_STD_DBEDIT_HEAD_@
 
-[seti page_title]Upsell: [cgi item_id][/seti]
-[seti page_banner]Upsell: edit item <B>[page href="__UI_BASE__/item_edit" form="item_id=[cgi item_id]"][cgi item_id]</A></B>[/seti]
+[seti page_title][L]Upsell[/L]: [cgi item_id][/seti]
+[seti page_banner][L]Upsell[/L]: [msg arg.0='<B>[page href="__UI_BASE__/item_edit" form="item_id=[cgi item_id]"][cgi item_id]</A></B>']edit item %s[/msg][/seti]
 [set help_name]upsell[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 
 @_UI_STD_HEAD_@
 <P>
-@_UI_STD_DBEDIT_TABLE_@
-
-[if-mm super]
-<A HREF="[area href=admin/flex_editor
-				form='
-					item_id=[cgi item_id]
-					mv_data_table=__UI_PRODUCT_TABLE__
-					page_title=Edit items: [cgi item_id]
-					help_name=inventory.edit
-					ui_no_meta_display=1
-					ui_hide_key=1
-					ui_return_to=admin/item
-					icon_name=admin/icon_item.gif
-					']">No meta display</A>
-[/if-mm]
+[table-editor cgi=1 output-map=1]
 
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->



1.17.4.1  +203 -157  interchange/dist/lib/UI/pages/admin/layout.html


rev 1.17.4.1, prev_rev 1.17
Index: layout.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/layout.html,v
retrieving revision 1.17
retrieving revision 1.17.4.1
diff -u -r1.17 -r1.17.4.1
--- layout.html	2 Oct 2000 12:38:10 -0000	1.17
+++ layout.html	25 Jan 2003 22:21:14 -0000	1.17.4.1
@@ -3,32 +3,22 @@
 [set page_banner]Layout Editor: Organize your site into categories[/set]
 [set page_perm]layout=e[/set]
 [set help_name]layout.edit[/set]
-[set icon_name]admin/icon_pages.gif[/set]
-[seti ui_body_extra][/seti]
+[set icon_name]icon_pages.gif[/set]
+[set ui_body_extra][/set]
 
 @_UI_STD_HEAD_@
-[if scratch ui_message]
-<BLOCKQUOTE>
-<FONT COLOR="__CONTRAST__" SIZE="+1"><B>[scratch ui_message][set ui_message][/set]</B></FONT>
-</BLOCKQUOTE>
-[/if]
-
-[if scratch ui_failure]
-	<FONT COLOR=RED>Failed:
-	[scratch ui_failure][set ui_failure][/set]</FONT><BR>
-[/if]
-
 <!-- ----- BEGIN REAL STUFF ----- -->
-<table __UI_T_PROPERTIES__>
+<table __UI_T_PROPERTIES__ width="90%">
+
+[flag type=write table=area]
+[flag type=write table=cat]
 
 [if cgi newarea]
 <!-- Creating area: 
-[flag type=write table=area]
 [value name=area set="[counter file=etc/area.recordnumber start=1000]" hide=1]
 [data table=area column=name key="[value area]" value="[cgi newarea]"] -->
 [elsif cgi newcat]
 <!-- Creating category: 
-[flag type=write table=cat]
 [value name=cat set="[counter file=etc/cat.recordnumber start=1000]" hide=1]
 [data table=cat column=name key="[value cat]" value="[cgi newcat]"]
 [data table=cat column=sel key="[value cat]" value="[value area]"] -->
@@ -45,13 +35,10 @@
 [/set]
 
 <tr>
-<td [if value area]colspan=3[/if] bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-<tr>
-<td valign=top bgcolor="__UI_C_INTBLOCK__">
+<td valign=top class=rnorm>
 
 <FORM METHOD=GET ACTION="[process]" name="areaform">
+<input type=hidden name=mv_session_id  value="[data session id]">
 <input type=hidden name=ui_window_name value="mainwindow[scratch window_name]">
 <input type=hidden name=mv_todo        value=return>
 <input type=hidden name=mv_nextpage    value="@@MV_PAGE@@">
@@ -64,6 +51,7 @@
 </select>
 <br>
 <select name="area" size=10 onchange="this.form.submit()">
+[calc]$Scratch->{start_sort} = 0; $Scratch->{area_sort} = []; return;[/calc]
 [loop   search="
 			fi=area
 			tf=sel
@@ -80,51 +68,86 @@
 			rf=code,name,sel
 		"
 		option=area ]
-<option value="[loop-code]">[loop-param sel] -- [loop-filter 20][loop-param name][/loop-filter]
+<option value="[loop-code]">[loop-param sel] -- [loop-filter 20][loop-param name][/loop-filter][loop-calc]
+	push @{ $Scratch->{area_sort} }, [
+		q{[loop-code]},
+		sprintf('%03d', ++$Scratch->{start_sort})
+	];
+	return;
+[/loop-calc]
 [/loop]
 </select>
+
+[perl tables=area]
+	my $db = $Db{area} || return;
+	foreach ( @{ $Scratch->{area_sort} } ) {
+		$db->set_field( $_->[0], 'sort', $_->[1] );
+	}
+	delete $Scratch->{start_sort};
+	return;
+[/perl]
 <br>
 
 <small>
-[button text="Section properties" hspace=2 vspace=5 src="@_UI_IMG_@admin/icon_pages.gif" hidetext=1]
+[button text="Section properties" hspace=2 vspace=5 src="icon_pages.gif" hidetext=1]
 [/button]
 
-[button text="Sort section higher" src="@_UI_IMG_@admin/up.gif" hidetext=1]
+[button text="Sort section higher" src="up.gif" hidetext=1]
 	[flag type=write table=area]
 	[perl tables=area]
 		my $db = $Db{area} || return;
-		my $curr = $db->field($CGI->{area}, 'sort');
-		$curr =~ s/^0+//;
-		$curr = 1 if ! $curr || $curr < 0;
-		$curr--;
-		$db->set_field($CGI->{area}, 'sort', sprintf("%02d", $curr));
+		my $arr = delete $Scratch->{area_sort};
+		my $sort;
+
+		foreach (reverse @$arr) {
+			# Swap sort with previous one
+			if ($sort) {
+				$db->set_field($CGI->{area}, 'sort', $_->[1]);
+				$db->set_field($_->[0], 'sort', $sort);
+				last;
+			}
+			# Current: swap with next
+			if ( $CGI->{area} eq $_->[0] ) {
+				$sort = $_->[1];
+			}
+		}
 		return;
 	[/perl]
 [/button]
 
 
-[button text="Sort section lower" src="@_UI_IMG_@admin/down.gif" hidetext=1]
+[button text="Sort section lower" src="down.gif" hidetext=1]
 	[flag type=write table=area]
 	[perl tables=area]
 		my $db = $Db{area} || return;
-		my $curr = $db->field($CGI->{area}, 'sort');
-		$curr =~ s/^0+//;
-		$curr = 0 if ! $curr || $curr < 0;
-		$curr++;
-		$db->set_field($CGI->{area}, 'sort', sprintf("%02d", $curr));
+		my $arr = delete $Scratch->{area_sort};
+		my $sort;
+
+		foreach (@$arr) {
+			# Swap sort with previous one
+			if ($sort) {
+				$db->set_field($CGI->{area}, 'sort', $_->[1]);
+				$db->set_field($_->[0], 'sort', $sort);
+				last;
+			}
+			# Current: swap with next
+			if ( $CGI->{area} eq $_->[0] ) {
+				$sort = $_->[1];
+			}
+		}
 		return;
 	[/perl]
 [/button]
 
-[button text="Create section" src="@_UI_IMG_@admin/plus.gif" hidetext=1]
+[button text="Create section" src="plus.gif" hidetext=1]
 	mv_todo=back
 	newarea=NEW
 [/button]
 
 [button
-	text="Delete section" src="@_UI_IMG_@admin/delete.gif" 
+	text="Delete section" src="delete.gif" 
 	confirm="Are you sure you want to delete this section?"
- hidetext=1]
+	hidetext=1]
 	[tag flag write]area[/tag]
 	[if-mm advanced sitedesign=d]
 		[perl tables="area"]
@@ -155,13 +178,14 @@
 </td>
 
 
-[if value area]
+[if cgi area]
 [then]
-<td valign=top bgcolor="__UI_C_INTBLOCK__">
+<td valign=top class=rnorm>
 
 <B>Contains:</B><BR>
 
 <select name="cat" size=10 [if !value cat]onChange="this.form.submit()"[/if]>
+[calc]$Scratch->{start_sort} = 0; $Scratch->{cat_sort} = []; return;[/calc]
 [loop   search="
 			fi=cat
 			st=db
@@ -178,45 +202,81 @@
 
 			rf=code,name,sort
 			" option=cat]
-<OPTION VALUE="[loop-code]">[loop-param name]
+<OPTION VALUE="[loop-code]">[loop-param name][loop-calc]
+	push @{ $Scratch->{cat_sort} }, [
+		q/[loop-code]/,
+		sprintf('%04d', ++$Scratch->{start_sort})
+	];
+	return;
+[/loop-calc]
 [/loop]
 </select>
+
+[perl tables=cat]
+	my $db = $Db{cat} || return;
+	foreach ( @{ $Scratch->{cat_sort} } ) {
+		$db->set_field( $_->[0], 'sort', $_->[1] );
+	}
+	delete $Scratch->{start_sort};
+	return;
+[/perl]
 <br>
+
 <small>
-[button text="Category properties" hspace=2 vspace=5 hidetext=1 src="@_UI_IMG_@admin/icon_pages.gif"][/button]
+[button text="Category properties" hspace=2 vspace=5 hidetext=1 src="icon_pages.gif"][/button]
 
-[button text="Sort category higher" hidetext=1 src="@_UI_IMG_@admin/up.gif"]
+[button text="Sort category higher" hidetext=1 src="up.gif"]
 	[flag type=write table=cat]
 	[perl tables=cat]
 		my $db = $Db{cat} || return;
-		my $curr = $db->field($CGI->{cat}, 'sort');
-		$curr =~ s/^0+//;
-		$curr = 1 if ! $curr || $curr < 0;
-		$curr--;
-		$db->set_field($CGI->{cat}, 'sort', sprintf("%02d", $curr));
+		my $arr = delete $Scratch->{cat_sort};
+		my $sort;
+
+		foreach (reverse @$arr) {
+			# Swap sort with previous one
+			if ($sort) {
+				$db->set_field($CGI->{cat}, 'sort', $_->[1]);
+				$db->set_field($_->[0], 'sort', $sort);
+				last;
+			}
+			# Current: swap with next
+			if ( $CGI->{cat} eq $_->[0] ) {
+				$sort = $_->[1];
+			}
+		}
 		return;
 	[/perl]
 [/button]
 
-[button text="Sort category lower" hidetext=1 src="@_UI_IMG_@admin/down.gif"]
+[button text="Sort category lower" hidetext=1 src="down.gif"]
 	[flag type=write table=cat]
 	[perl tables=cat]
 		my $db = $Db{cat} || return;
-		my $curr = $db->field($CGI->{cat}, 'sort');
-		$curr =~ s/^0+//;
-		$curr = 0 if ! $curr || $curr < 0;
-		$curr++;
-		$db->set_field($CGI->{cat}, 'sort', sprintf("%02d", $curr));
+		my $arr = delete $Scratch->{cat_sort};
+		my $sort;
+
+		foreach (@$arr) {
+			# Swap sort with previous one
+			if ($sort) {
+				$db->set_field($CGI->{cat}, 'sort', $_->[1]);
+				$db->set_field($_->[0], 'sort', $sort);
+				last;
+			}
+			# Current: swap with next
+			if ( $CGI->{cat} eq $_->[0] ) {
+				$sort = $_->[1];
+			}
+		}
 		return;
 	[/perl]
 [/button]
 
-[button text="Create category" hidetext=1 src="@_UI_IMG_@admin/plus.gif"]
+[button text="Create category" hidetext=1 src="plus.gif"]
 	mv_todo=back
 	newcat=NEW
 [/button]
 
-[button text="Delete category" hidetext=1 src="@_UI_IMG_@admin/delete.gif"
+[button text="Delete category" hidetext=1 src="delete.gif"
 	 confirm="Are you sure you want to delete this category?"
 ]
 	[tag flag write]cat[/tag]
@@ -248,7 +308,7 @@
 
 </td>
 
-<td bgcolor="__UI_C_INTBLOCK__" valign=top>
+<td class=rnorm valign=top>
 
 
 <table>
@@ -258,7 +318,7 @@
 [set name="<--"]
 [/set]
 
-[button text="Move category left" hidetext=1 src="@_UI_IMG_@admin/left.gif"]
+[button text="Move category left" hidetext=1 src="left.gif"]
 [if-mm advanced layout=e]
 [flag type=write table=cat]
 [perl tables=cat]
@@ -285,7 +345,7 @@
 [/if-mm]
 [/button]
 
-[button text="Move category right" hidetext=1 src="@_UI_IMG_@admin/right.gif"]
+[button text="Move category right" hidetext=1 src="right.gif"]
 [if-mm advanced layout=e]
 [flag type=write table=cat]
 [perl tables=cat]
@@ -338,14 +398,14 @@
 </td>
 </tr>
 </table>
-</form>
+</FORM>
 </td>
 </tr>
 </table>
 
-<table __UI_T_PROPERTIES__>
+<table __UI_T_PROPERTIES__ width="90%">
 <tr>
-<td valign=top bgcolor="__UI_C_INTBLOCK__">
+<td valign=top class=rnorm>
 <!--- BEGIN SECTION PROPERTIES -->
 
 [value name=mv_data_table set="area" hide=1]
@@ -383,7 +443,8 @@
 
 [loop list="[value area]" prefix=table]
 <FORM METHOD=POST name=layout_area_properties ACTION="[area ui]">
-<INPUT TYPE=hidden NAME=mv_doit VALUE="set">
+<input type=hidden name=mv_session_id  value="[data session id]">
+<INPUT TYPE=hidden NAME=mv_todo VALUE="set">
 <INPUT TYPE=hidden NAME=from_section VALUE=1>
 <INPUT TYPE=hidden NAME=mv_click VALUE="process_ui_area">
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="@@MV_PAGE@@">
@@ -393,27 +454,27 @@
 <INPUT TYPE=hidden name=mv_data_fields value="code sel which_page link_type name display_type">
 <INPUT TYPE=hidden NAME=code VALUE="[table-code]">
 
-<table __UI_T_PROPERTIES__>
+<table __UI_T_PROPERTIES__ width="90%">
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__ colspan=2><font color="#ffffff"><img src="@_UI_IMG_@admin/icon_pages.gif">&nbsp;Section Properties</td>
+<td class=rmarq colspan=2><img src="icon_pages.gif">&nbsp;Section Properties</td>
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Name</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<INPUT SIZE=40 NAME=name Value="[table-data area name]">
 	</td>
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Page&nbsp;class</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<input type=hidden name="ui_filter:which_page" value="null_to_space">
 	<table> <tr> <td>
 		<small>
@@ -450,10 +511,10 @@
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Page area</b>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<input type=hidden name="ui_filter:sel" value="nullselect">
 	<table><tr><td>
@@ -482,16 +543,16 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCK__><HR></td>
+<td colspan=2 class=rnorm><HR></td>
 </tr>
 
 [set ui_area_type][table-data area link_type][/set]
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Link type</b>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		[display table=area column=link_type key="[value area]" js=|onChange="this.form.submit()"|]
 	</td>
 </tr>
@@ -499,10 +560,10 @@
 [if scratch ui_area_type eq external]
 <INPUT TYPE=hidden NAME=mv_data_fields value="url">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>External</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<INPUT SIZE=40 NAME=url value="[table-data area url]">
 	</td>
@@ -510,10 +571,10 @@
 [elsif scratch ui_area_type eq internal]
 <INPUT TYPE=hidden NAME=mv_data_fields value="url">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Interchange page</B></small>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<input type=hidden name="ui_filter:url" value="null_to_space">
 	<select name=url>
@@ -535,10 +596,10 @@
 	</td>
 </tr>
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Parameters</B></small>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<INPUT NAME=url SIZE=40 VALUE="[calc]$ui_arg[/calc]">
 	</td>
@@ -551,7 +612,7 @@
 	return;
 [/calc]
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small><b>Table
 	</td>
 	<td>
@@ -563,20 +624,20 @@
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small><b>field=column pairs
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small>
 		<TEXTAREA NAME=selector COLS=30 ROWS=3>[table-data area selector]</TEXTAREA>
 	</td>
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small><b>Results page
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small>
 		<select name=page>
 		[calc]
@@ -600,12 +661,12 @@
 [elsif scratch ui_area_type eq complex]
 
 <INPUT TYPE=hidden NAME=mv_data_fields value="search">
-<INPUT TYPE=hidden NAME=ui_target value="mainwindow[scratch win]">
 <INPUT TYPE=hidden NAME=ui_searchblob value="">
+<INPUT TYPE=hidden NAME=ui_target value="mainwindow[scratch win]">
 <INPUT TYPE=hidden NAME=ui_return_to value="@@MV_PAGE@@">
 <INPUT TYPE=hidden NAME=ui_return_to value="area=[table-code]">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	[set Create]
 	mv_todo=back
 	mv_nextpage=__UI_BASE__/search_wizard
@@ -614,12 +675,10 @@
 						name=mv_click
 						value="Create"
 						onClick="
-							this.form.ui_target.value=window.name;
 							this.form.ui_searchblob.value=this.form.search.value;
-							this.form.target='search_prop';
 						">&nbsp;<small><INPUT TYPE=button onClick="this.form.search.value=''" VALUE="clear search">
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 		[calc]
 		my $n = 4;
@@ -645,16 +704,16 @@
 [/if]
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCK__><HR></td>
+<td colspan=2 class=rnorm><HR></td>
 </tr>
 
 [set ui_area_display][table-data area display_type][/set]
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Display type</b>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 		[display table=area column=display_type key="[value area]" js=|onChange="this.form.submit()"|]
 	</td>
@@ -665,20 +724,20 @@
 <INPUT TYPE=hidden NAME=mv_data_fields value="image_prop">
 <input type=hidden name="ui_filter:image" value="nullselect">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>Image</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<small>
 	[display table=area column=image key="[value area]" js=|onChange="this.form.submit()"|]
 	</td>
 </tr>
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>Image properties</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 		<input name="image_prop" size=30 VALUE="[calc]
 		$image_prop = q{[table-data area image_prop]};
@@ -689,11 +748,12 @@
 </tr>
 [/if]
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>Link template</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
+	<input type=hidden name=mv_data_fields value=link_template>
 	[display table=area column=link_template key="[value area]"]
 	</td>
 </tr>
@@ -701,14 +761,14 @@
 
 [button text="Change area"][/button]
 
-</form>
+</FORM>
 [/loop]
 
 </td>
 <!--- END SECTION PROPERTIES -->
 
 <!--- BEGIN CATEGORY PROPERTIES -->
-<td valign=top bgcolor="__UI_C_INTBLOCK__" width=50%">
+<td valign=top class=rnorm width="50%">
 
 [value name=mv_data_table set="cat" hide=1]
 
@@ -743,8 +803,9 @@
 [/set]
 
 [loop list="[either][value cat][or]NEW[/either]" prefix=table]
-<FORM METHOD=POST ACTION="[area ui]">
-<INPUT TYPE=hidden NAME=mv_doit VALUE="set">
+<FORM METHOD=GET ACTION="[area ui]" name=layout_cat_properties>
+<input type=hidden name=mv_session_id  value="[data session id]">
+<INPUT TYPE=hidden NAME=mv_todo VALUE="set">
 <INPUT TYPE=hidden NAME=from_category VALUE=1>
 <INPUT TYPE=hidden NAME=mv_click VALUE="process_ui_cat">
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="@@MV_PAGE@@">
@@ -754,16 +815,17 @@
 <INPUT TYPE=hidden NAME=mv_data_fields VALUE="code link_type name display_type">
 <INPUT TYPE=hidden NAME=code VALUE="[table-code]">
 
-<table __UI_T_PROPERTIES__>
+<table __UI_T_PROPERTIES__ width="90%">
 
-<td bgcolor=__UI_C_TOPBLOCKBAR__ colspan=2><font color="#ffffff"><img src="@_UI_IMG_@admin/icon_pages.gif">&nbsp;Category properties</td>
+<tr>
+<td class=rmarq colspan=2><img src="icon_pages.gif">&nbsp;Category properties</td>
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Name</B></small>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<INPUT SIZE=40 NAME=name Value="[table-data cat name]">
 	</td>
@@ -772,10 +834,10 @@
 [set ui_cat_type][table-data cat link_type][/set]
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Link type</b>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		[display table=cat column=link_type key="[value cat]" js=|onChange="this.form.submit()"|]
 	</td>
 </tr>
@@ -784,10 +846,10 @@
 [if scratch ui_cat_type eq external]
 <INPUT TYPE=hidden NAME=mv_data_fields value="url">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>External</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<INPUT SIZE=40 NAME=url value="[table-data cat url]">
 	</td>
@@ -795,10 +857,10 @@
 [elsif scratch ui_cat_type eq internal]
 <INPUT TYPE=hidden NAME=mv_data_fields value="url">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Interchange page</B></small>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<input type=hidden name="ui_filter:url" value="null_to_space">
 	<select name=url>
@@ -820,10 +882,10 @@
 	</td>
 </tr>
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Parameters</B></small>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<INPUT NAME=url SIZE=40 VALUE="[calc]$ui_arg[/calc]">
 	</td>
@@ -831,10 +893,10 @@
 [/elsif]
 [elsif scratch ui_cat_type eq explode]
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>Explode file</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<select name=explode>
 	[calc]
@@ -862,7 +924,7 @@
 	return;
 [/calc]
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small><b>Table
 	</td>
 	<td>
@@ -874,20 +936,20 @@
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small><b>field=column pairs
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small>
 		<TEXTAREA NAME=selector COLS=30 ROWS=3>[table-data cat selector]</TEXTAREA>
 	</td>
 </tr>
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small><b>Results page
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 		<small>
 		<select name=page>
 		[calc]
@@ -914,9 +976,10 @@
 <INPUT TYPE=hidden NAME=ui_target value="mainwindow[scratch win]">
 <INPUT TYPE=hidden NAME=ui_searchblob value="">
 <INPUT TYPE=hidden NAME=ui_return_to value="@@MV_PAGE@@">
+<INPUT TYPE=hidden NAME=ui_return_to value="area=[cgi area]">
 <INPUT TYPE=hidden NAME=ui_return_to value="cat=[table-code]">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	[set Create]
 	mv_todo=back
 	mv_nextpage=__UI_BASE__/search_wizard
@@ -925,12 +988,10 @@
 						name=mv_click
 						value="Create"
 						onClick="
-							this.form.ui_target.value=window.name;
 							this.form.ui_searchblob.value=this.form.search.value;
-							this.form.target='search_prop';
 						">&nbsp;<small><INPUT TYPE=button onClick="this.form.search.value=''" VALUE="clear search">
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 		[calc]
 		my $n = 4;
@@ -958,21 +1019,21 @@
 
 [if scratch needs_banner_info]
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<INPUT TYPE=hidden NAME=mv_data_fields value="banner_text">
 	<INPUT TYPE=hidden NAME=mv_data_fields value="banner_image">
 	<small><b>Banner Text
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<INPUT SIZE=40 NAME=banner_text value="[table-data cat banner_text]">
 	</td>
 </tr>
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><b>Banner Image
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 		<INPUT SIZE=40 NAME=banner_img value="[table-data cat banner_img]">
 	</td>
@@ -980,16 +1041,16 @@
 [/if]
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCK__><HR></td>
+<td colspan=2 class=rnorm><HR></td>
 </tr>
 
 [set ui_cat_display][table-data cat display_type][/set]
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small><B>Display type</b>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 		[display table=cat column=display_type key="[value cat]" js=|onChange="this.form.submit()"|]
 	</td>
@@ -1000,20 +1061,20 @@
 <INPUT TYPE=hidden NAME=mv_data_fields value="image_prop">
 <input type=hidden name="ui_filter:image" value="nullselect">
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>Image</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 	<small>
 	[display table=cat column=image key="[value cat]" js=|onChange="this.form.submit()"|]
 	</td>
 </tr>
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>Image properties</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
 		<input name="image_prop" size=30 VALUE="[calc]
 		$image_prop = q{[table-data cat image_prop]};
@@ -1025,11 +1086,12 @@
 [/if]
 
 <tr>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<B>Link template</B>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<small>
+	<input type=hidden name=mv_data_fields value=link_template>
 	[display table=cat column=link_template key="[value cat]"]
 	</td>
 </tr>
@@ -1041,7 +1103,7 @@
 [button text="Change category"]
 [/button]
 
-</form>
+</FORM>
 [/loop]
 
 </body>
@@ -1050,33 +1112,17 @@
 <!--- END CATEGORY PROPERTIES -->
 </tr>
 
-<tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-<tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
 [/then]
 [else]
 <!-- wait for them to select a category first -->
 </tr>
 
-<tr>
-<td [if value area]colspan=2[/if] bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
 [/else]
 [/if]
 
 </table>
 
 <BR>
+
 @_UI_STD_FOOTER_@
 <!-- page: @@MV_PAGE@@ -->
-
-
-
-
-
-



1.15.2.6  +49 -12    interchange/dist/lib/UI/pages/admin/login.html


rev 1.15.2.6, prev_rev 1.15.2.5
Index: login.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/login.html,v
retrieving revision 1.15.2.5
retrieving revision 1.15.2.6
diff -u -r1.15.2.5 -r1.15.2.6
--- login.html	9 Feb 2001 20:10:41 -0000	1.15.2.5
+++ login.html	25 Jan 2003 22:21:14 -0000	1.15.2.6
@@ -1,8 +1,21 @@
+[if session logged_in]
+	[if session su]
+		[su exit=1]
+		[calc]delete $Session->{su}; return; [/calc]
+		[bounce page="__UI_BASE__/index"]
+	[else]
+	[userdb function=logout clear=1 hide=1]
+	[/else]
+	[/if]
+[/if]
+[if !global Windows]
+[index table=ichelp export_only=1]
+[/if]
 [set mv_no_count][/set]
+[set mv_no_session_id][/set]
 [set no_login_required]1[/set]
-[set ui_class]None[/set]
-[set page_title]Welcome to Interchange[/set]
-[set page_banner]&nbsp;[/set]
+[set ui_class]Login[/set]
+[set page_title]Interchange: Log in to Administration[/set]
 [set help_name]logout.main[/set]
 @_UI_STD_HEAD_@
 
@@ -11,8 +24,12 @@
 <div align=center>
 <table width="60%" border="0" cellspacing="0" cellpadding="0" height="200">
 <tr>
-<td bgcolor="#EEEEEE" width="700"> <font size="3"><b><font face="Verdana, Arial, Helvetica, sans-serif" color="#000066">&nbsp;&nbsp;</font></b></font> 
-<table width="250" border="1" cellspacing="0" cellpadding="0" bordercolorlight="#6699FF" bordercolordark="#6699FF" align="center">
+<td valign=top style="
+			border: 2px solid #996633;
+			background-color: #EEEEEE;
+		"
+width="700"> <font size="3"><b><font face="Verdana, Arial, Helvetica, sans-serif" color="#000066">&nbsp;&nbsp;</font></b></font> 
+<table width="250" border="1" cellspacing="0" cellpadding="0" align="center">
 <tr>
 <td>
 <table width="250" border="0" cellspacing="0" cellpadding="0" align="center" bgcolor="#FFFFFF">
@@ -20,13 +37,11 @@
 <FONT COLOR=__CONTRAST__>[scratch ui_error]</FONT>
 [set ui_error][/set]
 [/if]
-<!-- logout: [if session logged_in]
-[userdb logout]
-[/if] -->
 
 <FORM ACTION="[process]" METHOD=POST>
 <INPUT TYPE=hidden NAME=mv_click VALUE=MMLogin>
-<INPUT TYPE=hidden NAME=mv_nextpage VALUE="@@MV_PAGE@@">
+<INPUT TYPE=hidden NAME=mv_nextpage VALUE="[either][cgi destination][or]__UI_BASE__/index[/either]">
+<INPUT TYPE=hidden NAME=destination VALUE="[cgi destination]">
 <INPUT TYPE=hidden NAME=mv_doit  VALUE=return>
 
 [if session failure]
@@ -63,8 +78,8 @@
 <H1>Admin interface will not work properly.</H1>
 Please install needed Perl modules:
 <small>
-<blockquote>
-	<FONT COLOR="__UI_C_CONTRAST__">$imp</FONT>
+<blockquote class=cerror>
+	$imp
 </blockquote>
 <blockquote>
 	$minor
@@ -97,9 +112,31 @@
 <div align="right"><font size="2"><b><font face="Verdana, Arial, Helvetica, sans-serif" color="#000066">[L]Password[/L]</font><font face="Verdana, Arial, Helvetica, sans-serif">&nbsp;&nbsp;</font></b></font></div>
 </td>
 <td> 
-<INPUT TYPE=password NAME=mv_password VALUE="" SIZE=15 onChange="this.form.submit()">
+<INPUT TYPE=password NAME=mv_password VALUE="" SIZE=15
+[if !session browser =~ /msie.*mac/i]
+onChange="this.form.submit()"
+[/if]
+>
 </td>
 </tr>
+[value name=currlocale set="[either][getlocale][or]en_US[/either]" hide=1]
+[comment] UI_LOCALE definition in ui.cfg, make empty to remove box [/comment]
+[loop acclist=1 option=currlocale list="[version extended=1 global_locale_options=1]"]
+[on-match]
+<tr> 
+<td> 
+<div align="right"><font size="2"><b><font face="Verdana, Arial, Helvetica, sans-serif" color="#000066">[L]Language[/L]</font><font face="Verdana, Arial, Helvetica, sans-serif">&nbsp;&nbsp;</font></b></font></div>
+</td>
+<td> 
+	<select name="ui_locale">
+[/on-match]
+		[list]<option value=[loop-code]>[loop-param label]
+		[/list]
+[on-match]</select>
+</td>
+</tr>[/on-match]
+[/loop]
+
 <tr> 
 <td>&nbsp;</td>
 <td> 



1.5.4.5   +65 -46    interchange/dist/lib/UI/pages/admin/merchandising.html


rev 1.5.4.5, prev_rev 1.5.4.4
Index: merchandising.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/merchandising.html,v
retrieving revision 1.5.4.4
retrieving revision 1.5.4.5
diff -u -r1.5.4.4 -r1.5.4.5
--- merchandising.html	27 Oct 2000 09:28:44 -0000	1.5.4.4
+++ merchandising.html	25 Jan 2003 22:21:14 -0000	1.5.4.5
@@ -11,22 +11,15 @@
 [/comment]
 
 [set ui_class]Merchandising[/set]
-[set page_title]Merchandising Editor[/set]
+[set page_title][L]Merchandising Editor[/L][/set]
 [set table_perm]1[/set]
 [set help_name]merchandising[/set]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 @_UI_STD_HEAD_@
 
 
 <!-- ----- BEGIN REAL STUFF ----- -->
-[if scratch ui_message]
-<BLOCKQUOTE>
-	[scratch ui_message]
-	[set ui_message][/set]
-</BLOCKQUOTE>
-<p>
-&nbsp;
-[/if]
+
 [flag type=write table=merchandising]
 [perl tables="merchandising __UI_META_TABLE__"]
 	my $db = $Db{merchandising};
@@ -55,13 +48,28 @@
 	return;
 [/perl]
 
+[output name=search_box]
 <FORM ACTION="[area @@MV_PAGE@@]">
 <INPUT NAME=ui_text_qualification>
-<INPUT TYPE=submit VALUE="Limit with search">
+<INPUT TYPE=submit VALUE="[L]Limit with search[/L]">
 </FORM>
+
+
+[output name=""]
+
 [if cgi ui_text_qualification]
-<H3>Entries containing "[cgi ui_text_qualification]"</H3>
+	[calc]
+		return if $CGI->{mv_like_spec};
+		$Scratch->{page_banner} ||= $Scratch->{page_title};
+		$Scratch->{page_banner} .= errmsg(
+																'-- entries containing "%s"',
+																$CGI->{ui_text_qualification},
+																);
+		return;
+	[/calc]
 [/if]
+
+
 [search-region more=1 arg="
 		[if cgi ui_text_qualification]
 		se=[cgi ui_text_qualification]
@@ -92,60 +100,71 @@
 	}
 	return;
 [/calc]
-<TABLE border=0 CELLSPACING=0 width="90%">
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<TR BGCOLOR="__UI_C_TITLEBARBG__">
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+<tr class=rhead>
+<td align=left>[page href=@@MV_PAGE@@ extra=rhead form=`
 	return "ui_sort_field=sku\n" . sortrev('sku');
-	`]SKU</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">[page href=@@MV_PAGE@@ form=`
+	`][L]SKU[/L]</td>
+<td align=left>[page href=@@MV_PAGE@@ extra=rhead form=`
 	return "ui_sort_field=description\n" . sortrev('description');
-	`]Description</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Qty pricing</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Up-sell</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Cross-sell</TH>
-<TH ALIGN=CENTER><FONT COLOR="__UI_C_TITLEBARTXT__">Promotion</TH>
-<TH><FONT COLOR="__UI_C_TITLEBARTXT__">&nbsp;</TH>
+	`][L]Description[/L]</td>
+<td align=center>[L]Qty pricing[/L]</td>
+<td align=center>[L]Up-sell[/L]</td>
+<td align=center>[L]Cross-sell[/L]</td>
+<td align=center>[L]Promotion[/L]</td>
+<td>&nbsp;</td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=7></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=7></td></tr>
 [/on-match]
 [search-list]
-<TR [item-alternate 2]BGCOLOR="__UI_T_ROW_EVEN__"[else]BGCOLOR="__UI_T_ROW_ODD__"[/else][/item-alternate]>
-<TD>[page href=__UI_BASE__/item_edit form="item_id=[item-code]"][item-code]</A></TD>
-<TD>[filter 30][item-description][/filter]</TD>
-<TD ALIGN=CENTER>[page href=__UI_BASE__/item_price form="
+<tr [item-alternate 2]class=rownorm[else]class=rowalt[/else][/item-alternate]>
+<td>[page href=__UI_BASE__/item_edit
+			form="
+				ui_return_to=@@MV_PAGE@@
+				item_id=[item-code]
+			"][item-code]</A></td>
+<td>[filter 30][item-description][/filter]</td>
+<td align=center>[page href=__UI_BASE__/item_price form="
+	ui_return_to=@@MV_PAGE@@
+	merchandising=1
 	item_id=[item-code]
-"][if-item-data pricing sku]Yes[else]No[/else][/if-item-data]</A>
-</TD>
-<TD ALIGN=CENTER>[page href=__UI_BASE__/item_up form="
+"][if-item-data pricing sku][L]Yes[/L][else][L]No[/L][/else][/if-item-data]</A>
+</td>
+<td align=center>[page href=__UI_BASE__/item_up form="
+	ui_return_to=@@MV_PAGE@@
+	merchandising=1
 	item_id=[item-code]
-"][if-item-data merchandising upsell_to]Yes[else]No[/else][/if-item-data]</a>
-</TD>
-<TD ALIGN=CENTER>[page href=__UI_BASE__/item_cross form="
+"][if-item-data merchandising upsell_to][L]Yes[/L][else][L]No[/L][/else][/if-item-data]</a>
+</td>
+<td align=center>[page href=__UI_BASE__/item_cross form="
+	ui_return_to=@@MV_PAGE@@
+	merchandising=1
 	item_id=[item-code]
-"][if-item-data merchandising cross_sell]Yes[else]No[/else][/if-item-data]</a>
-</TD>
-<TD ALIGN=CENTER>[page href=__UI_BASE__/item_feature form="item_id=[item-code]"][if-item-data merchandising featured][item-exec do_timed][item-code][/item-exec][display table=merchandising column=featured type=display key="[item-code]"][else]none[/else][/if-item-data]</a></td>
-<TD ALIGN=CENTER>[if-item-data merchandising timed_promotion]<font size=1>[item-exec show_exp][item-code][/item-exec]</font>[else]&nbsp;[/else][/if-item-data]
-</TD>
+"][if-item-data merchandising cross_sell][L]Yes[/L][else][L]No[/L][/else][/if-item-data]</a>
+</td>
+<td align=center>[page href=__UI_BASE__/item_feature
+		form="
+			ui_return_to=@@MV_PAGE@@
+			merchandising=1
+			item_id=[item-code]
+		"][if-item-data merchandising featured][item-exec do_timed][item-code][/item-exec][display table=merchandising column=featured type=display key="[item-code]"][else][L]none[/L][/else][/if-item-data]</a></td>
+<td align=center>[if-item-data merchandising timed_promotion]<font size=1>[item-exec show_exp][item-code][/item-exec]</font>[else]&nbsp;[/else][/if-item-data]
+</td>
 </tr>
 [/search-list]
 [no-match]
 <tr>
 <td colspan=6 align=left>
 <br>
-<B>Nothing matched.</B>
+<B>[L]Nothing matched.[/L]</B>
 <br><br>
 </td>
 </tr>
 [/no-match]
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=8><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 [more-list]
-<tr>
+<tr class=rownorm>
 <td colspan=6 align=center>
-More items: [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
+[L]More items[/L]: [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
 </td>
 </tr>
 [/more-list]



1.1.2.3   +76 -11    interchange/dist/lib/UI/pages/admin/meta_editor.html


rev 1.1.2.3, prev_rev 1.1.2.2
Index: meta_editor.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/meta_editor.html,v
retrieving revision 1.1.2.2
retrieving revision 1.1.2.3
diff -u -r1.1.2.2 -r1.1.2.3
--- meta_editor.html	26 Oct 2000 10:52:33 -0000	1.1.2.2
+++ meta_editor.html	25 Jan 2003 22:21:14 -0000	1.1.2.3
@@ -1,18 +1,38 @@
+[if cgi fieldmeta]
+	[cgi name=item_id set="[cgi fieldmeta]"]
+[/if]
 [if !cgi item_id]
 	[bounce page="__UI_BASE__/gentable"]
 [/if]
 [calc]
 	my $location = $CGI->{item_id};
 	my @parts = split /::/, $location;
-	($m_table, $m_col, $m_key) = @parts;
-	my $string = "Meta field edit: ";
-	$string .= "table=$m_table column=$m_col";
-	$string .= " key=$m_key" if $m_key;
-	$Scratch->{page_title} = $string;
+	if($Config->{Database}{$parts[0]}) {
+		($m_table, $m_col, $m_key) = @parts;
+	}
+	else {
+		($m_view, $m_table, $m_col, $m_key) = @parts;
+	}
+	my @frags;
+	push(@frags,errmsg('Meta field edit') . ':');
+    push(@frags,errmsg('view=%s', $m_view)) if $m_view;
+    push(@frags,errmsg('table=%s column=%s', $m_table, $m_col));
+	push(@frags,errmsg('key=%s', $m_key)) if $m_key;
+	$Scratch->{page_title} = join(' ',@frags);
 
-	$string = <<EOF;
+	my $string = <<EOF;
 	<B>Meta information edit&nbsp;&nbsp;&nbsp;</b><BR>
 	<table>
+EOF
+
+	$string .= <<EOF if $m_view;
+	<tr>
+	<td align=right>view:</td>
+	<td><B>$m_view</b></td>
+	</tr>
+EOF
+
+	$string .= <<EOF;
 	<tr>
 	<td align=right>table:</td>
 	<td><B>$m_table</b></td>
@@ -39,13 +59,58 @@
 	}
 	return;
 [/calc]
-@_UI_STD_DBEDIT_HEAD_@
 
-[set ui_class]Admin[/set]
+[set ui_class]Tables[/set]
 [set help_name]meta.edit[/set]
-[set icon_name][/set]
+[set icon_name]icon_config.gif[/set]
 
 @_UI_STD_HEAD_@
-@_UI_STD_DBEDIT_TABLE_@
+
+[table-editor
+	item_id="[cgi item_id]"
+	table="[cgi mv_data_table]"
+	no-table-meta=1
+	no-meta=1
+	ui_data_fields="
+		=Typical
+
+		code
+		label
+		type
+		filter
+		width
+		height
+		options
+
+	   =Help
+
+	   help
+	   help_url
+
+	   =Database lookup
+
+	   lookup
+	   field
+	   db
+	   lookup_query
+	   lookup_exclude
+
+	   =Advanced
+
+	   outboard
+	   pre_filter
+	   prepend
+	   append
+
+	   =Extended
+
+	   extended
+	"
+	widget.extended="textarea_5_50"
+	ui_style=1
+	output_map=1
+	tabbed=1
+	][/table-editor]
+
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 1.1.2.3 $ -->



1.19.4.5  +347 -192  interchange/dist/lib/UI/pages/admin/order.html


rev 1.19.4.5, prev_rev 1.19.4.4
Index: order.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/order.html,v
retrieving revision 1.19.4.4
retrieving revision 1.19.4.5
diff -u -r1.19.4.4 -r1.19.4.5
--- order.html	5 Nov 2000 16:45:57 -0000	1.19.4.4
+++ order.html	25 Jan 2003 22:21:14 -0000	1.19.4.5
@@ -3,7 +3,7 @@
 		delete $Values->{showpending};
 		$Values->{showarchive} = 1;
 		$Scratch->{archive_sense} = 'eq';
-		$Scratch->{archive_img} = 'admin/left.gif';
+		$Scratch->{archive_img} = 'left.gif';
 		$Scratch->{archive_nm} = 'unarchive';
 		$Scratch->{archive_label} = 'archived';
 	}
@@ -11,7 +11,7 @@
 		delete $Values->{showarchive};
 		$Values->{showpending} = 1;
 		$Scratch->{archive_sense} = 'ne';
-		$Scratch->{archive_img} = 'admin/right.gif';
+		$Scratch->{archive_img} = 'right.gif';
 		$Scratch->{archive_nm} = 'archive';
 		$Scratch->{archive_label} = 'pending';
 	}
@@ -19,178 +19,188 @@
 		delete $Values->{showarchive};
 		$Values->{showpending} = 1;
 		$Scratch->{archive_sense} = 'ne';
-		$Scratch->{archive_img} = 'admin/right.gif';
+		$Scratch->{archive_img} = 'right.gif';
 		$Scratch->{archive_nm} = 'archive';
 		$Scratch->{archive_label} = 'pending';
 	}
+	else {
+		$CGI->{showpending} = $Values->{showpending};
+		$CGI->{showarchive} = $Values->{showarchive};
+	}
+	if($CGI->{checked_status}) {
+		$Values->{checked_status} = $CGI->{checked_status};
+	}
+	else {
+		$Values->{checked_status} ||= '__UI_SHIPPED_STATUS__';
+	}
 	return;
 [/calc]
+[set icon_name]icon_orders.gif[/set]
+[seti page_title]
+	[if value showarchive]
+	[L]Orders[/L]: [L]Archived Orders[/L]
+	[set help_name]order.main.archived[/set]
+	[else]
+	[L]Orders[/L]: [L]Pending Orders[/L]
+	[set help_name]order.main.pending[/set]
+	[/else]
+	[/if]
+[/seti]
+[set ui_class]Orders[/set]
+[tmp page_perm]order=l[/tmp]
+
+[perl tables="[cgi mv_data_table] [scratch extra_tables] __UI_META_TABLE__"]
+	delete $Scratch->{ui_location};
+	my $dest = $CGI->{ui_sequence_destination} || '__UI_BASE__/order_status';
+	if($CGI->{ui_sequence_edit}) {
+		my $doit;
+		$CGI->{item_id_left} =~ s/-_NULL_-/\0/g;
+		$CGI->{item_id_left} =~ s/\0+/,/g;
+		$CGI->{item_id_left} =~ s/,+/,/g;
+		if($CGI->{item_id_left} =~ s/^(.*?),//) {
+			$CGI->{item_id} = $1;
+			$doit = 1;
+		}
+		elsif ($CGI->{item_id_left}) {
+			$CGI->{item_id} = delete $CGI->{item_id_left};
+			delete $CGI->{ui_sequence_edit};
+			$doit = 1;
+		}
+		else {
+			delete $CGI->{item_id};
+			delete $CGI->{ui_sequence_edit};
+		}
+		return unless $doit;
+		$Scratch->{ui_location}
+				= $Tag->area( {
+						href => $dest,
+						form => qq{
+							item_id=$CGI->{item_id}
+							item_id_left=$CGI->{item_id_left}
+							ui_sequence_edit=$CGI->{ui_sequence_edit}
+						},
+					});
+		return;
+	}
+
+[/perl]
+
+[if scratch ui_location]
+[comment]Comes from above include[/comment]
+[bounce href="[scratchd ui_location]"]
+[/if]
+
+@_UI_STD_HEAD_@
+
+[comment]
+<!-- sequence_edit: [cgi ui_sequence_edit] -->
+<!-- item_id_left: [cgi item_id_left] -->
+[/comment]
 
 [value name=mv_data_table set=transactions hide=1]
 [if-mm !tables]
 [set ui_error]
-	Not authorized for order administration. Contact administrator?
+	[L]Not authorized for order administration. Contact administrator?[/L]
 [/set]
 [bounce page="__UI_BASE__/error"]
 [/if-mm]
 
-[set ui_class]Orders[/set]
-[tmp page_perm]order[/tmp]
+[tmp can_delete][if-mm advanced order=d]1[/if-mm][/tmp]
 
-[tag flag write]transactions[/tag]
-[perl tables=transactions]
-	delete $Scratch->{ui_location};
-	my $db = $Db{transactions};
-	if(! $db) {
-		$Scratch->{ui_error} = "<FONT CLASS=error>Error: no transactions database.</FONT><BR>";
-		$Scratch->{ui_location} = "__UI_BASE__/error";
-		return;
-	}
-
-	my ($value, $action_col);
-	if($CGI->{archiveorder}) {
-		$value = 1;
-		$action_col = 'archived';
-	}
-	elsif($CGI->{unarchiveorder}) {
-		$value = 0;
-		$action_col = 'archived';
-	}
-	elsif($CGI->{deleteorder}) {
-		$value = 1;
-		$action_col = 'deleted';
-	}
-	elsif($CGI->{vieworder} and ! $CGI->{viewnext}) {
-		$CGI->{order} =~ s/^\0+//;
-		$CGI->{order} =~ s/\0+$//;
-		$Scratch->{ui_location} = $Tag->area('__UI_BASE__/order_view', $CGI->{order});
-	}
-	elsif($CGI->{xload}) {
-		$Scratch->{ui_location} = $Tag->area('__UI_BASE__/dbdownload');
-	}
-	else {
-		$CGI->{order} =~ s/^\0+//;
-		$CGI->{order} =~ s/\0.*//s;
-		$Scratch->{start_at} = "sm=$CGI->{order}";
-	}
+[include include/order_delete_archive]
 
-	if($action_col) {
-		for(grep $_, @{$CGI_array->{order}}) {
-			$db->set_field($_, $action_col, $value);
-		}
-	}
-	if(@errors) {
-		my $plural = @errors > 1 ? 's' : '';
-		return "<FONT CLASS=error>Error$plural:<UL><LI>" .
-				join ("<LI>", @errors)                    .
-				"</UL></FONT><BR>";
-	}
-	if($CGI->{viewnext}) {
-		my $ordnum = $CGI->{order};
-		$ordnum =~ s/[\0,\s].*//;
-		return if ! $ordnum;
-		$ordnum++;
-		CHECKNEXT: {
-			if (! $db->record_exists($ordnum) ) {
-				undef $ordnum;
-				last CHECKNEXT;
-			}
-			if ($db->field($ordnum, 'deleted') ) {
-				$ordnum++;
-				next CHECKNEXT;
-			}
-			if ($Values->{showarchive} and ! $db->field($ordnum, 'archived') ) {
-				undef $ordnum;
-				last CHECKNEXT;
-			}
-			else {
-				last CHECKNEXT;
-			}
-		}
-		if ($ordnum) {
-			$Scratch->{ui_location} = $Tag->area(
-									{
-										href => '__UI_BASE__/order_view',
-										form => "order=$ordnum",
-									}
-									);
-		}
-		else {
-			$Scratch->{message} = "[L]No next order.[/L]";
+[calc]
+	if ($CGI->{mv_like_spec}) {
+		my @f = split /\0/, $CGI->{mv_like_field};
+		my @s = split /\0/, $CGI->{mv_like_spec};
+		my @q = 'ra=yes';
+		my $found;
+		for(my $i = 0; $i < @f; $i++) {
+			next unless length $s[$i];
+			$found++;
+			push @q, "lf=$f[$i]";
+			push @q, "ls=$s[$i]";
 		}
+		if($found) { $CGI->{ui_text_qualification} = join "\n", @q; }
+		else	   { $CGI->{ui_text_qualification} = "" }
 	}
+	return if $CGI->{ui_text_qualification};
+	return unless
+		$Variable->{ORDER_VIEW_LARGE} or $Config->{Database}{transactions}{LARGE};
+	$Scratch->{ui_location} = $Tag->area( {
+									
+									href => '__UI_BASE__/flex_select',
+									form => q(
+										mv_data_table=transactions
+										page_title=Order select
+										page_banner=Order select
+										ui_searchpage=__UI_BASE__/order
+									),
+								},
+								);
 	return;
-[/perl]
-
+[/calc]
 
 [if scratch ui_location]
-[bounce href=`delete $Scratch->{ui_location}`]
+[comment]Comes from above include[/comment]
+[bounce href="[scratchd ui_location]"]
 [/if]
 
-[set icon_name]admin/icon_orders.gif[/set]
-[seti page_title]
-	[if value showarchive]
-	Orders: Archived Orders
-	[set help_name]order.main.archived[/set]
-	[else]
-	Orders: Pending Orders
-	[set help_name]order.main.pending[/set]
-	[/else]
-	[/if]
-[/seti]
 [update values]
 
-@_UI_STD_HEAD_@
-
 [if scratch message]
 <BLOCKQUOTE>
-[scratch message]
+[scratchd message]
 </BLOCKQUOTE>
-[set message][/set]
 [/if]
 </font>
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
-[if scratch ui_message]
-<BLOCKQUOTE>
-	[scratch ui_message]
-	[set ui_message][/set]
-</BLOCKQUOTE>
-<p>
-&nbsp;
-[/if]
-
-<table border=0><tr>
-<td>
-<small>
+[output name=search_box]
+<table align=right>
+	<tr>
+		<td class=s3>
+		<FORM ACTION="[area admin/order_view]">
+		View order: <INPUT NAME=order VALUE="[cgi order]" class=s3>
+		<INPUT TYPE=submit VALUE="[L]Go[/L]" class=s3>
+		</FORM>
+		</td>
+		<td>
     <FORM ACTION="[area @@MV_PAGE@@]">
-    <INPUT NAME=order VALUE="[cgi order]">
-    <INPUT TYPE=submit VALUE="Start at order number">
+    <INPUT NAME=ui_text_qualification VALUE="" class=s3>
+    <INPUT TYPE=submit VALUE="[L]Limit with search[/L]" class=s3>
     </FORM>
-</small>
-</td>
-<td valign=top><B> or </B></td>
-<td>
-<small>
-    <FORM ACTION="[area @@MV_PAGE@@]">
-    <INPUT NAME=ui_text_qualification VALUE="">
-    <INPUT TYPE=submit VALUE="Limit with search">
-    </FORM>
-</small>
-</td>
-</tr>
+		</td>
+	</tr>
 </table>
+
+
+
+[output name=""]
+
 [if cgi ui_text_qualification]
-<H4>Entries containing "[cgi ui_text_qualification]"</H3>
+	[calc]
+		return if $CGI->{mv_like_spec};
+		$Scratch->{page_banner} ||= $Scratch->{page_title};
+		$Scratch->{page_banner} .= errmsg(
+																'-- entries containing "%s"',
+																$CGI->{ui_text_qualification},
+																);
+		return;
+	[/calc]
 [/if]
+
 [search-region more=1 arg="
 		fi=transactions
 		ml=__UI_SZ_LIST_ORDER__
 		md=1
 		st=db
-		[if cgi ui_text_qualification]
+		[if cgi mv_like_spec]
+			[cgi ui_text_qualification]
+		[elsif cgi ui_text_qualification]
 			se=[cgi ui_text_qualification]
+		[/elsif]
 		[else]
 			co=yes
 			sf=archived
@@ -199,6 +209,11 @@
 			sf=deleted
 			se=1
 			op=ne
+			[if cgi only_status]
+			sf=status
+			se=[cgi only_status]
+			op=eq
+			[/if]
 		[/else]
 		[/if]
 		[scratch start_at][set start_at][/set]
@@ -209,7 +224,7 @@
 			tf=0
 		[/else]
 		[/if]
-		rf=code,order_date,total_cost,nitems,status,city,state,country,fname,lname,username
+		rf=code,order_date,total_cost,nitems,status,city,state,country,fname,lname,username,company
 "]
 [calc] 
 	my $so   = $CGI->{ui_sort_option};
@@ -226,119 +241,259 @@
 	}
 	return;
 [/calc]
+
+[output name=top_of_form]
 <FORM ACTION="[process]" METHOD=POST NAME=batch>
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="@@MV_PAGE@@">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
-<TABLE border=0 CELLSPACING=0 width="90%">
-<tr bgcolor=000000 height=1><td colspan=8></td></tr>
-<TR BGCOLOR="__UI_C_TITLEBARBG__">
-<th>&nbsp;</th>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">
+
+[output]
+
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+<tr class=rhead>
+<td>&nbsp;</td>
+<td class=rhead>
 [page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=code\n" . sortrev('code');
-	`]Order</A>
-</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">
+	`][L]Order[/L]</A>
+</td>
+<td class=rhead>
 [page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=lname,fname\n" . sortrev('lname');
-	`]User</A>
-</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">
+	`][L]User[/L]</A>
+</td>
+<td class=rhead>
 [page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=country,state,city\n" . sortrev('country');
-	`]Location</A>
-</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">
+	`][L]Location[/L]</A>
+</td>
+<td class=rhead>
 [page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=order_date\n" . sortrev('order_date');
-	`]Date/Time</A>
-</TH>
-<TH ALIGN=LEFT><FONT COLOR="__UI_C_TITLEBARTXT__">
+	`][L]Date[/L]/[L]Time[/L]</A>
+</td>
+<td class=rhead align=right>
 [page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=nitems\n" . sortrev('nitems', 1);
-`]Items</A>
-</TH>
-<TH ALIGN=CENTER><FONT SIZE=-1 COLOR="__UI_C_TITLEBARTXT__">
+`][L]Items[/L]</A>
+</td>
+<td class=rhead align=right>
 [page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=total_cost\n" . sortrev('total_cost', 1);
-`]Total</A>
-</TH>
-<TH ALIGN=RIGHT><FONT SIZE=-1 COLOR="__UI_C_TITLEBARTXT__">
+`][L]Total[/L]</A>
+</td>
+<td align=right class=rhead>
 [page href=@@MV_PAGE@@ form=`
 	return "ui_sort_field=status\n" . sortrev('status');
-`]Status</A>
-</TH>
+`][L]Status[/L]</A>
+</td>
 </tr>
-<tr bgcolor=000000 height=1><td colspan=8></td></tr>
-<tr bgcolor=FFFFFF height=2><td colspan=8></td></tr>
 [search-list]
-<TR [item-alternate 2]BGCOLOR="__UI_T_ROW_EVEN__"[else]BGCOLOR="__UI_T_ROW_ODD__"[/else][/item-alternate]>
-<TD>
+<tr [item-alternate 2]class=rownorm[else]class=rowalt[/else][/item-alternate]>
+<td>
 <INPUT TYPE=checkbox NAME=order VALUE="[item-code]"
 		[item-calc]
-			return if $Scratch->{archive_nm} eq 'unarchive';
-			return 'CHECKED' if q{[item-data transactions status]} eq '__UI_SHIPPED_STATUS__';
-			return;
+			my $string = '';
+			if(! $Scratch->{old_browser}) {
+				my $nm = 'checker[item-increment]';
+				push @els, qq{push_el('$nm', '[item-param status]');};
+				$string .= "id=$nm ";
+			}
+			return $string if $Scratch->{archive_nm} eq 'unarchive';
+			$string .= 'CHECKED'
+				if q{[item-param status]} eq $Values->{checked_status};
+			return $string;
 		[/item-calc]
 		>
 [page href="@@MV_PAGE@@"
 	form="
 		[scratch archive_nm]order=1
 		order=[item-code]
-	"]<IMG SRC="@_UI_IMG_@[scratch archive_img]" HEIGHT=10 WIDTH=11 ALT="[scratch archive_nm] [item-code]" BORDER=0></A>
+	"]<IMG SRC="[scratch archive_img]" HEIGHT=10 WIDTH=11 ALT="[scratch archive_nm] [item-code]" BORDER=0></A>
+[if scratch can_delete]
 <A HREF="[area
 	href='@@MV_PAGE@@'
 	form='
 		deleteorder=1
 		order=[item-code]
 	']"
-	onClick="return confirm('Are you sure you want to delete order [item-code]?')"><IMG src="@_UI_IMG_@admin/delsm.gif" ALT="DELETE [item-code]" BORDER=0></A>
-</TD>
-<TD>[page href=__UI_BASE__/order_view form="order=[item-code]"][item-code]</A></TD>
+	onClick="return confirm('Are you sure you want to delete order [item-code]?')"><IMG src="delsm.gif" ALT="DELETE [item-code]" BORDER=0></A>
+[/if]
+</td>
+<TD>[page href=__UI_BASE__/order_view form="order=[item-code]"][item-code]</A></td>
 <TD>
 	[page href=__UI_BASE__/customer_view form="customer=[item-param username]"][item-param lname], [item-param fname][if-item-param company] -- [item-param company][/if-item-param]</A>
-</TD>
-<TD>[item-filter 30][item-param city], [item-param state] [item-param country][/item-filter]</TD>
-<TD ALIGN=LEFT>[convert-date][item-param order_date][/convert-date]</TD>
-<TD ALIGN=CENTER>[item-param nitems]</TD>
-<TD ALIGN=Right>[currency][item-param total_cost][/currency]</TD>
-<TD ALIGN=Right>[page href="__UI_BASE__/order_status" form="order=[item-code]"][item-param status]</A></TD>
+</td>
+<td>[item-filter 30][item-param city], [item-param state] [item-param country][/item-filter]</td>
+<td align=left>[convert-date][item-param order_date][/convert-date]</td>
+<td align=right>[item-param nitems]</td>
+<td align=right>[currency][item-param total_cost][/currency]</td>
+<td align=right>[page href="__UI_BASE__/order_status" form="order=[item-code]"][loc][item-param status][/loc]</A></td>
 </tr>
 [/search-list]
 [no-match]
 <tr>
-<td colspan=6>
+<td colspan=8>
 <br>
-<B>No orders</B>
+<B>[L]No orders[/L]</B>
 <br><br>
 </td>
 </tr>
 [/no-match]
-<tr bgcolor=000000 height=1><td colspan=8></td></tr>
-<tr bgcolor=FFFFFF height=8><td colspan=8></td></tr>
 [more-list]
-<tr>
-<td colspan=6 align=center>
-Orders [matches] of [value mv_search_match_count] [scratch archive_label] displayed. More orders: [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
+<tr class=ralt>
+<td colspan=8 align=center>
+<br>
+<b>[msg arg.0="[matches]" arg.1="[value mv_search_match_count]"]Orders %s of %s [scratch archive_label] displayed.[/msg] [L]More orders[/L]:</b> [decade-next][/decade-next] [more] [decade-prev][/decade-prev]
+<br>
+&nbsp;
 </td>
 </tr>
 [/more-list]
 </table>
-[if-mm advanced order=d]
-[button form=batch text="Delete checked orders"
- confirm='Are you sure you want to delete the checked orders?']deleteorder=1
-[/button]
-[/if-mm]
-&nbsp;&nbsp;&nbsp;[button form=batch src="@_UI_IMG_@admin/[scratch archive_img]"
+[/search-region]
+
+[output name=bottom_buttons]
+
+[if scratch can_delete]
+	[button form=batch text="[L]Delete checked[/L]"
+	 no-src="__UI_IMG__delete.gif"
+		extra="class=s3"
+	 link-text-too=1
+	 confirm='[L]Are you sure you want to delete the checked orders?[/L]']deleteorder=1
+	[/button]
+&nbsp;
+[/if]
+
+[button form=batch
+			no-src="[scratch archive_img]"
+			extra="class=s3"
+			link-text-too=1
 			text=`
-			my $tmp = "$Scratch->{archive_nm} checked orders";
-			return "\u$tmp";
+			my $tmp = "$Scratch->{archive_nm} checked";
+			return errmsg("\u$tmp");
 			`]
-[scratch archive_nm]order=1[/button]
+[scratch archive_nm]order=1
+[/button]
+
+<input type=button
+		onClick="location='[area href=__UI_BASE__/spread
+													form="
+														mv_data_table=transactions
+													ui_meta_view=tracking
+													ui_text_qualification=tracking_number=
+													"]'"
+		value="[L]Enter tracking numbers[/L]" class=s3>
+
+[button form=batch
+			no-src="__UI_IMG__icon_merch.gif"
+			link-text-too=1
+			extra="class=s3"
+			text="Ship checked"
+			]
+ui_sequence_edit=[calc]
+	$CGI->{item_id} = delete $CGI->{order};
+	$CGI->{item_id_left} = $CGI->{item_id};
+	$CGI->{item_id_left} =~ s/\0+/,/g;
+	if($CGI->{item_id_left} =~ s/^(.*?),//) {
+		$CGI->{item_id} = $1;
+		return 1;
+	}
+	else {
+		delete $CGI->{item_id_left};
+		return '';
+	}
+[/calc]
+mv_nextpage=__UI_BASE__/order_status
+[/button]
+
+		<input
+			type=checkbox
+			name=ship_auto
+			value=1 class=s3>
+				<span title="Ship all lines of all orders, archive[if variable SETTLE_TRANSACTION], settle[/if]" class=s3>Ship all automatically</span>
+
+[output name=""]
+
+[if !scratch old_browser]
+<script>
+	var stat_array = new Array;
+	function push_el (el, status) {
+		if(stat_array[status] == undefined) {
+			stat_array[status] = new Array;
+// alert('created ' + status + ' array');
+		}
+		var els = stat_array[status];
+		els[els.length] = el;
+	}
+
+	function checkType (type, cond) {
+		var other = false;
+		if(cond == undefined) 
+			cond = true;
+		if(cond != true) 
+			other = true;
+		if(stat_array == undefined) {
+			return;
+		}
+		var i;
+		var alerted;
+		for(i in stat_array) {
+// alert("checking status of " + i);
+			var els = stat_array[i];
+			for (var j = 0; j < els.length; j++) {
+				var el = document.getElementById(els[j]);
+				if(el != undefined) {
+					if( type == 'none' ) {
+						el.checked = false;
+					}
+					else {
+						if( type == 'all' ) {
+							el.checked = true;
+						}
+						else {
+							if(i == type)
+								el.checked = cond;
+							else
+								el.checked = other;
+						}
+					}
+				}
+			}
+			var image_dir = '[image dir-only=1 ui=1 secure="__UI_SECURE__"]';
+			var types = ['all', 'none', 'shipped', 'pending', 'canceled', 'partial'];
+			for(var i = 0; i < types.length; i++) {
+				var img = document.getElementById('img_check_' + types[i]);
+				if(img != undefined) 
+					img.src= image_dir + 'box_empty.gif';
+			}
+			var img = document.getElementById('img_check_' + type);
+			img.src= image_dir + 'box_checked.gif';
+		}
+	}
+	[calc]
+		return join "\n", @els, '';
+	[/calc]
+</script>
+<br>
+			<A HREF="javascript:checkType('all')"><img id="img_check_all" src="__UI_IMG__box_empty.gif" border=0>Check all</A>
+			&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
+			<A HREF="javascript:checkType('none')"><img id="img_check_none" src="__UI_IMG__box_empty.gif" border=0>Uncheck all</A>
+[loop list="shipped pending canceled partial"]
+&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
+		<A HREF="javascript:checkType('[loop-code]')">
+			<img id="img_check_[loop-code]" src="__UI_IMG__box_empty.gif" border=0>Check all [loop-code]
+		</A>
+[/loop]
+[/if]
+
+[output name=bottom_of_form]
 </FORM>
-[/search-region]
+[output]
+
 <!-- ----- END REAL STUFF ----- -->
 
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Id: order.html,v 1.19.4.5 2003/01/25 22:21:14 racke Exp $ -->



1.2.4.1   +159 -275  interchange/dist/lib/UI/pages/admin/order_status.html


rev 1.2.4.1, prev_rev 1.2
Index: order_status.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/order_status.html,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- order_status.html	23 Sep 2000 17:55:33 -0000	1.2
+++ order_status.html	25 Jan 2003 22:21:14 -0000	1.2.4.1
@@ -1,300 +1,184 @@
-[if !cgi order]
-	[bounce page="__UI_BASE__/order"]
-[/if]
-
 [calc]
 	$Values->{ui_data_fields} = $CGI->{ui_data_fields} = 'status archive delete';
 	$CGI->{mv_data_table} = 'transactions';
-	$Scratch->{arg} = $CGI->{item_id} = $CGI->{order};
+	$CGI->{item_id} ||= $CGI->{order};
+	$CGI->{order} = $CGI->{item_id};
 	return;
 [/calc]
 
-@_UI_STD_DBEDIT_HEAD_@
-[set ui_class]Orders[/set]
-[seti page_title]Order status -- [cgi order][/seti]
-[tmp page_banner]Order status: order <B>[page href="__UI_BASE__/order_view" form="order=[cgi order]"][cgi order]</A></B>[/tmp]
-[set help_name]item.edit[/set]
-[set icon_name]admin/icon_item.gif[/set]
-
-@_UI_STD_HEAD_@
-
-[tmp order_lines_tmp][loop search="
-			fi=orderline
-			st=db
-			sf=order_number
-			se=[cgi order]
-			ml=1000
-	"][loop-code] [/loop][/tmp]
-
-<FORM METHOD=POST ACTION="[area ui]" NAME=transactions>
-<INPUT TYPE=hidden NAME=mv_doit VALUE="set">
-<INPUT TYPE=hidden NAME=mv_click VALUE="process_filter">
-<INPUT TYPE=hidden NAME=mv_nextpage VALUE="__UI_BASE__/order_view">
-<INPUT TYPE=hidden NAME=code VALUE="[cgi order]">
-<INPUT TYPE=hidden NAME=mv_data_table VALUE="[value mv_data_table]">
-<INPUT TYPE=hidden NAME=ui_meta_specific VALUE="[cgi ui_meta_specific]">
-<INPUT TYPE=hidden NAME=mv_data_key VALUE="[value ui_data_key_name]">
-<INPUT TYPE=hidden NAME=mv_update_empty VALUE="1">
-<INPUT TYPE=hidden NAME=mv_data_fields VALUE="code status archived deleted">
-<table width="95%"><tr><td BGCOLOR="__UI_C_TOPBLOCKBAR__">
-<table width="100%"><tr><td BGCOLOR="__UI_C_TITLEBARBG__">
-<table CELLSPACING=0 CELLMARGIN=0 WIDTH="100%">
-[loop list="[cgi order]"]
-<TR>
-<TD ALIGN=RIGHT><B>Order date</B></TD>
-<TD BGCOLOR="__UI_T_ROW_ODD__">
-[convert-date][loop-data transactions order_date][/convert-date]</TD>
-</TR>
-<TR>
-<TD ALIGN=RIGHT><B>Status last updated</B></TD>
-<TD BGCOLOR="__UI_T_ROW_ODD__">
-[convert-date][loop-data transactions update_date][/convert-date]</TD>
-</TR>
-[loop prefix=row list="status deleted archived"]
-[display table=transactions column="[row-code]" key="[loop-code]"
-										template=|
-<TR BGCOLOR="__UI_T_ROW_ODD__">
-<TD BGCOLOR="__UI_C_TITLEBARBG__" ALIGN=right>
-	<FONT COLOR="__UI_C_TITLEBARTXT__"><B>$LABEL$</B></FONT>
-</TD>
-<TD VALIGN=TOP>
-	<TABLE CELLSPACING=0 CELLMARGIN=0><TR><TD>$WIDGET$</TD><TD><I>$HELP$</I>{HELPURL}<BR><A HREF="$HELP_URL$">help</A>{/HELPURL}</TD></TR></TABLE>
-</TD>
-</TR>
-|]
+[if cgi ship_auto]
+[calc]
+	my $orders = join ",", delete $CGI->{item_id}, delete $CGI->{item_id_left};
+	$orders =~ s/-_NULL_-/\0/g;
+	$orders =~ s/\0+/,/g;
+	$orders =~ s/,+/,/g;
+	delete $CGI->{order};
+	$Scratch->{order_list} = $orders;
+[/calc]
+[loop list="[scratch order_list]"]
+	[update-order-status
+			order_number="[loop-code]"
+			ship_all=1
+			[if-loop-data transactions order_id]
+			settle_transaction="__SETTLE_TRANSACTION__"
+			[/if-loop-data]
+			archive=1]
 [/loop]
-<TR>
-<TD ALIGN=RIGHT>&nbsp;</TD>
-<TD BGCOLOR="__UI_T_ROW_ODD__">
-[if-mm advanced order]
-	[button form=transactions bold=1 text="Ship checked order lines, send email to customer if appropriate"]
-	mv_todo=back
-	order=[cgi code]
-	[tag flag write]orderline transactions[/tag]
-	[perl tables="orderline transactions userdb __UI_META_TABLE__"]
-		my $odb = $Db{orderline}
-			or die "No orderline database!\n";
-		my $tdb = $Db{transactions}
-			or die "No transactions database!\n";
-		my $udb = $Db{userdb}
-			or die "No userdb database!\n";
-
-		my $on = $Scratch->{ship_notice_order_number} = $CGI->{code};
-		my $user       = $tdb->field($on, 'username');
-		my $wants_copy = $udb->field($user, 'email_copy');
-#Log("Order number=$on username=$user wants=$wants_copy");
-		delete $Scratch->{ship_notice_username};
-		delete $Scratch->{ship_notice_email};
-		if($wants_copy) {
-			$Scratch->{ship_notice_username} = $user;
-			$Scratch->{ship_notice_email} = $udb->field($user, 'email')
-				or delete $Scratch->{ship_notice_username};
-		}
+			
 
-		if($CGI->{status} =~ /\d\d\d\d/) {
-			$tdb->set_field($on, 'status', $CGI->{status});
-		}
-		else {
-			$tdb->set_field($on, 'status', 'shipped');
-		}
 
-		my @shiplines = grep /\S/, split /\0/, $CGI->{lines_shipped};
-		my $to_ship = scalar @shiplines;
+[/if]
+[if !cgi order]
+	[bounce page="__UI_BASE__/order"]
+[/if]
 
-		my $count_q = "select * from orderline where order_number = '$on'";
-		my $lines_ary =  $odb->query($count_q);
-		if(! $lines_ary) {
-			$Scratch->{ui_message} = "No order lines for order $on";
-			return;
-		}
-		my $total_lines = scalar @$lines_ary;
+[set ui_class]Orders[/set]
+[seti page_title][L]Order status[/L] -- [cgi order][/seti]
+[tmp page_banner][L]Order status[/L]: [L]order[/L] <B>[page href="__UI_BASE__/order_view" form="order=[cgi order]"][cgi order]</A></B>[/tmp]
+[set help_name]item.edit[/set]
+[set icon_name]icon_item.gif[/set]
 
-		my $odb_keypos = $odb->config('KEY_INDEX');
+@_UI_STD_HEAD_@
 
-		# See if some items have already shipped
-		my %already;
-		for(@$lines_ary) {
-			my $code = $_->[$odb_keypos];
-			my $status = $odb->field($code, 'status');
-			if($status eq 'shipped') {
-				$already{$code} = $code;
+[tmp form_include]
+<tr class=rnorm>
+<td class=clabel align=center style="font-size: larger">
+	Actions
+</td>
+<td class=cdata>
+	<div 
+		style="
+			border: 2px solid black;
+			padding: 8px;
+		">
+
+	[tmp tmp_orderid][data table=transactions col=order_id key="[cgi order]"][/tmp]
+<script>
+	var have_orderid = '[scratch tmp_orderid]';
+	function copasetic (el,form) {
+		if(have_orderid == '')
+			return;
+		if(el.name == 'ship_all') {
+			if(el.options[el.selectedIndex].value == 0) {
+				if(form.void_transaction != undefined)
+					form.void_transaction.checked = false;
+				if(form.settle_transaction != undefined)
+					form.settle_transaction.checked = false;
+				form.do_archive.checked = false;
+			}
+			if(el.options[el.selectedIndex].value == 1) {
+				if(form.void_transaction != undefined)
+					form.void_transaction.checked = false;
+				if(form.settle_transaction != undefined)
+					form.settle_transaction.checked = true;
+				form.do_archive.checked = true;
+			}
+			if(el.options[el.selectedIndex].value == 2) {
+				if(form.void_transaction != undefined)
+					form.void_transaction.checked = true;
+				if(form.settle_transaction != undefined)
+					form.settle_transaction.checked = false;
+				form.do_archive.checked = true;
 			}
-		}
-		
-		my $ship_mesg;
-		my $g_status;
-		my %shipping;
-
-		@shipping = grep ! $already{$_}, @shipping;
-		@shipping{@shiplines} = @shiplines;
-
-		if($total_lines == $to_ship) {
-			$ship_mesg = "Order $on complete, $total_lines lines set shipped.";
-			$Scratch->{ship_notice_complete} = $ship_mesg;
-			$g_status = 'shipped';
 		}
 		else {
-			$ship_mesg = "Order $on partially shipped ($to_ship of $total_lines lines).";
-			delete $Scratch->{ship_notice_complete};
-			$g_status = 'partial';
-		}
-
-		my $minor_mesg = '';
-
-		my $email_mesg = $Scratch->{ship_notice_username}
-						? "Email copy sent to $Scratch->{ship_notice_email}."
-						: "No email copy sent as per user preference.";
-
-		# Actually update the orderline database
-		for(@$lines_ary) {
-			my $code = $_->[$odb_keypos];
-			next if $already{$code};
-			my $status = $shipping{$code} ? 'shipped' : 'backorder';
-			$odb->set_field($code, 'status', $status)
-				or do {
-					$Scratch->{ui_message} = "Orderline $code ship status update failed.";
-					return;
-				};
-
-		}
-
-		for(keys %already) {
-			$shipping{$_} = $_;
-		}
-
-		my $total_shipped_now = scalar keys %shipping; 
-
-
-		delete $Scratch->{ship_now_complete};
-		if (
-			$total_lines != scalar @shipping
-				and
-			$total_shipped_now == $total_lines 
-		  )
-		{
-			$g_status = 'shipped';
-			$Scratch->{ship_now_complete} = 1
-				if $total_shipped_now == $total_lines;
-			$ship_mesg = "Order $on now complete (all $total_lines lines).";
-		}
-
-		$tdb->set_field($on, 'status', $g_status);
-
-		$Scratch->{ui_message} = "$ship_mesg $email_mesg";
-		delete $Scratch->{ship_notice_username};
-		delete $Scratch->{ship_notice_email};
-		if($wants_copy) {
-			$Scratch->{ship_notice_username} = $user;
-			$Scratch->{ship_notice_email} = $tdb->field($on, 'email')
-				or $Scratch->{ship_notice_email} = $tdb->field($on, 'email')
-				or delete $Scratch->{ship_notice_username};
+			if (el.name == 'settle_transaction') {
+				if(el.checked == true) {
+					form.ship_all.selectedIndex = 1;
+					form.void_transaction.checked = false;
+				}
+			}
+			if(el.name == 'void_transaction') {
+				if(el.checked == true) {
+					form.ship_all.selectedIndex = 2;
+					form.settle_transaction.checked = false;
+				}
+			}
 		}
-		return;
-	[/perl]
-
+	}
+	document.tform.tracking_number.focus();
+</script>
+
+	<select name=ship_all onChange="copasetic(this, this.form)">
+		<option value=0> Ship per status above
+		<option value=1 SELECTED> Ship all lines
+		<option value=2> Cancel order
+	</select>
+
+	[button form=tform
+			extra='style="font-weight: bold"'
+			text="[L]Update the order[/L]"]
+	mv_todo=back
+	order=[cgi code]
+	[tag flag write]orderline transactions[/tag]
+	[update-order-status order-number="[cgi code]"]
 	[if scratch ship_notice_username]
 	[email-raw][include etc/ship_notice][/email-raw]
 	[/if]
 
-	[/button] <BR>
-
-	[loop prefix=partial list="[scratch order_lines_tmp]"]
-	<INPUT TYPE=checkbox NAME=lines_shipped VALUE="[partial-code]" CHECKED> Line [partial-increment] ([partial-filter 16][partial-data orderline description][/partial-filter])<BR>
-	[/loop]
-	<BR>
-	[button bold=1 text="Change global status"]
-	order=[cgi code]
-	[/button]&nbsp;&nbsp;&nbsp;
-	[button text="Cancel"]
-	mv_nextpage=__UI_BASE__/order_view
-	order=[cgi code]
-	mv_todo=back
 	[/button]
-[else]
-	[button text="Back"]
-	mv_nextpage=__UI_BASE__/order_view
-	order=[cgi code]
-	mv_todo=back
-	[/button]
-[/else]
-[/if-mm]
-</TD>
-</table>
-</td></tr></table>
-</td></tr></table>
-</FORM>
 
-[/loop]
+	Email
+	<select name=send_email>
+		<option value="">[L]Use customer preference[/L]</option>
+		<option value="0">[L]No[/L]</option>
+		<option value="1">[L]Yes[/L]</option>
+	</select>
+	[if variable SETTLE_TRANSACTION]
+	<br>
+		[if scratch tmp_orderid]
+			<input type=checkbox name=settle_transaction value=1
+				onChange="copasetic(this, this.form)"
+				[if type=scratch term=tmp_orderid op="!~" compare="/[-*]$/"] CHECKED [/if]>
+					<b>Settle transaction</b>
+			&nbsp;
+			&nbsp;
+			<input type=checkbox name=void_transaction onChange="copasetic(this, this.form)" value=1> <b>Void transaction </b>
 
-<h2>Individual line item status</H2>
-<TABLE>
-[loop search="
-		fi=orderline
-		st=db
-		sf=order_number
-		se=[cgi order]
-		ml=1000
-"]
-[calc]
-	$Values->{ui_data_fields} = $CGI->{ui_data_fields} = 'code status delete';
-	$CGI->{mv_data_table} = 'transactions';
-	$Scratch->{arg} = $CGI->{item_id} = $CGI->{order};
-	return;
-[/calc]
-
-<TR><TD>
-
-@@UI_STD_DBEDIT_HEAD@@
-<FORM METHOD=POST ACTION="[area ui]" NAME="orderline[loop-increment]">
-<INPUT TYPE=hidden NAME=mv_doit VALUE="set">
-<INPUT TYPE=hidden NAME=mv_click VALUE="process_filter">
-<INPUT TYPE=hidden NAME=mv_nextpage VALUE="@@MV_PAGE@@">
-<INPUT TYPE=hidden NAME=code VALUE="[loop-code]">
-<INPUT TYPE=hidden NAME=order VALUE="[cgi order]">
-<INPUT TYPE=hidden NAME=mv_data_table VALUE="orderline">
-<INPUT TYPE=hidden NAME=ui_meta_specific VALUE="[cgi ui_meta_specific]">
-<INPUT TYPE=hidden NAME=mv_data_key VALUE="code">
-<INPUT TYPE=hidden NAME=mv_update_empty VALUE="1">
-<INPUT TYPE=hidden NAME=mv_data_fields VALUE="code status">
-<table width="95%"><tr><td BGCOLOR="__UI_C_TOPBLOCKBAR__">
-<table width="100%"><tr><td BGCOLOR="__UI_C_TITLEBARBG__">
-<table CELLSPACING=0 CELLMARGIN=0 WIDTH="100%">
-<TR>
-<TD ALIGN=RIGHT><FONT COLOR="__UI_C_TITLEBARTXT__"><B>SKU/Description</B></TD>
-<TD BGCOLOR="__UI_T_ROW_ODD__">
-SKU: [loop-data orderline sku], [loop-data orderline quantity]@[filter %.2f][loop-data orderline price][/filter] = [currency][loop-data orderline subtotal][/currency]<BR>
-[loop-data orderline description]
-</TD>
-</TR>
-<TR>
-<TD ALIGN=RIGHT><FONT COLOR="__UI_C_TITLEBARTXT__"><B>Last updated</B></TD>
-<TD BGCOLOR="__UI_T_ROW_ODD__">
-[convert-date][loop-data orderline update_date][/convert-date]</TD>
-</TR>
-[display table=orderline column="status" key="[loop-code]"
-										template=|
-<TR BGCOLOR="__UI_T_ROW_ODD__">
-<TD BGCOLOR="__UI_C_TITLEBARBG__" ALIGN=right>
-	<FONT COLOR="__UI_C_TITLEBARTXT__"><B>$LABEL$</B></FONT>
-</TD>
-<TD VALIGN=TOP>
-	<TABLE CELLSPACING=0 CELLMARGIN=0><TR><TD>$WIDGET$</TD><TD><I>$HELP$</I>{HELPURL}<BR><A HREF="$HELP_URL$">help</A>{/HELPURL}</TD></TR></TABLE>
-</TD>
-</TR>
-|]
-<TR>
-<TD ALIGN=RIGHT>&nbsp;</TD>
-<TD BGCOLOR="__UI_T_ROW_ODD__">
-<INPUT TYPE=submit VALUE="Update status of line [loop-increment]">
-</TD>
-</table>
-</td></tr></table>
-</td></tr></table>
-</FORM>
-
-</TD></TR>
-[/loop]
-</TABLE>
+		[/if]
+	[/if]
+			&nbsp;
+			&nbsp;
+			<input type=checkbox name=do_archive value=1 CHECKED> <b>Archive transaction at end</b>
+	</div>
+</td>
+</tr>
+[/tmp]
+
+[table-editor 
+	table=transactions
+	key="[cgi order]"
+	output_map=1
+	button_delete=1
+	form-name=tform
+	table-width="100%"
+	next-text="Update status only, no ship function"
+	ok-button-style="font-weight: normal; font-size: smaller"
+	no-table-meta=1
+	mv-nextpage="__UI_BASE__/order"
+	ui_data_fields="code status tracking_number order_id auth_code archived deleted"
+	include-form="[scratch form_include]"
+	include-before="order_id"
+	help.order_id='<span style="font-size: larger;font-weight: bold">* = settled, - = voided</span>'
+	link-table=orderline
+	link-key=order_number
+	link-before=order_id
+	link-no-blank=1
+	link-label="Ordered Items"
+	hidden.ui_sequence_destination="@@MV_PAGE@@"
+/]
+
+<script>
+	var f = document.tform;
+	if(f != undefined) {
+		var str = f.order_id.value;
+// alert("in check, str=" + str);
+		if(str.match(/\*$/) ) {
+			f.settle_transaction.checked = false;
+// alert("set checked status!");
+		}
+	}
+</script>
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Id: order_status.html,v 1.2.4.1 2003/01/25 22:21:14 racke Exp $ -->



1.16.4.6  +334 -337  interchange/dist/lib/UI/pages/admin/order_view.html


rev 1.16.4.6, prev_rev 1.16.4.5
Index: order_view.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/order_view.html,v
retrieving revision 1.16.4.5
retrieving revision 1.16.4.6
diff -u -r1.16.4.5 -r1.16.4.6
--- order_view.html	22 Nov 2000 01:50:39 -0000	1.16.4.5
+++ order_view.html	25 Jan 2003 22:21:14 -0000	1.16.4.6
@@ -1,12 +1,22 @@
-[set page_title]Order manager: View order[/set]
+[set page_title][L]Order manager[/L]: [L]View order[/L][/set]
 [set ui_class]Orders[/set]
-[set page_banner]View order[/set]
 [set help_name]order.view[/set]
-[set icon_name]admin/icon_orders.gif[/set]
+[set icon_name]icon_orders.gif[/set]
 @_UI_STD_HEAD_@
 [calc]
 	delete $Scratch->{ui_bounce};
-	return if $CGI->{order};
+	if ($CGI->{order}) {
+		if($CGI->{deliver_encrypted}) {
+			my $dir = q{__ORDER_DIRECTORY__} || 'orders';
+			my $ord = $Tag->filter('filesafe', $CGI->{order});
+			$Tag->deliver({
+							file => "orders/$ord",
+							get_encrypted => 1,
+							type => 'application/pgp-encrypted',
+						});
+		}
+		return;
+	}
 	$CGI->{order} = $CGI->{mv_arg} 
 		or $Scratch->{ui_bounce} = '__UI_BASE__/order';
 	return;
@@ -15,373 +25,360 @@
 	[bounce page="[scratch ui_bounce]"]
 [/if]
 
-[if scratch ui_message]
-<BLOCKQUOTE>
-	[scratch ui_message]
-	[set ui_message][/set]
-</BLOCKQUOTE>
-<p>
-&nbsp;
-[/if]
-
-
 <!-- ----- BEGIN REAL STUFF ----- -->
 [update values]
-[loop list="[value-extended order]"]
-
-<table __UI_T_PROPERTIES__>
-<tr>
-<td colspan=6 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" height=1></td>
-</tr>
+[perl tables=country]### pre-open database for calcs below[/perl] 
 
-<tr>
-<td colspan=6 align=left bgcolor=__UI_C_INTBLOCK__>
-<b>Order number: [loop-code] Order date: [convert-date][loop-data transactions order_date][/convert-date]</b>
-</td>
-</tr>
-
-<tr>
-<td colspan=6 align=left bgcolor=__UI_C_INTBLOCK__>
-<b>Customer: 
-[if-loop-data transactions username]
-<A HREF="[area
+[loop list="[value-extended order]"]
+<table width="100%" border="0" cellspacing="0" cellpadding="0">
+   <tr> 
+      <td> 
+         <table width="100%" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+            <tr> 
+               <td width="25%" nowrap class="block4bold">User Name: &nbsp; <a href="[area href="admin/customer_view" form="customer=[loop-data transactions username]"]" title="View customer"><span class="maincontent">[loop-data transactions username]</span></a></td>
+               <td width="25%" nowrap class="block4bold">
+			   	Order Status: &nbsp;
+					[page href="admin/order_status" form="order=[loop-code]"]
+						<span class="alert">Pending</span>
+					</a>
+					[if-loop-data transactions archived == 1]
+					([L]archived[/L])
+					[/if-loop-data]
+					[if-loop-data transactions deleted == 1]
+					([L]deleted[/L])
+					[/if-loop-data]
+					
+				</td>
+               <td width="25%" nowrap class="block4bold">
+			   		
+					Affiliate: &nbsp;
+					[if-loop-data transactions affiliate]
+						[page href="admin/affiliate"
+							  form="affiliate=[loop-data transactions affiliate]"
+						]<span class="maincontent">[loop-data transactions affiliate]</span></A>
+					[else]
+							<span class="maincontent">none</span>
+					[/else]
+					[/if-loop-data]
+				</td>
+                <td width="25%" nowrap class="block4bold">
+			   		Order Date: &nbsp; <span class="maincontent">
+						[convert-date fmt="%b %e, %Y %l:%M %P"][loop-data transactions order_date][/convert-date]
+					</span>
+				</td>
+            </tr>
+         </table>
+      </td>
+   </tr>
+   <tr> 
+      <td height="6"><img src="bg.gif" width="1" height="6"></td>
+   </tr>
+   <tr> 
+      <td> 
+         <table width="100%" border="0" cellspacing="0" cellpadding="0">
+            <tr> 
+               <!-- CUSTOMER DETAILS -->
+		[loop prefix=customer list="[loop-data transactions username]"]
+               <td width="33%" valign="top"> 
+                  <table width="100%" height="160" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+                     <tr> 
+               
+                        <td height="1%" class="block4"><a href="[area href='admin/customer_view' form='customer=[loop-data transactions username]']">Customer Details</a></td>
+                     </tr>
+                     <tr> 
+                        <td height="99%" valign="top" class="block4"> 
+                           <table width="100%" border="0" cellspacing="0" cellpadding="1">
+                              <tr> 
+                                 <td width="30%" class="block4bold">Customer:</td>
+                                 <td width="70%" class="maincontent"><a href="[area href='admin/customer_view' form='customer=[loop-data transactions username]']">[customer-data userdb fname] [customer-data userdb lname]</a> 
+                                 </td>
+                              </tr>
+                              <tr> 
+                                 <td class="block4bold"> [L]Company[/L]:</td>
+                                 <td class="maincontent">[customer-data userdb company]</td>
+                              </tr>
+                              <tr> 
+                                 <td nowrap class="block4bold">[L]Home phone[/L]:</td>
+                                 <td class="maincontent">[customer-data userdb phone_night]</td>
+                              </tr>
+                              <tr> 
+                                 <td nowrap class="block4bold"> [L]Work phone[/L]:</td>
+                                 <td class="maincontent">[customer-data userdb phone_night]</td>
+                              </tr>
+                              <tr> 
+                                 <td class="block4bold">[L]Email[/L]:</td>
+                                 <td class="maincontent"><a href="mailto:[customer-data userdb email]">[loop-data transactions email]</a></td>
+                              </tr>
+                              <tr> 
+                                 <td nowrap class="block4bold">[L]Payment type[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions payment_method]</td>
+                              </tr>
+                              <tr> 
+                                 <td height="15" colspan="2" class="block4bold"><img src="bg.gif" width="1" height="1"></td>
+                              </tr>
+                           </table>
+                        </td>
+                     </tr>
+                  </table>
+               </td>
+		[/loop]
+               <td width="3"><img src="bg.gif" width="3" height="1"></td>
+               <!-- BILLING DETAILS -->
+               <td width="33%" valign="top"> 
+                  <table width="100%" height="160" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+                     <tr> 
+                        <td height="1%" class="block4"><a href="#">Billing Details</a></td>
+                     </tr>
+                     <tr> 
+                        <td height="99%" valign="top" class="block4"> 
+[if-loop-data transactions b_address1]
+	[loop prefix=bill list="[loop-code]"]
+                           <table width="100%" border="0" cellspacing="0" cellpadding="1">
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Name[/L]:</td>
+                                 <td width="70%" class="maincontent"><A HREF="[area
 				href=__UI_BASE__/customer_view
 				arg="[loop-data transactions username]"
-		]"><u>[loop-data transactions fname] [loop-data transactions lname]</u></A>
+		]"><u>[loop-data transactions b_fname] [loop-data transactions b_lname]</A>
+                                 </td>
+                              </tr>
+							  [if-bill-data transactions b_company]
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Company[/L]:</td>
+                                 <td width="70%" class="maincontent">
+								 	[loop-data transactions b_company]
+                                 </td>
+                              </tr>
+							  [/if-bill-data]
+                              <tr> 
+                                 <td valign="top" class="block4bold">[L]Address[/L]:</td>
+                                 <td class="maincontent">
+								 [loop-data transactions b_address1]
+								 [if-bill-data transactions b_address2]
+								 <br>
+								 [loop-data transactions b_address2]
+								 [/if-bill-data]
+								 </td>
+                              </tr>
+							  [if-bill-data transactions b_country =~ /^US|^CA/]
+                              <tr> 
+                                 <td class="block4bold">[L]City, State, Zip[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions b_city], [loop-data transactions state]  [loop-data transactions zip]</td>
+                              </tr>
+							  [else]
+                              <tr> 
+                                 <td class="block4bold">[L]City[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions b_city]</td>
+                              </tr>
+							  		[if-bill-data transactions b_state]
+                              <tr> 
+                                 <td class="block4bold">[L]State[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions b_state]</td>
+                              </tr>
+								    [/if-bill-data]
+							  		[if-bill-data transactions b_zip]
+                              <tr> 
+                                 <td class="block4bold">[L]Postal code[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions b_zip]</td>
+                              </tr>
+								    [/if-bill-data]
+							  [/else]
+							  [/if-bill-data]
+                              <tr> 
+                                 <td class="block4bold">[L]Country[/L]:</td>
+                                 <td class="maincontent">[data table=country col=name key="[loop-data transactions b_country]"]</td>
+                              </tr>
+                              <tr> 
+                                 <td height="15" colspan="2" class="block4bold"><img src="bg.gif" width="1" height="1"></td>
+                              </tr>
+                           </table>
+		[/loop]
 [else]
-		[loop-data transactions fname] [loop-data transactions lname]
+						<i>Same as shipping address</i>
 [/else]
 [/if-loop-data]
-		</b>
-</td>
-</tr>
-
-<!-- ----- Affiliate Check ----- -->
-[if-loop-data transactions affiliate]
-<tr>
-<td colspan=6 align=left bgcolor=__UI_C_INTBLOCK__>
-<b>Affiliate: [data table="__UI_AFFILIATE_TABLE__" column=name key="[loop-data transactions affiliate]"]</b>
-</td>
-</tr>
-[/if-loop-data]
-
-<tr>
-<td colspan=2 valign=top>
-
-<!-- ----- Customer information ----- -->
-
-<table>
-<tr><td align=right>
-<font size=2><b> Company: </b></font>
-</td><td><font size=2>[loop-data transactions company]</font></td></tr>
-
-<tr><td align=right>
-<font size=2><b> Home phone: </b></font>
-</td><td><font size=2>[loop-data transactions phone_night]</font></td></tr>
-
-<tr><td align=right>
-<font size=2><b> Work phone: </b></font>
-</td><td><font size=2>[loop-data transactions phone_day]</font></td></tr>
-
-<tr><td align=right>
-<font size=2><b> Email: </b></font>
-</td><td><font size=2> <a href="mailto:[loop-data transactions email]"><U>[loop-data transactions email]</U></a></font></td></tr>
-
-<tr><td align=right>
-<font size=2><b> Payment type: </b></font>
-</td><td><font size=2>[loop-data transactions payment_method]</a></font></tr>
-
-</table>
-
-</td><td valign=top colspan=4>
-[set bill_address]
-[loop-data transactions b_fname] [loop-data transactions b_lname]<br>
-[loop-data transactions b_address1]<br>
-[if-loop-data transactions b_address2]
-[loop-data transactions b_address2]<br>
-[/if-loop-data]
-[loop-data transactions b_city], [loop-data transactions b_state] [loop-data transactions b_zip]<br>
-[/set]
-
-[set ship_address]
-[loop-data transactions fname] [loop-data transactions lname]<br>
-[loop-data transactions address1]<br>
-[if-loop-data transactions address2]
-[loop-data transactions address2]<br>
-[/if-loop-data]
-[loop-data transactions city], [loop-data transactions state] [loop-data transactions zip]<br>
-[/set]
-
-<font size=2>
-<p>
-[if-loop-data transactions username]
-<A HREF="[area
-				href=__UI_BASE__/flex_editor
-				form=|
-					ui_return_to=__UI_BASE__/order_view
-					ui_return_to=order=[cgi order]
-					ui_hide_key=1
-					ui_data_fields=username company b_fname b_lname b_address1 b_address2 b_city b_state b_zip b_country b_email b_phone_day b_phone_night
-					page_title=Customer: [loop-data transactions fname] [loop-data transactions lname]
-					item_id=[loop-data transactions username]
-					mv_data_table=userdb
-				|
-		]"><b><u>Bill To</u>:</b></A>
-[else]
-		<b>Bill To:</b>
-[/else]
-[/if-loop-data]
-<blockquote>
-[if-loop-data transactions b_address1]
-[scratch bill_address]
-[else]
-[scratch ship_address]
-[/else]
-[/if-loop-data]
-</blockquote>
-
-<b>
-[if-loop-data transactions username]
-<A HREF="[area
-				href=__UI_BASE__/flex_editor
-				form=|
-					ui_return_to=__UI_BASE__/order_view
-					ui_return_to=mv_arg=[cgi order]
-					ui_hide_key=1
-					ui_data_fields=username company fname lname address1 address2 city state zip country email phone_day phone_night
-					page_title=Customer: [loop-data transactions fname] [loop-data transactions lname]
-					item_id=[loop-data transactions username]
-					mv_data_table=userdb
-				|
-		]"><b><u>Ship To</u>:</b></A>
-[else]
-		<b>Ship To:</b>
-[/else]
-[/if-loop-data]
-<br>
-<blockquote>
-[scratch ship_address]
-</blockquote>
-</font>
-
-<P>
-<B>Status:<B>[seti statestr][display    table=transactions
+                        </td>
+                     </tr>
+                  </table>
+               </td>
+               <td width="3"><img src="bg.gif" width="3" height="1"></td>
+               <!-- SHIPPING DETAILS -->
+               <td width="34%" valign="top"> 
+                  <table width="100%" height="160" border="0" cellpadding="6" cellspacing="1" class="rseparator">
+                     <tr> 
+                        <td height="1%" class="block4"><a href="#">Shipping Details</a></td>
+                     </tr>
+                     <tr> 
+                        <td height="99%" valign="top" class="block4"> 
+                           <table width="100%" border="0" cellspacing="0" cellpadding="1">
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Name[/L]:</td>
+                                 <td width="70%" class="maincontent"><A HREF="[area
+				href=__UI_BASE__/customer_view
+				arg="[loop-data transactions username]"
+		]"><u>[loop-data transactions fname] [loop-data transactions lname]</A>
+                                 </td>
+                              </tr>
+							  [if-loop-data transactions company]
+                              <tr> 
+                                 <td width="30%" class="block4bold">[L]Company[/L]:</td>
+                                 <td width="70%" class="maincontent">
+								 	[loop-data transactions company]
+                                 </td>
+                              </tr>
+							  [/if-loop-data]
+                              <tr> 
+                                 <td valign="top" class="block4bold">[L]Address[/L]:</td>
+                                 <td class="maincontent">
+								 [loop-data transactions address1]
+								 [if-loop-data transactions address2]
+								 <br>
+								 [loop-data transactions address2]
+								 [/if-loop-data]
+								 </td>
+                              </tr>
+							  [if-loop-data transactions country =~ /^US|^CA/]
+                              <tr> 
+                                 <td class="block4bold">[L]City, State, Zip[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions city], [loop-data transactions state]  [loop-data transactions zip]</td>
+                              </tr>
+							  [else]
+                              <tr> 
+                                 <td class="block4bold">[L]City[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions city]</td>
+                              </tr>
+							  		[if-loop-data transactions state]
+                              <tr> 
+                                 <td class="block4bold">[L]State[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions state]</td>
+                              </tr>
+								    [/if-loop-data]
+							  		[if-loop-data transactions zip]
+                              <tr> 
+                                 <td class="block4bold">[L]Postal code[/L]:</td>
+                                 <td class="maincontent">[loop-data transactions zip]</td>
+                              </tr>
+								    [/if-loop-data]
+							  [/else]
+							  [/if-loop-data]
+                              <tr> 
+                                 <td class="block4bold">[L]Country[/L]:</td>
+                                 <td class="maincontent">[data table=country col=name key="[loop-data transactions country]"]</td>
+                              </tr>
+                              <tr> 
+                                 <td height="15" colspan="2" class="block4bold"><img src="bg.gif" width="1" height="1"></td>
+                              </tr>
+                           </table>
+                        </td>
+                     </tr>
+                  </table>
+               </td>
+            </tr>
+         </table>
+      </td>
+   </tr>
+   <tr> 
+      <td height=6><img src="bg.gif" width=1 height=6></td>
+   </tr>
+   <tr> 
+      <td> 
+         <!-- CUSTOMERS ORDER GRID -->
+         <table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
+            <tr> 
+               <td width="14%" class=rhead style="padding: 5px">[L]Status[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px">[L]SKU[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px">[L]Name[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px; text-align: right">[L]Qty[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px; text-align: right">[L]Unit Price[/L]</td>
+               <td width="14%" class=rhead style="padding: 5px; text-align: right">[L]Total[/L]</td>
+            </tr>
+[query list=1 sql="select * from orderline where order_number = '[loop-code]'"]
+            <tr class="[sql-alternate 2]rowalt[else]rownorm[/else][/sql-alternate]"> 
+               <td style="padding: 5px">[page href="admin/order_status"
+			   							 form="order=[loop-code]"
+									]
+                [display    table=transactions
                             column=status
                             key="[loop-code]"
                             arbitrary=order_view
-                ][/seti]
-[page href=__UI_BASE__/order_status form="order=[loop-code]"]
-[if scratch statestr !~ /^<.*>$/]
-[scratchd statestr]
-[else]
-[loop-data transactions status]
-[/else]
-[/if]
-</A>
-[set bill_address][/set]
-[set ship_address][/set]
-</td></tr>
-
-<!-- ----- Order information ----- -->
-
-<tr>
-<td width=50 align=center bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-<b>Status</b></font></td>
-
-<td width=230 align=left bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-<b>Name</b></font></td>
-
-<td width=100 align=left bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-<b>SKU</b></font></td>
-
-<td width=50 align=center bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-<b>Qty.</b></font></td>
-
-<td width=70 align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-<b>Each</b></font></td>
-
-<td width=70 align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-<b>Discount</b></font></td>
-
-<td width=80 align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-<b>Total</b></font></td>
-</tr>
-[query st=db sql="select * from orderline where order_number = '[loop-data transactions order_number]'" list=1]
-<tr><td width=50 align=center bgcolor=__UI_C_INTBLOCK__>
-<font size=2>
 [calc]
 	$total_weight += ([field field=weight key="[sql-param sku]"] + 0 || 0) * [sql-data orderline quantity];
 	return;
 [/calc]
-[sql-filter upper]<B>[sql-data orderline status]</B>[/sql-filter]
-<BR>&nbsp;
-</font></td>
-
-<td width=330 bgcolor=__UI_C_INTBLOCK__>
-<font size=2>
-[either][sql-data orderline description][or][data table=__UI_PRODUCT_TABLE__ col=description key="[sql-data orderline sku]"][/either]
-[if-sql-data orderline size]
-<BR>
-Size: [sql-data orderline size]
-[/if-sql-data]
-[if-sql-data orderline color]
-<BR>
-Color: [sql-data orderline color]
-[/if-sql-data]
-
-[if-sql-data orderline options]
-<BR>
-Options: [sql-data orderline options]
-[/if-sql-data]
-</font></td>
-
-<td width=100 align=left bgcolor=__UI_C_INTBLOCK__>
-<font size=2>
-[sql-data orderline sku]
-</font></td>
-
-<td width=50 align=right bgcolor=__UI_C_INTBLOCK__>
-<font size=2>
-[sql-data orderline quantity]
-</font></td>
-
-<td width=70 align=right bgcolor=__UI_C_INTBLOCK__>
-<font size=2>
-[currency][sql-data orderline price][/currency]
-</font></td>
-
-<td width=70 align=right bgcolor=__UI_C_INTBLOCK__>
-<font size=2>
-&nbsp;[sql-data orderline discount]
-</font></td>
-
-<td width=80 align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-[currency][sql-data orderline subtotal][/currency]
-
-</font></td>
-</tr>
+               <td style="padding: 5px">[sql-param sku]</td>
+               <td style="padding: 5px">[sql-filter 30.][sql-param description][/sql-filter]</td>
+               <td align=right style="padding: 5px">[sql-param quantity]</td>
+               <td align=right style="padding: 5px">[sql-param price]</td>
+               <td align=right style="padding: 5px">[sql-param subtotal]</td>
+            </tr>
 [/query]
+            <tr> 
+               <td height=4 colspan=5 class=lightshade><img src="bg.gif" width=1 height=4></td>
+               <td class=lightshade><img src="bg.gif" width=1 height=4></td>
+            </tr>
+            <tr> 
+               <td height=39 colspan=5 align=right class=rsubbold>[L]Item Total[/L]:</td>
+               <td class=rownorm align=right>[currency][loop-data transactions subtotal][/currency]</td>
+            </tr>
+            <tr> 
+               <td colspan=5 align=right class=rsubbold>[L]Tax:[/L]</td>
+               <td class=rownorm align=right>[currency][loop-data transactions salestax][/currency]</td>
+            </tr>
+            <tr> 
+               <td colspan=5 align=right class=rsubbold>[L]Total Weight:[/L]</td>
+               <td class=rownorm align=right>[calc]$total_weight[/calc]</td>
+            </tr>
+			[if-loop-data transactions handling > 0]
+            <tr> 
+               <td colspan=5 align=right class=rsubbold>[L]Shipping[/L]</td>
+               <td class=rownorm align=right>[currency][loop-data transactions shipping][/currency]</td>
+            </tr>
+			[/if-loop-data]
+            <tr> 
+               <td colspan=5 align=right class=rsubbold>[L]Shipping[/L]</td>
+               <td class=rownorm align=right>[currency][loop-data transactions shipping][/currency]</td>
+            </tr>
+            <tr> 
+               <td colspan=5 align=right class=rsubbold>[L]GRAND TOTAL:[/L]</td>
+               <td class=rownormbold align=right>[currency][loop-data transactions total_cost][/currency]</td>
+            </tr>
+         </table>
+      </td>
+   </tr>
+</table>
 
-<!-- ----- Product total ----- -->
-
-<tr>
-<td colspan=6 align=right>
-<font size=2>Product Total:</font>
-</td>
-<td align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>[currency][loop-data transactions subtotal][/currency]</font>
-</td>
-</tr>
-
-<!-- ----- Tax total ----- -->
-
-<tr>
-<td colspan=6 align=right>
-<font size=2>Tax:</font>
-</td>
-<td align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>[currency][loop-data transactions salestax][/currency]</font>
-</td>
-</tr>
-
-<!-- ----- Shipping total ----- -->
-
-<tr>
-<td colspan=6 align=right>
-<font size=2>Shipping: [loop-data transactions shipmode]</font>
-</td>
-<td align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>
-[currency][loop-data transactions shipping][/currency]</font>
-</td>
-</tr>
-
-<!-- ----- Grand total ----- -->
-
-<tr>
-<td colspan=6 align=right>
-<font size=3><b>Grand total:</b></font>
-</td>
-<td align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=3><b>[currency][loop-data transactions total_cost][/currency]<br></b></font>
-</td>
-</tr>
-
-<!-- ----- Weight total ----- -->
-
-<tr></tr>
-
-<tr>
-<td colspan=6 align=right>
-<font size=2>Total weight:</font>
-</td>
-<td align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>[calc] $total_weight [/calc]</font>
-</td>
-</tr>
-
-<!-- ----- Volume total ----- -->
-
-<tr>
-<td colspan=6 align=right>
-<font size=2>Total volume:</font>
-</td>
-<td align=right bgcolor="__UI_C_INTBLOCKBAR__">
-<font size=2>0</font>
-</td>
-</tr>
-<tr>
-<td colspan=6>
-<b>Comments:</b>
-</td>
-</tr>
-
-<tr>
-<td colspan=7 align=left bgcolor=__UI_C_INTBLOCK__>
-<pre>[loop-data transactions comments]</pre>
-</td>
-</tr>
-
-<tr>
-<td colspan=7 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" height=1></td>
-</tr>
 
-</table>
-<SMALL>
+[output name=bottom_buttons]
 <form action="[area __UI_BASE__/order]" method=post>
+<input type=hidden name=mv_session_id value="[data session id]">
 <input type=hidden name=mv_action value=back>
 <input type=hidden name=order value="[loop-data transactions order_number]">
 <input type=hidden name=archive value=false>
 <input type=hidden name=viewnext value=1>
-[set Return]
+[set [L]Return[/L]]
 viewnext=
 vieworder=
 [/set]
-<input type=submit name=mv_click value="Return">
-<input type=submit name="vieworder" value="View next order">
+<input type=submit name=mv_click value="[L]Return[/L]" class=s3>
+<input type=submit name="vieworder" value="[L]View next order[/L]" class=s3>
 
 [if-loop-data transactions archived]
-<input type=submit name="unarchiveorder" value="Un-archive order and view next">
+<input type=submit name="unarchiveorder" value="[L]Un-archive order and view next[/L]" class=s3>
 [else]
-<input type=submit name="archiveorder" value="Archive order and view next">
+<input type=submit name="archiveorder" value="[L]Archive order and view next[/L]" class=s3>
 [/else]
 [/if-loop-data]
-<input type=submit name="deleteorder" value="Delete order and view next" 
- onClick="return confirm('Are you sure you want to delete this order?')">
-
+[if-mm advanced order=d]
+<input type=submit name="deleteorder" value="[L]Delete order and view next[/L]" 
+ onClick="return confirm('[L]Are you sure you want to delete this order?[/L]')" class=s3>
+[/if-mm]
 </form>
-</SMALL>
+
+[output]
 
 [/loop]
+
 <!-- ----- END REAL STUFF ----- -->
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Id: order_view.html,v 1.16.4.6 2003/01/25 22:21:14 racke Exp $ -->



1.8.4.2   +27 -25    interchange/dist/lib/UI/pages/admin/orderstats.html


rev 1.8.4.2, prev_rev 1.8.4.1
Index: orderstats.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/orderstats.html,v
retrieving revision 1.8.4.1
retrieving revision 1.8.4.2
diff -u -r1.8.4.1 -r1.8.4.2
--- orderstats.html	20 Oct 2000 10:18:26 -0000	1.8.4.1
+++ orderstats.html	25 Jan 2003 22:21:14 -0000	1.8.4.2
@@ -1,67 +1,69 @@
-[if !advanced report]
+@_UI_STD_INIT_@[if-mm !advanced orderstats]
+[set ui_error]
+[L]Not authorized for order statistics.[/L]
+[/set]
 [bounce page="__UI_BASE__/error"]
 [value name=saved_report set=""]
-[/if]
+[/if-mm]
 [set ui_class]Reports[/set]
-[set page_title]Order Statistics[/set]
-[set icon_name]admin/icon_stats.gif[/set]
+[set page_title][L]Order Statistics[/L][/set]
+[set icon_name]icon_stats.gif[/set]
 [set help_name]stats.order[/set]
 @_UI_STD_HEAD_@
 
 <table border=0 __UI_T_PROPERTIES__>
-<tr bgcolor="#000000" height=1><td colspan=2></td></tr>
+<tr height=1><td class=rborder colspan=2></td></tr>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><FONT COLOR="__UI_C_TITLEBARTXT__"><B>View stats for this month only</B></FONT></td>
+<td colspan=2 class=rmarq>[L]View stats for this month only[/L]</td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=2></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=2></td></tr>
+<tr height=1><td class=rborder colspan=2></td></tr>
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" colspan=2>
+<td class=rnorm colspan=2>
 
 <BLOCKQUOTE>
-<A HREF="[area __UI_BASE__/reports/order/ByAffiliate]">Overall by month</A><BR>
-<A HREF="[area __UI_BASE__/reports/order/Monthly]">By day for this month</A><BR>
-<A HREF="[area __UI_BASE__/reports/order/Detail]">Individual orders this month</A><BR>
+<A HREF="[area __UI_BASE__/reports/order/ByAffiliate]">[L]Overall by month[/L]</A><BR>
+<A HREF="[area __UI_BASE__/reports/order/Monthly]">[L]By day for this month[/L]</A><BR>
+<A HREF="[area __UI_BASE__/reports/order/Detail]">[L]Individual orders this month[/L]</A><BR>
 </BLOCKQUOTE>
 
 </td>
 </tr>
-<tr bgcolor="#ffffff" height=25><td colspan=2>&nbsp;</td></tr>
+<tr height=1><td class=rborder colspan=2></td></tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><FONT COLOR="__UI_C_TITLEBARTXT__"><B>View stats for any period of time</B></FONT></td>
+<td colspan=2 class=rmarq>[L]View stats for any period of time[/L]</td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=2></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=2></td></tr>
+<tr height=1><td class=rborder colspan=2></td></tr>
 
 <FORM ACTION="[process]">
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=return>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="__UI_BASE__/reports/order/ByAffiliate">
 <TR>
-<TD bgcolor="__UI_C_INTBLOCK__">
-<BLOCKQUOTE>Beginning:<BR>
+<TD class=rnorm>
+<BLOCKQUOTE>[L]Beginning:[/L]<BR>
 	[widget type=date name=ui_begin_date]
 </BLOCKQUOTE>
 </TD>
-<TD bgcolor="__UI_C_INTBLOCK__">
-<BLOCKQUOTE>Ending:<BR>
+<TD class=rnorm>
+<BLOCKQUOTE>[L]Ending:[/L]<BR>
 	[widget type=date name=ui_end_date]
 </BLOCKQUOTE>
 </TD>
 <TR>
-<TD COLSPAN=2 bgcolor="__UI_C_INTBLOCK__">
-	[set List individual orders]
+<TD COLSPAN=2 class=rnorm>
+	[set [L]List individual orders[/L]]
 	mv_nextpage=__UI_BASE__/reports/order/Detail
 	[/set]
-	[set By day]
+	[set [L]By day[/L]]
 	mv_nextpage=__UI_BASE__/reports/order/Monthly
 	[/set]
 	<BLOCKQUOTE>
-	<INPUT TYPE=submit VALUE="By month">&nbsp;&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=mv_click VALUE="By day">&nbsp;&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=mv_click VALUE="List individual orders">
+	<INPUT TYPE=submit VALUE="[L]By month[/L]">&nbsp;&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=mv_click VALUE="[L]By day[/L]">&nbsp;&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=mv_click VALUE="[L]List individual orders[/L]">
 	</BLOCKQUOTE>
 </TD>
 </TR>
-<tr bgcolor="#000000" height=1><td colspan=2></td></tr>
+<tr class=rborder height=1><td colspan=2></td></tr>
 </TABLE>
 </FORM>
 </td>



1.9.4.3   +36 -24    interchange/dist/lib/UI/pages/admin/payment.html


rev 1.9.4.3, prev_rev 1.9.4.2
Index: payment.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/payment.html,v
retrieving revision 1.9.4.2
retrieving revision 1.9.4.3
diff -u -r1.9.4.2 -r1.9.4.3
--- payment.html	20 Oct 2000 10:18:26 -0000	1.9.4.2
+++ payment.html	25 Jan 2003 22:21:14 -0000	1.9.4.3
@@ -1,12 +1,13 @@
+[flag type=write table=variable]
 [set page_title]Payment Options[/set]
 [set ui_class]Admin[/set]
 [set help_name]payment.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
+[set page_perm]payment[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
-[flag type=write table=variable]
 <!-- ----- BEGIN REAL STUFF ----- -->
 [perl tables=variable]
 	delete $Scratch->{change_payment};
@@ -41,7 +42,7 @@
 				]
 			|]
 [value name=ui_changes_made set=1 hide=1]
-<FONT COLOR="__CONTRAST__">You need to [page __UI_BASE__/reconfig @@MV_PAGE@@]apply changes[/page] for changes to take effect.</FONT>
+<span class=cerror>You need to [page __UI_BASE__/reconfig @@MV_PAGE@@]apply changes</a> for changes to take effect.</span>
 [/if]
 
 [calc]
@@ -66,23 +67,28 @@
 <INPUT TYPE=hidden NAME=change_payment VALUE=do>
 
 <table __UI_T_PROPERTIES__>
+
+<tr>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rmarq>Name</td>
+<td class=rmarq>Accepted</td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__><b>Name</b></td>
-<td bgcolor=__UI_C_INTBLOCK__><b>Accepted</b></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 [loop list="[scratch its]" lr=1]
 <tr>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 [loop-pos 1]
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <select name="cc_accepted[loop-increment]">
 <option value=""> Not Accepted
@@ -95,11 +101,11 @@
 
 <tr>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 Online Check
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <select name="check">
 <option value="0"> Not Accepted
@@ -112,11 +118,11 @@
 
 <tr>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 COD
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <select name="cod">
 <option value="0"> Not Accepted
@@ -130,11 +136,11 @@
 
 <tr>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 Postal billing
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <select name="postal">
 <option value="0"> Not Accepted
@@ -147,11 +153,11 @@
 
 <tr>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 Purchase Order
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <select name="po">
 <option value="0"> Not Accepted
@@ -161,8 +167,21 @@
 </td>
 
 </tr>
+
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+
+<tr class=rnorm>
+	<td>&nbsp;</td>
+	<td>
+		<input type=submit name="update" value="Update">
+	</td>
+</tr>
+
+
+<tr>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>
@@ -171,13 +190,6 @@
 [/loop]
 
 <p>
-
-<input type=submit name="update" value="Update">
-
-[button text="Back"]
-mv_todo=back
-mv_nextpage=__UI_BASE__/genconfig
-[/button]
 
 </form>
 



1.5.4.3   +96 -43    interchange/dist/lib/UI/pages/admin/preferences.html


rev 1.5.4.3, prev_rev 1.5.4.2
Index: preferences.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/preferences.html,v
retrieving revision 1.5.4.2
retrieving revision 1.5.4.3
diff -u -r1.5.4.2 -r1.5.4.3
--- preferences.html	20 Oct 2000 10:18:26 -0000	1.5.4.2
+++ preferences.html	25 Jan 2003 22:21:14 -0000	1.5.4.3
@@ -1,19 +1,17 @@
-[set page_title]Preferences[/set]
+[set page_title][L]Preferences[/L][/set]
 [set ui_class]Admin[/set]
 [set page_perm]knar[/set]
 [set help_name]knar.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
+[calc] $Config->{NoSearch} = ''; return; [/calc]
 
-<center>
-<table __UI_T_PROPERTIES__>
-
-<tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
+<div class=titlebox>Edit Preferences</div>
 
+<table style="margin-left: 20px" width="70%">
+	[table-organize columnize=1 cols=4]
 [loop search="
 		fi=variable
 		st=db
@@ -23,63 +21,118 @@
 		tf=pref_group
 		ml=10000
 "]
-<tr><td align=left bgcolor=__UI_C_INTBLOCK__>
-<font size="+1" face="arial,helvetica,sans-serif">
-<a href="[area href="__UI_BASE__/spread" form=|
+<TD width="25%">
+[if-loop-pos 0]
+<a href="[area href="__UI_BASE__/pref_select" form=|
 				mv_data_table=variable
-				page_title=Preferences -- [loop-code]
 				ui_meta_specific=1
 				ui_hide_key=1
-				ui_data_fields=Variable pref_group
 				ui_text_qualification=pref_group=[loop-code]
-				ui_spreadsheet_rows=20
-				ui_spread_size:variable=50
-				ui_spread_meta:variable=1
 				ui_return_to=__UI_BASE__/preferences
+				ui_return_to=page_title=[L]Preferences[/L] -- [loop-code]
+				ui_return_to=ui_text_qualification=pref_group=[loop-code]
+				ui_return_to=ui_hide_key=1
+				help_name=knar.main
+|]">[loop-code]</A>
+[else]
+<a href="[area href="__UI_BASE__/pref_select" form=|
+				mv_data_table=variable
+				ui_meta_specific=1
+				ui_hide_key=1
+				ui_text_qualification=pref_group=
+				ui_return_to=__UI_BASE__/preferences
+				ui_return_to=page_title=[L]Preferences[/L] -- [loop-code]
+				ui_return_to=ui_text_qualification=pref_group=[loop-code]
+				ui_return_to=ui_hide_key=1
 				help_name=knar.main
-|]"> [loop-code] </a>
+|]">(no category)</a>
+[/else]
+[/if-loop-pos]
 </font>
-</td></tr>
+</TD>
 
 [/loop]
+		[/table-organize]
+		</table>
 
-[if !variable UI_META_LINK]
-<tr>
-<td bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__>
-	[if value ui_meta_force]
+[output name=search_box]
+<FORM ACTION="[process href="__UI_BASE__/pref_select"]" METHOD=GET>
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
+<INPUT TYPE=hidden NAME=mv_data_table    VALUE="variable">
+<INPUT TYPE=hidden NAME=ui_meta_specific VALUE="1">
+<INPUT TYPE=hidden NAME=mv_action        VALUE=back>
+
+<span class="s3">Search for a preference:</span><input NAME=ui_text_qualification size=16 class=s3><INPUT TYPE=submit VALUE="[L]Search[/L]" class=s3>
+</FORM>
+
+[output name=""]
+
+
+[if-mm super]
+	<br>
+<div class=titlebox>Table Editor Control</div>
+
+	[if type=explicit compare=`
+			return
+				(! defined $Values->{ui_meta_force} and $Variable->{UI_META_LINK})
+				 ||
+				$Values->{ui_meta_force};
+			`]
 	[page href="@@MV_PAGE@@"
 			form="
 				mv_action=return
-				ui_meta_force=0"]Turn off meta links in database edit</A></td>
+				ui_meta_force=0"][L]Turn off meta links in database edit[/L]</A>
+	[elsif variable UI_META_LINK]
+	[page href="@@MV_PAGE@@"
+			form="
+				mv_action=return
+				ui_meta_force=1"][L]Turn on meta links in database edit[/L]</A>
+	[/elsif]
 	[else]
 	[page href="@@MV_PAGE@@"
 			form="
 				mv_action=return
-				ui_meta_force=1"]Temporarily turn on meta links in database edit</A></td>
+				ui_meta_force=1"][L]Temporarily turn on meta links in database edit[/L]</A>
 	[/else]
 	[/if]
-</tr>
+	<br>
+	[page href="__UI_BASE__/edit_metaconfig"]Configure defaults for table editor</A>
+<br>
+[/if-mm]
+
+[if !variable UI_REGISTERED]
+<br>
+<div class=titlebox>Register </div>
+<a href="http://interchange.redhat.com/cgi-bin/ic/register.html" title="Completely optional">[L]Register[/L]</a>
 [/if]
 
-<tr>
-<td bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-<tr><td bgcolor=__UI_C_INTBLOCK__>
-<a href="http://developer.akopia.com/cgi-bin/ic/register">Register</a>
-</td></tr>
-
-<tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-</table>
-</center>
+<br>
+<br>
 
+		<div class=titlebox>[L]Personal CSS[/L]</div>
+		<form action="[process href="@@MV_PAGE@@"]">
+		[if cgi personal_css]
+			[if type=explicit compare="[userdb function=save profile=ui]"]
+				<span class=cmessage>(saved successfully)</span>
+			[else]
+				<span class=cerror>(save FAILED)</span>
+			[/else]
+			[/if]
+		[/if]
+		<input type=submit value="[L]Set styles[/L]"
+				style="vertical-align: sub;
+						font-size: 8pt;
+						">
+		<br>
+		<table>
+			<tr>
+				<td>
+		<input type=hidden name=mv_session_id value="[data session id]">
+		<input type=hidden name=mv_action value="go">
+		<input type=hidden name=mv_check value="userdb_save">
+		<textarea name=personal_css rows=24 cols=50>[value personal_css]</textarea>
+				</td>
+		</form>
 
 <!-- ----- END REAL STUFF ----- -->
 



1.23.4.3  +48 -264   interchange/dist/lib/UI/pages/admin/quicklinks.html


rev 1.23.4.3, prev_rev 1.23.4.2
Index: quicklinks.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/quicklinks.html,v
retrieving revision 1.23.4.2
retrieving revision 1.23.4.3
diff -u -r1.23.4.2 -r1.23.4.3
--- quicklinks.html	20 Oct 2000 19:40:19 -0000	1.23.4.2
+++ quicklinks.html	25 Jan 2003 22:21:14 -0000	1.23.4.3
@@ -1,283 +1,41 @@
-<html>
+@_UI_STD_INIT_@<html>
 <head>
 <title>
-Quicklinks
+[L]Quicklinks[/L]
 </title>
-<style type="text/css">
-<!--
- a:visited { text-decoration: none }
- a:active { text-decoration: none }
- a:link { text-decoration: none }
-  -->
-</style>
+<link href="@_UI_IMAGE_DIR_@ic.css" rel="stylesheet" type="text/css" title="Main IC stylesheet">
+[if value personal_css]<style>[value personal_css]</style>[/if]
 </head>
 
 <body bgcolor="__UI_P_BG__" link="__UI_P_LINK__" alink="__UI_P_ALINK__" vlink="__UI_P_VLINK__">
 
 <div valign=middle>
 <center>
-<table border=0 width=120 cellpadding=1 cellspacing=0 bgcolor="__UI_C_TOPBLOCKBAR__">
+<table border=0 width=120 cellpadding=1 cellspacing=0 class=rborder>
 <tr>
-<td>
+<td class=rtitle>
 
-<table border=0 width=100% cellpadding=1 cellspacing=0>
-<tr>
-<td bgcolor="__UI_C_INTBLOCK__" nowrap>
-
-<font size=2 face="Verdana,Arial,Helvetica,sans-serif">
+<table border=0 width="100%" cellpadding=1 cellspacing=0>
+<tr class=rnorm>
+<td class=rnorm nowrap style="font-size: smaller">
 
 [if !scratch window_override]
 [seti win][data session arg][/seti]
 [/if]
 
-<b>Store Admin:</b>
-<br><br>
-
-[if-mm advanced order]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/order]">
-Orders</a><br>
-[/if-mm]
-
-[if-mm advanced userdb]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/customer]">
-Customers</a><br>
-[/if-mm]
-
-[if-mm advanced userdb]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/entry]">
-Order entry</a><br>
-[/if-mm]
-<P>
-[if-mm advanced orderstats]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/orderstats]">
-Order stats</a><br>
-[/if-mm]
-
-[if-mm advanced trafficstats]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/trafficstats]">
-Traffic stats</a><br>
-[/if-mm]
-
-[if-mm advanced affiliate]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/affiliates]">
-Affiliates</a><br>
-[/if-mm]
-<P>
-[if-mm advanced item]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/item]">
-Items</a><br>
-[/if-mm]
-
-
-[if-mm advanced sitedesign]
-<hr noshade size=1>
-<b>Site Design:</b>
-<br><br>
-
-
-
-[if-mm advanced layout]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/layout]">Site Layout</a><br>
-[/if-mm]
-
-
-[if-mm advanced layout]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/page]">
-Page Edit</a><br>
-[/if-mm]
-
-[if-mm advanced searchbuilder]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/regenerate]">
-Generate static</a><br>
-[/if-mm]
-
-[if-mm advanced searchbuilder]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/build_related]">
-Build related</a><br>
-[/if-mm]
-
-[if-mm advanced searchbuilder]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/search_wizard]">
-Search Builder</a><br>
-[/if-mm]
-
-[if-mm advanced buttonbuilder]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/button_builder]">
-Button Builder</a><br>
-[/if-mm]
-
-[/if-mm]
-
-<br>
-
-<hr noshade size=1>
-
-[if-mm advanced techadmin]
-<b>Technical Admin:</b>
-<br>
-<br>
-
-
-[if-mm advanced tax]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/tax]">
-Tax</a><br>
-[/if-mm]
-
-[if-mm advanced shipping]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/ship]">
-Shipping</a><br>
-[/if-mm]
-
-[if-mm advanced payment]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/payment]">
-Payment</a><br>
-[/if-mm]
-
-<br>
-
-
-[if-mm files]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/genupload]">
-File transfer</a><br>
-<p>
-[/if-mm]
-
-[if-mm advanced table_edit]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/gentable]">
-Direct Table Edit</a><br>
-[/if-mm]
-
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/import_table]">
-Table import</a><br>
-
-
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/export_table]">
-Table export</a><br>
-
-<br>
-
-[if-mm advanced access]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/access]">
-Administrators</a><br>
-[/if-mm]
-
-[if-mm advanced group]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/group]">
-Admin Groups</a><br>
-[/if-mm]
-
-[if-mm advanced perm]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/access_permissions]">
-Permissions</a><br>
-[/if-mm]
-
-<br>
-
-[if-mm advanced env_vars]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/env_vars]">
-Environment</a><br>
-[/if-mm]
-
-
-[if-mm advanced knar]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area href=__UI_BASE__/preferences]">
-Preferences</a><br>
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area href=__UI_BASE__/flex_select
-				form='
-					mv_data_table=variable
-					page_title=Knar editor
-					ui_meta_specific=1
-					help_name=knar.main
-				']">
-Knar editor</a><br>
-[/if-mm]
-
-<br>
-
-<hr noshade size=1>
-[/if-mm]
-
-<b>
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/logout]">
-Logout</a><br>
-</b>
+[menu menu-type=simple name=Quicklinks menu_group=mgroup]
+{PAGE:}
+	<b>{NAME?}{NAME}{/NAME?}</b>
+	<br>
+{/PAGE:}{PAGE?}
+&nbsp;&nbsp;&nbsp;
+<a
+	target="mainwindow{WIN}"
+	href="{HREF}"{DESCRIPTION?}
+	title="{DESCRIPTION}"{/DESCRIPTION?}>{NAME}</a><br>
+{/PAGE?}
+[/menu]
 
-
-[if-mm advanced reconfig]
-<b>
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/reconfig]">
-Apply Changes</a><br>
-</b>
-[/if-mm]
-
-<br>
-
-[comment]
-
-[if-mm advanced perm]
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/access_permissions]">
-Permissions</a><br>
-[/if-mm]
-
-<br>
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/dbupload]">
-Database import</a><br>
-
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/gensql]">
-Direct SQL</a><br>
-
-&nbsp;&nbsp;&nbsp;
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/dbdownload]">
-Database export</a><br>
-
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/config]">
-Technical settings</a>
-
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/prefs]">
-Change preferences</a><br>
-
-
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/affiliates]">
-Affiliates</a><br>
-
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/page]">
-Pages</a><br>
-
-
-<a target="mainwindow[scratch win]" href="[area __UI_BASE__/matrix]">
-Matrix</a>
-
-
-[/comment]
 </FONT>
                 </TD>
         </TR>
@@ -285,7 +43,33 @@
 </td></tr></table>
 </center>
 </div>
-<div align="center"><a href="javascript:self.window.close()">[close]</a></div>
+<div align="center">
+<a href="javascript:self.window.close()">&#91;[L]close[/L]]</a>
+<br>
+<a  target="mainwindow[scratch win]"
+	href="[area href='__UI_BASE__/menu_editor'
+				form='
+					qmenu_name=Quicklinks
+				'
+			]">&#91;[L]edit[/L]]</a>
+[if cgi mgroup eq full]
+<a href="[area
+			href='@@MV_PAGE@@'
+			form='
+				mv_arg=[scratch win]
+				'
+		]">&#91;[L]short menu[/L]]</a>
+[else]
+<a href="[area
+			href='@@MV_PAGE@@'
+			form='
+				mgroup=full
+				mv_arg=[scratch win]
+				'
+		]">&#91;[L]full menu[/L]]</a>
+[/else]
+[/if]
+</div>
 </BODY>
 </HTML>
 



1.9.4.2   +21 -23    interchange/dist/lib/UI/pages/admin/reconfig.html


rev 1.9.4.2, prev_rev 1.9.4.1
Index: reconfig.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/reconfig.html,v
retrieving revision 1.9.4.1
retrieving revision 1.9.4.2
diff -u -r1.9.4.1 -r1.9.4.2
--- reconfig.html	14 Oct 2000 14:47:56 -0000	1.9.4.1
+++ reconfig.html	25 Jan 2003 22:21:14 -0000	1.9.4.2
@@ -1,38 +1,36 @@
-[if-mm !reconfig]
-[set ui_error]Not authorized to regenerate.[/set]
+@_UI_STD_INIT_@[if-mm !advanced reconfig]
+[set ui_error][L]Not authorized to regenerate.[/L][/set]
 [bounce page="__UI_BASE__/error"]
 [/if-mm]
 [set help_name]reconfig[/set]
 [set ui_class]Admin[/set]
-[set page_title]Reconfiguring....[/set]
-[seti meta_header]
-[set name=its int][calc]
-					$hk = q{[global-value Global::HouseKeeping]};
-					$hk += 2;
-					return join " ", 1 .. $hk;
-				[/calc][/set]
-[/seti]
-[set icon_name]admin/icon_regen.gif[/set]
-@_UI_STD_HEAD_@
+[set page_title][L]Reconfiguring[/L]....[/set]
+[tmp meta_header]
+<META HTTP-EQUIV="refresh" content="[calc]
+		my $secs = $Tag->global_value('Global::HouseKeeping') || 10;
+		$secs += 2;
+		my $url = $Tag->area({
+							href => 'admin/genconfig',
+							form => 'start_at_index=1',
+							});
+		return "$secs; URL=$url";
+		[/calc]">
+[/tmp]
 
-[L]Reconfiguring catalog[/L]: ...<BR>[seti reconfig_status][reconfigure][/seti]
+[set icon_name]icon_regen.gif[/set]
 
-[loop arg="[scratch its]"]
-[reconfig-wait send=1]
-[/loop]
+@_UI_STD_HEAD_@
 
-[if scratch possible_timeout]
- [L]WARNING: Reconfiguration may have timed out[/L].<BR>
-[L]Last config[/L]: [reconfig-time]
+[L]Reconfiguring catalog[/L]...
+[if type=explicit compare="[reconfigure]"]
+[L]Catalog reconfigure request was sent successfully, please wait....[/L]
 [else]
-[L]SUCCESS[/L]
-[value name=ui_changes_made set=""]
+[L]Catalog reconfigure request failed.[/L]
 [/else]
 [/if]
-(<A HREF="[area href="[either][data session arg][or]__UI_BASE__/index[/either]"]">[L]return[/L]</A>)<BR>
 </HTML>
 
 <!-- ----- END REAL STUFF ----- -->
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 1.9.4.2 $ -->



1.7.4.1   +2 -1      interchange/dist/lib/UI/pages/admin/regen.html


rev 1.7.4.1, prev_rev 1.7
Index: regen.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/regen.html,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- regen.html	25 Sep 2000 11:32:41 -0000	1.7
+++ regen.html	25 Jan 2003 22:21:14 -0000	1.7.4.1
@@ -1,3 +1,4 @@
+@_UI_STD_INIT_@
 [if-mm !regen]
 [set ui_error]Not authorized to regenerate.[/set]
 [bounce page="__UI_BASE__/error"]
@@ -5,6 +6,6 @@
 [set ui_class]Design[/set]
 [set help_name]reconfig[/set]
 [set page_title]Regenerating....[/set]
-[set icon_name]admin/icon_regen.gif[/set]
+[set icon_name]icon_regen.gif[/set]
 [set spacer]&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[/set]
 [regenerate]



1.5.4.2   +13 -12    interchange/dist/lib/UI/pages/admin/regenerate.html


rev 1.5.4.2, prev_rev 1.5.4.1
Index: regenerate.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/regenerate.html,v
retrieving revision 1.5.4.1
retrieving revision 1.5.4.2
diff -u -r1.5.4.1 -r1.5.4.2
--- regenerate.html	10 Oct 2001 08:03:19 -0000	1.5.4.1
+++ regenerate.html	25 Jan 2003 22:21:14 -0000	1.5.4.2
@@ -1,9 +1,9 @@
-[set page_title]Static site generation[/set]
-[set page_banner]Static site generation[/set]
+[set page_title][L]Static site generation[/L][/set]
+[set page_banner][L]Static site generation[/L][/set]
 [set page_perm]regen[/set]
 [set help_name]regen.main[/set]
 [set ui_class]Design[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
@@ -14,13 +14,13 @@
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width="__UI_LEFT_WIDTH__" valign=top>
+<td class=rnorm width="__UI_LEFT_WIDTH__" valign=top>
 
-<input type="submit" value="Regenerate"><BR><BR>
-<input type=checkbox name=ui_build_verbose> Verbose<br>
+<input type="submit" value="[L]Regenerate[/L]"><BR><BR>
+<input type=checkbox name=ui_build_verbose> [L]Verbose[/L]<br>
 <select NAME=ui_max_build>
 <option VALUE=100>100
 <option VALUE=200>200
@@ -31,7 +31,7 @@
 <option VALUE=10000>10,000
 </select>
 </td>
-<td bgcolor="__UI_C_INTBLOCK__" width="__UI_RIGHT_WIDTH__">
+<td class=rnorm width="__UI_RIGHT_WIDTH__">
 
 [tmp pages][/tmp]
 
@@ -58,6 +58,7 @@
 			$_ = '' if defined $check->{$test};
 		} while ($test =~ s:(.*)/.*:$1:);
 	}
+	@pages = grep length($_), @pages;
 	$Scratch->{pages} = join "\n", grep $_, @pages;
 
     # Generated selection of forced pages
@@ -75,7 +76,7 @@
 [/calc]
 
 [if config StaticAll]
-<b>Entry page:</b><br>
+<b>[L]Entry page:[/L]</b><br>
 
 
 <select name="ui_initial_page">
@@ -87,14 +88,14 @@
 	<table>
 		<tr>
 			<td>
-			<b>Force build of:</b><br>
+			<b>[L]Force build of:[/L]</b><br>
 			<select name="ui_force_build" multiple size=25>
 			[scratchd forced_pages]  
 			</select>
 			</td>
 			<td>
 
-			<b>Never build:</b><br>
+			<b>[L]Never build:[/L]</b><br>
 			<select name="ui_never_build" multiple size=25>
 			[loop prefix=never list="[scratch pages]"]
 				<option>[never-code]
@@ -107,7 +108,7 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.9.4.2   +25 -25    interchange/dist/lib/UI/pages/admin/report.html


rev 1.9.4.2, prev_rev 1.9.4.1
Index: report.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/report.html,v
retrieving revision 1.9.4.1
retrieving revision 1.9.4.2
diff -u -r1.9.4.1 -r1.9.4.2
--- report.html	12 Oct 2000 12:47:56 -0000	1.9.4.1
+++ report.html	25 Jan 2003 22:21:14 -0000	1.9.4.2
@@ -2,10 +2,10 @@
 [set ui_error]Not authorized for table.[/set]
 [bounce page="__UI_BASE__/error"]
 [/if-mm]
-[if !advanced report]
+[if-mm !advanced report]
 [bounce page="__UI_BASE__/error"]
 [value name=saved_report set=""]
-[/if]
+[/if-mm]
 [if !cgi mv_data_table]
 [and !value saved_report]
 [bounce page="__UI_BASE__/gentable"]
@@ -17,7 +17,7 @@
 [seti page_title]Custom report [if value mv_data_table][value mv_data_table][/if][/seti]
 [set help_name]report[/set]
 [set ui_class]Reports[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [seti name=tables][list-databases][/seti]
 [seti meta_header]
 [perl table="[scratch tables]"]
@@ -185,22 +185,22 @@
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=3></td>
+<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=3></td>
 </tr>
 
 <TR>
-<TD BGCOLOR="__UI_C_INTBLOCK__" VALIGN=TOP WIDTH=200>
-	<IMG src="@_UI_IMG_@admin/icon_stats.gif"><B>
+<TD class=rnorm VALIGN=TOP WIDTH=200>
+	<IMG src="icon_stats.gif"><B>
 		Run saved report
 	</B>
 </TD>
-<TD BGCOLOR="__UI_C_INTBLOCK__" VALIGN=TOP WIDTH=200>
-	<IMG src="@_UI_IMG_@admin/icon_config.gif"><B>
+<TD class=rnorm VALIGN=TOP WIDTH=200>
+	<IMG src="icon_config.gif"><B>
 		Retrieve saved definition
 	</B>
 </TD>
-<TD BGCOLOR="__UI_C_INTBLOCK__" VALIGN=TOP WIDTH=200>
-	<IMG src="@_UI_IMG_@admin/icon_error.gif"><B>
+<TD class=rnorm VALIGN=TOP WIDTH=200>
+	<IMG src="icon_error.gif"><B>
 		Delete report
 	</B>
 </TD>
@@ -313,11 +313,11 @@
 <P>
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCK__>
+<td colspan=2 class=rnorm>
 <FORM NAME=report ACTION="[area __UI_BASE__/report_results]" METHOD=POST>
 <INPUT TYPE=hidden NAME=report_table VALUE="[value mv_data_table]">
 <INPUT TYPE=submit VALUE=Run>
@@ -327,14 +327,14 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH=20%>
+	<TD class=rnorm WIDTH=20%>
 		<B>Report Title</B>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__">
+	<TD class=rnorm>
 	<INPUT NAME="report_title" VALUE="[value report_title]">
 	Summary only <SELECT NAME="summary_only">
 	<OPTION VALUE="0">no
@@ -348,15 +348,15 @@
 </TR>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 [loop list="0 1 2"]
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH=20%>
+	<TD class=rnorm WIDTH=20%>
 		<B>Search filter</B>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__">
+	<TD class=rnorm>
 	<SELECT NAME="search_field[loop-code]">
 	<OPTION VALUE="[value search_field[loop-code]]">[value name=search_field[loop-code] default="--"]
 	<OPTION VALUE="">--none--
@@ -383,16 +383,16 @@
 [/loop]
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 
 [loop list="0 1 2"]
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH=20%>
+	<TD class=rnorm WIDTH=20%>
 		<B>Sort order [loop-increment]</B>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__">
+	<TD class=rnorm>
 	<SELECT NAME="sort_order[loop-code]">
 	<OPTION VALUE="[value sort_order[loop-code]]">[value name=sort_order[loop-code] default="--"]
 	<OPTION VALUE="">--none--
@@ -422,11 +422,11 @@
 [loop list="[scratch column_nums]"]
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH=20% VALIGN=TOP>
+	<TD class=rnorm WIDTH=20% VALIGN=TOP>
 		<B>Column [loop-increment]</B><BR>
 		<FONT SIZE="-1">
 		<INPUT onClick='this.form.submit()' TYPE=checkbox NAME="row_change" VALUE="insert[loop-code]"> insert<BR>
@@ -434,7 +434,7 @@
 		<INPUT onClick='this.form.submit()' TYPE=checkbox NAME="row_change" VALUE="delete[loop-code]"> delete<BR>
 		</FONT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" ALIGN=LEFT>
+	<TD class=rnorm ALIGN=LEFT>
 	<FONT SIZE="-1">
 	<SELECT NAME="table[loop-code]" onChange="populateTable(
 			this.form.table[loop-code].options,
@@ -507,7 +507,7 @@
 [/loop]
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCK__>
+<td colspan=2 class=rnorm>
 <INPUT TYPE=submit VALUE=Run>
 [if-mm advanced mml]
 <INPUT TYPE=submit NAME=generate_page VALUE="Generate definition">



1.3.4.1   +2 -2      interchange/dist/lib/UI/pages/admin/report_results.html


rev 1.3.4.1, prev_rev 1.3
Index: report_results.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/report_results.html,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- report_results.html	14 Sep 2000 07:46:48 -0000	1.3
+++ report_results.html	25 Jan 2003 22:21:14 -0000	1.3.4.1
@@ -8,7 +8,7 @@
 [/if-mm]
 [seti page_title][cgi report_title][/seti]
 [set ui_class]Reports[/set]
-[set icon_name]admin/icon_stats.gif[/set]
+[set icon_name]icon_stats.gif[/set]
 [set help_name]report[/set]
 [calc]
 	$Scratch->{head_put} = '@' . '_UI_STD_HEAD_@';
@@ -412,7 +412,7 @@
 Report name: <INPUT NAME=report_name VALUE="[cgi report_title]"><INPUT TYPE=submit VALUE=Save><BR CLEAR=LEFT>
 <TEXTAREA ROWS=50 COLS=80 NAME=page>
 &#91;set page_title][cgi report_title][/set]
-&#91;set icon_name]admin/icon_stats.gif[/set]
+&#91;set icon_name]icon_stats.gif[/set]
 &#91;set table_perm]1[/set]
 [scratch head_put]
 <TABLE>



1.1.4.1   +1 -0      interchange/dist/lib/UI/pages/admin/report_save.html


rev 1.1.4.1, prev_rev 1.1
Index: report_save.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/report_save.html,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- report_save.html	18 Jun 2000 08:42:45 -0000	1.1
+++ report_save.html	25 Jan 2003 22:21:14 -0000	1.1.4.1
@@ -1,3 +1,4 @@
+@_UI_STD_INIT_@
 [if value success]
 	[bounce page="__UI_BASE__/report"]
 [/if]



1.4.4.1   +58 -66    interchange/dist/lib/UI/pages/admin/search_wizard.html


rev 1.4.4.1, prev_rev 1.4
Index: search_wizard.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/search_wizard.html,v
retrieving revision 1.4
retrieving revision 1.4.4.1
diff -u -r1.4 -r1.4.4.1
--- search_wizard.html	23 Sep 2000 17:55:33 -0000	1.4
+++ search_wizard.html	25 Jan 2003 22:21:14 -0000	1.4.4.1
@@ -1,7 +1,8 @@
-[seti page_title]Search wizard[/seti]
+[seti page_title][L]Search Builder[/L][/seti]
 [set help_name]search_builder[/set]
 [set ui_class]Design[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set display_class]type5[/set]
+[set icon_name]icon_config.gif[/set]
 [seti name=tables][list-databases][/seti]
 [seti meta_header]
 [perl table="[scratch tables]"]
@@ -227,22 +228,26 @@
 
 @_UI_STD_HEAD_@
 
-<FORM NAME=search_wizard ACTION="[process]" METHOD=POST>
+<FORM NAME=search_wizard ACTION="[process]" METHOD=GET>
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
+<INPUT TYPE=hidden NAME=ui_target VALUE="[cgi ui_target]">
+<INPUT TYPE=hidden NAME=ui_source_form VALUE="[cgi ui_source_form]">
+<INPUT TYPE=hidden NAME=ui_source_var VALUE="[cgi ui_source_var]">
+<INPUT TYPE=hidden NAME=display_class VALUE="[cgi display_class]">
 [return-to]
 
 <P>
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search Table</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		[L]Search Table[/L]
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<SELECT NAME=search_table>
 	[if !value search_table]
 	[calc]
@@ -256,50 +261,45 @@
 	[/loop]
 	</SELECT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
-	The search must be based on a table, by default the main items table.<br><br>
-	<small>
-	NOTE: It is possible to search multiple tables in Interchange, but that is
-	not supported by this wizard.</small>
-	</small>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
+	[L]The search must be based on a table, by default the main items table.[/L]</small><br><br>
+	[L]NOTE: It is possible to search multiple tables in Interchange, 
+but that is not supported by this wizard.[/L]
 	</TD>
 </tr>
 
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search locality</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		[L]Search locality[/L]
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<select name=search_type>
-	<OPTION VALUE="db"> Database
-	<OPTION VALUE="text" [selected search_type text]> Text file
+	<OPTION VALUE="db"> [L]Database[/L]
+	<OPTION VALUE="text" [selected search_type text]> [L]Text file[/L]
 	</select>
 
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
-	For full-text searches, it is usually better to search the text file
-	source of the database (create at [page __UI_BASE__/genexport]Direct table export[/page]). When using SQL databases, the coordinated field-based searches are much
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
+	[msg arg.0="[page __UI_BASE__/export_table][L]Direct table export[/L]</a>"]For full-text searches, it is usually better to search the text file
+	source of the database (create at %s). When using SQL databases, the coordinated field-based searches are much
 	faster when the first search term is "equals to".
-	</small>
 	</TD>
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search Template</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		[L]Search Template[/L]
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<select NAME="search_template">
 		<option value=""> --default ([calc] $Config->{Special}{results} [/calc]) --
 		[loop option=search_template list="[list-pages]"]
@@ -307,93 +307,85 @@
 		[/loop]
 	</select>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	The results of the search are sent to a page template, by default
 	<b>[calc]$Config->{Special}{results};[/calc]</B>.<P>
 	If you select a page, it should have the [search-region] area necessary
 	to read and build the search.
-	</small>
 	</TD>
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Page size</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		[L]Page size[/L]
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<SELECT NAME="matchlimit">
 		[loop list="50 1 2 3 5 10 20 25 50 100 9999" option=matchlimit]<OPTION>[loop-code][/loop]
 	</SELECT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
-	You can limit the number of results per page, and use the
-	template &#91;more-list] to page between matches. The default is 50.
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
+	[L]You can limit the number of results per page, and use the
+	template &#91;more-list] to page between matches. The default is 50.[/L]
 	</TD>
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Unique only</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		[L]Unique only[/L]
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<SELECT NAME="unique_results">
-		<OPTION VALUE="">No
-		<OPTION VALUE="1" [selected unique_results 1]>Yes
+		<OPTION VALUE="">[L]No[/L]
+		<OPTION VALUE="1" [selected unique_results 1]>[L]Yes[/L]
 	</SELECT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
-	Normally one search result is returned for every matching record. If you
-	wish to eliminate duplicate result returns, you can use this.
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
+	[L]Normally one search result is returned for every matching record. If you
+	wish to eliminate duplicate result returns, you can use this.[/L]
 	</TD>
 </tr>
 
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Allow full expressions</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		[L]Allow full expressions[/L]
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<SELECT NAME="allow_regex">
-		<OPTION VALUE="">No
-		<OPTION VALUE="1" [selected allow_regex 1]>Yes
+		<OPTION VALUE="">[L]No[/L]
+		<OPTION VALUE="1" [selected allow_regex 1]>[L]Yes[/L]
 	</SELECT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
-	Normally characters are searched for literally, i.e. a period
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
+	[L]Normally characters are searched for literally, i.e. a period
 	will match a period. If you wish to use the power of Perl regular
 	expressions in your matching criteria, select <B>Yes</B>. Bear 
 	in mind that some things you enter may not behave just as you
 	might think they will; see <i>perldoc perlre</i> for a complete
-	description of what Perl regular expressions are.
-	</TD>
+	description of what Perl regular expressions are.[/L]
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCK__>
-[button text="Cancel"]
-	[return-to click]
-[/button]&nbsp;&nbsp;&nbsp;&nbsp;[button text="Next -->"]
+<td colspan=3 class=rnorm>
+<input type=submit name=mv_click value="[L]Cancel[/L]">&nbsp;&nbsp;&nbsp;&nbsp;[button text="[L]Next[/L] -->"]
 	mv_nextpage=__UI_BASE__/search_wizard2
 [/button]
 </tr>



1.3.4.1   +46 -48    interchange/dist/lib/UI/pages/admin/search_wizard2.html


rev 1.3.4.1, prev_rev 1.3
Index: search_wizard2.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/search_wizard2.html,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- search_wizard2.html	23 Sep 2000 17:55:33 -0000	1.3
+++ search_wizard2.html	25 Jan 2003 22:21:14 -0000	1.3.4.1
@@ -1,7 +1,8 @@
-[seti page_title]Search wizard: criteria [calc] $CGI->{current_column} + 1[/calc][/seti]
+[seti page_title]Search Builder: criteria [calc] $CGI->{current_column} + 1[/calc][/seti]
 [set help_name]search_builder[/set]
 [set ui_class]Design[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set display_class]type5[/set]
+[set icon_name]icon_config.gif[/set]
 [seti name=tables][list-databases][/seti]
 [seti meta_header]
 [perl table="[scratch tables]"]
@@ -145,22 +146,26 @@
 
 @_UI_STD_HEAD_@
 
-<FORM NAME=search_wizard ACTION="[process]" METHOD=POST>
+<FORM NAME=search_wizard ACTION="[process]" METHOD=GET>
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
 <INPUT TYPE=hidden NAME=current_column VALUE="[value current_column]">
+<INPUT TYPE=hidden NAME=ui_target VALUE="[cgi ui_target]">
+<INPUT TYPE=hidden NAME=ui_source_form VALUE="[cgi ui_source_form]">
+<INPUT TYPE=hidden NAME=ui_source_var VALUE="[cgi ui_source_var]">
+<INPUT TYPE=hidden NAME=display_class VALUE="[cgi display_class]">
 [return-to]
 <P>
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 [loop list="[value current_column]"]
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search table</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Search table
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 	[if !value current_column]
 		<B>[value search_table]</b>
@@ -178,8 +183,7 @@
 	[/else]
 	[/if]
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	[if !value current_column]
 		Since this is the first specification in the search, it must be based
 		on your current table. Use <I>Back</I> to change the table.
@@ -196,14 +200,14 @@
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search field</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Search field
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 
 	<SELECT NAME="search_field[loop-code]">
@@ -215,24 +219,22 @@
 	</SELECT>
 
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	You can search one specific field for a value. If you don't select a field,
 	a full-text search will be done on all fields of the database record.
-	</small>
 	</TD>
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search operation</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Search operation
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 	<SELECT NAME="search_op[loop-code]">
 	[loop prefix=op list="rm	Regular expression match
@@ -251,8 +253,7 @@
 	[/loop]
 	</SELECT></FONT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	You can use any number of search comparisons. Bear in mind that <I>equal to</i>
 	means exactly that; you should use <i>regular expression match</i> if you want
 	to search for contained text.
@@ -261,63 +262,60 @@
 
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search for</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Search for
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 	<INPUT NAME="search_spec[loop-code]" VALUE="[value search_spec[loop-code]]">
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	This is what you are searching for.
 	</TD>
 </tr>
 
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Case sensitive</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Case sensitive
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 	<SELECT NAME=case_sensitive[loop-code]>
 	<OPTION VALUE="">Not case-sensitive
 	<OPTION VALUE=1 [selected case_sensitive[loop-code] 1]>Yes, case-sensitive
 	</SELECT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	If a text search, you can specify to match case-sensitively.
 	</TD>
 </tr>
 
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Word/partial word</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Word/partial word
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 	<SELECT NAME=substring[loop-code]>
 	<OPTION VALUE="">Match words only
 	<OPTION VALUE=1 [selected substring[loop-code] 1]>Match partial
 	</SELECT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	If you select partial, a search for "bread" would match "breadbasket"
 	and "bread". If you select whole words, it would only match "bread".
 	</TD>
@@ -325,22 +323,21 @@
 
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Match beginning</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Match beginning
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 	<SELECT NAME=begin_string[loop-code]>
 	<OPTION VALUE="">Match anywhere in field
 	<OPTION VALUE=1 [selected begin_string[loop-code] 1]>Match beginning
 	</SELECT>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	Determines whether you must match the beginning of a search field.
 	<p>
 	By default, a search for of "bread" would match both "rye bread" and "bread
@@ -349,12 +346,12 @@
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 [/loop]
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCK__>
+<td colspan=3 class=rnorm>
 [button text="Cancel"]
 	saved_search=
 	mv_todo=return
@@ -379,6 +376,7 @@
 [/button]&nbsp;&nbsp;&nbsp;&nbsp;[button text="Next -->"]
 	mv_data_table=[value search_table]
 	mv_nextpage=__UI_BASE__/search_wizard3.html
+	[set Cancel][/set]
 [/button]
 </tr>
 



1.3.4.1   +21 -20    interchange/dist/lib/UI/pages/admin/search_wizard3.html


rev 1.3.4.1, prev_rev 1.3
Index: search_wizard3.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/search_wizard3.html,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- search_wizard3.html	23 Sep 2000 17:55:33 -0000	1.3
+++ search_wizard3.html	25 Jan 2003 22:21:14 -0000	1.3.4.1
@@ -1,7 +1,8 @@
-[seti page_title]Search wizard: sorting[/seti]
+[seti page_title]Search Builder: sorting[/seti]
 [set help_name]search_builder[/set]
 [set ui_class]Design[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set display_class]type5[/set]
+[set icon_name]icon_config.gif[/set]
 [seti name=tables][list-databases][/seti]
 [seti meta_header]
 [perl table="[scratch tables]"]
@@ -133,21 +134,25 @@
 
 @_UI_STD_HEAD_@
 
-<FORM NAME=search_wizard ACTION="[process]" METHOD=POST>
+<FORM NAME=search_wizard ACTION="[process]" METHOD=GET>
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
 <INPUT TYPE=hidden NAME=current_column VALUE="[value current_column]">
+<INPUT TYPE=hidden NAME=ui_target VALUE="[cgi ui_target]">
+<INPUT TYPE=hidden NAME=ui_source_form VALUE="[cgi ui_source_form]">
+<INPUT TYPE=hidden NAME=ui_source_var VALUE="[cgi ui_source_var]">
+<INPUT TYPE=hidden NAME=display_class VALUE="[cgi display_class]">
 [return-to]
 <P>
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Sort field</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Sort field
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 
 	[loop list="0 1 2"]
@@ -168,23 +173,21 @@
 	[/loop]
 
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<SMALL>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	You can sort the search return on one or more fields, with some options.
-	</small>
 	</TD>
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=3 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 
 <TR>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="20%" VALIGN=top>
-		<small><B>Search return field</B></small>
+	<TD class=rnorm WIDTH="20%" VALIGN=top>
+		Search return field
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	<small>
 	[loop list="1 2 3 4 5"]
 	<SELECT NAME="return[loop-code]">
@@ -195,18 +198,16 @@
 	[/loop]
 	</small>
 	</TD>
-	<TD BGCOLOR="__UI_C_INTBLOCK__" WIDTH="40%" VALIGN=top>
-	<small>
+	<TD class=rnorm WIDTH="40%" VALIGN=top>
 	By default, the database key for the searched table or file is returned. If
 	you are designing your own results page, you can optionally return more
 	fields for use with the &#91PREFIX-param field] tags.
-	</small>
 	</TD>
 </tr>
 
 <tr>
-<td colspan=3 bgcolor=__UI_C_INTBLOCK__>
-[button text="Cancel"]
+<td colspan=3 class=rspacer>
+[button text="Cancel search"]
 	saved_search=
 	mv_todo=return
 	[return-to click]
@@ -217,8 +218,8 @@
 	mv_nextpage=__UI_BASE__/search_wizard_results.html
 [/button]&nbsp;&nbsp;&nbsp;&nbsp;[button text="Finish -->"]
 	generate_page=1
-	[return_to click]
 	mv_nextpage=__UI_BASE__/search_wizard_results.html
+	[set Cancel search][/set]
 [/button]
 </tr>
 



1.2.4.1   +30 -1     interchange/dist/lib/UI/pages/admin/search_wizard_results.html


rev 1.2.4.1, prev_rev 1.2
Index: search_wizard_results.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/search_wizard_results.html,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- search_wizard_results.html	14 Sep 2000 07:46:48 -0000	1.2
+++ search_wizard_results.html	25 Jan 2003 22:21:14 -0000	1.2.4.1
@@ -7,7 +7,8 @@
 [bounce page="__UI_BASE__/error"]
 [/if-mm]
 [seti page_title][cgi report_title][/seti]
-[set icon_name]admin/icon_stats.gif[/set]
+[set icon_name]icon_stats.gif[/set]
+[set display_class]type5[/set]
 [set ui_class]Design[/set]
 [set help_name]report[/set]
 
@@ -170,6 +171,7 @@
 	$page .= "\tsearch=$qchar\n\t\t";
 	$page .= join "\n\t\t", @string;
 	$page .= "\n\t$qchar\n]";
+	$Scratch->{search_blob} = join "\r", grep /^\s*\w+=/, @string;
 	$Scratch->{search_page} = $page;
 	$Scratch->{rows} = scalar(@string) + 5;
 	return;
@@ -187,10 +189,37 @@
 [/elsif]
 [/if]
 
+Location: [return-to url]
 <A HREF="[scratch name=search_page interpolate=1]" TARGET=test>Test</A>
 
 <FORM>
 <TEXTAREA COLS=80 ROWS="[scratch rows]" NAME=junk>[scratch search_page]</TEXTAREA>
+<br>
+[if cgi ui_source_form]
+[and cgi ui_source_var]
+<script>
+	var par = window.opener;
+	function send_to (caller) {
+		if(par == undefined) {
+			alert("par is " + f);
+			return;
+		}
+		var f = par.document.[cgi ui_source_form].[cgi ui_source_var];
+		if(f == undefined) {
+			alert("f is " + f);
+		}
+		else {
+			caller.value = 'Sending to [cgi ui_source_form].[cgi ui_source_var]';
+			f.value = [jsq interpolate=1][scratch search_blob][/jsq];
+		}
+		window.close();
+	}
+
+	if(par)
+		document.write('<input style="font-weight: bold" type=button onClick="send_to(this); window.close()" value="Send back to source">');
+
+</script>
+[/if]
 </FORM>
 
 <A HREF="[scratch name=search_page interpolate=1]" TARGET=test>Test</A>



1.14.4.3  +16 -14    interchange/dist/lib/UI/pages/admin/ship.html


rev 1.14.4.3, prev_rev 1.14.4.2
Index: ship.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/ship.html,v
retrieving revision 1.14.4.2
retrieving revision 1.14.4.3
diff -u -r1.14.4.2 -r1.14.4.3
--- ship.html	14 Oct 2000 14:47:56 -0000	1.14.4.2
+++ ship.html	25 Jan 2003 22:21:14 -0000	1.14.4.3
@@ -1,7 +1,8 @@
 [set help_name]shipping[/set]
 [set ui_class]Admin[/set]
-[set page_title]Shipping configuration[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set page_title][L]Shipping configuration[/L][/set]
+[set icon_name]icon_config.gif[/set]
+[set page_perm]shipping[/set]
 @_UI_STD_HEAD_@
 <!-- 
 	read=[calc]
@@ -53,23 +54,24 @@
 				]
 			|]
 [value name=ui_changes_made set=1 hide=1]
-<FONT COLOR="__CONTRAST__">You need to [page __UI_BASE__/reconfig @@MV_PAGE@@]apply changes[/page] for changes to take effect.</FONT>
+<span class=cerror>[msg arg.0="[page __UI_BASE__/reconfig @@MV_PAGE@@]" arg.1="</a>"]You need to %sapply changes%s for changes to take effect.[/msg]</span>
 [/if]
 
 <p>
 <form action="[process]" method=POST>
+<input type=hidden name=mv_session_id value="[data session id]">
 <input type=hidden name=mv_todo value=return>
 
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 
 <tr>
-<td colspan=2 bgcolor="__UI_C_INTBLOCK__" width=__UI_LEFT_WIDTH__>
-[button text="Create new method"]
+<td colspan=2 class=rnorm width=__UI_LEFT_WIDTH__>
+[button text="[L]Create new method[/L]"]
 mv_nextpage=__UI_BASE__/ship_edit
 ui_shipmode=new
 ui_header=Create method
@@ -78,26 +80,26 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_LEFT_WIDTH__>
+<td class=rnorm width=__UI_LEFT_WIDTH__>
 
-[button text="Edit method"]
+[button text="[L]Edit method[/L]"]
 mv_nextpage=__UI_BASE__/ship_edit
 ui_header=Edit <I>[cgi ui_shipmode]</I> method
 [/button]
 
 <br>
-[button text="Edit data table"]
+[button text="[L]Edit data table[/L]"]
 mv_nextpage=__UI_BASE__/ship_data
 ui_header=Edit <I>[cgi ui_shipmode]</I> data table
 [/button]
 <br>
 
-[button text="Delete method"
- confirm='Are you sure you want to delete this method?'
+[button text="[L]Delete method[/L]"
+ confirm='[L]Are you sure you want to delete this method?[/L]'
 ]
 mv_nextpage=@@MV_PAGE@@
 ui_ship_action=delete
@@ -109,7 +111,7 @@
 
 <!-- Read the current shipping def, success=[read-shipping] -->
 
-<td bgcolor="__UI_C_INTBLOCK__" width=__UI_RIGHT_WIDTH__>
+<td class=rnorm width=__UI_RIGHT_WIDTH__>
 <select name=ui_shipmode size=10>
 [perl]
 	@modes = sort keys %{$Config->{Shipping_desc}};
@@ -128,7 +130,7 @@
 </td></tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.8.4.1   +59 -24    interchange/dist/lib/UI/pages/admin/ship_data.html


rev 1.8.4.1, prev_rev 1.8
Index: ship_data.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/ship_data.html,v
retrieving revision 1.8
retrieving revision 1.8.4.1
diff -u -r1.8 -r1.8.4.1
--- ship_data.html	23 Sep 2000 17:55:33 -0000	1.8
+++ ship_data.html	25 Jan 2003 22:21:14 -0000	1.8.4.1
@@ -2,7 +2,8 @@
 [set ui_class]Admin[/set]
 [seti page_title]Shipping options: edit data for method [cgi ui_shipmode][/seti]
 [seti page_banner]Shipping options: edit data for method <I>[cgi ui_shipmode]</I>[/seti]
-[set icon_name]admin/icon_config.gif[/set]
+[set page_perm]shipping[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
@@ -13,6 +14,7 @@
 <!-- do update?: [cgi price_ok]
 	[perl]
 		return if ! $CGI->{price_ok};
+		$CGI->{ui_shipmode} ||= $Values->{ui_shipmode};
 		my $inmode = $CGI->{ui_shipmode};
 		$inmode =~ s/\W+//g;
 		#Log("write inmode=$inmode");
@@ -70,6 +72,17 @@
 				$cost .= qq{ origin="$opt->{origin}"} if $opt->{origin};
 				$cost .= "]";
 			}
+			elsif(	!	$done_one_fed++
+				and $opt->{ui_ship_type}
+				and $opt->{ui_ship_type} =~ /^FEDE:(.*)/
+				)
+			{
+				my $m = $1;
+				$cost = "f [fedex-query cache=1 mode=$m weight=";
+				$cost .= '"@@TOTAL@'  . '@"';
+				$cost .= qq{ origin="$opt->{origin}"} if $opt->{origin};
+				$cost .= "]";
+			}
 			$modes[$i][5] = $cost;
 			$i++;
 		}
@@ -114,10 +127,11 @@
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=5 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=5 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 [perl]
+		$CGI->{ui_shipmode} ||= $Values->{ui_shipmode};
 		my $inmode = $CGI->{ui_shipmode};
 		#Log("ship_data inmode=$inmode");
 		my $lines = $Config->{Shipping_line};
@@ -149,8 +163,8 @@
 		}
 		my @out;
 		push (@out, <<EOF);
-<tr>
-<td colspan=5 align=left bgcolor=__UI_C_INTBLOCK__>
+<tr class=rnorm>
+<td colspan=5 align=left>
 &nbsp;
 <p>
 <b>[cgi ui_shipmode] -- [shipping-desc mode="[cgi ui_shipmode]"]</b>
@@ -163,15 +177,15 @@
 </tr>
 
 <tr>
-<td align=left colspan=5 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=1 height=1></td>
+<td align=left colspan=5 class=rborder><img src="bg.gif" width=1 height=1></td>
 </tr>
 
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__><INPUT TYPE=hidden NAME=ui_shipmode VALUE="$inmode"><b>Start range</b></td>
-<td bgcolor=__UI_C_INTBLOCK__><b>End range</b></td>
-<td bgcolor=__UI_C_INTBLOCK__><b>Charge type</b></td>
-<td bgcolor=__UI_C_INTBLOCK__><b>Charge amount</b></td>
-<td bgcolor=__UI_C_INTBLOCK__> &nbsp; </td>
+<tr class=rnorm>
+<td class=ctitle><INPUT TYPE=hidden NAME=ui_shipmode VALUE="$inmode">Start range</td>
+<td class=ctitle>End range</td>
+<td class=ctitle>Charge type</td>
+<td class=ctitle>Charge amount</td>
+<td> &nbsp; </td>
 </tr>
 EOF
 		my $idx = -1;
@@ -179,7 +193,7 @@
 		@types = (
 			''	=> 'Number',
 			f	=> 'Formula',
-			'!'	=> 'UPS WWW Lookup',
+			'!'	=> 'UPS/FedEx WWW Lookup',
 			x	=> 'Multiply by',
 			u	=> 'Internal UPS',
 			e	=> 'Message',
@@ -206,6 +220,27 @@
 						$opt,
 					];
 			}
+			elsif ($opt->{ui_ship_type} =~ /^FEDE:(.*)/) {
+				push @modes, 
+					[	$inmode,
+						$master->[1],
+						$master->[2],
+						0,
+						150,
+						"f [fedex-query mode=$1 cache=1 weight=" . '@@TOTAL' . '@@]', 
+						'',
+						$opt,
+					],
+					[	$inmode,
+						$master->[1],
+						$master->[2],
+						150,
+						9999999,
+						"e Too heavy for FedEx",
+						'',
+						$opt,
+					];
+			}
 			elsif ($opt->{ui_ship_type} =~ /^UPSI/) {
 				push @modes, 
 					[	$inmode,
@@ -249,26 +284,26 @@
 			$ref->[4] = 9999999 if ! length $ref->[4];
 			if ($ref->[4] > 9999998 and ! $modes[$idx + 1]) {
 				$max_display = qq{<INPUT TYPE=hidden NAME=max$idx VALUE=9999999>(infinity)};
-				$bgcolor = '__UI_C_TOPBLOCKBAR__';
+				$class = 'rborder';
 			}
 			else {
 				$max_display = qq{<INPUT size=7 name=max$idx VALUE="$ref->[4]">};
-				$bgcolor = '__UI_C_INTBLOCK__';
+				$class = 'rnorm';
 			}
 			$out = <<EOF;
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__ align=center><input type=hidden name=mode$idx value="$inmode"><input size=7 name=min$idx value="$ref->[3]"></td>
-<td bgcolor=$bgcolor>
+<td class=rborder align=center><input type=hidden name=mode$idx value="$inmode"><input size=7 name=min$idx value="$ref->[3]"></td>
+<td class=$class>
 $max_display
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <select name="cost$idx">
 EOF
 			$ref->[5] =~ s/^\s*([A-Za-z])\s*//;
 			$selector = $1;
 			if($selector eq 'f') {
-				$selector = '!' if $ref->[5] =~ s/\[(ups.query)/&#91;$1/;
+				$selector = '!' if $ref->[5] =~ s/\[((?:ups|fedex).query)/&#91;$1/;
 			}
 			$ref->[5] =~ s/"/&quot;/g;
 			$ref->[5] =~ s/\[/&#91;/g;
@@ -282,12 +317,12 @@
 </select>
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input size=20 name="cost$idx" value="$ref->[5]">
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
-<input type=image name="ui_delete_range$idx" src="@_UI_IMG_@admin/delete.gif" alt="Delete this range" width=20 height=20 border=0>
+<td class=rnorm>
+<input type=image name="ui_delete_range$idx" src="delete.gif" alt="Delete this range" width=20 height=20 border=0>
 </td>
 
 </tr>
@@ -300,13 +335,13 @@
 <tr>
 
 <tr>
-<td colspan=5 bgcolor=__UI_C_INTBLOCK__>
-<INPUT TYPE=image name=ui_add_line src="@_UI_IMG_@admin/plus.gif" alt="Add a new range" width=20 height=20 border=0>
+<td colspan=5 class=rnorm>
+<INPUT TYPE=image name=ui_add_line src="plus.gif" alt="Add a new range" width=20 height=20 border=0>
 </td>
 </tr>
 
 <tr>
-<td colspan=5 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1 border=0></td>
+<td colspan=5 class=rnorm><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1 border=0></td>
 </tr>
 
 </table>



1.12.4.1  +33 -32    interchange/dist/lib/UI/pages/admin/ship_edit.html


rev 1.12.4.1, prev_rev 1.12
Index: ship_edit.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/ship_edit.html,v
retrieving revision 1.12
retrieving revision 1.12.4.1
diff -u -r1.12 -r1.12.4.1
--- ship_edit.html	23 Sep 2000 17:55:33 -0000	1.12
+++ ship_edit.html	25 Jan 2003 22:21:14 -0000	1.12.4.1
@@ -2,7 +2,8 @@
 [set ui_class]Admin[/set]
 [seti page_title]Shipping options: edit method [cgi ui_shipmode][/seti]
 [seti page_banner]Shipping options: edit method <I>[cgi ui_shipmode]</I>[/seti]
-[set icon_name]admin/icon_config.gif[/set]
+[set page_perm]shipping[/set]
+[set icon_name]icon_config.gif[/set]
 [set meta_header]
 <SCRIPT LANGUAGE=JavaScript>
 		function check_for_ups(form, mode) {
@@ -176,33 +177,33 @@
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right WIDTH="__UI_LEFT_WIDTH">
+<td class=rnorm align=right WIDTH="__UI_LEFT_WIDTH">
 <small>Name of this method</small><BR><small><i>(letters/digits only)</i></small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input type=text size=40 name="ui_shipmode" value="[value ui_shipmode]">
 </td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right WIDTH="__UI_LEFT_WIDTH">
+<td class=rnorm align=right WIDTH="__UI_LEFT_WIDTH">
 <small>Label for this method</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input type=text size=40 name="ui_ship_description" value="[value ui_ship_description]">
 </td>
 </tr>
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Total based on this criteria</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
 <select name=ui_ship_criteria>
 [loop lr=1 option=ui_ship_criteria list="
@@ -220,10 +221,10 @@
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Calculate based on this algorithm</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <select name=ui_ship_type onChange="check_for_ups(this.form,
 			this.form.ui_ship_type.options[this.form.ui_ship_type.selectedIndex].value) && this.form.submit()">
 [loop lr=1 option=ui_ship_type
@@ -241,10 +242,10 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right valign=top>
+<td class=rnorm align=right valign=top>
 <BR><small>Apply this method by country<BR><I>(select as many as desired)</I></small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <FONT SIZE=-1>
 [calc]
 	$modes = <<'EOF';
@@ -281,28 +282,28 @@
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Minimum shipping charge</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input type=text size=10 name="ui_ship_at_least" value="[value ui_ship_at_least]">
 </td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Additional shipping calculation</small><BR><I><SMALL>(number only is additional charge)</SMALL></I>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input type=text size=50 name="ui_ship_adder" value="[value ui_ship_adder]">
 </td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Round up to nearest even [L currency_symbol]$[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <SELECT NAME=ui_ship_round>
 <OPTION VALUE=""> No
 <OPTION VALUE="1" [selected ui_ship_round 1]> Yes
@@ -312,10 +313,10 @@
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Allow to be zero cost</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <SELECT NAME=ui_ship_free>
 <OPTION VALUE=""> No
 <OPTION VALUE="1" [selected ui_ship_free 1]> Yes
@@ -325,10 +326,10 @@
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
+<td class=rnorm align=right>
 <small>Message when zero</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <INPUT NAME=ui_ship_message VALUE="[either][value ui_ship_message][or]Nothing to ship![/either]">
 </td>
 </tr>
@@ -339,10 +340,10 @@
   [if value ui_ship_ups_internal]
 	[seti available_ups_internal][available_ups_internal][/seti]
 	<tr>
-	<td bgcolor=__UI_C_INTBLOCK__ align=right>
+	<td class=rnorm align=right>
 	<small>UPS Zone chart</small>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<SELECT NAME=ui_ship_zone>
 	[loop lr=1 option=ui_ship_zone
 		list="[scratch available_ups_internal]"
@@ -353,10 +354,10 @@
 	</tr>
 
 	<tr>
-	<td bgcolor=__UI_C_INTBLOCK__ align=right>
+	<td class=rnorm align=right>
 	<small>Table for lookups</small>
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<SELECT NAME=ui_ship_table>
 	[loop option=ui_ship_table list="[list-databases]"]
 	<OPTION>[loop-code]
@@ -367,10 +368,10 @@
 
   [else]
 	<tr>
-	<td bgcolor=__UI_C_INTBLOCK__ align=right>
+	<td class=rnorm align=right>
 	<small>UPS Origin Zone</small>[if variable UPS_ORIGIN]<BR><SMALL><I>(default __UPS_ORIGIN__)</I></SMALL>[/if]
 	</td>
-	<td bgcolor=__UI_C_INTBLOCK__>
+	<td class=rnorm>
 	<input type=text size=50 name="ui_ship_origin" value="[value ui_ship_origin]">
 	</td>
 	</tr>
@@ -378,10 +379,10 @@
   [/if]
 
   <tr>
-  <td bgcolor=__UI_C_INTBLOCK__ align=right>
+  <td class=rnorm align=right>
   <small>Field that chooses UPS destination</small>[if variable UPS_POSTCODE_FIELD]<BR><SMALL><I>(default __UPS_POSTCODE_FIELD__)</I></SMALL>[/if]
   </td>
-  <td bgcolor=__UI_C_INTBLOCK__>
+  <td class=rnorm>
   <input type=text size=50 name="ui_ship_geo" value="[value ui_ship_geo]">
   </td>
   </tr>
@@ -392,7 +393,7 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>
@@ -406,7 +407,7 @@
 	do_update_cmd=Ok
 	ui_bounce_url=__UI_BASE__/ship_data
 [/button]
-[button text="[L]Cancel[/L]"]
+[button text="[L]Cancel ship edit[/L]"]
 	mv_nextpage=__UI_BASE__/ship
 	mv_todo=back
 [/button]



1.8.4.1   +19 -18    interchange/dist/lib/UI/pages/admin/ship_range.html


rev 1.8.4.1, prev_rev 1.8
Index: ship_range.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/ship_range.html,v
retrieving revision 1.8
retrieving revision 1.8.4.1
diff -u -r1.8 -r1.8.4.1
--- ship_range.html	23 Sep 2000 17:55:33 -0000	1.8
+++ ship_range.html	25 Jan 2003 22:21:14 -0000	1.8.4.1
@@ -2,7 +2,8 @@
 [set ui_class]Admin[/set]
 [set page_banner]Shipping method tables[/set]
 [set help_name]shipping.methodtables[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set page_perm]shipping[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
@@ -13,11 +14,11 @@
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=5 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=5 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td colspan=5 align=left bgcolor=__UI_C_INTBLOCK__>
+<td colspan=5 align=left class=rnorm>
 &nbsp;
 <p>
 <b> -- Standard shipping by weight</b>
@@ -29,22 +30,22 @@
 </tr>
 
 <tr>
-<td align=left colspan=5 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=1 height=1></td>
+<td align=left colspan=5 class=rborder><img src="bg.gif" width=1 height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__><b>Start range</b></td>
-<td bgcolor=__UI_C_INTBLOCK__><b>End range</b></td>
-<td bgcolor=__UI_C_INTBLOCK__><b>Charge type</b></td>
-<td bgcolor=__UI_C_INTBLOCK__><b>Charge amount</b></td>
-<td bgcolor=__UI_C_INTBLOCK__> &nbsp; </td>
+<td class=rnorm><b>Start range</b></td>
+<td class=rnorm><b>End range</b></td>
+<td class=rnorm><b>Charge type</b></td>
+<td class=rnorm><b>Charge amount</b></td>
+<td class=rnorm> &nbsp; </td>
 </tr>
 
 <tr>
 
-<td bgcolor=__UI_C_TOPBLOCKBAR__ align=center> 0 </td>
-<td align=center bgcolor=__UI_C_TOPBLOCKBAR__> (infinity) </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rborder align=center> 0 </td>
+<td align=center class=rborder> (infinity) </td>
+<td class=rnorm>
 
 <select name="1005_type">
 <option value=0> Flat rate </option>
@@ -52,24 +53,24 @@
 </select>
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input size=7 name="1005_val" value="0">
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__>
-<a href="shipping?sid=1005&deleteprice=1005"><img src="@_UI_IMG_@admin/delete.gif" alt="Delete this range" width=20 height=20 border=0></a>
+<td class=rnorm>
+<a href="shipping?sid=1005&deleteprice=1005"><img src="delete.gif" alt="Delete this range" width=20 height=20 border=0></a>
 </td>
 
 </tr>
 
 <tr>
-<td colspan=5 bgcolor=__UI_C_INTBLOCK__>
-<a href="shipping?addnewprice=ok&sid=1005"><img src="@_UI_IMG_@admin/plus.gif" alt="Add a new range" width=20 height=20 border=0></a>
+<td colspan=5 class=rnorm>
+<a href="shipping?addnewprice=ok&sid=1005"><img src="plus.gif" alt="Add a new range" width=20 height=20 border=0></a>
 </td>
 </tr>
 
 <tr>
-<td colspan=5 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=5 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.2.2.3   +6 -6      interchange/dist/lib/UI/pages/admin/sku_selector.html


rev 1.2.2.3, prev_rev 1.2.2.2
Index: sku_selector.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/sku_selector.html,v
retrieving revision 1.2.2.2
retrieving revision 1.2.2.3
diff -u -r1.2.2.2 -r1.2.2.3
--- sku_selector.html	15 Oct 2000 12:18:28 -0000	1.2.2.2
+++ sku_selector.html	25 Jan 2003 22:21:14 -0000	1.2.2.3
@@ -1,5 +1,5 @@
 [seti page_title]Interchange SKU selector (selecting for [description code="[cgi item_id]"])[/seti]
-[set icon_name]admin/icon_item.gif[/set]
+[set icon_name]icon_item.gif[/set]
 [set meta_header]
 <script language="JavaScript1.2">
 <!--
@@ -104,11 +104,11 @@
 <INPUT TYPE=hidden NAME=item_id VALUE="[cgi item_id]">
 
 <TABLE __UI_T_PROPERTIES__>
-<tr bgcolor="__UI_C_TITLEBARBG__">
-<td colspan=2>&nbsp;&nbsp;<FONT COLOR="__UI_C_TITLEBARTXT__"><B><INPUT TYPE=submit VALUE="Select these SKUs"></b>&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=Cancel VALUE="Cancel"></FONT></td>
+<tr class=rmarq>
+<td colspan=2>&nbsp;&nbsp;<INPUT TYPE=submit VALUE="Select these SKUs">&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=Cancel VALUE="Cancel"></td>
 </tr>
 <TR>
-<TD colspan=2 bgcolor="__UI_C_INTBLOCK__">
+<TD colspan=2 class=rnorm>
 	<table>
 	<TR>
 	<TD>
@@ -138,8 +138,8 @@
 	</tr>
 	</table>
 </td>
-<tr bgcolor="__UI_C_TITLEBARBG__">
-<td colspan=2>&nbsp;&nbsp;<FONT COLOR="__UI_C_TITLEBARTXT__"><B><INPUT TYPE=submit VALUE="Select these SKUs"></b>&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=Cancel VALUE="Cancel"></FONT></td>
+<tr class=rmarq>
+<td colspan=2>&nbsp;&nbsp;<INPUT TYPE=submit VALUE="Select these SKUs">&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=Cancel VALUE="Cancel"></td>
 </tr>
 </table>
 



1.9.4.4   +229 -173  interchange/dist/lib/UI/pages/admin/spread.html


rev 1.9.4.4, prev_rev 1.9.4.3
Index: spread.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/spread.html,v
retrieving revision 1.9.4.3
retrieving revision 1.9.4.4
diff -u -r1.9.4.3 -r1.9.4.4
--- spread.html	27 Nov 2000 01:47:35 -0000	1.9.4.3
+++ spread.html	25 Jan 2003 22:21:14 -0000	1.9.4.4
@@ -7,226 +7,295 @@
 	[either]
 		[cgi page_title]
 	[or]
-		Spreadsheet Edit: [cgi mv_data_table]
+		[L]Spreadsheet Edit:[/L] [cgi mv_data_table]
+	[/either]
+[/seti]
+[seti page_banner]
+	[either]
+		[cgi page_banner]
+	[or]
+		Spreadsheet Edit: [page href=__UI_BASE__/db_metaconfig
+								form="
+									ui_table=[cgi mv_data_table]
+									ui_view=[cgi ui_meta_view]
+									start_at=extended.spread_height
+								"][cgi mv_data_table]</A>
 	[/either]
 [/seti]
 [set ui_class]Admin[/set]
 [seti help_name][either][cgi help_name][or]gensql.main[/either][/seti]
-[seti icon_name][either][cgi icon_name][or]admin/icon_config.gif[/either][/seti]
+[seti icon_name][either][cgi icon_name][or]icon_config.gif[/either][/seti]
+
 @_UI_STD_HEAD_@
 
-[perl tables="[cgi mv_data_table]"]
+[tmp extra_title]
+[loop list="[cgi mv_data_table]"]
+	[if-loop-data __UI_META_TABLE__ name]
+	<B>[loop-data __UI_META_TABLE__ name]</B>
+	[/if-loop-data]
+	[if-loop-data __UI_META_TABLE__ help_url]
+	&nbsp;&nbsp;&nbsp;<small><A HREF="[loop-data __UI_META_TABLE__ help_url]">help</A></small>
+	[/if-loop-data]
+	[if-loop-data __UI_META_TABLE__ help]
+	<i>[loop-data __UI_META_TABLE__ name]</i>
+	[/if-loop-data]
+[/loop]
+[/tmp]
+[calc]
+	$Scratch->{page_banner} .= $Scratch->{extra_title};
+	$Scratch->{page_title} .= $Scratch->{extra_title};
+	return;
+[/calc]
+
+[output name=search_box]
+<FORM ACTION="[area href="[either][cgi ui_searchpage][or]@@MV_PAGE@@[/either]"]" METHOD=GET>
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
+<INPUT TYPE=hidden NAME=mv_data_table    VALUE="[cgi mv_data_table]">
+<INPUT TYPE=hidden NAME=ui_meta_view     value="[cgi ui_meta_view]">
+<INPUT TYPE=hidden NAME=mv_action        VALUE=back>
+<INPUT TYPE=hidden NAME=ui_show_fields VALUE="[cgi ui_show_fields]">
+<span class=s3>[L]Limit with search[/L]:</span> <input NAME=ui_text_qualification size=16 class=s2> 
+</FORM>
+[output name=""]
+
+[perl tables="[cgi mv_data_table] __UI_META_TABLE__"]
 	my $table = $CGI->{mv_data_table};
 	my $db = $Db{$table};
-	$Values->{mv_data_table} = $table;
-	$Values->{ui_data_key_name} = $Db{$table}->config('KEY');
-	$Values->{ui_data_fields} =
-		$CGI->{ui_data_fields} ||
-		$CGI->{mv_data_fields} ||
-		$Values->{"spread:$table:ui_data_fields"} ||
-		join(" ", $db->columns());
-	my @fields;
-	@fields = grep
-				$_ ne $Values->{ui_data_key_name},
-				split /[\0\s,]+/, $Values->{ui_data_fields};
-	$Values->{ui_data_fields} = join " ", @fields;
-	$Values->{"ui_spread_meta:$table"} = $CGI->{"ui_spread_meta:$table"}
-		if defined $CGI->{"ui_spread_meta:$table"};
-	$Values->{ui_meta_display} = $Values->{"ui_spread_meta:$table"};
+	my $mrec = $Tag->meta_record($table, $CGI->{ui_meta_view}) || {};
+	my $sp = q{@@MV_PAGE@@};
+	$mrec ||= {};
+	$mrec->{spread_fields} ||= join(" ", $db->columns());
+	$mrec->{spread_height} ||= 10;
+	my $key = $CGI->{ui_data_key_name} = $db->config('KEY');
+	$mrec->{spread_sort} ||= $key;
+	$CGI->{ui_description_field} = $mrec->{label};
 
-	if($Values->{"ui_spreadsheet_rows:$table"}) {
-		$Values->{"ui_spreadsheet_rows"} = $Values->{"ui_spreadsheet_rows:$table"};
-	}
-	else {
-		$Values->{"ui_spreadsheet_rows"} = 10;
-	}
-
-	if($Values->{"ui_textarea_rows:$table"}) {
-		$Values->{"ui_textarea_rows"} = $Values->{"ui_textarea_rows:$table"};
+	my $qualbase = qq{
+				sp=$sp
+				st=db
+				ml=$mrec->{spread_height}
+				ms=0
+			};
+	my $qualsimple = qq{
+				fi=$table
+				rf=$CGI->{ui_data_key_name}
+				tf=$mrec->{spread_sort}
+			};
+	my $qual;
+	my $sstring;
+	if(! $CGI->{ui_text_qualification}) {
+		$qual = "ra=yes";
 	}
-	else {
-		$Values->{"ui_textarea_rows"} = 4;
+	elsif ($CGI->{ui_text_qualification} =~ /^\s*select/ ) {
+		$qual = "sq=$CGI->{ui_text_qualification}";
+		$sstring = join "\n", $qualbase, $qual;
 	}
-
-	if($CGI->{"ui_spread_size:$table"}) {
-		$Values->{"ui_spread_size"}
-			= $Values->{"ui_spread_size:$table"}
-			= $CGI->{"ui_spread_size:$table"};
+	elsif ($CGI->{ui_text_qualification} =~ /=/ ) {
+		my ($f, $s) = split /\s*=\s*/, $CGI->{ui_text_qualification} , 2;
+		$qual = "co=1\nop=eq\nse=$s\nsf=$f";
 	}
-	elsif($Values->{"ui_spread_size:$table"}) {
-		$Values->{"ui_spread_size"} = $Values->{"ui_spread_size:$table"};
+	elsif ($CGI->{ui_text_qualification}) {
+		$qual = "se=$CGI->{ui_text_qualification}";
 	}
 	else {
-		$Values->{"ui_spread_size"} = 12;
+		$qual = "ra=yes";
 	}
 
+	$sstring ||= join "\n", $qualbase, $qualsimple, $qual;
+
+	my @fields = split /[\0\s,]+/, $mrec->{spread_fields};
+	@fields = grep length($_) && $_ ne $key, @fields;
+
+	$CGI->{mv_data_fields} = join " ", @fields;
+
+	$CGI->{mrec_textarea_rows} ||= 4;
+
+	$CGI->{mrec_spread_width} ||= $mrec->{spread_width} || 12; 
+
+	$Scratch->{mrec_options} = $sstring;
+
+	$Scratch->{ui_num_col} = scalar(@fields) + 2;
+	$Scratch->{ui_most_col} = $Scratch->{ui_num_col} - 1; 
+	$Config->{NoSearch} = '';
 	return;
 [/perl]
-[if scratch ui_failure]
-<BLOCKQUOTE>
-<FONT COLOR=__CONTRAST__>Error: [scratch ui_failure]</FONT>
-[set ui_failure][/set]
-</BLOCKQUOTE>
-[/if]
+
+[output name="top_of_form"]
 <FORM METHOD=POST ACTION="[base-url]/ui">
 <INPUT TYPE=hidden NAME="mv_todo" VALUE="set">
 <INPUT TYPE=hidden NAME="mv_nextpage" VALUE="@@MV_PAGE@@">
-<INPUT TYPE=hidden NAME="mv_data_table" VALUE="[value mv_data_table]">
-<INPUT TYPE=hidden NAME="mv_data_key" VALUE="[value ui_data_key_name]">
+<INPUT TYPE=hidden NAME="mv_data_table" VALUE="[cgi mv_data_table]">
+<INPUT TYPE=hidden NAME="mv_data_key" VALUE="[cgi ui_data_key_name]">
 <INPUT TYPE=hidden NAME="mv_data_decode" VALUE="yes">
+<INPUT TYPE=hidden NAME="mv_data_multiple" VALUE="1">
+<INPUT TYPE=hidden NAME="mv_click" VALUE="process_filter">
 <INPUT TYPE=hidden NAME="mv_update_empty" VALUE="1">
+<INPUT TYPE=hidden NAME="mv_update_empty_key" VALUE="0">
+<INPUT TYPE=hidden NAME="ui_meta_view" value="[cgi ui_meta_view]">
 <INPUT TYPE=hidden NAME="ui_text_qualification" value="[cgi ui_text_qualification]">
-[calc]
-for(@{$CGI_array->{'ui_return_to'}}) {
-	$out .= <<EOF;
-<INPUT TYPE=hidden NAME=ui_return_to VALUE="$_">
-EOF
-}
-return $out;
-[/calc]
-<INPUT TYPE=hidden NAME="mv_data_fields"
-	VALUE="[db-columns columns='[value ui_data_fields]']">
-
+<INPUT TYPE=hidden NAME="ui_return_to" value="[cgi ui_return_to]">
+<INPUT TYPE=hidden NAME="mv_data_fields" VALUE="[cgi mv_data_fields]">
 <INPUT TYPE=hidden NAME="mv_data_function" VALUE="update">
 
+[output name=""]
 [calc]
-	@areas = grep /\S/, split /[\s,\0]+/, $Values->{ui_data_fields};
-	$Scratch->{ui_num_col} = scalar(@areas) + 2;
-	$Config->{NoSearch} = '';
-	if ($CGI->{ui_text_qualification} and $CGI->{ui_text_qualification} =~ /=/ ) {
-		my ($f, $s) = split /\s*=\s*/, $CGI->{ui_text_qualification} , 2;
-		$CGI->{ui_text_qualification} = "co=1\nop=eq\nse=$s\nsf=$f";
-	}
-	elsif ($CGI->{ui_text_qualification}) {
-		$CGI->{ui_text_qualification} = "se=$CGI->{ui_text_qualification}";
-	}
-	else {
-		$CGI->{ui_text_qualification} = "ra=yes";
-	}
-	$CGI->{ui_description_field} =
-		q{[data table=__UI_META_TABLE__
-				col=field
-				key="[cgi mv_data_table]"
-			]};
-
-	return;
 [/calc]
 
-[if !value ui_spreadsheet_rows]
-[value name=ui_spreadsheet_rows set=10 hide=1]
-[/if]
-[search-region more=1 arg="
-				[cgi ui_text_qualification]
-				ml=[value ui_spreadsheet_rows]
-				rf=[value ui_data_key_name]
-				tf=[value ui_data_key_name]
-				st=db
-				sp=@@MV_PAGE@@
-				fi=[value mv_data_table]
-			"]
-[rotate-table reparse=0 rotate="[value ui_rotate_spread]" interpolate=1]
-
-<table __UI_T_PROPERTIES__>
+[search-region more=1 arg="[scratch mrec_options]"]
+<table width="100%" border=0 cellpadding=0 cellspacing=1 class=rseparator>
 
+[more-list]
+[prev-anchor]&nbsp;&nbsp;<span style="font-size: larger; font-weight: bolder">&lt;</span>&nbsp;&nbsp;[/prev-anchor]
+[next-anchor]&nbsp;&nbsp;<span style="font-size: larger; font-weight: bolder">&gt;</span>&nbsp;&nbsp;[/next-anchor]
+[first-anchor]&nbsp;<span style="font-size: larger; font-weight: bolder">&lt;&lt;</span>[/first-anchor]
+[last-anchor]&nbsp;<span style="font-size: larger; font-weight: bolder">&gt;&gt;</span>[/last-anchor]
+[page-anchor]&nbsp;<span style="font-size: larger; font-weight: bolder">$PAGE$</span>[/page-anchor]
 <tr>
-<td colspan="[scratch ui_num_col]" bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan="[scratch ui_num_col]" class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
-
-[with param=table value="[value mv_data_table]"]
-<TR BGCOLOR="__UI_C_INTBLOCK__" CELLPADDING=2>
-	<TH ALIGN=CENTER>&nbsp;</TH>
-	<TH ALIGN=CENTER>[value ui_data_key_name]</TH>
-	[row-edit
-		columns="[value ui_data_fields]"
-		height=`$Values->{"ui_textarea_rows:$Values->{mv_data_table}"}`
-		textarea="[value name='ui_textarea_fields:[value mv_data_table]']"
-		]
-</TR>
-
 <tr>
-<td colspan="[scratch ui_num_col]" bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rhead>&nbsp;</td>
+<td colspan="[scratch ui_most_col]" class=rhead>
+	[msg arg.0=`q{[more]}`]More pages: %s[/msg]
+</td>
 </tr>
+[/more-list]
+
+<TR class=rhead CELLPADDING=2>
+	<td align=center>&nbsp;</td>
+	<td>[cgi ui_data_key_name]</td>
+	[row-edit columns="[cgi mv_data_fields]" ]
+</TR>
 
 	[search-list]
+	[item-sub addnum]
+		my $inc = shift;
+		my $out = '';
+		if($ss_row_num) {
+			$out = $ss_row_num . '_';
+		}
+		$ss_row_num++ if $inc;
+		return $out;
+	[/item-sub]
 	[if-mm keys [item-code]]
-<TR BGCOLOR="__UI_C_INTBLOCK__">
-	<td><input type=checkbox name="batch_id" value="[item-code]"><input type=hidden name="[value ui_data_key_name]" value="[item-code]"></td>
-	<TD>
+<TR class=rownorm>
+	<td valign=top><input type=checkbox name="batch_id" value="[item-code]"><input type=hidden name="[item-exec addnum][/item-exec][cgi ui_data_key_name]" value="[item-code]"></td>
+	<TD valign=top>
 	[page href="__UI_BASE__/flex_editor"
 	form=|
-		page_title=Edit [value mv_data_table]: [item-code]
-		mv_data_table=[value mv_data_table]
+		page_title=Edit [cgi mv_data_table]: [item-code]
+		mv_data_table=[cgi mv_data_table]
+		ui_meta_specific=[cgi ui_meta_specific]
 		item_id=[item-code]
-	|]<small><small><u>edit</u></small></small>&nbsp;<b>[item-code]</b></A>
+	|][item-code]</A>
 	</TD>
 	[row-edit
 		key="[item-code]"
-		size="[value ui_spread_size]"
-		columns="[value ui_data_fields]"
-		height=`
-					my $tab = $Values->{mv_data_table};
-					return $Values->{"ui_textarea_rows:$tab"};
-				`
-		textarea=`
-					my $tab = $Values->{mv_data_table};
-					return $Values->{"ui_textarea_fields:$tab"};
-			`
+		extra="valign=top"
+		pointer="[item-exec addnum]1[/item-exec]"
+		columns="[cgi mv_data_fields]"
+		ui_meta_specific="[cgi ui_meta_specific]"
 		]
-</TR>
+</tr>
 	[/if-mm]
 	[set row_number][item-increment][/set]
 	[/search-list]
 
-<TR BGCOLOR="__UI_C_INTBLOCK__">
-	<td COLSPAN=2>
-	<input type=text size=12 name="[value ui_data_key_name]">
+<tr>
+<td colspan="[scratch ui_num_col]" class=rhead><b>New record</b></td>
+</tr>
+
+<TR class=rhead CELLPADDING=2>
+	<TH ALIGN=CENTER>&nbsp;</TH>
+	<TH ALIGN=CENTER>[cgi ui_data_key_name]</TH>
+	[row-edit columns="[cgi mv_data_fields]"]
+</TR>
+
+
+<TR class=rownorm>
+	<td COLSPAN=2 valign=top>
+	<input type=text size=12 name="999999_[cgi ui_data_key_name]">
 	</TD>
-	[row-edit blank=1 size="[value ui_spread_size]" columns="[value ui_data_fields]"]
+	[row-edit
+		blank=1
+		pointer=999999
+		extra="valign=top"
+		columns="[cgi mv_data_fields]"
+		extra="valign=top"
+		]
 </TR>
 
 [more-list]
+[prev-anchor]&nbsp;&nbsp;<span style="font-size: larger; font-weight: bolder">&lt;</span>&nbsp;&nbsp;[/prev-anchor]
+[next-anchor]&nbsp;&nbsp;<span style="font-size: larger; font-weight: bolder">&gt;</span>&nbsp;&nbsp;[/next-anchor]
+[first-anchor]&nbsp;<span style="font-size: larger; font-weight: bolder">&lt;&lt;</span>[/first-anchor]
+[last-anchor]&nbsp;<span style="font-size: larger; font-weight: bolder">&gt;&gt;</span>[/last-anchor]
+[page-anchor]&nbsp;<span style="font-size: larger; font-weight: bolder">$PAGE$</span>[/page-anchor]
 <tr>
-<td colspan="[scratch ui_num_col]" bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__>&nbsp;</td>
-<td colspan="[calc]$Scratch->{ui_num_col} - 1[/calc]" bgcolor=__UI_C_INTBLOCK__>
-	<FONT SIZE="+1">More pages: [more] </FONT>
+<td class=rhead>&nbsp;</td>
+<td colspan="[scratch ui_most_col]" class=rhead>
+	[msg arg.0=`q{[more]}`]More pages: %s[/msg]
 </td>
 </tr>
 [/more-list]
 
-<tr>
-<td colspan="[scratch ui_num_col]" bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
+</TABLE>
+</center>
+[/search-region]
 
-<tr>
-<td colspan="[scratch ui_num_col]" bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
+[output name=top_buttons]
+	[button text="[L]Ok[/L]" extra=|style="font-weight: bold"|]
+		mv_todo=set
+		[return-to click]
+	[/button]
+	[button text="[L]Delete checked[/L]"
+		confirm="[L]Are you sure you want to delete the checked rows?[/L]"]
+[flag type=write table="[cgi mv_data_table]"]
+mv_nextpage=__UI_BASE__/flex_select
+mv_auto_export=
+mv_todo=return
+[if-mm tables =d]
+	[perl tables="[cgi mv_data_table]"]
+		my $tab = $CGI->{mv_data_table};
+		my $db  = $Db{$tab};
+		unless ($db) {
+			$Scratch->{ui_message} = "No table '$tab'";
+			return;
+		}
+		my @items = split /\0/, $CGI->{batch_id};
+		foreach my $item (@items) {
+			if ($db->delete_record($item)) {
+				$out .= "Deleted $item from table $tab<BR>";
+			}
+			else {
+				$out .= "Item $item not in $tab table (or delete failed)<BR>";
+			}
+		}
+		$Scratch->{ui_message} = $out;
+		return;
+	[/perl]
+[else]
+	[set ui_message][L]Not authorized to delete items.[/L][/set]
+[/else]
+[/if-mm]
+	[return-to click]
+[/button]
 
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__>&nbsp;</td>
-<td colspan="[calc]$Scratch->{ui_num_col} - 1[/calc]" bgcolor=__UI_C_INTBLOCK__>
+	<INPUT TYPE=submit NAME=mv_click VALUE="[L]Cancel[/L]" type=s3>
+
+[output name=bottom_buttons]
 
+	[if-mm super]
+	<INPUT TYPE=checkbox NAME=mv_auto_export [if !scratch ui_too_large]CHECKED [/if]VALUE="[cgi mv_data_table]" class=s3>
+		<span class=s3>[L]Auto-export[/L]</span>
+	[/if-mm]
 
-[set Cancel]
-mv_todo=back
-[return-to click]
-[/set]
-
-	[set OK]
-	[/set]
-	<B></B>&nbsp;&nbsp;&nbsp;[button text="Ok" bold=1]
+	[button text="[L]Ok[/L]" extra=|style="font-weight: bold"|]
 		mv_todo=set
 		[return-to click]
-	[/button]&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
-	[button text="Change display"]
-	mv_todo=return
-	mv_data_table=[cgi mv_data_table]
-	mv_nextpage=__UI_BASE__/spread_control
 	[/button]
-	[button text="Delete checked rows"
-		confirm="Are you sure you want to delete the checked rows?"]
+	[button text="[L]Delete checked[/L]"
+		confirm="[L]Are you sure you want to delete the checked rows?[/L]"]
 [flag type=write table="[cgi mv_data_table]"]
 mv_nextpage=__UI_BASE__/flex_select
 mv_auto_export=
@@ -252,29 +321,16 @@
 		return;
 	[/perl]
 [else]
-	[set ui_message]Not authorized to delete items.[/set]
+	[set ui_message][L]Not authorized to delete items.[/L][/set]
 [/else]
 [/if-mm]
 	[return-to click]
-[/button]&nbsp;&nbsp;&nbsp;
-	[button text=Cancel]
-		mv_todo=back
-		[return-to click]
-	[/button]
-	[if-mm super]
-	<BR><b><INPUT TYPE=checkbox NAME=mv_auto_export [if !scratch ui_too_large]CHECKED [/if]VALUE="[value mv_data_table]">
-		Auto-export</b>
-	[/if-mm]
+[/button]
 
-</td>
-</tr>
+	<INPUT TYPE=submit NAME=mv_click VALUE="[L]Cancel[/L]" type=s3>
+[output name="bottom_of_form"]
 
-</TABLE>
-[/rotate-table]
-</center>
-[/search-region]
 </FORM>
-
 
 
 <!-- ----- END REAL STUFF ----- -->



1.3.4.2   +13 -14    interchange/dist/lib/UI/pages/admin/spread_control.html


rev 1.3.4.2, prev_rev 1.3.4.1
Index: spread_control.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/spread_control.html,v
retrieving revision 1.3.4.1
retrieving revision 1.3.4.2
diff -u -r1.3.4.1 -r1.3.4.2
--- spread_control.html	14 Oct 2000 14:47:56 -0000	1.3.4.1
+++ spread_control.html	25 Jan 2003 22:21:14 -0000	1.3.4.2
@@ -3,7 +3,7 @@
 [/seti]
 [set ui_class]Admin[/set]
 [seti help_name]gentable[/seti]
-[seti icon_name]admin/icon_config.gif[/seti]
+[seti icon_name]icon_config.gif[/seti]
 [set table_perm]1[/set]
 @_UI_STD_HEAD_@
 
@@ -17,11 +17,11 @@
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
+<td class=rnorm valign=top>
 <b>Fields to display</b><br>
 [widget name="[scratch ui_data_fields_name]"
 		type="multiple"
@@ -39,7 +39,7 @@
 		> Use display info</B>
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__ valign=top>
+<td class=rnorm valign=top>
 <b>Fields to display as textarea</b><br>
 [widget name="ui_textarea_fields:[value mv_data_table]"
 		type="multiple"
@@ -50,21 +50,16 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_INTBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ WIDTH=__UI_LEFT_WIDTH__>
+<td class=rnorm WIDTH=__UI_LEFT_WIDTH__>
 
 [set Display All Fields]
 [scratch ui_data_fields_name]=
 [/set]
 
-[set Cancel]
-mv_todo=back
-mv_nextpage=__UI_BASE__/flex_select
-[/set]
-
 [set Set]
 [if type="!cgi" term="ui_textarea_fields:[cgi mv_data_table]"]
 ui_textarea_fields:[cgi mv_data_table]=
@@ -72,11 +67,15 @@
 [/set]
 
 <B><INPUT TYPE=submit name=mv_click VALUE="Set"></b>
-<INPUT TYPE=submit name=mv_check VALUE="Cancel"><BR>
+[button text="Cancel display change"]
+mv_todo=back
+mv_nextpage=__UI_BASE__/flex_select
+[/button]<BR>
+
 
 </td>
 
-<td bgcolor=__UI_C_INTBLOCK__ WIDTH=__UI_RIGHT_WIDTH__>
+<td class=rnorm WIDTH=__UI_RIGHT_WIDTH__>
 
 <b>Column size</b><br>
 <SELECT NAME="ui_spread_size:[cgi mv_data_table]">
@@ -105,7 +104,7 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 </table>
 



1.3.4.2   +14 -14    interchange/dist/lib/UI/pages/admin/tablereport.html


rev 1.3.4.2, prev_rev 1.3.4.1
Index: tablereport.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/tablereport.html,v
retrieving revision 1.3.4.1
retrieving revision 1.3.4.2
diff -u -r1.3.4.1 -r1.3.4.2
--- tablereport.html	12 Oct 2000 12:47:56 -0000	1.3.4.1
+++ tablereport.html	25 Jan 2003 22:21:14 -0000	1.3.4.2
@@ -2,14 +2,14 @@
 [set ui_error]Not authorized for table.[/set]
 [bounce page="__UI_BASE__/error"]
 [/if-mm]
-[if !advanced report]
+[if-mm !advanced report]
 [bounce page="__UI_BASE__/error"]
 [value name=saved_report set=""]
-[/if]
+[/if-mm]
 [seti page_title]Reports[/seti]
 [set ui_class]Reports[/set]
 [set help_name]report[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [seti name=tables][list-databases][/seti]
 
 @_UI_STD_HEAD_@
@@ -22,22 +22,22 @@
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=3></td>
+<td colspan=3 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=3></td>
 </tr>
 
 <TR>
-<TD BGCOLOR="__UI_C_INTBLOCK__" VALIGN=TOP WIDTH=200>
-	<IMG src="@_UI_IMG_@admin/icon_stats.gif"><B>
+<TD class=rnorm VALIGN=TOP WIDTH=200>
+	<IMG src="icon_stats.gif"><B>
 		Run saved report
 	</B>
 </TD>
-<TD BGCOLOR="__UI_C_INTBLOCK__" VALIGN=TOP WIDTH=200>
-	<IMG src="@_UI_IMG_@admin/icon_config.gif"><B>
+<TD class=rnorm VALIGN=TOP WIDTH=200>
+	<IMG src="icon_config.gif"><B>
 		Retrieve saved definition
 	</B>
 </TD>
-<TD BGCOLOR="__UI_C_INTBLOCK__" VALIGN=TOP WIDTH=200>
-	<IMG src="@_UI_IMG_@admin/icon_error.gif"><B>
+<TD class=rnorm VALIGN=TOP WIDTH=200>
+	<IMG src="icon_error.gif"><B>
 		Delete report
 	</B>
 </TD>
@@ -152,14 +152,14 @@
 <P>
 <table __UI_T_PROPERTIES__>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td WIDTH="40%" bgcolor=__UI_C_INTBLOCK__ ALIGN=center>
+<td WIDTH="40%" class=rnorm ALIGN=center>
 	<INPUT TYPE=submit VALUE="Report on table">
 </TD>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <FORM NAME=report ACTION="[area __UI_BASE__/report]" METHOD=POST>
 <INPUT TYPE=hidden NAME=mv_action VALUE="return">
 <SELECT NAME=mv_data_table>
@@ -171,7 +171,7 @@
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 </table>
 



1.13.4.3  +173 -117  interchange/dist/lib/UI/pages/admin/tax.html


rev 1.13.4.3, prev_rev 1.13.4.2
Index: tax.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/tax.html,v
retrieving revision 1.13.4.2
retrieving revision 1.13.4.3
diff -u -r1.13.4.2 -r1.13.4.3
--- tax.html	27 Nov 2000 01:58:03 -0000	1.13.4.2
+++ tax.html	25 Jan 2003 22:21:14 -0000	1.13.4.3
@@ -1,149 +1,205 @@
+@_UI_STD_INIT_@
+[if config SalesTax ne multi]
+	[bounce page="__UI_BASE__/tax_simple"]
+[/if]
 [calc]
-	$Values->{mv_data_table} = $CGI->{mv_data_table} = 'variable';
+	$Values->{mv_data_table} = $CGI->{mv_data_table} = 'country';
 	$CGI->{no_dbmenu} = 1;
 	return;
 [/calc]
-[set table_perm]1[/set]
+[flag type=write table=country]
+[flag type=write table=state]
+[set page_perm]tax[/set]
 [set ui_class]Admin[/set]
-[set page_title]Tax configuration[/set]
+[set page_title][L]Tax configuration[/L][/set]
 [set help_name]tax.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 @_UI_STD_HEAD_@
 
-[flag type=write table=variable]
 <!-- ----- BEGIN REAL STUFF ----- -->
-[perl tables=variable]
-	delete $Scratch->{changes};
-	return unless $CGI->{tax_format} eq 'do';
-	for (my $i = 0; $i < 1000; $i++) {
-		last unless defined $CGI->{"taxarea$i"};
-		next if defined $CGI->{"Delete$i.x"};
-		my $area = $CGI->{"taxarea$i"};
-		my $rate = $CGI->{"taxrate$i"};
-		my $ship = $CGI->{"taxship$i"};
-		push @areas, ($area || 'new');
-		push @rates, "$area=$rate";
-		push (@taxes, $area) if $CGI->{"taxship$i"};
-	}
-	$Scratch->{taxarea} = join " ", @areas;
-	$Scratch->{taxrate} = join ",", @rates;
-	$Scratch->{taxship} = join " ", @taxes;
-	$Scratch->{changes} = 1;
-	return;
-[/perl]
-[if scratch changes]
-	<!-- setting:
-	[perl tables=variable]
-	my $db = $Db{variable};
-	$Values->{ui_changes_made} = 1;
-
-	my %sets = qw/taxarea TAXAREA taxrate TAXRATE taxship TAXSHIPPING/;
-
-	my ($v, $k);
-	while( ($v, $k) = each %sets) {
-		$out .= "Set $k ($Scratch->{$v}): ";
-		$out .= $db->set_field($k, 'Variable', delete $Scratch->{$v});
-	}
-	return $out;
-	[/perl]
-	exporting: [export variable] -->
-[/if]
 
-[if type=explicit
-	compare=|
-			[newer
-				source=__UI_PRODUCT_DIR__/variable.txt
-				target=`"$Config->{ConfDir}/status.$Config->{CatalogName}"`
-				]
-			|]
-[value name=ui_changes_made set=1 hide=1]
-<FONT COLOR="__CONTRAST__">You need to [page __UI_BASE__/reconfig @@MV_PAGE@@]apply changes[/page] for changes to take effect.</FONT>
-[/if]
 
-[calc]
-		@areas = grep /\S/, split /\s+/, tag_data(qw/variable Variable TAXAREA/);
-		@rates = grep /\S/, split /,/, tag_data(qw/variable Variable TAXRATE/);
-		my $taxship = tag_data(qw/variable Variable TAXSHIPPING/);
-		$taxship = " $taxship ";
-		my $i;
-		my $last = -1;
-		for ($i = 0; $i < scalar @areas; $i++) {
-			my $rate = $rates[$i];
-			$rate =~ s/.*=//;
-			$rate =~ s/[^\d.]//g;
-			my $ship = ($taxship =~ / $areas[$i] /i) ? $areas[$i] : '';
-			push @out, "$i\t$areas[$i]\t$rate\t$ship";
-			$last = $i;
+<FORM ACTION="[area @@MV_PAGE@@]" METHOD=GET>
+<table __UI_T_PROPERTIES__>
+<input type=hidden name=mv_action value="go">
+<tr>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+<tr>
+<td colspan=2  class=rnorm>
+<B>Set tax type</B>
+</td>
+</tr>
+<tr>
+<td colspan=2 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+
+<tr>
+<td class=rnorm align=right>
+<B>Country</B>
+</td>
+<td class=rnorm>
+	      <SELECT onChange="this.form.submit()" NAME=taxcountry>
+		  <OPTION VALUE="US">[L]United States[/L]
+	      [loop option=taxcountry search="
+				ra=yes
+				fi=country
+				st=db
+				rf=code,name
+				ml=1000
+				tf=name
+	      "]
+	      <OPTION VALUE="[loop-code]"> [loop-data country name] 
+	      [/loop]
+	      </SELECT>
+</td>
+</tr>
+
+[if value taxcountry]
+[try]
+[perl tables="country state"]
+	my $col   = $::Variable->{MV_COUNTRY_TAX_FIELD} || 'tax';
+	my $taxdata;
+	my $out;
+	my $set;
+	if($CGI->{tax_set}) {
+		if($CGI->{taxtype} eq '' or $CGI->{taxtype} eq 'none') {
+			$taxdata = '';
 		}
-		if ($CGI->{addnewtax}) {
-			$last++;
-			push @out, "$last\tnew";
+		elsif($CGI->{taxtype} eq 'simple:state') {
+			$taxdata = 'simple:state';
 		}
-		$Scratch->{its} = join "\n", @out;
-		return;
-[/calc]
-<p>
-<form action="[area @@MV_PAGE@@]" method=POST>
-<INPUT TYPE=hidden NAME=tax_format VALUE=do>
-<TABLE width="90%" border=0 callpadding=0 cellspacing=0>
-<tr bgcolor="#000000" height=1><td colspan=4></td></tr>
-<TR BGCOLOR="#__UI_C_TOPBLOCKBAR__">
-<TD VALIGN="top" width="20%">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<b>Location</b>
+		elsif($CGI->{taxtype} eq 'state') {
+			$taxdata = 'state';
+		}
+		else {
+			$taxdata = $CGI->{taxdata} || 'default = 10%, food = 0';
+		}
+		tag_data('country', $col, $CGI->{taxcountry}, { value => $taxdata });
+		if($taxdata eq 'state') {
+			my $sdb = $Db{state};
+			my (@row) = split /\0/, $CGI->{taxstate};
+			my (@val) = split /\0/, $CGI->{taxstate_data};
+			my $scol   = $::Variable->{MV_STATE_TAX_FIELD} || 'tax';
+
+			for(my $i = 0; $i < @row; $i++) {
+				$sdb->set_field($row[$i], $scol, $val[$i]);
+			}
+		}
+	}
+	else {
+		$taxdata = tag_data('country', $col, $Values->{taxcountry});
+	}
+	if(! length($taxdata) ) {
+		# None
+		$Values->{taxtype} = 'none';
+		delete $Values->{taxdata};
+	}
+	elsif($taxdata eq 'simple:state') {
+		$Values->{taxtype} = 'simple:state';
+		delete $Values->{taxdata};
+	}
+	elsif($taxdata eq 'state') {
+		$Values->{taxtype} = 'state';
+		delete $Values->{taxdata};
+	}
+	else {
+		$Values->{taxtype} = 'vat';
+		$Values->{taxdata} = $taxdata;
+	}
+	return unless $set;
+	$out = ::errmsg(
+				"set tax type for %s to: %s",
+				$CGI->{taxcountry},
+				$Values->{taxtype},
+			);
+	return qq{
+		<tr>
+		<td class=rnorm align=right>
+		<B>Action</B>
+		</td>
+		<td class=rnorm>
+		$out
+		</td>
+		</tr>
+	};
+[/perl]
+[/try]
+
+<tr>
+<td class=rnorm align=right>
+<B>Tax type</B>
 </td>
-<TD align=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<b>Tax Rate (%)</b>
+<td class=rnorm>
+[catch]Trouble getting/setting tax data.[/catch]
+	      <SELECT NAME=taxtype>
+		  <OPTION VALUE="">[L]No tax[/L]
+		  <OPTION VALUE="state" [selected taxtype state]>[L]State/Province based[/L]
+		  <OPTION VALUE="vat" [selected taxtype vat]>[L]VAT, based on country and tax category[/L]
+	      </SELECT>
 </td>
-<TD align=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<b>Apply tax to shipping charge</b>
+</tr>
+	[if value taxdata]
+<tr>
+<td class=rnorm align=right>
+<B>Tax Data</B>
 </td>
-<TD VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-&nbsp;
+<td class=rnorm>
+	      <TEXTAREA NAME=taxdata ROWS=8 COLS=60>[value taxdata]</TEXTAREA>
 </td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=4></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=4></td></tr>
-
-[loop lr=1 list="[scratch its]"]
+	[/if]
+	[if value taxtype eq 'state']
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
-<input type=text name="taxarea[loop-code]" size=40 value="[loop-pos 1]">
+<td class=rnorm align=right colspan=2>
+<B>State Tax Data</B>
 </td>
+</tr>
 
-<td align=center bgcolor="__UI_C_INTBLOCK__">
-<input type=text name="taxrate[loop-code]" 
- size=7 value="[loop-pos 2]">
+<tr>
+[query list=1
+	sql="select code,name,tax from state where country = '[value taxcountry]'"
+	]
+<tr>
+<td class=rnorm align=right>
+<INPUT TYPE=hidden NAME=taxstate VALUE="[sql-code]">
+[sql-param name]
 </td>
-
-<td bgcolor="__UI_C_INTBLOCK__" align=center valign=center>
-<INPUT TYPE=CHECKBOX NAME=taxship[loop-code] VALUE="1"[if-loop-pos 3] CHECKED[/if-loop-pos]>
+<td class=rnorm>
+<INPUT TYPE=text SIZE=60 NAME=taxstate_data VALUE="[sql-param tax]">
 </td>
+</tr>
+[/query]
+	[/if]
 
-<td bgcolor="__UI_C_INTBLOCK__" align=lrft valign=center>
-<INPUT TYPE=image src="@_UI_IMG_@admin/delete.gif" width=20 height=20 border=0 NAME=Delete[loop-code]>
+<tr>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+<tr>
+<td colspan=2  class=rnorm>
+<B>
+<INPUT TYPE=submit NAME=tax_set VALUE="[L]Set tax type[/L]">
+</B>
 </td>
-
 </tr>
-[/loop]
+[else]
 <tr>
-<td colspan=4 bgcolor="__UI_C_INTBLOCK__"><a href="[area href=@@MV_PAGE@@ form='addnewtax=ok']"><img src="@_UI_IMG_@admin/plus.gif" width=20 height=20 border=0></a></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+</tr>
+<tr>
+<td colspan=2  class=rnorm>
+<B>
+<INPUT TYPE=submit VALUE="[L]Get current tax data[/L]">
+</B>
+</td>
+</tr>
+[/else]
+[/if]
+<tr>
+<td colspan=2 class=rspacer><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
-
-<tr bgcolor="#000000" height=1><td colspan=4></td></tr>
-
 </table>
-
-<p>
-[button text="Update values"]
-mv_todo=return
-[/button]
-</form>
-
-
+</FORM>
 <!-- ----- END REAL STUFF ----- -->
 
 @_UI_STD_FOOTER_@



1.7.4.1   +32 -30    interchange/dist/lib/UI/pages/admin/trafficstats.html


rev 1.7.4.1, prev_rev 1.7
Index: trafficstats.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/trafficstats.html,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- trafficstats.html	22 Sep 2000 07:07:17 -0000	1.7
+++ trafficstats.html	25 Jan 2003 22:21:14 -0000	1.7.4.1
@@ -1,67 +1,69 @@
-[if !advanced report]
+@_UI_STD_INIT_@[if-mm !advanced trafficstats]
+[set ui_error]
+[L]Not authorized for traffic statistics.[/L]
+[/set]
 [bounce page="__UI_BASE__/error"]
 [value name=saved_report set=""]
-[/if]
-[set page_title]Traffic Statistics[/set]
+[/if-mm]
+[set page_title][L]Traffic Statistics[/L][/set]
 [set ui_class]Reports[/set]
-[set icon_name]admin/icon_stats.gif[/set]
+[set icon_name]icon_stats.gif[/set]
 [set help_name]stats.traffic[/set]
 @_UI_STD_HEAD_@
 
-<table border=0 __UI_T_PROPERTIES__>
-<tr bgcolor="#000000" height=1><td colspan=2></td></tr>
+<table border=0 __UI_T_PROPERTIES__ width="60%">
+<tr class=rborder height=1><td colspan=2></td></tr>
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><FONT COLOR="__UI_C_TITLEBARTXT__">View Stats for this Month Only</FONT></td>
+<td colspan=2 class=rmarq>[L]View stats for this month only[/L]</td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__" colspan=2>
+<td class=rnorm colspan=2>
 
-<A HREF="[area href=__UI_BASE__/reports/traffic/ByAffiliate]">Overall by month</A><BR>
+<A HREF="[area href=__UI_BASE__/reports/traffic/ByAffiliate]">[L]Overall by month[/L]</A><BR>
 <A HREF="[area href=__UI_BASE__/reports/traffic/ByAffiliate
 				form="
 						ui_by_day=1
 						ui_begin_date=[tag time]%Y%m[/tag]
-				"]">By day for this month</A><BR>
+				"]">[L]By day for this month[/L]</A><BR>
 
 </td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 
 </table>
 <br>
-<table border=0 __UI_T_PROPERTIES__>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
+<table border=0 __UI_T_PROPERTIES__ width="60%">
+<tr class=rborder height=1><td colspan=8></td></tr>
 <tr>
-<td colspan=3 bgcolor=__UI_C_TOPBLOCKBAR__><FONT COLOR="__UI_C_TITLEBARTXT__">View Stats for Any Period of Time</FONT></td>
+<td colspan=3 class=rmarq>[L]View stats for any period of time[/L]</td>
 </tr>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 
 <FORM ACTION="[process]">
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=return>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE="__UI_BASE__/reports/traffic/ByAffiliate">
 
 <TR>
-<TD bgcolor="__UI_C_INTBLOCK__">
+<TD class=rnorm>
 
-Beginning:<BR>
+[L]Beginning:[/L]<BR>
 	[widget type=date name=ui_begin_date]
 
 </TD>
-<TD bgcolor="__UI_C_INTBLOCK__">
+<TD class=rnorm>
 
-Ending:<BR>
+[L]Ending:[/L]<BR>
 	[widget type=date name=ui_end_date]
 
 </TD>
 [if-mm advanced affiliate=l]
-<TD bgcolor="__UI_C_INTBLOCK__">
+<TD class=rnorm>
 
-For affiliate:<BR>
+[L]For affiliate:[/L]<BR>
 	<SELECT NAME=affiliate>
-		<OPTION VALUE=""> --all--
+		<OPTION VALUE=""> --[L]all[/L]--
 		[loop search="
 			fi=affiliate
 			st=db
@@ -76,22 +78,22 @@
 </TD>
 </TR>
 <TR>
-<TD COLSPAN=3 bgcolor="__UI_C_INTBLOCK__">
+<TD COLSPAN=3 class=rnorm>
 [else]
 </TR>
 <TR>
-<TD COLSPAN=3 bgcolor="__UI_C_INTBLOCK__">
+<TD COLSPAN=3 class=rnorm>
 [/else]
 [/if-mm]
-	[set By day]
+	[set [L]By day[/L]]
 	ui_by_day=1
 	[/set]
 	<BLOCKQUOTE>
-	<INPUT TYPE=submit VALUE="By month">&nbsp;&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=mv_click VALUE="By day">
+	<INPUT TYPE=submit VALUE="[L]By month[/L]">&nbsp;&nbsp;&nbsp;&nbsp;<INPUT TYPE=submit NAME=mv_click VALUE="[L]By day[/L]">
 	</BLOCKQUOTE>
 </TD>
 </TR>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 </TABLE>
 </FORM>
 </td>



1.3.4.1   +1 -1      interchange/dist/lib/UI/pages/admin/upload_config.html


rev 1.3.4.1, prev_rev 1.3
Index: upload_config.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/upload_config.html,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- upload_config.html	14 Sep 2000 07:46:48 -0000	1.3
+++ upload_config.html	25 Jan 2003 22:21:14 -0000	1.3.4.1
@@ -1,5 +1,5 @@
 [set help_name]upload.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [set ui_class]Admin[/set]
 [set page_title]Configuration Upload/Download[/set]
 [set page_perm]pages[/set]



1.4.4.3   +31 -34    interchange/dist/lib/UI/pages/admin/upload_file.html


rev 1.4.4.3, prev_rev 1.4.4.2
Index: upload_file.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/upload_file.html,v
retrieving revision 1.4.4.2
retrieving revision 1.4.4.3
diff -u -r1.4.4.2 -r1.4.4.3
--- upload_file.html	25 Oct 2000 12:21:33 -0000	1.4.4.2
+++ upload_file.html	25 Jan 2003 22:21:14 -0000	1.4.4.3
@@ -1,11 +1,11 @@
-[set page_title]Upload File[/set]
-[set page_banner]Upload File[/set]
+@_UI_STD_INIT_@[set page_title][L]Upload File[/L][/set]
+[set page_banner][L]Upload File[/L][/set]
 [set ui_class]Content[/set]
 [set page_perm]files[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 
 [if-mm function="!files" name="[data session arg]"]
-[seti ui_error]Not authorized to upload file [data session arg].[/seti]
+[seti ui_error][msg arg.0="[data session arg]"]Not authorized to upload file %s.[/msg][/seti]
 [bounce page="__UI_BASE__/error"]
 [/if-mm]
 
@@ -22,19 +22,19 @@
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 	[if type=explicit compare=`$Session->{arg} =~ m{[^/]$}`]
-	Uploading file <b>[data session arg]</B>
+	[msg arg.0="[data session arg]"]Uploading file <b>%s</B>[/msg]
 	<INPUT type=hidden NAME=ui_upload_fn VALUE="[data session arg]">
 	[elsif session arg]
-	Uploading file to 
-	<INPUT NAME=ui_upload_fn VALUE="[data session arg]" SIZE=40>
+	[msg arg.0="[data session arg]"]Uploading file to <b>%s</B>[/msg]
+	<INPUT type=hidden NAME=ui_upload_fn VALUE="[data session arg]">
 	[comment]
-	<B>File to upload</B>
+	<B>[L]File to upload[/L]</B>
 		<BLOCKQUOTE>
 		<INPUT NAME=ui_upload_fn type=hidden VALUE="[data session arg]">
 		<INPUT NAME=ui_upload_fn SIZE=40>
@@ -42,7 +42,7 @@
 	[/comment]
 	[/elsif]
 	[else]
-	<B>File to upload</B>
+	<B>[L]File to upload[/L]</B>
 		<BLOCKQUOTE>
 		<INPUT NAME=ui_upload_fn SIZE=40>
 		</BLOCKQUOTE>
@@ -53,56 +53,56 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 [set existing][/set]
 [if type=explicit compare=`$CGI->{ui_image_preview} =~ m{[^/]$}`]
 [set existing]1[/set]
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__>
-Preview: <BR>
+<td class=rnorm>
+[L]Preview:[/L] <BR>
 <IMG SRC="[cgi ui_image_preview]">
 </td>
 </tr>
 [/if]
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__>
-<B>Local file</B><BR>
+<td class=rnorm>
+<B>[L]Local file[/L]</B><BR>
 	<BLOCKQUOTE>
 	<INPUT TYPE=file NAME="ui_upload_file" SIZE=40>
 	</BLOCKQUOTE>
 <P>
-<B>Upload mode</B>
+<B>[L]Upload mode[/L]</B>
 	<BLOCKQUOTE>
 [if session arg =~ /\.(gif|jpe?g|png)$/i]
 [or cgi ui_upload_binary]
-	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=1>&nbsp;ASCII<BR>
-	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=0 CHECKED>&nbsp;Binary
+	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=1>&nbsp;[L]ASCII[/L]<BR>
+	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=0 CHECKED>&nbsp;[L]Binary[/L]
 	<P>
 	[if scratch existing]
-	<INPUT NAME=ui_upload_newfn TYPE=radio VALUE=1>&nbsp;Use new file name<BR>
-	<INPUT NAME=ui_upload_newfn TYPE=radio VALUE=0 CHECKED>&nbsp;Use existing file name
+	<INPUT NAME=ui_upload_newfn TYPE=radio VALUE=1>&nbsp;[L]Use new file name[/L]<BR>
+	<INPUT NAME=ui_upload_newfn TYPE=radio VALUE=0 CHECKED>&nbsp;[L]Use existing file name[/L]
 	[/if]
 [else]
-	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=1 CHECKED>&nbsp;ASCII<BR>
-	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=0>&nbsp;Binary
+	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=1 CHECKED>&nbsp;[L]ASCII[/L]<BR>
+	<INPUT NAME=ui_upload_ascii TYPE=radio VALUE=0>&nbsp;[L]Binary[/L]
 [/else]
 [/if]
 	</BLOCKQUOTE>
 <P>
-<B>Backup mode</B>
+<B>[L]Backup mode[/L]</B>
 	<BLOCKQUOTE>
 	[if cgi ui_backup]
-	<INPUT NAME=ui_backup TYPE=radio VALUE=1 CHECKED>&nbsp;Back up<BR>
-	<INPUT NAME=ui_backup TYPE=radio VALUE=0>&nbsp;NO backup
+	<INPUT NAME=ui_backup TYPE=radio VALUE=1 CHECKED>&nbsp;[L]Back up[/L]<BR>
+	<INPUT NAME=ui_backup TYPE=radio VALUE=0>&nbsp;[L]NO backup[/L]
 	[else]
-	<INPUT NAME=ui_backup TYPE=radio VALUE=1>&nbsp;Back up<BR>
-	<INPUT NAME=ui_backup TYPE=radio VALUE=0 CHECKED>&nbsp;NO backup
+	<INPUT NAME=ui_backup TYPE=radio VALUE=1>&nbsp;[L]Back up[/L]<BR>
+	<INPUT NAME=ui_backup TYPE=radio VALUE=0 CHECKED>&nbsp;[L]NO backup[/L]
 	[/else]
 	[/if]
 	</BLOCKQUOTE>
 <P>
-[button text="Upload" src="@_UI_IMG_@admin/upload.gif"]
+[button text="[L]Upload[/L]" src="upload.gif"]
 	[calc]
 		if( $CGI->{ui_upload_newfn} or $CGI->{ui_upload_fn} =~ m:/$:) {
 			my $image = $CGI->{ui_upload_file};
@@ -128,17 +128,14 @@
 		return;
 	[/calc]
 [/button]
-[button text="Cancel" src="@_UI_IMG_@admin/dalete.gif"]
-	[return-to click]
-	mv_todo=back
-[/button]
+<INPUT TYPE=submit NAME=mv_click VALUE=[L]Cancel[/L]>
 
 </FORM>
 </td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 </table>



1.2.4.1   +1 -1      interchange/dist/lib/UI/pages/admin/upload_image.html


rev 1.2.4.1, prev_rev 1.2
Index: upload_image.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/upload_image.html,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- upload_image.html	14 Sep 2000 07:46:48 -0000	1.2
+++ upload_image.html	25 Jan 2003 22:21:14 -0000	1.2.4.1
@@ -1,5 +1,5 @@
 [set help_name]upload.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [set ui_class]Items[/set]
 [set page_title]Image check Upload[/set]
 [set page_perm]pages[/set]



1.3.4.1   +1 -1      interchange/dist/lib/UI/pages/admin/upload_pages.html


rev 1.3.4.1, prev_rev 1.3
Index: upload_pages.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/upload_pages.html,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- upload_pages.html	14 Sep 2000 07:46:48 -0000	1.3
+++ upload_pages.html	25 Jan 2003 22:21:14 -0000	1.3.4.1
@@ -1,5 +1,5 @@
 [set help_name]upload.main[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [set ui_class]Design[/set]
 [set page_title]Upload/Download Pages[/set]
 [set page_perm]pages[/set]



1.6.4.2   +60 -127   interchange/dist/lib/UI/pages/admin/user_change_pass.html


rev 1.6.4.2, prev_rev 1.6.4.1
Index: user_change_pass.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/user_change_pass.html,v
retrieving revision 1.6.4.1
retrieving revision 1.6.4.2
diff -u -r1.6.4.1 -r1.6.4.2
--- user_change_pass.html	20 Oct 2000 10:18:26 -0000	1.6.4.1
+++ user_change_pass.html	25 Jan 2003 22:21:14 -0000	1.6.4.2
@@ -1,182 +1,115 @@
+[tmp passuser][either][cgi username][or][cgi user_id][/either][/tmp]
 [calc]
 	$CGI->{no_dbmenu} = 1;
 	$CGI->{access_menu} = 1;
-	return [/calc]
-[seti page_title]Change password: [cgi user_id][/seti]
-[seti page_banner]Change password: <B>[cgi user_id]</B>[/seti]
+	return;
+[/calc]
+[seti page_title][L]Change password[/L]: [scratch passuser][/seti]
+[seti page_banner][L]Change password[/L]: <b>[scratch passuser]</b>[/seti]
 [set ui_class]Admin[/set]
 [set page_perm]access=e[/set]
 [set help_name]change.password[/set]
-[set icon_name]admin/icon_config.gif[/set]
-[set no_old_needed][/set]
+[set icon_name]icon_config.gif[/set]
+[tmp old_needed]1[/tmp]
 [if-mm super]
 	[calc]
-		$Scratch->{no_old_needed} = 1
-			unless $CGI->{user_id} eq $Session->{username};
+		# Note that the final authority on whether the old password is needed
+		# is &Vend::UserDB::change_pass -- this logic is for widget display only.
+		$Scratch->{old_needed} = 0 if $CGI->{user_id} ne $Session->{username};
 		return;
 	[/calc]
 [/if-mm]
 @_UI_STD_HEAD_@
 
 [if session failure]
-<P>
-&nbsp;
-<BLOCKQUOTE>
-<FONT COLOR=RED>[L]Failure:[/L]</FONT> [data session failure][data base=session field=failure value=""]
-</BLOCKQUOTE>
-<P>
-&nbsp;
+	<blockquote class=cerror>
+		[L]Failure:[/L] [data session failure][data base=session field=failure value=""]
+	</blockquote>
 [/if]
 
 [if scratch ui_message]
-<P>
-<BLOCKQUOTE>
-	[scratch ui_message][set ui_message][/set]
-</BLOCKQUOTE>
-<P>
-&nbsp;
+	<blockquote class=cmessage>
+		[scratchd ui_message]
+	</blockquote>
 [/if]
 
-[if scratch no_old_needed]
-[then]
-[set no_old_needed][/set]
-[loop list="[cgi user_id]"]
-
-[set check_match]
-[calc]
-	if ($CGI->{password} eq $CGI->{verify}) {
-		$CGI->{password} = $Tag->filter( 'crypt', $CGI->{password} );
-		return 'mv_todo=set';
-	}
-	$Session->{failure} = "Password and verify do not match.";
-	return "mv_todo=back\nmv_nextpage=@@MV_PAGE@@";
-[/calc]
-[/set]
-
-<form action="[area ui]" method="post">
-<INPUT TYPE=hidden NAME=mv_todo VALUE=back>
+<FORM ACTION="[process]" METHOD=POST>
+<INPUT TYPE=hidden NAME=mv_session_id VALUE="[data session id]">
+<INPUT TYPE=hidden NAME=mv_todo     VALUE=back>
 <INPUT TYPE=hidden NAME=mv_nextpage VALUE=__UI_BASE__/access>
-<INPUT TYPE=hidden NAME=mv_data_table VALUE="[value mv_data_table]">
-<INPUT TYPE=hidden NAME=mv_data_key VALUE="username">
-<INPUT TYPE=hidden NAME=mv_click VALUE="check_match">
-<INPUT TYPE=hidden NAME=mv_data_fields VALUE="username password">
+<INPUT TYPE=hidden NAME=mv_failpage VALUE=@@MV_PAGE@@>
+<INPUT TYPE=hidden NAME=mv_username VALUE="[scratch passuser]">
+<INPUT TYPE=hidden NAME=user_id     VALUE="[scratch passuser]">
 
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>User name</small>
+<td class=rnorm align=right>
+<small>[L]User name[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
-	<input type=hidden name=mv_data_function value="update">
-	<input type=hidden name=username value="[loop-code]">[loop-code]
+<td class=rnorm>
+[scratch passuser]
 </td>
 </tr>
 
+[if scratch old_needed]
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td class=rnorm align=right>
+<small>[L]Old password[/L]</small>
+</td>
+<td class=rnorm>
+<INPUT TYPE=password NAME=mv_password_old VALUE="" SIZE=12>
+</td>
 </tr>
+[/if]
+
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>New password</small>
+<td class=rnorm align=right>
+<small>[L]New password[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
-<INPUT TYPE=password NAME=password VALUE="" SIZE=10>
+<td class=rnorm>
+<INPUT TYPE=password NAME=mv_password VALUE="" SIZE=12>
 </td>
 </tr>
 
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>Verify password</small>
+<tr>
+<td class=rnorm align=right>
+<small>[L]Verify password[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
-<INPUT TYPE=password SIZE=10 NAME=verify VALUE="">
+<td class=rnorm>
+<INPUT TYPE=password NAME=mv_verify VALUE="" SIZE=12>
 </td>
 </tr>
 
-
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
 </tr>
 
-</table>
-
-<p>
+</TABLE>
 
-[set Ok]
-[/if-mm]
-[/set]
 [if-mm advanced access=e]
-	[set Ok]
-	mv_todo=set
-	[/set]
-	<input type=submit name="mv_click" value="Ok">
-	<input type=submit value="Cancel">
+	[button text="[if scratch old_needed][L]Change[/L][else][L]Set Password[/L][/else][/if]"]
+		mv_todo=set
+		mv_click=MMChange
+	[/button]
+	[button text=[L]Permissions[/L]]
+		mv_todo=set
+		mv_click=MMChange
+		mv_nextpage=__UI_BASE__/access_permissions
+	[/button]
+	[button text=[L]Cancel[/L]]
+	[/button]
 [else]
-	[set Back]
-	mv_todo=back
-	[/set]
-	<input type=submit value="Back">
+	[button text=[L]Back[/L]]
+	[/button]
 [/else]
 [/if-mm]
 
-</form>
-[/loop]
-[/then]
-[else]
-
-<FORM ACTION="[process]" METHOD=POST>
-	<INPUT TYPE=hidden NAME=mv_click VALUE=MMChange>
-	<INPUT TYPE=hidden NAME=mv_todo  VALUE=back>
-	<INPUT TYPE=hidden NAME=mv_nextpage VALUE=__UI_BASE__/access>
-	<INPUT TYPE=hidden NAME=mv_failpage VALUE=@@MV_PAGE@@>
-	<INPUT TYPE=hidden NAME=mv_username VALUE="[cgi user_id]">
-<table __UI_T_PROPERTIES__>
-
-<tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>Old password</small>
-</td>
-<td bgcolor=__UI_C_INTBLOCK__>
-<INPUT TYPE=password NAME=mv_password_old VALUE="" SIZE=10>
-</td>
-</tr>
-
-
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>New password</small>
-</td>
-<td bgcolor=__UI_C_INTBLOCK__>
-<INPUT TYPE=password NAME=mv_password VALUE="" SIZE=10>
-</td>
-</tr>
-
-<tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>Verify password</small>
-</td>
-<td bgcolor=__UI_C_INTBLOCK__>
-<INPUT TYPE=password NAME=mv_verify VALUE="" SIZE=10>
-</td>
-</tr>
-
-<tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1></td>
-</tr>
-
-</TABLE>
-<INPUT TYPE=submit VALUE="Change" SIZE=10>
 </FORM>
-[/else]
-[/if]
 
 @_UI_STD_FOOTER_@
 



1.8.4.2   +42 -31    interchange/dist/lib/UI/pages/admin/user_edit.html


rev 1.8.4.2, prev_rev 1.8.4.1
Index: user_edit.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/user_edit.html,v
retrieving revision 1.8.4.1
retrieving revision 1.8.4.2
diff -u -r1.8.4.1 -r1.8.4.2
--- user_edit.html	20 Oct 2000 10:18:26 -0000	1.8.4.1
+++ user_edit.html	25 Jan 2003 22:21:14 -0000	1.8.4.2
@@ -3,12 +3,12 @@
 	$CGI->{access_menu} = 1;
 	return;
 [/calc]
-[seti page_title]Administrator Edit: [cgi user_id][/seti]
+[seti page_title][L]Administrator Edit[/L]: [cgi user_id][/seti]
+[seti page_banner][L]Administrator Edit[/L]: <b>[cgi user_id]</b>[/seti]
 [set ui_class]Admin[/set]
-[seti page_banner]Administrator Edit: <B>[cgi user_id]</B>[/seti]
 [set page_perm]access=v[/set]
 [set help_name]admin.edit[/set]
-[set icon_name]admin/icon_config.gif[/set]
+[set icon_name]icon_config.gif[/set]
 [calc]
 	$CGI->{mv_data_table} = $Values->{mv_data_table} = '__UI_ACCESS_TABLE__'; 
 	return;
@@ -26,40 +26,44 @@
 [loop list="[cgi user_id]"]
 <form action="[area ui]" method="post">
 <INPUT TYPE=hidden NAME=mv_todo VALUE=back>
-<INPUT TYPE=hidden NAME=mv_nextpage VALUE=__UI_BASE__/access>
+<INPUT TYPE=hidden NAME=mv_nextpage VALUE=[comment]
+If creating new user, go to password entry page after this.
+[/comment]"[if cgi user_id eq 'NEW']__UI_BASE__/user_change_pass[else]__UI_BASE__/access[/else][/if]">
 <INPUT TYPE=hidden NAME=mv_data_table VALUE="[value mv_data_table]">
 <INPUT TYPE=hidden NAME=mv_data_key VALUE="username">
 <INPUT TYPE=hidden NAME=mv_update_empty VALUE="1">
-<INPUT TYPE=hidden NAME=mv_data_fields VALUE="username name super groups">
+<INPUT TYPE=hidden NAME=yes_tables VALUE="NONE">
+<INPUT TYPE=hidden NAME=yes_functions VALUE="NONE">
+<INPUT TYPE=hidden NAME=mv_data_fields VALUE="username name super groups yes_tables yes_functions">
 
 <table __UI_T_PROPERTIES__>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
 <input type="hidden" name="user_id" value="[cgi user_id]">
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>Real name</small>
+<td class=rnorm align=right>
+<small>[L]Real name[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <input type=text size=40 name=name maxlength=100 value="[filter entities][loop-data __UI_ACCESS_TABLE__ name][/filter]">
 </td>
 </tr>
 
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>User name</small>
+<td class=rnorm align=right>
+<small>[L]User name[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 [if cgi ui_hide_key]
 	<input type=hidden name=mv_data_function value="update">
 	<input type=hidden name=username value="[loop-code]">[loop-code]
 [else]
 	[if-mm !advanced access=c]
-	[set ui_error]No permission to create user.[/set]
+	[set ui_error][L]No permission to create user.[/L][/set]
 	[bounce page="__UI_BASE__/error"]
 	[/set]
 	[/if-mm]
@@ -71,27 +75,31 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>Super-user</small>
+<td class=rnorm align=right>
+<small>[L]Super-user[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 <INPUT type=checkbox name=super value=1 [if-loop-data __UI_ACCESS_TABLE__ super]checked[/if-loop-data]>
 </td>
 </tr>
 
-<tr><td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=1 height=1></td></tr>
+<tr><td colspan=2 class=rborder><img src="bg.gif" width=1 height=1></td></tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__ align=right>
-<small>Groups</small>
+<td class=rnorm align=right>
+<small>[L]Groups[/L]</small>
 </td>
-<td bgcolor=__UI_C_INTBLOCK__>
-[value name=groups set="[loop-data __UI_ACCESS_TABLE__ groups]" filter=space_to_null hide=1]
+<td class=rnorm>
+[calc]
+	$Values->{groups} = q{[loop-data __UI_ACCESS_TABLE__ groups]};
+	$Values->{groups} =~ s/(\w+)/:$1/g;
+	$Values->{groups} =~ s/\s+/\0/g;
+	return;
+[/calc]
 <INPUT TYPE=hidden NAME=ui_filter:groups VALUE=null_to_space>
 <select name=groups size=5 multiple>
 [loop
 	prefix=group
-	option=groups
 	multiple=1
 	search="
 		fi=__UI_ACCESS_TABLE__
@@ -103,14 +111,14 @@
 		bs=yes
 		ml=1000
 	"
-]<OPTION VALUE="[group-code]">[group-data __UI_ACCESS_TABLE__ name]
+]<OPTION VALUE="[group-code]" [selected groups [group-code]]>[group-data __UI_ACCESS_TABLE__ name]
 [/loop]
 </select>
 </td>
 </tr>
 
 <tr>
-<td colspan=2 bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td colspan=2 class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
 </table>
@@ -118,16 +126,19 @@
 <p>
 
 [if-mm advanced access=e]
-	[button text=Ok]
+	[button text=[L]Ok[/L]]
+		[calc]$CGI->{groups} =~ s/://g; return[/calc]
 		mv_todo=set
 	[/button]
-	[button text=Permissions]
-		mv_todo=back
-		mv_nextpage=__UI_BASE__/access_permissions
-	[/button]
-	<input type=submit value="Cancel">
+	[if cgi user_id ne 'NEW']
+		[button text=[L]Permissions[/L]]
+			mv_todo=set
+			mv_nextpage=__UI_BASE__/access_permissions
+		[/button]
+	[/if]
+	<input type=submit value="[L]Cancel[/L]">
 [else]
-	[button text=Back]
+	[button text=[L]Back[/L]]
 	mv_todo=back
 	[/button]
 [/else]



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/.access


<<.access: empty>>


2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/.autoload


rev 2.0.4.1, prev_rev 2.0
Index: .autoload
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/.autoload,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/auto_wizard.html


rev 1.1.2.1, prev_rev 1.1
Index: auto_wizard.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/auto_wizard.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/commerce.html


rev 2.1.2.1, prev_rev 2.1
Index: commerce.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/commerce.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.6.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/content.html


rev 1.6.2.1, prev_rev 1.6
Index: content.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/content.html,v
retrieving revision 1.6
retrieving revision 1.6.2.1
diff -u -r1.6 -r1.6.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/content_components.html


rev 2.1.2.1, prev_rev 2.1
Index: content_components.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/content_components.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.4.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/content_editor.html


rev 1.4.2.1, prev_rev 1.4
Index: content_editor.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/content_editor.html,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/content_preview.html


rev 1.1.2.1, prev_rev 1.1
Index: content_preview.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/content_preview.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/content_publish.html


rev 1.2.2.1, prev_rev 1.2
Index: content_publish.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/content_publish.html,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.3.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/content_push.html


rev 1.3.2.1, prev_rev 1.3
Index: content_push.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/content_push.html,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/content_templates.html


rev 2.1.2.1, prev_rev 2.1
Index: content_templates.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/content_templates.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/customer_all.html


rev 2.2.2.1, prev_rev 2.2
Index: customer_all.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_all.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/customer_comments.html


rev 2.1.2.1, prev_rev 2.1
Index: customer_comments.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_comments.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.6.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/customer_mailing.html


rev 1.6.2.1, prev_rev 1.6
Index: customer_mailing.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/customer_mailing.html,v
retrieving revision 1.6
retrieving revision 1.6.2.1
diff -u -r1.6 -r1.6.2.1



2.11.2.1  +1 -1      interchange/dist/lib/UI/pages/admin/db_metaconfig.html


rev 2.11.2.1, prev_rev 2.11
Index: db_metaconfig.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/db_metaconfig.html,v
retrieving revision 2.11
retrieving revision 2.11.2.1
diff -u -r2.11 -r2.11.2.1
--- db_metaconfig.html	14 Jan 2003 02:25:50 -0000	2.11
+++ db_metaconfig.html	25 Jan 2003 22:21:13 -0000	2.11.2.1
@@ -344,4 +344,4 @@
 
 ]
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ version: $Revision: 2.11 $ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 2.11.2.1 $ -->



2.2.2.1   +1 -1      interchange/dist/lib/UI/pages/admin/db_newview.html


rev 2.2.2.1, prev_rev 2.2
Index: db_newview.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/db_newview.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1
--- db_newview.html	14 Jan 2003 02:25:50 -0000	2.2
+++ db_newview.html	25 Jan 2003 22:21:13 -0000	2.2.2.1
@@ -84,4 +84,4 @@
 
 @_UI_STD_FOOTER_@
 
-<!-- page: @@MV_PAGE@@ Revision: $Id: db_newview.html,v 2.2 2003/01/14 02:25:50 mheins Exp $ -->
+<!-- page: @@MV_PAGE@@ Revision: $Id: db_newview.html,v 2.2.2.1 2003/01/25 22:21:13 racke Exp $ -->



2.5.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/dbconfig.html


rev 2.5.2.1, prev_rev 2.5
Index: dbconfig.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/dbconfig.html,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/dbconfig_save.html


rev 2.1.2.1, prev_rev 2.1
Index: dbconfig_save.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/dbconfig_save.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/direct_sql.html


rev 1.2.2.1, prev_rev 1.2
Index: direct_sql.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/direct_sql.html,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



2.1.2.1   +1 -1      interchange/dist/lib/UI/pages/admin/edit_metaconfig.html


rev 2.1.2.1, prev_rev 2.1
Index: edit_metaconfig.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/edit_metaconfig.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1
--- edit_metaconfig.html	14 Jan 2003 02:25:50 -0000	2.1
+++ edit_metaconfig.html	25 Jan 2003 22:21:13 -0000	2.1.2.1
@@ -297,4 +297,4 @@
 
 ]
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ version: $Revision: 2.1 $ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 2.1.2.1 $ -->



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/file_transfer.html


rev 2.1.2.1, prev_rev 2.1
Index: file_transfer.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/file_transfer.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/flex_group.html


rev 2.2.2.1, prev_rev 2.2
Index: flex_group.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/flex_group.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/generic.html


rev 2.1.2.1, prev_rev 2.1
Index: generic.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/generic.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/genfunction.html


rev 2.1.2.1, prev_rev 2.1
Index: genfunction.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/genfunction.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/gpg_key.html


rev 2.1.2.1, prev_rev 2.1
Index: gpg_key.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/gpg_key.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.6.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/help.html


rev 2.6.2.1, prev_rev 2.6
Index: help.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/help.html,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/item_group.html


rev 2.2.2.1, prev_rev 2.2
Index: item_group.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_group.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/item_option.html


rev 2.2.2.1, prev_rev 2.2
Index: item_option.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_option.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/item_option_phantom.html


rev 2.1.2.1, prev_rev 2.1
Index: item_option_phantom.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/item_option_phantom.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.6.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/layout_auto.html


rev 2.6.2.1, prev_rev 2.6
Index: layout_auto.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/layout_auto.html,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1



2.19.2.1  +0 -0      interchange/dist/lib/UI/pages/admin/menu_editor.html


rev 2.19.2.1, prev_rev 2.19
Index: menu_editor.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/menu_editor.html,v
retrieving revision 2.19
retrieving revision 2.19.2.1
diff -u -r2.19 -r2.19.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/menu_loader.html


rev 2.2.2.1, prev_rev 2.2
Index: menu_loader.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/menu_loader.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/merge_meta.html


rev 2.1.2.1, prev_rev 2.1
Index: merge_meta.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/merge_meta.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.3.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/misc_order_number.html


rev 2.3.4.1, prev_rev 2.3
Index: misc_order_number.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/misc_order_number.html,v
retrieving revision 2.3
retrieving revision 2.3.4.1
diff -u -r2.3 -r2.3.4.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/order_status_alt.html


rev 2.1.2.1, prev_rev 2.1
Index: order_status_alt.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/order_status_alt.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +1 -1      interchange/dist/lib/UI/pages/admin/page_metaconfig.html


rev 2.1.2.1, prev_rev 2.1
Index: page_metaconfig.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/page_metaconfig.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1
--- page_metaconfig.html	14 Jan 2003 02:25:50 -0000	2.1
+++ page_metaconfig.html	25 Jan 2003 22:21:14 -0000	2.1.2.1
@@ -65,5 +65,5 @@
 
 ]
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ version: $Revision: 2.1 $ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 2.1.2.1 $ -->
 



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/page_upload.html


rev 2.1.2.1, prev_rev 2.1
Index: page_upload.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/page_upload.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/pref_colors.html


rev 2.1.2.1, prev_rev 2.1
Index: pref_colors.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/pref_colors.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +1 -1      interchange/dist/lib/UI/pages/admin/pref_select.html


rev 2.1.2.1, prev_rev 2.1
Index: pref_select.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/pref_select.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1
--- pref_select.html	14 Jan 2003 02:25:50 -0000	2.1
+++ pref_select.html	25 Jan 2003 22:21:14 -0000	2.1.2.1
@@ -596,4 +596,4 @@
 [update values]
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ Revision: $Id: pref_select.html,v 2.1 2003/01/14 02:25:50 mheins Exp $ -->
+<!-- page: @@MV_PAGE@@ Revision: $Id: pref_select.html,v 2.1.2.1 2003/01/25 22:21:14 racke Exp $ -->



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/quick_question.html


rev 2.1.2.1, prev_rev 2.1
Index: quick_question.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/quick_question.html,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.5.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/search_replace.html


rev 1.5.2.1, prev_rev 1.5
Index: search_replace.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/search_replace.html,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/show_session.html


rev 2.2.2.1, prev_rev 2.2
Index: show_session.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/show_session.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.4.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/tax_simple.html


rev 2.4.2.1, prev_rev 2.4
Index: tax_simple.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/tax_simple.html,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/test_code.html


rev 1.2.2.1, prev_rev 1.2
Index: test_code.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/test_code.html,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/accounting/index.html


rev 1.2.2.1, prev_rev 1.2
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/accounting/index.html,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.4.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/accounting/return.html


rev 1.4.2.1, prev_rev 1.4
Index: return.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/accounting/return.html,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



No                   revision



No                   revision



1.10.4.10 +35 -18    interchange/dist/lib/UI/pages/admin/reports/order/ByAffiliate.html


rev 1.10.4.10, prev_rev 1.10.4.9
Index: ByAffiliate.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/reports/order/ByAffiliate.html,v
retrieving revision 1.10.4.9
retrieving revision 1.10.4.10
diff -u -r1.10.4.9 -r1.10.4.10
--- ByAffiliate.html	27 Nov 2000 01:43:11 -0000	1.10.4.9
+++ ByAffiliate.html	25 Jan 2003 22:21:19 -0000	1.10.4.10
@@ -4,11 +4,29 @@
 			return;
 	[/calc]
 [/if-mm]
-[seti page_title]Orders by Affiliate[if cgi affiliate]: [cgi affiliate][/if][/seti]
-[set icon_name]admin/icon_stats.gif[/set]
+[seti page_title][L]Orders by Affiliate[/L][if cgi affiliate]: [cgi affiliate][/if][/seti]
+[set icon_name]icon_stats.gif[/set]
 [set help_name]orderstats.view[/set]
 
 @_UI_STD_HEAD_@
+<TABLE width="90%" border=0 cellpadding=0 cellspacing=0>
+<tr class=rborder height=1><td colspan=4></td></tr>
+<TR class=rmarq>
+	<TD VALIGN=top width="20%">
+		[L]Date[/L]
+	</TD>
+	<TD VALIGN=top>
+		[L]Affiliate[/L]
+	</TD>
+	<TD ALIGN=right VALIGN=top>
+		[L]Number of Orders[/L]
+	</TD>
+	<TD ALIGN=right VALIGN=top>
+		[L]Revenue[/L]
+	</TD>
+</TR>
+<tr class=rborder height=1><td colspan=4></td></tr>
+
 [calc]
 	if($Session->{arg}) {
 		$Scratch->{date_limit} = "AND order_date like '$Session->{arg}%'";
@@ -94,6 +112,7 @@
 
 [query
 	st=db
+	ml=100000
 	table=transactions
 	hashref=main
 	sql="
@@ -102,7 +121,8 @@
 			WHERE deleted != '1' [scratch date_limit] [scratch synd_limit]
 			order by affiliate, [scratch campaign_field], order_date
 	"][/query]
-
+[tmp ALL][L]ALL[/L][/tmp]
+[tmp TOTAL][L]GRAND TOTAL[/L][/tmp]
 [perl tables="transactions"]
 	my %sales;
 	$master = {};
@@ -153,7 +173,7 @@
 	foreach $month (sort { $b <=> $a } keys %$master) {
 		my $year = $month;
 		$year =~ s/(\d\d\d\d)(\d\d)/$1/;
-		my $mname = $names{$2};
+		my $mname = errmsg($names{$2});
 		my $subtotal_sales  = 0;
 		my $subtotal_quantity  = 0;
         my $subtotal_commission = 0;
@@ -166,19 +186,19 @@
 			$subtotal_quantity += $record->{orders};
             $subtotal_commission += $record->{commission};
 			($syn, $camp) = split /\0/, $id, 2;
-			my $synlabel = $syn || '(none)';
+			my $synlabel = $syn || errmsg'(none)';
 			my $burl = $Tag->area('__UI_BASE__/reports/order/Monthly', $month);
 			my $url = qq{<A HREF="$burl$syndstring">$mname&nbsp;$year</A>}
 				if $mname;
 			$out .= <<EOF;
-	<TR BGCOLOR=__UI_C_INTBLOCK__>
+	<TR class=rnorm>
 	<TD VALIGN=top>
 	$url&nbsp;
 	</TD>
 	<TD VALIGN=top>
 	<A HREF="$burl&affiliate=$syn">$synlabel</A>&nbsp;<A HREF="$burl&affiliate=$syn&campaign=$camp">$camp</A>
 	</TD>
-	<TD ALIGN=center VALIGN=top>
+	<TD ALIGN=right VALIGN=top>
 	$record->{orders}
 	</TD>
 	<TD ALIGN=right VALIGN=top>
@@ -199,14 +219,14 @@
 		$subtotal_sales  = $Tag->currency({}, $subtotal_sales);
         $subtotal_commission = $Tag->currency({}, $subtotal_commission);
 		$out .= <<EOF;
-	<TR BGCOLOR="__UI_C_INTBLOCK__">
+	<TR class=rnorm>
 	<TD VALIGN=top>
 	&nbsp;
 	</TD>
 	<TD VALIGN=top>
-	ALL<BR><HR color=black size=1>
+	$Scratch->{ALL}<BR><HR color=black size=1>
 	</TD>
-	<TD ALIGN=center VALIGN=top>
+	<TD ALIGN=right VALIGN=top>
 	$subtotal_quantity
 	</TD>
 	<TD ALIGN=right VALIGN=top>
@@ -224,16 +244,16 @@
 		$total_sales  = $Tag->currency({}, $total_sales);
         $total_commission = $Tag->currency({}, $total_commission);
 		$out .= <<EOF;
-	<TR BGCOLOR="__UI_C_INTBLOCK__">
+	<TR class=rnorm>
 	<TD VALIGN="top">
 
-	GRAND TOTAL
+	$Scratch->{TOTAL}
 	</TD>
 	<TD VALIGN="top">
 
-	ALL
+	$Scratch->{ALL}
 	</TD>
-	<TD ALIGN=center VALIGN="top">
+	<TD ALIGN=right VALIGN="top">
 
 	$total_quantity
 	</TD>
@@ -249,10 +269,7 @@
 	$total_commission
 	</TD>
 	</TR>
-EOF
-    }
-    $out .= <<EOF; 
-	<tr bgcolor="#000000" height=1><td colspan=[scratch cols]></td></tr>
+	<tr class=rborder height=1><td colspan=[scratch cols]></td></tr>
 
 EOF
 [/perl]



1.10.4.4  +43 -78    interchange/dist/lib/UI/pages/admin/reports/order/Detail.html


rev 1.10.4.4, prev_rev 1.10.4.3
Index: Detail.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/reports/order/Detail.html,v
retrieving revision 1.10.4.3
retrieving revision 1.10.4.4
diff -u -r1.10.4.3 -r1.10.4.4
--- Detail.html	27 Nov 2000 00:44:59 -0000	1.10.4.3
+++ Detail.html	25 Jan 2003 22:21:19 -0000	1.10.4.4
@@ -4,74 +4,37 @@
 			return;
 	[/calc]
 [/if-mm]
-[set page_title]Order detail report[/set]
-[set icon_name]admin/icon_stats.gif[/set]
+[set page_title][L]Order detail report[/L][/set]
+[set icon_name]icon_stats.gif[/set]
 [set help_name]orderstats.view[/set]
 @_UI_STD_HEAD_@
 
-[calc]
-	if ($comm_field = $Tag->var('UI_COMMISSION_FIELD')) {
-		$Scratch->{comm_select} = ", $comm_field";
-        $Scratch->{comm_states} = [split (/\s+/, '__UI_COMMISSION_STATES__')];
-		if (@{$Scratch->{comm_states}}) {
-		    $Scratch->{comm_select} .= ', status';
-		}
-		$Scratch->{cols} = 8;
-	} else {
-		$Scratch->{comm_select} = '';
-		$Scratch->{cols} = 7;
-	}
-	return;
-[/calc]
-
-<TABLE width="90%" border=0 callpadding=0 cellspacing=0>
-<tr bgcolor="#000000" height=1><td colspan=[scratch cols]></td></tr>
-<TR BGCOLOR="#__UI_C_TOPBLOCKBAR__">
-<TD VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Order</B>
-</FONT>
-</TD>
-<TD VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Affiliate</B>
-</FONT>
-</TD>
-<TD VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Campaign</B>
-</FONT>
-</TD>
-<TD VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Address</B>
-</FONT>
-</TD>
-<TD VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Date/Time</B>
-</FONT>
-</TD>
-<TD ALIGN="right" VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Amount</B>
-</FONT>
-</TD>
-[if scratch comm_select]
-<TD ALIGN="right" VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Commission</B>
-</FONT>
-</TD>
-[/if]
-<TD ALIGN="right" VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Status</B>
-</FONT>
-</TD>
+<TABLE width="90%" border=0 cellpadding=0 cellspacing=0>
+<tr class=rborder height=1><td colspan=7></td></tr>
+<TR class=rmarq>
+	<TD VALIGN=top>
+	[L]Order[/L]
+	</TD>
+	<TD VALIGN=top>
+		[L]Affiliate[/L]
+	</TD>
+	<TD VALIGN=top>
+		[L]Campaign[/L]
+	</TD>
+	<TD VALIGN=top>
+		[L]Address[/L]
+	</TD>
+	<TD VALIGN=top>
+		[L]Date[/L]/[L]Time[/L]
+	</TD>
+	<TD ALIGN=right VALIGN=top>
+		[L]Amount[/L]
+	</TD>
+	<TD ALIGN=right VALIGN=top>
+		[L]Status[/L]
+	</TD>
 </TR>
-<tr bgcolor="#000000" height=1><td colspan=[scratch cols]></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=[scratch cols]></td></tr>
+<tr class=rborder height=1><td colspan=7></td></tr>
 
 <!-- will default to current if not set:
 		[seti today][tag time]%Y%m[/tag][/seti]
@@ -117,6 +80,7 @@
 
 [query	hashref=main
 	st=db
+	ml=100000
 	table=transactions
 	sql="
 	select order_number, affiliate, [scratch campaign_field], total_cost, payment_method, state, city, status, order_date[scratch comm_select]
@@ -128,14 +92,16 @@
 
 [perl tables="store"]
 	return <<EOF unless $Tmp->{main};
-	<TR BGCOLOR="__UI_C_INTBLOCK__">
+	<TR class=rnorm>
 	<TD VALIGN=top>
 	<H2>Bad query specified, caused error.</H2>
 	</TD>
 EOF
+	$out = '';
 	foreach $line (@{$Tmp->{main}}) {
 		$total_sales    += $line->{total_cost};
 		$amount = sprintf '%.2f', $line->{total_cost};
+	    $line->{status} = $Tag->loc('', $line->{status});
 		$url = $Tag->area('__UI_BASE__/order_view', $line->{order_number});
 		if ($Scratch->{comm_select}) {
 			if (! @{$Scratch->{comm_states}} 
@@ -155,7 +121,7 @@
 			$commcell = '';
 		}
 		$out .= <<EOF;
-	<TR BGCOLOR="__UI_C_INTBLOCK__">
+	<TR class=rnorm>
 	<TD VALIGN=top>
 	<A HREF="$url">$line->{order_number}</A>
 	</TD>
@@ -183,33 +149,32 @@
 	}
 		$total_sales  = sprintf '$%.2f', $total_sales;
 		$out .= <<EOF;
-<tr bgcolor="#FFFFFF" height=2><td colspan=[scratch cols]></td></tr>
-<tr bgcolor="#000000" height=1><td colspan=[scratch cols]></td></tr>
-	<TR BGCOLOR="__UI_C_INTBLOCK__">
-	<TD VALIGN="top">
-	GRAND TOTAL
+<tr class=rborder height=1><td colspan=7></td></tr>
+	<TR class=rnorm>
+	<TD VALIGN=top>
+		[L]GRAND TOTAL[/L]
 	</TD>
-	<TD VALIGN="top">
+	<TD VALIGN=top>
 	&nbsp;
 	</TD>
-	<TD VALIGN="top">
+	<TD VALIGN=top>
 	&nbsp;
 	</TD>
-	<TD ALIGN="right" VALIGN="top">
+	<TD ALIGN=right VALIGN=top>
 	&nbsp;
 	</TD>
-	<TD ALIGN="right" VALIGN="top">
+	<TD ALIGN=right VALIGN=top>
 	&nbsp;
 	</TD>
-	<TD ALIGN="right" VALIGN="top">
+	<TD ALIGN=right VALIGN=top>
 	$total_sales
 	</TD>
-	<TD ALIGN="right" VALIGN="top">
+	<TD ALIGN=right VALIGN=top>
 	&nbsp;
 	</FONT>
 	</TD>
 	</TR>
-	<tr bgcolor="#000000" height=1><td colspan=7></td></tr>
+	<tr class=rborder height=1><td colspan=7></td></tr>
 
 EOF
 [/perl]



1.11.4.7  +31 -60    interchange/dist/lib/UI/pages/admin/reports/order/Monthly.html


rev 1.11.4.7, prev_rev 1.11.4.6
Index: Monthly.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/reports/order/Monthly.html,v
retrieving revision 1.11.4.6
retrieving revision 1.11.4.7
diff -u -r1.11.4.6 -r1.11.4.7
--- Monthly.html	27 Nov 2000 00:44:59 -0000	1.11.4.6
+++ Monthly.html	25 Jan 2003 22:21:19 -0000	1.11.4.7
@@ -4,59 +4,28 @@
 			return;
 	[/calc]
 [/if-mm]
-[set page_title]Orders by day for a month[/set]
-[set icon_name]admin/icon_stats.gif[/set]
+[set page_title][L]Orders by day for a month[/L][/set]
+[set icon_name]icon_stats.gif[/set]
 [set help_name]orderstats.view[/set]
 @_UI_STD_HEAD_@
 
-[calc]
-	if ($comm_field = $Tag->var('UI_COMMISSION_FIELD')) {
-		$Scratch->{comm_select} = ", $comm_field";
-        $Scratch->{comm_states} = [split (/\s+/, '__UI_COMMISSION_STATES__')];
-		if (@{$Scratch->{comm_states}}) {
-		    $Scratch->{comm_select} .= ', status';
-		}
-		$Scratch->{cols} = 5;
-	} else {
-		$Scratch->{comm_select} = '';
-		$Scratch->{cols} = 4;
-	}
-	return;
-[/calc]
-
-<TABLE width="90%" border=0 callpadding=0 cellspacing=0>
-<tr bgcolor="#000000" height=1><td colspan=4></td></tr>
-<TR BGCOLOR="#__UI_C_TOPBLOCKBAR__">
-<TD VALIGN="top" width="20%">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Date</B>
-</FONT>
-</TD>
-<TD VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Affiliate/Campaign</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Number of Orders</B>
-</FONT>
-</TD>
-<TD ALIGN=right VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Revenue</B>
-</FONT>
-</TD>
-[if scratch comm_select]
-<TD ALIGN=right VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Commission Owed</B>
-</FONT>
-</TD>
-[/if]
+<TABLE width="90%" border=0 cellpadding=0 cellspacing=0>
+<tr class=rborder height=1><td colspan=4></td></tr>
+<TR class=rmarq>
+	<TD VALIGN="top" width="20%">
+		[L]Date[/L]
+	</TD>
+	<TD VALIGN="top">
+		[L]Affiliate[/L]/[L]Campaign[/L]
+	</TD>
+	<TD ALIGN=center VALIGN="top">
+		[L]Number of Orders[/L]
+	</TD>
+	<TD ALIGN=right VALIGN="top">
+		[L]Revenue[/L]
+	</TD>
 </TR>
-<tr bgcolor="#000000" height=1><td colspan=[scratch cols]></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=[scratch cols]></td></tr>
+<tr class=rborder height=1><td colspan=4></td></tr>
 
 <!-- will default to current if not set:
 		[seti today][tag time]%Y%m[/tag][/seti]
@@ -102,6 +71,7 @@
 
 [query	hashref=main
 	st=db
+	ml=100000
 	table=transactions
 	nu=0,0,0,0
 	sql="
@@ -109,7 +79,8 @@
 		FROM  transactions
 		WHERE deleted != '1' [scratch date_limit] [scratch synd_limit]
 	"][/query]
-
+[tmp ALL][L]ALL[/L][/tmp]
+[tmp TOTAL][L]GRAND TOTAL[/L][/tmp]
 [perl tables="store"]
 	my %sales;
 	$master = {};
@@ -159,7 +130,7 @@
 	foreach $month (sort { $a <=> $b } keys %$master) {
 		my $year = $month;
 		$year =~ s/(\d\d\d\d)(\d\d)(\d\d)/$1/;
-		my $mname = $names{$2};
+		my $mname = errmsg($names{$2});
 		my $day = $3;
 		$day =~ s/^0+//;
 		my $subtotal_sales  = 0;
@@ -175,13 +146,13 @@
 			}
 			$subtotal_sales  += $record->{sales};
 			$subtotal_quantity += $record->{orders};
-			($syn, $camp) = split /\0/, $id, 2;
-			my $synlabel = $syn || '(none)';
+			($syn, $camp) = split /-/, $id, 2;
+			my $synlabel = $syn || errmsg('(none)');
 			my $burl = $Tag->area('__UI_BASE__/reports/order/Detail', $month);
 			my $url = qq{<A HREF="$burl$syndstring">$mname&nbsp;$day,&nbsp;$year</A>}
 				if $mname;
 			$out .= <<EOF;
-	<TR BGCOLOR=__UI_C_INTBLOCK__>
+	<TR class=rnorm>
 	<TD VALIGN=top>
 	$url&nbsp;
 	</FONT>
@@ -217,13 +188,13 @@
 		}
 		$subtotal_sales  = $Tag->currency({}, $subtotal_sales);		
 		$out .= <<EOF;
-	<TR BGCOLOR=__UI_C_INTBLOCK__>
+	<TR class=rnorm>
 	<TD VALIGN=top>
 	&nbsp;
 	</FONT>
 	</TD>
 	<TD VALIGN=top>
-	ALL<BR><HR color=black size=1>
+	$Scratch->{ALL}<BR><HR color=black size=1>
 	</FONT>
 	</TD>
 	<TD ALIGN=center VALIGN=top>
@@ -245,13 +216,13 @@
 				. $Tag->currency({}, $total_commission) . '</TD>';
 		}
 		$out .= <<EOF;
-	<TR BGCOLOR=__UI_C_INTBLOCK__>
+	<TR class=rnorm>
 	<TD VALIGN="top">
-	GRAND TOTAL
+	$Scratch->{TOTAL}
 	</FONT>
 	</TD>
 	<TD VALIGN="top">
-	ALL
+	$Scratch->{ALL}
 	</FONT>
 	</TD>
 	<TD ALIGN=center VALIGN="top">
@@ -264,7 +235,7 @@
 	</TD>
 	$commstr
 	</TR>
-	<tr bgcolor="#000000" height=1><td colspan=$Scratch->{cols}></td></tr>
+	<tr class=rborder height=1><td colspan=4></td></tr>
 EOF
 [/perl]
 </TABLE>



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/reports/order/.access


<<.access: empty>>


2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/reports/order/.autoload


rev 2.0.4.1, prev_rev 2.0
Index: .autoload
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/reports/order/.autoload,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



1.6.4.3   +39 -49    interchange/dist/lib/UI/pages/admin/reports/traffic/ByAffiliate.html


rev 1.6.4.3, prev_rev 1.6.4.2
Index: ByAffiliate.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/reports/traffic/ByAffiliate.html,v
retrieving revision 1.6.4.2
retrieving revision 1.6.4.3
diff -u -r1.6.4.2 -r1.6.4.3
--- ByAffiliate.html	26 Oct 2000 17:44:45 -0000	1.6.4.2
+++ ByAffiliate.html	25 Jan 2003 22:21:19 -0000	1.6.4.3
@@ -11,64 +11,48 @@
 	Traffic statistics
 	[/else]
 [/if][/seti]
-[set icon_name]admin/icon_stats.gif[/set]
+[set icon_name]icon_stats.gif[/set]
 [set help_name]stats.traffic[/set]
 
 @_UI_STD_HEAD_@
 
-<TABLE width="90%" border=0 callpadding=0 cellspacing=0>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<TR BGCOLOR="#__UI_C_TOPBLOCKBAR__">
-<TD VALIGN="top" width="20%">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Date</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Affiliate</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Visits</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Hits</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Pages</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Prod. Views</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Items in cart</B>
-</FONT>
-</TD>
-<TD ALIGN=center VALIGN="top">
-<FONT COLOR="__UI_C_TITLEBARTXT__">
-<B>Orders</B>
-</FONT>
-</TD>
+<TABLE width="90%" border=0 cellpadding=0 cellspacing=0>
+<tr class=rborder height=1><td colspan=8></td></tr>
+<TR class=rmarq>
+	<TD VALIGN=top width="20%">
+		[L]Date[/L]
+	</TD>
+	<TD ALIGN=center VALIGN=top>
+		[L]Affiliate[/L]
+	</TD>
+	<TD ALIGN=center VALIGN=top>
+		[L]Visits[/L]
+	</TD>
+	<TD ALIGN=center VALIGN=top>
+		[L]Hits[/L]
+	</TD>
+	<TD ALIGN=center VALIGN=top>
+		[L]Pages[/L]
+	</TD>
+	<TD ALIGN=center VALIGN=top>
+		[L]Prod. Views[/L]
+	</TD>
+	<TD ALIGN=center VALIGN=top>
+		[L]Items in cart[/L]
+	</TD>
+	<TD ALIGN=center VALIGN=top>
+		[L]Orders[/L]
+	</TD>
 </TR>
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
-<tr bgcolor="#FFFFFF" height=2><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 
 [perl tables=affiliate]
 
 	my $file = $Config->{TrackFile};
-	unless ($file) {
+	unless (-f $file) {
 		return '<tr><td>No traffic statistics found</td></tr>';
 	}
+
 	$Scratch->{$file} = 1;
 
 	%opts = (
@@ -77,6 +61,11 @@
 				fi => $file,
 				ml => 999999,
 	);
+
+	unless($file =~ m{^/}) {
+		$opts{bd} = '.';
+	}
+
 	%names = qw/
 		 01 January
 		 02 February
@@ -198,6 +187,7 @@
 			$visit_by_aff_by_day{$_->[0]}{$_->[5]}++;
 		}
 
+		# Leave this at & instead of UrlJoiner because of Vend::Track
 		my (@items) = split /\&/, $_->[6];
 		foreach $it (@items) {
 			my($tag, $val) = split /=/, $it, 2;
@@ -214,7 +204,7 @@
 		my $date;
 		$date = $day ? "$names{$mon} $day, $yr" : "$names{$mon} $yr";
 		$out = <<EOF;
-<TR BGCOLOR=__UI_C_INTBLOCK__><TD VALIGN="top">
+<TR class=rnorm><TD VALIGN="top">
 $date
 </TD>
 EOF
@@ -267,7 +257,7 @@
   }
   return join "\n\n", @out;
 [/perl]
-<tr bgcolor="#000000" height=1><td colspan=8></td></tr>
+<tr class=rborder height=1><td colspan=8></td></tr>
 
 </TABLE>
 @_UI_STD_FOOTER_@



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/reports/traffic/.access


<<.access: empty>>


2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/reports/traffic/.autoload


rev 2.0.4.1, prev_rev 2.0
Index: .autoload
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/reports/traffic/.autoload,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



1.7.4.1   +4 -4      interchange/dist/lib/UI/pages/admin/special/key_violation.html


rev 1.7.4.1, prev_rev 1.7
Index: key_violation.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/special/key_violation.html,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- key_violation.html	23 Sep 2000 17:55:33 -0000	1.7
+++ key_violation.html	25 Jan 2003 22:21:19 -0000	1.7.4.1
@@ -1,17 +1,17 @@
 [seti page_title]Error: [scratch ui_error][/seti]
 [set help_name]item.error[/set]
-[set icon_name]admin/icon_error.gif[/set]
+[set icon_name]icon_error.gif[/set]
 @_UI_STD_HEAD_@
 
 <!-- ----- BEGIN REAL STUFF ----- -->
 
 <table __UI_T_PROPERTIES__>
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
 <tr>
-<td bgcolor="__UI_C_INTBLOCK__">
+<td class=rnorm>
 &nbsp;
 <p>
 
@@ -36,7 +36,7 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=600 height=1></td>
+<td class=rborder><img src="bg.gif" width=600 height=1></td>
 </tr>
 
 </table>



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/special/.access


<<.access: empty>>


2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/special/.autoload


rev 2.0.4.1, prev_rev 2.0
Index: .autoload
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/special/.autoload,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



1.3.2.1   +1 -1      interchange/dist/lib/UI/pages/admin/survey/index.html


rev 1.3.2.1, prev_rev 1.3
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/survey/index.html,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1
--- index.html	14 Jan 2003 02:25:52 -0000	1.3
+++ index.html	25 Jan 2003 22:21:19 -0000	1.3.2.1
@@ -72,4 +72,4 @@
 <!-- ----- END REAL STUFF ----- -->
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ version: $Id: index.html,v 1.3 2003/01/14 02:25:52 mheins Exp $ -->
+<!-- page: @@MV_PAGE@@ version: $Id: index.html,v 1.3.2.1 2003/01/25 22:21:19 racke Exp $ -->



1.3.2.1   +1 -1      interchange/dist/lib/UI/pages/admin/survey/overall.html


rev 1.3.2.1, prev_rev 1.3
Index: overall.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/survey/overall.html,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1
--- overall.html	14 Jan 2003 02:25:52 -0000	1.3
+++ overall.html	25 Jan 2003 22:21:19 -0000	1.3.2.1
@@ -432,4 +432,4 @@
 </table>
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ version: $Revision: 1.3 $ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 1.3.2.1 $ -->



1.1.2.1   +1 -1      interchange/dist/lib/UI/pages/admin/survey/question.html


rev 1.1.2.1, prev_rev 1.1
Index: question.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/survey/question.html,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- question.html	20 Nov 2002 18:52:17 -0000	1.1
+++ question.html	25 Jan 2003 22:21:19 -0000	1.1.2.1
@@ -117,4 +117,4 @@
 	][/table-editor]
 
 @_UI_STD_FOOTER_@
-<!-- page: @@MV_PAGE@@ version: $Revision: 1.1 $ -->
+<!-- page: @@MV_PAGE@@ version: $Revision: 1.1.2.1 $ -->



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/.access


<<.access: empty>>


2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/.autoload


rev 2.0.4.1, prev_rev 2.0
Index: .autoload
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/.autoload,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/X_dump.html


rev 2.0.4.1, prev_rev 2.0
Index: X_dump.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/X_dump.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/X_test.html


rev 2.0.4.1, prev_rev 2.0
Index: X_test.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/X_test.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/demo_init.html


rev 2.0.4.1, prev_rev 2.0
Index: demo_init.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/demo_init.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/demo_zero.html


rev 2.0.4.1, prev_rev 2.0
Index: demo_zero.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/demo_zero.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/do_launch.html


rev 2.2.2.1, prev_rev 2.2
Index: do_launch.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/do_launch.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.7.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/do_save.html


rev 2.7.2.1, prev_rev 2.7
Index: do_save.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/do_save.html,v
retrieving revision 2.7
retrieving revision 2.7.2.1
diff -u -r2.7 -r2.7.2.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/guess_info.html


rev 2.0.4.1, prev_rev 2.0
Index: guess_info.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/guess_info.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/index.html


rev 2.1.4.1, prev_rev 2.1
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/index.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_about.html


rev 2.1.4.1, prev_rev 2.1
Index: step_about.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_about.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.4.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_company.html


rev 2.4.2.1, prev_rev 2.4
Index: step_company.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_company.html,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_email.html


rev 2.1.4.1, prev_rev 2.1
Index: step_email.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_email.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_groupcontent.html


rev 2.0.4.1, prev_rev 2.0
Index: step_groupcontent.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_groupcontent.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_grouppolicy.html


rev 2.0.4.1, prev_rev 2.0
Index: step_grouppolicy.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_grouppolicy.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_index.html


rev 2.1.4.1, prev_rev 2.1
Index: step_index.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_index.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_launch.html


rev 2.1.4.1, prev_rev 2.1
Index: step_launch.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_launch.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.3.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_pay.html


rev 2.3.2.1, prev_rev 2.3
Index: step_pay.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_pay.html,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.2.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_pay_auth.html


rev 2.2.4.1, prev_rev 2.2
Index: step_pay_auth.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_pay_auth.html,v
retrieving revision 2.2
retrieving revision 2.2.4.1
diff -u -r2.2 -r2.2.4.1



2.4.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_pay_cyber.html


rev 2.4.2.1, prev_rev 2.4
Index: step_pay_cyber.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_pay_cyber.html,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_pay_itransact.html


rev 2.2.2.1, prev_rev 2.2
Index: step_pay_itransact.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_pay_itransact.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_pay_pgp.html


rev 2.1.4.1, prev_rev 2.1
Index: step_pay_pgp.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_pay_pgp.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.2.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_pay_signio.html


rev 2.2.4.1, prev_rev 2.2
Index: step_pay_signio.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_pay_signio.html,v
retrieving revision 2.2
retrieving revision 2.2.4.1
diff -u -r2.2 -r2.2.4.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_pay_skipjack.html


rev 2.2.2.1, prev_rev 2.2
Index: step_pay_skipjack.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_pay_skipjack.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.3.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_preview.html


rev 2.3.2.1, prev_rev 2.3
Index: step_preview.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_preview.html,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_products.html


rev 2.2.2.1, prev_rev 2.2
Index: step_products.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_products.html,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_security.html


rev 2.1.4.1, prev_rev 2.1
Index: step_security.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_security.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_ship.html


rev 2.1.4.1, prev_rev 2.1
Index: step_ship.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_ship.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_ship_country.html


rev 2.1.4.1, prev_rev 2.1
Index: step_ship_country.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_ship_country.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_ship_default.html


rev 2.1.4.1, prev_rev 2.1
Index: step_ship_default.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_ship_default.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_ship_fedex.html


rev 2.1.4.1, prev_rev 2.1
Index: step_ship_fedex.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_ship_fedex.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_ship_ups.html


rev 2.1.4.1, prev_rev 2.1
Index: step_ship_ups.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_ship_ups.html,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_style.html


rev 2.0.4.1, prev_rev 2.0
Index: step_style.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_style.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_style_logo.html


rev 2.0.4.1, prev_rev 2.0
Index: step_style_logo.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_style_logo.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.2.4.1   +0 -0      interchange/dist/lib/UI/pages/admin/wizard/step_tax.html


rev 2.2.4.1, prev_rev 2.2
Index: step_tax.html
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/admin/wizard/step_tax.html,v
retrieving revision 2.2
retrieving revision 2.2.4.1
diff -u -r2.2 -r2.2.4.1



No                   revision



No                   revision



1.3.2.1   +0 -0      interchange/dist/lib/UI/pages/include/component_editor


rev 1.3.2.1, prev_rev 1.3
Index: component_editor
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/component_editor,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



2.3.2.1   +0 -0      interchange/dist/lib/UI/pages/include/item_option_matrix


rev 2.3.2.1, prev_rev 2.3
Index: item_option_matrix
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/item_option_matrix,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/include/item_option_modular


rev 2.2.2.1, prev_rev 2.2
Index: item_option_modular
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/item_option_modular,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.2.2.1   +0 -0      interchange/dist/lib/UI/pages/include/item_option_simple


rev 2.2.2.1, prev_rev 2.2
Index: item_option_simple
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/item_option_simple,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/include/order_delete_archive


rev 1.2.2.1, prev_rev 1.2
Index: order_delete_archive
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/order_delete_archive,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.8.2.1   +0 -0      interchange/dist/lib/UI/pages/include/page_editor


rev 1.8.2.1, prev_rev 1.8
Index: page_editor
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/page_editor,v
retrieving revision 1.8
retrieving revision 1.8.2.1
diff -u -r1.8 -r1.8.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/table_populator


rev 2.1.2.1, prev_rev 2.1
Index: table_populator
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/table_populator,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.5.2.1   +0 -0      interchange/dist/lib/UI/pages/include/template_editor


rev 1.5.2.1, prev_rev 1.5
Index: template_editor
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/template_editor,v
retrieving revision 1.5
retrieving revision 1.5.2.1
diff -u -r1.5 -r1.5.2.1



2.4.2.1   +0 -0      interchange/dist/lib/UI/pages/include/wizard_checklist


rev 2.4.2.1, prev_rev 2.4
Index: wizard_checklist
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/wizard_checklist,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1



2.1.4.1   +0 -0      interchange/dist/lib/UI/pages/include/wizard_profiles


rev 2.1.4.1, prev_rev 2.1
Index: wizard_profiles
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/wizard_profiles,v
retrieving revision 2.1
retrieving revision 2.1.4.1
diff -u -r2.1 -r2.1.4.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Accounting.txt


rev 1.2.2.1, prev_rev 1.2
Index: Accounting.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Accounting.txt,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.6.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Admin.txt


rev 1.6.2.1, prev_rev 1.6
Index: Admin.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Admin.txt,v
retrieving revision 1.6
retrieving revision 1.6.2.1
diff -u -r1.6 -r1.6.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Commerce.txt


rev 1.1.2.1, prev_rev 1.1
Index: Commerce.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Commerce.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Content.txt


rev 1.3.2.1, prev_rev 1.3
Index: Content.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Content.txt,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/ContentEdit.txt


rev 1.1.2.1, prev_rev 1.1
Index: ContentEdit.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/ContentEdit.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Customers.txt


rev 1.3.2.1, prev_rev 1.3
Index: Customers.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Customers.txt,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/DbConfig.txt


rev 1.1.2.1, prev_rev 1.1
Index: DbConfig.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/DbConfig.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Design.txt


rev 1.3.2.1, prev_rev 1.3
Index: Design.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Design.txt,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Fixed.txt


rev 1.1.2.1, prev_rev 1.1
Index: Fixed.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Fixed.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.3.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Items.txt


rev 1.3.2.1, prev_rev 1.3
Index: Items.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Items.txt,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Layout.txt


rev 1.1.2.1, prev_rev 1.1
Index: Layout.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Layout.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Legacy.txt


rev 1.1.2.1, prev_rev 1.1
Index: Legacy.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Legacy.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Merchandising.txt


rev 1.2.2.1, prev_rev 1.2
Index: Merchandising.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Merchandising.txt,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Misc.txt


rev 1.1.2.1, prev_rev 1.1
Index: Misc.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Misc.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/MiscFunction.txt


rev 1.1.2.1, prev_rev 1.1
Index: MiscFunction.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/MiscFunction.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/None.txt


rev 1.1.2.1, prev_rev 1.1
Index: None.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/None.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/OrderView.txt


rev 1.1.2.1, prev_rev 1.1
Index: OrderView.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/OrderView.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Orders.txt


rev 1.2.2.1, prev_rev 1.2
Index: Orders.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Orders.txt,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.6.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Quicklinks.txt


rev 1.6.2.1, prev_rev 1.6
Index: Quicklinks.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Quicklinks.txt,v
retrieving revision 1.6
retrieving revision 1.6.2.1
diff -u -r1.6 -r1.6.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Reports.txt


rev 1.1.2.1, prev_rev 1.1
Index: Reports.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Reports.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Surveys.txt


rev 1.1.2.1, prev_rev 1.1
Index: Surveys.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Surveys.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Tables.txt


rev 1.1.2.1, prev_rev 1.1
Index: Tables.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Tables.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.4.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Top.txt


rev 1.4.2.1, prev_rev 1.4
Index: Top.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Top.txt,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/Wizard.txt


rev 1.1.2.1, prev_rev 1.1
Index: Wizard.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/Wizard.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/menus/uiExport.txt


rev 1.1.2.1, prev_rev 1.1
Index: uiExport.txt
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/menus/uiExport.txt,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.3.2.1   +0 -0      interchange/dist/lib/UI/pages/include/meta/mv_metadata.asc


rev 1.3.2.1, prev_rev 1.3
Index: mv_metadata.asc
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/meta/mv_metadata.asc,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/templates/ui_type1


rev 1.1.2.1, prev_rev 1.1
Index: ui_type1
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/templates/ui_type1,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/templates/ui_type2


rev 1.1.2.1, prev_rev 1.1
Index: ui_type2
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/templates/ui_type2,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/templates/ui_type3


rev 1.1.2.1, prev_rev 1.1
Index: ui_type3
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/templates/ui_type3,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/pages/include/templates/ui_type5


rev 1.1.2.1, prev_rev 1.1
Index: ui_type5
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/pages/include/templates/ui_type5,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.1.4.1   +15 -1     interchange/dist/lib/UI/profiles/login


rev 1.1.4.1, prev_rev 1.1
Index: login
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/login,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- login	28 Jun 2000 07:15:54 -0000	1.1
+++ login	25 Jan 2003 22:21:22 -0000	1.1.4.1
@@ -1,9 +1,10 @@
 __NAME__ MMLogin
 mv_todo=return
 [if type=explicit compare="[userdb function=login profile=ui]"]
-mv_nextpage=__UI_BASE__/index
+mv_nextpage=[either][cgi mv_nextpage][or]__UI_BASE__/index[/either]
 [else]
 mv_username=[perl]$Session->{ui_username} = $Session->{username} = '';[/perl]
+mv_nextpage=[either][cgi mv_failpage][or]__UI_BASE__/login[/either]
 [/else]
 [/if]
 __END__
@@ -14,6 +15,19 @@
 [else]
 mv_username=
 mv_nextpage=[either][cgi mv_failpage][or][cgi mv_nextpage][/either]
+[/else]
+[/if]
+__END__
+
+__NAME__ MMsu
+[if type=explicit
+    compare=|
+		[su username='[cgi user]' admin='[cgi admin]' ]
+		|
+]
+mv_nextpage=[calc]$CGI->{dest} || $Config->{SpecialPage}{catalog}[/calc]
+[else]
+[calc]$Session->{ui_error} = "Failed to su to user $CGI->{user}"; return;[/calc]
 [/else]
 [/if]
 __END__



1.4.4.1   +1 -1      interchange/dist/lib/UI/profiles/order_button_build


rev 1.4.4.1, prev_rev 1.4
Index: order_button_build
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/order_button_build,v
retrieving revision 1.4
retrieving revision 1.4.4.1
diff -u -r1.4 -r1.4.4.1
--- order_button_build	5 Sep 2000 21:10:27 -0000	1.4
+++ order_button_build	25 Jan 2003 22:21:22 -0000	1.4.4.1
@@ -8,7 +8,7 @@
 	delete $Scratch->{test_button};
 	my $result = <<EOF;
 <tr>
-<td colspan=2  bgcolor=__UI_C_INTBLOCK__ VALIGN=TOP>
+<td colspan=2  class=rnorm VALIGN=TOP>
 	<B>Resulting button</B><BR>
 <TEXTAREA ROWS=5 COLS=70 NAME="item_result">
 EOF



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/dist/lib/UI/profiles/Cancel


rev 2.0.4.1, prev_rev 2.0
Index: Cancel
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/Cancel,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/profiles/db_maintenance


rev 2.1.2.1, prev_rev 2.1
Index: db_maintenance
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/db_maintenance,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.1.2.1   +0 -0      interchange/dist/lib/UI/profiles/file_maintenance


rev 2.1.2.1, prev_rev 2.1
Index: file_maintenance
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/file_maintenance,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



1.1.2.1   +0 -0      interchange/dist/lib/UI/profiles/miscellaneous


rev 1.1.2.1, prev_rev 1.1
Index: miscellaneous
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/miscellaneous,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.3.2.1   +1 -1      interchange/dist/lib/UI/profiles/process_filter


rev 2.3.2.1, prev_rev 2.3
Index: process_filter
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/process_filter,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1
--- process_filter	14 Jan 2003 02:25:53 -0000	2.3
+++ process_filter	25 Jan 2003 22:21:22 -0000	2.3.2.1
@@ -1,7 +1,7 @@
 __NAME__ process_filter
 [flag type=write table="[cgi mv_data_table]"]
 [perl tables="[list-databases]"]
-# $Id: process_filter,v 2.3 2003/01/14 02:25:53 mheins Exp $
+# $Id: process_filter,v 2.3.2.1 2003/01/25 22:21:22 racke Exp $
 	my @filters = grep /^ui_filter:/, keys %$CGI;
   FILTERS: {
 	last FILTERS unless @filters;



1.1.2.1   +0 -0      interchange/dist/lib/UI/profiles/recompute_transaction


rev 1.1.2.1, prev_rev 1.1
Index: recompute_transaction
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/profiles/recompute_transaction,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.4.4.3   +70 -12    interchange/dist/lib/UI/vars/UI_STD_FILE_NAV


rev 1.4.4.3, prev_rev 1.4.4.2
Index: UI_STD_FILE_NAV
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/vars/UI_STD_FILE_NAV,v
retrieving revision 1.4.4.2
retrieving revision 1.4.4.3
diff -u -r1.4.4.2 -r1.4.4.3
--- UI_STD_FILE_NAV	25 Oct 2000 12:20:33 -0000	1.4.4.2
+++ UI_STD_FILE_NAV	25 Jan 2003 22:21:23 -0000	1.4.4.3
@@ -1,24 +1,65 @@
 Variable UI_STD_FILE_NAV <<EONav
-<center>
-<table cellpadding=3 cellspacing=0 width=__UI_MAIN_WIDTH__>
+<table cellpadding=3 cellspacing=0 width="85%">
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1 alt=x></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1 alt=x></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 	<table WIDTH=100%>
 		<tr>
 			<td WIDTH=__UI_LEFT_WIDTH__>
 				<SMALL>
-				<IMG SRC="@_UI_IMG_@admin/index.gif" HEIGHT=11 WIDTH=10> view<BR>
-				<IMG SRC="@_UI_IMG_@admin/down.gif" HEIGHT=11 WIDTH=10> download<BR>
-				<IMG SRC="@_UI_IMG_@admin/up.gif" HEIGHT=11 WIDTH=10> upload [if session arg]<a href="[area href="__UI_BASE__/upload_file" arg="[data session arg]/" form="ui_return_to=[var MV_PAGE 1]"]">new file to [data session arg]</a>[else](select directory to upload new file)[/else][/if]<BR>
-				<IMG SRC="@_UI_IMG_@admin/layout.gif" HEIGHT=11 WIDTH=10> edit (if applicable)
+				<IMG SRC="index.gif" HEIGHT=11 WIDTH=10> [msg]view[/msg]<BR>
+				<IMG SRC="down.gif" HEIGHT=11 WIDTH=10> [msg]download[/msg]<BR>
+				[if-mm advanced delete_files]
+				<IMG SRC="delete.gif" HEIGHT=10 WIDTH=10> [msg]DELETE[/msg]<BR>
+				[/if-mm]
+				<IMG SRC="up.gif" HEIGHT=11 WIDTH=10> [msg]upload[/msg]<BR>
+				<IMG SRC="layout.gif" HEIGHT=11 WIDTH=10> [msg]edit (if applicable)[/msg]
 				</SMALL>
 			</td>
 			<td>
+			<FORM ACTION="[area @_MV_PAGE_@]" METHOD=GET>
+			<INPUT TYPE=hidden NAME=mv_action VALUE=back>
+			<INPUT TYPE=hidden NAME=action VALUE=find>
+			[msg]Find files in and under current directory:[/msg]<BR>
+			<INPUT NAME=find VALUE="[calc]
+										return unless $CGI->{find};
+										my $str = $CGI->{find};
+										$str =~ s/"/&quot;/g;
+										return $str;
+									[/calc]">
+			<SELECT NAME="find_action">
+			<OPTION>[msg]In contents[/msg]
+			<OPTION VALUE="filename" [selected
+										cgi=1
+										name=find_action
+										value=filename]>[msg]By file name[/msg]
+			</SELECT>
+			<INPUT TYPE=submit VALUE="[msg]Find files[/msg]"><BR>
+			<small>
+			<INPUT TYPE=checkbox NAME="find_session" VALUE=1 [checked cgi=1 name=find_session value=1]> [msg]Look in session and temporary files[/msg]
+			&nbsp;&nbsp;&nbsp;
+			[if type=explicit
+				compare=`
+					my $status;
+					if(defined $CGI->{details}) {
+						$status = $CGI->{details};
+					}
+					else {
+						$status = $Session->{ui_file_details};
+					}
+					$Scratch->{details_coming} = $status;
+			`]
+			[page href="@_MV_PAGE_@" form="details=0"][msg]Hide file details[/msg]</A>
+			[else]
+			[page href="@_MV_PAGE_@" form="details=1"][msg]Show file details[/msg]</A>
+			[/else]
+			[/if]
+			</small>
+			</FORM>
 			</td>
 		</tr>
 	</table>
@@ -26,27 +67,44 @@
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1 alt=x></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1 alt=x></td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_INTBLOCK__>
+<td class=rnorm>
 
+[if scratch details_coming]
 	[file-navigator
 		mask="[scratch dir_mask]"
 		include_mask="[scratch include_mask]"
 		exclude_mask="[scratch exclude_mask]"
 		view_link="[scratch view_link]"
 		start_open="[scratch start_open]"
+		initial_dir="[cgi initial_dir]"
 	]
+[else]
+<table width="100%">
+[table-organize columns=3 columnize=1 min-rows=15 interpolate=1]
+	[file-navigator
+		mask="[scratch dir_mask]"
+		include_mask="[scratch include_mask]"
+		exclude_mask="[scratch exclude_mask]"
+		template=|<TD width="33%">%s</TD>|
+		view_link="[scratch view_link]"
+		start_open="[scratch start_open]"
+		initial_dir="[cgi initial_dir]"
+	]
+[/table-organize]
+</table>
+[/else]
+[/if]
 
 </td>
 </tr>
 
 <tr>
-<td bgcolor=__UI_C_TOPBLOCKBAR__><img src="@_UI_IMG_@admin/bg.gif" width=__UI_MAIN_WIDTH__ height=1 alt=x></td>
+<td class=rborder><img src="bg.gif" width=__UI_MAIN_WIDTH__ height=1 alt=x></td>
 </tr>
 
 </table>
-</center>
 EONav



1.11.4.4  +17 -45    interchange/dist/lib/UI/vars/UI_STD_FOOTER


rev 1.11.4.4, prev_rev 1.11.4.3
Index: UI_STD_FOOTER
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/vars/UI_STD_FOOTER,v
retrieving revision 1.11.4.3
retrieving revision 1.11.4.4
diff -u -r1.11.4.3 -r1.11.4.4
--- UI_STD_FOOTER	20 Oct 2000 10:18:30 -0000	1.11.4.3
+++ UI_STD_FOOTER	25 Jan 2003 22:21:23 -0000	1.11.4.4
@@ -1,47 +1,19 @@
 Variable UI_STD_FOOTER  <<EOV
-[if !scratch ui_no_title]
-				</td>
-		</tr>
-</table>
-[/if]
-<center>
-<table cellpadding="0" cellspacing="0" border="0" width="100%">
-        <tr>
-                <td colspan="2">
-                        <br>
-                                <hr noshade size="2" width="100%">
-                </td>
-        </tr>
-        <tr>
-			<td valign=top>
-					&nbsp;&nbsp;&nbsp;&nbsp; <a href="http://developer.akopia.com/"><font face="Verdana,Arial,Helvetica,sans-serif" size="1"><b>Akopia Interchange&#8482;</b></font></a><font face="Verdana,Arial,Helvetica,sans-serif" size="1"><b> - &copy;2000 Akopia, Inc. &nbsp;&nbsp;&nbsp;&nbsp;Username: [data session username]
-					 &nbsp;&nbsp;&nbsp;&nbsp; StoreID: <A HREF="[area index]">[calc]$Config->{CatalogName}[/calc] </b></a>&nbsp;&nbsp;&nbsp;[tag time]%d %B, %Y %H:%M:%S[/tag]</font>
-			</td>
-			<td valign=top align="right">
-[tmp window_name][tag time]%m%d%H%M%S[/tag][/tmp]
-			<table>
-			<tr>
-				<td>
-<font face="Verdana,Arial,Helvetica,sans-serif" size="1">
-[if session logged_in]
-	<a href="[area __UI_BASE__/gentable]">Tables</A><br>
-
-	<a href="javascript:window.name = 'mainwindow[scratch window_name]';window.open('[area href=|admin/quicklinks| arg=|[scratch window_name]|]','Quicklinks[scratch window_name]','top=0,left=0,scrollbars,location=no,status=no,toolbar=no,resizable,fullsize=no,width=170,height=700'); void 0">Quicklinks</A><br>
-[/if]
-			[if-mm advanced reconfig]
-			<A href="[area __UI_BASE__/reconfig]">Apply changes</A><br>
-			[/if-mm]
-			<A href="[area __UI_BASE__/login]">Log out</A>
-				</td>
-				<td>
-			<a href="[area admin/index]"><img height="46" width="90" border="0" src="@_UI_IMG_@__UI_BOTTOMIMG__" align=top></a><br>
-				</td>
-			</tr>
-			</table>
-        </tr>
-</table>
-</center> 
-</body>
-</html>
-
+[unpack]
+[include file="include/templates/ui_[either][scratch display_class][or]type1[/either]"]
+[/unpack]
+[comment] Clear these puppies [/comment][calc]
+	for (qw/
+				page_title
+				page_banner
+				icon_name
+				help_name
+				page_perm
+				table_perm
+				ui_body_extra
+				display_class
+		/) { delete $Scratch->{$_} }
+	return;
+[/calc]
+	
 EOV



1.25.4.5  +293 -229  interchange/dist/lib/UI/vars/UI_STD_HEAD


rev 1.25.4.5, prev_rev 1.25.4.4
Index: UI_STD_HEAD
===================================================================
RCS file: /var/cvs/interchange/dist/lib/UI/vars/UI_STD_HEAD,v
retrieving revision 1.25.4.4
retrieving revision 1.25.4.5
diff -u -r1.25.4.4 -r1.25.4.5
--- UI_STD_HEAD	13 May 2001 08:17:07 -0000	1.25.4.4
+++ UI_STD_HEAD	25 Jan 2003 22:21:23 -0000	1.25.4.5
@@ -1,26 +1,83 @@
+## UI Header vars, version: $Id: UI_STD_HEAD,v 1.25.4.5 2003/01/25 22:21:23 racke Exp $
+Variable UI_STD_INIT <<EOV
+[calcn]
+	# is this browser able to grok DHTML ?
+	# (Called separately to prevent bad user value in MV_DHTML_BROWSER
+	# from crashing init...)
+	my $regex = q{__MV_DHTML_BROWSER__}
+				|| 'MSIE.*5.5|MSIE.*6|Mozilla\W*5|Mozilla.*Gecko';
+	$Scratch->{ui_old_browser} = $Session->{browser} !~ /$regex/;
+	return;
+[/calcn][calcn]
+	# call only once per page
+	return if $Config->{ImageDirOriginal};
+
+	# determine catalog URL before mangling config URLs
+	$Scratch->{ui_catalog_url} = $Tag->area('index');
+
+	# replace ImageDir variables with UI equivalents to take advantage
+	# of Interchange's automatic image path rewriting
+	$Config->{ImageDirOriginal} = $Config->{ImageDir};
+	$Config->{ImageDirSecureOriginal} = $Config->{ImageDirSecure};
+	$Variable->{UI_IMG} = $Config->{ImageDir} =
+		$Tag->image( { ui => 1, secure => 0, dir_only => 1 } );
+	$Config->{ImageDirSecure} =
+		$Tag->image( { ui => 1, secure => 1, dir_only => 1 } );
+
+	# force using secure URL for this page?
+	$Config->{VendURLOriginal} = $Config->{VendURL};
+	if ($Variable->{UI_SECURE} or $Tag->var('UI_SECURE', 1)) {
+		$Variable->{UI_IMG} = $Config->{ImageDirSecure};
+		$Config->{VendURL} = $Config->{SecureURL};
+	}
+
+	''
+[/calcn][page-meta]
+EOV
+
 Variable UI_STD_HEAD <<EOV
-[strip interpolate=1]
+[tag pragma strip_white][/tag]
+[tag pragma no_image_rewrite 0][/tag]
+@_UI_STD_INIT_@
 [if-mm !logged_in]
+	[set ui_checklist][/set]
+	[set icon_name][/set]
+	[set page_perm][/set]
+	[set table_perm][/set]
 	[if !scratch no_login_required]
-		[bounce page="__UI_BASE__/login"]
+		[bounce href=|
+			[area href="__UI_BASE__/login" form="destination=[var MV_PAGE 1]"]
+		|]
 	[/if]
 [/if-mm]
 [calc]
+	$Tag->tmpn('ui_meta_link');
+	$Scratch->{ui_meta_link} = defined $Values->{ui_meta_force}
+							 ?  $Values->{ui_meta_force}
+							 :  $Variable->{UI_META_LINK};
+
 	delete $Scratch->{no_login_required};
 	@parms = grep /^ui_class_/, keys %$Scratch;
 	my $last;
 	for(@parms) {
 		delete $Scratch->{$_};
 		$last = $_;
-		$last =~ s/ui_class_//;
 	} 
-	$ui_tag = delete $Scratch->{ui_class} || $last;
+	$last =~ s/ui_class_//;
+	if($CGI->{display_class}) {
+		$Scratch->{display_class} = $CGI->{display_class};
+	}
+	if($Scratch->{check_publish} and $Scratch->{check_publish} =~ /^[1yt].?.?$/) {
+		$Scratch->{check_publish} = q{ onClick="return check_publish()" };
+	}
+	$ui_tag = (delete $Scratch->{ui_class} || $CGI->{ui_class} || $last || 'None');
+	$Scratch->{ui_class} = $ui_tag;
 	$Scratch->{"ui_class_$ui_tag"} = 1;
-	return $out;
+	return;
 [/calc]
 [if scratch table_perm]
 	[calc]
-		my $table = $CGI->{mv_data_table} || $Value->{mv_data_table};
+		my $table = $CGI->{mv_data_table} || $Values->{mv_data_table};
 		if($Scratch->{table_perm} =~ /^\s*=(\w+)/) {
 			$Scratch->{table_perm} = "$CGI->{mv_data_table}=$1";
 		}
@@ -33,240 +90,247 @@
 		return;
 	[/calc]
 	[if-mm function="!tables" table="[scratch table_perm]"]
-	[seti ui_error]Sorry, no permission [scratch table_perm] for table [cgi mv_data_table] in [var MV_PAGE 1].[/seti]
+	[seti ui_error][msg arg.0="[scratch table_perm]" arg.1="[cgi mv_data_table]" arg.2="[var MV_PAGE 1]"]Sorry, no permission '%s' for table '%s' in '%s'.[/msg][/seti]
 	[set table_perm][/set]
 	[bounce page="__UI_BASE__/error"]
 	[/if-mm]
 [/if]
 [if scratch page_perm]
 	[if-mm function="!advanced" name="[scratch page_perm]"]
-	[seti ui_error]Sorry, no permission for page [scratch page_perm][/seti]
+	[seti ui_error][msg arg.0="[scratch page_perm]"]Sorry, no permission for page '%s'.[/msg][/seti]
 	[set page_perm][/set]
 	[bounce page="__UI_BASE__/error"]
 	[/if-mm]
 [/if]
-[/strip]<html>
-<head>
-<title>[scratch page_title]</title>
-<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
-<script language="JavaScript">
-<!--
-function MM_swapImgRestore() { //v3.0
-  var i,x,a=document.MM_sr; for(i=0;a&&i<a.length&&(x=a[i])&&x.oSrc;i++) x.src=x.oSrc;
-}
-
-function addItem(selector, receptor, joiner) {
-	if(joiner == null) {
-		joiner = " ";
-	}
-	else {
-		joiner = "\n";
-	}
-    if(receptor.value != '') {
-        receptor.value = receptor.value + joiner;
-    }
-    if(selector[selector.selectedIndex].value != null) {
-        receptor.value = receptor.value + selector[selector.selectedIndex].value;
-    }
-    else {
-        if(selector[selector.selectedIndex].text != null) {
-        receptor.value = receptor.value + selector[selector.selectedIndex].text;
-        }
-    }
-    return true;
-}
-
-function open_help(url) {
-  opts="top=0,left=0,scrollbars,status=no,menubar=no,location=yes,toolbar=no,resizable=yes,fullsize=no,width=__UI_HELP_WIDTH__,height=__UI_HELP_HEIGHT__";
-  window.open(url, 'Help', opts);
-}
-
-function MM_preloadImages() { //v3.0
-  var d=document; if(d.images){ if(!d.MM_p) d.MM_p=new Array();
-    var i,j=d.MM_p.length,a=MM_preloadImages.arguments; for(i=0; i<a.length; i++)
-    if (a[i].indexOf("#")!=0){ d.MM_p[j]=new Image; d.MM_p[j++].src=a[i];}}
-}
-
-function MM_findObj(n, d) { //v3.0
-  var p,i,x;  if(!d) d=document; if((p=n.indexOf("?"))>0&&parent.frames.length) {
-    d=parent.frames[n.substring(p+1)].document; n=n.substring(0,p);}
-  if(!(x=d[n])&&d.all) x=d.all[n]; for (i=0;!x&&i<d.forms.length;i++) x=d.forms[i][n];
-  for(i=0;!x&&d.layers&&i<d.layers.length;i++) x=MM_findObj(n,d.layers[i].document); return x;
-}
-
-function MM_swapImage() { //v3.0
-  var i,j=0,x,a=MM_swapImage.arguments; document.MM_sr=new Array; for(i=0;i<(a.length-2);i+=3)
-   if ((x=MM_findObj(a[i]))!=null){document.MM_sr[j++]=x; if(!x.oSrc) x.oSrc=x.src; x.src=a[i+2];}
-}
-//-->
-</script>
-<STYLE TYPE="text/css">
-<!--
-body { font-family: Verdana, Arial, Helvetica, sans-serif }
-.margin { margin-top: 0px; margin-left: 0px}
-a:link { text-decoration: none; font-weight: normal; color: __UI_C_LINK__ }
-a:hover { text-decoration: underline; font-weight: normal; color: __UI_C_LINK__ }
-a:active { text-decoration: none; font-weight: normal; color: __UI_C_ALINK__ }
-a:visited { text-decoration: none; font-weight: normal; color: __UI_C_VLINK__ }
--->
-</STYLE>
-[scratch meta_header][set meta_header][/set]
-</head>
-
-<body [scratch ui_body_extra] bgcolor="__UI_C_BG__"  onLoad="MM_preloadImages('@_UI_IMG_@navigation/B3_b.gif','@_UI_IMG_@navigation/B4_b.gif','@_UI_IMG_@navigation/B5_b.gif','@_UI_IMG_@navigation/B6_b.gif','@_UI_IMG_@navigation/B7_b.gif','@_UI_IMG_@navigation/B2_b.gif','@_UI_IMG_@navigation/B8_b.gif','@_UI_IMG_@navigation/B9_b.gif','@_UI_IMG_@navigation/A1_b.gif','@_UI_IMG_@navigation/A2_b.gif','@_UI_IMG_@navigation/A3_b.gif')" td align="0" valign="0" leftmargin=" 0" topmargin=" 0" marginwidth=" 0" marginheight=" 0">
-<!-- ----- BEGIN TITLEBAR ----- -->
-<table width="100%" border="0" cellspacing="0" cellpadding="0">
-  <tr>
-    <td><A HREF="http://www.akopia.com"><img src="@_UI_IMG_@navigation/akopia_logo.gif" width="69" height="53" border=0 alt="Akopia logo"></A></td><td align="right" valign="bottom" nowrap><a href="[if session logged_in]@_UI_ABOUT_NORMAL_URL_@[else]@_UI_ABOUT_LOGIN_URL_@[/else][/if]" onMouseOut="MM_swapImgRestore()" onMouseOver="MM_swapImage('About','','@_UI_IMG_@navigation/A1_b.gif',1)"><img name="About" border="0" src="@_UI_IMG_@navigation/A1.gif" width="102" height="38" alt=About></a><a href="[area __UI_BASE__/index]" onMouseOut="MM_swapImgRestore()" onMouseOver="MM_swapImage('Index','','@_UI_IMG_@navigation/A2_b.gif',1)"><img name="Index" border="0" src="@_UI_IMG_@navigation/A2.gif" width="294" height="38" alt=Menu></a><a href="javascript:open_help('__UI_HELP_BASE_URL__/[scratch help_name].html')" onMouseOut="MM_swapImgRestore()" onMouseOver="MM_swapImage('Help','','@_UI_IMG_@navigation/A3_b.gif',1)"><img name="Help" border="0" src="@_UI_IMG_@navigation/A3.gif" width="125" height="38" alt=Help></a></td>
-  </tr></table>
-
-[tmp ui_menu_content]code	img_dn	img_up	img_sel	page	url	alt	name
-[if-mm advanced order]2	B2.gif	B2_b.gif	B2_b.gif	__UI_BASE__/order		Order administration	Orders
-[/if-mm][if-mm advanced userdb]3	B3.gif	B3_b.gif	B3_b.gif	__UI_BASE__/customer		Customer administration	Customers
-[/if-mm][if-mm advanced item]4	B4.gif	B4_b.gif	B4_b.gif	__UI_BASE__/item		Item management	Items
-[/if-mm][if-mm advanced page]5	B5.gif	B5_b.gif	B5_b.gif	__UI_BASE__/page		Content edit	Content
-[/if-mm][if-mm advanced layout]6	B6.gif	B6_b.gif	B6_b.gif	__UI_BASE__/layout		Site design	Design
-[/if-mm][if-mm advanced item]7	B7.gif	B7_b.gif	B7_b.gif	__UI_BASE__/merchandising		merchandising	Merchandising
-[/if-mm][if-mm advanced stats]8	B8.gif	B8_b.gif	B8_b.gif	__UI_BASE__/orderstats		Statistics and reports	Reports
-[/if-mm][if-mm advanced admin]9	B9.gif	B9_b.gif	B9_b.gif	__UI_BASE__/genconfig		System administration	Admin
-[/if-mm][/tmp]
-<table width="100%" border="0" cellspacing="0" cellpadding="0">
-  <tr bgcolor="#000000"> 
-    <td><img src="@_UI_IMG_@navigation/spacer1.gif" width="1" height="1" alt=line></td>
-  </tr>
-  <tr bgcolor="#FFFFFF"> 
-    <td><img src="@_UI_IMG_@navigation/spacer2.gif" width="1" height="1" alt=line></td>
-  </tr>
-  <tr bgcolor="#99CCFF"> 
-    <td nowrap> 
-      <div align="left"><img src="@_UI_IMG_@navigation/B1.gif" width="9" height="19" alt=line>[loop
-	  prefix=am
-	  head_skip=1
-	  list="[scratch ui_menu_content]"
-	  lr=1]<!-- class=[am-param name]=[scratch ui_class_[am-param name]] --><a href="[area [am-param page]]" onMouseOut="MM_swapImgRestore()" onMouseOver="MM_swapImage('[am-param name]','','@_UI_IMG_@navigation/[am-param img_up]',1)"><img name="[am-param name]" alt="[am-param alt]" border="0" src="@_UI_IMG_@navigation/[if scratch ui_class_[am-param name]][am-param img_up][else][am-param img_dn][/else][/if]"></a>[/loop]<img src="@_UI_IMG_@navigation/B10.gif" width="17" height="19" alt=line></div>
-    </td>
-  </tr>
-</table>
-
-[loop
-	lr=1
-	head_skip=1
-	prefix=sm
-	list=`$Variable->{"UI_SUBMENU_$ui_tag"};`
-][sm-calc]
-	my $pre  = '';
-	my $post = '';
-	my $indicator = q{[sm-param indicator]};
-	my $exclude = q{[sm-param exclude_on]};
-#Log("indicator=$indicator");
-	my $depend = q{[sm-param depends_on]};
-	return '' if $exclude and $CGI->{$exclude};
-	return '' if $depend and ! $CGI->{$depend};
-	my $name = q{[sm-param name]};
-	my $next = q{[sm-param next_line]};
-	if($name =~ s/^((&nbsp;)+)//i) {
-		$pre = $1;
-	}
-	if($name =~ s/((&nbsp;)+)$//i) {
-		$post = $1;
-	}
-	$name =~ s/ /&nbsp;/g;
-	my $page = q{[sm-param page]};
-	my $form = q{[sm-param form]};
-#Log("Form is: $form");
-	$form =~ tr/&/\n/;
-#Log("Form is: $form");
-	my $out = '';
-	$out .= <<'EOF' if ! $sm_once++;
-<table width="100%" border="0" cellspacing="0" cellpadding="0">
-  <tr> 
-    <td bgcolor="__UI_C_TOPBLOCKBAR__"><img src="@_UI_IMG_@navigation/spacer3.gif" width=1 height=1 alt=line></td>
-  </tr>
-  <tr bgcolor="A1C6FF"> 
-    <td><img src="@_UI_IMG_@navigation/spacer4.gif" width=1 height=1 alt=line></td>
-  </tr>
-  <tr bgcolor="__UI_C_TITLEBARBG__"> 
-    <td valign=center nowrap><font face="Verdana, Arial, Helvetica, sans-serif" size="-1"><img src="@_UI_IMG_@admin/bg.gif" height=19 width=3 align=middle alt=x>&nbsp;&nbsp;&nbsp;&nbsp;
-EOF
-	$out .= $pre;
-	$out .= q{</td></tr><tr bgcolor="__UI_C_INTBLOCKBAR__"><td nowrap valign=center><img src="@_UI_IMG_@admin/bg.gif" height=19 width=3 align=middle alt=x>&nbsp;&nbsp;&nbsp;&nbsp;
-}
-		if $next;
-	$out .= qq{<A HREF="} if $page;
-	$out .= $Tag->area( { href => $page, form => $form } )
-		if $page;
-	$out .= qq{">} if $page;
-	my $fc = q{__UI_C_TITLEBARCONT__};
-	my $rev = $indicator =~ s/^!//;
-
-#Log("indicator=$indicator rev=$rev CGI=$CGI->{$indicator} VALUES=$Values->{$indicator}");
-
-	if($indicator) {
-		if($rev) {
-			$fc = q{__UI_C_TITLEBARTXT__}
-				if ! ($CGI->{$indicator} || $Values->{$indicator});
-		}
-		else {
-			$fc = q{__UI_C_TITLEBARTXT__}
-				if ($CGI->{$indicator} || $Values->{$indicator});
-		}
-	}
-	elsif($Tag->var('MV_PAGE', 1) eq $page) {
-#Log("page presence select");
-		$fc = q{__UI_C_TITLEBARTXT__};
-	}
 
-	$out .= qq{<FONT face="Verdana, Arial, Helvetica, sans-serif" COLOR="$fc" SIZE="-1">$name</FONT>};
-	$out .= '</A>' if $page;
-	$out .= $post;
-[/sm-calc]&nbsp;&nbsp;&nbsp; [/loop]
-	[calc]
-	return unless $sm_once;
-	return q!<tr bgcolor="#000000"><td><IMG SRC="@_UI_IMG_@admin/bg.gif" WIDTH="1" HEIGHT="1" alt=x></td></tr>
-                 </td></tr></table>!;
-	[/calc]
-<!-- ----- END MENUBAR ----- -->
-[if !scratch ui_no_title]
-<table width="100%">
-<TR>
-<TD WIDTH="20">&nbsp;</td><TD>
-          <br>
-		[if scratch icon_name]<img src="@_UI_IMG_@[scratch icon_name]" width=16 height=16 border=0 valign=top alt=icon> &nbsp; [/if]
-	   <font size="+1" face="Verdana,arial,helvetica,sans-serif" color="__UI_C_HEADERTXT__">[either][scratch page_banner][or][scratch page_title][/either]&nbsp;</font><p>
-    [if type=explicit compare="[error all=1 show_var=1 keep=1]"]
-	<P>
-	<B>Error:</B>
-	<BLOCKQUOTE class=cerror>
-		[error all=1 show_error=1 joiner="<br>"]
-	</BLOCKQUOTE>
-	</P>
-	[/if]
-	[if scratch ui_failure]
-	<P>
-	<BLOCKQUOTE>
-	<FONT COLOR="__CONTRAST__">[scratchd ui_failure]</FONT>
-	</BLOCKQUOTE>
-	</P>
-	[/if]
-	[if scratch ui_message]
-	<P>
-	<BLOCKQUOTE>
-	<FONT COLOR="__UI_C_SUCCESS__">[scratchd ui_message]</FONT>
-	</BLOCKQUOTE>
-	</P>
+[if scratch superuser]
+	[if-mm !super]
+	[seti ui_error][msg arg.0="[var MV_PAGE 1]"]Sorry, must be superuser for page '%s'.[/msg][/seti]
+	[bounce page="__UI_BASE__/error"]
+	[/if-mm]
+[/if]
+[if scratch dhtml_required]
+[and scratch ui_old_browser]
+	[seti ui_error][loc]Modern browser like Mozilla or MSIE 5 required for page accessed[/loc][/seti]
+	[bounce page="__UI_BASE__/error"]
+[/if]
+
+[output name=fixed_menu]
+[if session logged_in]
+[menu
+	name=Fixed
+	ui_security=depends_on
+	extra_value.check_publish=`$Scratch->{check_publish}`
+	superuser=super
+	full_interpolate=page
+	localize="name,description"
+	]
+	<td nowrap>&nbsp;<a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=toplink>{NAME}</a>&nbsp;</td>
+[menu-footer]
+[if-mm super]
+	[if scratch ui_meta_link]
+			<td nowrap>
+				&nbsp;&nbsp;<a
+					href="[area href='admin/menu_editor' form='qmenu_name=Fixed']"
+					style="font-size: 7pt" class=edittablink {CHECK_PUBLISH} title="[msg]Edit this menu[/msg]">edit</A>
+			&nbsp;&nbsp;</td>
 	[/if]
+[/if-mm]
+[/menu-footer]
+[/menu]
 [/if]
-[comment] Clear these puppies [/comment]
-[calc]
-	for (qw/
-				page_title
-				page_banner
-				icon_name
-				help_name
-				page_perm
-				table_perm
-				ui_body_extra
-		/) { delete $Scratch->{$_} }
-	return;
-[/calc]
+
+[output name=top_tabs]
+[menu
+	  name="[either][scratch top_menu][or]Top[/either]"
+	  superuser=super
+	  inactive=inactive
+	  localize=name
+	  indicator=indicator
+	  ui_security=depends_on
+	  extra_value.check_publish=`$Scratch->{check_publish}`
+	  link_class=menufont
+	  entities=description
+	  ]
+{INDICATED:}
+	<!-- class={NAME} down -->
+               <td height=15 class=tabdown>
+                  <table width="100%" border=0 cellspacing=0 cellpadding=0>
+                     <tr>
+                        <td class=tabdownleft><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=tablink><img src="bg.gif" width=24 height=15 border=0></A></td>
+                        <td nowrap class=tabdownfill><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=tablink>{NAME}</a></td>
+                        <td class=tabdownright><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=tablink><img src="bg.gif" width=24 height=15 border=0></A></td>
+                     </tr>
+                            <tr><td colspan=3 class=darkshade><img src="bg.gif" height=1></td></tr>
+                            <tr><td colspan=3 class=lightshade><img src="bg.gif" height=1></td></tr>
+                  </table>
+               </td>
+{/INDICATED:}
+{INDICATED?}
+<!-- tab: {NAME} (up) -->
+               <td class=block1>
+                  <table width="100%" border=0 cellspacing=0 cellpadding=0>
+                     <tr>
+                        <td class=tableft><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=tablink><img src="bg.gif" width=24 height=15 border=0></A></td>
+                        <td nowrap class=tabfill><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=tablink>{NAME}</a></td>
+                        <td class=tabright><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=tablink><img src="bg.gif" width=24 height=15 border=0></A></td>
+                     </tr>
+                  </table>
+               </td>
+{/INDICATED?}
+[/menu]
+	<!-- menu edit=Top -->
+	[if-mm super][if scratch ui_meta_link]
+               <td height=15 class=tabdown>
+                  <table width="100%" border=0 cellspacing=0 cellpadding=0>
+                     <tr>
+                        <td class=tabdownleft><a href="[area href='admin/menu_editor' form='qmenu_name=Top']" {CHECK_PUBLISH} title="[msg]Edit these menu tabs[/msg]"><img src="bg.gif" width=24 height=15 border=0></td>
+                        <td nowrap class=tabdownfill><a href="[area href='admin/menu_editor' form='qmenu_name=[either][scratch top_menu][or]Top[/either]']" {CHECK_PUBLISH} title="[msg]Edit these menu tabs[/msg]" class=edittablink>edit</A></td>
+                        <td class=tabdownright><a href="[area href='admin/menu_editor' form='qmenu_name=Top']" {CHECK_PUBLISH} title="[msg]Edit these menu tabs[/msg]"><img src="bg.gif" width=24 height=15 border=0></td>
+                     </tr>
+							<tr><td colspan=3 class=darkshade><img src="bg.gif" height=1></td></tr>
+							<tr><td colspan=3 class=lightshade><img src="bg.gif" height=1></td></tr>
+                  </table>
+               </td>
+[/if][/if-mm]
+
+[output name=second_tabs]
+[menu
+	name="[either][scratch second_menu][or][scratch ui_class][/either]"
+	superuser=super
+	exclude_on=exclude_on
+	depends_on=depends_on
+	expand_values=name,page
+	expand_values_form=form
+	extra_value.check_publish=`$Scratch->{check_publish}`
+	localize=name
+	indicator=indicator
+	last_line="[if scratch third_menu]next_line[/if]"
+	indicator_page=page
+	inactive=inactive
+	entities=description
+	nbsp=name
+	reparse=1
+]
+<!-- PAGE=[var MV_PAGE 1] -->
+{NEXT_LINE?}[output name=third_tabs]{/NEXT_LINE?}
+{INDICATED?}
+<td class=block3> 
+   <table width="100%" border=0 cellspacing=0 cellpadding=0>
+	  <tr> 
+		 <td class=subtableft><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+		 <td nowrap class=subtabfill><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=subtablink>{NAME}</a></td>
+		 <td class=subtabright><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=subtabfilllwr><img src="bg.gif" height=1></td>
+	  </tr>
+   </table>
+</td>
+{/INDICATED?}
+{INDICATED:}
+<td class=subtabdown> 
+   <table width="100%" border=0 cellspacing=0 cellpadding=0>
+	  <tr> 
+		 <td class=subtabdownleft><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+		 <td nowrap class=subtabdownfill><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=subtablink>{NAME}</a></td>
+		 <td class=subtabdownright><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=darkshade><img src="bg.gif" height=1></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=lightshade><img src="bg.gif" height=1></td>
+   </table>
+</td>
+{/INDICATED:}
+[/menu]
+[output name=second_tabs]
+<!-- menu edit=Second -->
+[if-mm super][if scratch ui_meta_link]
+<td class=subtabdown> 
+   <table width="100%" border=0 cellspacing=0 cellpadding=0>
+	  <tr> 
+		 <td class=subtabdownleft><img src="bg.gif" width=16 height=16></td>
+		 <td nowrap class=subtabdownfill><a href="[area href='admin/menu_editor' form='qmenu_name=[either][scratch second_menu][or][scratch ui_class][/either]']" {CHECK_PUBLISH} title="[msg]Edit these menu tabs[/msg]" class=edittablink>edit</a></td>
+		 <td class=subtabdownright><img src="bg.gif" width=16 height=16></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=darkshade><img src="bg.gif" height=1></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=lightshade><img src="bg.gif" height=1></td>
+   </table>
+</td>
+[/if][/if-mm]
+
+[if scratch third_menu]
+[output name=third_tabs]
+[menu
+	name="[scratch third_menu]"
+	superuser=super
+	extra_value.check_publish=`$Scratch->{check_publish}`
+	exclude_on=exclude_on
+	depends_on=depends_on
+	expand_values=name,page
+	expand_values_form=form
+	localize=name
+	indicator=indicator
+	indicator_page=page
+	inactive=inactive
+	entities=description
+	nbsp=name
+	reparse=1
+]
+<!-- PAGE=[var MV_PAGE 1] -->
+{INDICATED?}
+<td class=block3> 
+   <table width="100%" border=0 cellspacing=0 cellpadding=0>
+	  <tr> 
+		 <td class=subtableft><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+		 <td nowrap class=subtabfill><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=subtablink>{NAME}</a></td>
+		 <td class=subtabright><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=subtabfilllwr><img src="bg.gif" height=1></td>
+	  </tr>
+   </table>
+</td>
+{/INDICATED?}
+{INDICATED:}
+<td class=subtabdown> 
+   <table width="100%" border=0 cellspacing=0 cellpadding=0>
+	  <tr> 
+		 <td class=subtabdownleft><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+		 <td nowrap class=subtabdownfill><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}" class=subtablink>{NAME}</a></td>
+		 <td class=subtabdownright><a href="{HREF}" {CHECK_PUBLISH} title="{DESCRIPTION}"><img src="bg.gif" width=16 height=16 border=0></a></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=darkshade><img src="bg.gif" height=1></td>
+	  </tr>
+	  <tr> 
+		 <td colspan=3 class=lightshade><img src="bg.gif" height=1></td>
+   </table>
+</td>
+{/INDICATED:}
+[/menu]
+	<!-- menu edit=Third -->
+	[if-mm super][if scratch ui_meta_link]
+	<td class=subtabdown> 
+	   <table width="100%" border=0 cellspacing=0 cellpadding=0>
+		  <tr> 
+			 <td class=subtabdownleft><img src="bg.gif" width=16 height=16></td>
+			 <td nowrap class=subtabdownfill><a href="[area href='admin/menu_editor' form='qmenu_name=[scratch third_menu]']" {CHECK_PUBLISH} title="[msg]Edit these menu tabs[/msg]" class=edittablink>edit</a></td>
+			 <td class=subtabdownright><img src="bg.gif" width=16 height=16></td>
+		  </tr>
+		  <tr> 
+			 <td colspan=3 class=darkshade><img src="bg.gif" height=1></td>
+		  </tr>
+		  <tr> 
+			 <td colspan=3 class=lightshade><img src="bg.gif" height=1></td>
+	   </table>
+	</td>
+	[/if][/if-mm]
+[/if]
+[output name=""]
 EOV



No                   revision



No                   revision



1.1.1.1.4.1 +1 -1      interchange/dist/src/config.h.in


rev 1.1.1.1.4.1, prev_rev 1.1.1.1
Index: config.h.in
===================================================================
RCS file: /var/cvs/interchange/dist/src/config.h.in,v
retrieving revision 1.1.1.1
retrieving revision 1.1.1.1.4.1
diff -u -r1.1.1.1 -r1.1.1.1.4.1
--- config.h.in	26 May 2000 18:50:22 -0000	1.1.1.1
+++ config.h.in	25 Jan 2003 22:21:24 -0000	1.1.1.1.4.1
@@ -22,7 +22,7 @@
  * This must be in the local filesystem, not an NFS mounted one. The
  * configure script will normally set this for you.
  *
- * LINK_TIMEOUT (both tlink.c and vlink.c
+ * LINK_TIMEOUT (both tlink.c and vlink.c)
  * Define timeout in seconds to wait for the server to start listening
  * on the socket.
  *



1.2.4.1   +18 -17    interchange/dist/src/mod_perl_tlink.pl


rev 1.2.4.1, prev_rev 1.2
Index: mod_perl_tlink.pl
===================================================================
RCS file: /var/cvs/interchange/dist/src/mod_perl_tlink.pl,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- mod_perl_tlink.pl	12 Jul 2000 03:08:10 -0000	1.2
+++ mod_perl_tlink.pl	25 Jan 2003 22:21:24 -0000	1.2.4.1
@@ -1,23 +1,24 @@
 #!/usr/bin/perl
-# tlink.pl: runs as a cgi program and passes request to Vend server
+
+# tlink.pl: runs as a cgi program and passes request to Interchange server
 #
-#   $Id: mod_perl_tlink.pl,v 1.2 2000/07/12 03:08:10 heins Exp $
+# $Id: mod_perl_tlink.pl,v 1.2.4.1 2003/01/25 22:21:24 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-#    This program is free software; you can redistribute it and/or
-#    modify it under the terms of the GNU General Public License as
-#    published by the Free Software Foundation; either version 2 of the
-#    License, or (at your option) any later version.
+# This program is free software; you can redistribute it and/or
+# modify it under the terms of the GNU General Public License as
+# published by the Free Software Foundation; either version 2 of the
+# License, or (at your option) any later version.
 #
-#    This program is distributed in the hope that it will be useful,
-#    but WITHOUT ANY WARRANTY; without even the implied warranty of
-#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-#    General Public License for more details.
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# General Public License for more details.
 #
-#    You should have received a copy of the GNU General Public License
-#    along with this program; if not, write to the Free Software
-#    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 
 require 5.005;
 use strict;
@@ -75,8 +76,8 @@
 <BODY BGCOLOR="#FFFFFF">
 <H3>We're sorry, the Interchange server was not running...</H3>
 <P>
-We are out of service or may be experiencing high system demand,
-please try again soon.
+We are out of service or may be experiencing high system demand.
+Please try again soon.
 
 <H3>This is it:</H3>
 <PRE>
@@ -94,7 +95,7 @@
 #
 sub die_page {
   $r->print("Content-type: text/plain\r\n\r\n");
-  $r->print("We are sorry, but the cgi-bin server is unavailable due to a\r\n");
+  $r->print("We are sorry, but the Interchange server is unavailable due to a\r\n");
   $r->print("system error.\r\n\r\n");
   $r->print(sprintf "%s: %s (%d)\r\n", $_[0], $!, $?);
   if($ERROR_ACTION =~ /not/i) {



1.2.4.1   +23 -23    interchange/dist/src/mvctl.c


rev 1.2.4.1, prev_rev 1.2
Index: mvctl.c
===================================================================
RCS file: /var/cvs/interchange/dist/src/mvctl.c,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- mvctl.c	12 Jul 2000 03:08:10 -0000	1.2
+++ mvctl.c	25 Jan 2003 22:21:24 -0000	1.2.4.1
@@ -1,26 +1,26 @@
-/* minivend.c:  runs as a command line or cgi program and starts up
-			    Interchange in various modes
-
-   $Id: mvctl.c,v 1.2 2000/07/12 03:08:10 heins Exp $
-
-   Copyright (C) 1997-2000 Akopia, Inc. <info@akopia.com>
-
-   This program is free software; you can redistribute it and/or modify
-   it under the terms of the GNU General Public License as published by
-   the Free Software Foundation; either version 2 of the License, or
-   (at your option) any later version.
-
-   This program is distributed in the hope that it will be useful,
-   but WITHOUT ANY WARRANTY; without even the implied warranty of
-   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-   GNU General Public License for more details.
-
-   You should have received a copy of the GNU General Public
-   License along with this program; if not, write to the Free
-   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
-   MA  02111-1307  USA.
-
-*/
+/*
+ * mvctl.c: runs as a command line or cgi program and starts up
+ *			Interchange in various modes
+ *
+ * $Id: mvctl.c,v 1.2.4.1 2003/01/25 22:21:24 racke Exp $
+ *
+ * Copyright (C) 1997-2002 Red Hat, Inc. <interchange@redhat.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the Free
+ * Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA  02111-1307  USA.
+ */
 
 #define PERL      "/usr/bin/perl"
 #define VendRoot  "/home/minivend"



1.2.4.1   +30 -29    interchange/dist/src/tlink.c


rev 1.2.4.1, prev_rev 1.2
Index: tlink.c
===================================================================
RCS file: /var/cvs/interchange/dist/src/tlink.c,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- tlink.c	12 Jul 2000 03:08:10 -0000	1.2
+++ tlink.c	25 Jan 2003 22:21:24 -0000	1.2.4.1
@@ -1,28 +1,28 @@
-/* tlink.c:  runs as a cgi program and passes request to Vend server
-			 via TCP/IP 
-
-   $Id: tlink.c,v 1.2 2000/07/12 03:08:10 heins Exp $
-
-   Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-
-   Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-
-   This program is free software; you can redistribute it and/or modify
-   it under the terms of the GNU General Public License as published by
-   the Free Software Foundation; either version 2 of the License, or
-   (at your option) any later version.
-
-   This program is distributed in the hope that it will be useful,
-   but WITHOUT ANY WARRANTY; without even the implied warranty of
-   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-   GNU General Public License for more details.
-
-   You should have received a copy of the GNU General Public
-   License along with this program; if not, write to the Free
-   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
-   MA  02111-1307  USA.
-
-*/
+/*
+ * tlink.c: runs as a CGI program and passes request to Interchange
+ *          server via TCP/IP
+ *
+ * $Id: tlink.c,v 1.2.4.1 2003/01/25 22:21:24 racke Exp $
+ *
+ * Copyright (C) 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
+ *
+ * Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the Free
+ * Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA  02111-1307  USA.
+ */
 
 #include "config.h"
 #include <errno.h>
@@ -72,10 +72,10 @@
 void server_not_running()
 {
   printf("Content-type: text/html\r\n\r\n");
-  printf("<HTML><TITLE>No response</TITLE></HEAD><BODY  BGCOLOR=\"#FFFFFF\">");
+  printf("<HTML><HEAD><TITLE>No response</TITLE></HEAD><BODY BGCOLOR=\"#FFFFFF\">");
   printf("<H3>We're sorry, the Interchange server is unavailable...</H3>\r\n");
   printf("We are out of service or may be experiencing high system\r\n");
-  printf("demand, please try again soon.</BODY></HTML>\r\n");
+  printf("demand. Please try again soon.</BODY></HTML>\r\n");
   exit(1);
 }
 
@@ -107,7 +107,7 @@
      char* msg;
 {
   printf("Content-type: text/plain\r\n\r\n");
-  printf("We are sorry, but the cgi-bin server is unavailable due to a\r\n");
+  printf("We are sorry, but the Interchange server is unavailable due to a\r\n");
   printf("system error.\r\n\r\n");
   printf("%s: %s (%d)\r\n", msg, ERRMSG(e), e);
   exit(1);
@@ -174,13 +174,14 @@
   char* lpstring;
   int lport;
   unsigned int p; /* port */
+  char *machine = LINK_HOST;  //static and global string;
   uid_t euid;
   gid_t egid;
 
 
   lhost = getenv("MINIVEND_HOST");
   if(lhost == NULL) {
-  	lhost = LINK_HOST;
+  	lhost = machine;
   }
 
   lpstring = getenv("MINIVEND_PORT");



1.2.4.2   +24 -20    interchange/dist/src/tlink.pl


rev 1.2.4.2, prev_rev 1.2.4.1
Index: tlink.pl
===================================================================
RCS file: /var/cvs/interchange/dist/src/tlink.pl,v
retrieving revision 1.2.4.1
retrieving revision 1.2.4.2
diff -u -r1.2.4.1 -r1.2.4.2
--- tlink.pl	27 Nov 2000 02:05:31 -0000	1.2.4.1
+++ tlink.pl	25 Jan 2003 22:21:24 -0000	1.2.4.2
@@ -1,24 +1,25 @@
 #!/usr/bin/perl -wT
-# tlink.pl: runs as a cgi program and passes request to Vend server
+
+# tlink.pl: runs as a cgi program and passes request to Interchange server
 #
-#   $Id: tlink.pl,v 1.2.4.1 2000/11/27 02:05:31 racke Exp $
+# $Id: tlink.pl,v 1.2.4.2 2003/01/25 22:21:24 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-#    This program is free software; you can redistribute it and/or
-#    modify it under the terms of the GNU General Public License as
-#    published by the Free Software Foundation; either version 2 of the
-#    License, or (at your option) any later version.
-#
-#    This program is distributed in the hope that it will be useful,
-#    but WITHOUT ANY WARRANTY; without even the implied warranty of
-#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-#    General Public License for more details.
-#
-#    You should have received a copy of the GNU General Public
-#    License along with this program; if not, write to the Free
-#    Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
-#    MA  02111-1307  USA.
+# This program is free software; you can redistribute it and/or
+# modify it under the terms of the GNU General Public License as
+# published by the Free Software Foundation; either version 2 of the
+# License, or (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public
+# License along with this program; if not, write to the Free
+# Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+# MA  02111-1307  USA.
 
 require 5.002;
 use strict;
@@ -53,8 +54,8 @@
 <BODY BGCOLOR="#FFFFFF">
 <H3>We're sorry, the Interchange server was not running...</H3>
 <P>
-We are out of service or may be experiencing high system demand,
-please try again soon.
+We are out of service or may be experiencing high system demand.
+Please try again soon.
 
 </BODY></HTML>
 EOF
@@ -65,7 +66,7 @@
 #
 sub die_page {
   printf("Content-type: text/plain\r\n\r\n");
-  printf("We are sorry, but the cgi-bin server is unavailable due to a\r\n");
+  printf("We are sorry, but the Interchange server is unavailable due to a\r\n");
   printf("system error.\r\n\r\n");
   printf("%s: %s (%d)\r\n", $_[0], $!, $?);
   if($ERROR_ACTION =~ /not/i) {
@@ -86,6 +87,9 @@
   return '' unless $len;
 
   my $check;
+
+  # Can't hurt, helps Windows people
+  binmode(STDIN);
 
   $check = read(STDIN, $Entity, $len);
 



1.2.4.1   +27 -26    interchange/dist/src/vlink.c


rev 1.2.4.1, prev_rev 1.2
Index: vlink.c
===================================================================
RCS file: /var/cvs/interchange/dist/src/vlink.c,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- vlink.c	12 Jul 2000 03:08:10 -0000	1.2
+++ vlink.c	25 Jan 2003 22:21:24 -0000	1.2.4.1
@@ -1,26 +1,27 @@
-/* vlink.c:  runs as a cgi program and passes request to Vend server
-
-   $Id: vlink.c,v 1.2 2000/07/12 03:08:10 heins Exp $
-
-   Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-
-   Modified by Mike Heins <heins@akopia.com>
-
-   This program is free software; you can redistribute it and/or modify
-   it under the terms of the GNU General Public License as published by
-   the Free Software Foundation; either version 2 of the License, or
-   (at your option) any later version.
-
-   This program is distributed in the hope that it will be useful,
-   but WITHOUT ANY WARRANTY; without even the implied warranty of
-   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-   GNU General Public License for more details.
-
-   You should have received a copy of the GNU General Public
-   License along with this program; if not, write to the Free
-   Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
-   MA  02111-1307  USA.
-*/
+/*
+ * vlink.c: runs as a cgi program and passes request to Interchange server
+ *
+ * $Id: vlink.c,v 1.2.4.1 2003/01/25 22:21:24 racke Exp $
+ *
+ * Copyright (C) 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
+ *
+ * Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the Free
+ * Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA  02111-1307  USA.
+ */
 
 #include "config.h"
 #include <errno.h>
@@ -58,10 +59,10 @@
 void server_not_running()
 {
   printf("Content-type: text/html\r\n\r\n");
-  printf("<HTML><TITLE>No response</TITLE></HEAD><BODY  BGCOLOR=\"#FFFFFF\">");
+  printf("<HTML><HEAD><TITLE>No response</TITLE></HEAD><BODY BGCOLOR=\"#FFFFFF\">");
   printf("<H3>We're sorry, the Interchange server is unavailable...</H3>\r\n");
   printf("We are out of service or may be experiencing high system\r\n");
-  printf("demand, please try again soon.</BODY></HTML>\r\n");
+  printf("demand. Please try again soon.</BODY></HTML>\r\n");
   exit(1);
 }
 
@@ -73,7 +74,7 @@
      char* msg;
 {
   printf("Content-type: text/plain\r\n\r\n");
-  printf("We are sorry, but the cgi-bin server is unavailable due to a\r\n");
+  printf("We are sorry, but the Interchange server is unavailable due to a\r\n");
   printf("system error.\r\n\r\n");
   printf("%s: %s (%d)\r\n", msg, ERRMSG(e), e);
   exit(1);



1.2.4.1   +16 -14    interchange/dist/src/vlink.pl


rev 1.2.4.1, prev_rev 1.2
Index: vlink.pl
===================================================================
RCS file: /var/cvs/interchange/dist/src/vlink.pl,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- vlink.pl	12 Jul 2000 03:08:10 -0000	1.2
+++ vlink.pl	25 Jan 2003 22:21:24 -0000	1.2.4.1
@@ -1,19 +1,21 @@
 #!/usr/bin/perl -wT
-# vlink.pl: runs as a cgi program and passes request to Vend server
+
+# vlink.pl: runs as a cgi program and passes request to Interchange server
 #           via TCP UNIX-domain socket
-#   $Id: vlink.pl,v 1.2 2000/07/12 03:08:10 heins Exp $
+
+# $Id: vlink.pl,v 1.2.4.1 2003/01/25 22:21:24 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-#    This program is free software; you can redistribute it and/or
-#    modify it under the terms of the GNU General Public License as
-#    published by the Free Software Foundation; either version 2 of the
-#    License, or (at your option) any later version.
+# This program is free software; you can redistribute it and/or
+# modify it under the terms of the GNU General Public License as
+# published by the Free Software Foundation; either version 2 of the
+# License, or (at your option) any later version.
 #
-#    This program is distributed in the hope that it will be useful,
-#    but WITHOUT ANY WARRANTY; without even the implied warranty of
-#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-#    General Public License for more details.
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# General Public License for more details.
 #
 # You should have received a copy of the GNU General Public
 # License along with this program; if not, write to the Free
@@ -50,8 +52,8 @@
 <BODY BGCOLOR="#FFFFFF">
 <H3>We're sorry, the Interchange server is unavailable...</H3>
 <P>
-We are out of service or may be experiencing high system demand,
-please try again soon.
+We are out of service or may be experiencing high system demand.
+Please try again soon.
 
 </BODY></HTML>
 EOF
@@ -62,7 +64,7 @@
 #
 sub die_page {
   printf("Content-type: text/plain\r\n\r\n");
-  printf("We are sorry, but the cgi-bin server is unavailable due to a\r\n");
+  printf("We are sorry, but the Interchange server is unavailable due to a\r\n");
   printf("system error.\r\n\r\n");
   printf("%s: %s (%d)\r\n", $_[0], $!, $?);
   if($ERROR_ACTION =~ /not/i) {



No                   revision



No                   revision



1.1.4.2   +13 -22    interchange/dist/src/mod_interchange/Makefile


rev 1.1.4.2, prev_rev 1.1.4.1
Index: Makefile
===================================================================
RCS file: /var/cvs/interchange/dist/src/mod_interchange/Makefile,v
retrieving revision 1.1.4.1
retrieving revision 1.1.4.2
diff -u -r1.1.4.1 -r1.1.4.2
--- Makefile	3 Apr 2001 08:14:38 -0000	1.1.4.1
+++ Makefile	25 Jan 2003 22:21:24 -0000	1.1.4.2
@@ -1,42 +1,33 @@
-##
-##  Makefile -- Build procedure for mod_interchange Apache module
-##  Originally autogenerated via ``apxs -n mod_interchange -g''.
-##
-
-#   the used tools
+#
+#	$Id: Makefile,v 1.1.4.2 2003/01/25 22:21:24 racke Exp $
+#
+#	mod_interchange makefile
+#
 APXS=apxs
 APACHECTL=apachectl
 
-#   additional defines, includes and libraries
-#DEF=-Dmy_define=my_value
-#INC=-Imy/include/dir
-#LIB=-Lmy/lib/dir -lmylib
+#
+#	uncomment if you are running some weird OS that
+#	doesn't have a socklen_t, such as OS/X
+#
+#OSX=-DOSX
 
-#   the default target
 all: mod_interchange.so
 
-#   compile the shared object file
 mod_interchange.so: mod_interchange.c
-	$(APXS) -c $(DEF) $(INC) $(LIB) mod_interchange.c
+	$(APXS) $(OSX) -c $(DEF) $(INC) $(LIB) mod_interchange.c
 
-#   install the shared object file into Apache 
-install: all
-	$(APXS) -i -a -n interchange mod_interchange.so
+#install: all
+#	$(APXS) -i -a -n 'interchange' mod_interchange.so
 
-#   cleanup
 clean:
 	-rm -f mod_interchange.o mod_interchange.so
 
-#   simple test
 test: reload
 	lynx -mime_header http://localhost/mod_interchange
 
-#   install and activate shared object by reloading Apache to
-#   force a reload of the shared object file
 reload: install restart
 
-#   the general Apache start/restart/stop
-#   procedures
 start:
 	$(APACHECTL) start
 restart:



1.1.4.2   +90 -105   interchange/dist/src/mod_interchange/README


rev 1.1.4.2, prev_rev 1.1.4.1
Index: README
===================================================================
RCS file: /var/cvs/interchange/dist/src/mod_interchange/README,v
retrieving revision 1.1.4.1
retrieving revision 1.1.4.2
diff -u -r1.1.4.1 -r1.1.4.2
--- README	3 Apr 2001 08:14:38 -0000	1.1.4.1
+++ README	25 Jan 2003 22:21:24 -0000	1.1.4.2
@@ -1,147 +1,132 @@
 mod_interchange
 ===============
 
-Version: 1.04
+$Id: README,v 1.1.4.2 2003/01/25 22:21:24 racke Exp $
+
+Version: 1.29
 
 Description
 -----------
-mod_interchange is designed to replace the vlink and tlink programs that
-come with Interchange. The Interchange link protocol is implemented via
-an Apache module which saves us the (small) overhead of the execution
-of a CGI program.
 
-Requires
---------
-Apache 1.3.6 or later
-Any version of Interchange (all the way back to MiniVend 3.12)
+mod_interchange is designed to replace the vlink and tlink programs
+that comes with Interchange.  The Interchange link protocol has been
+implemented via an Apache module which saves us the (small) overhead
+of the execution of a CGI program.
+
+Note that this module is not compatible with Apache 2.
 
-Installing
-----------
-The included Makefile builds the module as a DSO object. So if your
-Apache has mod_dso.so configured you can do:
+Building the module
+-------------------
 
-make 
-make install
+The included Makefile builds the module as a DSO object. So if
+you're Apache has mod_dso.so configured you can do
 
-If not, you can copy the file mod_interchange.c to src/modules/extra
-and add the option:
+    make
+    make install
 
---activate-module=src/modules/extra/mod_interchange.c
+If not, you should be able to copy the file mod_interchange.c under
+src/modules/extra and add the line when building Apache:
 
-to the 'configure' command when building Apache.
+    --activate-module=src/modules/extra/mod_interchange.c
 
-Configuring Interchange
------------------------
-First you need to decide what URL path you want to point to Interchange,
-and make sure you don't need any files from that same path. For example,
-with the default Construct Something demo you have HTML and images in:
 
-http://www.yourdomain.com/construct/*
+Installing the module as a DSO object
+-------------------------------------
 
-So you can't have mod_interchange take over the /construct path. Instead
-use a different name like /store, so that users will access the site with
-a URL like:
+Copy mod_intercange.so into your Apache DSO library directory and
+add the following lines to your httpd.conf:
 
-http://www.yourdomain.com/store
+    LoadModule interchange_module /wherever/lib/apache/mod_interchange.so
+    AddModule mod_interchange.c
 
-And Apache will still be able to serve images from /construct/* just fine.
 
-To make such a change, you need to modify the Catalog directive in
-interchange.cfg to look like this:
+Documentation
+-------------
 
-Catalog  construct  /var/lib/interchange/construct  /store
+The module understands directives which specify the way to contact the
+primary, and possibly a secondary, Interchange server.  The InterchangeServer
+directive takes either a pathname to the Interchange UNIX socket or a
+host:port specification if you want to use INET mode.
 
-And update the CGI_URL variable in catalog.cfg by uncommenting and changing
-this line:
+The optional InterchangeServerBackup directive takes the same arguments,
+but should obviously point to a different Interchange server than the
+primary.  The InterchangeServerBackup directive is only of any use if
+you have multiple Interchange servers configured in a clustered environment.
 
-Variable  CGI_URL  /store
+Note: The Apache <Location> path should not contain a dot (.) or any
+other characters except A-Z, a-z, 0-9 or a hyphen (-), so:
 
-Configuring Apache
-------------------
-The module understands one directive which specifies the way to contact
-the Interchange server. The directive InterchangeServer takes either a
-full pathname to the Interchange UNIX socket or a host:port specification
-if you want to use INET mode.
+	<Location /shop.name> is invalid, whereas:
+	<Location /shop-name> is valid.
 
-That means you need to add new Location section to your Apache httpd.conf.
-We'll discuss the two kinds of InterchangeServer settings separately.
 
-UNIX socket setup
------------------
-Here is an example httpd.conf section for connecting to Interchange via
-a UNIX socket on the same machine Apache's running on:
+Examples
+--------
+
+UNIX mode local connection:
 
-<Location /store>
+    <Location /shop>
 	SetHandler interchange-handler
-	InterchangeServer /var/run/interchange/socket
-</Location>
+	InterchangeServer /opt/interchange/etc/socket
+    </Location>
 
-Since you're not using the set-UID CGI executable anymore, you need to
-allow the Apache daemon to read from and write to the socket directly.
-This is slightly tricky because Interchange recreates the socket file each
-time it is run, so you can't just modify the ownership and permissions
-of the socket file directly.
+INET mode local connection:
 
-We solve this by setting the group ownership of the directory the socket
-is in to a group Apache is a member of (usually www, apache, http, nobody,
-or similar):
+    <Location /shop>
+	SetHandler interchange-handler
+	InterchangeServer localhost:7786
+    </Location>
 
-chgrp apache /var/run/interchange
+UNIX mode local primary connection and INET mode remote backup connection:
 
-Then we make the directory set-GID so any files created in it will have
-the same group ownership as the directory:
+    <Location /shop>
+	SetHandler interchange-handler
+	InterchangeServer /opt/interchange/etc/socket
+	InterchangeServerBackup another.server.com:7786
+    </Location>
+
+The ConnectTries parameter specifies the number of connection attempts to
+make before giving up.  ConnectRetryDelay specifies the delay, in seconds,
+between each retry attempt.
 
-chmod g+srx /var/run/interchange
+The ConnectTries default is 10 and the ConnectRetryDelay default is 2 seconds.
+Here is an example:
 
-Obviously you'll need to substitute the correct group for 'apache' and the
-right parent directory of the socket where we show '/var/run/interchange'.
-In a non-RPM Interchange installation the directory is 'etc' inside the
-Interchange software directory (perhaps /usr/local/interchange).
+    <Location /shop>
+	SetHandler interchange-handler
+	InterchangeServer localhost:7786
+	ConnectTries 10
+	ConnectRetryDelay 1
+    </Location>
+
+The DropRequestList allows a list of up to 10 space-separated URI components
+to be specified.  If one of the list entries is found anywhere in the
+requested URI, the request will be dropped with a 404 (not found) error,
+without the request being passed to Interchange.  This parameter is useful
+for blocking known Microsoft IIS attacks like "Code Red", so that we don't
+waste any more time processing the (bogus) requests than we have to.
 
-Next you need to add this directive to interchange.cfg:
+    <Location /shop>
+	SetHandler interchange-handler
+	InterchangeServer localhost:7786
+	DropRequestList /default.ida /x.ida /cmd.exe /root.exe
+    </Location>
 
-SocketPerms 0660
 
-This tells Interchange to allow reading from and writing to the socket by
-the group (which our set-GID directory will set to the group the Apache
-daemon is in), instead of the default 0600, which would only allow reading
-and writing by the owner (the Interchange user, usually 'interch').
+Bugs
+----
 
-INET socket setup
------------------
-This is the configuration to connect to Interchange via INET sockets:
+Send bug reports and suggestions to Kevin Walsh <kevin@cursor.biz>
 
-<Location /store>
-	SetHandler interchange-handler
-	InterchangeServer ic.host.com:7786
-</Location>
 
-The port number is optional if you're using the default port 7786.
+Copyright and License
+---------------------
 
-Support
--------
-Visit http://developer.akopia.com/ to find information on how you can join
-the Interchange mailing lists, browse documentation and mailing list
-archives, and get other support.
-
-History
--------
-mod_interchange is the direct descendant of mod_minivend, created by
-Francis J. Lacoste <francis.lacoste@iNsu.com> at iNsu Innovations Inc.
-in 1999. Thanks, Francis!
-
-Maintenance of the module was taken over by Red Hat (formerly Akopia)
-in February 2001, with Francis's blessing. The only changes we've made
-so far are to rename occurrences of MiniVend to Interchange, expand the
-documentation, and include it in the standard Interchange distribution
-starting with Interchange 4.6.4.
-
-Copyright
----------
-Copyright (c) 1999 Francis J. Lacoste and iNsu Innovations Inc. 
+Copyright (c) 1999 Francis J. Lacoste and iNsu Innovations Inc.
+Copyright (c) 2000-2003 Cursor Software Limited.
 All rights reserved.
 
-This program is free software; you can redistribute it and/or modify
+This program is free software.  You can redistribute it and/or modify
 it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 2 of the License, or
-(at your option) any later version.
+the Free Software Foundation.  You may refer to either version 2 of the
+License or (at your option) any later version.



1.2.4.2   +749 -414  interchange/dist/src/mod_interchange/mod_interchange.c


rev 1.2.4.2, prev_rev 1.2.4.1
Index: mod_interchange.c
===================================================================
RCS file: /var/cvs/interchange/dist/src/mod_interchange/mod_interchange.c,v
retrieving revision 1.2.4.1
retrieving revision 1.2.4.2
diff -u -r1.2.4.1 -r1.2.4.2
--- mod_interchange.c	3 Apr 2001 08:14:38 -0000	1.2.4.1
+++ mod_interchange.c	25 Jan 2003 22:21:24 -0000	1.2.4.2
@@ -1,34 +1,32 @@
+#define	MODULE_VERSION	"mod_interchange/1.29"
 /*
- *  mod_interchange.c
- *  Apache module implementation of the Interchange link program.
+ *	$Id: mod_interchange.c,v 1.2.4.2 2003/01/25 22:21:24 racke Exp $
  *
- *  Support: http://developer.akopia.com/
+ *	Apache Module implementation of the Interchange application server
+ *	link programs.
  *
- *  Author: Francis J. Lacoste <francis.lacoste@iNsu.COM>
+ *	Author: Kevin Walsh <kevin@cursor.biz>
+ *	Based on original code by Francis J. Lacoste <francis.lacoste@iNsu.COM>
  *
- *  Copyright (C) 1999 Francis J. Lacoste, iNsu Innovations
+ *	Copyright (c) 1999 Francis J. Lacoste, iNsu Innovations.
+ *	Copyright (c) 2000-2003 Cursor Software Limited.
+ *	All rights reserved.
  *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License as published by
- *  the Free Software Foundation; either version 2 of the License, or
- *  (at your option) any later version.
+ *	This program is free software; you can redistribute it and/or modify
+ *	it under the terms of the GNU General Public License as published by
+ *	the Free Software Foundation; either version 2 of the License, or
+ *	(at your option) any later version.
  *
- *  This program is distributed in the hope that it will be useful,
- *  but WITHOUT ANY WARRANTY; without even the implied warranty of
- *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- *  GNU General Public License for more details.
+ *	This program is distributed in the hope that it will be useful,
+ *	but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *	GNU General Public License for more details.
  *
- *  You should have received a copy of the GNU General Public License
- *  along with this program; if not, write to the Free Software
- *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
- *  02111-1307 USA
+ *	You should have received a copy of the GNU General Public License
+ *	along with this program; if not, write to the Free Software
+ *	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+ *	02111-1307 USA
  */
-
-/*
- *  $Id: mod_interchange.c,v 1.2.4.1 2001/04/03 08:14:38 racke Exp $
- *
-*/
-
 #include "httpd.h"
 #include "http_config.h"
 #include "http_core.h"
@@ -43,519 +41,856 @@
 #include <sys/un.h>
 #include <unistd.h>
 
-#define IC_DEFAULT_PORT 7786
-#define IC_DEFAULT_ADDR "127.0.0.1"
+#ifdef	OSX
+typedef long socklen_t;
+#endif
+
+#ifndef	AF_LOCAL
+#define	AF_LOCAL	AF_UNIX
+#endif
+
+#ifndef	PF_LOCAL
+#define	PF_LOCAL	PF_UNIX
+#endif
+
+#ifndef SUN_LEN
+#define SUN_LEN(su)	(sizeof(*(su)) - sizeof((su)->sun_path) + strlen((su)->sun_path))
+#endif
+
+#define IC_DEFAULT_PORT			7786
+#define IC_DEFAULT_ADDR			"127.0.0.1"
+#define	IC_DEFAULT_TIMEOUT		10
+#define	IC_DEFAULT_CONNECT_TRIES	10
+#define	IC_DEFAULT_CONNECT_RETRY_DELAY	2
+
+#define	IC_MAX_DROPLIST			10
+#define IC_MAX_SERVERS			2
 
-/* Forward declaration */
 module MODULE_VAR_EXPORT interchange_module;
 
-typedef struct ic_conf_struct
-{
-	struct sockaddr *sockaddr;  /* Socket of Interchange Server */
-	int				family;		/* The socket family of that one */
-	NET_SIZE_T		size;		/* The size of the socket */
-	char			*address;	/* Human readable version of the above */
-} ic_conf_rec;
+typedef struct ic_socket_struct{
+	struct sockaddr *sockaddr; /* socket to the Interchange server */
+	int family;		/* the socket family in use */
+	socklen_t size;		/* the size of the socket structure */
+	char *address;		/* human-readable form of the address */
+}ic_socket_rec;
+
+typedef struct ic_conf_struct{
+	ic_socket_rec *server[IC_MAX_SERVERS];	/* connection to IC server(s) */
+	int connect_tries;	/* number of times to ret to connect to IC */
+	int connect_retry_delay; /* delay this many seconds between retries */
+	int droplist_no;
+	int loclen;			/* size of the location string */
+	char location[HUGE_STRING_LEN];	/* configured <Location> */
+	char droplist[IC_MAX_DROPLIST][HUGE_STRING_LEN];
+}ic_conf_rec;
+
+typedef struct ic_response_buffer_struct{
+	int buff_size;
+	int pos;
+	char buff[HUGE_STRING_LEN];
+}ic_response_buffer;
 
-typedef struct ic_response_buffer_struct
+static void ic_initialise(server_rec *,pool *);
+static void *ic_create_dir_config(pool *,char *);
+static const char *ic_server_cmd(cmd_parms *,void *,const char *);
+static const char *ic_serverbackup_cmd(cmd_parms *,void *,const char *);
+static const char *ic_server_setup(cmd_parms *,void *,int,const char *arg);
+static const char *ic_connecttries_cmd(cmd_parms *,void *,const char *);
+static const char *ic_connectretrydelay_cmd(cmd_parms *,void *,const char *);
+static BUFF *ic_connect(request_rec *,ic_conf_rec *);
+static int ic_select(int,int,int,int);
+static int ic_send_request(request_rec *,ic_conf_rec *,BUFF *);
+static int ic_transfer_response(request_rec *,BUFF *);
+static int ic_handler(request_rec *);
+
+/*
+ *	ic_initialise()
+ *	---------------
+ *	Module initialisation.
+ */
+static void ic_initialise(server_rec *s,pool *p)
 {
-	int  buff_size;
-	int  pos;
-	char buff[HUGE_STRING_LEN];
-} ic_response_buffer;
+	ap_add_version_component(MODULE_VERSION);
+}
 
-static void*
-ic_create_dir_config(pool *p, char *dir)
+/*
+ *	ic_create_dir_config()
+ *	----------------------
+ *	This module's per-directory config creator.
+ *	Sets up the default configuration for this location,
+ *	which can be overridden using the module's configuration
+ *	directives
+ */
+static void *ic_create_dir_config(pool *p,char *dir)
 {
 	struct sockaddr_in *inet_sock;
+	int tmp;
 
-	ic_conf_rec *conf_rec = (ic_conf_rec *)ap_pcalloc(p, sizeof(ic_conf_rec));
+	ic_conf_rec *conf_rec = (ic_conf_rec *)ap_pcalloc(p,sizeof(ic_conf_rec));
+	if (conf_rec == NULL)
+		return NULL;
+
+	/*
+	 *	the default connection method is INET to localhost
+	 */
+	inet_sock = (struct sockaddr_in *)ap_pcalloc(p,sizeof(struct sockaddr_in));
+	if (inet_sock == NULL)
+		return NULL;
 
-	/* Default connection method is INET to localhost */
-	inet_sock =
-		(struct sockaddr_in *)ap_pcalloc( p, sizeof (struct sockaddr_in));
 	inet_sock->sin_family = AF_INET;
-	inet_aton( IC_DEFAULT_ADDR, &inet_sock->sin_addr );
-	inet_sock->sin_port   = htons( IC_DEFAULT_PORT );
+	inet_aton(IC_DEFAULT_ADDR,&inet_sock->sin_addr);
+	inet_sock->sin_port = htons(IC_DEFAULT_PORT);
 
-	conf_rec->sockaddr  = (struct sockaddr *)inet_sock;
-	conf_rec->size      = sizeof (struct sockaddr_in);
-	conf_rec->family    = PF_INET;
-	conf_rec->address   = IC_DEFAULT_ADDR ":" "IC_DEFAULT_PORT";
+	conf_rec->server[0] = (ic_socket_rec *)ap_pcalloc(p,sizeof(ic_socket_rec));
+	if (conf_rec->server[0] == NULL)
+		return NULL;
+
+	conf_rec->server[0]->sockaddr = (struct sockaddr *)inet_sock;
+	conf_rec->server[0]->size = sizeof (struct sockaddr_in);
+	conf_rec->server[0]->family = PF_INET;
+	conf_rec->server[0]->address = IC_DEFAULT_ADDR;
+
+	for (tmp = 1; tmp < IC_MAX_SERVERS; tmp++)
+		conf_rec->server[tmp] = (ic_socket_rec *)NULL;
+
+	if (dir){
+		if (*dir == '/')
+			dir++;
+		strcpy(conf_rec->location,dir);
+		conf_rec->loclen = strlen(conf_rec->location);
+	}else{
+		conf_rec->location[0] = '\0';
+		conf_rec->loclen = 0;
+	}
+	if (conf_rec->location[conf_rec->loclen] != '/'){
+		conf_rec->location[conf_rec->loclen++] = '/';
+		conf_rec->location[conf_rec->loclen] = '\0';
+	}
+	conf_rec->connect_tries = IC_DEFAULT_CONNECT_TRIES;
+	conf_rec->connect_retry_delay = IC_DEFAULT_CONNECT_RETRY_DELAY;
+	conf_rec->droplist_no = 0;
 
 	return conf_rec;
 }
 
-static const char*
-ic_server_cmd(cmd_parms *parms, void *mconfig, const char *arg)
+/*
+ *	ic_server_cmd()
+ *	---------------
+ *	Handle the "InterchangeServer" module configuration directive
+ */
+static const char *ic_server_cmd(cmd_parms *parms,void *mconfig,const char *arg)
 {
-	ic_conf_rec *conf_rec   = (ic_conf_rec *)mconfig;
+	return ic_server_setup(parms,mconfig,0,arg);
+}
 
-	conf_rec->address		= ap_pstrdup( parms->pool, arg );
-	if ( conf_rec->address == NULL )
-		return "not enough memory";
-
-	/* Verify type of the argument */
-	if ( *arg == '/' ) {
-		/* This is a UNIX socket specification */
-		struct sockaddr_un *unix_sock;
+/*
+ *	ic_serverbackup_cmd()
+ *	---------------------
+ *	Handle the "InterchangeServerBackup" module configuration directive
+ */
+static const char *ic_serverbackup_cmd(cmd_parms *parms,void *mconfig,const char *arg)
+{
+	ic_conf_rec *conf_rec = (ic_conf_rec *)mconfig;
 
-		unix_sock	= (struct sockaddr_un *)
-			ap_pcalloc( parms->pool, sizeof( struct sockaddr_un ) );
-		if (unix_sock == NULL)
-			return "not enough memory";
+	conf_rec->server[1] = (ic_socket_rec *)ap_pcalloc(parms->pool,sizeof(ic_socket_rec));
+	if (conf_rec->server[1] == NULL)
+		return "not enough memory for backup socket record";
 
-		unix_sock->sun_family = AF_LOCAL;
-		ap_cpystrn( unix_sock->sun_path, conf_rec->address,
-				 sizeof (unix_sock->sun_path));
+	return ic_server_setup(parms,mconfig,1,arg);
+}
+
+/*
+ *	ic_server_setup()
+ *	-----------------
+ *	Do the actual primary/backup server setup on behalf of the
+ *	ic_server_cmd() and ic_serverbackup_cmd() functions.
+ */
+static const char *ic_server_setup(cmd_parms *parms,void *mconfig,int server,const char *arg)
+{
+	static char errmsg[100];
+
+	ic_conf_rec *conf_rec = (ic_conf_rec *)mconfig;
+	ic_socket_rec *sock_rec = conf_rec->server[server];
 
-		conf_rec->family   = PF_LOCAL;
-		conf_rec->size     = SUN_LEN( unix_sock );
-		conf_rec->sockaddr = (struct sockaddr *)unix_sock;
-	} else {
-		/* INET Socket
+	sock_rec->address = ap_pstrdup(parms->pool,arg);
+	if (sock_rec->address == NULL)
+		return "not enough memory for the socket address";
+
+	/*
+	 *	verify type of the argument, which will indicate
+	 *	whether we should be using a UNIX or Inet socket
+	 *	to connect to the Interchange server
+	 */
+	if (*arg == '/'){
+		/*
+		 *	this is to be a UNIX socket
+		 */
+		struct sockaddr_un *unix_sock;
 
-		   The argument is an IP address or hostname followed by
-		   an optional port specification.
+		unix_sock = (struct sockaddr_un *)ap_pcalloc(parms->pool,sizeof(struct sockaddr_un));
+		if (unix_sock == NULL){
+			sprintf(errmsg,"not enough memory for %s UNIX socket structure",server ? "primary" : "backup");
+			return errmsg;
+		}
+
+		unix_sock->sun_family = AF_LOCAL;
+		ap_cpystrn(unix_sock->sun_path,sock_rec->address,sizeof(unix_sock->sun_path));
+		sock_rec->sockaddr = (struct sockaddr *)unix_sock;
+		sock_rec->size = SUN_LEN(unix_sock);
+		sock_rec->family = PF_LOCAL;
+	}else{
+		/*
+		 *	this is to be an INET socket
+		 *
+		 *	the argument is an IP address or hostname followed by
+		 *	an optional port specification
 		 */
 		struct sockaddr_in *inet_sock;
-		char **hostaddress, *hostname;
+		char **hostaddress;
+		char *hostname;
+
+		inet_sock = (struct sockaddr_in *)ap_pcalloc(parms->pool,sizeof(struct sockaddr_in));
+		if (inet_sock == NULL){
+			sprintf(errmsg,"not enough memory for %s INET socket structure",server ? "primary" : "backup");
+			return errmsg;
+		}
 
-		inet_sock	= (struct sockaddr_in *)
-			ap_pcalloc( parms->pool, sizeof( struct sockaddr_in ) );
-		if (inet_sock == NULL)
-			return "not enough memory";
 		inet_sock->sin_family = AF_INET;
+		hostaddress = &(sock_rec->address);
+		hostname = ap_getword_nc(parms->temp_pool,hostaddress,':');
+
+		if (!inet_aton(hostname,&inet_sock->sin_addr)){
+			/*
+			 *	address must point to a hostname
+			 */
+			struct hostent *host = ap_pgethostbyname(parms->temp_pool,hostname);
+			if (!host)
+				return "invalid hostname specification";
 
-		hostaddress = &(conf_rec->address);
-		hostname    = ap_getword_nc( parms->temp_pool, hostaddress, ':');
+			memcpy(&inet_sock->sin_addr,host->h_addr,sizeof(inet_sock->sin_addr));
+		}
 
-		if ( ! inet_aton( hostname, &inet_sock->sin_addr ) )
-		{
-			/* Address must be a host */
-			struct hostent * host;
-			host = ap_pgethostbyname( parms->temp_pool, hostname );
-			if ( ! host )
-				return "invalid host specification";
-
-			memcpy(&inet_sock->sin_addr, host->h_addr,
-				   sizeof(inet_sock->sin_addr) );
-		}
-
-		/* Check if there is a port spec */
-		if ( **hostaddress ) {
-			int port = atoi( *hostaddress );
+		/*
+		 *	check if a port number has been specified
+		 */
+		if (**hostaddress){
+			int port = atoi(*hostaddress);
 
-			if ( port < 1 || port > 65535 )
+			if (port <= 100 || port > 65535)
 				return "invalid port specification";
 
-			inet_sock->sin_port = htons( port );
-		} else {
-			inet_sock->sin_port = htons( IC_DEFAULT_PORT );
+			inet_sock->sin_port = htons(port);
+		}else{
+			inet_sock->sin_port = htons(IC_DEFAULT_PORT);
 		}
 
-		conf_rec->sockaddr = (struct sockaddr *)inet_sock;
-		conf_rec->family   = PF_INET;
-		conf_rec->size     = sizeof( struct sockaddr_in );
-		conf_rec->sockaddr = (struct sockaddr *)inet_sock;
+		sock_rec->sockaddr = (struct sockaddr *)inet_sock;
+		sock_rec->family = PF_INET;
+		sock_rec->size = sizeof(struct sockaddr_in);
 	}
+	return NULL;
+}
 
+/*
+ *	ic_connecttries_cmd()
+ *	---------------------
+ *	Handle the "ConnectTries" module configuration directive
+ */
+static const char *ic_connecttries_cmd(cmd_parms *parms,void *mconfig,const char *arg)
+{
+	ic_conf_rec *conf_rec = (ic_conf_rec *)mconfig;
+
+	conf_rec->connect_tries = atoi(arg);
 	return NULL;
 }
 
-static BUFF *
-ic_connect( request_rec *r, ic_conf_rec *conf_rec )
+/*
+ *	ic_connectretrydelay_cmd()
+ *	--------------------------
+ *	Handle the "ConnectRetries" module configuration directive
+ */
+static const char *ic_connectretrydelay_cmd(cmd_parms *parms,void *mconfig,const char *arg)
+{
+	ic_conf_rec *conf_rec = (ic_conf_rec *)mconfig;
+
+	conf_rec->connect_retry_delay = atoi(arg);
+	return NULL;
+}
+
+/*
+ *	ic_droprequest_cmd()
+ *	--------------------
+ *	Handle the "DropRequestList" module configuration directive
+ */
+static const char *ic_droprequestlist_cmd(cmd_parms *parms,void *mconfig,const char *arg)
+{
+	ic_conf_rec *conf_rec = (ic_conf_rec *)mconfig;
+
+	if (conf_rec->droplist_no < IC_MAX_DROPLIST)
+		strcpy(conf_rec->droplist[conf_rec->droplist_no++],arg);
+
+	return NULL;
+}
+
+/*
+ *	ic_connect()
+ *	------------
+ *	Connect to the Interchange server
+ */
+static BUFF *ic_connect(request_rec *r,ic_conf_rec *conf_rec)
 {
-	int ic_sock;
 	BUFF *ic_buff;
+	ic_socket_rec *sock_rec;
+	int ic_sock,retry,srv;
+	int connected = 0;
+
+	/*
+	 *	connect the new socket to the Interchange server
+	 *
+	 *	if the connection to the Interchange server fails then
+	 *	retry IC_DEFAULT_CONNECT_TRIES times, sleeping for
+	 *	IC_DEFAULT_CONNECT_RETRY_DELAY seconds between each retry
+	 */
+	for (retry = 0; retry != conf_rec->connect_tries; retry++){
+		for (srv = 0; srv != IC_MAX_SERVERS; srv++){
+			if ((sock_rec = conf_rec->server[srv]) == NULL)
+				break;
+			if (srv){
+				ap_log_rerror(APLOG_MARK,APLOG_ERR|APLOG_NOERRNO,r,"Attempting to connect to backup server %d",srv);
+			}
 
-	/* Open connection to the server */
-	ic_sock = ap_psocket( r->pool, conf_rec->family, SOCK_STREAM, 0 );
-	if ( ic_sock < 0 ) {
-		ap_log_reason( "socket", r->uri, r);
-		return NULL;
+			/*
+			 *	attempt to connect to the Interchange server
+			 */
+			ic_sock = ap_psocket(r->pool,sock_rec->family,SOCK_STREAM,0);
+			if (ic_sock < 0){
+				ap_log_reason("socket",r->uri,r);
+				return NULL;
+			}
+			ap_hard_timeout("ic_connect",r);
+			if (connect(ic_sock,sock_rec->sockaddr,sock_rec->size) >= 0){
+				connected++;
+				break;
+			}
+			ap_kill_timeout(r);
+			ap_pclosesocket(r->pool,ic_sock);
+		}
+		if (connected)
+		    break;
+		sleep(conf_rec->connect_retry_delay);
 	}
-
-	/* Initialize a timeout */
-	ap_hard_timeout( "ic_connect", r );
-	if ( connect( ic_sock, conf_rec->sockaddr, conf_rec->size ) < 0 )
-	{
-		ap_log_reason( "Connection failed", r->uri, r );
+	ap_kill_timeout(r);
+	if (retry == conf_rec->connect_tries){
+		ap_log_reason("Connection failed",r->uri,r);
 		return NULL;
 	}
-	ap_kill_timeout( r );
 
-	/* Create a BUFF struct of that socket */
-	ic_buff = ap_bcreate( r->pool, B_RDWR | B_SOCKET );
-	if ( !ic_buff) {
-		ap_log_reason( "failed to create BUFF", r->uri, r );
+	/*
+	 *	create an Apache BUFF structure for our new connection
+	 */
+	ic_buff = ap_bcreate(r->pool,B_RDWR|B_SOCKET);
+	if (!ic_buff){
+		ap_log_reason("failed to create BUFF",r->uri,r);
 		return NULL;
 	}
-	ap_bpushfd( ic_buff, ic_sock, ic_sock );
-
+	ap_bpushfd(ic_buff,ic_sock,ic_sock);
 	return ic_buff;
 }
 
-static int
-ic_send_request( request_rec *r, ic_conf_rec *conf_rec, BUFF *ic_buff )
+/*
+ *	ic_select()
+ *	-----------
+ *	Convenient wrapper for select().
+ *	Wait for data to become available on the socket, or
+ *	for an error to occur, and return the appropriate status
+ *	code to the calling function.
+ */
+static int ic_select(int sock_rd,int sock_wr,int secs,int usecs)
 {
-	char **env, **e;
-	int env_count, rc;
+	fd_set sock_set_rd,sock_set_wr;
+	fd_set *rd = NULL,*wr = NULL;
+	struct timeval tv;
+	int rc;
 
-	/* Initialize a timeout */
-	ap_hard_timeout( "ic_send_request", r );
+	do{
+		if (sock_rd > 0){
+			FD_ZERO(&sock_set_rd);
+			FD_SET(sock_rd,&sock_set_rd);
+			rd = &sock_set_rd;
+		}
+		if (sock_wr > 0){
+			FD_ZERO(&sock_set_wr);
+			FD_SET(sock_wr,&sock_set_wr);
+			wr = &sock_set_wr;
+		}
 
-	/* Send the arg param
-	   This is always empty for a CGI request
+		tv.tv_sec = secs;
+		tv.tv_usec = usecs;
+		rc = ap_select(((sock_rd > sock_wr) ? sock_rd : sock_wr) + 1,rd,wr,NULL,&tv);
+	}while (rc == 0);
+	return rc;
+}
+
+/*
+ *	ic_send_request()
+ *	-----------------
+ *	Send the client's page/form request to the Interchange server
+ */
+static int ic_send_request(request_rec *r,ic_conf_rec *conf_rec,BUFF *ic_buff)
+{
+	char **env,**e,*rp;
+	int env_count,rc;
+	char request_uri[HUGE_STRING_LEN];
+	char redirect_url[HUGE_STRING_LEN];
+
+	/*
+	 *	send the Interchange-link arg parameter
+	 *	(this is always empty for a CGI request)
 	 */
-	if ( ap_bputs( "arg 0\n", ic_buff ) < 0 ) {
-		ap_log_reason( "error writing to Interchange", r->uri, r );
+	ap_hard_timeout("ic_send_request",r);
+	if (ap_bputs("arg 0\n",ic_buff) < 0){
+		ap_log_reason("error writing to Interchange",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
-	ap_reset_timeout( r );
-
-	/* Now on with the environment */
+	ap_reset_timeout(r);
 
-	/* Initialize Environment to send to Interchange */
-	ap_add_common_vars( r );
-	ap_add_cgi_vars( r );
+	/*
+	 *	initialize the environment to send to Interchange
+	 */
+	ap_add_common_vars(r);
+	ap_add_cgi_vars(r);
+	env = ap_create_environment(r->pool,r->subprocess_env);
 
-	env = ap_create_environment( r->pool, r->subprocess_env );
+	/*
+	 *	count the number of environment variables present
+	 */
+	for (e = env,env_count = 0; *e != NULL; e++,env_count++){
+		if (strncmp(*e,"PATH_INFO=",10) == 0)
+			env_count--;
+	}
+	env_count++;
 
-	/* Send the count */
-	for (e = env, env_count = 0;  *e != NULL;  ++e, ++env_count);
-	if ( ap_bprintf( ic_buff, "env %d\n", env_count ) < 0 ) {
-		ap_log_reason( "error writing to Interchange", r->uri, r );
+	/*
+	 *	send the environment variable count to Interchange
+	 */
+	if (ap_bprintf(ic_buff,"env %d\n",env_count) < 0){
+		ap_log_reason("error writing to Interchange",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
-	ap_reset_timeout( r );
+	ap_reset_timeout(r);
 
-	/* Now the vars */
-	for ( e = env;  *e != NULL;  ++e) {
-		if ( ap_bprintf(ic_buff, "%d %s\n", strlen(*e), *e ) < 0 ) {
-			ap_log_reason( "error writing to Interchange", r->uri, r );
+	/*
+	 *	ignore the PATH_INFO variable and fix the SCRIPT_NAME,
+	 *	REQUEST_URI and REDIRECT_URL variable content
+	 */
+	request_uri[0] = '\0';
+	redirect_url[0] = '\0';
+	for (e = env; *e != NULL; e++){
+		int len;
+
+		if (strncmp(*e,"PATH_INFO=",10) == 0)
+			continue;
+		if (strncmp(*e,"REDIRECT_URL=",13) == 0){
+			strcpy(redirect_url,(*e) + 13);
+			continue;
+		}
+		if (strncmp(*e,"REQUEST_URI=",12) == 0)
+			strcpy(request_uri,(*e) + 12);
+		else if (strncmp(*e,"SCRIPT_NAME=",12) == 0){
+			*(*e + 12) = '/';
+			strcpy(*e + 13,conf_rec->location);
+			if (*(*e + 12 + conf_rec->loclen) == '/')
+				*(*e + 12 + conf_rec->loclen) = '\0';
+		}
+		len = strlen(*e);
+		if (len && ap_bprintf(ic_buff,"%d %s\n",len,*e) < 0){
+			ap_log_reason("error writing to Interchange",r->uri,r);
 			return HTTP_INTERNAL_SERVER_ERROR;
 		}
-		ap_reset_timeout( r );
+		ap_reset_timeout(r);
 	}
 
-	/* Send the request body if any */
-	if ( r->method_number == M_POST ) {
-		if ( (rc = ap_setup_client_block( r, REQUEST_CHUNKED_ERROR) ) != OK)
-			return rc;
-
-		if ( ap_should_client_block(r) ) {
-			char buffer[HUGE_STRING_LEN];
-			int  len_read;
-			long length = r->remaining;
-
-			if (ap_bprintf( ic_buff, "entity\n%ld ", length ) < 0 ) {
-				ap_log_reason( "error writing to Interchange", r->uri, r );
-				return HTTP_INTERNAL_SERVER_ERROR;
-			}
-
-			while ( (len_read =
-					 ap_get_client_block(r, buffer, sizeof(buffer ))
-					 ) > 0 )
-			{
-				ap_reset_timeout(r);
-
-				/* Send that to Interchange */
-				if ( ap_bwrite( ic_buff, buffer, len_read ) != len_read ) {
-					ap_log_reason( "error writing to Interchange", r->uri, r );
-					return HTTP_INTERNAL_SERVER_ERROR;
-				}
-				ap_reset_timeout(r);
-			}
-			if ( len_read < 0 ) {
-				ap_log_reason( "error reading from client", r->uri, r );
-				return HTTP_INTERNAL_SERVER_ERROR;
-			}
-			/* Send end of line */
-			if ( ap_bputc( '\n', ic_buff ) < 0 ) {
-				ap_log_reason( "error writing to Interchange", r->uri, r );
-				return HTTP_INTERNAL_SERVER_ERROR;
-			}
+	rp = request_uri;
+	while (*rp == '/')
+		rp++;
+
+	if (strncmp(rp,conf_rec->location,conf_rec->loclen) == 0)
+		rp += (conf_rec->loclen - 1);
+
+	strcpy(request_uri,rp);
+	for (rp = request_uri; *rp != '\0'; rp++){
+		if (*rp == '?'){
+			*rp = '\0';
+			break;
 		}
 	}
-
-	/* We are done */
-	if ( ap_bputs( "end\n", ic_buff ) < 0 ) {
-		ap_log_reason( "error writing to Interchange", r->uri, r );
+	switch (ap_unescape_url(request_uri)){
+	case BAD_REQUEST:
+	case NOT_FOUND:
+		ap_log_reason("Bad URI entities found",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
-	ap_reset_timeout( r );
-	if ( ap_bflush( ic_buff ) < 0 ) {
-		ap_log_reason( "error writing to Interchange", r->uri, r );
+
+	/*
+	 *	send the PATH_INFO variable as our "fixed" REQUEST_URI
+	 */
+	if (ap_bprintf(ic_buff,"%d PATH_INFO=%s\n",strlen(request_uri) + 10,request_uri) < 0){
+		ap_log_reason("error writing to Interchange",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
 
-	ap_kill_timeout( r );
+	/*
+	 *	check if we have a REDIRECT_URL
+	 *	if so then give it the same "fixes" as PATH_INFO (REQUEST_URI)
+	 */
+	if (redirect_url[0] != '\0'){
+		rp = redirect_url;
+		while (*rp == '/')
+			rp++;
+
+		if (strncmp(rp,conf_rec->location,conf_rec->loclen) == 0)
+			rp += (conf_rec->loclen - 1);
+
+		strcpy(redirect_url,rp);
+		for (rp = redirect_url; *rp != '\0'; rp++){
+			if (*rp == '?'){
+				*rp = '\0';
+				break;
+			}
+		}
+		switch (ap_unescape_url(redirect_url)){
+		case BAD_REQUEST:
+		case NOT_FOUND:
+			ap_log_reason("Bad URI entities found",r->uri,r);
+			return HTTP_INTERNAL_SERVER_ERROR;
+		}
 
-	return OK;
-}
+		if (ap_bprintf(ic_buff,"%d REDIRECT_URL=%s\n",strlen(redirect_url) + 13,redirect_url) < 0){
+			ap_log_reason("error writing to Interchange",r->uri,r);
+			return HTTP_INTERNAL_SERVER_ERROR;
+		}
+	}
+	ap_reset_timeout(r);
 
-static int
-ic_transfer_response( request_rec *r, ic_conf_rec *conf_rec,
-					  BUFF *ic_buff )
-{
-	char error_buff[MAX_STRING_LEN];
-	BUFF *client_buff;
-	int rc;
+	/*
+	 *	send the request body, if any
+	 */
+	if (ap_should_client_block(r)){
+		char buffer[HUGE_STRING_LEN];
+		int len_read;
+		long length = r->remaining;
 
-	array_header *resp_buff_arr;
-	int cur_reading_elt;
-	int cur_writing_elt;
-
-	/* For ap_select */
-	fd_set readers,writers;
-	int client_fd,ic_fd,maxfd;
-	int reading,writing;
+		if (ap_bprintf(ic_buff,"entity\n%ld ",length) < 0){
+			ap_log_reason("error writing to Interchange",r->uri,r);
+			return HTTP_INTERNAL_SERVER_ERROR;
+		}
 
-	ap_hard_timeout( "ic_transfer_response", r );
+		/*
+		 *	read a block of data from the client and send
+		 *	it to the Interchange server, until there
+		 *	is nothing more to read from the client
+		 */
+		while ((len_read = ap_get_client_block(r,buffer,sizeof(buffer))) > 0){
+			ap_reset_timeout(r);
 
-	/* Scan the request response for CGI headers */
-	if ( ap_scan_script_header_err_buff( r, ic_buff, error_buff ) != OK )
-	{
-		ap_log_rerror( APLOG_MARK, APLOG_ERR|APLOG_NOERRNO, r,
-					   "Error while scanning response headers: %s",
-					   error_buff );
+			if (ap_bwrite(ic_buff,buffer,len_read) != len_read){
+				ap_log_reason("error writing client block to Interchange",r->uri,r);
+				return HTTP_INTERNAL_SERVER_ERROR;
+			}
+			ap_reset_timeout(r);
+		}
+		if (len_read < 0){
+			ap_log_reason("error reading block from client",r->uri,r);
+			return HTTP_INTERNAL_SERVER_ERROR;
+		}
 
-		return HTTP_INTERNAL_SERVER_ERROR;
+		/*
+		 *	send an end of line character to Interchange
+		 */
+		if (ap_bputc('\n',ic_buff) < 0){
+			ap_log_reason("error writing to Interchange",r->uri,r);
+			return HTTP_INTERNAL_SERVER_ERROR;
+		}
 	}
 
-	/* Send beggining of the response */
-	ap_reset_timeout( r );
-	ap_send_http_header( r );
-	/* Make sure all headers are flushed */
-	if ( ap_rflush( r ) < 0 ) {
-		ap_log_reason( "error sending headers to client", r->uri, r );
-		return HTTP_INTERNAL_SERVER_ERROR;
-	}
+	/*
+	 *	all data has been sent, so send the "end" marker
+	 */
 	ap_reset_timeout(r);
-
-	/* OK, now turn on non blocking IO */
-	client_buff = r->connection->client;
-	if ( (rc = ap_bnonblock( client_buff, B_WR ) ) != 0 )
-	{
-		ap_log_reason( "error turning non blocking I/O on client",
-					   r->uri, r );
+	if (ap_bputs("end\n",ic_buff) < 0){
+		ap_log_reason("error writing the end marker to Interchange",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
-	if ( (rc = ap_bnonblock( ic_buff, B_RD ) ) != 0 )
-	{
-		ap_log_reason( "error turning non blocking I/O on Interchange",
-					   r->uri, r );
+	if (ap_bflush(ic_buff) < 0){
+		ap_log_reason("error flushing data to Interchange",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
-	ap_bsetflag( ic_buff, B_SAFEREAD, 1 );
 
-	reading = 1, writing = 1;
-	client_fd    = ap_bfileno( client_buff, B_WR );
-	ic_fd		 = ap_bfileno( ic_buff, B_RD );
-	maxfd       = client_fd > ic_fd ? client_fd : ic_fd;
-	maxfd++;
+	ap_kill_timeout(r);
+	return OK;
+}
 
-	/* Allocate array for response */
-	resp_buff_arr = ap_make_array(r->pool, 5, sizeof(ic_response_buffer ) );
-	if ( !resp_buff_arr ) {
-		ap_log_reason( "failed to allocate response buffer", r->uri, r );
+/*
+ *	ic_transfer_response()
+ *	----------------------
+ *	Read the response from the Interchange server
+ *	and relay it to the client
+ */
+static int ic_transfer_response(request_rec *r,BUFF *ic_buff)
+{
+	const char *location;
+	int rc,ic_sock;
+	char sbuf[MAX_STRING_LEN],argsbuffer[HUGE_STRING_LEN];
+
+	/*
+	 *	get the socket we are using to talk to the
+	 *	Interchange server, and wait for Interchange to
+	 *	send us some data
+	 */
+	ic_sock = ap_bfileno(ic_buff,B_RD);
+	rc = ic_select(ic_sock,0,IC_DEFAULT_TIMEOUT,0);
+	if (rc < 0){
+		ap_log_reason("Failed to select the response header",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
-	/* Create the first element */
-	if ( ap_push_array( resp_buff_arr ) == NULL ) {
-		ap_log_reason( "failed to allocate first element", r->uri, r );
+
+	/*
+	 *	check the HTTP header to make sure that it looks valid
+	 */
+	if (ap_scan_script_header_err_buff(r,ic_buff,sbuf)){
+		ap_log_rerror(APLOG_MARK,APLOG_ERR|APLOG_NOERRNO,r,"Malformed header return by Interchange: %s",sbuf);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
-	cur_reading_elt = 0, cur_writing_elt = 0;
-
-	while (1) {
-		int i;
-
-		FD_ZERO(&readers);
-		FD_ZERO(&writers);
-
-		if ( !reading && !writing) {
-			break;
-		}
 
-		if ( reading )
-			FD_SET( ic_fd, &readers );
+	/*
+	 *	check the header for an HTTP redirect request
+	 */
+	location = ap_table_get(r->headers_out,"Location");
+	if (r->status == 200 && location){
+		fd_set sock_set;
 
-		if ( writing )
-			FD_SET(client_fd, &writers);
+		/*
+		 *	check if we need to do an external redirect
+		 */
+		if (*location != '/')
+			return REDIRECT;
 
-		if ( ( rc = ap_select( maxfd, &readers, &writers, NULL, NULL ) ) < 0 )
-		{
-			ap_log_reason( "error in ap_select", r->uri, r );
+		/*
+		 *	we are here because we need to do an internal redirect
+		 *
+		 *	soak up any data from the Interchange socket
+		 */
+		rc = ic_select(ic_sock,0,IC_DEFAULT_TIMEOUT,0);
+		if (rc < 0){
+			ap_log_reason("Failed to select the response text",r->uri,r);
 			return HTTP_INTERNAL_SERVER_ERROR;
 		}
 
-		if ( reading && FD_ISSET( ic_fd, &readers ) )
-		{
-			int read_len,left;
-			ic_response_buffer *resp_buff;
-			char *buff;
-
-			resp_buff = ((ic_response_buffer *)resp_buff_arr->elts);
-			for ( i=0; i< cur_reading_elt; i++)
-				resp_buff++;
-
-			buff = resp_buff->buff;
-			buff += resp_buff->buff_size;
-			left = HUGE_STRING_LEN - resp_buff->buff_size;
-
-			read_len = ap_bread( ic_buff, buff, left );
-			if ( read_len < 0 ) {
-				ap_log_reason( "error while reading Interchange response",
-							   r->uri, r );
-				return HTTP_INTERNAL_SERVER_ERROR;
-			} else if ( read_len == 0 ) {
-				reading = 0;
-			} else {
-				resp_buff->buff_size += read_len;
-				writing = 1; /* Flag to indicate that there is now
-								writing to do */
-
-				if ( resp_buff->buff_size == HUGE_STRING_LEN ) {
-					/* Create a new response buffer in the array */
-					resp_buff =
-						(ic_response_buffer *)ap_push_array(resp_buff_arr);
-					if ( !resp_buff ) {
-						ap_log_reason( "error while allocating "
-									   "response buffer", r->uri, r );
-						return HTTP_INTERNAL_SERVER_ERROR;
-					}
-					cur_reading_elt++;
-				}
-			}
-		}
-		if ( writing && FD_ISSET( client_fd, &writers ) )
-		{
-			int write_len,left;
-			ic_response_buffer *resp_buff;
-			char *buff;
-
-			resp_buff = (ic_response_buffer *)resp_buff_arr->elts;
-			for ( i=0; i< cur_writing_elt; i++)
-				resp_buff++;
-
-			buff = resp_buff->buff;
-			buff += resp_buff->pos;
-			left = resp_buff->buff_size - resp_buff->pos;
-			if ( left > 0 ) {
-				write_len = ap_bwrite( client_buff, buff, left );
-				if ( write_len < 0 ) {
-					ap_log_reason( "error while sending response",
-								   r->uri, r );
-					return HTTP_INTERNAL_SERVER_ERROR;
-				}
-				resp_buff->pos += write_len;
-
-				if ( resp_buff->pos == resp_buff->buff_size ) {
-					if ( ! reading && cur_writing_elt ==
-						 cur_reading_elt )
-					{
-						/* Done */
-						writing = 0;
-					} else if ( resp_buff->pos == HUGE_STRING_LEN )
-					{
-						/* No remaining space in the buffer
-						 */
-						cur_writing_elt++;
-					} else {
-						/*
-						  It seems that all that was read has been
-						  sent, so wait for more data.
-						 */
-						writing = 0;
-					}
-				}
-			} else {
-				writing = 0;
-			}
-		}
-
-		ap_reset_timeout(r);
+		/*
+		 *	soak up any body-text sent by the Interchange server
+		 */
+		ap_soft_timeout("mod_interchange: Interchange read",r);
+		while (ap_bgets(argsbuffer,HUGE_STRING_LEN,ic_buff) > 0)
+			;
+		ap_kill_timeout(r);
+
+		/*
+		 *	always use the GET method for internal redirects
+		 *	also, unset the Content-Length so that nothing
+		 *	else tries to re-read the text we just soaked up
+		 */
+		r->method = ap_pstrdup(r->pool,"GET");
+		r->method_number = M_GET;
+		ap_table_unset(r->headers_in,"Content-Length");
+		ap_internal_redirect(location,r);
+		return OK;
 	}
 
-	/* Push everything to the client */
-	if ( ap_bflush( client_buff ) < 0 ) {
-		ap_log_reason( "error sending response to client", r->uri, r);
+	/*
+	 *	we were not redirected, so send the HTTP headers
+	 *	to the client
+	 */
+	ap_hard_timeout("mod_interchange: Client write",r);
+	ap_send_http_header(r);
+	if (ap_rflush(r) < 0){
+		ap_log_reason("error sending headers to client",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
 
+	/*
+	 *	if Interchange is sending body text (HTML), then
+	 *	relay this to the client
+	 */
+	if (!r->header_only){
+		ap_reset_timeout(r);
+		if ((rc = ap_bnonblock(ic_buff,B_RD)) != 0){
+			ap_log_reason("error turning non blocking I/O on Interchange socket",r->uri,r);
+			return HTTP_INTERNAL_SERVER_ERROR;
+		}
+		ap_bsetflag(ic_buff,B_SAFEREAD,1);
+		if (ap_send_fb(ic_buff,r) <= 0){
+			ap_log_reason("error sending response body to client",r->uri,r);
+			return HTTP_INTERNAL_SERVER_ERROR;
+		}
+	}
 	ap_kill_timeout(r);
 	return OK;
 }
 
-static int
-ic_handler( request_rec *r)
+/*
+ *	ic_handler()
+ *	------------
+ *	module content handler
+ */
+static int ic_handler(request_rec *r)
 {
 	ic_conf_rec *conf_rec;
 	BUFF *ic_buff;
-	int result;
+	int i,rc;
+
+	if (r->method_number == M_OPTIONS){
+		r->allowed |= (1 << M_GET);
+		r->allowed |= (1 << M_PUT);
+		r->allowed |= (1 << M_POST);
+		return DECLINED;
+	}
+
+	if ((rc = ap_setup_client_block(r,REQUEST_CHUNKED_ERROR)) != OK)
+		return rc;
 
-	/* Grab our configuration */
-	conf_rec = (ic_conf_rec *)ap_get_module_config( r->per_dir_config,
-													&interchange_module );
-	if ( ! conf_rec ) {
-		ap_log_reason( "interchange-handler not configured properly",
-					   r->uri, r);
+	/*
+	 *	get our configuration
+	 */
+	conf_rec = (ic_conf_rec *)ap_get_module_config(r->per_dir_config,&interchange_module);
+	if (!conf_rec){
+		ap_log_reason("interchange-handler not configured properly",r->uri,r);
 		return HTTP_INTERNAL_SERVER_ERROR;
 	}
 
-	ic_buff = ic_connect( r, conf_rec );
-	if ( !ic_buff )
+	/*
+	 *	check if the requested URI matches strings
+	 *	in the drop list
+	 */
+	for (i = 0; i < conf_rec->droplist_no; i++){
+		if (strstr(r->uri,conf_rec->droplist[i])){
+			ap_log_reason("interchange-handler match found in the drop list",r->uri,r);
+			ap_log_rerror(APLOG_MARK,APLOG_ERR|APLOG_NOERRNO,r,"Requested URI (%s) matches drop list entry (%s)",r->uri,conf_rec->droplist[i]);
+			return DECLINED;
+		}
+	}
+
+	/*
+	 *	connect to the Interchange server
+	 */
+	ic_buff = ic_connect(r,conf_rec);
+	if (!ic_buff)
 		return HTTP_INTERNAL_SERVER_ERROR;
 
-	result = ic_send_request( r, conf_rec, ic_buff );
-	if ( result != OK )
-		return result;
+	/*
+	 *	send the client's request to Interchange
+	 */
+	rc = ic_send_request(r,conf_rec,ic_buff);
 
-	return ic_transfer_response( r, conf_rec, ic_buff );
+	/*
+	 *	receive the response from the Interchange server
+	 *	and relay that response to the client
+	 */
+	if (rc == OK)
+		rc = ic_transfer_response(r,ic_buff);
+
+	/*
+	 *	close the Interchange socket and return
+	 */
+	ap_bclose(ic_buff);
+	return rc;
 }
 
-/* Our configuration directives */
-static command_rec ic_cmds[] =
-{
-    {
-    "InterchangeServer",			/* directive name */
-    ic_server_cmd,					/* config action routine */
-    NULL,							/* argument to include in call */
-    ACCESS_CONF,					/* where available */
-    TAKE1,							/* arguments */
-    "address of Interchange server"	/* directive description */
-    },
+/*
+ *	the module's configuration directives
+ */
+static command_rec ic_cmds[] ={
+	{
+		"InterchangeServer",	/* directive name */
+		ic_server_cmd,		/* config action routine */
+		NULL,			/* argument to include in call */
+		ACCESS_CONF,		/* where available */
+		TAKE1,			/* arguments */
+		"Address of the primary Interchange server - for use in a <Location> block"
+					/* directive description */
+	},
+	{
+		"InterchangeServerBackup",	/* directive name */
+		ic_serverbackup_cmd,		/* config action routine */
+		NULL,			/* argument to include in call */
+		ACCESS_CONF,		/* where available */
+		TAKE1,			/* arguments */
+		"Address of the backup Interchange server - for use in a <Location> block"
+					/* directive description */
+	},
+	{
+		"ConnectTries",		/* directive name */
+		ic_connecttries_cmd,	/* config action routine */
+		NULL,			/* argument to include in call */
+		ACCESS_CONF,		/* where available */
+		TAKE1,			/* arguments */
+		"The number of connection attempts to make before giving up"
+					/* directive description */
+	},
+	{
+		"ConnectRetryDelay",	/* directive name */
+		ic_connectretrydelay_cmd, /* config action routine */
+		NULL,			/* argument to include in call */
+		ACCESS_CONF,		/* where available */
+		TAKE1,			/* arguments */
+		"The number of connection attempts to make before giving up"
+					/* directive description */
+	},
+	{
+		"DropRequestList",	/* directive name */
+		ic_droprequestlist_cmd,	/* config action routine */
+		NULL,			/* argument to include in call */
+		ACCESS_CONF,		/* where available */
+		ITERATE,		/* arguments */
+		"Drop the URI request if it contains the specified string"
+					/* directive description */
+	},
 	{NULL}
 };
 
-/* Make the name of the content handler known to Apache */
-static handler_rec ic_handlers[] = {
-    {"interchange-handler", ic_handler},
-    {NULL}
+/*
+ *	make the name of the content handler known to Apache
+ */
+static handler_rec ic_handlers[] ={
+	{"interchange-handler",ic_handler},
+	{NULL}
 };
 
-/* Tell Apache what phases of the transaction we handle */
-module MODULE_VAR_EXPORT interchange_module =
-{
-		STANDARD_MODULE_STUFF,
-		NULL,					/* module initializer                 */
-		ic_create_dir_config,	/* per-directory config creator       */
-		NULL,					/* dir config merger                  */
-		NULL,					/* server config creator              */
-		NULL,					/* server config merger               */
-		ic_cmds,				/* command table                      */
-		ic_handlers,			/* [7]  content handlers              */
-		NULL,					/* [2]  URI-to-filename translation   */
-		NULL,					/* [5]  check/validate user_id        */
-		NULL,					/* [6]  check user_id is valid *here* */
-		NULL,					/* [4]  check access by host address  */
-		NULL,					/* [7]  MIME type checker/setter      */
-		NULL,					/* [8]  fixups                        */
-		NULL,					/* [9]  logger                        */
-		NULL,					/* [3]  header parser                 */
-		NULL,					/* process initialization             */
-		NULL,					/* process exit/cleanup               */
-		NULL					/* [1]  post read_request handling    */
+/*
+ *	tell Apache what phases of the transaction we handle
+ */
+module MODULE_VAR_EXPORT interchange_module ={
+	STANDARD_MODULE_STUFF,
+	ic_initialise,		/* module initialiser                 */
+	ic_create_dir_config,	/* per-directory config creator       */
+	NULL,			/* dir config merger                  */
+	NULL,			/* server config creator              */
+	NULL,			/* server config merger               */
+	ic_cmds,		/* command table                      */
+	ic_handlers,		/* [7]  content handlers              */
+	NULL,			/* [2]  URI-to-filename translation   */
+	NULL,			/* [5]  check/validate user_id        */
+	NULL,			/* [6]  check user_id is valid *here* */
+	NULL,			/* [4]  check access by host address  */
+	NULL,			/* [7]  MIME type checker/setter      */
+	NULL,			/* [8]  fixups                        */
+	NULL,			/* [9]  logger                        */
+	NULL,			/* [3]  header parser                 */
+	NULL,			/* process initialization             */
+	NULL,			/* process exit/cleanup               */
+	NULL			/* [1]  post read_request handling    */
 };
+
+/*
+ *	vim:ts=8:sw=8
+ */



1.1.4.2   +481 -54   interchange/dist/src/mod_interchange/mod_interchange.html


rev 1.1.4.2, prev_rev 1.1.4.1
Index: mod_interchange.html
===================================================================
RCS file: /var/cvs/interchange/dist/src/mod_interchange/mod_interchange.html,v
retrieving revision 1.1.4.1
retrieving revision 1.1.4.2
diff -u -r1.1.4.1 -r1.1.4.2
--- mod_interchange.html	3 Apr 2001 08:14:38 -0000	1.1.4.1
+++ mod_interchange.html	25 Jan 2003 22:21:24 -0000	1.1.4.2
@@ -1,56 +1,483 @@
-<HTML>
-<HEAD>
-   <META HTTP-EQUIV="Content-Type" CONTENT="text/html; charset=iso-8859-1">
-   <TITLE>Module mod_interchange</TITLE>
-</HEAD>
-<BODY>
-
-<H1>Module mod_interchange</H1>
-
-<H2>Interchange link module</H2>
-
-<p>This module replaces the <tt>tlink</tt> and <tt>vlink</tt> programs
-that come with <a href="http://developer.akopia.com/">Interchange</a>.</p>
-
-<P>This modules requires Apache 1.3.6 or greater, and works with any
-version of Interchange (back to MiniVend 3.12).</p>
-
-<P>&nbsp;</P>        
-
-<P><A href="#example">Configuration example</A></p>
-
-<H2>Directives</H2>
-
-<ul>
-<li><A href="#server">InterchangeServer</A></li>
-</ul>
-
-<hr>
-<h2>
-<A name="server"></A>InterchangeServer</H2>
-<B>Syntax:</B> InterchangeServer <I>address</I>
-<BR><B>Context:</B> Directory
-<BR><B>Override:</B> None
-<BR><B>Status:</B> Extension
-
-<p>Specifies the way to connect to the Interchange server.</p>
-
-<HR>
-<H2>
-<A NAME="example"></A>Example</H2>
-Here is an example UNIX configuration:
-
-<PRE>&lt;Location /store&gt;
-   SetHandler interchange-handler
-   InterchangeServer /var/run/interchange/socket
-&lt;/Location&gt;</PRE>
-
-and here is an INET example:
-
-<PRE>&lt;Location /store&gt;
-   SetHandler interchange-handler
-   InterchangeServer ic.host.com:7786
-&lt;/Location&gt;</PRE>
-
+<!-- $Id: mod_interchange.html,v 1.1.4.2 2003/01/25 22:21:24 racke Exp $ -->
+<html>
+<head>
+   <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
+   <title>Apache module: mod_interchange (version 1.29)</title>
+</head>
+<body bgcolor="#FFFFFF" text="#000000">
+    <h1>Apache module: mod_interchange (version 1.29)</h1>
+    <h2>Apache link module for Interchange</h2>
+    <p>
+	This module replaces the <i>tlink</i> and <i>vlink</i> programs
+	that come with <a href="http://www.icdevgroup.org/">Interchange</a>.&nbsp;
+	It has been tested with all Interchange versions up to and
+	including 4.9.6 (development).&nbsp;
+	Although this module is known to have worked with MiniVend versions 3
+	and 4, its current compatibility has not been tested.
+    </p>
+    <p>
+	This module has been tested with Apache versions 1.3.6
+	through 1.3.26.&nbsp;
+	<b>Note that this module is not compatible with Apache 2.</b>
+    </p>
+
+    <h2>Contents</h2>
+    <ol>
+	<li>Module Directives:
+	    <ul>
+		<li><a href="#server">InterchangeServer</a></li>
+		<li><a href="#serverbackup">InterchangeServerBackup</a></li>
+		<li><a href="#tries">ConnectTries</a></li>
+		<li><a href="#retrydelay">ConnectRetryDelay</a></li>
+		<li><a href="#droplist">DropRequestList</a></li>
+	    </ul>
+	    <br>
+	</li>
+	<li><a href="#example">Configuration Examples</a></li>
+	<li><a href="#copyright">Copyright and License</a></li>
+    </ol>
+
+    <hr>
+    <h2><a name="server">InterchangeServer</a></h2>
+    <b>Syntax:</b> <code>InterchangeServer <i>address</i></code>
+    <br><b>Context:</b> Location
+    <br><b>Override:</b> None
+    <br><b>Status:</b> Extension
+    <p>
+	Specifies the way Apache should connect to the primary
+	Interchange server.
+    </p>
+
+    <h2><a name="serverbackup">InterchangeServerBackup</a></h2>
+    <b>Syntax:</b> <code>InterchangeServerBackup <i>address</i></code>
+    <br><b>Context:</b> Location
+    <br><b>Override:</b> None
+    <br><b>Status:</b> Extension
+    <p>
+	Specifies the way Apache should connect to the backup
+	Interchange server in the event that the primary server is
+	unavailable for any reason.
+    </p><p>
+	InterchangeServerBackup takes the same arguments as the
+	InterchangeServer directive but should obviously point to a
+	different Interchange server than the primary.&nbsp;
+	The InterchangeServerBackup directive is only of any use if you
+	have multiple Interchange servers configured in a clustered
+	environment.
+    </p>
+
+    <h2><a name="tries">ConnectTries</a></h2>
+    <b>Syntax:</b> <code>ConnectTries <i>number</i></code>
+    <br><b>Context:</b> Location
+    <br><b>Override:</b> None
+    <br><b>Status:</b> Extension
+    <p>
+	Number of connection attempts to make before giving up.&nbsp;
+	The default is 10.
+    </p>
+
+    <h2><a name="retrydelay">ConnectRetryDelay</a></h2>
+    <b>Syntax:</b> <code>ConnectRetryDelay <i>seconds</i></code>
+    <br><b>Context:</b> Location
+    <br><b>Override:</b> None
+    <br><b>Status:</b> Extension
+    <p>
+	Delay, in seconds, between each retry attempt.&nbsp;
+	The default is 2.
+    </p>
+
+    <h2><a name="droplist">DropRequestList</a></h2>
+    <b>Syntax:</b> <code>DropRequestList <i>entry entry entry</i></code>
+    <br><b>Context:</b> Location
+    <br><b>Override:</b> None
+    <br><b>Status:</b> Extension
+    <p>
+	Space-separated list of URI path components to deny access to.&nbsp;
+	Various attacks are made on Microsoft IIS systems and, while they
+	don't affect Apache, they do tend to waste valuable processor time.
+    </p><p>
+	If any of the entries in the list are found anywhere in the requested
+	URI, the request will be dropped with a 404 (not found) error.
+    </p><p>
+	A maximum of 10 entries may be present in the list.&nbsp;
+	Any other entries will be ignored.&nbsp;
+	If you need more than 10 entries, edit the <code>IC_DROPLIST_NO</code>
+	value in <code>mod_interchange.c</code> and recompile the module.&nbsp;
+	See the example below for a common use of this directive.
+    </p>
+
+    <hr>
+    <h2><a name="example">Configuration Examples</a></h2>
+    <p>
+	Note: The Apache <Location> URI path should not contain a dot (.) or
+	any other characters except A-Z, a-z, 0-9 or a hyphen (-), so:
+    </p><p>
+	<code>&nbsp;&nbsp;&nbsp;&nbsp;&lt;<b>Location</b> <i>/shop.name</i>&gt</code>&nbsp; is invalid, whereas:<br>
+	<code>&nbsp;&nbsp;&nbsp;&nbsp;&lt;<b>Location</b> <i>/shop-name</i>&gt</code>&nbsp; is valid.
+    </p><p>
+	Here is an example UNIX-socket configuration:
+    </p>
+    <code>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;Location</b> <i>/shop</i><b>&gt;</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>SetHandler interchange-handler</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>InterchangeServer</b> <i>/opt/interchange/etc/socket</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;/Location&gt;</b><br>
+    </code>
+    <p>
+	Here is an INET-socket example:
+    </p>
+    <code>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;Location</b> <i>/shop</i><b>&gt;</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>SetHandler interchange-handler</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>InterchangeServer</b> <i>localhost</i>:<i>7786</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;/Location&gt;</b><br>
+    </code>
+    <p>
+	UNIX-socket local primary connection and INET-socket remote backup
+	connection:
+    </p>
+    <code>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;Location</b> <i>/shop</i><b>&gt;</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>SetHandler interchange-handler</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>InterchangeServer</b> <i>/opt/interchange/etc/socket</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>InterchangeServerBackup</b> <i>another.server.com</i>:<i>7786</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;/Location&gt;</b><br>
+    </code>
+    <p>
+	Two parameters control what happens when mod_interchange
+	fails to connect to the Interchange server.&nbsp;
+	The most likely reason for a failure to connect is that Interchange
+	is being restarted by the administrator.
+    </p><p>
+	<b>ConnectTries</b> specifies the number of connection attempts
+	to make before giving up.&nbsp;
+	The default is 10.&nbsp;
+	<b>ConnectRetryDelay</b> specifies the delay, in seconds, between each
+	retry attempt.&nbsp;
+	The default is 2.&nbsp;
+	Connection retry example:
+    </p>
+    <code>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;Location</b> <i>/shop</i><b>&gt;</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>SetHandler interchange-handler</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>InterchangeServer</b> <i>localhost</i>:<i>7786</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>ConnectTries</b> <i>10</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>ConnectRetryDelay</b> <i>1</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;/Location&gt;</b><br>
+    </code>
+    <p>
+	If an <b>InterchangeServerBackup</b> directive has been specified
+	then the backup server will be tried immediately after an attempt
+	to contact the primary server fails.&nbsp;
+	The <b>ConnectTries</b> and <b>ConnectRetryDelay</b> paramaters will
+	only come into affect if both the primary and backup Interchange
+	servers are found to be unavailable.
+    </p><p>
+	The <b>DropRequestList</b> allows a list of up to 10 space-separated URI
+	components to be specified.&nbsp;
+	If any of the list entries is found anywhere in the requested URI,
+	the request will be dropped with a 404 (not found) error, without
+	the request being passed to Interchange.&nbsp;
+	This parameter is useful for blocking known Microsoft IIS attacks,
+	such as &quot;Code Red&quot;, so that we don't waste any more time processing
+	these bogus requests than we have to.&nbsp;
+	<b>DropRequestList</b> example:
+    </p>
+    <code>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;Location</b> <i>/shop</i><b>&gt;</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>SetHandler interchange-handler</b><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>InterchangeServer</b> <i>localhost</i>:<i>7786</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<b>DropRequestList</b> <i>/default.ida /x.ida /cmd.exe /root.exe</i><br>
+	&nbsp;&nbsp;&nbsp;&nbsp;<b>&lt;/Location&gt;</b><br>
+    </code>
+
+    <br><hr>
+    <h2><a name="changelog">Change Log</a></h2>
+    <ul>
+	<li>
+	    1.29
+	    (Thu 09 Jan 2003)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Fixed a bug reported by Jeff Dafoe.&nbsp;
+		    The request information enabled Interchange to show the
+		    correct page but prevented it from storing the request in
+		    the session's history.&nbsp;
+		    The problem only showed itself when Interchange's
+		    [history-scan] tag was used.&nbsp;
+		    As almost no page history was saved, [history-scan] sent
+		    the user to the default page (usually index) most of the
+		    time.&nbsp;
+		    This bug seems to have originated in version 1.28.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.28
+	    (Thu 09 Jan 2003)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Fixed a weird bug where empty HTTP variables were being
+		    passed under certain circumstances.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.27
+	    (Wed 27 Nov 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Implemented a proper (automatic) URILevels mechanism and
+		    removed the URILevels configuration directive.&nbsp;
+		    This also fixes a bug, reported by Philip Hempel in the
+		    interchange-users mail list, where [PT] redirects were
+		    not being handled correctly.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.26
+	    (Sun 03 Nov 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added proper support for internal redirects which will
+		    help with the security of "soft product" delivery.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.25
+	    (Sat 02 Nov 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Fixed a bug reported by Jeff Dafoe.&nbsp;
+		    There are some instances where the socket to Interchange
+		    may not be closed upon error.&nbsp;
+		    While I'm reasonably certain that Apache will handle
+		    this for us, it doesn't hurt to ensure that the socket
+		    is closed.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.24
+	    (Mon 31 Oct 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Fixed a bug reported by Shawn Mathews.&nbsp;
+		    The URILevels directive was not taken into account when
+		    munging the PATH_INFO HTTP environment variable.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.23
+	    (Wed 02 Oct 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added the module identification to the Apache version
+		    string so that it shows up in the "Server:" response
+		    header field when Apache is configured to show version
+		    information.&nbsp;
+		    Of course, suitably paranoid system administrators should
+		    configure Apache so that it doesn't release unnecessay
+		    server information.&nbsp;
+		    Any competent adminsitrator should know what module
+		    versions they have anyway. :-)
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.22
+	    (Mon 05 Aug 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Fixed a bug reported by John Young.&nbsp;
+		    Mod_interchange was not decoding entities in the
+		    REQUEST_URI, which caused Interchange searches (scan)
+		    with encoded spaces to fail.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.21
+	    (Mon 01 Apr 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added Support for Solaris 8 with a patch supplied
+		    by John Young.&nbsp;
+		    Apparently Solaris doesn't have the <code>AF_LOCAL</code>,
+		    <code>PF_LOCAL</code> or <code>SUN_LEN</code> macros.&nbsp;
+		    John's patch conditionally <code>#define</code>s the
+		    missing <code>_LOCAL</code> macros as aliases for
+		    <code>AF_UNIX</code> and <code>PF_UNIX</code>, and
+		    conditionally <code>#define</code>s a <code>SUN_LEN</code>
+		    macro.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.20
+	    (Fri 15 Mar 2002)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added the <code>InterchangeServerBackup</code> module
+		    parameter to allow the module to automatically try a
+		    backup Interchange server if the primary is unavailable.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.14
+	    (Wed 26 Sep 2001)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added the <code>DropRequestList</code> module parameter
+		    to stop Interchange from having to waste its time
+		    processing known IIS exploits.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.13
+	    (Wed 22 Aug 2001)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added a retry loop so that connections delay for a while,
+		    instead of failing, while the Interchange server is being
+		    restarted.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.12
+	    (Sun 10 Aug 2001)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added OS/X patch as it doesn't appear to have a typedef
+		    for <code>socklen_t</code>.&nbsp;
+		    The poor Apple <nobr>OS/X</nobr> users must un-comment the OSX line
+		    in the Makefile to the module to compile the definition in.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.11
+	    (Fri 20 Apr 2001)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Added the <code>URILevels</code> parameter to allow for
+		    sites that need to specify <code>&lt;Location&gt;</code>s
+		    that have more than one directory level.&nbsp;
+		    The default <code>URILevel</code> is 1.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.10
+	    (Tue 27 Feb 2001)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Rewrote the <code>ic_send_request()</code> and
+		    <code>ic_transfer_response()</code> functions because
+		    they were giving all sorts of <code>EPIPE</code> errors
+		    when writing data to clients during a concurrent-user
+		    test.&nbsp;
+		    Testing tools used were ab (ApacheBench/1.3) and httperf.&nbsp;
+		    We have now lost the &quot;connreset&quot; errors that
+		    were reported by httperf as well as the associated
+		    &quot;broken pipe&quot; meessages in the Apache error logs.&nbsp;
+		    The module now stands up properly when placed under a heavy
+		    load.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.05
+	    (Mon 29 Jan 2001)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Nothing more than a rename from <code>mod_minivend</code>
+		    to <code>mod_interchange</code>.&nbsp;
+		    (Changed &quot;<code>mv_</code>&quot; function names to
+		    &quot;<code>ic_</code>&quot; etc.)
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.04
+	    (Tue 23 May 2000)
+	    Kevin Walsh &lt;kevin@cursor.biz&gt;<br>
+	    <ul>
+		<li>
+		    Changed to make the module work with Apache name-based
+		    <code>&lt;VirtualHost&gt;</code> entries that have been
+		    configured with the Apache <code>ServerPath</code>
+		    directive.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.03-1i
+	    (Mon 02 Aug 1999)
+	    Francis J. Lacoste &lt;francis.lacoste@iNsu.COM&gt;<br>
+	    <ul>
+		<li>
+		    Last bugfixes.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.02-1i
+	    (Mon 02 Aug 1999)
+	    Francis J. Lacoste &lt;francis.lacoste@iNsu.COM&gt;<br>
+	    <ul>
+		<li>
+		    Fixed spec files bugs.
+		</li>
+	    </ul>
+	    <br>
+	</li><li>
+	    1.00-1i
+	    (Mon 02 Aug 1999)
+	    Francis J. Lacoste &lt;francis.lacoste@iNsu.COM&gt;<br>
+	    <ul>
+		<li>
+		    Packaged for iNs/linux.
+		</li>
+	    </ul>
+	</li>
+    </ul>
+
+    <br><hr>
+    <h2><a name="copyright">Copyright and License</a></h2>
+    <p>
+	Copyright &copy; 1999 Francis J. Lacoste and iNsu Innovations Inc.<br>
+	Copyright &copy; 2000-2003 Cursor Software Limited.<br>
+	All rights reserved.
+    </p><p>
+	This program is free software.&nbsp;
+	You can redistribute it and/or modify it under the terms of the
+	GNU General Public License as published by the Free Software
+	Foundation.&nbsp;
+	You may refer to either version 2 of the License or (at your option)
+	any later version.
+    </p>
 </body>
 </html>



1.1.4.2   +2 -2      interchange/dist/src/mod_interchange/mod_interchange.spec


rev 1.1.4.2, prev_rev 1.1.4.1
Index: mod_interchange.spec
===================================================================
RCS file: /var/cvs/interchange/dist/src/mod_interchange/mod_interchange.spec,v
retrieving revision 1.1.4.1
retrieving revision 1.1.4.2
diff -u -r1.1.4.1 -r1.1.4.2
--- mod_interchange.spec	3 Apr 2001 08:14:38 -0000	1.1.4.1
+++ mod_interchange.spec	25 Jan 2003 22:21:24 -0000	1.1.4.2
@@ -4,8 +4,8 @@
 Release: 1
 Copyright: GPL
 Group: WWW/Applications
-Source: http://ftp.interchange.com/interchange/%{name}-%{version}.tar.gz
-URL: http://developer.akopia.com/
+Source: http://ftp.akopia.com/interchange/%{name}-%{version}.tar.gz
+URL: http://interchange.redhat.com/
 BuildRoot: /var/tmp/%{name}-%{version}-root
 
 #



No                   revision



No                   revision



1.1.4.1   +12 -13    interchange/dist/test/catalog.cfg


rev 1.1.4.1, prev_rev 1.1
Index: catalog.cfg
===================================================================
RCS file: /var/cvs/interchange/dist/test/catalog.cfg,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- catalog.cfg	30 Sep 2000 10:50:04 -0000	1.1
+++ catalog.cfg	25 Jan 2003 22:21:24 -0000	1.1.4.1
@@ -1,4 +1,4 @@
-# MiniVend test catalog
+# Interchange test catalog
 
 Database             products  products.asc  TAB
 Database             products2 products2.asc dbi:mysql:test
@@ -15,11 +15,13 @@
 
 ProductFiles         products  products2
 
-Variable    SERVER_NAME   bill.minivend.com
-Variable    CGI_URL       /cgi-bin/test
-Variable    ORDERS_TO     mike
-Variable    IMAGE_DIR     http://bill.minivend.com/simple/images
-Variable    COMPANY  	 MiniVend Test Catalog
+Variable    SERVER_NAME  bill.minivend.com
+Variable    CGI_URL      /cgi-bin/test
+Variable    ORDERS_TO    interch
+ParseVariables  Yes
+Variable    IMAGE_DIR    http://__SERVER__NAME__/simple/images
+ParseVariables  No
+Variable    COMPANY  	 Interchange Test Catalog
 Variable    ADDRESS  	 123 Your St.
 Variable    CITY     	 Anytown, USA 00000
 Variable    PHONE    	 (513) 555-5555
@@ -29,14 +31,14 @@
 Variable    ENCRYPTOR	 none
 
 PriceField  no_price
-CommonAdjust   pricing:price1,price5,price10:, ;:price:, ==size:pricing, ==color:pricing:common
+CommonAdjust   $ ;pricing:price1,price5,price10,price15,price20,price21,price97..price102:, ;:price:, ==size:pricing, ==color:pricing:common
 
 ##########################################################
 ParseVariables  Yes
 
 MailOrderTo             __ORDERS_TO__
 VendURL                 http://__SERVER_NAME____CGI_URL__
-SecureURL               http://bill__CGI_URL__
+SecureURL               http://__SERVER_NAME____CGI_URL__
 EncryptProgram          __ENCRYPTOR__
 ImageDir                __IMAGE_DIR__/
 
@@ -45,12 +47,8 @@
 
 #Autoload   secure_on
 AlwaysSecure         ord/checkout
-AsciiBackend         etc/backend.asc
 AsciiTrack           etc/tracking.asc
 
-ButtonBars           buttonbar
-
-CheckoutPage         ord/basket
 CreditCardAuto       Yes
 CustomShipping       Yes
 
@@ -63,7 +61,6 @@
 Password        bAWoVkuzphOX.
 
 ReadPermission  group
-ReceiptPage     ord/receipt
 RobotLimit      50
 
 SalesTax        zip,state
@@ -121,3 +118,5 @@
 Locale en_US   currency_symbol	$
 
 Locale en_US   default  1
+
+Pragma  safe_data



No                   revision



No                   revision



1.1.4.2   +1 -1      interchange/dist/test/products/mv_metadata.asc


rev 1.1.4.2, prev_rev 1.1.4.1
Index: mv_metadata.asc
===================================================================
RCS file: /var/cvs/interchange/dist/test/products/mv_metadata.asc,v
retrieving revision 1.1.4.1
retrieving revision 1.1.4.2
diff -u -r1.1.4.1 -r1.1.4.2
--- mv_metadata.asc	12 Oct 2000 12:48:08 -0000	1.1.4.1
+++ mv_metadata.asc	25 Jan 2003 22:21:24 -0000	1.1.4.2
@@ -122,7 +122,7 @@
 variable::Variable::CREDIT_CARDS_ACCEPTED	checkbox							visa=Visa, mc=Mastercard, discover=Discover, amex=American Express					null_to_space					
 userdb::zip	text	10								Postcode			uc word					
 dbconfig::mv_metadata::height	text	4								Select page rows	Number of rows to display at selector page.		digits					
-products::category	combo				products					Category	Enter in box for new category.	category			nullsellect			
+products::category	combo				products					Category	Enter in box for new category.	category			nullselect			
 custview::userdb::email_copy	display							=No, 1=Yes		Payment method								
 userdb::state	text	10								State								
 custview::userdb::dealer	display							=No,1=Yes		Dealer								



1.1.4.1   +12 -11    interchange/dist/test/products/pricing.asc


rev 1.1.4.1, prev_rev 1.1
Index: pricing.asc
===================================================================
RCS file: /var/cvs/interchange/dist/test/products/pricing.asc,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- pricing.asc	30 Sep 2000 10:50:05 -0000	1.1
+++ pricing.asc	25 Jan 2003 22:21:24 -0000	1.1.4.1
@@ -1,11 +1,12 @@
-sku	price	XL	S	common	price1	price5	price10
-00-0011	price data ok					500	250
-00-0011a	50			45		35	30
-00-343	400			200		50	20
-19-202	400			200		50	20
-21-221	400			200		50	20
-99-102		2	-0.50		12	9	8
-34-101	400			200		50	20
-00-341	400			200		50	20
-red		1	-0.50	-1.00		9	8
-00-342	400			200		50	20
+sku	price	XL	S	common	price1	price5	price10	price15	price20	price21	price98	price102
+00-0011	price data ok					500	250					
+00-0011a	50			45		35	30					
+00-343	400			200		50	20					
+19-202	400			200		50	20					
+21-221	400			200		50	20					
+99-102		2	-0.50		12	9	8					
+34-101	400			200		50	20					
+00-341	400			200		50	20					
+red		1	-0.50	-1.00		9	8					
+00-342	400			200		50	20					
+93-111	85.00				80.00	72.50			69.95		67.25	65



1.1.4.1   +326 -324  interchange/dist/test/products/tests.asc


rev 1.1.4.1, prev_rev 1.1
Index: tests.asc
===================================================================
RCS file: /var/cvs/interchange/dist/test/products/tests.asc,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- tests.asc	30 Sep 2000 10:50:05 -0000	1.1
+++ tests.asc	25 Jan 2003 22:21:24 -0000	1.1.4.1
@@ -119,108 +119,111 @@
 %%%
 000009
 %%
-<A MV=page MV.SEND=1 MV.HREF="test" HREF="not_here_I_hope.html">Try new tag style</A><BR>
+[try]
+	[calc] 2 / 0 [/calc]
+[/try]
+[catch] There was an error -- $@ [else] No error[/else][/catch]
 %%
-test(\.html)?[?"]
+There was an error
 %%
-
+No error
 %%
 
 %%
-HTML-style tag
+Try/catch on error
 %%%
 000010
 %%
-<A MV=area MV.HREF="test" TARGET=top HREF="not_here_I_hope.html">Try new tag style, insert</A><BR>
+[try]
+	[calc] 1/1; [/calc]
+[/try]
+[catch] There was an error -- $@ [else] No error[/else][/catch]
 %%
-test(\.html)?[?"]
+No error
 %%
-
+There was an error
 %%
 
 %%
-
+Try/catch no error
 %%%
 000011
 %%
-<A MV=area MV.SEND=1 MV.HREF="test" MV.NOREPLACE=1 TARGET=top HREF="HERE_I_HOPE.html">Try new tag style, no replace, should show up as 404/undercon if traveled </A><BR>
+[filter lc]UPPERCASE[/filter]
 %%
-HERE_I_HOPE
+^[a-z\s]+$
 %%
-
+[A-Z]
 %%
 
 %%
-
+Lowercase filter
 %%%
 000012
 %%
-<A MV=area MV.HREF="test" MV.NOINSERT=1 TARGET=top HREF="HERE_I_HOPE.html"> <<-- Should be no tag, just URL
+[filter uc]lowercase[/filter]
 %%
-test[^"]*$
+^[A-Z\s]+$
 %%
-
+[a-z]
 %%
 
 %%
-
+Uppercase filter
 %%%
 000013
 %%
-<A MV=URLD href="[value%20name=testpage%20set=test]">Should be a another link to this page</A><BR>
+[filter digits_dot]Abc 9.8[/filter]
 %%
-test[^\]"]*">
+^[\d.]+$
 %%
-
+[^\d.]
 %%
 
 %%
-
+Digits/dot filter
 %%%
 000014
 %%
-<A MV="value testpage" MV.SEND=1 MV.APPEND=1 MV.URLD=1 MV.INTERPOLATE=1 href="[value name=testpage set=test]"> <== Should be "test" in a link</A><BR>
+[filter entities]<A HREF=this.html>[itl tag][/filter]
 %%
->\s*test\s*<
+&lt;.*&gt;.*&#91
 %%
-
+[<>\[]
 %%
 
 %%
-
+Entities filter
 %%%
 000015
 %%
-Should be test ==> <A MV="value testpage" MV.PREPEND=1 MV.INTERPOLATE=1 href="[value name=testpage set=test]"> and a link </A>
+[calc]$CGI->{something} = '[' . "the value]"; return; [/calc][cgi something]
 %%
-test.*<.*>.*<
+&#91;the value]
 %%
-
+\[
 %%
 
 %%
-
+CGI blocking left square bracket
 %%%
 000016
 %%
-<FORM MV=process ACTION="test.action">
+[calc]$Values->{something} = '[' . "the value]"; return; [/calc][value something]
 %%
-ACTION="[^"]*process[?"]
+&#91;the value]
 %%
-
+\[
 %%
 
 %%
-HTML-style process
+Value blocking left square bracket
 %%%
 000017
 %%
-<SELECT MV="loop" MV.ARG="1 2 3">
-
-<OPTION> [loop-code]
-</SELECT>
+[area form=auto abc=def ghi=jkl]
 %%
-<OPTION>\s*1\s*<OPTION>\s*2
+abc=def.ghi=jkl|ghi=jkl.abc=def
 %%
 
 %%
@@ -230,146 +233,108 @@
 %%%
 000018
 %%
-<TABLE BORDER=1>
-<TR MV=loop MV.ARG="1 2 3">
-<TD>[loop-code]</TD>
-<TD>[loop-code]</TD>
-</TR>
-</table>
+[set foo]bar[/set][scratchd foo][scratch foo]
 %%
-<TD>1<.TD>\s*<TD>1<.TD>\s*<.[tT][rR]>\s*<TR>\s*<TD>2
+bar
 %%
-
+barbar
 %%
 
 %%
-
+Scratchd tag
 %%%
 000019
 %%
-
-<U>Loop with rowfix</U><BR>
-<TABLE BORDER=1>
-<TR>
-<TD MV=loop MV.ARG="1 2 3" MV.ROWFIX=1>[loop-code]</TD>
-<TD>[loop-code]</TD>
-</TR>
-</table>
+[fly-list 00-0011][item-description][/fly-list]
 %%
-(?i:<TD>1<.TD>\s*<TD>1<.TD>\s*<.[tT][rR]>\s*<TR>\s*<TD>2)
+MONA LISA
 %%
 
 %%
 
 %%
-
+Fly-list tag
 %%%
 000020
 %%
-<U>Tag each</U><BR>
-<TABLE BORDER=1>
-<TR MV="tag each products" MV.SEND=1>
-<TD>[loop-code]</TD>
-<TD>[loop-field title]</TD>
-</TR>
-</table>
+[sql query="select artist from products where category like 'Americana'"][sql-param artist] [/sql]
 %%
-<TD>00-0011</TD>
+Grant Wood The Art Store Jean Langan
 %%
 
 %%
 
 %%
-
+[sql]  and [sql-param]
 %%%
 000021
 %%
-
-<P>
-<U>Tag each with URLDECODE</U><BR>
-<TABLE BORDER=1>
-<TR MV="tag each products">
-<TD>[loop-code]</TD>
-<TD>[loop-field%20title]</TD>
-<TD><IMG HEIGHT=20 WIDTH=20 SRC="[loop-field%20image]" MV.URL=1></TD>
-</TR>
-</table>
+[sql query="select * from products where category like 'Americana'"][sql-field artist] [/sql]
 %%
-Mona Lisa
+Grant Wood The Art Store Jean Langan
 %%
 
 %%
 
 %%
-
+[sql]  and [sql-field]
 %%%
 000022
 %%
-<U>If table</U><BR>
-<TABLE BORDER=1>
-<TR MV="if value nevairbe">
-<TD>ERROR</TD>
-<TD>row</TD>
-</TR>
-<TR MV="[elsif !value nevairbe]">
-<TD>elsif</TD>
-<TD>should be only row</TD>
-</TR>
-<TR MV="else">
-<TD>ERROR</TD>
-<TD>row</TD>
-</TR>
-</table>
-%%
-only
+[calc] $Carts->{main} = [{
+							code => 'onfly', mv_price => 5,
+							description => 'Zum description',
+							quantity => 1,
+						}]; return;[/calc]
+[item-list][item-description][/item-list]
 %%
-ERROR
+Zum descrip
 %%
 
 %%
 
+%%
+On-the-fly part description
 %%%
 000023
 %%
-<U>If table, no lookahead</U><BR>
-<TABLE BORDER=1>
-<TR MV="if value nevairbe" mv.nolook=1>
-<TD>ERROR</TD>
-<TD>row</TD>
-</TR>
-<TR MV="[elsif value nevairbe2]">
-<TD>elsif</TD>
-<TD>This should be row one</TD>
-</TR>
-<TR MV="else">
-<TD>else</TD>
-<TD>This should be row two and final</TD>
-</TR>
-</table>
+[calc] $Carts->{main} = [{
+							code => 'onfly',
+							mv_price => 5,
+							description => 'Zum description',
+							quantity => 1,
+							foo => 'bar',
+						}]; return;[/calc]
+[item-list][item-field foo][/item-list]
 %%
-row.one[\S\s]*two and final
-%%
-ERROR
+bar
 %%
 
 %%
 
+%%
+On-the-fly arbitrary fields
 %%%
 000024
 %%
-<P>
-<U>replaceHTML</U>
-<PRE MV="calc"> return 'should      be     normally        spaced.'</PRE>
-<XMP MV="calc"> return 'should      be     normally        spaced.'</XMP>
-<DEL MV="calc"> return 'should      be     normally        spaced.'</DEL>
-%%
-normally
+[calc] $Carts->{main} = [{
+							code => 'onfly',
+							mv_price => 5,
+							description => 'Zum description',
+							foo => 'bar',
+							quantity => 1,
+						}];
+						$Config->{OnFly} = 1;
+						return;[/calc]
+[item-list][item-price][/item-list]
 %%
-(DEL|XMP|PRE)
+5\.00
 %%
 
 %%
 
+%%
+On-the-fly pricing (requires $ in CommonAdjust)
 %%%
 000025
 %%
@@ -515,9 +480,9 @@
 %%%
 000036
 %%
-[value name=var_name set="A value with stuff in't" hide=1] [selected var_name a value with stuff in't]
+[value name=var_name set="A value with stuff in't" hide=1] [selected var_name a value with stuff in't] [selected name=var_name value="a value with stuff in't"]
 %%
-SELECTED
+SELECTED\s+SELECTED
 %%
 
 %%
@@ -587,47 +552,47 @@
 %%%
 000042
 %%
-[value name=var_name set=val hide=1]<INPUT MV="checked var_name val" NAME=junk>
+[calc] q{[read-cookie MV_SESSION_ID]} =~ /^$Session->{id}/ ; [/calc]
 %%
-CHECKED
+^1$
 %%
 
 %%
 
 %%
-
+Read-cookie tag
 %%%
 000043
 %%
-[value name=var_name set=off hide=1]<INPUT MV="checked var_name val" NAME=junk>
+[scratch fooer][tmp fooer]barer[/tmp][scratch fooer]
 %%
-
+barer$
 %%
-CHECKED
+barerbarer
 %%
 
 %%
-
+tmp tag, second click tests
 %%%
 000044
 %%
-[value name=var_name set=val hide=1]<OPTION MV="selected var_name val" VALUE=val>
+works on second click: [set-cookie name=WORKS_ON_SECOND_CLICK value="testfoo"][read-cookie WORKS_ON_SECOND_CLICK]
 %%
-SELECTED
+testfoo
 %%
 
 %%
 
 %%
-
+Set cookie, works on second click
 %%%
 000045
 %%
-[value name=var_name set=off hide=1]<OPTION MV="selected var_name val" NAME=junk>
+[scratch foobaby][tmpn foobaby][cgi whatever][/tmpn][scratch foobaby]
 %%
-
+.cgi whatever
 %%
-SELECTED
+cgi.*cgi
 %%
 
 %%
@@ -1288,11 +1253,11 @@
 %%%
 000086
 %%
-[if validcc 5959595959595959 mc 12/02]OK[else]ERROR[/else][/if] 1.
-[if validcc 5959595959595958 mc 12/02]ERROR[else]OK[/else][/if] 2.
+[if validcc 5959595959595959 mc 12/08]OK[else]ERROR[/else][/if] 1.
+[if validcc 5959595959595958 mc 12/08]ERROR[else]OK[/else][/if] 2.
 [if validcc 5959595959595959 mc 12/94]ERROR[else]OK[/else][/if] 3.
-[if type=validcc term=5959595959595959 op="mc" comp=12/02]OK[else]ERROR[/else][/if] 1.
-[if type=validcc term=5959595959595958 op=mc comp=12/02]ERROR[else]OK[/else][/if] 2.
+[if type=validcc term=5959595959595959 op="mc" comp=12/08]OK[else]ERROR[/else][/if] 1.
+[if type=validcc term=5959595959595958 op=mc comp=12/08]ERROR[else]OK[/else][/if] 2.
 [if type=validcc term=5959595959595959 op=mc comp=12/94]ERROR[else]OK[/else][/if] 3.
 %%
 OK
@@ -1601,7 +1566,7 @@
 %%
 [perl]$Carts->{main} = [ { qw/code 00-0011 quantity 1 foo bar / } ]; return '';[/perl]
 [cart main]
-Quantity name: [item-list] [quantity-name] [/item-list]
+Quantity name: [item-list] [quantity_name] [/item-list]
 %%
 quantity0
 %%
@@ -1940,110 +1905,147 @@
 %%
 Commify filter, filter args.
 %%%
-999999
-%%
-[the test] [perl]
-# Make this come out right
-return 'The expected result as a regex.';
-[/perl]
-%%
-The expected result as a regex.
-%%
-The NOT expected result.
+000128
 %%
+[perl]
+    $MVSAFE::Safe = 1;
+	    my $hash = { hash => { key => 'OK' } };
 
-%%
-Skeletion test.
-%%%
-999999
-%%
-[the test] [perl]
-# Make this come out right
-return 'The expected result as a regex.';
+		my $text = <<EOF;
+{key2 ERROR}
+{key2?}ERROR{/key2?}
+{key:}ERROR{/key:}
+{key|ERROR}
+{key2|OK}
+{key2:}OK{/key2:}
+{key OK}
+{key?}OK{/key?}
+EOF
+		return $Tag->attr_list($hash, $text);
 [/perl]
 %%
-The expected result as a regex.
+^\s*OK\s+OK\s+OK\s+OK\s+\OK\s*$
 %%
-The NOT expected result.
+ERROR
 %%
 
 %%
-Skeletion test.
+attr_list test
 %%%
-999999
+000129
 %%
-[the test] [perl]
-# Make this come out right
-return 'The expected result as a regex.';
-[/perl]
+[assign clear=1]
+[value name=mv_shipmode set=1 hide=1]
+[value name=mv_handling set=1 hide=1]
+[calc] $Carts->{main} = [ { code => '99-102', quantity => 1 } ]; return; [/calc]
+[tmp tmp_subtotal][subtotal noformat=1][/tmp]
+[assign handling="5"]
+[assign salestax="0.50"]
+[assign shipping="4"]
+[calc]
+	my $total = $Scratch->{tmp_subtotal} + 9.50;
+	my $realtotal = q{[total-cost noformat=1]};
+	return 'OK' if $total == $realtotal;
+	return "ERROR total=$total != real=$realtotal";
+[/calc]
+[assign subtotal=100]
+[total-cost noformat=1] [salestax noformat=1] [shipping noformat=1] [handling noformat=1]
+[assign clear=1]
+[calc] $Carts->{main} = []; return; [/calc]
 %%
-The expected result as a regex.
+OK\s+109.50*\s+0*.50*\s+4\s+5
 %%
-The NOT expected result.
+ERROR
 %%
 
 %%
-Skeletion test.
+Test for assign tag's effects on the cart.
 %%%
-999999
+000130
 %%
-[the test] [perl]
-# Make this come out right
-return 'The expected result as a regex.';
-[/perl]
+Set: [error name=junk set="An error"]
+Test: [error all=1 keep=1]
+Show_delete: [error all=1 show_error=1]
+Should_be_blank:[error all=1]
 %%
-The expected result as a regex.
+(?x)
+	Set:\s*1
+	\s+
+	Test:\s+1
+	\s+
+	Show_delete:\s+ An.error
+	\s+
+	Should_be_blank:\s*$
 %%
-The NOT expected result.
+0
 %%
 
 %%
-Skeletion test.
+error tag test
 %%%
-999999
+000131
 %%
-[the test] [perl]
-# Make this come out right
-return 'The expected result as a regex.';
-[/perl]
+[value name=something set=OK hide=1]
+[either][value something][or]ERROR[/either]
+[value name=something set="" hide=1]
+[either][value something][or]OK[/either]
+[value name=something set=" " hide=1]
+[either][value something][or]OK[/either]
 %%
-The expected result as a regex.
+OK\s+OK\s+OK
 %%
-The NOT expected result.
+ERROR
 %%
 
 %%
-Skeletion test.
+Test of [item-accessories attribute]
 %%%
-999999
+000132
 %%
-[the test] [perl]
-# Make this come out right
-return 'The expected result as a regex.';
+[perl]
+	$Carts->{main} = [ { code => '99-102', quantity => 1, size => 'S' } ];
+	return;
 [/perl]
+[item-list][item-accessories size][item-accessories size, value][/item-list]
 %%
-The expected result as a regex.
+"S" SELECTED>Small.*S\s*$
 %%
-The NOT expected result.
+accessories
 %%
 
 %%
-Skeletion test.
+accessories tag test
 %%%
-999999
+000133
 %%
-[the test] [perl]
-# Make this come out right
-return 'The expected result as a regex.';
+[perl]
+$Carts->{main} = [
+	{ code => '93-111', quantity => 1000, },
+	{ code => '93-111', quantity => 102, },
+	{ code => '93-111', quantity => 100, },
+	{ code => '93-111', quantity => 98, },
+	{ code => '93-111', quantity => 21, },
+	{ code => '93-111', quantity => 20, },
+	{ code => '93-111', quantity => 15, },
+	{ code => '93-111', quantity => 10, },
+	{ code => '93-111', quantity => 9, },
+	{ code => '93-111', quantity => 5, },
+	{ code => '93-111', quantity => 4, },
+	{ code => '93-111', quantity => 1, },
+	{ code => '00-342', quantity => 2, },
+	{ code => '00-0011a', quantity => 1, },
+];
+return;
 [/perl]
+:[item-list main][item-subtotal noformat=1] [/item-list]:
 %%
-The expected result as a regex.
+:65000 6630 6725 6590\.5 1468\.95 1399 1087\.5 725 652\.5 362\.5 320 80 40000000 1000 :
 %%
-The NOT expected result.
+
 %%
 
 %%
-Skeletion test.
+sparse quantity pricing check (introduced in Interchange 4.9.7)
 %%%
 999999
 %%
@@ -2058,7 +2060,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2073,7 +2075,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2088,7 +2090,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2103,7 +2105,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2118,7 +2120,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2133,7 +2135,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2148,7 +2150,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2163,7 +2165,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2178,7 +2180,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2193,7 +2195,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2208,7 +2210,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2223,7 +2225,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2238,7 +2240,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2253,7 +2255,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2268,7 +2270,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2283,7 +2285,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2298,7 +2300,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2313,7 +2315,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2328,7 +2330,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2343,7 +2345,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2358,7 +2360,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2373,7 +2375,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2388,7 +2390,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2403,7 +2405,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2418,7 +2420,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2433,7 +2435,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2448,7 +2450,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2463,7 +2465,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2478,7 +2480,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2493,7 +2495,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2508,7 +2510,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2523,7 +2525,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2538,7 +2540,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2553,7 +2555,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2568,7 +2570,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2583,7 +2585,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2598,7 +2600,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2613,7 +2615,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2628,7 +2630,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2643,7 +2645,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2658,7 +2660,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2673,7 +2675,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2688,7 +2690,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2703,7 +2705,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2718,7 +2720,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2733,7 +2735,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2748,7 +2750,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2763,7 +2765,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2778,7 +2780,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2793,7 +2795,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2808,7 +2810,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2823,7 +2825,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2838,7 +2840,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2853,7 +2855,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2868,7 +2870,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2883,7 +2885,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2898,7 +2900,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2913,7 +2915,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2928,7 +2930,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2943,7 +2945,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2958,7 +2960,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2973,7 +2975,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -2988,7 +2990,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3003,7 +3005,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3018,7 +3020,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3033,7 +3035,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3048,7 +3050,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3063,7 +3065,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3078,7 +3080,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3093,7 +3095,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3108,7 +3110,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3123,7 +3125,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3138,7 +3140,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3153,7 +3155,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3168,7 +3170,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3183,7 +3185,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3198,7 +3200,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3213,7 +3215,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3228,7 +3230,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3243,7 +3245,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3258,7 +3260,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3273,7 +3275,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3288,7 +3290,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3303,7 +3305,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3318,7 +3320,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3333,7 +3335,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3348,7 +3350,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3363,7 +3365,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3378,7 +3380,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3393,7 +3395,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3408,7 +3410,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3423,7 +3425,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3438,7 +3440,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3453,7 +3455,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3468,7 +3470,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3483,7 +3485,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3498,7 +3500,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3513,7 +3515,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3528,7 +3530,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3543,7 +3545,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3558,7 +3560,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3573,7 +3575,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3588,7 +3590,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3603,7 +3605,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3618,7 +3620,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3633,7 +3635,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3648,7 +3650,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3663,7 +3665,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3678,7 +3680,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3693,7 +3695,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3708,7 +3710,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3723,7 +3725,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3738,7 +3740,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3753,7 +3755,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3768,7 +3770,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3783,7 +3785,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3798,7 +3800,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3813,7 +3815,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3828,7 +3830,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3843,7 +3845,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3858,7 +3860,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3873,7 +3875,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3888,7 +3890,7 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.
 %%%
 999999
 %%
@@ -3903,4 +3905,4 @@
 %%
 
 %%
-Skeletion test.
+Skeleton test.



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/eg/gpg_display


rev 1.1.2.1, prev_rev 1.1
Index: gpg_display
===================================================================
RCS file: /var/cvs/interchange/eg/gpg_display,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



1.2.4.1   +0 -0      interchange/eg/reset_order_number


rev 1.2.4.1, prev_rev 1.2
Index: reset_order_number
===================================================================
RCS file: /var/cvs/interchange/eg/reset_order_number,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1



1.1.2.1   +0 -0      interchange/eg/survey_graph.tag


rev 1.1.2.1, prev_rev 1.1
Index: survey_graph.tag
===================================================================
RCS file: /var/cvs/interchange/eg/survey_graph.tag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.7.2.1   +1 -1      interchange/eg/te


rev 2.7.2.1, prev_rev 2.7
Index: te
===================================================================
RCS file: /var/cvs/interchange/eg/te,v
retrieving revision 2.7
retrieving revision 2.7.2.1
diff -u -r2.7 -r2.7.2.1
--- te	26 Nov 2002 15:21:56 -0000	2.7
+++ te	25 Jan 2003 22:21:24 -0000	2.7.2.1
@@ -84,7 +84,7 @@
 
 =head1 VERSION
 
-$Id: te,v 2.7 2002/11/26 15:21:56 jon Exp $
+$Id: te,v 2.7.2.1 2003/01/25 22:21:24 racke Exp $
 
 =head1 CHANGELOG
 



No                   revision



No                   revision



1.1.2.3   +33 -16    interchange/eg/globalsub/authorizenet


rev 1.1.2.3, prev_rev 1.1.2.2
Index: authorizenet
===================================================================
RCS file: /var/cvs/interchange/eg/globalsub/authorizenet,v
retrieving revision 1.1.2.2
retrieving revision 1.1.2.3
diff -u -r1.1.2.2 -r1.1.2.3
--- authorizenet	3 Feb 2001 10:56:04 -0000	1.1.2.2
+++ authorizenet	25 Jan 2003 22:21:25 -0000	1.1.2.3
@@ -9,6 +9,9 @@
 
 # Edited only for references to Minivend, changed to Interchange
 # by Mike Heins. Thanks, guys!
+
+# Patches for AUTH_CAPTURE and VOID support contributed by
+# nferrari@ccsc.com (Nelson H Ferrari)
  
 Variable AUTHORIZENET_HELP <<EOV
  
@@ -24,6 +27,9 @@
  Variable MV_PAYMENT_SECRET  YourAuthorizeNetPassword 
  Variable MV_PAYMENT_MODE    custom authorizenet 
  Variable MV_PAYMENT_REFERER A valid referering url (match this with your setting on secure.authorize.net 
+
+ # If planning to do AUTH_ONLY or other with special admin page
+ Variable MV_PAYMENT_REMAP order_id=mv_order_id auth_code=mv_auth_code
   
  3. Make sure CreditCardAuto is off (default in Interchange demos) 
  
@@ -77,15 +83,18 @@
                         $actual{mv_credit_card_exp_month}, 
                         $actual{mv_credit_card_exp_year};                     
                          
-	 $actual{cyber_mode} = 'AUTH_CAPTURE' 
+	# Using mv_payment_mode for compatibility with older versions, probably not
+	# necessary.
+	$actual{cyber_mode} = $actual{mv_payment_mode} || 'AUTH_CAPTURE'
         unless $actual{cyber_mode}; 
-	 
+
 	my %type_map = ( 
 		mauth_capture 			=>	'AUTH_CAPTURE', 
 		mauthonly				=>	'AUTH_ONLY', 
 		CAPTURE_ONLY			=>  'CAPTURE_ONLY', 
 		CREDIT					=>	'CREDIT', 
 		VOID					=>	'VOID', 
+		AUTH_ONLY				=>	'AUTH_ONLY',
 		PRIOR_AUTH_CAPTURE		=>	'PRIOR_AUTH_CAPTURE', 
  
 	);                        
@@ -109,24 +118,27 @@
  
     # $mon is the month index where Jan=0 and Dec=11, so we use 
     # $mon+1 to get the more familiar Jan=1 and Dec=12 
-    $orderID = sprintf("%02d%02d%02d%02d%02d%05d%s", 
-            $year + 1900,$mon + 1,$mday,$hour,$min,$Vend::SessionName); 
+    $orderID = sprintf("%04d%02d%02d%02d%02d%05d%s", 
+            $year + 1900,$mon + 1,$mday,$hour,$min,$$,$Vend::SessionName); 
              
     my %query = ( 
+#                    x_Test_Request	=> $::Variable->{MV_PAYMENT_TEST},
                     x_Card_Num		=> $actual{mv_credit_card_number}, 
-                    x_First_Name        => $actual{b_fname}, 
-                    x_Last_Name         => $actual{b_lname},
-                    x_Address           => $actual{address}, 
-                    x_City              => $actual{b_city}, 
-                    x_State             => $actual{b_state}, 
-                    x_Zip		=> $actual{zip},
-                    x_Type		=> $actual{mv_payment_mode}, 
+                    x_First_Name    => $actual{b_fname}, 
+                    x_Last_Name     => $actual{b_lname},
+                    x_Address       => $actual{b_address}, 
+                    x_City          => $actual{b_city}, 
+                    x_State         => $actual{b_state}, 
+                    x_Zip			=> $actual{b_zip},
+					x_Type			=> $actual{cyber_mode},
                     x_Amount    	=> $amount, 
                     x_Exp_Date  	=> $exp,
                     x_Method    	=> 'CC',
-                    x_Invoice_Num       => $actual{mv_order_number},
-#                    x_Company           => $actual{company},
-#                    x_Phone             => $actaul{day_phone},  
+					x_Trans_ID		=> $actual{order_id},
+					x_Auth_Code		=> $actual{auth_code},
+                    x_Invoice_Num   => $actual{mv_order_number},
+#                    x_Company      => $actual{company},
+#                    x_Phone        => $actaul{day_phone},  
                     x_Password  	=> $secret, 
                     x_Login     	=> $user, 
                     x_Version   	=> '3.0', 
@@ -186,14 +198,18 @@
     	$avs_code, 
     	$trans_id) = split (/,/,$page); 
     	 
-#::logError(qq{authorizenet response_reason_text=$response_reason_text response_code: $response_code});    	 
+::logError(qq{authorizenet response_reason_text=$response_reason_text response_code: $response_code});    	 
  
     my %result; 
     if ($response_code == 1) { 
     	$result{MStatus} = 'success'; 
-    	$result{'order-id'} = 1; # ? Why this this set to 1? -mark 
+    	# order-id and auth_code are set to 0 if Authorize.net in test mode.
+		# Order.pm interprets order-id == 0 as authorization error.
+		$result{'order-id'} = $trans_id || 1;
+		$result{'auth_code'} = $auth_code;
     } else { 
     	$result{MStatus} = 'failure'; 
+    	$Vend::Session->{MStatus} = 'failure'; 
  
 		# NOTE: A lot more AVS codes could be checked for here.  
     	if ($avs_code eq 'N') { 
@@ -204,6 +220,7 @@
 					$response_reason_text,
 					);
     	} 
+		$Vend::Session->{payment_error} = $result{MErrMsg};
     } 
      
     return (%result); 



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/eg/globalsub/ccvs


rev 2.0.4.1, prev_rev 2.0
Index: ccvs
===================================================================
RCS file: /var/cvs/interchange/eg/globalsub/ccvs,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/eg/globalsub/test_card


rev 2.0.4.1, prev_rev 2.0
Index: test_card
===================================================================
RCS file: /var/cvs/interchange/eg/globalsub/test_card,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



1.2.4.1   +0 -0      interchange/eg/news_feature/README


rev 1.2.4.1, prev_rev 1.2
Index: README
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/README,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1



No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/eg/news_feature/dbconf/default_db/news.dbm


rev 1.1.4.1, prev_rev 1.1
Index: news.dbm
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/dbconf/default_db/news.dbm,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1



No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/eg/news_feature/dbconf/mysql/news.mysql


rev 1.1.4.1, prev_rev 1.1
Index: news.mysql
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/dbconf/mysql/news.mysql,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1



No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/eg/news_feature/dbconf/oracle/news.ora


rev 1.1.4.1, prev_rev 1.1
Index: news.ora
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/dbconf/oracle/news.ora,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1



No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/eg/news_feature/dbconf/pgsql/news.pgsql


rev 1.1.4.1, prev_rev 1.1
Index: news.pgsql
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/dbconf/pgsql/news.pgsql,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1



No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/eg/news_feature/pages/news.html


rev 1.1.4.1, prev_rev 1.1
Index: news.html
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/pages/news.html,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/eg/news_feature/products/news.txt


rev 1.2.2.1, prev_rev 1.2
Index: news.txt
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/products/news.txt,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



No                   revision



No                   revision



1.1.4.1   +0 -0      interchange/eg/news_feature/templates/components/news


rev 1.1.4.1, prev_rev 1.1
Index: news
===================================================================
RCS file: /var/cvs/interchange/eg/news_feature/templates/components/news,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1



No                   revision



No                   revision



1.1.2.1   +2 -2      interchange/extensions/Interchange.pm


rev 1.1.2.1, prev_rev 1.1
Index: Interchange.pm
===================================================================
RCS file: /var/cvs/interchange/extensions/Interchange.pm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- Interchange.pm	23 Jul 2002 17:45:21 -0000	1.1
+++ Interchange.pm	25 Jan 2003 22:21:25 -0000	1.1.2.1
@@ -1,6 +1,6 @@
 # Interchange.pm - Interchange access for Perl scripts
 #
-# $Id: Interchange.pm,v 1.1 2002/07/23 17:45:21 jon Exp $
+# $Id: Interchange.pm,v 1.1.2.1 2003/01/25 22:21:25 racke Exp $
 # 
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -30,7 +30,7 @@
 use strict;
 use Fcntl;
 use vars qw($VERSION @EXPORT @EXPORT_OK);
-$VERSION = substr(q$Revision: 1.1 $, 10);
+$VERSION = substr(q$Revision: 1.1.2.1 $, 10);
 
 BEGIN {
 	require 5.005;



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/extensions/ECML/ecml.coretag


rev 1.1.2.1, prev_rev 1.1
Index: ecml.coretag
===================================================================
RCS file: /var/cvs/interchange/extensions/ECML/ecml.coretag,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.1.2.1   +1 -1      interchange/extensions/ECML/Vend/ECML.pm


rev 1.1.2.1, prev_rev 1.1
Index: ECML.pm
===================================================================
RCS file: /var/cvs/interchange/extensions/ECML/Vend/ECML.pm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- ECML.pm	18 Feb 2002 01:30:40 -0000	1.1
+++ ECML.pm	25 Jan 2003 22:21:25 -0000	1.1.2.1
@@ -1,6 +1,6 @@
 # Vend::ECML - map Interchange forms/userdb to ECML checkout
 #
-# $Id: ECML.pm,v 1.1 2002/02/18 01:30:40 mheins Exp $
+# $Id: ECML.pm,v 1.1.2.1 2003/01/25 22:21:25 racke Exp $
 #
 # Copyright (C) 1996-2001 Red Hat, Inc. <interchange@redhat.com>
 #



No                   revision



No                   revision



1.1.4.1   +191 -205  interchange/extensions/quickbooks/README


rev 1.1.4.1, prev_rev 1.1
Index: README
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/README,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- README	5 Sep 2000 17:17:56 -0000	1.1
+++ README	25 Jan 2003 22:21:26 -0000	1.1.4.1
@@ -1,284 +1,270 @@
-=head1 NAME
+NAME
+    Interchange QuickBooks -- QuickBooks support for transactions and items
 
-Interchange QuickBooks -- QuickBooks support for transactions and items
+VERSION
+    This document describes software based on Interchange 4.5 and later.
 
-=head2 Version
+DESCRIPTION
+    Interchange is a business-to-business and business-to-consumer internet
+    ordering and cataloguing product. It has the ability to take orders via
+    the World Wide Web, and store transaction data.
 
-This document describes software based on Interchange 4.5.x.
+    This document describes how to interface Interchange with QuickBooks,
+    the popular small-business accounting program from Intuit.
 
-=head1 DESCRIPTION
+    QuickBooks has an import/export format called IIF, a mnemonic for Intuit
+    Interchange Format. Fitting, eh?
 
-Interchange is a business-to-business and business-to-consumer internet
-ordering and cataloguing product. It has the ability to take orders via the
-World Wide Web, and store transaction data.
+    The standard capabilities of Interchange allow production of IIF files
+    for transaction passing. With some support from Interchange UserTags,
+    can even import and export item listings.
 
-This document describes how to interface Interchange with QuickBooks, the
-popular small-business accounting program from Intuit.
+CONTENTS
+    The following files are used with this extension:
 
-QuickBooks has an import/export format called IIF, a mnemonic for Intuit
-Interchange Format. Fitting, eh?
+      ic_qb.pod                     The source for this document
+      usertag/import_quicken_items  UserTag for importing items
+      usertag/export_quicken_items  UserTag for exporting items
+      pages/admin/quickbooks/*      Menu support for Interchange UI
+      etc/trans_quickbooks          Report file used with quickbooks route
+      qb.catalog.cfg                Route for quickbooks transaction logging
 
-The standard capabilities of Interchange allow producition of IIF files
-for transaction passing.  With some support from Interchange UserTags,
-can even import and export item listings.
+INSTALLATION
+    To set up this extension, the basic steps are:
 
-=head1 CONTENTS
+        * Create and copy directories and files.
+        * Add additional database fields (if any).
+        * Modify catalog.cfg with additions.
+        * Add "quickbooks" order route to default route (or pages in setups
+		  that use an mv_order_route form field).
+        * Restart Interchange.
+        * Export your items from Interchange catalog (or import your
+          existing QuickBooks items to Interchange).
+        * Test.
 
-The following files are used with this extension:
+  Terms and locations
 
-  ic_qb.pod                     The source for this document
-  usertag/import_quicken_items  UserTag for importing items
-  usertag/export_quicken_items  UserTag for exporting items
-  pages/admin/quickbooks/*      Menu support for Interchange UI
-  etc/trans_quickbooks          Report file used with quickbooks route
-  qb.catalog.cfg                Route for quickbooks transaction logging
+    Several terms are used in the examples.
 
-=head1 INSTALLATION
+    Catalog Directory
+        This is the main directory for the catalog, where catalog.cfg
+        resides. It will have a NAME, the name for the catalog. (Some common
+        Interchange demo names are "foundation", "construct", "barry", and
+        "simple".)
 
-To install this extension, the basic steps are:
+        Common locations:
 
-    * Untar the distribution to the extensions directory.
-    * Create and copy directories and files.
-    * Add additional database fields.
-    * Modify catalog.cfg with additions.
-    * Add "quickbooks" order route to checkout pages.
-    * Restart Interchange.
-    * Export your items from Interchange catalog (or import your
-      existing QuickBooks items to Interchange).
-    * Test.
+            /var/lib/interchange/NAME
+            /usr/local/interchange/catalogs/NAME
+            $HOME/catalogs/NAME
 
-=head2 Terms and locations
+        We will use the path "/var/lib/interchange/foundation" in these
+        examples.
 
-Several terms are used in the examples.
+    Interchange software directory
+        This is the main directory for your Interchange server, where the
+        file "interchange.cfg" resides. Common locations:
 
-=over 4
+            /usr/lib/interchange
+            /usr/local/interchange
+            $HOME/ic
 
-=item Catalog Directory
+        We will use the path "/usr/lib/interchange" in these examples.
 
-This is the main directory for the catalog, where catalog.cfg resides. It
-will have a NAME, the name for the catalog. (Some common Interchange
-demo names are C<construct>, C<barry>, and C<simple>.)
+    Interchange User
+        The Interchange daemon runs as a user ID that cannot be root. It
+        will require write permission on directories it must modify to do
+        its work.
 
-Common locations:
+        We will use the user ID "interch" in these examples.
 
-    /var/lib/interchange/NAME
-    $HOME/catalogs/NAME
-    /usr/local/interchange/catalogs/NAME
+  Create and copy directories and files
 
-We will use the path C</var/lib/interchange/construct> in these examples.
+    This extension requires you to add some files to your catalog.
 
-=item Interchange software directory
+    It is assumed you have tools and knowledge to create directories with
+    the proper permissions. Any directories that will contain varying files
+    like order transaction logs will require write permission for the
+    Interchange daemon user; pages and configuration only need have read
+    permission.
 
-This is the main directory for your Interchange server, where the file
-C<interchange.cfg> or C<minivend.cfg> resides. Common locations:
+    Make orders directory
+        Create the directory "orders" in your Catalog Directory if it
+        doesn't already exist. (It may be a symbolic link to another
+        location.) It must have write permission on it.
 
-    /usr/local/interchange
-    /usr/local/minivend
-    /usr/lib/interchange
-    $HOME/ic
-    $HOME/mvend
+            cd /var/lib/interchange/foundation
+            mkdir orders
 
-We will use the path C</usr/lib/interchange> in these examples.
+        If you are doing this as root, also do:
 
-=item Interchange User
+            chown interch orders
 
-The Interchange daemon runs as a user ID that cannot be root. It will require
-write permission on directories it must modify to do its work.
+        This directory is used to store the QuickBooks IIF files produced
+        for orders. The files are created with the form:
 
-We will use the user ID C<interchange> in these examples.
+            qbYYYYMMDD.iif
 
-=back
+        Each day will have a file, and when a day is complete you should
+        download the orders. (There are other schemes possible.)
 
-=head2 Untar the extension
+    Copy pages
+        You will want the Interchange UI support if you are using the UI. It
+        provides links for importing/exporting items, downloading and
+        viewing IIF files, and possibly other functions over time. At the
+        UNIX command line:
 
-The assumption is that you will untar the distribution tar file to
-the subdirectory C<extensions> in your Interchange software directory.
-If you stored it in the directory C</tmp>, the command would be:
+            cp -r /usr/lib/interchange/extensions/quickbooks/pages/admin/quickbooks \
+                  /var/lib/interchange/foundation/pages
 
-	cd /usr/lib/interchange
-	gzip -dc /tmp/ic_qb*.tar.gz | tar xvf -
+    Copy report generation file etc/trans_quickbooks
+        This file is used to generate the IIF file(s) for transaction
+        oimport into QuickBooks.
 
-This will create the directory C<extensions> if it doesn't already
-exist.
+            cp /usr/lib/interchange/extensions/quickbooks/etc/trans_quickbooks \
+               /var/lib/interchange/foundation/etc
 
-If you place the distribution somewhere else you must adjust your paths
-in the example commands given below.
+    Copy usertags
+        If you want to use the UI item import/export, two usertags are
+        required. The easiest thing is just to copy them to the Interchange
+        software directory subdirectory "lib/UI/usertag", which is #included
+        as a part of the UI configuration file.
 
-=head2 Create and copy directories and files
+            cd /usr/lib/interchange
+            cp -i extensions/quickbooks/usertag/* lib/UI/usertag
 
-This extension requires you to add some files to your catalog.
+  Additional database fields -- userdb
 
-It is assumed you have tools and knowledge to create directories with the
-proper permissions. Any directories that will contain varying files like
-order transaction logs will require write permission for the Interchange
-user (daemon); pages and configuration only need have read permission.
+    Quickbooks requires a couple more fields than Interchange has. If you
+    want the user to retain their customer number, add the following field
+    to the "userdb" table:
 
-=over 4
+        customer_number
 
-=item Make orders directory
+    It can be an integer number field if your database needs that
+    information. To add the field in MySQL, you can issue the following
+    queries at the mysql prompt:
 
-Create the directory C<orders> in your Catalog Directory if it doesn't already
-exist. (It may be a symbolic link to another location.) It must have write
-permission on it.
+        alter table userdb add column customer_number int;
 
-    cd /var/lib/interchange/construct
-    mkdir orders
+    If you don't add it, it just means that a new customer number will be
+    assigned every time.
 
-If you are doing this as root, also do:
+    WARNING: If you are using Interchange DBM files and have live data it is
+    not recommended you add this field unless you are positive you will not
+    overwrite your data. If you are not a developer, get one to help you. In
+    any case, back up your userdb.gdbm or userdb.db file first.
 
-    chown interchange orders
+  Additional database fields -- inventory
 
-This directory is used to store the QuickBooks IIF files produced for orders.
-The files are createed with the form:
+    Quicken also needs an account to debit for the split transactions it
+    uses to track item sales. If you don't create these fields to relate to
+    each SKU, the account "Other Income" will be used in the exports.
 
-    qbYYYYMMDD.iif
+    Add the following fields to the "inventory" table if they don't
+	already exist:
 
-Each day will have a file, and when a day is complete you should download
-the orders. (There are other schemes possible.)
+        account
+        cogs_account
 
-=item Copy pages
+    To add the fields in MySQL, you can issue the following queries at the
+    mysql prompt:
 
-You will want the Interchange UI support if you are using the UI. It provides
-links for importing/exporting items, downloading and viewing IIF files, and
-possibly other functions over time. At the UNIX command line:
+        alter table inventory add column account char(20);
+        alter table inventory add column cogs_account char(20);
 
-    cp -r /usr/lib/interchange/extensions/quickbooks/pages/admin/quickbooks \
-          /var/lib/interchange/construct/pages
+    Other SQL databases will have similar facilities.
 
-=item Copy report generation file etc/trans_quickbooks
+    If you are using Interchange DBM files, just export the inventory
+    database, stop the Interchange server (to prevent corruption), add the
+    fields on the first line by editing the "inventory.txt" file, then
+    restart Interchange.
 
-This file is used to generate the IIF file(s) for transaction oimport
-into QuickBooks.
+  Modify catalog.cfg with additions:
 
-    cp /usr/lib/interchange/extensions/quickbooks/etc/trans_quickbooks \
-       /var/lib/interchange/construct/etc
+    Add the entries in qb.catalog.cfg to catalog.cfg (you can use a #include
+    statement if you wish).
 
-=item Copy usertags
+    There are some Require directives to ensure that the needed UserTag
+    definitions are included in the catalog, as well as the Route which is
+    used
 
-If you want to use the UI item import/export, two usertags are required.
-The easiest thing is just to copy them to the Interchange Software
-Directory subdirectory C<dist/lib/UI/usertag>, which is #included as a
-part of the UI configuration file.
+  Add quickbooks order route
 
-    cd /usr/lib/interchange
-    cp -i extensions/quickbooks/usertag/* dist/lib/UI/usertag
+    In the Interchange UI, there is a Preferences area "ORDER_ROUTES". You
+    should add the "quickbooks" route. Place it after the transaction
+    logging step, i.e.
 
-=back
+        code     ORDER_ROUTES
+            Variable log quickbooks main copy_user
 
-=head2 Additional database fields
+    ADVANCED: If you know Interchange Variable settings, you can add it
+    directly:
 
-Quickbooks requires an account to debit for the split transactions it uses
-to track item sails. If you don't create these fields to relate to each SKU,
-the account "Other Income" will be used in the exports.
+        Variable ORDER_ROUTES  log quickbooks main copy_user
 
-Add the following fields to the "inventory" table:
+    Also, you can use other methods to set order routes. See the Interchange
+    reference documentation.
 
-    account
-    cogs_account
+  Restart the catalog
 
-To add the fields in MySQL, you can issue the following queries at
-the mysql prompt:
+    This can be done by restarting the Interchange server or by clicking
+    "Apply Changes" in the UI.
 
-    alter table inventory add column account char(20);
-    alter table inventory add column cogs_account char(20);
+  Export the items
 
-Other SQL databases will have similar facilities.
+    You can access the Quickbooks UI index by making your URL:
 
-If you are using Interchange DBM files, just export the inventory
-database, stop the Interchange server (to prevent corruption), add the
-fields on the first line by editing the C<inventory.txt> file, then
-restart Interchange.
+        http://YOURCATALOG_URL/admin/quickbooks/index
 
-=head2 Modify catalog.cfg with additions:
+    It will provide options for importing and exporting items. This is
+    necessary so QuickBooks will be able to take orders for your items.
 
-Add the entries in qb.catalog.cfg to catalog.cfg (you can use a #include
-statement if you wish).
+    QuickBooks uses the product "name" as an SKU, along with an integer
+    reference number. Either you need to make your SKUs match the integer
+    reference number, or you must ensure your product title is unique.
 
-There are some Require directives to ensure that the needed UserTag definitions
-are included in the catalog, as well as the Route which is used
+  Test
 
-=head2 Add quickbooks order route to order pages
+    Place a test order on your Interchange catalog once you have finished
+    installing. You should find a file in the "orders" directory with the
+    name "qbYYYYMMDD.iif". (YYYY=year, MM=month, DD=day.) Transfer this file
+    to your QuickBooks machine and run File/Import and select that file as
+    the source. This should import the customer and order into the system.
+    If it doesn't work, it may be due to lack of sales tax or shipping
+    definitions, discussed below.
 
-Edit the checkout pages, pages/ord/checkout.html (and possibly
-pages/multi/checkout.html), in your Catalog Directory. Find the hidden field
-referring to C<mv_order_route>.
+DISCUSSION
+    The interface provided works for the sample company data distributed
+    with QuickBooks. There are certain requirements to make sure it works in
+    your environment.
 
-If the line looks like this:
+    Also, you can change the configuration by editing the file
+    etc/trans_quickbooks to suit your IIF file needs.
 
-  <INPUT TYPE=hidden NAME=mv_order_route VALUE="log main copy_user">
+  Sales Tax
 
-You will want to change it to:
+    QuickBooks has a taxing system whereby tax rates are defined by customer
+    location. There is usually also a generic "Sales Tax Item", such as
+    contained in the sample company data. This allows Interchange to
+    calculate the sales tax. If that item is not present then you will need
+    to create it.
 
-  <INPUT TYPE=hidden NAME=mv_order_route VALUE="log quickbooks main copy_user">
+  Shipping
 
-If it looks like:
+    Interchange will add a generic item "Shipping" to each order that has a
+    shipping cost. Its MEMO field will contain the text description of the
+    mode. If that item is not in your QuickBooks item definitions, then you
+    must create it.
 
-  <INPUT TYPE=hidden NAME=mv_order_route
-         VALUE="[either]__ORDER_ROUTES__[or]log main copy_user[/either]">
+  Customer Imports
 
-you will want to change the Variable/Knar entry ORDER_ROUTES to include
-the C<quickbooks> route. Place it after the transaction logging step, i.e.
+    To generate a QuickBooks transtype of INVOICE, a CUSTOMER is required.
+    Interchange outputs a CUST IIF record for each sale with the customer
+    information. Since QuickBooks uses the customer name or company to
+    generate the unique listing, we place the Interchange username in
+    parentheses after the company or name.
 
-    Variable ORDER_ROUTES  log quickbooks main copy_user
-
-=head2 Restart the catalog
-
-This can be done by restarting the Interchange server or by clicking
-C<Apply Changes> in the UI.
-
-=head2 Export the items 
-
-You can access the Quickbooks UI index by making your URL:
-
-    http://YOURCATALOG_URL/admin/quickbooks/index
-
-It will provide options for importing and exporting items. This is necessary
-so QuickBooks will be able to take orders for your items.
-
-QuickBooks uses the product "name" as an SKU, along with an integer reference
-number. Either you need to make your SKUs match the integer reference number,
-or you must ensure your product title is unique.
-
-=head2 Test
-
-Place a test order on your Interchange catalog once you have finished installing.
-You should find a file in the C<orders> directory with the name C<qbYYYYMMDD.iif>.
-(YYYY=year, MM=month, DD=day.) Transfer this file to your QuickBooks machine and
-run File/Import and select that file as the source. This should import the customer
-and order into the system. If it doesn't work, it may be due to lack of sales tax
-or shipping definitions, discussed below.
-
-=head1 DISCUSSION
-
-The interface provided works for the sample company data distributed with
-QuickBooks. There are certain requirements to make sure it works in your
-environment.
-
-Also, you can change the configuration by editing the file etc/trans_quickbooks
-to suit your IIF file needs.
-
-=head2 Sales Tax
-
-QuickBooks has a taxing system whereby tax rates are defined by customer location.
-There is usually also a generic C<Sales Tax Item>, such as contained in the sample
-company data. This allows Interchange to calculate the salestax. If that item is
-not present then you will need to create it.
-
-=head2 Shipping
-
-Interchange will add a generic item C<Shipping> to each order that has a shipping
-cost. It's MEMO field will contain the text description of the mode. If that item
-is not in your QuickBooks item definitions, then you must create it.
-
-=head2 Customer Imports
-
-To generate a QuickBooks transtype of INVOICE, a CUSTOMER is
-required. Interchange outputs a CUST IIF record for each sale with the
-customer information. Since QuickBooks uses the customer name or company
-to generate the unique listing, we place the Interchange username in
-parentheses after the company or name.
-
-=head1 AUTHOR
-
-Mike Heins, Akopia, Inc. <heins@akopia.com>.
+AUTHOR
+    Mike Heins, mike@perusion.com
 



1.1.4.1   +81 -59    interchange/extensions/quickbooks/ic_qb.pod


rev 1.1.4.1, prev_rev 1.1
Index: ic_qb.pod
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/ic_qb.pod,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- ic_qb.pod	5 Sep 2000 17:11:31 -0000	1.1
+++ ic_qb.pod	25 Jan 2003 22:21:26 -0000	1.1.4.1
@@ -2,9 +2,9 @@
 
 Interchange QuickBooks -- QuickBooks support for transactions and items
 
-=head2 Version
+=head1 VERSION
 
-This document describes software based on Interchange 4.5.x.
+This document describes software based on Interchange 4.5 and later.
 
 =head1 DESCRIPTION
 
@@ -18,7 +18,7 @@
 QuickBooks has an import/export format called IIF, a mnemonic for Intuit
 Interchange Format. Fitting, eh?
 
-The standard capabilities of Interchange allow producition of IIF files
+The standard capabilities of Interchange allow production of IIF files
 for transaction passing.  With some support from Interchange UserTags,
 can even import and export item listings.
 
@@ -35,9 +35,8 @@
 
 =head1 INSTALLATION
 
-To install this extension, the basic steps are:
+To set up this extension, the basic steps are:
 
-    * Untar the distribution to the extensions directory.
     * Create and copy directories and files.
     * Add additional database fields.
     * Modify catalog.cfg with additions.
@@ -57,26 +56,24 @@
 
 This is the main directory for the catalog, where catalog.cfg resides. It
 will have a NAME, the name for the catalog. (Some common Interchange
-demo names are C<construct>, C<barry>, and C<simple>.)
+demo names are C<foundation>, C<construct>, C<barry>, and C<simple>.)
 
 Common locations:
 
     /var/lib/interchange/NAME
-    $HOME/catalogs/NAME
     /usr/local/interchange/catalogs/NAME
+    $HOME/catalogs/NAME
 
-We will use the path C</var/lib/interchange/construct> in these examples.
+We will use the path C</var/lib/interchange/foundation> in these examples.
 
 =item Interchange software directory
 
 This is the main directory for your Interchange server, where the file
-C<interchange.cfg> or C<minivend.cfg> resides. Common locations:
+C<interchange.cfg> resides. Common locations:
 
-    /usr/local/interchange
-    /usr/local/minivend
     /usr/lib/interchange
+    /usr/local/interchange
     $HOME/ic
-    $HOME/mvend
 
 We will use the path C</usr/lib/interchange> in these examples.
 
@@ -85,25 +82,10 @@
 The Interchange daemon runs as a user ID that cannot be root. It will require
 write permission on directories it must modify to do its work.
 
-We will use the user ID C<interchange> in these examples.
+We will use the user ID C<interch> in these examples.
 
 =back
 
-=head2 Untar the extension
-
-The assumption is that you will untar the distribution tar file to
-the subdirectory C<extensions> in your Interchange software directory.
-If you stored it in the directory C</tmp>, the command would be:
-
-	cd /usr/lib/interchange
-	gzip -dc /tmp/ic_qb*.tar.gz | tar xvf -
-
-This will create the directory C<extensions> if it doesn't already
-exist.
-
-If you place the distribution somewhere else you must adjust your paths
-in the example commands given below.
-
 =head2 Create and copy directories and files
 
 This extension requires you to add some files to your catalog.
@@ -111,7 +93,7 @@
 It is assumed you have tools and knowledge to create directories with the
 proper permissions. Any directories that will contain varying files like
 order transaction logs will require write permission for the Interchange
-user (daemon); pages and configuration only need have read permission.
+daemon user; pages and configuration only need have read permission.
 
 =over 4
 
@@ -121,15 +103,15 @@
 exist. (It may be a symbolic link to another location.) It must have write
 permission on it.
 
-    cd /var/lib/interchange/construct
+    cd /var/lib/interchange/foundation
     mkdir orders
 
 If you are doing this as root, also do:
 
-    chown interchange orders
+    chown interch orders
 
 This directory is used to store the QuickBooks IIF files produced for orders.
-The files are createed with the form:
+The files are created with the form:
 
     qbYYYYMMDD.iif
 
@@ -143,7 +125,7 @@
 possibly other functions over time. At the UNIX command line:
 
     cp -r /usr/lib/interchange/extensions/quickbooks/pages/admin/quickbooks \
-          /var/lib/interchange/construct/pages
+          /var/lib/interchange/foundation/pages
 
 =item Copy report generation file etc/trans_quickbooks
 
@@ -151,24 +133,46 @@
 into QuickBooks.
 
     cp /usr/lib/interchange/extensions/quickbooks/etc/trans_quickbooks \
-       /var/lib/interchange/construct/etc
+       /var/lib/interchange/foundation/etc
 
 =item Copy usertags
 
 If you want to use the UI item import/export, two usertags are required.
-The easiest thing is just to copy them to the Interchange Software
-Directory subdirectory C<dist/lib/UI/usertag>, which is #included as a
+The easiest thing is just to copy them to the Interchange software
+directory subdirectory C<lib/UI/usertag>, which is #included as a
 part of the UI configuration file.
 
     cd /usr/lib/interchange
-    cp -i extensions/quickbooks/usertag/* dist/lib/UI/usertag
+    cp -i extensions/quickbooks/usertag/* lib/UI/usertag
 
 =back
 
-=head2 Additional database fields
+=head2 Additional database fields -- userdb
+
+Quickbooks requires a couple more fields than Interchange has. If you
+want the user to retain their customer number, add the following field to the
+"userdb" table:
+
+    customer_number
 
-Quickbooks requires an account to debit for the split transactions it uses
-to track item sails. If you don't create these fields to relate to each SKU,
+It can be an integer number field if your database needs that information.
+To add the field in MySQL, you can issue the following queries at
+the mysql prompt:
+
+    alter table userdb add column customer_number int;
+
+If you don't add it, it just means that a new customer number will be assigned
+every time.
+
+WARNING: If you are using Interchange DBM files and have live data it
+is not recommended you add this field unless you are positive you will
+not overwrite your data. If you are not a developer, get one to help you.
+In any case, back up your userdb.gdbm or userdb.db file first.
+
+=head2 Additional database fields -- inventory
+
+Quicken also needs an account to debit for the split transactions it uses
+to track item sales. If you don't create these fields to relate to each SKU,
 the account "Other Income" will be used in the exports.
 
 Add the following fields to the "inventory" table:
@@ -197,29 +201,47 @@
 There are some Require directives to ensure that the needed UserTag definitions
 are included in the catalog, as well as the Route which is used
 
-=head2 Add quickbooks order route to order pages
-
-Edit the checkout pages, pages/ord/checkout.html (and possibly
-pages/multi/checkout.html), in your Catalog Directory. Find the hidden field
-referring to C<mv_order_route>.
-
-If the line looks like this:
+=head2 Add quickbooks order route
 
-  <INPUT TYPE=hidden NAME=mv_order_route VALUE="log main copy_user">
+In the Interchange UI, there is a Preferences area "ORDER_ROUTES". You should
+add the C<quickbooks> route. Place it after the transaction logging step, i.e.
 
-You will want to change it to:
+    code     ORDER_ROUTES
+	Variable log quickbooks main copy_user
 
-  <INPUT TYPE=hidden NAME=mv_order_route VALUE="log quickbooks main copy_user">
+ADVANCED: If you know Interchange Variable settings, you can add it directly:
 
-If it looks like:
+    Variable ORDER_ROUTES  log quickbooks main copy_user
 
-  <INPUT TYPE=hidden NAME=mv_order_route
-         VALUE="[either]__ORDER_ROUTES__[or]log main copy_user[/either]">
+Also, you can use other methods to set order routes. See the Interchange
+reference documentation.
 
-you will want to change the Variable/Knar entry ORDER_ROUTES to include
-the C<quickbooks> route. Place it after the transaction logging step, i.e.
+=head2 Additional Variables
 
-    Variable ORDER_ROUTES  log quickbooks main copy_user
+Optionally, you may specify some variables that modify the behavior of the
+Quickbooks export feature.  Below is a command that will append the empty variables to
+your variable.txt file.
+ 
+ cat >>/path/to/your/products/variable.txt  <<EOF
+ QB_DISABLE_DOCNUM		Quickbooks
+ QB_ITEM_PREFIX		Quickbooks
+ QB_ITEM_LENGTH		Quickbooks
+ QB_FILE_SUFFIX		Quickbooks
+ QB_SHIPPING_ACCOUNT		Quickbooks
+ QB_SHIPPING_ITEM		Quickbooks
+ QB_DEFAULT_ACCOUNT		Quickbooks
+ QB_SALES_TAX_ACCOUNT		Quickbooks
+ QB_SALES_TAX_AGENCY		Quickbooks
+ QB_SALES_TAX_ITEM		Quickbooks
+ EOF
+
+Documentation for these variables is provided via item-specific meta data, which can
+be added to your mv_metadata.asc file for automatic display by the Admin UI.  See 
+
+See the mv_metadata-additions.asc file in this directory, and parhaps append its
+contents to your mv_metadata.asc file:
+ 
+ cat >>/path/to/your/products/mv_metadata.asc  <mv_metadata-additions.asc
 
 =head2 Restart the catalog
 
@@ -261,13 +283,13 @@
 
 QuickBooks has a taxing system whereby tax rates are defined by customer location.
 There is usually also a generic C<Sales Tax Item>, such as contained in the sample
-company data. This allows Interchange to calculate the salestax. If that item is
+company data. This allows Interchange to calculate the sales tax. If that item is
 not present then you will need to create it.
 
 =head2 Shipping
 
 Interchange will add a generic item C<Shipping> to each order that has a shipping
-cost. It's MEMO field will contain the text description of the mode. If that item
+cost. Its MEMO field will contain the text description of the mode. If that item
 is not in your QuickBooks item definitions, then you must create it.
 
 =head2 Customer Imports
@@ -280,5 +302,5 @@
 
 =head1 AUTHOR
 
-Mike Heins, Akopia, Inc. <heins@akopia.com>.
+Mike Heins, mike@perusion.com
 



1.1.4.1   +3 -3      interchange/extensions/quickbooks/qb.catalog.cfg


rev 1.1.4.1, prev_rev 1.1
Index: qb.catalog.cfg
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/qb.catalog.cfg,v
retrieving revision 1.1
retrieving revision 1.1.4.1
diff -u -r1.1 -r1.1.4.1
--- qb.catalog.cfg	5 Sep 2000 17:11:31 -0000	1.1
+++ qb.catalog.cfg	25 Jan 2003 22:21:26 -0000	1.1.4.1
@@ -1,6 +1,3 @@
-# We need this tag 
-Require usertag fcounter
-
 # You can remove these requires if you don't want to use the 
 # Quickbooks UI menu items
 Require usertag import_quicken_items
@@ -16,3 +13,6 @@
 Route quickbooks       report          etc/trans_quickbooks
 Route quickbooks       supplant        0
 Route quickbooks       track           logs/log
+
+### THIS ENTRY SHOULD REPLACE EXISTING Route default cascade
+Route   default   cascade         "log quickbooks main copy_user"



No                   revision



No                   revision



2.2.2.1   +0 -0      interchange/extensions/quickbooks/mv_metadata-additions.asc


rev 2.2.2.1, prev_rev 2.2
Index: mv_metadata-additions.asc
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/mv_metadata-additions.asc,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1



2.0.4.1   +0 -0      interchange/extensions/quickbooks/qb_getord.pl


rev 2.0.4.1, prev_rev 2.0
Index: qb_getord.pl
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/qb_getord.pl,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



1.2.4.1   +60 -39    interchange/extensions/quickbooks/etc/trans_quickbooks


rev 1.2.4.1, prev_rev 1.2
Index: trans_quickbooks
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/etc/trans_quickbooks,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- trans_quickbooks	14 Sep 2000 08:28:48 -0000	1.2
+++ trans_quickbooks	25 Jan 2003 22:21:26 -0000	1.2.4.1
@@ -1,4 +1,5 @@
-[perl] Log("Doing quickbooks transaction."); [/perl]
+#### begin quickbooks for [value mv_order_number] #####
+[tmp quickbooks_record]
 [if type=explicit compare="[salestax noformat=1]"]
 	[set NAMEISTAXABLE]Y[/set]
 	[set ISTAXABLE]1[/set]
@@ -9,6 +10,7 @@
 	[set NAME]Invoice with Sales Tax[/set]
 [/else]
 [/if]
+Setting salestax: ISTAXABLE=[scratch ISTAXABLE]
 
 [if type=explicit compare="[shipping noformat=1]"]
 	[set HASSHIPPING]1[/set]
@@ -16,44 +18,46 @@
 	[set HASSHIPPING]0[/set]
 [/else]
 [/if]
+Checking shipping: HASSHIPPING=[scratch HASSHIPPING]
 
 [if value b_address1]
 [then]
-	[seti ADDR1][if value company][value company] -- [/if][if value b_fname][value b_fname] [value b_lname][else][value fname] [value lname][/else][/if][/seti]
-	[seti ADDR2][value b_address1][if value b_address2], [value b_address2][/if][/seti]
-	[seti ADDR3][value b_city], [value b_state] [value b_zip][/seti]
-	[seti ADDR4][if value b_country ne US]INTL: [data table=country col=name key="[value b_country]"][/if][/seti]
-	[seti ADDR5][value phone_day] [value phone_night] [value email][/seti]
-	[seti SADDR1][if value company][value company] -- [/if][value fname] [value lname][/seti]
-	[seti SADDR2][value address1][if value address2], [value address2][/if][/seti]
-	[seti SADDR3][value city], [value state] [value zip][/seti]
-	[seti SADDR4][if value country ne US]INTL: [data table=country col=name key="[value country]"][/if][/seti]
-	[seti SADDR5][value phone_day][/seti]
+	[seti ADDR1][if value b_fname][value b_fname] [value b_lname][else][value fname] [value lname][/else][/if][/seti]
+	[seti ADDR2][if value company][value company][/if][/seti]
+	[seti ADDR3][value b_address1][if value b_address2], [value b_address2][/if][/seti]
+	[seti ADDR4][value b_city], [value b_state] [value b_zip][/seti]
+	[seti ADDR5][if value b_country][if !value country =~ /^US.*/]INTL: [data table=country col=name key="[value b_country]"][/if][/if][/seti]
+	[seti SADDR1][value fname] [value lname][/seti]
+	[seti SADDR2][if value company][value company][/if][/seti]
+	[seti SADDR3][value address1][if value address2], [value address2][/if][/seti]
+	[seti SADDR4][value city], [value state] [value zip][/seti]
+	[seti SADDR5][if value country][if !value country =~ /^US.*/]INTL: [data table=country col=name key="[value country]"][/if][/if][/seti]
 [/then]
 [else]
-	[seti ADDR1][if value company][value company] -- [/if][value fname] [value lname][/seti]
-	[seti ADDR2][value address1][if value address2], [value address2][/if][/seti]
-	[seti ADDR3][value city], [value state] [value zip][/seti]
-	[seti ADDR4][if value country ne US]INTL: [data table=country col=name key="[value country]"][/if][/seti]
-	[seti ADDR5][value phone_day] [value phone_night] [value email][/seti]
-	[seti SADDR1][if value company][value company] -- [/if][value fname] [value lname][/seti]
-	[seti SADDR2][value address1][if value address2], [value address2][/if][/seti]
-	[seti SADDR3][value city], [value state] [value zip][/seti]
-	[seti SADDR4][if value country ne US]INTL: [data table=country col=name key="[value country]"][/if][/seti]
-	[seti SADDR5][value phone_day][/seti]
+	[seti ADDR1][value fname] [value lname][/seti]
+	[seti ADDR2][if value company][value company][/if][/seti]
+	[seti ADDR3][value address1][if value address2], [value address2][/if][/seti]
+	[seti ADDR4][value city], [value state] [value zip][/seti]
+	[seti ADDR5][if value country][if !value country =~ /^US.*/]INTL: [data table=country col=name key="[value country]"][/if][/if][/seti]
+	[seti SADDR1][value fname] [value lname][/seti]
+	[seti SADDR2][if value company][value company][/if][/seti]
+	[seti SADDR3][value address1][if value address2], [value address2][/if][/seti]
+	[seti SADDR4][value city], [value state] [value zip][/seti]
+	[seti SADDR5][if value country][if !value country =~ /^US.*/]INTL: [data table=country col=name key="[value country]"][/if][/if][/seti]
 [/else]
 [/if]
 
-[seti CUSTNAME][either][value company][or][value lname], [value fname][/either] ([data session username])[/seti]
-[if scratch auto_create][set TRNSTYPE]CASH SALE[/set][else][set TRNSTYPE]INVOICE[/set][/else][/if]
+[seti CUSTNAME][either][value company][or][value lname], [value fname][/either] ([either][scratch auto_username][or][data session username][/either])[/seti]
+[set TRNSTYPE]INVOICE[/set]
 [seti DATE][tag time]%m/%d/%y[/tag][/seti]
 [seti FILEDATE][tag time]%Y%m%d[/tag][/seti]
-[if !value customer_number][value name=customer_number set="[fcounter etc/qbcust.number]"][userdb save][/if]
-[seti qb_trans]!CUST	NAME	REFNUM	TIMESTAMP	BADDR1	BADDR2	BADDR3	BADDR4	BADDR5	SADDR1	SADDR2	SADDR3	SADDR4	SADDR5	PHONE1	PHONE2	FAXNUM	NOTE	CONT1	CONT2	CTYPE	TERMS	TAXABLE	LIMIT	RESALENUM	REP	TAXITEM	NOTEPAD	SALUTATION	COMPANYNAME	FIRSTNAME	MIDINIT	LASTNAME	CUSTFLD1	CUSTFLD2	CUSTFLD3	CUSTFLD4	CUSTFLD5	CUSTFLD6	CUSTFLD7	CUSTFLD8	CUSTFLD9	CUSTFLD10	CUSTFLD11	CUSTFLD12	CUSTFLD13	CUSTFLD14	CUSTFLD15	JOBDESC	JOBTYPE	JOBSTATUS	JOBSTART	JOBPROJEND	JOBEND	HIDDEN	DELCOUNT
+Setting customer number: [if !value customer_number][value name=customer_number set="[fcounter etc/qbcust.number]"][userdb save][/if]
+[seti qb_trans]!CUST	NAME	REFNUM	TIMESTAMP	EMAIL	BADDR1	BADDR2	BADDR3	BADDR4	BADDR5	SADDR1	SADDR2	SADDR3	SADDR4	SADDR5	PHONE1	PHONE2	FAXNUM	NOTE	CONT1	CONT2	CTYPE	TERMS	TAXABLE	LIMIT	RESALENUM	REP	TAXITEM	NOTEPAD	SALUTATION	COMPANYNAME	FIRSTNAME	MIDINIT	LASTNAME	CUSTFLD1	CUSTFLD2	CUSTFLD3	CUSTFLD4	CUSTFLD5	CUSTFLD6	CUSTFLD7	CUSTFLD8	CUSTFLD9	CUSTFLD10	CUSTFLD11	CUSTFLD12	CUSTFLD13	CUSTFLD14	CUSTFLD15	JOBDESC	JOBTYPE	JOBSTATUS	JOBSTART	JOBPROJEND	JOBEND	HIDDEN	DELCOUNT
 [filter tabbed]CUST
 [scratch CUSTNAME]
 [value customer_number]
 [tag time]%s[/tag]
+[value email]
 [scratch ADDR1]
 [scratch ADDR2]
 [scratch ADDR3]
@@ -67,7 +71,7 @@
 [value name=phone_day filter=mac]
 [value name=phone_night filter=mac]
 [value name=fax filter=mac]
-[value name=gift_note filter=mac]
+[value name=gift_note filter=mac] 
 [value fname] [value lname]
 [value b_fname] [value b_lname]
 Retail
@@ -84,7 +88,7 @@
 [comment]MIDINIT[/comment]
 [value lname]
 [comment]CUSTFLD1[/comment]
-[comment]CUSTFLD2[/comment]
+[value email][comment]CUSTFLD2[/comment]
 [comment]CUSTFLD3[/comment]
 [value email]
 [comment]CUSTFLD5[/comment]
@@ -106,7 +110,7 @@
 [comment]JOBDESC[/comment]
 N
 __STORE_ID__[/filter]
-!TRNS	TRNSID	TRNSTYPE	DATE	ACCNT	NAME	CLASS	AMOUNT	DOCNUM	MEMO	CLEAR	TOPRINT	NAMEISTAXABLE	ADDR1	ADDR2	ADDR3	ADDR4	ADDR5	SADDR1	SADDR2	SADDR3	SADDR4	SADDR5
+!TRNS	TRNSID	TRNSTYPE	DATE	ACCNT	NAME	CLASS	AMOUNT	[if !var QB_DISABLE_DOCNUM]DOCNUM[/if]	MEMO	CLEAR	TOPRINT	NAMEISTAXABLE	ADDR1	ADDR2	ADDR3	ADDR4	ADDR5	SADDR1	SADDR2	SADDR3	SADDR4	SADDR5
 !SPL	SPLID	TRNSTYPE	DATE	ACCNT	NAME	CLASS	AMOUNT	DOCNUM	MEMO	CLEAR	QNTY	PRICE	INVITEM	PAYMETH	TAXABLE	VALADJ	SERVICEDATE	OTHER2	EXTRA
 !ENDTRNS
 [filter tabbed]TRNS
@@ -117,8 +121,8 @@
 [scratch CUSTNAME]
 
 [total-cost noformat=1]
-[value mv_order_number]
-[value name=gift_note filter=mac]
+[if !var QB_DISABLE_DOCNUM][value mv_order_number][/if]
+[value name=gift_note filter=mac] - Order Number: [value mv_order_number]
 N
 N
 [scratch NAMEISTAXABLE]
@@ -136,7 +140,7 @@
 [fcounter etc/qbline.number]
 [scratch TRNSTYPE]
 [scratch DATE]
-[if-item-data inventory account][item-data inventory account][else]Other Income[/else][/if-item-data]
+[either][item-data inventory account][or]__QB_DEFAULT_ACCOUNT__[or]Other Income[/either]
 [scratch CUSTNAME]
 
 -[item-subtotal noformat]
@@ -145,7 +149,16 @@
 N
 -[item-quantity]
 [item-price noformat=1]
-[item-field title]
+[seti DESC][filter
+                interpolate=1
+                op="strip mac __QB_ITEM_LENGTH__ 30"
+            ]
+            [either]
+                __QB_ITEM_PREFIX__[item-field title]
+            [or]
+                __QB_ITEM_PREFIX__[item-description]
+            [/either]
+[/filter][/seti][scratch DESC]
 
 [if-item-field nontaxable]N[else][scratch NAMEISTAXABLE][/else][/if-item-field]
 N
@@ -156,7 +169,7 @@
 [fcounter etc/qbline.number]
 [scratch TRNSTYPE]
 [scratch DATE]
-Other Income
+[either]__QB_SHIPPING_ACCOUNT__[or]Other Income[/either] 
 [scratch CUSTNAME]
 
 -[shipping noformat=1]
@@ -165,7 +178,7 @@
 N
 -1
 [shipping noformat=1]
-Shipping
+[either]__QB_SHIPPING_ITEM__[or]Shipping[/either]
 
 N
 N
@@ -176,8 +189,8 @@
 [fcounter etc/qbline.number]
 [scratch TRNSTYPE]
 [scratch DATE]
-Sales Tax Payable
-State Board of Equalization
+[either]__QB_SALES_TAX_ACCOUNT__[or]Sales Tax Payable[/either]
+[either]__QB_SALES_TAX_AGENCY__[or]State Board of Equalization[/either]
 
 -[salestax noformat=1]
 [value mv_order_number]
@@ -185,7 +198,7 @@
 N
 -1
 
-Sales Tax Item
+[either]__QB_SALES_TAX_ITEM__[or]Sales Tax Item[/either]
 
 N
 N
@@ -199,9 +212,8 @@
 	$Scratch->{qb_trans} =~ s/\s*$/\r\n/;
 	return;
 [/calc]
-[tag op=log umask=022 file="orders/qb[scratch FILEDATE].iif" type=text interpolate=1][scratch qb_trans]
+Logging transaction to orders/qb[either]__QB_FILE_SUFFIX__[or][scratch FILEDATE][/either].iif: [tag op=log umask=022 file="orders/qb[value mv_order_number].iif" type=text interpolate=1][scratch qb_trans]
 [/tag]
-[perl] Log("Past quickbooks transaction."); [/perl]
 
 [calc]
 
@@ -231,3 +243,12 @@
 	}
 	return;
 [/calc]
+[/tmp][perl]
+	my $out = $Scratch->{quickbooks_record};
+	$out =~ s/^\s+//mg;
+	$out =~ s/\s+$//mg;
+	$out =~ s/[\r\n]+/\n/;
+	$out =~ s/:\n(1|yes|succe\w+|fail\w+)\n/: $1\n/g;
+	return $out;
+[/perl]
+#### end quickbooks for [value mv_order_number] #####



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/extensions/quickbooks/pages/admin/quickbooks/export_coa.html


rev 2.0.4.1, prev_rev 2.0
Index: export_coa.html
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/pages/admin/quickbooks/export_coa.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/extensions/quickbooks/pages/admin/quickbooks/export_items.html


rev 2.0.4.1, prev_rev 2.0
Index: export_items.html
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/pages/admin/quickbooks/export_items.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/extensions/quickbooks/pages/admin/quickbooks/get_orders.html


rev 2.0.4.1, prev_rev 2.0
Index: get_orders.html
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/pages/admin/quickbooks/get_orders.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/extensions/quickbooks/pages/admin/quickbooks/import_items.html


rev 2.0.4.1, prev_rev 2.0
Index: import_items.html
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/pages/admin/quickbooks/import_items.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/extensions/quickbooks/pages/admin/quickbooks/index.html


rev 2.0.4.1, prev_rev 2.0
Index: index.html
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/pages/admin/quickbooks/index.html,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.0.4.1   +0 -0      interchange/extensions/quickbooks/usertag/export_quicken_coa.tag


rev 2.0.4.1, prev_rev 2.0
Index: export_quicken_coa.tag
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/usertag/export_quicken_coa.tag,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.0.4.1   +0 -0      interchange/extensions/quickbooks/usertag/export_quicken_items.tag


rev 2.0.4.1, prev_rev 2.0
Index: export_quicken_items.tag
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/usertag/export_quicken_items.tag,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



2.1.2.1   +0 -0      interchange/extensions/quickbooks/usertag/get_quicken_orders.tag


rev 2.1.2.1, prev_rev 2.1
Index: get_quicken_orders.tag
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/usertag/get_quicken_orders.tag,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



2.0.4.1   +0 -0      interchange/extensions/quickbooks/usertag/import_quicken_items.tag


rev 2.0.4.1, prev_rev 2.0
Index: import_quicken_items.tag
===================================================================
RCS file: /var/cvs/interchange/extensions/quickbooks/usertag/import_quicken_items.tag,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1



No                   revision



No                   revision



2.1.2.1   +0 -0      interchange/extra/Business/Fedex.pm


rev 2.1.2.1, prev_rev 2.1
Index: Fedex.pm
===================================================================
RCS file: /var/cvs/interchange/extra/Business/Fedex.pm,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1



No                   revision



No                   revision



2.0.4.1   +2 -2      interchange/extra/Tie/ShadowHash.pm


rev 2.0.4.1, prev_rev 2.0
Index: ShadowHash.pm
===================================================================
RCS file: /var/cvs/interchange/extra/Tie/ShadowHash.pm,v
retrieving revision 2.0
retrieving revision 2.0.4.1
diff -u -r2.0 -r2.0.4.1
--- ShadowHash.pm	18 Jul 2001 02:23:07 -0000	2.0
+++ ShadowHash.pm	25 Jan 2003 22:21:26 -0000	2.0.4.1
@@ -1,5 +1,5 @@
 # Tie::ShadowHash -- Merge multiple data sources into a hash.  -*- perl -*-
-# $Id: ShadowHash.pm,v 2.0 2001/07/18 02:23:07 jon Exp $
+# $Id: ShadowHash.pm,v 2.0.4.1 2003/01/25 22:21:26 racke Exp $
 #
 # Copyright 1999 by Russ Allbery <rra@stanford.edu>
 #
@@ -25,7 +25,7 @@
 use vars qw($VERSION);
 
 # The version of this module is its CVS revision.
-($VERSION = (split (' ', q$Revision: 2.0 $ ))[1]) =~ s/\.(\d)$/.0$1/;
+($VERSION = (split (' ', q$Revision: 2.0.4.1 $ ))[1]) =~ s/\.(\d)$/.0$1/;
 
 
 ############################################################################



No                   revision



No                   revision



1.1.1.1.4.1 +1 -1      interchange/extra/URI/URL.pm


rev 1.1.1.1.4.1, prev_rev 1.1.1.1
Index: URL.pm
===================================================================
RCS file: /var/cvs/interchange/extra/URI/URL.pm,v
retrieving revision 1.1.1.1
retrieving revision 1.1.1.1.4.1
diff -u -r1.1.1.1 -r1.1.1.1.4.1
--- URL.pm	26 May 2000 18:50:31 -0000	1.1.1.1
+++ URL.pm	25 Jan 2003 22:21:26 -0000	1.1.1.1.4.1
@@ -1,6 +1,6 @@
 package URI::URL;
 
-$VERSION = "4.14";   # $Date: 2000/05/26 18:50:31 $
+$VERSION = "4.14";   # $Date: 2003/01/25 22:21:26 $
 sub Version { $VERSION; }
 
 require 5.004;



No                   revision



No                   revision



1.1.1.1.4.1 +1 -0      interchange/lib/.cvsignore


rev 1.1.1.1.4.1, prev_rev 1.1.1.1
Index: .cvsignore
===================================================================
RCS file: /var/cvs/interchange/lib/.cvsignore,v
retrieving revision 1.1.1.1
retrieving revision 1.1.1.1.4.1
diff -u -r1.1.1.1 -r1.1.1.1.4.1
--- .cvsignore	26 May 2000 18:50:31 -0000	1.1.1.1
+++ .cvsignore	25 Jan 2003 22:21:27 -0000	1.1.1.1.4.1
@@ -2,3 +2,4 @@
 File
 HTML
 IniConf.pm
+Tie



No                   revision



No                   revision



1.2.4.1   +228 -38   interchange/lib/Vend/Cart.pm


rev 1.2.4.1, prev_rev 1.2
Index: Cart.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Cart.pm,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- Cart.pm	12 Jul 2000 03:08:10 -0000	1.2
+++ Cart.pm	25 Jan 2003 22:21:27 -0000	1.2.4.1
@@ -1,14 +1,11 @@
-#!/usr/bin/perl
+# Vend::Cart - Interchange shopping cart management routines
 #
-# $Id: Cart.pm,v 1.2 2000/07/12 03:08:10 heins Exp $
+# $Id: Cart.pm,v 1.2.4.1 2003/01/25 22:21:27 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -27,27 +24,64 @@
 
 package Vend::Cart;
 
-$VERSION = substr(q$Revision: 1.2 $, 10);
+$VERSION = substr(q$Revision: 1.2.4.1 $, 10);
 
 use strict;
 
 sub TIESCALAR {
 	my $class = shift;
 	my $instance = shift || undef;
+	$Vend::CurrentCart = 'main';
+	$::Levies = $Vend::Session->{levies}{main} ||= [];
 	return bless \$instance => $class;
 }
 
 sub FETCH {
-	return scalar ($::Carts->{$Vend::CurrentCart || 'main'} ||= []);
+	my $cartname = $Vend::CurrentCart;
+	$::Levies = $Vend::Session->{levies}{$cartname} ||= [];
+	return scalar ($::Carts->{$cartname} ||= []);
 }
 
 sub STORE {
 	my ($self, $cart) = @_;
 	my $name;
-	if(ref $cart) {
+	if( ref($cart) eq 'ARRAY' ) {
 		for(keys %$::Carts) {
+#::logDebug("checking name $_ via ref comparison");
 			$name = $_ if $::Carts->{$_} eq $cart;
 		}
+
+		if (! $name) {
+			$name = $cart->[0]{mv_cartname} if $cart->[0]{mv_cartname};
+		}
+
+		if (! $name) {
+			for my $pname (keys %$::Carts) {
+#::logDebug("checking name $pname via line comparison");
+				my $pros = $::Carts->{$pname};
+				next if ref($pros) ne 'ARRAY';
+				next if @$pros != @$cart;
+				CHECKLINES: {
+					for( my $i = 0; $i < @$pros; $i++ ) {
+						my $p = $pros->[$i];
+						my $c = $cart->[$i];
+						my @k1 = keys %$p;
+						my @k2 = keys %$c;
+						last CHECKLINES if @k1 != @k2;
+						foreach my $k (@k1) {
+							last CHECKLINES
+								unless exists $c->{$k};
+							last CHECKLINES
+								unless $c->{$k} eq $p->{$k};
+						}
+					}
+#::logDebug("found name $pname via line comparison");
+					$name = $pname;
+				}
+				last if $name;
+			}
+		}
+
 		if (! $name) {
 			$name = 'UNKNOWN';
 			$::Carts->{UNKNOWN} = $cart;
@@ -57,51 +91,207 @@
 	else {
 		$Vend::CurrentCart = $cart;
 	}
+	$::Levies = $Vend::Session->{levies}{$Vend::CurrentCart} ||= [];
 	return $::Carts->{$Vend::CurrentCart};
 }
 
 sub DESTROY { }
 
+
+# BEGTEST
+
+=head2 Test header for item toss
+
+ my $cart = [
+	{
+		code => 1,
+		mv_mi => 1,
+		mv_si => 0,
+		mv_ci => 0,
+		quantity => 0,
+	},
+	{
+		code => 2,
+		mv_mi => 1,
+		mv_si => 1,
+		mv_ci => 2,
+		quantity => 1,
+	},
+	{
+		code => 3,
+		mv_mi => 2,
+		mv_si => 1,
+		mv_ci => 0,
+		quantity => 1,
+	},
+	{
+		code => 5,
+		mv_mi => 1,
+		mv_si => 1,
+		mv_ci => 3,
+		quantity => 1,
+	},
+	{
+		code => 50,
+		mv_mi => 3,
+		mv_si => 1,
+		mv_ci => 0,
+		quantity => 1,
+	},
+	{
+		code => 51,
+		mv_mi => 3,
+		mv_si => 1,
+		mv_ci => 31,
+		quantity => 1,
+	},
+	{
+		code => 52,
+		mv_mi => 31,
+		mv_si => 1,
+		mv_ci => 0,
+		quantity => 1,
+	},
+	{
+		code => 6,
+		mv_mi => 1,
+		mv_si => 1,
+		mv_ci => 0,
+		quantity => 1,
+	},
+	{
+		code => 7,
+		mv_mi => 0,
+		mv_si => 0,
+		mv_ci => 0,
+		quantity => 1,
+	},
+];
+
+=cut
+
 # If the user has put in "0" for any quantity, delete that item
 # from the order list.
 sub toss_cart {
-	my($s) = @_;
+	my($s, $cartname) = @_;
 	my $i;
+	my $sub;
 	my (@master);
-    DELETE: for (;;) {
-        foreach $i (0 .. $#$s) {
-            if ($s->[$i]->{quantity} <= 0) {
-				next if defined $s->[$i]->{mv_control} and
-								$s->[$i]->{mv_control} =~ /\bnotoss\b/;
-				push (@master, $s->[$i]->{mv_mi})
-					if $s->[$i]->{mv_mi} && ! $s->[$i]->{mv_si};
-                splice(@$s, $i, 1);
-                next DELETE;
-            }
-        }
-        last DELETE;
-    }
+	my (@cascade);
+	DELETE: for (;;) {
+		foreach $i (0 .. $#$s) {
+			my $item = $s->[$i];
+			if ($sub = $Vend::Cfg->{ItemAction}{$s->[$i]{code}}) {
+				$sub->($item);
+			}
+			if ($item->{quantity} <= 0) {
+				next if defined $item->{mv_control} and
+								$item->{mv_control} =~ /\bnotoss\b/;
+				if ($item->{mv_mi} && ! $item->{mv_si}) {
+					push (@master, $item->{mv_mi});
+				}
+				elsif ( $item->{mv_ci} ) {
+					push (@master, $item->{mv_ci});
+				}
+				splice(@$s, $i, 1);
+				next DELETE;
+			}
+
+			if($Vend::Cfg->{MinQuantityField}) {
+				if(! defined $item->{mv_min_quantity}) {
+					my ($tab, $col) = split /:+/, $Vend::Cfg->{MinQuantityField};
+					if(! length $col) {
+						$col = $tab;
+						$tab = $item->{mv_ib} || $Vend::Cfg->{ProductFiles}[0];
+					}
+					$item->{mv_min_quantity} = ::tag_data($tab, $col, $item->{code})
+											 || '';
+				}
+
+				if(
+					length $item->{mv_min_quantity}
+					and 
+					$item->{quantity} < $item->{mv_min_quantity}
+					)
+				{
+					$item->{quantity} = $item->{mv_min_quantity};
+					$item->{mv_min_under} = 1;
+				}
+			}
+
+			if($Vend::Cfg->{MaxQuantityField}) {
+				my ($tab, $col) = split /:+/, $Vend::Cfg->{MaxQuantityField};
+				if(! length $col) {
+					$col = $tab;
+					$tab = $item->{mv_ib} || $Vend::Cfg->{ProductFiles}[0];
+				}
+				$item->{mv_max_quantity} = ::tag_data($tab, $col, $item->{code})
+											 || '';
+
+				if(
+					length $item->{mv_max_quantity}
+					and 
+					$item->{quantity} > $item->{mv_max_quantity}
+					)
+				{
+					$item->{quantity} = $item->{mv_max_quantity};
+					$item->{mv_max_over} = 1;
+				}
+			}
+
+			next unless $Vend::Cfg->{Limit}{cart_quantity_per_line};
+			
+			$item->{quantity} = $Vend::Cfg->{Limit}{cart_quantity_per_line}
+				if
+					$item->{quantity}
+						>
+					$Vend::Cfg->{Limit}{cart_quantity_per_line};
+		}
+		last DELETE;
+	}
 
-	return 1 unless @master;
 	my $mi;
 	my %save;
 	my @items;
+
 	# Brute force delete for subitems of any deleted master items
-	foreach $mi (@master) {
-        foreach $i (0 .. $#$s) {
-            $save{$i} = 1
-				unless $s->[$i]->{mv_si} and $s->[$i]->{mv_mi} eq $mi;
-        }
+	while (@master) {
+		@cascade = @master;
+		@master = ();
+		foreach $mi (@cascade) {
+			%save = ();
+			foreach $i (0 .. $#$s) {
+				if ( $s->[$i]->{mv_si} and $s->[$i]->{mv_mi} eq $mi ) {
+					delete $save{$i};
+# print "mi=$mi == $s->[$i]->{mv_mi}, si=$s->[$i]->{mv_si}, ci=$s->[$i]->{mv_ci}\n";
+					push(@master, $s->[$i]->{mv_ci})
+						if $s->[$i]->{mv_ci};
+				}
+				else {
+# print "mi=$mi != $s->[$i]->{mv_mi}, si=$s->[$i]->{mv_si}\n";
+					$save{$i} = 1;
+				}
+			}
+			@items = @$s;
+			@{$s} = @items[sort {$a <=> $b} keys %save];
+		}
 	}
-	@items = @$s;
-	@{$s} = @items[sort {$a <=> $b} keys %save];
-    1;
+	Vend::Interpolate::levies(1, $cartname);
+	return 1;
 }
 
-sub get_cart {
-	my($cart) = shift or return $Vend::Items;
-	return $Vend::Items = $cart;
-}
+=head2 Test footer for item toss
+
+	toss_cart($cart);
+
+	use Data::Dumper;
+	$Data::Dumper::Indent = 2;
+	$Data::Dumper::Terse = 2;
+	print Data::Dumper::Dumper($cart);
+
+	# ENDTEST
+
+=cut
 
 1;
 



1.23.4.12 +2184 -1000interchange/lib/Vend/Config.pm


rev 1.23.4.12, prev_rev 1.23.4.11
Index: Config.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Config.pm,v
retrieving revision 1.23.4.11
retrieving revision 1.23.4.12
diff -u -r1.23.4.11 -r1.23.4.12
--- Config.pm	29 Oct 2001 08:55:21 -0000	1.23.4.11
+++ Config.pm	25 Jan 2003 22:21:27 -0000	1.23.4.12
@@ -1,14 +1,12 @@
-# Config.pm - Configure Interchange
+# Vend::Config - Configure Interchange
 #
-# $Id: Config.pm,v 1.23.4.11 2001/10/29 08:55:21 racke Exp $
+# $Id: Config.pm,v 1.23.4.12 2003/01/25 22:21:27 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
+# Copyright (C) 2003 ICDEVGROUP <interchange@icdevgroup.org>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -30,81 +28,25 @@
 
 @ISA = qw(Exporter);
 
-@EXPORT		= qw( config global_config );
+@EXPORT		= qw( config global_config config_named_catalog );
 
 @EXPORT_OK	= qw( get_catalog_default get_global_default parse_time parse_database);
 
-my $OldDirectives = q{
-	AdminDatabase
-	AdminPage
-	AsciiBackend
-	BackendOrder
-	ButtonBars
-	CheckoutFrame
-	CheckoutPage
-	DataDir
-	Delimiter
-	DescriptionTrim
-	DebugMode
-	FieldDelimiter
-	FrameFlyPage
-	FrameLinkDir
-	FrameOrderPage
-	FrameSearchPage
-	ItemLinkDir
-	ItemLinkValue
-	MsqlDB
-	MsqlProducts
-	Mv_AlinkColor
-	Mv_Background
-	Mv_BgColor
-	Mv_LinkColor
-	Mv_TextColor
-	Mv_VlinkColor
-    NewEscape
-	NewReport
-	NewTags
-	OldShipping
-	OrderFrame
-	PageCache
-	PriceDatabase
-	Random
-	ReceiptPage
-	RecordDelimiter
-	ReportIgnore
-    RetireDBM
-	Rotate
-    SearchCache
-	SearchFrame
-	SearchOverMsg
-	SecureOrderMsg
-	SpecialFile
-	SubArgs
-	TolerateGet
-    TransparentItem
-	Tracking
-};
-
 use strict;
 use vars qw(
-			$VERSION $C $CanTie
+			$VERSION $C
 			@Locale_directives_ary @Locale_directives_scalar
 			@Locale_directives_code
 			@Locale_directives_currency @Locale_keys_currency
+			$GlobalRead  $SystemCodeDone $SystemGroupsDone $CodeDest
 			);
 use Safe;
 use Fcntl;
 use Vend::Parse;
 use Vend::Util;
+use Vend::Data;
 
-BEGIN {
-	eval {
-		require Tie::Watch or die;
-		$CanTie = 1;
-	};
-}
-
-$VERSION = substr(q$Revision: 1.23.4.11 $, 10);
+$VERSION = substr(q$Revision: 1.23.4.12 $, 10);
 
 my %CDname;
 
@@ -120,6 +62,7 @@
 		PriceField
 		PriceDefault
 		SalesTax
+		Levies
 		TaxShipping
 
 /	);
@@ -144,31 +87,33 @@
 
 @Locale_directives_scalar = (
 qw/
-		Autoload
 		AutoEnd
-		CommonAdjust
+        Autoload
+		CategoryField
+        CommonAdjust
 		DescriptionField
+        HTMLsuffix
 		ImageDir
 		ImageDirSecure
 		PageDir
-		SpecialPageDir
-		PriceDivide
 		PriceCommas
-		PriceField
 		PriceDefault
+        PriceDivide
+        PriceField
 		SalesTax
+        SpecialPageDir
 		StaticPath
-		HTMLsuffix
 		TaxShipping
 
 /   );
 
 @Locale_directives_ary = (
 qw/
+	AutoModifier
+	Levies
 	PriceAdjustment
 	ProductFiles
 	UseModifier
-	AutoModifier
 /   );
 
 # These are extra routines that are run if certain directives are
@@ -183,8 +128,17 @@
 	[ 'ProductFiles', \&Vend::Data::update_productbase ],
 );
 
+my %HashDefaultBlank = (qw(
+					SOAP			1
+					Mail			1
+					DatabaseDefault	1
+					Accounting		1
+					Levy			1
+				));
+
 my %DumpSource = (qw(
 					SpecialPage			1
+					GlobalSub			1
 				));
 
 my %DontDump = (qw(
@@ -198,44 +152,51 @@
 					Variable			1
 				));
 
-my $configfile;
+my $StdTags;
+
+use vars qw/ $configfile /;
+
+### This is unset when interchange script is run, so that the default
+### when used by an external program is not to compile subroutines
+$Vend::ExternalProgram = 1;
 
 # Report a fatal error in the configuration file.
 sub config_error {
-    my($msg) = @_;
-
-	if($msg =~ /unknown\s+directive\s+'(\w+)/i) {
-		my $check = $1;
-		if($OldDirectives =~ /\b$check\b/i) {
-			warn "MiniVend 3.x directive '$check' ignored at line $. of $configfile.\n";
-			return 1;
-		}
+	my $msg = shift;
+	if(@_) {
+		$msg = errmsg($msg, @_);
 	}
+
+	local($^W);
 	$msg = errmsg("%s\nIn line %s of the configuration file '%s':\n%s\n",
 			$msg,
 			$.,
 			$configfile,
 			$Vend::config_line,
 	);
-    if ($Vend::ExternalProgram) {
+	if ($Vend::ExternalProgram) {
 		warn "$msg\n" unless $Vend::Quiet;
 	}
 	else {
-		::logGlobal({level => 'warn'}, $msg);
+		logGlobal({level => 'warn'}, $msg);
 		die "$msg\n";
 	}
 }
 
 sub config_warn {
-    my($msg) = @_;
+	my $msg = shift;
+	if(@_) {
+		$msg = errmsg($msg, @_);
+	}
 
-    ::logGlobal({level => 'notice'},
-				errmsg("%s\nIn line %s of the configuration file '%s':\n%s\n",
+	local($^W);
+
+	::logGlobal({level => 'notice'},
+				"%s\nIn line %s of the configuration file '%s':\n%s\n",
 						$msg,
 						$.,
 						$configfile,
 						$Vend::config_line,
-				)
 	);
 }
 
@@ -250,25 +211,71 @@
 
 #   Directive name      Parsing function    Default value
 
+	['RunDir',			 'root_dir',     	 $Global::RunDir || 'etc'],
+	['DebugFile',		  undef,     	     ''],
 	['ConfigDir',		  undef,	         'etc/lib'],
 	['ConfigDatabase',	 'config_db',	     ''],
+	['ConfigParseComments',	'yesno',		'Yes'],
 	['ConfigAllBefore',	 'array',	         "$Global::VendRoot/catalog_before.cfg"],
 	['ConfigAllAfter',	 'array',	         "$Global::VendRoot/catalog_after.cfg"],
-    ['Message',          'message',           ''],
-    ['VarName',          'varname',           ''],
-    ['DumpStructure',	 'yesno',     	     'No'],
-    ['DisplayErrors',    'yesno',            'No'],
-    ['TcpPort',          'warn',             ''],
-    ['TcpMap',           'hash',             ''],
+	['Message',          'message',           ''],
+	['Capability',		 'capability',		 ''],
+	['Require',			 'require',			 ''],
+	['Suggest',			 'suggest',			 ''],
+	['VarName',          'varname',           ''],
+	['Windows',          undef,               $Global::Windows || ''],
+	['LockType',         undef,           	  $Global::Windows ? 'none' : ''],
+	['DumpStructure',	 'yesno',     	     'No'],
+	['DumpAllCfg',	     'yesno',     	     'No'],
+	['DisplayErrors',    'yesno',            'No'],
+	['DeleteDirective', sub {
+							my $c = $Global::DeleteDirective || {};
+							shift;
+							my @sets = map { lc $_ } split /[,\s]+/, shift;
+							@{$c}{@sets} = map { 1 } @sets;
+							return $c;
+						 },            ''],
+	['Inet_Mode',         'yesno',            (
+												defined $Global::Inet_Mode
+												||
+												defined $Global::Unix_Mode
+												)
+												? ($Global::Inet_Mode || 0) : 'No'],
+	['Unix_Mode',         'yesno',            (
+												defined $Global::Inet_Mode
+												||
+												defined $Global::Unix_Mode
+												)
+												? ($Global::Unix_Mode || 0) : 'Yes'],
+	['TcpMap',           'hash',             ''],
 	['Environment',      'array',            ''],
-    ['TcpHost',           undef,             'localhost 127.0.0.1'],
-	['SendMailProgram',  'executable',		$Global::SendMailLocation
-												|| '/usr/lib/sendmail'],
+	['TcpHost',           undef,             'localhost 127.0.0.1'],
+	['AcceptRedirect',	 'yesno',			 'No'],
+	['SendMailProgram',  'executable',		 [
+												$Global::SendMailLocation,
+											   '/usr/sbin/sendmail',
+											   '/usr/lib/sendmail',
+											   'Net::SMTP',
+											  ]
+										  ],
+	['EncryptProgram',  'executable',		 [ 'gpg', 'pgpe', 'none', ] ],
 	['PIDfile',     	  undef,             "$Global::VendRoot/etc/$Global::ExeName.pid"],
-	['SocketFile',     	  undef,             "$Global::VendRoot/etc/socket"],
+	['SocketFile',     	 'array',            "$Global::VendRoot/etc/socket"],
 	['SocketPerms',      'integer',          0600],
+	['SOAP',     	     'yesno',            'No'],
+	['SOAP_Socket',       'array',            ''],
+	['SOAP_Perms',        'integer',          0600],
+	['MaxRequestsPerChild','integer',           50],
+	['StartServers',      'integer',          0],
+	['PreFork',		      'yesno',            0],
+	['SOAP_MaxRequests', 'integer',           50],
+	['SOAP_StartServers', 'integer',          1],
+	['SOAP_Host',         undef,              'localhost 127.0.0.1'],
+	['IPCsocket',		 undef,	     	 	 "$Global::VendRoot/etc/socket.ipc"],
 	['HouseKeeping',     'integer',          60],
 	['Mall',	          'yesno',           'No'],
+	['TagGroup',		 'tag_group',		 $StdTags],
+	['TagInclude',		 'tag_include',		 'ALL'],
 	['ActionMap',		 'action',			 ''],
 	['FormAction',		 'action',			 ''],
 	['MaxServers',       'integer',          10],
@@ -279,32 +286,43 @@
 	['HitCount',		 'yesno',            'No'],
 	['IpHead',			 'yesno',            'No'],
 	['IpQuad',			 'integer',          '1'],
-	['TemplateDir',      'root_dir', 	     ''],
+	['TagDir',      	 'root_dir_array', 	 'code'],
+	['TemplateDir',      'root_dir_array', 	 ''],
 	['DomainTail',		 'yesno',            'Yes'],
-	['SafeSignals',	 	 'warn',             ''],
+	['TrustProxy',		 'list_wildcard_full', ''],
 	['AcrossLocks',		 'yesno',            'No'],
+	['RobotUA',			 'list_wildcard',      ''],
+	['RobotIP',			 'list_wildcard_full', ''],
+	['RobotHost',		 'list_wildcard_full', ''],
+	['HostnameLookups',	 'yesno',            'No'],
+	['TolerateGet',		 'yesno',            'No'],
 	['PIDcheck',		 'integer',          '0'],
-    ['LockoutCommand',    undef,             ''],
-    ['SafeUntrap',       'array',            'ftfile sort'],
+	['LockoutCommand',    undef,             ''],
+	['SafeUntrap',       'array',            'ftfile sort'],
+	['SafeTrap',         'array',            ':base_io'],
 	['NoAbsolute',		 'yesno',			 'No'],
 	['AllowGlobal',		 'boolean',			 ''],
 	['AddDirective',	 'directive',		 ''],
 	['UserTag',			 'tag',				 ''],
-	['AdminSub',		 'boolean',			 ''],
+	['CodeDef',			 'mapped_code',		 ''],
+	['HotDBI',			 'boolean',			 ''],
 	['AdminUser',		  undef,			 ''],
 	['AdminHost',		  undef,			 ''],
-    ['HammerLock',		 'integer',     	 30],
-    ['DebugMode',		 'warn',     	     ''],
-    ['DebugFile',		  undef,     	     ''],
-    ['ErrorFile',		  undef,     	     undef],
-    ['SysLog',			 'hash',     	     undef],
-    ['CheckHTML',		  undef,     	     ''],
+	['HammerLock',		 'integer',     	 30],
+	['DataTrace',		 'integer',     	 0],
+	['ShowTimes',		 'yesno',	     	 0],
+	['ErrorFile',		  undef,     	     undef],
+	['SysLog',			 'hash',     	     undef],
+	['Logging',			 'integer',     	 0],
+	['CheckHTML',		  undef,     	     ''],
+	['UrlSepChar',		 'url_sep_char',     '&'],
 	['Variable',	  	 'variable',     	 ''],
 	['Profiles',	  	 'profile',     	 ''],
-    ['Catalog',			 'catalog',     	 ''],
-    ['SubCatalog',		 'catalog',     	 ''],
+	['Catalog',			 'catalog',     	 ''],
+	['SubCatalog',		 'catalog',     	 ''],
+	['AutoVariable',	 'autovar',     	 'UrlJoiner'],
 
-    ];
+	];
 	return $directives;
 }
 
@@ -319,33 +337,50 @@
 	['ErrorFile',        undef,              'error.log'],
 	['ActionMap',		 'action',			 ''],
 	['FormAction',		 'action',			 ''],
+	['ItemAction',		 'action',			 ''],
 	['PageDir',          'relative_dir',     'pages'],
 	['SpecialPageDir',   undef,     		 'special_pages'],
 	['ProductDir',       'relative_dir',     'products'],
 	['OfflineDir',       'relative_dir',     'offline'],
+	['ConfDir',          'relative_dir',	 'etc'],
 	['ConfigDir',        'relative_dir',	 'config'],
 	['TemplateDir',      'dir_array', 		 ''],
 	['ConfigDatabase',	 'config_db',	     ''],
+	['ConfigParseComments',	'yesno',		'Yes'],
 	['Require',			 'require',			 ''],
-    ['Message',          'message',           ''],
+	['Suggest',			 'suggest',			 ''],
+	['Message',          'message',           ''],
 	['Variable',	  	 'variable',     	 ''],
+	['VarName',          'varname',           ''],
+	['Limit',			 'hash',    'option_list 5000 chained_cost_levels 32'],
 	['ScratchDefault',	 'hash',     	 	 ''],
-	['Profile',			 'hash',     	 	 ''],
+	['Profile',			 'locale',     	 	 ''],
 	['ValuesDefault',	 'hash',     	 	 ''],
-    ['ProductFiles',	 'array_complete',  'products'],
-    ['DisplayErrors',    'yesno',            'No'],
-    ['ParseVariables',	 'yesno',     	     'No'],
-    ['SpecialPage',		 'special',     	 'order ord/basket results results search results flypage flypage'],
+	['ProductFiles',	 'array_complete',  'products'],
+	['PageTables',		 'array_complete',  ''],
+	['PageTableMap',	 'hash',			qq{
+												expiration_date expiration_date
+												show_date       show_date
+												page_text       page_text
+												base_page       base_page
+												code            code
+											}],
+	['DisplayErrors',    'yesno',            'No'],
+	['ParseVariables',	 'yesno',     	     'No'],
+	['SpecialPage',		 'special', 'order ord/basket results results search results flypage flypage'],
+	['DirectoryIndex',	 undef,				 ''],
 	['Sub',				 'subroutine',       ''],
 	['VendURL',          'url',              undef],
 	['SecureURL',        'url',              undef],
 	['History',          'integer',          0],
-	['OrderReport',      undef,       'etc/report'],
+	['OrderReport',      undef,       		 'etc/report'],
 	['ScratchDir',       'relative_dir',     'tmp'],
 	['SessionDB',  		 undef,     		 ''],
 	['SessionType', 	 undef,     		 'File'],
 	['SessionDatabase',  'relative_dir',     'session'],
 	['SessionLockFile',  undef,     		 'etc/session.lock'],
+	['DatabaseDefault',  'hash',	     	 ''],
+	['DatabaseAuto',	 'dbauto',	     	 ''],
 	['Database',  		 'database',     	 ''],
 	['Autoload',		 undef,		     	 ''],
 	['AutoEnd',			 undef,		     	 ''],
@@ -359,133 +394,174 @@
 	['SendMailProgram',  'executable',		$Global::SendMailProgram],
 	['PGP',              undef,       		 ''],
 # GLIMPSE
-    ['Glimpse',          'executable',       ''],
+	['Glimpse',          'executable',       ''],
 # END GLIMPSE
- 	['Locale',           'locale',           ''],
-    ['Route',            'locale',           ''],
-	['LocaleDatabase',    undef,             ''],
+	['Locale',           'locale',           ''],
+	['Route',            'locale',           ''],
+	['LocaleDatabase',   'configdb',         ''],
+	['ExecutionLocale',   undef,             'C'],
+	['DefaultLocale',     undef,             ''],
 	['DbDatabase',        'dbdatabase',        ''],
-	['RouteDatabase',     'routeconfig',        ''],
+	['RouteDatabase',     'configdb',        ''],
 	['DirectiveDatabase', 'dbconfig',        ''],
 	['VariableDatabase',  'dbconfig',        ''],
-    ['RequiredFields',   undef,              ''],
-    ['NoSearch',         'wildcard',         'userdb'],
-    ['OrderCounter',	 undef,     	     ''],
-    ['ImageAlias',	 	 'hash',     	     ''],
-    ['TableRestrict',	 'hash',     	     ''],
-    ['Filter',		 	 'hash',     	     ''],
-    ['ImageDirSecure',   undef,     	     ''],
-    ['ImageDirInternal', undef,     	     ''],
-    ['ImageDir',	 	 undef,     	     ''],
-    ['UseCode',		 	 undef,     	     'yes'],
-    ['SetGroup',		 'valid_group',      ''],
-    ['UseModifier',		 'array',     	     ''],
-    ['AutoModifier',	 'array',     	     ''],
-    ['LogFile', 		  undef,     	     'etc/log'],
-    ['Pragma',		 	 'boolean',     	 ''],
-    ['DynamicData', 	 'boolean',     	 ''],
-    ['NoImport',	 	 'boolean',     	 ''],
-    ['NoImportExternal', 'yesno',	     	 'no'],
-    ['CommonAdjust',	 undef,  	     	 ''],
-    ['PriceAdjustment',	 'array',  	     	 ''],
-    ['PriceBreaks',	 	 'array',  	     	 ''],
-    ['PriceDivide',	 	 undef,  	     	 1],
-    ['PriceCommas',		 'yesno',     	     'Yes'],
-    ['MixMatch',		 'yesno',     	     'No'],
-    ['DifferentSecure',	 'boolean',  	     ''],
-    ['AlwaysSecure',	 'boolean',  	     ''],
+	['DirConfig',         'dirconfig',        ''],
+	['FileDatabase',	 undef,				 ''],
+	['RequiredFields',   undef,              ''],
+	['NoSearch',         'wildcard',         'userdb'],
+	['OrderCounter',	 undef,     	     ''],
+	['MimeType',         'hash',             ''],
+	['AliasTable',	 	 undef,     	     ''],
+	['ImageAlias',	 	 'hash',     	     ''],
+	['TableRestrict',	 'hash',     	     ''],
+	['Filter',		 	 'hash',     	     ''],
+	['ImageDirSecure',   undef,     	     ''],
+	['ImageDirInternal', undef,     	     ''],
+	['ImageDir',	 	 undef,     	     ''],
+	['UseCode',		 	 undef,     	     'yes'],
+	['SetGroup',		 'valid_group',      ''],
+	['UseModifier',		 'array',     	     ''],
+	['AutoModifier',	 'array',     	     ''],
+	['MaxQuantityField', undef,     	     ''],
+	['MinQuantityField', undef,     	     ''],
+	['LogFile', 		  undef,     	     'etc/log'],
+	['Pragma',		 	 'boolean_value',    ''],
+	['DynamicData', 	 'boolean',     	 ''],
+	['NoImport',	 	 'boolean',     	 ''],
+	['NoImportExternal', 'yesno',	     	 'no'],
+	['CommonAdjust',	 undef,  	     	 ''],
+	['PriceAdjustment',	 'array',  	     	 ''],
+	['PriceBreaks',	 	 'array',  	     	 ''],
+	['PriceDivide',	 	 undef,  	     	 1],
+	['PriceCommas',		 'yesno',     	     'Yes'],
+	['MixMatch',		 'yesno',     	     'No'],
+	['DifferentSecure',	 'boolean',  	     ''],
+	['AlwaysSecure',	 'boolean',  	     ''],
 	['Password',         undef,              ''],
-    ['ExtraSecure',		 'yesno',     	     'No'],
-    ['FallbackIP',		 'yesno',     	     'No'],
-    ['WideOpen',		 'yesno',     	     'No'],
-    ['Cookies',			 'yesno',     	     'Yes'],
+	['AdminSub',		 'boolean',			 ''],
+	['ExtraSecure',		 'yesno',     	     'No'],
+	['FallbackIP',		 'yesno',     	     'No'],
+	['WideOpen',		 'yesno',     	     'No'],
+	['Promiscuous',		 'yesno',     	     'No'],
+	['Cookies',			 'yesno',     	     'Yes'],
+	['CookieName',		 undef,     	     ''],
+	['CookiePattern',	 'regex',     	     '[-\w:.]+'],
 	['CookieLogin',      'yesno',            'No'],
 	['CookieDomain',     undef,              ''],
-    ['MasterHost',		 undef,     	     ''],
-    ['UserTag',			 'tag', 	    	 ''],
-    ['RemoteUser',		 undef,     	     ''],
-    ['TaxShipping',		 undef,     	     ''],
+	['MasterHost',		 undef,     	     ''],
+	['UserTag',			 'tag', 	    	 ''],
+	['CodeDef',			 'mapped_code',    	 ''],
+	['RemoteUser',		 undef,     	     ''],
+	['TaxShipping',		 undef,     	     ''],
 	['FractionalItems',  'yesno',			 'No'],
 	['SeparateItems',    'yesno',			 'No'],
-    ['PageSelectField',  undef,     	     ''],
-    ['NonTaxableField',  undef,     	     ''],
-    ['CyberCash',	 	 'yesno',     	     'No'],
-    ['CreditCardAuto',	 'yesno',     	     'No'],
-    ['NoCache',	     	 'boolean',    	     ''],
-    ['ClearCache',	     'yesno',     	     'No'],
-    ['FormIgnore',	     'boolean',    	     ''],
-    ['EncryptProgram',	 undef,     	     ''],
-    ['AsciiTrack',	 	 undef,     	     ''],
-    ['TrackFile',	 	 undef,     	     ''],
-    ['SalesTax',		 undef,     	     ''],
-    ['SalesTaxFunction', undef,     	     ''],
-    ['StaticDBM',  	 	 undef,     	     ''],
-    ['Static',   	 	 'yesno',     	     'No'],
-    ['StaticAll',		 'yesno',     	     'No'],
-    ['StaticDepth',		 undef,     	     '1'],
-    ['StaticFly',		 'yesno',     	     'No'],
-    ['StaticLogged',	 'yesno',     	     'No'],
-    ['StaticDir',		 undef,     	     ''],
-    ['StaticIndex',		 undef,     	     ''],
-    ['StaticSessionDefault',	'hash',	     ''],
+	['PageSelectField',  undef,     	     ''],
+	['NonTaxableField',  undef,     	     ''],
+	['CyberCash',	 	 'warn',     	     ''],
+	['CreditCardAuto',	 'yesno',     	     'No'],
+	['NoCache',	     	 'boolean',    	     ''],
+	['ClearCache',	     'yesno',     	     'No'],
+	['FormIgnore',	     'boolean',    	     ''],
+	['EncryptProgram',	 undef,     	     $Global::EncryptProgram || ''],
+	['EncryptKey',		 undef,     	     ''],
+	['AsciiTrack',	 	 undef,     	     ''],
+	['TrackFile',	 	 undef,     	     ''],
+	['TrackPageParam',	 'hash',     	     ''],
+	['SalesTax',		 undef,     	     ''],
+	['SalesTaxFunction', undef,     	     ''],
+	['StaticDBM',  	 	 undef,     	     ''],
+	['Static',   	 	 'yesno',     	     'No'],
+	['StaticAll',		 'yesno',     	     'No'],
+	['StaticDepth',		 undef,     	     '1'],
+	['StaticFly',		 'yesno',     	     'No'],
+	['StaticLogged',	 'yesno',     	     'No'],
+	['StaticDir',		 undef,     	     ''],
+	['StaticIndex',		 undef,     	     ''], 					  
+	['StaticSessionDefault',	 'hash',     ''],
 	['StaticTrack',		 undef,     	     ''],
+	['SOAP',			 'yesno',			 'No'],
+	['SOAP_Enable',		 'hash',			 ''],
 	['UserDB',			 'locale',	     	 ''], 
 	['UserDatabase',	 undef,		     	 ''],  #undocumented
-    ['RobotLimit',		 'integer',		      0],
-    ['OrderLineLimit',	 'integer',		      0],
-    ['StaticPage',		 'boolean',     	 ''],
-    ['StaticPath',		 undef,     	     '/'],
-    ['StaticPattern',	 'regex',     	     ''],
-    ['StaticSuffix',	 undef,     	     '.html'],
-    ['HTMLsuffix',	     undef,     	     '.html'],
-    ['CustomShipping',	 undef,     	     ''],
-    ['DefaultShipping',	 undef,     	     'default'],
-    ['UpsZoneFile',		 undef,     	     ''],
-    ['OrderProfile',	 'profile',     	 ''],
-    ['SearchProfile',	 'profile',     	 ''],
-    ['OnFly',		 	 undef,     	     ''],
-    ['HTMLmirror',		 'yesno',            'No'],
-    ['DescriptionField', undef,              'description'],
-    ['PriceDefault',	 undef,              'price'],
-    ['PriceField',		 undef,              'price'],
+	['RobotLimit',		 'integer',		      0],
+	['OrderLineLimit',	 'integer',		      0],
+	['StaticPage',		 'boolean',     	     ''],
+	['StaticPath',		 undef,     	     '/'],
+	['StaticPattern',	 'regex',     	     ''],
+	['StaticSuffix',	 undef,     	     '.html'],
+	['HTMLsuffix',	     undef,     	     '.html'],
+	['CustomShipping',	 undef,     	     ''],
+	['DefaultShipping',	 undef,     	     'default'],
+	['UpsZoneFile',		 undef,     	     ''],
+	['OrderProfile',	 'profile',     	 ''],
+	['SearchProfile',	 'profile',     	 ''],
+	['OnFly',		 	 undef,     	     ''],
+	['HTMLmirror',		 'yesno',            'No'],
+	['CategoryField',    undef,              'category'],
+	['DescriptionField', undef,              'description'],
+	['PriceDefault',	 undef,              'price'],
+	['PriceField',		 undef,              'price'],
+	['Cron',		 	 'hash',     	 	 ''],
 	['Shipping',         'locale',           ''],
-    ['IPC',		 		 'array',     	 	 ''],
-    ['IPCmode',		 	 'integer',    	 	 '0777'],
-    ['IPCdir',		 	 undef,    	 	     ''],
+	['Accounting',	 	 'locale',     	 	 ''],
+	['Levies',		 	 'array',     	 	 ''],
+	['Levy',		 	 'locale',     	 	 ''],
+	['AutoVariable',	 'autovar',     	 ''],
 
-    ];
+	];
 
 	push @$directives, @$Global::AddDirective
 		if $Global::AddDirective;
 	return $directives;
 }
 
+sub get_parse_routine {
+	my $parse = shift
+		or return undef;
+	my $routine;
+	my $rname = $parse;
+	if(ref $parse eq 'CODE') {
+		$routine = $parse;
+	}
+	elsif( $parse =~ /^\w+$/) {
+		no strict 'refs';
+		$routine = \&{'parse_' . $parse};
+		$rname = "parse_$rname";
+	}
+	else {
+		no strict 'refs';
+		$routine = \&{"$parse"};
+	}
+
+	if(ref($routine) ne 'CODE') {
+		config_error('Unknown parse routine %s', $rname);
+	}
+
+	return $routine;
+	
+}
+
 sub set_directive {
-    my ($directive, $value, $global) = @_;
-    my $directives;
+	my ($directive, $value, $global) = @_;
+	my $directives;
 
 	if($global)	{ $directives = global_directives(); }
 	else		{ $directives = catalog_directives(); }
 
-    my ($d, $dir, $parse);
-    no strict 'refs';
-    foreach $d (@$directives) {
-        next unless (lc $directive) eq (lc $d->[0]);
-        if (defined $d->[1]) {
-            $parse = 'parse_' . $d->[1];
-        } else {
-            $parse = undef;
-        }
-        $dir = $d->[0];
-        $value = &{$parse}($dir, $value)
-            if defined $parse;
-        last;
-    }
-    return [$dir, $value] if defined $dir;
-    return undef;
+	my ($d, $dir, $parse);
+	no strict 'refs';
+	foreach $d (@$directives) {
+		next unless (lc $directive) eq (lc $d->[0]);
+		$parse = get_parse_routine($d->[1]);
+		$dir = $d->[0];
+		$value = $parse->($dir, $value)
+			if $parse;
+		last;
+	}
+	return [$dir, $value] if defined $dir;
+	return undef;
 }
 
-
 sub get_catalog_default {
 	my ($directive) = @_;
 	my $directives = catalog_directives();
@@ -545,15 +621,10 @@
 # This is what happens when ParseVariables is true
 sub substitute_variable {
 	my($val) = @_;
-	# Return after globals so can others can be contained
-	$val =~ s/\@\@([A-Z][A-Z_0-9]+[A-Z0-9])\@\@/$Global::Variable->{$1}/g
-		and return $val;
-	return $val unless $val =~ /([_%])\1/;
 	1 while $val =~ s/__([A-Z][A-Z_0-9]*?[A-Z0-9])__/$C->{Variable}->{$1}/g;
-	# YALOS (yet another level)
-	return $val unless $val =~ /%%[A-Z]/;
-	$val =~ s/%%([A-Z][A-Z_0-9]+[A-Z0-9])%%/$Global::Variable->{$1}/g;
-	$val =~ s/__([A-Z][A-Z_0-9]*?[A-Z0-9])__/$C->{Variable}->{$1}/g;
+	# Only parse once for globals so they can contain other
+	# global and catalog variables
+	$val =~ s/\@\@([A-Z][A-Z_0-9]+[A-Z0-9])\@\@/$Global::Variable->{$1}/g;
 	return $val;
 }
 
@@ -563,86 +634,103 @@
 # Directives which have no defined default value ("undef") must be specified
 # in the config file.
 
+my($directives, $directive, %parse);
+
 sub config {
-	my($catalog, $dir, $confdir, $subconfig) = @_;
-    my($directives, $d, %parse, $var, $value, $lvar, $parse);
-    my($directive);
-	%CDname = ();
-	$C = {};
-	$C->{CatalogName} = $catalog;
-	$C->{VendRoot} = $dir;
-	$C->{ConfDir} = $confdir;
+	my($catalog, $dir, $confdir, $subconfig, $existing, $passed_file) = @_;
+	my($d, $parse, $var, $value, $lvar);
 
-	unless (defined $subconfig) {
-		$C->{ErrorFile} = 'error.log';
-		$C->{ConfigFile} = 'catalog.cfg';
+	if(ref $existing eq 'HASH') {
+#::logDebug("existing=$existing");
+		$C = $existing;
 	}
 	else {
-        $C->{ConfigFile} = "$catalog.cfg";
-		$C->{BaseCatalog} = $subconfig;
+		undef $existing;
+		$C = {};
+		$C->{CatalogName} = $catalog;
+		$C->{VendRoot} = $dir;
+
+		unless (defined $subconfig) {
+			$C->{ErrorFile} = 'error.log';
+			$C->{ConfigFile} = 'catalog.cfg';
+		}
+		else {
+			$C->{ConfigFile} = "$catalog.cfg";
+			$C->{BaseCatalog} = $subconfig;
+		}
 	}
 
-    no strict 'refs';
-
-    $directives = catalog_directives();
-
-	foreach $d (@$directives) {
-		($directive = $d->[0]) =~ tr/A-Z/a-z/;
-		$CDname{$directive} = $d->[0];
-		if (defined $d->[1]) {
-			$parse = 'parse_' . $d->[1];
-		} else {
-			$parse = undef;
+	unless($directives) {
+		$directives = catalog_directives();
+		foreach $d (@$directives) {
+			my $ucdir = $d->[0];
+			$directive = lc $d->[0];
+			next if $Global::DeleteDirective->{$directive};
+			$CDname{$directive} = $ucdir;
+			$parse{$directive} = get_parse_routine($d->[1]);
 		}
-		$parse{$directive} = $parse;
-
-		# We don't set up defaults if it is a subconfiguration
-		next if defined $subconfig;
+	}
 
-		$value = ( 
-					! defined $MV::Default{$catalog} or
-					! defined $MV::Default{$catalog}{$d->[0]}
-				 )
-				 ? $d->[2]
-				 : $MV::Default{$catalog}{$d->[0]};
+	no strict 'refs';
 
-		if (defined $parse and defined $value and ! defined $subconfig) {
-			$value = &$parse($d->[0], $value);
+	if(! $subconfig and ! $existing ) {
+		foreach $d (@$directives) {
+			my $ucdir = $d->[0];
+			$directive = lc $d->[0];
+			next if $Global::DeleteDirective->{$directive};
+			$parse = $parse{$directive};
+
+			$value = ( 
+						! defined $MV::Default{$catalog} or
+						! defined $MV::Default{$catalog}{$ucdir}
+					 )
+					 ? $d->[2]
+					 : $MV::Default{$catalog}{$ucdir};
+
+			if (defined $parse and defined $value) {
+#::logDebug("parsing default directive=$directive ucdir=$ucdir parse=$parse value=$value CDname=$CDname{$directive}");
+				$value = $parse->($ucdir, $value);
+			}
+			$C->{$CDname{$directive}} = $value;
 		}
-		$C->{$CDname{$directive}} = $value;
 	}
 
-	my(@include) = ($C->{ConfigFile});
+	my(@include) = ($passed_file || $C->{ConfigFile});
+	my %include_hash = ($include[0] => 1);
 	my $done_one;
 	my ($db, $dname, $nm);
 	my ($before, $after);
 	my $recno = 'C0001';
 
 	my @hidden_config;
-	@hidden_config = grep -f $_, 
-							 "$C->{CatalogName}.site",
-							 "$Global::ConfDir/$C->{CatalogName}.before",
-							 @{$Global::ConfigAllBefore},
-						 ;
-
-	# Backwards because of unshift;
-	for (@hidden_config) {
-		unshift @include, $_;
-	}
-
-	@hidden_config = grep -f $_, 
-							 "$Global::ConfDir/$C->{CatalogName}.after",
-							 @{$Global::ConfigAllAfter},
-						 ;
-
-	for (@hidden_config) {
-		push @include, $_;
+	if(! $existing and ! $subconfig) {
+		@hidden_config = grep -f $_, 
+								 "$C->{CatalogName}.site",
+								 "$Global::ConfDir/$C->{CatalogName}.before",
+								 @{$Global::ConfigAllBefore},
+							 ;
+
+		# Backwards because of unshift;
+		for (@hidden_config) {
+			unshift @include, $_;
+			$include_hash{$_} = 1;
+		}
+
+		@hidden_config = grep -f $_, 
+								 "$Global::ConfDir/$C->{CatalogName}.after",
+								 @{$Global::ConfigAllAfter},
+							 ;
+
+		for (@hidden_config) {
+			push @include, $_;
+			$include_hash{$_} = 1;
+		}
 	}
 
 	# %MV::Default holds command-line mods to config, which we write
 	# to a file for easier processing 
-	if(defined $MV::Default{$catalog}) {
-		my $fn = "$Global::ConfDir/$catalog.cmdline";
+	if(! $existing and defined $MV::Default{$catalog}) {
+		my $fn = "$Global::RunDir/$catalog.cmdline";
 		open(CMDLINE, ">$fn")
 			or die "Can't create cmdline configfile $fn: $!\n";
 		for(@{$MV::DefaultAry{$catalog}}) {
@@ -657,18 +745,28 @@
 		}
 		close CMDLINE;
 		push @include, $fn;
+		$include_hash{$_} = 1;
 	}
 
+	my $allcfg;
+	if($Global::DumpAllCfg) {
+		open ALLCFG, ">$Global::RunDir/allconfigs.cfg"
+			and $allcfg = 1;
+	}
 	# Create closure that reads and sets config values
 	my $read = sub {
-		my ($lvar, $value, $tie) = @_;
-		$parse = $parse{$lvar};
-					# call the parsing function for this directive
-		if($C->{ParseVariables} and $value =~ /([_%@])\1/) {
+		my ($lvar, $value, $tie, $var) = @_;
+
+		# parse variables in the value if necessary
+		if($C->{ParseVariables} and $value =~ /(?:__|\@\@)/) {
 			save_variable($CDname{$lvar}, $value);
 			$value = substitute_variable($value);
 		}
-		$value = &$parse($CDname{$lvar}, $value) if defined $parse and ! $tie;
+
+		# call the parsing function for this directive
+		$parse = $parse{$lvar};
+		$value = $parse->($CDname{$lvar}, $value) if defined $parse and ! $tie;
+
 		# and set the $C->directive variable
 		if($tie) {
 			watch ( $CDname{$lvar}, $value );
@@ -691,7 +789,7 @@
 	# main configuration file.  If there is a file, then we
 	# will do it (after pushing the main one on @include).
 	
-    -f $configfile && open(CONFIG, "< $configfile")
+	-f $configfile && open(CONFIG, "< $configfile")
 		or do {
 			my $msg = "Could not open configuration file '" . $configfile .
 					"' for catalog '" . $catalog . "':\n$!";
@@ -703,29 +801,45 @@
 				die "$msg\n";
 			}
 		};
+	print ALLCFG "# READING FROM $configfile\n" if $allcfg;
 	seek(CONFIG, $tellmark, 0) if $tellmark;
 #print "seeking to $tellmark in $configfile, include is @include\n";
 	my ($ifdef, $begin_ifdef);
-    while(<CONFIG>) {
+	while(<CONFIG>) {
+		if($allcfg) {
+			print ALLCFG $_
+				unless /^#?include\s+/i;
+		}
 		chomp;			# zap trailing newline,
-		if(/^#endif\s*$/) {
+		# Look for meta commands (ifdef, endif, include) after '#'?
+		my $leadinghash = $C->{ConfigParseComments} ? '#?' : '';
+		if(/^\s*${leadinghash}endif\s*$/i) {
+#print "found $_\n";
 			undef $ifdef;
 			undef $begin_ifdef;
 			next;
 		}
-		if(/^#if(n?)def\s+(.*)/) {
+		if(/^\s*${leadinghash}if(n?)def\s+(.*)/i) {
 			if(defined $ifdef) {
-				config_error("Can't overlap #ifdef at line $. of $configfile");
+				config_error("Can't overlap ifdef at line %s of %s", $., $configfile);
 			}
 			$ifdef = evaluate_ifdef($2,$1);
 			$begin_ifdef = $.;
+#print "found $_\n";
 			next;
 		}
 		if(defined $ifdef) {
 			next unless $ifdef;
 		}
-		if(/^\s*#include\s+(.+)/) {
+		if(/^\s*${leadinghash}include\s+(.+)/i) {
+#print "found $_\n";
 			my $spec = $1;
+			$spec = substitute_variable($spec) if $C->{ParseVariables};
+			if ($include_hash{$spec}) {
+				config_error("Possible infinite loop through inclusion of $spec at line %s of %s, skipping", $., $configfile);
+				next;
+			}
+			$include_hash{$spec} = 1;
 			my $ref = [ $configfile, tell(CONFIG)];
 #print "saving config $configfile (pos $ref->[1])\n";
 			#unshift @include, [ $configfile, tell(CONFIG) ];
@@ -734,94 +848,14 @@
 			unshift @include, grep -f $_, glob($spec);
 			next CONFIGLOOP;
 		}
-		my $tie = undef;
-		s/^\s*#.*//;    # comments,
-		s/\s+$//;		#  trailing spaces
-		next if $_ eq '';
-		$Vend::config_line = $_;
-		# lines read from the config file become untainted
-		m/^(\w+)\s+(.*)/ or config_error("Syntax error");
-		$var = $1;
-		$value = $2;
-		($lvar = $var) =~ tr/A-Z/a-z/;
-		my($codere) = '[-\w_#/.:]+';
-
-		if ($value =~ /^(.*)<<(\w+)\s*/) {                  # "here" value
-			my $begin  = $1 || '';
-			$begin .= "\n" if $begin;
-			my $mark  = $2;
-			my $startline = $.;
-			$value = $begin . read_here(\*CONFIG, $mark);
-			unless (defined $value) {
-				config_error (sprintf('%d: %s', $startline,
-					qq#no end marker ("$mark") found#));
-			}
-		}
-		elsif ($value =~ /^(.*)<&(\w+)\s*/) {                # "here sub" value
-			my $begin  = $1 || '';
-			$begin .= "\n" if $begin;
-			my $mark  = $2;
-			my $startline = $.;
-			$value = $begin . read_here(\*CONFIG, $mark);
-			unless (defined $value) {
-				config_error (sprintf('%d: %s', $startline,
-					qq#no end marker ("$mark") found#));
-			}
-			if ($CanTie) {
-				$tie = 1;
-			}
-			else {
-				config_warn errmsg(
-					"No Tie::Watch module installed at %s, setting %s to default.",
-								$startline,
-								$var,
-							);
-				$value = '';
-			}
-		}
-		elsif ($value =~ /^(\S+)?(\s*)?<\s*($codere)$/o) {   # read from file
-			$value = $1 || '';
-			my $file = $3;
-			$value .= "\n" if $value;
-			unless (defined $C->{ConfigDir}) {
-				config_error
-					("$CDname{$lvar}: Can't read from file until ConfigDir defined");
-			}
-			$file = $CDname{$lvar} unless $file;
-			if($Global::NoAbsolute) {
-				config_error(<<EOF) if Vend::Util::file_name_is_absolute($file);
-Absolute filenames not allowed if NoAbsolute set. Contact administrator.
-EOF
-				config_error(
-			  "No leading ../.. allowed if NoAbsolute set. Contact administrator.\n")
-					if $file =~ m#^\.\./.*\.\.#;
-				config_error(
-			  "Symbolic links not allowed if NoAbsolute set. Contact administrator.\n")
-					if -l $file;
-			}
-			$file = "$C->{ConfigDir}/$file"
-				unless Vend::Util::file_name_is_absolute($file);
-			$file = escape_chars($file);			# make safe for filename
-			my $tmpval = readfile($file);
-			unless( defined $tmpval ) {
-				config_warn errmsg(
-						"%s: read from non-existent file %s, skipping.",
-						$CDname{$lvar},
-						$file,
-						);
-				next;
-			}
-			chomp($tmpval) unless $tmpval =~ m!.\n.!;
-			# untaint
-			$tmpval =~ /([\000-\377]*)/;
-			$value .= $1;
-		}
-			
-		# Now we can give an unknown error
-		config_error("Unknown directive '$var'"), next unless defined $CDname{$lvar};
+
+		my ($lvar, $value, $var, $tie) =
+			read_config_value($_, \*CONFIG, $allcfg);
+
+		next unless $lvar;
 
 		# Use our closure defined above
-		&$read($lvar, $value, $tie);
+		$read->($lvar, $value, $tie);
 
 		# If we have passed off configuration to a database we stop here...
 		last if $C->{ConfigDatabase}->{ACTIVE};
@@ -842,8 +876,12 @@
 
 			# set directive name
 			$status = Vend::Data::set_field($db, $recno, 'directive', $nm);
-			config_error("ConfigDatabase failed for $dname, field 'directive'")
-				unless defined $status;
+			defined $status
+				or config_error(
+					"ConfigDatabase failed for %s, field '%s'",
+					$dname,
+					'directive',
+					);
 
 			# use extended value field if necessary or directed
 			if (length($value) > 250 or $UseExtended{$nm}) {
@@ -851,21 +889,30 @@
 				$extended =~ s/(\S+)\s*//;
 				$value = $1 || '';
 				$status = Vend::Data::set_field($db, $recno, 'extended', $extended);
-				config_error("ConfigDatabase failed for $dname, field 'extended'")
-					unless defined $status;
+				defined $status
+					or config_error(
+						"ConfigDatabase failed for %s, field '%s'",
+						$dname,
+						'extended',
+						);
 			}
 
 			# set value -- just a name if extended was used
 			$status = Vend::Data::set_field($db, $recno, 'value', $value);
-			config_error("Configdatabase failed for $dname, field 'value'")
-				unless defined $status;
+			defined $status
+				or config_error(
+						"ConfigDatabase failed for %s, field '%s'",
+						$dname,
+						'value',
+					);
 
 			$recno++;
 		}
 		
-    }
+	}
 	$done_one = 1;
-    close CONFIG;
+	close CONFIG;
+	delete $include_hash{$configfile};
 
 	# See if we have an active configuration database
 	if($C->{ConfigDatabase}->{ACTIVE}) {
@@ -882,23 +929,25 @@
 			$value =~ s/^\s+//;
 			$value =~ s/\s+$//;
 			$lvar = lc $dir;
-			&$read($lvar, $value);
+			$read->($lvar, $value);
 		}
 	}
 
 	# We need to make this directory if it isn't already there....
-	if($C->{ScratchDir} and ! -e $C->{ScratchDir}) {
+	if(! $existing and $C->{ScratchDir} and ! -e $C->{ScratchDir}) {
 		mkdir $C->{ScratchDir}, 0700
 			or die "Can't make temporary directory $C->{ScratchDir}: $!\n";
 	}
 
 	if(defined $ifdef) {
-		config_error("Failed to close #ifdef on line $begin_ifdef.");
+		config_error("Failed to close #ifdef on line %s.", $begin_ifdef);
 	}
 
 } # end CONFIGLOOP
 
-    # check for unspecified directives that don't have default values
+	return $C if $existing;
+
+	# check for unspecified directives that don't have default values
 
 	# but set some first if appropriate
 	set_defaults();
@@ -911,64 +960,338 @@
 				my $msg = errmsg(
 					"Please specify the %s directive in the configuration file '%s'",
 					$CDname{$var},
-					$configfile,
+					($passed_file || $C->{ConfigFile}),
 				);
 
 				die "$msg\n";
 			}
 		}
 	}
+
+	finalize_mapped_code();
+
 	# Ugly legacy stuff so API won't break
 	$C->{Special} = $C->{SpecialPage} if defined $C->{SpecialPage};
-	%CDname = ();
 	return $C;
 }
 
 sub read_here {
-	my($handle, $marker) = @_;
+	my($handle, $marker, $allcfg) = @_;
 	my $foundeot = 0;
 	my $startline = $.;
 	my $value = '';
 	while (<$handle>) {
+		print ALLCFG $_ if $allcfg;
 		if ($_ =~ m{^$marker$}) {
 			$foundeot = 1;
 			last;
 		}
 		$value .= $_;
 	}
-    return undef unless $foundeot;
+	return undef unless $foundeot;
 	#untaint
 	$value =~ /([\000-\377]*)/;
 	$value = $1;
 	return $value;
 }
 
+sub config_named_catalog {
+	my ($cat_name, $source, $db_only, $dbconfig) = @_;
+	my ($g,$c);
+
+	$g = $Global::Catalog{$cat_name};
+	unless (defined $g) {
+		logGlobal( "Can't find catalog '%s'" , $cat_name );
+		return undef;
+	}
+
+	$Vend::Log_suppress = 1;
+
+	unless ($db_only or $Vend::Quiet) {
+		logGlobal( "Config '%s' %s%s", $g->{'name'}, $source );
+	}
+	undef $Vend::Log_suppress;
+
+    chdir $g->{'dir'}
+            or die "Couldn't change to $g->{'dir'}: $!\n";
+
+	if($db_only) {
+		logGlobal(
+			"Config table '%s' (file %s) for catalog %s from %s",
+			$db_only,
+			$dbconfig,
+			$g->{'name'},
+			$source,
+			);
+		my $cfg = $Global::Selector{$g->{script}}
+			or die errmsg("'%s' not a catalog (%s).", $g->{name}, $g->{script});
+		undef $cfg->{Database}{$db_only};
+		$Vend::Cfg = config(
+				$g->{name},
+				$g->{dir},
+				undef,
+				undef,
+				$cfg,
+				$dbconfig,
+				)
+			or die errmsg("error configuring catalog %s table %s: %s",
+							$g->{name},
+							$db_only,
+							$@,
+					);
+		open_database();
+		close_database();
+		return $Vend::Cfg;
+	}
+
+    eval {
+        $c = config($g->{'name'},
+					$g->{'dir'},
+					undef,
+					$g->{'base'} || undef,
+# OPTION_EXTENSION
+#					$Vend::CommandLine->{$g->{'name'}} || undef
+# END OPTION_EXTENSION
+					);
+    };
+
+    if($@) {
+		my $msg = $@;
+        logGlobal( "%s config error: %s" , $g->{'name'}, $msg );
+     	return undef;
+    }
+
+	if (defined $g->{base}) {
+		open_database(1);
+		dump_structure($c, $g->{name}) if $Global::DumpStructure;
+		return $c;
+	}
+
+	eval {
+		$Vend::Cfg = $c;	
+		$::Variable = $Vend::Cfg->{Variable};
+		$::Pragma   = $Vend::Cfg->{Pragma};
+		Vend::Data::read_salestax();
+		Vend::Data::read_shipping();
+		open_database(1);
+		my $db;
+		close_database();
+	};
+
+	undef $Vend::Cfg;
+    if($@) {
+		my $msg = $@;
+		$msg =~ s/\s+$//;
+        logGlobal( "%s config error: %s" , $g->{'name'}, $msg );
+     	return undef;
+    }
+
+	dump_structure($c, $g->{name}) if $Global::DumpStructure;
+
+	my $stime = scalar localtime();
+	Vend::Util::writefile(">$Global::RunDir/status.$g->{name}", "$stime\n");
+	Vend::Util::writefile(">$c->{ConfDir}/status.$g->{name}", "$stime\n");
+
+	return $c;
+
+}
+
+
+use File::Find;
+
+my %extmap = qw/
+	ia	ItemAction
+	fa	FormAction
+	am	ActionMap
+	oc	OrderCheck
+	ut	UserTag
+	fi	Filter
+	fw	Widget
+	lc	LocaleChange
+	tag	UserTag
+	ct	CoreTag
+/;
+
+for( values %extmap ) {
+	$extmap{lc $_} = $_;
+}
+
+sub get_system_groups {
+
+	my @files;
+	my $wanted = sub {
+		return if (m{^\.} || ! -f $_);
+		$File::Find::name =~ m{/([^/]+)/([^/.]+)\.(\w+)$}
+			or return;
+		my $group = $1;
+		my $tname = $2;
+		my $ext = $extmap{lc $3} or return;
+		$ext =~ /Tag$/ or return;
+		push @files, [ $group, $tname ];
+	};
+	File::Find::find($wanted, @$Global::TagDir);
+
+	$Global::TagGroup ||= {};
+	for(@files) {
+		my $g = $Global::TagGroup->{":$_->[0]"} ||= [];
+		push @$g, $_->[1];
+	}
+	return;
+}
+
+sub get_system_code {
+
+	return if $CodeDest;
+	return if $Vend::ControllingInterchange;
+	
+	# defined means don't go here anymore
+	$SystemCodeDone = '';
+	my @files;
+	my $wanted = sub {
+		return if (m{^\.} || ! -f $_);
+		return unless m{^[^.]+\.(\w+)$};
+		my $ext = $extmap{lc $1} or return;
+		push @files, [ $File::Find::name, $ext];
+	};
+	File::Find::find($wanted, @$Global::TagDir);
+
+	local($configfile);
+	for(@files) {
+		$CodeDest = $_->[1];
+
+		$configfile = $_->[0];
+		open SYSTAG, "< $configfile"
+			or config_error("read system tag file %s: %s", $configfile, $!);
+		while(<SYSTAG>) {
+			my($lvar, $value) = read_config_value($_, \*SYSTAG);
+			next unless $lvar;
+			$GlobalRead->($lvar, $value);
+		}
+		close SYSTAG;
+	}
+
+	undef $CodeDest;
+	# 1 means read system tag directories
+	$SystemCodeDone = 1;
+}
+
+sub read_config_value {
+	local($_) = shift;
+	return undef unless $_;
+	my ($fh, $allcfg) = @_;
+
+	my $lvar;
+	my $tie;
+
+	chomp;			# zap trailing newline,
+	s/^\s*#.*//;            # comments,
+				# mh 2/10/96 changed comment behavior
+				# to avoid zapping RGB values
+				#
+	s/\s+$//;		#  trailing spaces
+	return undef unless $_;
+
+	local($Vend::config_line);
+	$Vend::config_line = $_;
+	# lines read from the config file become untainted
+	m/^[ \t]*(\w+)\s+(.*)/ or config_error("Syntax error");
+	my $var = $1;
+	my $value = $2;
+	($lvar = $var) =~ tr/A-Z/a-z/;
+
+	config_error("Unknown directive '%s'", $lvar), next
+		unless defined $CDname{$lvar};
+
+	my($codere) = '[-\w_#/.]+';
+
+	if ($value =~ /^(.*)<<(\w+)\s*/) {                  # "here" value
+		my $begin  = $1 || '';
+		$begin .= "\n" if $begin;
+		my $mark = $2;
+		my $startline = $.;
+		$value = $begin . read_here($fh, $mark);
+		unless (defined $value) {
+			config_error (sprintf('%d: %s', $startline,
+				qq#no end marker ("$mark") found#));
+		}
+	}
+	elsif ($value =~ /^(.*)<&(\w+)\s*/) {                # "here sub" value
+		my $begin  = $1 || '';
+		$begin .= "\n" if $begin;
+		my $mark  = $2;
+		my $startline = $.;
+		$value = $begin . read_here($fh, $mark, $allcfg);
+		unless (defined $value) {
+			config_error (sprintf('%d: %s', $startline,
+				qq#no end marker ("$mark") found#));
+		}
+		eval {
+			require Tie::Watch;
+		};
+		unless ($@) {
+			$tie = 1;
+		}
+		else {
+			config_warn(
+				"No Tie::Watch module installed at %s, setting %s to default.",
+				$startline,
+				$var,
+			);
+			$value = '';
+		}
+	}
+	elsif ($value =~ /^(\S+)?(\s*)?<\s*($codere)$/o) {   # read from file
+		my $confdir = $C ? $C->{ConfigDir} : $Global::ConfigDir;
+		$value = $1 || '';
+		my $file = $3;
+		$value .= "\n" if $value;
+		unless ($confdir) {
+			config_error(
+				"%s: Can't read from file until ConfigDir defined",
+				$CDname{$lvar},
+			);
+		}
+		$file = $CDname{$lvar} unless $file;
+		$file = "$confdir/$file" unless $file =~ m!^/!;
+		$file = escape_chars($file);			# make safe for filename
+		my $tmpval = readfile($file);
+		unless( defined $tmpval ) {
+			config_warn(
+					"%s: read from non-existent file %s, skipping.",
+					$CDname{$lvar},
+					$file,
+			);
+			return undef;
+		}
+		chomp($tmpval) unless $tmpval =~ m!.\n.!;
+		$value .= $tmpval;
+	}
+	return($lvar, $value, $var, $tie);
+}
+
 # Parse the global configuration file for directives.  Each directive sets
 # the corresponding variable in the Global:: package.  E.g.
 # "DisplayErrors No" in the config file sets Global::DisplayErrors to 0.
 # Directives which have no default value ("undef") must be specified
 # in the config file.
-
 sub global_config {
-    my($directives, $d, %name, %parse, $var, $value, $lvar, $parse);
-    my($directive, $seen_catalog);
-    no strict 'refs';
+	my(%parse, $var, $value, $lvar, $parse);
+	my($directive, $seen_catalog);
+	no strict 'refs';
 
-    $directives = global_directives();
+	%CDname = ();
+
+	my $directives = global_directives();
 
 	$Global::Structure = {} unless $Global::Structure;
 
 	# Prevent parsers from thinking it is a catalog
 	undef $C;
 
-    foreach $d (@$directives) {
-		($directive = $d->[0]) =~ tr/A-Z/a-z/;
-		$name{$directive} = $d->[0];
-		if (defined $d->[1]) {
-			$parse = 'parse_' . $d->[1];
-		} else {
-			$parse = undef;
-		}
+	foreach my $d (@$directives) {
+		$directive = lc $d->[0];
+		$CDname{$directive} = $d->[0];
+		$parse = get_parse_routine($d->[1]);
 		$parse{$directive} = $parse;
 		undef $value;
 		$value = ( 
@@ -978,49 +1301,50 @@
 				 ? $d->[2]
 				 : $MV::Default{mv_global}{$d->[0]};
 
-		if (defined $DumpSource{$name{$directive}}) {
-			$Global::Structure->{ $name{$directive} } = $value;
+		if (defined $DumpSource{$CDname{$directive}}) {
+			$Global::Structure->{ $CDname{$directive} } = $value;
 		}
 
 		if (defined $parse and defined $value) {
-			$value = &$parse($d->[0], $value);
+			$value = $parse->($d->[0], $value);
 		}
 
 		if(defined $value) {
-			${'Global::' . $name{$directive}} = $value;
+			${'Global::' . $CDname{$directive}} = $value;
 
-			$Global::Structure->{ $name{$directive} } = $value
-				unless defined $DontDump{ $name{$directive} };
+			$Global::Structure->{ $CDname{$directive} } = $value
+				unless defined $DontDump{ $CDname{$directive} };
 		}
 
-    }
+	}
 
 	my (@include) = $Global::ConfigFile; 
 
 	# Create closure for reading of value
 
 	my $read = sub {
-		my ($lvar, $value) = @_;
-		# Error out on extra parameters only if we know
-		# we are not standalone
-		unless (defined $name{$lvar}) {
-			config_error("Unknown directive '$var'");
+		my ($lvar, $value, $tie) = @_;
+
+		unless (defined $CDname{$lvar}) {
+			config_error("Unknown directive '%s'", $var);
 			return;
 		}
 
-		$parse = $parse{$lvar};
-					# call the parsing function for this directive
-
-		if (defined $DumpSource{$name{$directive}}) {
-			$Global::Structure->{ $name{$directive} } = $value;
+		if (defined $DumpSource{$CDname{$directive}}) {
+			$Global::Structure->{ $CDname{$directive} } = $value;
 		}
 
-		$value = &$parse($name{$lvar}, $value) if defined $parse;
-					# and set the Global::directive variable
-		${'Global::' . $name{$lvar}} = $value;
-		$Global::Structure->{ $name{$lvar} } = $value
-			unless defined $DontDump{ $name{$lvar} };
+		# call the parsing function for this directive
+		$parse = $parse{$lvar};
+		$value = $parse->($CDname{$lvar}, $value) if defined $parse;
+
+		# and set the Global::directive variable
+		${'Global::' . $CDname{$lvar}} = $value;
+		$Global::Structure->{ $CDname{$lvar} } = $value
+			unless defined $DontDump{ $CDname{$lvar} };
 	};
+
+	$GlobalRead = $read;
 	my $done_one;
 GLOBLOOP:
 	while ($configfile = shift @include) {
@@ -1030,7 +1354,7 @@
 #print "recalling $configfile (pos $tellmark)\n";
 		}
 
-    -f $configfile && open(GLOBAL, "< $configfile")
+	-f $configfile && open(GLOBAL, "< $configfile")
 		or do {
 			my $msg = errmsg(
 						"Could not open global configuration file '%s': %s",
@@ -1048,15 +1372,23 @@
 	seek(GLOBAL, $tellmark, 0) if $tellmark;
 #print "seeking to $tellmark in $configfile, include is @include\n";
 	my ($ifdef, $begin_ifdef);
-    while(<GLOBAL>) {
-		if(/^#endif\s*$/) {
+	while(<GLOBAL>) {
+		# Look for meta commands (ifdef, endif, include) after '#'?
+		my $leadinghash = $Global::ConfigParseComments ? '#?' : '';
+		if(/^\s*${leadinghash}endif\s*$/i) {
+#print "found $_";
 			undef $ifdef;
 			undef $begin_ifdef;
 			next;
 		}
-		if(/^#if(n?)def\s+(.*)/) {
+		if(/^\s*${leadinghash}if(n?)def\s+(.*)/i) {
+#print "found $_";
 			if(defined $ifdef) {
-				config_error("Can't overlap #ifdef at line $. of $configfile");
+				config_error(
+					"Can't overlap ifdef at line %s of %s",
+					$.,
+					$configfile,
+				);
 			}
 			$ifdef = evaluate_ifdef($2,$1,1);
 			$begin_ifdef = $.;
@@ -1065,7 +1397,8 @@
 		if(defined $ifdef) {
 			next unless $ifdef;
 		}
-		if(/^\s*#include\s+(.+)/) {
+		if(/^\s*${leadinghash}include\s+(.+)/) {
+#print "found $_";
 			my $spec = $1;
 			my $ref = [ $configfile, tell(GLOBAL)];
 #print "saving config $configfile (pos $ref->[1])\n";
@@ -1075,87 +1408,55 @@
 			unshift @include, grep -f $_, glob($spec);
 			next GLOBLOOP;
 		}
-		chomp;			# zap trailing newline,
-		s/^\s*#.*//;            # comments,
-					# mh 2/10/96 changed comment behavior
-					# to avoid zapping RGB values
-					#
-		s/\s+$//;		#  trailing spaces
-		next if $_ eq '';
-		$Vend::config_line = $_;
-		# lines read from the config file become untainted
-		m/^(\w+)\s+(.*)/ or config_error("Syntax error");
-		$var = $1;
-		$value = $2;
-		($lvar = $var) =~ tr/A-Z/a-z/;
-		my($codere) = '[-\w_#/.]+';
-
-		if ($value =~ /^(.*)<<(\w+)\s*/) {                  # "here" value
-			my $begin  = $1 || '';
-			$begin .= "\n" if $begin;
-			my $mark = $2;
-			my $startline = $.;
-			$value = $begin . read_here(\*GLOBAL, $mark);
-			unless (defined $value) {
-				config_error (sprintf('%d: %s', $startline,
-					qq#no end marker ("$mark") found#));
-			}
-		}
-		elsif ($value =~ /^(\S+)?(\s*)?<\s*($codere)$/o) {   # read from file
-			$value = $1 || '';
-			my $file = $3;
-			$value .= "\n" if $value;
-			unless (defined $Global::ConfigDir) {
-				config_error
-					("$name{$lvar}: Can't read from file until ConfigDir defined");
-			}
-			$file = $name{$lvar} unless $file;
-			$file = "$Global::ConfigDir/$file" unless $file =~ m!^/!;
-			$file = escape_chars($file);			# make safe for filename
-			my $tmpval = readfile($file);
-			unless( defined $tmpval ) {
-				config_warn errmsg(
-						"%s: read from non-existent file %s, skipping.",
-						$name{$lvar},
-						$file,
-						);
-				next;
-			}
-			chomp($tmpval) unless $tmpval =~ m!.\n.!;
-			$value .= $tmpval;
-		}
 
-		&$read($lvar, $value);
+		my ($lvar, $value, $tie) = read_config_value($_, \*GLOBAL);
+		next unless $lvar;
+		$read->($lvar, $value, $tie);
 
-   }
-    close GLOBAL;
+	}
+	close GLOBAL;
 	$done_one = 1;
 } # end GLOBLOOP;
 
-    # check for unspecified directives that don't have default values
-    foreach $var (keys %name) {
+	# In case no user-supplied config has been given...returns
+	# with no effect if that has been done already.
+	get_system_code() unless defined $SystemCodeDone;
+
+	# Do some cleanup
+	set_global_defaults();
+
+	# check for unspecified directives that don't have default values
+	foreach $var (keys %CDname) {
 		last if defined $Vend::ExternalProgram;
-        if (!defined ${'Global::' . $name{$var}}) {
-            die "Please specify the $name{$var} directive in the\n" .
-            "configuration file '$Global::ConfigFile'\n";
-        }
-    }
+		if (!defined ${'Global::' . $CDname{$var}}) {
+			die "Please specify the $CDname{$var} directive in the\n" .
+			"configuration file '$Global::ConfigFile'\n";
+		}
+	}
 
 	# Inits Global UserTag entries
 	ADDTAGS: {
 		Vend::Parse::global_init;
 	}
+	undef $GlobalRead;
+
+	finalize_mapped_code();
+
+	dump_structure($Global::Structure, "$Global::RunDir/$Global::ExeName")
+		if $Global::DumpStructure and ! $Vend::ExternalProgram;
 
-	dump_structure($Global::Structure, "$Global::ConfDir/$Global::ExeName")
-		if $Global::DumpStructure;
+	%CDname = ();
 	return 1;
 }
 
 # Use Tie::Watch to attach subroutines to config variables
 sub watch {
 	my($name, $value) = @_;
+	$C->{Tie_Watch} = [] unless $C->{Tie_Watch};
+	push @{$C->{Tie_Watch}}, $name;
+
 	my ($ref, $orig);
-#::logDebug("Contents of $name: " . ::uneval($C->{$name}));
+#::logDebug("Contents of $name: " . uneval_it($C->{$name}));
 	if(ref($C->{$name}) =~ /ARRAY/) {
 #::logDebug("watch ref=array");
 		$ref = $C->{$name};
@@ -1189,19 +1490,50 @@
 					);
 }
 
+sub get_wildcard_list {
+	my($var, $value, $base) = @_;
+
+	$value =~ s/^\s+//;
+	$value =~ s/\s+$//;
+	return '' if ! $value;
+
+	if($value !~ /\|/) {
+		$value =~ s/([\\\+\|\[\]\(\){}])/\\$1/g;
+		$value =~ s/\./\\./g;
+		$value =~ s/\*/.*/g;
+		$value =~ s/\?/./g;
+		my @items = grep /\S/, split /\s*,\s*/, $value;
+		for (@items) {
+			s/\s+/\\s+/g;
+			my $extra = $_;
+			if ($base && $extra =~ s/^\.\*\\\.//){
+				push(@items,$extra) if $extra;
+			}
+		}
+		$value = join '|', @items;
+	}
+	return parse_regex($var, $value);
+}
+
 # Set up an ActionMap or FormAction
 sub parse_action {
-	my ($var, $value) = @_;
+	my ($var, $value, $mapped) = @_;
 	return {} if ! $value;
+
+	return if $Vend::ExternalProgram;
+
 	my $c;
-	if(defined $C) {
+	if($mapped) {
+		$c = $mapped;
+	}
+	elsif(defined $C) {
 		$c = $C->{$var};
 	}
 	else {
 		no strict 'refs';
 		$c = ${"Global::$var"};
-		
 	}
+
 	if (defined $C and ! $c->{_mvsafe}) {
 		my $calc = Vend::Interpolate::reset_calc();
 		$c->{_mvsafe} = $calc;
@@ -1217,7 +1549,7 @@
 			if defined $Global::GlobalSub->{$_};
 		return $c;
 	}
-	elsif ( $sub !~ /^sub\b/) {
+	elsif ( ! $mapped and $sub !~ /^sub\b/) {
 		my $code = <<EOF;
 sub {
 				return Vend::Interpolate::interpolate_html(<<EndOfThisHaiRYTHING);
@@ -1236,20 +1568,199 @@
 		$c->{$name} = $c->{_mvsafe}->reval($sub);
 	}
 	if($@) {
-		config_warn(errmsg("Action '%s' did not compile correctly.", $name));
+		config_warn("Action '%s' did not compile correctly.", $name);
 	}
 	return $c;
 	
 }
 
-# Checks to see if a globalsub, sub, or usertag is present
+sub get_directive {
+	my $name = shift;
+	$name = $CDname{lc $name} || $name;
+	no strict 'refs';
+	if($C) {
+		return $C->{$name};
+	}
+	else {
+		return ${"Global::$name"};
+	}
+}
+
+# Changes configuration directives into Variable settings, i.e.
+# DescriptionField becomes __DescriptionField__, ProductFiles becomes
+# __ProductFiles_0__, ProductFiles_1__, etc. Doesn't handle hash keys
+# that have non-word chars.
 
-sub parse_require {
+sub parse_autovar {
 	my($var, $val) = @_;
 
+	return '' if ! $val;
+
+	my @dirs = grep /\w/, split /[\s,\0]+/, $val;
+
+	my $name;
+	foreach $name (@dirs) {
+		next unless $name =~ /^\w+$/;
+		my $val = get_directive($name);
+		if(! ref $val) {
+			parse_variable('Variable', "$name $val");
+		}
+		elsif ($val =~ /ARRAY/) {
+			for(my $i = 0; $i < @$val; $i++) {
+				my $an = "${name}_$i";
+				parse_variable('Variable', "$an $val->[$i]");
+			}
+		}
+		elsif ($val =~ /HASH/) {
+			my ($k, $v);
+			while ( ($k, $v) = each %$val) {
+				next unless $k =~ /^\w+$/;
+				parse_variable('Variable', "$k $v");
+			}
+		}
+		else {
+			config_warn('%s directive not parsable by AutoVariable', $name);
+		}
+	}
+}
+
+
+# Checks to see if a globalsub, sub, usertag, or Perl module is present
+# If called with a third parameter, is just "suggestion"
+# If called with a fourth parameter, is just capability check
+
+sub parse_capability {
+	return parse_require(@_, 1, 1);
+}
+
+sub parse_tag_group {
+	my ($var, $setting) = @_;
+
+	my $c;
+	if(defined $C) {
+		$c = $C->{$var} || {};
+	}
+	else {
+		no strict 'refs';
+		$c = ${"Global::$var"} || {};
+	}
+	
+	$setting =~ tr/-/_/;
+	$setting =~ s/[,\s]+/ /g;
+	$setting =~ s/^\s+//;
+	$setting =~ s/\s+$//;
+
+	my @pairs = Text::ParseWords::shellwords($setting);
+
+	while(@pairs) {
+		my ($group, $sets) = splice @pairs, 0, 2;
+		my @sets = grep $_, split /\s+/, $sets;
+		my @groups = grep /:/, @sets;
+		@sets = grep $_ !~ /:/, @sets;
+		for(@groups) {
+			next unless $c->{$_};
+			push @sets, @{$c->{$_}};
+		}
+		$c->{$group} = \@sets;
+	}
+	return $c;
+}
+
+my %incmap = qw/TagInclude TagGroup/;
+sub parse_tag_include {
+	my ($var, $setting) = @_;
+
+	my $c;
+	my $g;
+
+	my $mapper = $incmap{$var} || 'TagGroup';
+	if(defined $C) {
+		$c = $C->{$var} || {};
+		$g = $C->{$mapper} || {};
+	}
+	else {
+		no strict 'refs';
+		$c = ${"Global::$var"} || {};
+		$g = ${"Global::$mapper"} || {};
+	}
+	
+	$setting =~ s/"/ /g;
+	$setting =~ s/^\s+//;
+	$setting =~ s/\s+$//;
+	$setting =~ s/[,\s]+/ /g;
+
+	if($setting eq 'ALL') {
+		return { ALL => 1 };
+	}
+
+	delete $c->{ALL};
+
+	get_system_groups() unless $SystemGroupsDone;
+
+	my @incs = Text::ParseWords::shellwords($setting);
+
+	for(@incs) {
+		my @things;
+		my $not = 0;
+		if(/:/) {
+			$not = 1 if s/^!//;
+			if(! $g->{$_}) {
+				config_warn(
+					"unknown %s %s included from %s",
+					$mapper,
+					$_,
+					$var,
+				);
+			}
+			else {
+				@things = @{$g->{$_}}
+			}
+		}
+		else {
+			@things = ($_);
+		}
+		for(@things) {
+			my $not = s/^!// ? ! $not : $not;
+			$c->{$_} = not $not;
+		}
+	}
+	return $c;
+}
+
+sub parse_suggest {
+	return parse_require(@_, 1);
+}
+
+sub parse_require {
+	my($var, $val, $warn, $cap) = @_;
+
 	return if $Vend::ExternalProgram;
+	return if $Vend::ControllingInterchange;
+
+	my $carptype;
+	my $error_message;
+
+	if($val =~ s/\s+"(.*)"//s) {
+		$error_message = "\a\n\n$1\n";
+	}
+
+	if($cap) {
+		$carptype = sub { return; };
+	}
+	elsif($warn) {
+		$carptype = sub { return parse_message('', @_) };
+		$error_message = "\a\n\nSuggest %s %s for proper catalog operation. Not all functions will work!\n"
+			unless $error_message;
+	}
+	else {
+		$carptype = \&config_error;
+		$error_message = 'Required %s %s not present. Aborting catalog.'
+			unless $error_message;
+	}
 
+	my $vref = $C ? $C->{Variable} : $Global::Variable;
 	my $require;
+	my $testsub = sub { 0 };
 	my $name;
 	if($val =~ s/^globalsub\s+//i) {
 		$require = $Global::GlobalSub;
@@ -1259,15 +1770,64 @@
 		$require = $C->{Sub};
 		$name = 'Sub';
 	}
+	elsif($val =~ s/^taggroup\s+//i) {
+		$require = $Global::UserTag->{Routine};
+		my @groups = grep /\S/, split /[\s,]+/, $val;
+		my @needed;
+		my $ref;
+		for (@groups) {
+			if($ref = $Global::TagGroup->{$_}) {
+				push @needed, @$ref;
+			}
+			else {
+				push @needed, $_;
+			}
+		}
+		$name = "TagGroup $val member";
+		$val = join " ", @needed;
+	}
 	elsif($val =~ s/^usertag\s+//i) {
 		$require = $Global::UserTag->{Routine};
 		$name = 'UserTag';
 	}
+	elsif($val =~ s/^(?:perl)?module\s+//i) {
+		$require = {};
+		$name = 'Perl module';
+		$testsub = sub {
+			my $module = shift;
+			my $oldtype = '';
+			if($module =~ s/\.pl$//) {
+				$oldtype = '.pl';
+			}
+			$module =~ /[^\w:]/ and return undef;
+			if(! $C or $Global::AllowGlobal->{$C->{CatalogName}}) {
+				eval "require $module$oldtype;";
+				return ! $@;
+			}
+			else {
+				# Since we aren't safe to actually require, we will 
+				# just look for a readable module file
+				$module =~ s!::!/!g;
+				$oldtype = '.pm' if ! $oldtype;
+				my $found;
+				for(@INC) {
+					next unless -f "$_/$module$oldtype" and -r _;
+					$found = 1;
+				}
+				return $found;
+			}
+		};
+	}
 	my @requires = grep /\S/, split /\s+/, $val;
 
+	my $uname = uc $name;
+	$uname =~ s/.*\s+//;
 	for(@requires) {
+		$vref->{"MV_REQUIRE_${uname}_$_"} = 1;
 		next if defined $require->{$_};
-		config_error("Required $name $_ not present. Aborting catalog.");
+		next if $testsub->($_);
+		delete $vref->{"MV_REQUIRE_${uname}_$_"};
+		$carptype->( $error_message, $name, $_ );
 	}
 	return '';	
 }
@@ -1282,7 +1842,10 @@
 }
 
 sub parse_varname {
-    my($item,$settings) = @_;
+	my($item,$settings) = @_;
+
+	return if $Vend::ExternalProgram;
+
 	my($iv,$vn,$k,$v,@set);
 #logDebug("parse_varname: $settings");
 	if(defined $C) {
@@ -1309,7 +1872,7 @@
 		$vn = $Global::VN;
 	}
 
-    @set = grep /\S/, split /\s+/, $settings;
+	@set = grep /\S/, split /\s+/, $settings;
 	while( $k = shift @set, $v = shift @set ) {
 		$vn->{$k} = $v;
 		$iv->{$v} = $k;
@@ -1320,11 +1883,13 @@
 
 # Allow addition of a new catalog directive
 sub parse_directive {
-    my($name, $val) = @_;
+	my($name, $val) = @_;
 
 	return '' unless $val;
 	my($dir, $parser, $default) = split /\s+/, $val, 3 ;
-	$parser = undef unless defined &{"parse_$parser"};
+	if(! defined &{"parse_$parser"} and ! defined &{"$parser"}) {
+		$parser = undef;
+	}
 	$default = '' if ! $default or $default eq 'undef';
 	$Global::AddDirective = [] unless $Global::AddDirective;
 	push @$Global::AddDirective, [ $dir, $parser, $default ];
@@ -1333,11 +1898,11 @@
 
 # Allow a subcatalog value to completely replace a base value
 sub parse_replace {
-    my($name, $val) = @_;
+	my($name, $val) = @_;
 
 	return {} unless $val;
 
-    $C->{$val} = get_catalog_default($val);
+	$C->{$val} = get_catalog_default($val);
 	$C->{$name}->{$val} = 1;
 	$C->{$name};
 }
@@ -1346,27 +1911,48 @@
 # Send a message during configuration, goes to terminal if during
 # daemon startup, always goes to error log
 sub parse_message {
-    my($name, $val) = @_;
+	my($name, $val) = @_;
 
 	return '' unless $val;
 
-    ::logGlobal({level => 'info'},
+	return 1 if $Vend::Quiet;
+
+	my $strip;
+	my $info_only;
+	## strip trailing whitespace if -n beins message
+	while($val =~ s/^-([ni])\s+//) {
+		$1 eq 'n' and $val =~ s/^-n\s+// and $strip = 1 and $val =~ s/\s+$//;
+		$info_only = 1 if $1 eq 'i';
+	}
+
+	my $msg = errmsg($val,
+						$name,
+						$.,
+						$configfile,
+				);
+
+	if($info_only and $Global::Foreground) {
+		print $msg;
+	}
+	else {
+		logGlobal({level => 'info', strip => $strip },
 				errmsg($val,
 						$name,
 						$.,
 						$configfile,
 				)
-	);
+		);
+	}
 }
 
 
 # Warn about directives no longer supported in the configuration file.
 sub parse_warn {
-    my($name, $val) = @_;
+	my($name, $val) = @_;
 
 	return '' unless $val;
 
-    ::logGlobal({level => 'info'},
+	::logGlobal({level => 'info'},
 				errmsg("Directive %s no longer supported at line %s of %s.",
 						$name,
 						$.,
@@ -1401,6 +1987,34 @@
 	return $c;
 }
 
+# Sets a boolean array, but configurable value with tag=value
+sub parse_boolean_value {
+	my($item,$settings) = @_;
+	my(@setting) = split /[\s,]+/, $settings;
+	my $c;
+
+	if(defined $C) {
+		$c = $C->{$item} || {};
+	}
+	else {
+		no strict 'refs';
+		$c = ${"Global::$item"} || {};
+	}
+
+	for (@setting) {
+		my ($k,$v);
+		if(/=/) {
+			($k,$v) = split /=/, $_, 2;
+		}
+		else {
+			$k = $_;
+			$v = 1;
+		}
+		$c->{$k} = $v;
+	}
+	return $c;
+}
+
 use POSIX qw(
 				setlocale localeconv
 				LC_ALL		LC_CTYPE	LC_COLLATE
@@ -1413,11 +2027,11 @@
 # the moment).  Otherwise uses US-English settings if not set.
 #
 sub parse_locale {
-    my($item,$settings) = @_;
+	my($item,$settings) = @_;
 	return ($settings || '') unless $settings =~ /[^\d.]/;
 	$settings = '' if "\L$settings" eq 'default';
-    my $name;
-    my ($c, $store);
+	my $name;
+	my ($c, $store);
 	if(defined $C) {
 		$c = $C->{$item} || { };
 		$C->{$item . "_repository"} = {}
@@ -1432,22 +2046,15 @@
 		$store = ${"Global::$item" . "_repository"};
 	}
 
-    # Try POSIX first if Locale.
-    $name = POSIX::setlocale(POSIX::LC_ALL, $settings)
-		if $item eq 'Locale';
+	# Try POSIX first if Locale.
+	$name = POSIX::setlocale(POSIX::LC_ALL, $settings)
+		if $item eq 'Locale' and $settings !~ /\s/;
 
 	my ($eval, $safe);
-    if (defined $name and $name and $item eq 'Locale') {
-        $c = POSIX::localeconv();
-        $c->{mon_thousands_sep} = ','
-            unless $c->{mon_thousands_sep};
-        $c->{decimal_point} = '.'
-            unless $c->{decimal_point};
-        $c->{frac_digits} = 2
-            unless defined $c->{frac_digits};
-		$store->{$name} = $c;
-    }
-    elsif ($settings =~ s/^\s*(\w+)\s+//) {
+	if ($name and $item eq 'Locale') {
+		$store->{$name} = POSIX::localeconv();
+	}
+	elsif ($settings =~ s/^\s*([-\w.@]+)\s+//) {
 		$name = $1;
 
 		undef $eval;
@@ -1456,51 +2063,38 @@
 				and $eval = 1;
 		$eval and ! $safe and $safe = new Safe;
 		if(! defined $store->{$name} and $item eq 'Locale') {
-			if(POSIX::setlocale(POSIX::LC_ALL, $settings) ) {
+			if(POSIX::setlocale(POSIX::LC_ALL, $name) ) {
 				$store->{$name} = POSIX::localeconv();
 			}
 		}
-#		if(defined $store->{$name}) {
-#			for (sort keys %{$store->{$name}}) {
-#				printf "%-5s %-16s %s\n", $name, $_, $store->{$name}{$_};
-#			}
-#		}
-        my($sethash);
+
+		my($sethash);
 		if ($eval) {
 			$sethash = $safe->reval($settings)
-				or config_warn(errmsg("bad Locale setting in %s: %s", $name,$settings)),
+				or config_warn("bad Locale setting in %s: %s", $name,$settings),
 						$sethash = {};
 		}
-		elsif(index($settings, "\n") > -1) {
-			$settings =~ s/^(\S+\s+)"([\000-\377]*)"\s+$/$1$2/;
-			$sethash = {};
-			%{$sethash} = split(/\s+/, $settings, 2);
-		}
 		else {
+			$settings =~ s/^\s+//;
+			$settings =~ s/\s+$//;
 			$sethash = {};
 			%{$sethash} = Text::ParseWords::shellwords($settings);
 		}
 		$c = $store->{$name} || {};
-        for (keys %{$sethash}) {
-            $c->{$_} = $sethash->{$_};
-        }
-		if($item eq 'Locale') {
-			$Vend::Cfg->{DefaultLocale} = $name;
-			$c->{mon_thousands_sep} = ','
-				unless defined $c->{mon_thousands_sep};
-			$c->{decimal_point} = '.'
-				unless $c->{decimal_point};
-			$c->{frac_digits} = 2
-				unless defined $c->{frac_digits};
+		my $nodefaults = delete $sethash->{MV_LOCALE_NO_DEFAULTS};
+		for (keys %{$sethash}) {
+			$c->{$_} = $sethash->{$_};
 		}
-    }
-    else {
-        config_error("Bad locale setting $settings.\n");
-    }
+	}
+	else {
+		config_error("Bad locale setting $settings.\n");
+	}
+
+	$C->{LastLocale} = $name if $C and $item eq 'Locale';
 
 	$store->{$name} = $c unless $store->{$name};
 
-    return $c;
+	return $c;
 }
 
 #
@@ -1540,7 +2134,7 @@
 	my(%setting) = grep /\S/, split /[\s,]+/, $settings;
 	for (keys %setting) {
 		if($Global::NoAbsolute and file_name_is_absolute($setting{$_}) ) {
-			config_warn(errmsg("Absolute file name not allowed: %s", $setting{$_}));
+			config_warn("Absolute file name not allowed: %s", $setting{$_});
 			next;
 		}
 		$C->{$item}{$_} = $setting{$_};
@@ -1556,10 +2150,9 @@
 
 sub parse_hash {
 	my($item,$settings) = @_;
-	return {} if ! $settings;
-	$settings =~ s/^\s+//;
-	$settings =~ s/\s+$//;
-	my(@setting) = Text::ParseWords::shellwords($settings);
+	if (! $settings) {
+		return $HashDefaultBlank{$item} ? '' : {};
+	}
 
 	my $c;
 
@@ -1571,12 +2164,7 @@
 		$c = ${"Global::$item"} || {};
 	}
 
-	my $i;
-	for ($i = 0; $i < @setting; $i += 2) {
-		$c->{$setting[$i]} = $setting[$i + 1];
-#::logDebug("$item hash $setting[$i]=$setting[$i+1]");
-	}
-	$c;
+	return Vend::Util::hash_string($settings,$c);
 }
 
 # Set up illegal values for certain directives
@@ -1587,6 +2175,7 @@
 								mv_ib 1
 								group 1
 								code  1
+								sku   1
 								quantity 1
 								item  1     /
 						},
@@ -1595,6 +2184,7 @@
 								mv_ib 1
 								group 1
 								code  1
+								sku   1
 								quantity 1
 								item  1     /
 						}
@@ -1603,67 +2193,137 @@
 
 # Set up defaults for certain directives
 my $Have_set_global_defaults;
+
+# Set the default search files based on ProductFiles setting
+# Honor a NO_SEARCH parameter in the Database structure
+# Set MV_DEFAULT_SEARCH_FILE to the {file} entry,
+# and set MV_DEFAULT_SEARCH_TABLE to the table name.
+#
+# Error out if not SubCatalog and can't find a setting.
+#
+sub set_default_search {
+	my $setting = $C->{ProductFiles};
+
+	if(! $setting) {
+		return 1 if $C->{BaseCatalog};
+		return (undef, errmsg("No ProductFiles setting!") );
+	}
+	
+	my @fout;
+	my @tout;
+	my $nofile;
+	my $notable;
+
+	if ($C->{Variable}{MV_DEFAULT_SEARCH_FILE}) {
+		@fout =
+			grep /\S/,
+			split /[\s,]+/,
+			$C->{Variable}{MV_DEFAULT_SEARCH_FILE};
+		$nofile = 1;
+		for(@fout) {
+			next if /\./;
+			next unless exists $C->{Database}{$_};
+			$_ = $C->{Database}{$_}{file};
+		}
+	}
+	if ($C->{Variable}{MV_DEFAULT_SEARCH_TABLE}) {
+		@tout =
+			grep defined $C->{Database}{$_},
+				split /[\s,]+/,
+				$C->{Variable}{MV_DEFAULT_SEARCH_TABLE}
+		;
+		$notable = 1;
+	}
+
+	for(@$setting) {
+		next if $C->{Database}{$_}{NO_SEARCH};
+		push @tout, $_ unless $notable;
+		next unless defined $C->{Database}{$_}{file};
+		push @fout, $C->{Database}{$_}{file}
+			unless $nofile;
+	}
+	unless (scalar @fout) {
+		return 1 if $C->{BaseCatalog};
+		return (undef, errmsg("No default search file!") );
+	}
+	$C->{Variable}{MV_DEFAULT_SEARCH_FILE}  = \@fout;
+	$C->{Variable}{MV_DEFAULT_SEARCH_TABLE} = \@tout;
+	return 1;
+}
+
 my %Default = (
 		UserDB => sub {
-							shift;
-							my $set = $C->{UserDB_repository};
-							for(keys %$set) {
-								next unless defined $set->{$_}{admin};
-								$C->{AdminUserDB} = {} unless $C->{AdminUserDB};
-								$C->{AdminUserDB}{$_} = $set->{$_}{admin};
-							}
-							return 1;
-						},
-		# Turn the array of IPC keys into a hash value so that we can
-		# grep for enables
-		IPC => sub {
-							my $ref = shift;
-							return 1 unless ref $ref;
-							my $hash = {};
-							for(@$ref) {
-								$hash->{$_} = 1;
-							}
-							$C->{IPCkeys} = $hash;
-							return 1;
-						},
+					shift;
+					my $set = $C->{UserDB_repository};
+					for(keys %$set) {
+						next unless defined $set->{$_}{admin};
+						$C->{AdminUserDB} = {} unless $C->{AdminUserDB};
+						$C->{AdminUserDB}{$_} = $set->{$_}{admin};
+					}
+					return 1;
+				},
+		Glimpse => sub {
+					return 1 unless shift;
+					require Vend::Glimpse;
+					return 1;
+				},
+		SOAP_Socket => sub {
+					shift;
+					return 1 if $Have_set_global_defaults;
+					$Global::SOAP_Socket = ['7780']
+						if $Global::SOAP and ! $Global::SOAP_Socket;
+					return 1;
+				},
 		TcpMap => sub {
-							shift;
-							return 1 if defined $Have_set_global_defaults;
-							$Have_set_global_defaults = 1;
-							my (@sets) = keys %{$Global::TcpMap};
-							if(scalar @sets == 1 and $sets[0] eq '-') {
-								$Global::TcpMap = {};
-							}
-							return 1 if @sets;
-							$Global::TcpMap->{7786} = '-';
-							return 1;
-						},
-
-		ProductFiles => sub {
-							shift;
-							my $setting = $C->{ProductFiles};
-							if (defined $C->{Variable}{MV_DEFAULT_SEARCH_FILE}
-								and  ! ref $C->{Variable}{MV_DEFAULT_SEARCH_FILE})
-							{
-								$C->{Variable}{MV_DEFAULT_SEARCH_FILE} =
-									[ $C->{Variable}{MV_DEFAULT_SEARCH_FILE} ];
-								return 1;
-							}
-							my @out;
-							for(@$setting) {
-								next unless defined $C->{Database}{$_}{'file'};
-								push @out, $C->{Database}{$_}{'file'};
+					shift;
+					return 1 if defined $Have_set_global_defaults;
+					my (@sets) = keys %{$Global::TcpMap};
+					if(scalar @sets == 1 and $sets[0] eq '-') {
+						$Global::TcpMap = {};
+					}
+					return 1 if @sets;
+					$Global::TcpMap->{7786} = '-';
+					return 1;
+				},
+		Database => sub {
+			my @del;
+			for ( keys %{$C->{Database}}) {
+				push @del, $_ unless defined $C->{Database}{$_}{type};
+			}
+			for(@del) {
+#::logDebug("deleted non-existent db $_");
+				delete $C->{Database}{$_};
+			}
+			return 1;
+		},
+		Locale => sub {
+						my $repos = $C->{Locale_repository}
+							or return 1;
+						if ($C->{DefaultLocale}) {
+							my $def = $C->{DefaultLocale};
+							$C->{Locale} = $repos->{$def};
+						}
+						else {
+							for(keys %$repos) {
+								if($repos->{$_}{default}) {
+									$C->{Locale} = $repos->{$_};
+									$C->{DefaultLocale} = $_;
+								}
 							}
-							unless (scalar @out) {
-								return 1 if $C->{BaseCatalog};
-								return (undef, "No default search file!") 
-									unless scalar @out;
+							if(! $C->{DefaultLocale} and $C->{LastLocale}) {
+								$C->{DefaultLocale} = $C->{LastLocale};
+								$C->{Locale} = $repos->{$C->{LastLocale}};
 							}
-							$C->{Variable}{MV_DEFAULT_SEARCH_FILE} = \@out;
-							return 1;
-						},
+						}
+						return 1;
+					},
+		ProductFiles => \&set_default_search,
 );
 
+sub set_global_defaults {
+	## Nothing here currently
+}
+
 sub set_defaults {
 	for(keys %Default) {
 		my ($status, $error) = $Default{$_}->($C->{$_});
@@ -1676,9 +2336,42 @@
 				)
 		);
 	}
+	$Have_set_global_defaults = 1;
 	return;
 }
 
+sub parse_url_sep_char {
+	my($var,$val) = @_;
+
+	$val =~ s/\s+//g;
+
+	if($val =~ /[\w%]/) {
+		config_error(
+			errmsg("%s character value '%s' must not be word character or %%.", $var, $val)
+		);
+	}
+	elsif(length($val) > 1) {
+		config_error(
+			"%s character value '%s' longer than one character.",
+			$var,
+			$val,
+		);
+	}
+	elsif($val !~ /[&;:]/) {
+		config_warn("%s character value '%s' not a recommended value.", $var, $val);
+	}
+
+	if($val eq '&') {
+		$Global::UrlJoiner = $Global::Variable->{MV_HTML4_COMPLIANT} ? '&amp;' : '&';
+		$Global::UrlSplittor = qr/\&/;
+	}
+	else {
+		$Global::UrlJoiner = $val;
+		$Global::UrlSplittor = qr/[&$val]/o;
+	}
+	return $val;
+}
+
 sub check_legal {
 	my ($directive, $value) = @_;
 	return 1 unless defined $IllegalValue{$directive}->{$value};
@@ -1721,13 +2414,30 @@
 
 	$c;
 }
+
+sub parse_list_wildcard {
+	my $value = get_wildcard_list(@_,0);
+	return '' unless length($value);
+	return qr/$value/i;
+}
+
+sub parse_list_wildcard_full {
+	my $value = get_wildcard_list(@_,1);
+	return '' unless length($value);
+	return qr/^($value)$/i;
+}
+
 # Make a dos-ish regex into a Perl regex, check for errors
 sub parse_wildcard {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
+	return '' if ! $value;
 
 	$value =~ s/\./\\./g;
 	$value =~ s/\*/.*/g;
-	$value =~ s/\*/.*/g;
+	$value =~ s/\?/./g;
+	$value =~
+		s[({(?:.+?,)+.+?})]
+		 [ local $_ = $1; tr/{,}/(|)/; $_ ]eg;
 	$value =~ s/\s+/|/g;
 	eval {  
 		my $never = 'NeVAirBE';
@@ -1737,14 +2447,14 @@
 	if($@) {
 		config_error("Bad regular expression in $var.");
 	}
-    return $value;
+	return $value;
 }
 
 
 # Check that a regex won't cause a syntax error. Uses m{}, which
 # should be used for all user-input regexes.
 sub parse_regex {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
 
 	eval {  
 		my $never = 'NeVAirBE';
@@ -1754,33 +2464,48 @@
 	if($@) {
 		config_error("Bad regular expression in $var.");
 	}
-    return $value;
+	return $value;
 }
 
 # Prepend the Global::VendRoot pathname to the relative directory specified,
 # unless it already starts with a leading /.
 
 sub parse_root_dir {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
+	return '' unless $value;
+	$value = "$Global::VendRoot/$value"
+		unless Vend::Util::file_name_is_absolute($value);
+	$value =~ s./+$..;
+	return $value;
+}
+
+sub parse_root_dir_array {
+	my($var, $value) = @_;
 	return [] unless $value;
-    $value = "$Global::VendRoot/$value"
-		unless Vend::Util::file_name_is_absolute($value);
-    $value =~ s./+$..;
+
 	no strict 'refs';
-    my $c = ${"Global::$var"} || [];
-    push @$c, $value;
+	my $c = ${"Global::$var"} || [];
+
+	my @dirs = grep /\S/, Text::ParseWords::shellwords($value);
+
+	foreach my $dir (@dirs) {
+		$dir = "$Global::VendRoot/$dir"
+			unless Vend::Util::file_name_is_absolute($dir);
+		$dir =~ s./+$..;
+		push @$c, $dir;
+	}
 	return $c;
 }
 
 sub parse_dir_array {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
 	return [] unless $value;
-    $value = "$C->{VendRoot}/$value"
+	$value = "$C->{VendRoot}/$value"
 		unless Vend::Util::file_name_is_absolute($value);
-    $value =~ s./+$..;
-    $C->{$var} = [] unless $C->{$var};
-    my $c = $C->{$var} || [];
-    push @$c, $value;
+	$value =~ s./+$..;
+	$C->{$var} = [] unless $C->{$var};
+	my $c = $C->{$var} || [];
+	push @$c, $value;
 	return $c;
 }
 
@@ -1788,7 +2513,7 @@
 # unless it already starts with a leading /.
 
 sub parse_relative_dir {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
 
 	config_error(
 	  "No leading / allowed if NoAbsolute set. Contact administrator.\n"
@@ -1799,27 +2524,29 @@
 	  )
 	  if $value =~ m#^\.\./.*\.\.# and $Global::NoAbsolute;
 
-    $value = "$C->{VendRoot}/$value"
+	$C->{Source}{$var} = $value;
+
+	$value = "$C->{VendRoot}/$value"
 		unless Vend::Util::file_name_is_absolute($value);
-    $value =~ s./+$..;
-    $value;
+	$value =~ s./+$..;
+	$value;
 }
 
 # Ensure only an integer value in the directive
 sub parse_integer {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
 	$value = hex($value) if $value =~ /^0x[\dA-Fa-f]+$/;
 	$value = oct($value) if $value =~ /^0[0-7]+$/;
-    config_error("The $var directive (now set to '$value') must be an integer\n")
+	config_error("The $var directive (now set to '$value') must be an integer\n")
 		unless $value =~ /^\d+$/;
-    $value;
+	$value;
 }
 
 # Make sure no trailing slash in VendURL etc.
 sub parse_url {
-    my($var, $value) = @_;
-    $value =~ s,/+$,,;
-    $value;
+	my($var, $value) = @_;
+	$value =~ s,/+$,,;
+	$value;
 }
 
 # Parses a time specification such as "1 day" and returns the
@@ -1827,84 +2554,118 @@
 # not be parsed.
 
 sub time_to_seconds {
-    my($str) = @_;
-    my($n, $dur);
+	my($str) = @_;
+	my($n, $dur);
 
-    ($n, $dur) = ($str =~ m/(\d+)[\s\0]*(\w+)?/);
-    return undef unless defined $n;
-    if (defined $dur) {
-	$_ = $dur;
-	if (m/^s|sec|secs|second|seconds$/i) {
-	} elsif (m/^m|min|mins|minute|minutes$/i) {
-	    $n *= 60;
-	} elsif (m/^h|hour|hours$/i) {
-	    $n *= 60 * 60;
-	} elsif (m/^d|day|days$/i) {
-	    $n *= 24 * 60 * 60;
-	} elsif (m/^w|week|weeks$/i) {
-	    $n *= 7 * 24 * 60 * 60;
-	} else {
-	    return undef;
+	($n, $dur) = ($str =~ m/(\d+)[\s\0]*(\w+)?/);
+	return undef unless defined $n;
+	if (defined $dur) {
+		local($_) = $dur;
+		if (m/^s|sec|secs|second|seconds$/i) {
+		}
+		elsif (m/^m|min|mins|minute|minutes$/i) {
+			$n *= 60;
+		}
+		elsif (m/^h|hour|hours$/i) {
+			$n *= 60 * 60;
+		}
+		elsif (m/^d|day|days$/i) {
+			$n *= 24 * 60 * 60;
+		}
+		elsif (m/^w|week|weeks$/i) {
+			$n *= 7 * 24 * 60 * 60;
+		}
+		else {
+			return undef;
+		}
 	}
-    }
 
-    $n;
+	$n;
 }
 
 sub parse_valid_group {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
 
 	return '' unless $value;
 
 	my($name,$passwd,$gid,$members) = getgrnam($value);
 
-    config_error("$var: Group name '$value' is not a valid group\n")
+	config_error("$var: Group name '$value' is not a valid group\n")
 		unless defined $gid;
 	$name = getpwuid($<);
-    config_error("$var: Interchange user '$name' not in group '$value'\n")
+	config_error("$var: Interchange user '$name' not in group '$value'\n")
 		unless $members =~ /\b$name\b/;
-    $gid;
+	$gid;
 }
 
 sub parse_executable {
-    my($var, $value) = @_;
-    my($x);
-	my $root = $value;
-	$root =~ s/\s.*//;
-
-	return $value if $Global::Windows;
-	if( ! defined $value or $value eq '') {
-		$x = '';
-	}
-	elsif( $value eq 'none') {
-		$x = 'none';
-	}
-	elsif ($root =~ m#^/# and -x $root) {
-		$x = $value;
+	my($var, $initial) = @_;
+	my($x);
+	my(@tries);
+	
+	if(ref $initial) {
+		@tries = @$initial;
 	}
 	else {
-		my @path = split /:/, $ENV{PATH};
-		for (@path) {
-			next unless -x "$_/$root";
+		@tries = $initial;
+	}
+
+	TRYEXE:
+	foreach my $value (@tries) {
+#::logDebug("trying $value for $var");
+		my $root = $value;
+		$root =~ s/\s.*//;
+
+		return $value if $Global::Windows;
+		if( ! defined $value or $value eq '') {
+			$x = '';
+		}
+		elsif( $value eq 'none') {
+			$x = 'none';
+			last;
+		}
+		elsif( $value =~ /^\w+::[:\w]+\w$/) {
+			## Perl module like Net::SMTP
+			eval {
+				eval "require $value";
+				die if $@;
+				$x = $value;
+			};
+			last if $x;
+		}
+		elsif ($root =~ m#^/# and -x $root) {
 			$x = $value;
+			last;
+		}
+		else {
+			my @path = split /:/, $ENV{PATH};
+			for (@path) {
+				next unless -x "$_/$root";
+				$x = $value;
+				last TRYEXE;
+			}
 		}
 	}
-
-    config_error("Can't find executable ('$value') for the $var directive\n")
-		unless defined $x;
-    $x;
+	config_error( errmsg(
+					"Can't find executable (%s) for the %s directive\n",
+					join('|', @tries),
+					$var,
+					)
+		) unless defined $x;
+#::logDebug("$var=$x");
+	return $x;
 }
 
 sub parse_time {
-    my($var, $value) = @_;
-    my($n);
+	my($var, $value) = @_;
+	my($n);
 
 	$C->{Source}->{$var} = [$value];
 
-    $n = time_to_seconds($value);
-    config_error("Bad time format ('$value') in the $var directive\n")
+	$n = time_to_seconds($value);
+	config_error("Bad time format ('$value') in the $var directive\n")
 	unless defined $n;
-    $n;
+	$n;
 }
 
 # Determine catalog structure from Catalog config line(s)
@@ -1978,7 +2739,7 @@
 		push @{$cat->{$key}}, @rest if @rest;
 	}
 	elsif($key eq 'global') {
-		$cat->{$key} = $Global::AllowGlobal{$name} = is_yes($value);
+		$cat->{$key} = $Global::AllowGlobal->{$name} = is_yes($value);
 	}
 	elsif($key eq 'directive') {
 		no strict 'refs';
@@ -2003,7 +2764,7 @@
 		$cat->{$key} = $value;
 	}
 
-#::logDebug ("parsing catalog $name = " . ::uneval($cat));
+#::logDebug ("parsing catalog $name = " . uneval_it($cat));
 
 	$Global::Catalog{$name} = $cat;
 
@@ -2015,19 +2776,31 @@
 							FILTER_FROM   FILTER_FROM
 							FILTER_TO     FILTER_TO 
 							COLUMN_DEF    COLUMN_DEF
+							DEFAULT       DEFAULT
+							DEFAULT_SESSION       DEFAULT_SESSION
 							FIELD_ALIAS   FIELD_ALIAS
 							NUMERIC       NUMERIC
+							PREFER_NULL   PREFER_NULL
 							WRITE_CATALOG WRITE_CATALOG
 					! );
 
 my %Ary_ref = (   qw!
-							NAME         NAME
-							BINARY       BINARY 
-							POSTCREATE   POSTCREATE 
+						NAME                NAME
+						BINARY              BINARY 
+						PRECREATE           PRECREATE 
+						POSTCREATE          POSTCREATE 
+						INDEX               INDEX 
+						ALTERNATE_DSN       ALTERNATE_DSN
+						ALTERNATE_USER      ALTERNATE_USER
+						ALTERNATE_PASS      ALTERNATE_PASS
+						ALTERNATE_BASE_DN   ALTERNATE_BASE_DN
+						ALTERNATE_LDAP_HOST ALTERNATE_LDAP_HOST
+						ALTERNATE_BIND_DN   ALTERNATE_BIND_DN
+						ALTERNATE_BIND_PW   ALTERNATE_BIND_PW
 					! );
 
 sub parse_config_db {
-    my($name, $value) = @_;
+	my($name, $value) = @_;
 	my ($d, $new);
 	unless (defined $value && $value) { 
 		$d = {};
@@ -2108,18 +2881,20 @@
 			push @{$d->{$p}}, @v;
 		}
 		else {
-			config_warn errmsg(
-				"ConfigDatabase scalar parameter %s redefined to '%s', was %s.",
-							$p,
-							$val,
-							$d->{$p},
-						)
-				if defined $d->{$p};
+			defined $d->{$p}
+			and ! defined $C->{DatabaseDefault}{$p}
+				and config_warn(
+						"ConfigDatabase %s scalar parameter %s redefined to '%s', was %s.",
+						$d->{name},
+						$p,
+						$val,
+						$d->{$p},
+					);
 			$d->{$p} = $val;
 		}
 	}
 
-#::logDebug("d object: " . ::uneval($d));
+#::logDebug("d object: " . uneval_it($d));
 	if($d->{ACTIVE} and ! $d->{OBJECT}) {
 		my $name = $d->{'name'};
 		$d->{OBJECT} = Vend::Data::import_database($d)
@@ -2138,6 +2913,19 @@
 	
 }
 
+sub parse_dbauto {
+	my ($var, $value) = @_;
+	return '' unless $value;
+	my @inc = Vend::Table::DBI::auto_config($value);
+	my %noed;
+	for(@inc) {
+		my ($t, $thing) = @$_;
+		parse_boolean('NoImport', $t) unless $noed{$t}++;
+		parse_database('Database', "$t $thing");
+	}
+	return 1;
+}
+
 sub parse_database {
 	my ($var, $value) = @_;
 	my ($c, $new);
@@ -2179,6 +2967,22 @@
 			}
 		}
 # END LDAP
+		elsif(	$type =~ /^ic:(\w*)(:(.*))?/ ) {
+			my $class = $1;
+			my $dir = $3;
+			$d->{DIR} = $dir if $dir;
+			if($class =~ /^default$/i) {
+				# Do nothing
+			}
+			elsif($class) {
+				$class = uc $class;
+				if(! $Vend::Data::db_config{$class}) {
+					config_error("unrecognized IC database class: %s (from %s)", $class, $type);
+				}
+				$d->{Class} = $class;
+			}
+			$d->{'type'} = 6;
+		}
 		elsif(	"\U$type" eq 'TAB'	) {
 			$d->{'type'} = 6;
 		}
@@ -2203,7 +3007,13 @@
 		}
 		if    ($d->{'type'} eq '8')	{ $d->{Class} = 'DBI'						}
 		elsif ($d->{'type'} eq '9') { $d->{Class} = 'LDAP'						}
-		else 						{ $d->{Class} = $Global::Default_database	}
+		else 						{ $d->{Class} ||= $Global::Default_database	}
+
+		if($C->{DatabaseDefault}) {
+			while ( my($k, $v) = each %{$C->{DatabaseDefault}}) {
+				$d->{$k} = $v;
+			}
+		}
 
 		$d->{HOT} = 1 if $d->{Class} eq 'MEMORY';
 #::logDebug("parse_database: type $type -> $d->{type}");
@@ -2228,25 +3038,81 @@
 			$d->{$p} = [] unless defined $d->{$p};
 			push @{$d->{$p}}, @v;
 		}
-		elsif ($p =~ /^(MEMORY|GDBM|DB_FILE|LDAP)$/i) {
+		elsif ($p =~ /^(MEMORY|SDBM|GDBM|DB_FILE|LDAP)$/i) {
 			$d->{Class} = uc $p;
 		}
 		elsif ($p eq 'ALIAS') {
 			if (defined $c->{$val}) {
-				config_warn("Database '$val' already exists, can't alias.");
+				config_warn("Database '%s' already exists, can't alias.", $val);
 			}
 			else {
 				$c->{$val} = $d;
 			}
 		}
+		elsif ($p eq 'MAP') {
+			my @f = split(/\s+/, $val);
+			my %parms;
+			my %map_options = (fallback => 1);
+			my ($map_table, $map_column);
+			
+			if (@f < 2) {
+				config_error("At least two parameters needed for MAP.");
+			} elsif (@f == 2) {
+				@f = ($f[0], 'default', $f[1]);
+			}
+
+			my $field = shift @f;
+
+			if (@f % 2) {
+				config_error("Incomplete parameter list for MAP.");
+			}
+
+			# now we have a valid configuration and change the database type
+			# if necessary
+
+			unless ($d->{type} eq 10) {
+				$d->{OrigClass} = $d->{Class};
+				$d->{Class} = 'SHADOW';
+				$d->{type} = 10;
+			}
+
+			while (@f) {
+				my $map_key = shift @f;
+				my $map_value = shift @f;
+
+				if (exists $map_options{$map_key}) {
+					# option like fallback
+					$d->{MAP}->{$field}->{$map_key} = $map_value;
+				} else {
+					# mapping direction
+					if ($map_value =~ m%^((.*?)::(.*?)/)?(.*?)::(.*)%) {
+						if ($1) {
+							$d->{MAP}->{$field}->{$map_key} = {lookup_table => $2,
+															   lookup_column => $3,
+															   table => $4,
+															   column => $5}
+						} else {
+							$d->{MAP}->{$field}->{$map_key} = {table => $4,
+															   column => $5};
+						}
+					} else {
+						$d->{MAP}->{$field}->{$map_key} = {column => $map_value};
+					}
+				}
+			}
+		}
+
 		else {
-			config_warn errmsg(
-				"ConfigDatabase scalar parameter %s redefined to '%s', was %s.",
-							$p,
-							$val,
-							$d->{$p},
-						)
-				if defined $d->{$p};
+			defined $d->{$p}
+			and ! defined $C->{DatabaseDefault}{$p}
+				and
+				config_warn(
+					"Database %s scalar parameter %s redefined to '%s', was %s.",
+					$d->{name},
+					$p,
+					$val,
+					$d->{$p},
+				);
 			$d->{$p} = $val;
 		}
 		$d->{HOT} = 1 if $d->{Class} eq 'MEMORY';
@@ -2266,10 +3132,9 @@
 		parse_database('Database',"$table $file $type");
 		unless ($C->{Database}{$table}) {
 			config_warn(
-				errmsg(	"Bad $var value '%s': %s\n%s",
-						"Database $table $file $type",
-						::uneval($C->{Database}),
-						)
+				"Bad $var value '%s': %s\n%s",
+				"Database $table $file $type",
+				uneval($C->{Database}),
 			);
 			return '';
 		}
@@ -2282,30 +3147,30 @@
 	unless ($db = $C->{Database}{$table}) {
 		return if $Vend::ExternalProgram;
 		my $err = $@;
-		config_warn(
-			errmsg("Bad $var '%s': %s", $table, $err)
-		);
+		config_warn("Bad $var '%s': %s", $table, $err);
 		return '';
 	}
 	$db = Vend::Data::import_database($db);
 	if(! $db) {
 		my $err = $@;
-		config_warn(
-			errmsg("Bad $var '%s': %s", $table, $err)
-		);
+		config_warn("Bad $var '%s': %s", $table, $err);
 		return '';
 	}
 	return ($db, $table);
 }
 
-sub parse_routeconfig {
+my %Columnar = (Locale => 1);
+
+sub parse_configdb {
 	my ($var, $value) = @_;
 
 	my ($file, $type);
 	return '' if ! $value;
 	local($Vend::Cfg) = $C;
-
-	my ($db, $table) = get_configdb($var, $value);
+	my ($db, $table);
+	eval {
+		($db, $table) = get_configdb($var, $value);
+	};
 
 	return '' if ! $db;
 
@@ -2314,20 +3179,74 @@
 	my @n;			# names of locales
 	my @h;			# names of locales
 
+	my $base_direc = $var;
+	$base_direc =~ s/Database$//;
+	my $repos_name = $base_direc . '_repository';
+	my $repos = $C->{$repos_name} ||= {};
+
 	@n = $db->columns();
 	shift @n;
 	my $i;
-	while( ($k, undef, @f ) = $db->each_record) {
-#::logDebug("Got route key=$k f=@f");
-		for ($i = 0; $i < @f; $i++) {
-			next unless length($f[$i]);
-			$C->{Route_repository}{$k}{$n[$i]} = $f[$i];
+	if($Columnar{$base_direc}) {
+		my @l;
+		for(@n) {
+			$repos->{$_} ||= {};
+			push @l, $repos->{$_};
+		}
+		my $i;
+		while( ($k , undef, @f ) = $db->each_record) {
+			for ($i = 0; $i < @f; $i++) {
+				next unless length($f[$i]);
+				$l[$i]->{$k} = $f[$i];
+			}
+		}
+	}
+	else {
+		while( ($k, undef, @f ) = $db->each_record) {
+			for ($i = 0; $i < @f; $i++) {
+				next unless length($f[$i]);
+				$repos->{$k}{$n[$i]} = $f[$i];
+			}
 		}
 	}
 	$db->close_table();
 	return $table;
 }
 
+sub parse_dirconfig {
+	my ($var, $value) = @_;
+
+	return '' if ! $value;
+	$value =~ s/(\w+)\s+//;
+	my $direc = $1;
+#::logDebug("direc=$direc value=$value");
+	 
+	my $ref = $C->{$direc};
+
+	unless(ref($ref) eq 'HASH') {
+		config_error("DirConfig called for non-hash configuration directive.");
+	}
+
+	my $source = $C->{$var}   || {};
+	my $sref = $source->{$direc} || {};
+
+	my @dirs = grep -d $_, glob($value);
+	foreach my $dir (@dirs) {
+		opendir(DIRCONFIG, $dir)
+			or next;
+		my @files = grep /^\w+$/, readdir(DIRCONFIG);
+		for(@files) {
+			next unless -f "$dir/$_";
+#::logDebug("reading key=$_ from $dir/$_");
+			$ref->{$_} = readfile("$dir/$_", $Global::NoAbsolute, 0);
+			$ref->{$_} = substitute_variable($ref->{$_}) if $C->{ParseVariables};
+			$sref->{$_} = "$dir/$_";
+		}
+	}
+	$source->{$direc} = $sref;
+	return $source;
+}
+
 sub parse_dbconfig {
 	my ($var, $value) = @_;
 
@@ -2335,7 +3254,10 @@
 	return '' if ! $value;
 	local($Vend::Cfg) = $C;
 
-	my ($db, $table) = get_configdb($var, $value);
+	my ($db, $table);
+	eval {
+		($db, $table) = get_configdb($var, $value);
+	};
 
 	return '' if ! $db;
 
@@ -2381,7 +3303,7 @@
 	my ($db, $table) = get_configdb($var, $value);
 	$db = $db->ref();
 	my $kindex = $db->config('KEY_INDEX');
-#::logGlobal("kindex=$kindex");
+#::logDebug("kindex=$kindex");
 	local($^W) = 0;
 	my ($k, @f);	# key and fields
 	my @l;			# refs to locale repository
@@ -2403,7 +3325,7 @@
 		for ($i = 0; $i < @f; $i++) {
 			next if $i == $kindex;
 			next unless length $f[$i];
-#::logGlobal("f-i=$f[$i] i=$i kindex=$kindex");
+#::logDebug("f-i=$f[$i] i=$i kindex=$kindex");
 			Vend::Config::parse_database('', "$n[$i] $k $f[$i]");
 		}
 	}
@@ -2434,6 +3356,7 @@
 
 	my (@files) = glob($value);
 	for(@files) {
+		next unless $_;
 		config_error(
 		  "No leading / allowed if NoAbsolute set. Contact administrator.\n")
 		if m.^/. and $Global::NoAbsolute;
@@ -2457,13 +3380,13 @@
 	my ($var, $value) = @_;
 	my ($c, $name, $param);
 
-    if(defined $C) {
-        $c = $C->{$var};
-    }
-    else { 
-        no strict 'refs';
-        $c = ${"Global::$var"};
-    }
+	if(defined $C) {
+		$c = $C->{$var};
+	}
+	else { 
+		no strict 'refs';
+		$c = ${"Global::$var"};
+	}
 
 	if ($var eq 'Variable' || $var eq 'Member') {
 		$value =~ s/^\s*(\w+)\s*//;
@@ -2490,56 +3413,188 @@
 
 my %tagCanon = ( qw(
 
+	group			Group
+	actionmap		ActionMap
+	arraycode		ArrayCode
+	hashcode		HashCode
+	coretag  		CoreTag
+	filter			Filter
+	formaction		FormAction
+	ordercheck		OrderCheck
+	usertag			UserTag
+	systemtag		SystemTag
+	widget  		Widget
+
 	alias			Alias
 	addattr  		addAttr
 	attralias		attrAlias
 	cannest			canNest
+	description  	Description
 	documentation	Documentation
-	endhtml			endHTML
+	gobble			Gobble
 	hasendtag		hasEndTag
 	implicit		Implicit
-	inserthtml		insertHTML
-	insidehtml		insideHTML
 	interpolate		Interpolate
 	invalidatecache	InvalidateCache
 	isendanchor		isEndAnchor
-	lookaheadhtml	lookaheadHTML
+	norearrange		noRearrange
 	order			Order
 	posnumber		PosNumber
 	posroutine		PosRoutine
-	replaceattr		replaceAttr
-	replacehtml		replaceHTML
+	maproutine		MapRoutine
+	noreparse		NoReparse
 	required		Required
 	routine			Routine
-
+	version			Version
 ));
 
 
-my %tagAry 	= ( qw! Order 1 Required 1 ! );
+my %tagAry 	= ( qw! Order 1 Required 1 Version 1 ! );
 my %tagHash	= ( qw!
-				replaceAttr	1
-				Implicit	1
-				attrAlias	1
+                attrAlias   1
+                Implicit    1
 				! );
 my %tagBool = ( qw!
-				hasEndTag	1
-				Interpolate 1
-				canNest		1
-				isEndAnchor	1
-				addAttr 	1
-				isOperator	1
+                ActionMap   1
+                addAttr     1
+                canNest     1
+                Filter      1
+                FormAction  1
+                hasEndTag   1
+                Interpolate 1
+                isEndAnchor 1
+                isOperator  1
+                ItemAction  1
+				noRearrange	1
+				NoReparse   1
+                OrderCheck  1
+                UserTag     1
 				! );
 
+my %current_dest;
+my %valid_dest = qw/
+					actionmap        ActionMap
+					coretag          UserTag
+					filter           Filter
+					formaction       FormAction
+					itemaction       ItemAction
+					ordercheck       OrderCheck
+					usertag          UserTag
+					hashcode         HashCode
+					arraycode        ArrayCode
+					widget           Widget
+				/;
+
+sub finalize_mapped_code {
+	my $c = $C ? $C->{CodeDef} : $Global::CodeDef;
+	my $ref;
+	my $cfg;
+
+	if(! $C and my $ref = $c->{Filter}) {
+		next unless $ref = $ref->{Routine};
+		for(keys %$ref) {
+			$Vend::Interpolate::Filter{$_} = $ref->{$_};
+		}
+	}
+
+	no strict 'refs';
+	for my $type (qw/ ActionMap FormAction ItemAction OrderCheck /) {
+		my $ref;
+		my $r;
+		next unless $r = $c->{$type};
+		next unless $ref = $r->{Routine};
+		my $cfg = $C
+				  ? ($C->{$type}		||= {})
+				  : (${"Global::$type"}	||= {})
+				  ;
+		for(keys %$ref ) {
+			$cfg->{$_} = $ref->{$_};
+		}
+	}
+}
+
+my %Compiled = qw/
+					Routine     Routine
+					PosRoutine  PosRoutine
+					HashCode    Routine
+					ArrayCode   Routine
+				/;
+
+sub parse_mapped_code {
+	my ($var, $value) = @_;
+
+	return {} if ! $value;
+
+	## Can't give CodeDef a default or this will be premature
+	get_system_code() unless defined $SystemCodeDone;
+
+	my($tag,$p,$val) = split /\s+/, $value, 3;
+	
+	# Canonicalize
+	$p = $tagCanon{lc $p};
+	$tag =~ tr/-/_/;
+	$tag =~ s/\W//g
+		and config_warn("Bad characters removed from '%s'.", $tag);
+
+	my $repos = $C ? ($C->{CodeDef} ||= {}) : ($Global::CodeDef ||= {});
+
+	my $dest = $valid_dest{lc $p} || $current_dest{$tag} || $CodeDest;
+
+	if(! $dest) {
+		config_warn("no destination for %s %s, skipping.", $var, $tag);
+		return $repos;
+	}
+	$current_dest{$tag} = $dest;
+	$repos->{$dest} ||= {};
+
+	my $c = $repos->{$dest};
+
+	if($Compiled{$p}) {
+		$c->{$Compiled{$p}} ||= {};
+		parse_action($var, "$tag $val", $c->{$Compiled{$p}} ||= {});
+	}
+	elsif(defined $tagAry{$p}) {
+		my(@v) = Text::ParseWords::shellwords($val);
+		$c->{$p}{$tag} = [] unless defined $c->{$p}{$tag};
+		push @{$c->{$p}{$tag}}, @v;
+	}
+	elsif(defined $tagHash{$p}) {
+		my(%v) = Text::ParseWords::shellwords($val);
+		$c->{$p}{$tag} = {} unless defined $c->{$p}{$tag};
+		for (keys %v) {
+		  $c->{$p}{$tag}{$_} = $v{$_};
+		}
+	}
+	elsif(defined $tagBool{$p}) {
+		$c->{$p}{$tag} = 1
+			unless defined $val and $val =~ /^[0nf]/i;
+	}
+	else {
+		config_warn("%s %s scalar parameter %s redefined.", $var, $tag, $p)
+			if defined $c->{$p}{$tag};
+		$c->{$p}{$tag} = $val;
+	}
+
+	return $repos;
+}
+
 # Parses the user tags
 sub parse_tag {
 	my ($var, $value) = @_;
-	my ($c, $new);
+	my ($new);
+
+	return if $Vend::ExternalProgram;
 
 	unless (defined $value && $value) { 
 		return {};
 	}
 
-	$c = defined $C ? $C->{UserTag} : $Global::UserTag;
+	return parse_mapped_code($var, $value)
+		if $var ne 'UserTag';
+
+	get_system_code() unless defined $SystemCodeDone;
+
+	my $c = defined $C ? $C->{UserTag} : $Global::UserTag;
 
 	my($tag,$p,$val) = split /\s+/, $value, 3;
 	
@@ -2547,14 +3602,34 @@
 	$p = $tagCanon{lc $p};
 	$tag =~ tr/-/_/;
 	$tag =~ s/\W//g
-		and config_warn("Bad characters removed from '$tag'.");
+		and config_warn("Bad characters removed from '%s'.", $tag);
 
 	unless ($p) {
-		config_warn "Bad user tag parameter '$p' for '$tag', skipping.";
+		config_warn("Bad user tag parameter '%s' for '%s', skipping.", $p, $tag);
 		return $c;
 	}
 
-	if($p eq 'Routine' or $p eq 'posRoutine') {
+	if($CodeDest and $CodeDest eq 'CoreTag') {
+		return $c unless $Global::TagInclude->{$tag} || $Global::TagInclude->{ALL};
+	}
+
+	if($p eq 'Routine' or $p eq 'PosRoutine') {
+		if (defined $c->{Source}->{$tag}->{$p}){
+			config_error(
+				errmsg(
+					"Duplicate usertag %s found",
+					$tag,
+				)
+			);
+		}
+		if (defined $C && defined $Global::UserTag->{Source}->{$tag}->{$p}){
+			config_warn(
+				errmsg(
+					"Local usertag %s overrides global definition",
+					$tag,
+				)
+			);
+		}
 
 		my $sub;
 		$c->{Source}->{$tag}->{$p} = $val;
@@ -2563,50 +3638,61 @@
 			my $code = $val;
 			$code =~ s'$Vend::Session->'$foo'g;
 			$code =~ s'$Vend::Cfg->'$bar'g;
+			$safe->trap(@{$Global::SafeTrap});
 			$safe->untrap(@{$Global::SafeUntrap});
 			$sub = $safe->reval($code);
 			if($@) {
 				config_warn(
-					 errmsg(
 						"UserTag '%s' subroutine failed safe check: %s",
 						$tag,
 						$@,
-						)
 				);
 				return $c;
 			}
 		}
-		my $fail;
+		local($^W) = 1;
+		my $fail = '';
 		{
-			local $SIG{'__WARN__'} = sub {$fail .= "@_";};
+			local $SIG{'__WARN__'} = sub {$fail .= "$_[0]\n";};
 			eval {
 				package Vend::Interpolate;
 				$sub = eval $val;
-				die $@ if $@;
+				warn $@ if $@;
 			};
 		}
-		if($@ or $fail) {
+		if($@) {
 			config_warn(
-					 errmsg(
 						"UserTag '%s' subroutine failed compilation:\n\n\t%s",
 						$tag,
-						"$fail $@",
-						)
+					"$@ (warnings=$fail)",
 			);
 			return $c;
 		}
-		else {
+		elsif($fail) {
 			config_warn(
-				errmsg(
-					"UserTag '%s' code is not a subroutine reference",
+						"Warning while compiling UserTag '%s':\n\n\t%s",
 					$tag,
-				)
-			) unless ref($sub) =~ /CODE/;
+						$fail,
+			);
+			return $c;
 		}
+		config_warn(
+				"UserTag '%s' code is not a subroutine reference",
+				$tag,
+		) unless ref($sub) eq 'CODE';
+
 		$c->{$p}{$tag} = $sub;
 		$c->{Order}{$tag} = []
 			unless defined $c->{Order}{$tag};
 	}
+	elsif (! $C and $p eq 'MapRoutine') {
+		$val =~ s/^\s+//;
+		$val =~ s/\s+$//;
+		no strict 'refs';
+		$c->{Routine}{$tag} = \&{"$val"};
+		$c->{Order}{$tag} = []
+			unless defined $c->{Order}{$tag};
+	}
 	elsif(defined $tagAry{$p}) {
 		my(@v) = Text::ParseWords::shellwords($val);
 		$c->{$p}{$tag} = [] unless defined $c->{$p}{$tag};
@@ -2624,7 +3710,7 @@
 			unless defined $val and $val =~ /^[0nf]/i;
 	}
 	else {
-		config_warn errmsg("UserTag %s scalar parameter %s redefined.", $tag, $p)
+		config_warn("UserTag %s scalar parameter %s redefined.", $tag, $p)
 			if defined $c->{$p}{$tag};
 		$c->{$p}{$tag} = $val;
 	}
@@ -2635,6 +3721,7 @@
 sub parse_eval {
 	my($var,$value) = @_;
 	return '' unless $value =~ /\S/;
+	return if $Vend::ExternalProgram;
 	return eval $value;
 }
 
@@ -2657,35 +3744,59 @@
 		$c = ${"Global::$var"};
 	}
 
-	if($value =~ /\n/) {
-		($name, $param) = split /\s+/, $value, 2;
-		chomp $param;
-	}
-	else {
-		($name, $param) = split /\s+/, $value, 2;
-	}
+	($name, $param) = split /\s+/, $value, 2;
+	chomp $param;
 	$c->{$name} = $param;
 	return $c;
 }
 
 
-# Designed to parse Global subroutines only
+# Parse Sub and GlobalSub
 sub parse_subroutine {
 	my ($var, $value) = @_;
 	my ($c, $name);
+
+	return if $Vend::ExternalProgram;
+
+#::logDebug("parsing subroutine $var, " . substr($value, 0, 20) ) unless $C;
 	unless (defined $value and $value) { 
 		$c = {};
 		return $c;
 	}
+#::logDebug("into parse for $var") unless $C;
 
 	no strict 'refs';
 	$c = defined $C ? $C->{$var} : ${"Global::$var"};
 
-	$value =~ s/\s*sub\s+(\w+)\s*{/sub {/;
-	config_error("Bad $var: no subroutine name? ") unless $name = $1;
+	$value =~ s/^(\w+\s+)?\s*sub\s+(\w+\s*)?{/sub {/;
+
+	if($1 and $2) {
+		$name = $1;
+		my $alt = $2;
+		$name =~ s/\s+//;
+		$alt =~ s/\s+//;
+		config_warn("%s %s: named also %s?", $var, $name, $alt);
+		
+	}
+	else {
+		$name = $1 || $2;
+	}
+
+	unless ($name) {
+		config_error(
+			errmsg(
+				"Bad %s: no subroutine name",
+				$var,
+			)
+		);
+	}
+
+	$name =~ s/\s+//g;
+#::logDebug("into parse for $var, found sub named $name") unless $C;
 	# Untainting
 	$value =~ /([\000-\377]*)/;
 	$value = $1;
+
 	if(! defined $C) {
 		$c->{$name} = eval $value;
 	}
@@ -2703,7 +3814,8 @@
 	}
 
 #::logDebug("Parsing subroutine/variable (C=$C) $var=$name");
-	config_error("Bad $var '$name'") if $@;
+	config_error("Bad $var '$name': $@") if $@;
+#::logDebug("Parsed subroutine/variable $var=$name code=$c->{$name}") unless $C;
 	return $c;
 }
 
@@ -2725,238 +3837,310 @@
 # Returns 1 for Yes and 0 for No.
 
 sub parse_yesno {
-    my($var, $value) = @_;
-    $_ = $value;
-    if (m/^y/i || m/^t/i || m/^1/) {
+	my($var, $value) = @_;
+	$_ = $value;
+	if (m/^y/i || m/^t/i || m/^1/ || m/^on/i) {
 		return 1;
-    }
-	elsif (m/^n/i || m/^f/i || m/^0/) {
+	}
+	elsif (m/^n/i || m/^f/i || m/^0/ || m/^of/i) {
 		return 0;
-    }
+	}
 	else {
 		config_error("Use 'yes' or 'no' for the $var directive\n");
-    }
+	}
 }
 
 sub parse_permission {
-    my($var, $value) = @_;
+	my($var, $value) = @_;
 
-    $_ = $value;
-    tr/A-Z/a-z/;
-    if ($_ ne 'user' and $_ ne 'group' and $_ ne 'world') {
-	config_error(
-"Permission must be one of 'user', 'group', or 'world' for
-the $var directive\n");
-    }
-    $_;
-}
+	$_ = $value;
+	tr/A-Z/a-z/;
+	if ($_ ne 'user' and $_ ne 'group' and $_ ne 'world') {
+		config_error("Permission must be one of 'user', 'group', or 'world' for the $var directive\n");
+	}
+	$_;
+}
+
+$StdTags = <<'EOF';
+				:core "
+					accessories
+					area
+					assign
+					attr_list
+					banner
+					calc
+					calcn
+					cart
+					catch
+					cgi
+					charge
+					checked
+					control
+					control_set
+					counter
+					currency
+					data
+					default
+					description
+					discount
+					dump
+					ecml
+					either
+					error
+					export
+					field
+					file
+					filter
+					flag
+					fly_list
+					fly_tax
+					handling
+					harness
+					html_table
+					import
+					include
+					index
+					input_filter
+					item_list
+					log
+					loop
+					mail
+					msg
+					mvasp
+					nitems
+					onfly
+					options
+					order
+					page
+					perl
+					price
+					process
+					profile
+					query
+					read_cookie
+					record
+					region
+					row
+					salestax
+					scratch
+					scratchd
+					search_region
+					selected
+					set
+					set_cookie
+					seti
+					setlocale
+					shipping
+					shipping_desc
+					soap
+					sql
+					strip
+					subtotal
+					tag
+					time
+					timed_build
+					tmp
+					tmpn
+					total_cost
+					tree
+					try
+					update
+					userdb
+					value
+					value_extended
+					warnings
+				"
+				:base "
+						area
+						cgi
+						data
+						either
+						filter
+						flag
+						loop
+						page
+						query
+						scratch
+						scratchd
+						set
+						seti
+						tag
+						tmp
+						tmpn
+						value
+				"
+				:commerce "
+						assign
+						cart
+						charge
+						currency
+						description
+						discount
+						ecml
+						error
+						field
+						fly_list
+						fly_tax
+						handling
+						item_list
+						nitems
+						onfly
+						options
+						order
+						price
+						salestax
+						shipping
+						shipping_desc
+						subtotal
+						total_cost
+						userdb
+				"
+				:data "
+						data
+						export
+						field
+						flag
+						import
+						index
+						query
+						record
+						sql
+				"
+				:form "
+					accessories
+					cgi
+					checked
+					error
+					flag
+					input_filter
+					msg
+					process
+					profile
+					selected
+					update
+					value_extended
+					warnings
+				"
+				:debug "
+					catch
+					dump
+					error
+					flag
+					harness
+					log
+					msg
+					tag
+					try
+					warnings
+				"
+				:file "
+					counter
+					file
+					include
+					log
+					value_extended
+				"
+				:http "
+					area
+					cgi
+					filter
+					input_filter
+					page
+					process
+					read_cookie
+					set_cookie
+					value_extended
+				"
+				:crufty "
+					banner
+					default
+					ecml
+					html_table
+					onfly
+					sql
+				"
+				:text "
+					row
+					strip
+					filter
+				"
+				:html "
+					accessories
+					checked
+					filter
+					html_table
+					process
+				"
+				:mail "
+					mail
+				"
+				:perl "
+					perl
+					calc
+					calcn
+					mvasp
+				"
+				:time "
+					time
+				"
+EOF
 
 1;
 
 __DATA__
-mv_action                mv_action
-mv_admin                 mv_admin
-mv_alinkcolor            mv_alinkcolor
-mv_all_chars             mv_all_chars
-mv_arg                   mv_arg
-mv_argument              mv_argument
-mv_background            mv_background
-mv_base_directory        mv_base_directory
-mv_begin_string          mv_begin_string
-mv_bgcolor               mv_bgcolor
-mv_cache_key             mv_cache_key
-mv_cache_price           mv_cache_price
-mv_cartname              mv_cartname
-mv_case                  mv_case
-mv_cat                   mv_cat
-mv_change_frame          mv_change_frame
-mv_check                 mv_check
-mv_click                 mv_click
-mv_click_arg             mv_click_arg
-mv_click_map             mv_click_map
-mv_column_op             mv_column_op
-mv_control               mv_control
-mv_cookie_password       mv_cookie_password
-mv_cookie_username       mv_cookie_username
-mv_coordinate            mv_coordinate
-mv_credit_card_error     mv_credit_card_error
-mv_credit_card_exp_all   mv_credit_card_exp_all
-mv_credit_card_exp_month mv_credit_card_exp_month
-mv_credit_card_exp_year  mv_credit_card_exp_year
-mv_credit_card_force     mv_credit_card_force
-mv_credit_card_info      mv_credit_card_info
-mv_credit_card_number    mv_credit_card_number
-mv_credit_card_type      mv_credit_card_type
-mv_credit_card_valid     mv_credit_card_valid
-mv_currency              mv_currency
-mv_cyber_mode            mv_cyber_mode
-mv_cybermode             mv_cybermode
-mv_data_decode           mv_data_decode
-mv_data_fields           mv_data_fields
-mv_data_function         mv_data_function
-mv_data_key              mv_data_key
-mv_data_table            mv_data_table
-mv_data_verify           mv_data_verify
-mv_delay_page            mv_delay_page
-mv_dict_end              mv_dict_end
-mv_dict_fold             mv_dict_fold
-mv_dict_limit            mv_dict_limit
-mv_dict_look             mv_dict_look
-mv_dict_order            mv_dict_order
-mv_discount              mv_discount
-mv_doit                  mv_doit
-mv_email                 mv_email
-mv_error_                mv_error_
-mv_exact_match           mv_exact_match
-mv_expire_time           mv_expire_time
-mv_failpage              mv_failpage
-mv_field_names           mv_field_names
-mv_first_match           mv_first_match
-mv_global                mv_global
-mv_handling              mv_handling
-mv_head_skip             mv_head_skip
-mv_ib                    mv_ib
-mv_ignore_frame          mv_ignore_frame
-mv_index_delim           mv_index_delim
-mv_item_object           mv_item_object
-mv_last                  mv_last
-mv_linkcolor             mv_linkcolor
-mv_list_only             mv_list_only
-mv_locale                mv_locale
-mv_matchlimit            mv_matchlimit
-mv_max_matches           mv_max_matches
-mv_mi                    mv_mi
-mv_min_string            mv_min_string
-mv_more_matches          mv_more_matches
-mv_more_id               mv_more_id
-mv_negate                mv_negate
-mv_nextpage              mv_nextpage
-mv_no_cache              mv_no_cache
-mv_no_count              mv_no_count
-mv_no_order_increment    mv_no_order_increment
-mv_no_session_id         mv_no_session_id
-mv_numeric               mv_numeric
-mv_order_                mv_order_
-mv_order_base            mv_order_base
-mv_order_group           mv_order_group
-mv_order_mv_ib           mv_order_mv_ib
-mv_order_number          mv_order_number
-mv_order_profile         mv_order_profile
-mv_order_quantity        mv_order_quantity
-mv_order_receipt         mv_order_receipt
-mv_order_report          mv_order_report
-mv_order_route           mv_order_route
-mv_order_subject         mv_order_subject
-mv_orderpage             mv_orderpage
-mv_orsearch              mv_orsearch
-mv_page                  mv_page
-mv_password              mv_password
-mv_password_old          mv_password_old
-mv_pc                    mv_pc
-mv_profile               mv_profile
-mv_range_alpha           mv_range_alpha
-mv_range_look            mv_range_look
-mv_range_max             mv_range_max
-mv_range_min             mv_range_min
-mv_raw_dict_look         mv_raw_dict_look
-mv_raw_searchspec        mv_raw_searchspec
-mv_record_delim          mv_record_delim
-mv_return_all            mv_return_all
-mv_return_delim          mv_return_delim
-mv_return_fields         mv_return_fields
-mv_return_file_name      mv_return_file_name
-mv_return_format         mv_return_format
-mv_return_reference      mv_return_reference
-mv_return_spec           mv_return_spec
-mv_save_session          mv_save_session
-mv_search_arg            mv_search_arg
-mv_search_debug          mv_search_debug
-mv_search_field          mv_search_field
-mv_search_file           mv_search_file
-mv_search_immediate      mv_search_immediate
-mv_search_line_return    mv_search_line_return
-mv_search_map            mv_search_map
-mv_search_match_count    mv_search_match_count
-mv_search_over_msg       mv_search_over_msg
-mv_search_page           mv_search_page
-mv_searchspec            mv_searchspec
-mv_searchtype            mv_searchtype
-mv_separate_items        mv_separate_items
-mv_session_id            id
-mv_shipmode              mv_shipmode
-mv_si                    mv_si
-mv_sort_field            mv_sort_field
-mv_sort_option           mv_sort_option
-mv_special_              mv_special_
-mv_spelling_errors       mv_spelling_errors
-mv_sql_array             mv_sql_array
-mv_sql_hash              mv_sql_hash
-mv_sql_hash_order        mv_sql_hash_order
-mv_sql_names             mv_sql_names
-mv_sql_param             mv_sql_param
-mv_sql_query             mv_sql_query
-mv_status_               mv_status_
-mv_sub                   mv_sub
-mv_subroutine            mv_subroutine
-mv_substring_match       mv_substring_match
-mv_textcolor             mv_textcolor
-mv_todo                  mv_todo
-mv_unique                mv_unique
-mv_update_empty          mv_update_empty
-mv_username              mv_username
-mv_value                 mv_value
-mv_verbatim_columns      mv_verbatim_columns
-mv_verify                mv_verify
-mv_vlinkcolor            mv_vlinkcolor
 mv_all_chars             ac
+mv_arg                   mv_arg
 mv_base_directory        bd
 mv_begin_string          bs
-mv_coordinate            co
 mv_case                  cs
+mv_cat                   mv_cat
+mv_column_op             op
+mv_coordinate            co
+mv_delay_page            dp
 mv_dict_end              de
 mv_dict_fold             df
 mv_dict_limit            di
 mv_dict_look             dl
 mv_dict_order            do
-mv_delay_page            dp
-mv_record_delim          dr
 mv_exact_match           em
-mv_spelling_errors       er
-mv_search_file           fi
-mv_first_match           fm
 mv_field_names           fn
+mv_first_match           fm
 mv_head_skip             hs
 mv_index_delim           ix
-mv_search_line_return    lr
 mv_list_only             lo
 mv_matchlimit            ml
 mv_max_matches           mm
-mv_more_matches          MM
-mv_more_id               mi
-mv_profile               mp
 mv_min_string            ms
+mv_more_id               mi
+mv_more_matches          MM
 mv_negate                ne
 mv_numeric               nu
-mv_column_op             op
 mv_orsearch              os
-mv_return_all            ra
-mv_search_immediate      si
-mv_return_delim          rd
-mv_return_fields         rf
+mv_pc                    mv_pc
+mv_profile               mp
 mv_range_alpha           rg
 mv_range_look            rl
+mv_range_max             rx
 mv_range_min             rm
+mv_record_delim          dr
+mv_return_all            ra
+mv_return_delim          rd
+mv_return_fields         rf
 mv_return_file_name      rn
 mv_return_reference      rr
 mv_return_spec           rs
-mv_range_max             rx
-mv_searchspec            se
 mv_search_field          sf
+mv_search_file           fi
+mv_search_immediate      si
+mv_search_line_return    lr
 mv_search_page           sp
-mv_sql_query             sq
+mv_searchspec            se
 mv_searchtype            st
-mv_substring_match       su
+mv_session_id            id
 mv_sort_field            tf
 mv_sort_option           to
+mv_spelling_errors       er
+mv_sql_query             sq
+mv_substring_match       su
 mv_unique                un
 mv_value                 va



1.5.4.2   +54 -22    interchange/lib/Vend/Control.pm


rev 1.5.4.2, prev_rev 1.5.4.1
Index: Control.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Control.pm,v
retrieving revision 1.5.4.1
retrieving revision 1.5.4.2
diff -u -r1.5.4.1 -r1.5.4.2
--- Control.pm	20 Oct 2000 10:18:42 -0000	1.5.4.1
+++ Control.pm	25 Jan 2003 22:21:27 -0000	1.5.4.2
@@ -1,14 +1,11 @@
-# Control.pm - Interchange routines rarely used or not requiring much performance
+# Vend::Control - Routines that alter the running Interchange daemon
 # 
-# $Id: Control.pm,v 1.5.4.1 2000/10/20 10:18:42 racke Exp $
+# $Id: Control.pm,v 1.5.4.2 2003/01/25 22:21:27 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -32,6 +29,7 @@
 @EXPORT = qw/
 				signal_reconfig
 				signal_add
+				signal_cron
 				signal_remove
 				control_interchange
 				change_catalog_directive
@@ -47,28 +45,45 @@
 	my (@cats) = @_;
 	for(@cats) {
 		my $ref = $Global::Catalog{$_}
-			or die ::errmsg("Unknown catalog '%s'. Stopping.\n", $_);
-		Vend::Util::writefile("$Global::ConfDir/reconfig", "$ref->{script}\n");
+			or die errmsg("Unknown catalog '%s'. Stopping.\n", $_);
+		Vend::Util::writefile("$Global::RunDir/reconfig", "$ref->{script}\n");
 	}
 }
 
+sub signal_cron {
+	shift;
+	$Vend::mode = 'cron';
+	my $arg = shift;
+	my ($cat, $job) = split /\s*=\s*/, $arg, 2;
+	$Vend::CronCat = $cat;
+#::logGlobal("signal_cron: called cron cat=$cat job=$job");
+	$job = join ",", $job, $Vend::CronJob;
+	$job =~ s/^,+//;
+	$job =~ s/,+$//;
+	$Vend::CronJob = $job;
+	Vend::Util::writefile("$Global::RunDir/restart", "cron $cat $job\n");
+#::logGlobal("signal_cron: wrote file, ready to control_interchange");
+	control_interchange('cron', 'HUP');
+}
+
 sub signal_remove {
 	shift;
 	$Vend::mode = 'reconfig';
 	my $cat = shift;
-	Vend::Util::writefile("$Global::ConfDir/restart", "remove catalog $cat\n");
+	Vend::Util::writefile("$Global::RunDir/restart", "remove catalog $cat\n");
 	control_interchange('remove', 'HUP');
 }
 
 sub signal_add {
 	$Vend::mode = 'reconfig';
-	Vend::Util::writefile("$Global::ConfDir/restart", <>);
+	Vend::Util::writefile("$Global::RunDir/restart", <>);
 	control_interchange('add', 'HUP');
 }
 
 sub control_interchange {
 	my ($mode, $sig, $restart) = @_;
 
+	$Vend::ControllingInterchange = 1;
 	unless(-f $Global::PIDfile) {
 		warn errmsg(
 			"The Interchange server was not running (%s).\n",
@@ -77,14 +92,13 @@
 		exit 1 unless $restart;
 		return;
 	}
-	Vend::Server::open_pid()
+	my $pidh = Vend::Server::open_pid()
 		or die errmsg(
 				"Couldn't open PID file %s: %s\n",
 				$Global::PIDfile,
 				$!,
 				);
-	my $pid = Vend::Server::grab_pid();
-	Vend::Server::unlink_pid();
+	my $pid = Vend::Server::grab_pid($pidh);
 	if(! $pid) {
 		warn errmsg(<<EOF);
 The previous Interchange server was not running and probably
@@ -95,8 +109,26 @@
 	if(! $sig) {
 		$sig = $mode ne 'kill' ? 'TERM' : 'KILL';
 	}
-	print "Killing Interchange server $pid with $sig.\n"
-		unless $Vend::Quiet;
+	my $msg;
+	if($mode eq 'cron') {
+		$msg = errmsg(
+					"Dispatching jobs=%s for cat %s to Interchange server %s with %s.\n",
+					$Vend::CronJob,
+					$Vend::CronCat,
+					$pid,
+					$sig,
+				);
+	}
+	else {
+		$msg = errmsg(
+					"Killing Interchange server %s with %s.\n",
+					$pid,
+					$sig,
+				);
+	} 
+
+	print $msg unless $Vend::Quiet;
+
 	kill $sig, $pid
 		or die errmsg("Interchange server would not stop.\n");
 	exit 0 unless $restart;
@@ -108,7 +140,7 @@
 	my @aliases;
 
 	unless(defined $g) {
-		::logGlobal( "Attempt to remove non-existant catalog %s." , $name );
+		logGlobal( {level => 'error'}, "Attempt to remove non-existant catalog %s." , $name );
 		return undef;
 	}
 
@@ -151,7 +183,7 @@
 			if (exists $Global::Selector{$_}
 				and $Global::SelectorAlias{$_} ne $g->{'script'})
 			{
-				logGlobal("Alias %s used a second time, skipping.", $_);
+				logGlobal({level => 'notice'}, "Catalog ScriptAlias %s used a second time, skipping.", $_);
 				next;
 			}
 			elsif (m![^-\w_\~:#/.]!) {
@@ -162,7 +194,7 @@
 		}
 	}
 
-	Vend::Util::writefile("$Global::ConfDir/reconfig", "$script\n");
+	Vend::Util::writefile("$Global::RunDir/reconfig", "$script\n");
 	my $msg = <<EOF;
 Added/changed catalog %s:
 
@@ -170,7 +202,7 @@
  Script:    %s
 EOF
 	
-	logGlobal( $msg, $name, $dir, $script);
+	logGlobal({level => 'notice'},  $msg, $name, $dir, $script);
 
 	$Global::Selector{$g->{script}} = $c;
 }
@@ -197,7 +229,7 @@
 	$Global::Structure->{$ref->[0]} = $ref->[1]
 		if $Global::DumpStructure;
 
-	dump_structure($Global::Structure, "$Global::ConfDir/$Global::ExeName")
+	dump_structure($Global::Structure, "$Global::RunDir/$Global::ExeName")
 		if $Global::DumpStructure;
 	return 1;
 }



1.13.4.10 +1134 -151 interchange/lib/Vend/Data.pm


rev 1.13.4.10, prev_rev 1.13.4.9
Index: Data.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Data.pm,v
retrieving revision 1.13.4.9
retrieving revision 1.13.4.10
diff -u -r1.13.4.9 -r1.13.4.10
--- Data.pm	18 Feb 2002 20:22:35 -0000	1.13.4.9
+++ Data.pm	25 Jan 2003 22:21:27 -0000	1.13.4.10
@@ -1,14 +1,11 @@
-# Data.pm - Interchange databases
+# Vend::Data - Interchange databases
 #
-# $Id: Data.pm,v 1.13.4.9 2002/02/18 20:22:35 racke Exp $
+# $Id: Data.pm,v 1.13.4.10 2003/01/25 22:21:27 racke Exp $
 # 
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -41,6 +38,7 @@
 import_database
 increment_field
 item_category
+item_common
 item_description
 item_field
 item_price
@@ -51,9 +49,13 @@
 product_code_exists_ref
 product_code_exists_tag
 product_description
+product_common
 product_field
 product_price
+product_row
+product_row_hash
 set_field
+update_data
 
 );
 @EXPORT_OK = qw(update_productbase column_index);
@@ -84,16 +86,56 @@
 		require Vend::Table::DB_File;
 	}
 	require Vend::Table::InMemory;
+	require Vend::Table::Shadow;
 }
 
 my ($Products, $Item_price);
 
+sub instant_database {
+	my($file) = @_;
+	return undef unless $file =~ /\.(txt|asc)$/;
+	my $dir   = File::Basename::dirname($file);
+	my $fname = File::Basename::basename($file);
+	my $dbname = $fname;
+	$dbname =~ s:\W:_:g;
+	
+	$Vend::Database{$dbname}
+		and return $Vend::Database{$dbname}->ref();
+	$Vend::WriteDatabase{$file} and $Vend::WriteDatabase{$dbname} = 1;
+	if( file_name_is_absolute($_[0]) ) {
+		my $msg = errmsg(
+						"Instant database (%s): no absolute file names.",
+						$_[0],
+					);
+		logError($msg);
+		logGloba($msg);
+		return undef;
+	}
+	elsif (! -f $_[0]) {
+		my $msg = errmsg(
+						"Instant database (%s): no file found.",
+						$_[0],
+					);
+		logError($msg);
+		return undef;
+	}
+	return $Vend::Database{$dbname} = import_database({
+													name => $dbname,
+													DIR => $dir,
+													type => 'AUTO',
+													file => $fname,
+													Class => 'TRANSIENT',
+													EXPORT_ON_CLOSE => 1,
+												});
+}
+
 sub database_exists_ref {
 	return $_[0]->ref() if ref $_[0];
 	return $Vend::Interpolate::Db{$_[0]}
 			if $Vend::Interpolate::Db{$_[0]};
-	return undef unless defined $Vend::Database{$_[0]};
-	return $Vend::Database{$_[0]}->ref() || undef;
+	$Vend::Database{$_[0]}
+		and return $Vend::Database{$_[0]}->ref();
+	return instant_database(@_);
 }
 
 sub database_key_exists {
@@ -111,7 +153,7 @@
     }
 
     foreach $ref (@Vend::Productbase) {
-        return ($ref->ref()) if $ref->record_exists($code);
+        return ($return = $ref) if $ref->record_exists($code);
     }
     return undef;
 }
@@ -150,12 +192,11 @@
 		push @Vend::Productbase, $Vend::Database{$_};
 		$Vend::OnlyProducts = $_;
 	}
-	$Products = $Vend::Productbase[0];
 
 	undef $Vend::OnlyProducts if scalar @Vend::Productbase > 1;
-	
-#::logError("Productbase: '@Vend::Productbase' --> " . ::uneval(\%Vend::Basefinder));
-	return $Products;
+
+	$Products = $Vend::Productbase[0];
+#::logError("Productbase: '@Vend::Productbase' --> " . uneval(\%Vend::Basefinder));
 
 }
 
@@ -188,15 +229,17 @@
 }
 
 sub database_field {
-    my ($db, $key, $field_name) = @_;
+    my ($db, $key, $field_name, $foreign) = @_;
+#::logDebug("database_field: " . uneval_it(\@_));
     $db = database_exists_ref($db) or return undef;
-    return '' unless $db->test_record($key);
     return '' unless defined $db->test_column($field_name);
+	$key = $db->foreign($key, $foreign) if $foreign;
+    return '' unless $db->test_record($key);
     return $db->field($key, $field_name);
 }
 
 sub database_row {
-    my ($db, $key, $field_name) = @_;
+    my ($db, $key) = @_;
     $db = database_exists_ref($db) or return undef;
 return undef unless defined $db;
     return '' unless $db->test_record($key);
@@ -208,7 +251,7 @@
 	$db = $db->ref();
     return undef unless $db->test_record($key);
     return undef unless defined $db->test_column($field_name);
-#::logDebug(__PACKAGE__ . "increment_field: " . ::uneval(\@_));
+#::logDebug(__PACKAGE__ . "increment_field: " . uneval_it(\@_));
     return $db->inc_field($key, $field_name, $adder);
 }
 
@@ -253,11 +296,11 @@
 	}
 	else {
 		$options->{field_names} = \@columns;
-		$options->{'delimiter'} = $delimiter;
+		$options->{delimiter} = $options->{DELIMITER} = $delimiter;
 	}
 
-	if($options->{'file'}) {
-		$fn = $options->{'file'};
+	if($options->{file}) {
+		$fn = $options->{file};
 		if( $Global::NoAbsolute) {
 			die "No absolute file names like '$fn' allowed.\n"
 				if Vend::Util::file_name_is_absolute($fn);
@@ -282,11 +325,14 @@
 }
 
 sub set_field {
-    my ($db, $key, $field_name, $value, $append) = @_;
+    my ($db, $key, $field_name, $value, $append, $foreign) = @_;
 
 	$db = database_exists_ref($db);
     return undef unless defined $db->test_column($field_name);
 
+	$key = $db->foreign($key, $foreign)
+		if $foreign;
+
 	# Create it if it doesn't exist
 	unless ($db->record_exists($key)) {
 		$db->set_row($key);
@@ -297,17 +343,47 @@
     return $db->set_field($key, $field_name, $value);
 }
 
+sub product_row {
+	my ($code) = @_;
+	my $db = product_code_exists_ref($code) or return;
+	return $db->row($code);
+}
+
+sub product_row_hash {
+	my ($code) = @_;
+	my $db = product_code_exists_ref($code) or return;
+	return $db->row_hash($code);
+}
+
 sub product_field {
     my ($field_name, $code, $base) = @_;
+#::logDebug("product_field: name=$field_name code=$code base=$base");
 	return database_field($Vend::OnlyProducts, $code, $field_name)
 		if $Vend::OnlyProducts;
+#::logDebug("product_field: onlyproducts=$Vend::OnlyProducts");
 	my ($db);
     $db = product_code_exists_ref($code, $base || undef)
 		or return '';
+#::logDebug("product_field: exists db=$db");
     return "" unless defined $db->test_column($field_name);
     return $db->field($code, $field_name);
 }
 
+
+sub product_common {
+    my ($field_name, $code) = @_;
+#::logDebug("product_field: name=$field_name code=$code base=$base");
+	my $result;
+	for(@{$Vend::Cfg->{ProductFiles}}) {
+		my $db = database_exists_ref($_)
+			or next;
+		next unless defined $db->test_column($field_name);
+		$result = database_field($db, $code, $field_name);
+		length($result) and last;
+	}
+    return $result;
+}
+
 my %T;
 
 TAGBUILD: {
@@ -339,11 +415,11 @@
 	my ($db);
 
 	$opt->{table} = $Vend::Cfg->{ProductFiles}[0] unless defined $opt->{table};
-	$db = $Vend::Database{$opt->{table}}
+	$db = database_exists_ref($opt->{table})
 		or die "dbi_query: unknown base table $opt->{table}.\n";
-	$db = $db->ref();
 
 	$type = lc $type;
+	$type ||= 'list';
 
 	if ($list and $type ne 'list') {
 		$query = '' if ! defined $query;
@@ -415,15 +491,18 @@
 }
 
 sub close_database {
-	my($db, $name);
+	my $name;
 	undef $Products;
 	while( ($name)	= each %Vend::Database ) {
     	$Vend::Database{$name}->close_table()
 			unless defined $Vend::Cfg->{SaveDatabase}{$name};
 		delete $Vend::Database{$name};
 	}
+	undef %Vend::Table::DBI::DBI_connect_bad;
+	undef %Vend::TransactionDatabase;
 	undef %Vend::WriteDatabase;
 	undef %Vend::Basefinder;
+	undef $Vend::VarDatabase;
 }
 
 sub database_ref {
@@ -438,29 +517,6 @@
 
 *read_shipping = \&Vend::Interpolate::read_shipping;
 
-# Read in the accessories file.
-
-sub read_accessories {
-    my($code, $accessories);
-
-	my $file = $Vend::Cfg->{Special}{'accessories.asc'}
-				|| Vend::Util::catfile($Vend::Cfg->{ProductDir}, 'accessories.asc');
-	return undef unless -f $file;
-    open(Vend::ACCESSORIES, "< $file") or return undef;
-    while(<Vend::ACCESSORIES>) {
-		chomp;
-		tr/\r//d;
-		if (s/\\\s*$//) { # handle continues
-	        $_ .= <Vend::ACCESSORIES>;
-			redo;
-		}
-		($code, $accessories) = split(/\t/, $_, 2);
-		$Vend::Cfg->{Accessories}->{$code} = $accessories;
-    }
-    close Vend::ACCESSORIES;
-	1;
-}
-
 # Read in the sales tax file.
 sub read_salestax {
     my($code, $percent);
@@ -471,21 +527,13 @@
 		unless $file;
 
 	$Vend::Cfg->{SalesTaxTable} = {};
-    -f $file and open(Vend::SALESTAX, "< $file") or do {
-					logError( "Could not open salestax file %s: %s" ,
-								$file,
-								$!
-							)
-						if ! $Vend::Cfg->{SalesTaxFunction};
-					return undef;
-				};
-    while(<Vend::SALESTAX>) {
-		chomp;
+
+	my @lines = split /\n/, readfile($file);
+    for(@lines) {
 		tr/\r//d;
 		($code, $percent) = split(/\s+/, $_, 2);
 		$Vend::Cfg->{SalesTaxTable}->{"\U$code"} = $percent;
     }
-    close Vend::SALESTAX;
 
 	if(not defined $Vend::Cfg->{SalesTaxTable}->{DEFAULT}) {
 		$Vend::Cfg->{SalesTaxTable}->{DEFAULT} = 0;
@@ -508,6 +556,9 @@
 	CSV => ["CSV","\n"],
 	PIPE => ['|', "\n"],
 	TAB => ["\t", "\n"],
+	"\t" => ["\t", "\n"],
+	'|'  => ['|', "\n"],
+	"\n%%\n" => ["\n%%\n", "\n%%%\n"],
 
 	);
 
@@ -593,7 +644,9 @@
 
 =cut
 
-my %db_config = (
+use vars '%db_config';
+
+%db_config = (
 # SQL
 		'DBI' => {
 				qw/
@@ -603,6 +656,19 @@
 				/
 				},
 # END SQL
+		'SHADOW' => {
+				qw/
+					Class                Vend::Table::Shadow
+				/
+				},
+		'TRANSIENT' => {
+				qw/
+					Cacheable			 0
+					Tagged_write		 1
+					Class                Vend::Table::InMemory
+					Export_on_close		 1
+				/
+				},
 		'MEMORY' => {
 				qw/
 					Cacheable			 1
@@ -626,6 +692,15 @@
 					Class                Vend::Table::DB_File
 				/
 		},
+		'SDBM' => {
+				qw/
+					TableExtension		 .sdbm
+					Extension			 sdbm
+					Tagged_write		 1
+					Class                Vend::Table::SDBM
+				/,
+				FileExtensions	=> [ qw/dir pag/ ],
+		},
 # LDAP
 		'LDAP' => {
 				qw/
@@ -642,25 +717,58 @@
 	if($Global::Database) {
 		copyref($Global::Database, $Vend::Cfg->{Database});
 	}
-    while (($name,$data) = each %{$Vend::Cfg->{Database}}) {
-		if( $data->{type} > 6 or $data->{HOT} ) {
-#::logDebug("Importing $data->{name}...");
-			$Vend::Database{$name} = import_database($data);
-		}
-		else {
-			if($data->{GUESS_NUMERIC}) {
-				my $dir = $data->{DIR} || $Vend::Cfg->{ProductDir};
-				my $fn = Vend::Util::catfile( $dir, $data->{file} );
-				my @fields = grep /\S/, split /\s+/, ::readfile("$fn.numeric");
-#::logDebug("fields=@fields");
-				$data->{NUMERIC} = {};
-				for(@fields) {
-					$data->{NUMERIC}{$_} = 1;
+
+	my @tables = keys %{$Vend::Cfg->{Database}};
+
+	my @delayed;
+	my $redone;
+
+	TIEDB: {
+
+		foreach $name (@tables) {
+			$data = $Vend::Cfg->{Database}{$name} || {};
+			if(! $redone and $data->{MIRROR}) {
+#::logDebug("mirror database $name, delaying");
+				$data->{HOT} = 1;
+				push @delayed, $name;
+				next;
+			}
+			if(! $data->{name}) {
+				next;
+			}
+			if( $data->{type} > 6 or $data->{HOT} or $data->{IMPORT_ONCE} ) {
+				eval {
+					$Vend::Database{$name} = import_database($data);
+				};
+				if($@) {
+						my $msg = "table '%s' failed: %s";
+						$msg = errmsg($msg, $name, $@);
+						logError($msg);
+				}
+			}
+			else {
+				if($data->{GUESS_NUMERIC}) {
+					my $dir = $data->{DIR} || $Vend::Cfg->{ProductDir};
+					my $fn = Vend::Util::catfile( $dir, $data->{file} );
+					my @fields = grep /\S/, split /\s+/, readfile("$fn.numeric");
+					$data->{NUMERIC} = {};
+					for(@fields) {
+						$data->{NUMERIC}{$_} = 1;
+					}
 				}
+				my $class = $db_config{$data->{Class}}->{Class};
+				$Vend::Database{$name} = new $class ($data);
 			}
-			my $class = $db_config{$data->{Class}}->{Class};
-			$Vend::Database{$name} = new $class ($data);
 		}
+
+		# So mirrors will not happen until after mirror source
+		if(@delayed) {
+			@tables = @delayed;
+			@delayed = ();
+			$redone = 1;
+			redo TIEDB;
+		}
+
 	}
 	update_productbase();
 }
@@ -681,6 +789,23 @@
 
 my $tried_import;
 
+sub create_empty_txt {
+	my ($obj, $database_txt, $delimiter, $record_delim) = @_;
+	return if -f $database_txt;
+	return unless $obj->{CREATE_EMPTY_TXT};
+	if(! ref($obj->{NAME}) eq 'ARRAY') {
+		logError("Cannot create text file with no database NAME parameter");
+	}
+	else {
+		$delimiter ||= "\t";
+		$record_delim ||= "\n";
+		my $line = join $obj->{DELIMITER}, @{$obj->{NAME}};
+		$line .= $record_delim;
+		Vend::Util::writefile($database_txt, $line);
+	}
+	return;
+}
+
 sub import_database {
     my ($obj, $dummy) = @_;
 
@@ -691,10 +816,10 @@
 #	if($type == 9) {
 #my @caller = caller();
 #::logDebug ("enter import_database: dummy=$dummy");
-#::logDebug("opening table table=$database config=" . ::uneval($obj) . " caller=@caller");
+#::logDebug("opening table table=$database config=" . uneval($obj) . " caller=@caller");
 #
-#::logDebug ("database=$database type=$type name=$name obj=" . ::uneval($obj));
-#::logDebug ("database=$database type=$type name=$name obj=" . ::uneval($obj)) if $obj->{HOT};
+#::logDebug ("database=$database type=$type name=$name obj=" . uneval($obj));
+#::logDebug ("database=$database type=$type name=$name obj=" . uneval($obj)) if $obj->{HOT};
 #	
 #	}
 	return $Vend::Cfg->{SaveDatabase}->{$name}
@@ -724,14 +849,22 @@
 	$base = $obj->{'name'};
 	$dir = $obj->{DIR} if defined $obj->{DIR};
 
-	$class_config = $db_config{$obj->{Class} || $Global::Default_database};
+	if ($obj->{OrigClass}) {
+		my $ref = $db_config{$obj->{OrigClass} || $Global::Default_database};
+		$class_config = {%$ref};
+		$class_config->{Class} = $db_config{$obj->{Class}}->{Class};
+		$class_config->{OrigClass} = $obj->{OrigClass};
+	} else {
+		$class_config = $db_config{$obj->{Class} || $Global::Default_database};
+	}
 
-::logDebug ("params=$database_txt path='$path' base='$base' tail='$tail' dir='$dir'") if $type == 9;
+#::logDebug ("params=$database_txt path='$path' base='$base' tail='$tail' dir='$dir'") if $type == 9;
 	$table_name     = $name;
 	my $export;
 
   IMPORT: {
 	last IMPORT if $no_import and $obj->{DIR};
+#::logDebug ("no_import_check: once=$obj->{IMPORT_ONCE} dir=$obj->{DIR}");
 	last IMPORT if defined $obj->{IMPORT_ONCE} and $obj->{DIR};
 #::logDebug ("first no_import_check: passed") if $type == 9;
 
@@ -758,10 +891,12 @@
 
 	$obj->{ObjectType} = $class_config->{Class};
 
+	my $dot = $obj->{HIDE_AUTO_FILES} ? '.' : '';
+
 	if($class_config->{Extension}) {
 		$database_dbm = Vend::Util::catfile(
 												$dir,
-												"$base."     .
+												"$dot$base."     .
 												$class_config->{Extension}
 											);
 		$new_database_dbm =  Vend::Util::catfile(
@@ -786,7 +921,7 @@
 		if (
 			$Vend::Cfg->{NoImportExternal}
 			or -f $database_dbm
-			or ! -f $database_txt
+			or (! $obj->{CREATE_EMPTY_TXT} and ! -f $database_txt)
 			)
 		{
 			$no_import = 1;
@@ -798,6 +933,17 @@
 		}
 	}
 
+	if($obj->{MIRROR}) {
+		if($obj->{Mirror_complete}) {
+			$no_import = 1;
+		}
+		else {
+#::logDebug ("table $new_table_name: undeffing $database_dbm, hot=$obj->{HOT}");
+			undef $database_dbm;
+			undef $no_import;
+		}
+	}
+
 	last IMPORT if $no_import;
 #::logDebug ("moving to import") if $type == 9;
 
@@ -808,12 +954,12 @@
     if (
 		! defined $database_dbm
 		or ! -e $database_dbm
-        or ($txt_time = file_modification_time($database_txt))
+		or $obj->{MIRROR}
+        or ($txt_time = file_modification_time($database_txt, $obj->{PRELOAD}))
 				>
            ($dbm_time = file_modification_time($database_dbm))
 		)
 	{
-		
         warn "Importing $obj->{'name'} table from $database_txt\n"
 			unless $Vend::Quiet;
 
@@ -824,25 +970,52 @@
 			($delimiter, $record_delim) = auto_delimiter($database_txt);
 		}
 
-		$obj->{'delimiter'} = $obj->{'DELIMITER'} = $delimiter;
+		$obj->{delimiter} = $obj->{DELIMITER} = $delimiter;
 
 		my $save = $/;
 
 		local($/) = $record_delim if defined $record_delim;
 
+		if($obj->{CREATE_EMPTY_TXT}) {
+			create_empty_txt($obj, $database_txt, $delimiter, $record_delim);
+		}
+
+		if($obj->{MIRROR}) {
+			$db = Vend::Table::Common::import_from_ic_db(
+							$database_txt,
+							$obj,
+							$new_table_name,
+				);
+		}
+		else {
         $db = Vend::Table::Common::import_ascii_delimited(
 							$database_txt,
 							$obj,
 							$new_table_name,
 				);
+		}
 
 		$/ = $save;
 		if(defined $database_dbm) {
 			$db->close_table() if defined $db;
 			undef $db;
 			unlink $database_dbm if $Global::Windows;
-        	rename($new_database_dbm, $database_dbm)
-            	or die "Couldn't move '$new_database_dbm' to '$database_dbm': $!\n";
+			if($class_config->{FileExtensions}) {
+				open(TOUCH, ">>$database_dbm")
+					or die "Couldn't freshen $database_dbm: $_";
+				close TOUCH 
+					or die "Couldn't freshen $database_dbm: $_";
+				for(@{$class_config->{FileExtensions}}) {
+					my ($old, $new) = ("$new_database_dbm.$_", "$database_dbm.$_");
+					rename($old, $new)
+						or die
+							"Couldn't move '$old' to '$new': $!\n";
+				}
+			}
+			else {
+				rename($new_database_dbm, $database_dbm)
+					or die "Couldn't move '$new_database_dbm' to '$database_dbm': $!\n";
+			}
 		}
     }
 	elsif ($obj->{AUTO_EXPORT} and $dbm_time > $txt_time) {
@@ -861,11 +1034,11 @@
 			$obj->{Read_only} = 0;
 		}
 		elsif($obj->{WRITE_CATALOG}) {
-			$obj->{Read_only} = $obj->{WRITE_CATALOG}{$Vend::Cfg->{CatalogName}}
+			$obj->{Read_only} = $obj->{WRITE_CATALOG}{$Vend::Cat}
 					? (! defined $Vend::WriteDatabase{$name}) 
 					: 1;
 		}
-		elsif($obj->{WRITE_TAGGED}) {
+		elsif(! defined $obj->{WRITE_TAGGED} or $obj->{WRITE_TAGGED}) {
 			$obj->{Read_only} = ! defined $Vend::WriteDatabase{$name};
 		}
 	}
@@ -874,37 +1047,40 @@
 			if $class_config->{Tagged_write};
 	}
 
-		
+	$obj->{Transactions} = 1 if $Vend::TransactionDatabase{$name};
+
     if($class_config->{Extension}) {
 
 		$obj->{db_file} = $table_name unless $obj->{db_file};
 		$obj->{db_text} = $database_txt unless $obj->{db_text};
 		no strict 'refs';
+#::logDebug("ready to try opening db $table_name") if ! $db;
 		eval { 
 			if($MVSAFE::Safe) {
                 if (exists $Vend::Interpolate::Db{$class_config->{Class}}) {
- 				    $db = $Vend::Interpolate::Db{$class_config->{Class}}->open_table( $obj, $table_name );
+				    $db = $Vend::Interpolate::Db{$table_name}->open_table( $obj, $obj->{db_file} );
                 } else {
                     die errmsg("no access for database %s", $table_name);
                 }
 			}
 			else {
-#::logDebug("Opening $obj->{name}: table=$table_name") if $type == 9;
-				$db = $class_config->{Class}->open_table( $obj, $table_name );
-#::logDebug("Opened $obj->{name}") if $type == 9;
+				$db = $class_config->{Class}->open_table( $obj, $obj->{db_file} );
 			}
 			$obj->{NAME} = $db->[$Vend::Table::Common::COLUMN_INDEX]
 				unless defined $obj->{NAME};
+#::logDebug("didn't die but no db") if ! $db;
 		};
 
+#::logDebug("db=$db, \$\!='$!' \$\@='$@' (" . length($@) . ")\n") if ! $db;
 		if($@) {
 #::logDebug("Dieing of $@");
 			die $@ unless $no_import;
-			die $@ unless $tried_import++;
+			die $@ if $tried_import++;
 			if(! -f $database_dbm) {
 				$Vend::ForceImport{$obj->{name}} = 1;
 				return import_database($obj);
 			}
+			die $@;
 		}
 		undef $tried_import;
 #::logDebug("Opening $obj->{name}: RO=$obj->{Read_only} WC=$obj->{WRITE_CONTROL} WA=$obj->{WRITE_ALWAYS}");
@@ -942,7 +1118,7 @@
 
 #::logDebug(
 #	"dbname=$dbname db_fn=$db_fn bx_fn=$bx_fn ix_fn=$ix_fn\n" .
-#	"options: " . Vend::Util::uneval($opt) . "\n"
+#	"options: " . uneval($opt) . "\n"
 #	);
 
 	if(		! -f $bx_fn
@@ -972,7 +1148,7 @@
 		my @fields = grep $_ ne $key, split /[\0,\s]+/, $opt->{fn};
 		my $sort = join ",", @fields;
 		if(! $opt->{fn}) {
-			::logError(errmsg("index attempted on table '%s' with no fields, no search spec", $dbname));
+			logError(errmsg("index attempted on table '%s' with no fields, no search spec", $dbname));
 			return undef;
 		}
 		$opt->{spec} = <<EOF;
@@ -986,7 +1162,7 @@
 	$scan =~ s:^scan/::;
 
 	my $c = {
-				mv_list_only		=> 1,
+				mv_list_only        => 1,
 				mv_search_file		=> $bx_fn,
 			};
 
@@ -1002,7 +1178,7 @@
 		@fn = split /\s*[\0,]+\s*/, $c->{mv_return_fields};
 	}
 
-#::logDebug( "search options: " . Vend::Util::uneval($c) . "\n");
+#::logDebug( "search options: " . uneval($c) . "\n");
 
 	open(Vend::Data::INDEX, "+<$ix_fn") or
 		open(Vend::Data::INDEX, "+>$ix_fn") or
@@ -1057,6 +1233,8 @@
 	}
 
 	my ($delim, $record_delim) = find_delimiter($type || $db->config('type'));
+	$delim or ($delim, $record_delim) = find_delimiter($db->config('DELIMITER'));
+	$delim or ($delim, $record_delim) = find_delimiter('TAB');
 
 	$file = $file || $db->config('file');
 	my $dir = $db->config('DIR');
@@ -1068,7 +1246,7 @@
 
 	my ($notouch, $nuke);
 	if ($field and ! $delete) {
-#::logDebug("Trying for delete field=$field delete=$delete");
+#::logDebug("Trying for add field=$field delete=$delete");
 		if($db->column_exists($field)) {
 			logError(
 				"Can't define column '%s' twice in table '%s'",
@@ -1082,7 +1260,7 @@
 		$notouch = 1;
 	}
 	elsif ($field) {
-#::logDebug("Trying for add field=$field delete=$delete");
+#::logDebug("Trying for delete field=$field delete=$delete");
 		if(! $db->column_exists($field)) {
 			logError(
 				"Can't delete non-existent column '%s' in table '%s'",
@@ -1178,9 +1356,11 @@
 	elsif($record_delim eq "\n") {
 		print EXPORT join $delim, @cols;
 		print EXPORT $record_delim;
+		my $detab = ($delim eq "\t") ? 1 : 0;
 		if(defined $nuke) {
 			while( (undef, @data) = $db->each_record() ) {
-				splice(@data, $nuke, 1) if defined $nuke;
+				splice(@data, $nuke, 1);
+				if ($detab) { s/\t/ /g for @data; }
 				$tempdata = join $delim, @data;
 				$tempdata =~ s/\r?\n/\r/g;
 				print EXPORT $tempdata, $record_delim;
@@ -1188,6 +1368,7 @@
 		}
 		else {
 			while( (undef, @data) = $db->each_record() ) {
+				if ($detab) { s/\t/ /g for @data; }
 				$tempdata = join $delim, @data;
 				$tempdata =~ s/\r?\n/\r/g;
 				print EXPORT $tempdata, $record_delim;
@@ -1197,8 +1378,10 @@
 	else {
 		print EXPORT join $delim, @cols;
 		print EXPORT $record_delim;
+		my $detab = ($delim eq "\t" or $record_delim eq "\t") ? 1 : 0;
 		while( (undef, @data) = $db->each_record() ) {
 			splice(@data, $nuke, 1) if defined $nuke;
+			if ($detab) { s/\t/ /g for @data; }
 			print EXPORT join($delim, @data);
 			print EXPORT $record_delim;
 		}
@@ -1217,8 +1400,150 @@
 	1;
 }
 
+my $opt_remap = 0;
+my %opt_map;
+
+sub remap_options {
+	return if not defined $opt_remap;
+	my $record = shift;
+	if($opt_remap and $record) {
+		my %rec;
+		my @del;
+		my ($k, $v);
+		while (($k, $v) = each %opt_map) {
+			next unless defined $record->{$v};
+			$rec{$k} = $record->{$v};
+			push @del, $v;
+		}
+		delete @{$record}{@del};
+		@{$record}{keys %rec} = (values %rec);
+	}
+	elsif($::Variable->{MV_OPTION_TABLE_MAP}) {
+		$opt_remap = $::Variable->{MV_OPTION_TABLE_MAP};
+		$opt_remap =~ s/^\s+//;
+		$opt_remap =~ s/\s+$//;
+		map { m{(.*?)=(.*)} and $opt_map{$2} = $1} split /[\0,\s]+/, $opt_remap;
+		$opt_remap = 1;
+		remap_options($record);
+	}
+	else {
+		undef $opt_remap;
+	}
+	return;
+}
+
+sub modular_cost {
+	my ($item, $table, $final) = @_;
+#::logDebug("called modular_cost");
+	return unless $item->{mv_si};
+	my $ptr = $item->{mv_mp}
+		or return;
+#::logDebug("modular_cost ptr=$ptr");
+
+	my $db = database_exists_ref($table);
+	if(! $db) {
+		logError('Non-existent price option table %s', $table);
+		return;
+	}
+#::logDebug("database $table exists");
+	
+	remap_options();
+
+	return unless $db->record_exists($ptr);
+#::logDebug("record $ptr exists");
+
+	my $fld = $opt_map{differential} || 'differential';
+	return unless $db->column_exists($fld);
+#::logDebug("field $fld exists");
+
+	my $p = $db->field($ptr,$fld);
+#::logDebug("p=$p for $fld") if $p;
+
+	return $p if $p != 0;
+	return;
+}
+
+sub option_cost {
+	my ($item, $table, $final) = @_;
+#::logDebug("called option_cost");
+	my $db = database_exists_ref($table);
+	if(! $db) {
+		logError('Non-existent price option table %s', $table);
+		return;
+	}
+
+	my $sku = $item->{code};
+
+	$db->record_exists($sku)
+		or return;
+	my $record = $db->row_hash($sku)
+		or return;
+
+	remap_options($record);
+
+#	if(! $opt_remap and $::Variable->{MV_OPTION_TABLE_MAP}) {
+#		$opt_remap = $::Variable->{MV_OPTION_TABLE_MAP};
+#		$opt_remap =~ s/^\s+//;
+#		$opt_remap =~ s/\s+$//;
+#		%opt_map = split /[,\s]+/, $opt_remap;
+#		my %rec;
+#		my @del;
+#		my ($k, $v);
+#		while (($k, $v) = each %opt_map) {
+#			next unless defined $record->{$v};
+#			$rec{$k} = $record->{$v};
+#			push @del, $v;
+#		}
+#		delete @{$record}{@del};
+#		@{$record}{keys %rec} = (values %rec);
+#	}
+
+	return if ! $record->{o_enable};
+
+#::logDebug("option_cost found enabled record");
+	my $fsel = $opt_map{sku} || 'sku';
+	my $rsel = $db->quote($sku, $fsel);
+	my @rf;
+	for(qw/o_group price o_master/) {
+		push @rf, ($opt_map{$_} || $_);
+	}
+
+	my $q = "SELECT " . join (",", @rf) . " FROM $table where $fsel = $rsel";
+	my $ary = $db->query($q); 
+	return if ! $ary->[0];
+	my $ref;
+	my $price = 0;
+	my $f;
+
+	foreach $ref (@$ary) {
+#::logDebug("checking option " . uneval_it($ref));
+		next unless defined $item->{$ref->[0]};
+		$ref->[1] =~ s/^\s+//;
+		$ref->[1] =~ s/\s+$//;
+		$ref->[1] =~ s/==/=:/g;
+		my %info = split /\s*[=,]\s*/, $ref->[1];
+		if(defined $info{ $item->{$ref->[0]} } ) {
+			my $atom = $info{ $item->{$ref->[0]} };
+			if($atom =~ s/^://) {
+				$f = $atom;
+				next;
+			}
+			elsif ($atom =~ s/\%$//) {
+				$f = $final if ! defined $f;
+				$f += ($atom * $final / 100);
+			}
+			else {
+				$price += $atom;
+			}
+		}
+	}
+#::logDebug("option_cost returning price=$price f=$f");
+	return ($price, $f);
+}
+
 sub chain_cost {
 	my ($item, $raw) = @_;
+
 	return $raw if $raw =~ /^[\d.]*$/;
 	my $price;
 	my $final = 0;
@@ -1228,24 +1553,25 @@
 	$raw =~ s/\s+$//;
 	if($raw =~ /^\[\B/ and $raw =~ /\]$/) {
 		my $ref = Vend::Interpolate::tag_calc($raw);
-		@p = @{$ref} if ref $ref;
+		@p = ref $ref ? @{$ref} : $ref;
 	}
 	else {
 		@p = Text::ParseWords::shellwords($raw);
 	}
-	if(scalar @p > 16) {
-			::logError('Too many chained cost levels for item ' .  uneval($item) );
-			return undef;
+	if(scalar @p > ($Vend::Cfg->{Limit}{chained_cost_levels} || 64)) {
+		logError('Too many chained cost levels for item ' .  uneval($item) );
+		return undef;
 	}
 
-#::logDebug("chain_cost item = " . uneval ($item) );
+#::logDebug("chain_cost item = " . uneval ($item) . "\np=" . uneval(\@p) );
 	my ($chain, $percent);
 	my $passed_key;
 	my $want_key;
 CHAIN:
 	foreach $price (@p) {
-		if($its++ > 20) {
-			::logError('Too many chained cost levels for item ' .  uneval($item) );
+		next if ! length($price);
+		if($its++ > ($Vend::Cfg->{Limit}{chained_cost_levels} || 64)) {
+			logError('Too many chained cost levels for item ' .  uneval($item) );
 			last CHAIN;
 		}
 		$price =~ s/^\s+//;
@@ -1269,8 +1595,9 @@
 				$price = $item->{mv_price} || $mod;
 				redo CHAIN;
 			}
-			elsif($mod =~ /^(\w*):([^:]*)(:(\S*))?$/) {
-				my ($table,$field,$key) = ($1, $2, $4);
+			elsif($mod =~ /^(\w*):([^:]*)(?::(\S*))?$/) {
+				my ($table, $field, $key) = ($1, $2, $3);
+#::logDebug("field begins as '$field'");
 				$field = $Vend::Cfg->{PriceDefault} if ! $field;
 				if($passed_key) {
 					(! $key   and $key   = $passed_key)
@@ -1280,12 +1607,17 @@
 					(! $table and $table = $passed_key);
 					undef $passed_key;
 				}
+				$table = $item->{mv_ib} || $Vend::Cfg->{ProductFiles}[0]
+					if ! $table;
+				if($key and defined $item->{$key}) {
+					$key = $item->{$key};
+				}
 				my @breaks;
 				if($field =~ /,/ || $field =~ /\.\./) {
 					my (@tmp) = split /,/, $field;
 					for(@tmp) {
-						if (/(.+)\.\.+(.+)/) {
-							push @breaks, $1 .. $2;
+						if (/(.+?)(\d+)\.\.+.+?(\d+)/) {
+							push @breaks, map { "$1$_" } $2 .. $3;
 						}
 						else {
 							push @breaks, $_;
@@ -1293,6 +1625,7 @@
 					}
 				}
 				if(@breaks) {
+#::logDebug("price breaks: " . join(',', @breaks));
 					my $quantity;
 					my $attribute;
 					$attribute = shift @breaks  if $breaks[0] !~ /\d/;
@@ -1316,18 +1649,57 @@
 					my $test = $field;
 					$test =~ s/\D+//;
 					redo CHAIN if $quantity < $test;
-					for(@breaks) {
+
+					my $row = database_row(
+						($table || $item->{mv_ib} || $Vend::Cfg->{ProductFiles}[0]),
+						($key || $item->{code}),
+					);
+#::logDebug("database reference to price breaks found table=$table key=$key|$item->{$key}|$item->{code} row=" . ::uneval($row));
+
+					my $keep;
+					$keep = $row->{$field} if $row->{$field} != 0;
+					for (@breaks) {
+						next unless exists $row->{$_};
 						$test = $_;
 						$test =~ s/\D+//;
 						last if $test > $quantity;
 						$field = $_;
+						$keep = $row->{$field} if $row->{$field} != 0;
 					}
+#::logDebug("price=$keep") if $keep;
+					$price = $keep if $keep;
+					redo CHAIN;
 				}
 				$price = database_field(
 						($table || $item->{mv_ib} || $Vend::Cfg->{ProductFiles}[0]),
-											($key || $item->{code}),
-											$field
-										);
+						($key || $item->{code}),
+						$field
+						);
+#::logDebug("database reference found table=$table field=$field key=$key|$item->{$key}|$item->{code} price=$price");
+				redo CHAIN;
+			}
+			elsif ($mod =~ s/(\w+)=(.*)//) {
+				my $tag = $1;
+				my(@args) = split /:/, $2;
+				my $sub	=   # $intrinsic_price{$tag} ||
+							$Vend::Cfg->{Sub}{$tag} || $Global::GlobalSub->{$tag};
+
+				my %i = %$item;
+			
+				for(@args) {
+					my($k, $v) = split /=/, $_;
+					$i{$k} = $v;
+				}
+
+				$i{final} = $final;
+				$i{passed_key} = $passed_key if $passed_key;
+
+				if ($sub) {
+					$price = $sub->(\%i);
+				}
+				else {
+					$price = Vend::Tags->$tag(\%i);
+				}
 				redo CHAIN;
 			}
 			elsif ($mod =~ s/^[&]//) {
@@ -1341,18 +1713,31 @@
 			elsif ($mod =~ s/^=([\d.]*)=([^=]+)//) {
 				$final += $1 if $1;
 				my ($attribute, $table, $field, $key) = split /:/, $2;
-				$item->{$attribute} and
-					do {
-						$key = $field ? $item->{$attribute} : $item->{'code'}
-							unless $key;
-						$price = database_field( ( $table ||
-													$item->{mv_ib} ||
-													$Vend::Cfg->{ProductFiles}[0]),
-												$key,
-												($field || $item->{$attribute})
-										);
-						redo CHAIN;
-					};
+				if($item->{$attribute}) {
+					$key = $field ? $item->{$attribute} : $item->{code}
+						unless $key;
+					$price = database_field( ( $table ||
+												$item->{mv_ib} ||
+												$Vend::Cfg->{ProductFiles}[0]),
+											$key,
+											($field || $item->{$attribute})
+									);
+					redo CHAIN;
+				}
+				elsif ($table) {
+#::logDebug("before option_cost price=$price final=$final");
+					my ($p, $f);
+					if($item->{mv_mp}) {
+						($p, $f) = modular_cost($item, $table, $final);
+					}
+					else {
+						($p, $f) = option_cost($item, $table, $final);
+					}
+					$final = $f if defined $f;
+					$price = $p || '';
+#::logDebug("option_cost returned p=$p f=$f, price=$price final=$final");
+					redo CHAIN;
+				}
 			}
 			elsif($mod =~ /^\s*[[_]+/) {
 				$::Scratch->{mv_item_object} = $Vend::Interpolate::item = $item;
@@ -1394,26 +1779,77 @@
 
 sub item_price {
 	my($item, $quantity, $noformat) = @_;
-#::logDebug("item_price: " . ::uneval_it(\@_));
+
+#::logDebug("item_price initial call: " . (ref $item ? $item->{code} : $item));
+
 	return $item->{mv_cache_price}
 		if ! $quantity and defined $item->{mv_cache_price};
-	my ($price, $base, $adjusted);
+
 	$item = { 'code' => $item, 'quantity' => ($quantity || 1) } unless ref $item;
-	if(not $base = $item->{mv_ib}) {
-		$base = product_code_exists_tag($item->{code}, $item->{mv_ib})
-			or $Vend::Cfg->{OnFly}
-			or return undef;
-	}
-	$price = database_field($base, $item->{code}, $Vend::Cfg->{PriceField})
-		if $Vend::Cfg->{PriceField};
-#::logDebug("item_price before chain cost: $price PriceField=$Vend::Cfg->{PriceField} base=$base");
-	$price = chain_cost($item,$price || $Vend::Cfg->{CommonAdjust});
-	$price = $price / $Vend::Cfg->{PriceDivide};
-#::logDebug("item_price before cache: $price");
-	$item->{mv_cache_price} = $price
-		if ! $quantity and exists $item->{mv_cache_price};
-#::logDebug("item_price final: $price");
-	return $price;
+
+	my $master;
+
+	my @items;
+
+	if ($item->{mv_mp}) {
+		return 0 if $item->{mv_si};
+		$master = $item;
+		my $mv_mp = $item->{mv_mi}
+			or do {
+				logError("Bad modular item %s: ", uneval_it($item));
+				return 0;
+			};
+		for(@$Vend::Items) {
+			next unless $_->{mv_si} and $_->{mv_mi} eq $mv_mp;
+#::logDebug("pushing item $_->{code}, mv_mi=$item->{mv_mi}, mv_mp=$item->{mv_mp}, mv_si=$item->{mv_si}");
+			push @items, $_;
+		}
+	}
+	
+
+	my $final = 0;
+	do {
+		my $base;
+		if(not $base = $item->{mv_ib}) {
+			$base = product_code_exists_tag($item->{code})
+				or ($Vend::Cfg->{OnFly} && 'mv_fly')
+				or return undef;
+		}
+
+		my $price;
+		$price = database_field($base, $item->{code}, $Vend::Cfg->{PriceField})
+			if $Vend::Cfg->{PriceField};
+
+#::logDebug("price for item before chain $item->{code}=$price PriceField=$Vend::Cfg->{PriceField}");
+		$price = chain_cost($item,$price || $Vend::Cfg->{CommonAdjust});
+		if($Vend::Cfg->{PriceDivide} == 0) {
+			my $msg = "Locale %s PriceDivide non-numeric or zero [%s].";
+			$msg .= " Possibly bad locale data.",
+			logError(
+				$msg,
+				$::Scratch->{mv_currency} || $::Scratch->{mv_locale},
+				$Vend::Cfg->{PriceDivide},
+			);
+			$Vend::Cfg->{PriceDivide} = 1;
+		}
+		$price = $price / $Vend::Cfg->{PriceDivide};
+
+		$item->{mv_cache_price} = $price
+			if ! $quantity and exists $item->{mv_cache_price};
+#::logDebug("price for item $item->{code}=$price item=" . ::uneval_it($item)) if $price != 0;
+		$final += $price;
+	} while ($item = shift @items);
+#::logDebug("#### final price for item $master->{code}=$final item=" . ::uneval($master)) if $master;
+	$master->{mv_cache_price} = $final 
+			if $master and ! $quantity and exists $master->{mv_cache_price};
+#::logDebug("final price in item $master->{code} is $master->{mv_cache_price}") if $master;
+	return $final;
+}
+
+sub item_category {
+	my $item = shift;
+	my $base = $Vend::Database{$item->{mv_ib}} || $Products;
+	return database_field($base, $item->{code}, $Vend::Cfg->{CategoryField});
 }
 
 sub item_category {
@@ -1423,17 +1859,564 @@
 }
 
 sub item_description {
-	return item_field($_[0], $Vend::Cfg->{DescriptionField});
+	my $item = shift;
+	my $base = $Vend::Database{$item->{mv_ib}} || $Products;
+	return database_field($base, $item->{code}, $Vend::Cfg->{DescriptionField});
+}
+
+sub item_common {
+	my ($item, $field) = @_;
+	my $base = $item->{mv_ib};
+	my $res;
+	foreach my $code ($item->{code}, $item->{mv_sku}) {
+		next if ! length($code);
+		for my $dbname ($base, @{$Vend::Cfg->{ProductFiles}} ) {
+			next if ! $dbname;
+			my $db = database_exists_ref($dbname)
+				or next;
+			last unless defined $db->test_column($field);
+			$res = database_field($db, $code, $field);
+			return $res if length $res;
+		}
+	}
 }
 
 sub item_field {
-	my $base = $Vend::Database{$_[0]->{mv_ib}} || $Products;
-	return database_field($base, $_[0]->{code}, $_[1]);
+	my ($item, $field) = @_;
+	my $base = $Vend::Database{$item->{mv_ib}} || $Products;
+	my $res = database_field($base, $item->{code}, $field);
+	return $res if length($res);
+	return database_field($base, $item->{mv_sku}, $field);
 }
 
 sub item_subtotal {
 	item_price($_[0]) * $_[0]->{quantity};
 }
+
+sub set_db {
+	my ($base, $thing) = @_;
+	return ($base, $thing) unless $thing =~ /^(\w+):+(.*)/;
+	my $t = $1;
+	my $c = $2;
+
+	# Security handled before this in update_data
+	$Vend::WriteDatabase{$t} = 1;
+
+	my $db = database_exists_ref($t);
+	return undef unless $db;
+	return ($db->ref(), $c);
+}
+
+## Update the user-entered fields.
+sub update_data {
+	my($key,$value);
+	my @cgi_keys = keys %CGI::values;
+    # Update a database record
+	# Check to see if this is allowed
+#::logDebug("mv_data_enable=$::Scratch->{mv_data_enable}");
+	if(! $::Scratch->{mv_data_enable}) {
+		logError(
+			 "Attempted database update without permission, table=%s key=%s.",
+			 $CGI::values{mv_data_table},
+			 $CGI::values{$CGI::values{mv_data_key}},
+		);
+		return undef;
+	}
+	unless (defined $CGI::values{mv_data_table} and 
+		    defined $CGI::values{mv_data_key}      ) {
+		logError("Attempted database operation without table, fields, or key.\n" .
+					 "Table: '%s'\n" .
+					 "Fields:'%s'\n" .
+					 "Key:   '%s'\n",
+					 $CGI::values{mv_data_table},
+					 $CGI::values{mv_data_fields},
+					 $CGI::values{mv_data_key},
+				 );
+
+		return undef;
+	}
+
+	my $function	= lc (delete $CGI::values{mv_data_function});
+	if($function eq 'delete' and ! delete $CGI::values{mv_data_verify}) {
+		logError("update_data: DELETE without VERIFY, abort");
+		return undef;
+	}
+	my $table		= $CGI::values{mv_data_table};
+	my $prikey		= $CGI::values{mv_data_key};
+	my $decode		= is_yes($CGI::values{mv_data_decode});
+	my ($ref, $db, $database);
+
+	my $en_col;
+#::logDebug("data_enable=$::Scratch->{mv_data_enable}, checking");
+	if($::Scratch->{mv_data_enable} =~ /^(\w+):(.*?):/) {
+		# check for single key and possible set of columns
+		my $en_table = $1;
+		$en_col   = $2;
+		my $en_key   = $::Scratch->{mv_data_enable_key};
+#::logDebug("en_table=$en_table en_col=$en_col, en_key=$en_key, checking");
+		if(  $en_table ne $table
+			 or 
+			 ($en_key and $CGI::values{$prikey} ne $en_key)
+			)
+		{
+			logError("Attempted database operation without permission:\n" .
+						 "Permission: '%s' (key='$en_key')\n" .
+						 "Table: '%s'\n" .
+						 "Fields:'%s'\n" .
+						 "Key:   '%s'\n",
+						 $::Scratch->{mv_data_enable},
+						 $CGI::values{mv_data_table},
+						 $CGI::values{mv_data_fields},
+						 $CGI::values{$CGI::values{mv_data_key}},
+				 );
+			return undef;
+		}
+	}
+
+
+	$Vend::WriteDatabase{$table} = 1;
+
+    my $base_db = database_exists_ref($table)
+        or die "Not a defined database '$table': $!\n";
+    $base_db = $base_db->ref();
+
+	my @fields		= grep $_ && $_ ne $prikey,
+						split /[\s\0,]+/, $CGI::values{mv_data_fields};
+	unshift(@fields, $prikey);
+
+    my @file_fields = split /[\s\0,]+/, $CGI::values{mv_data_file_field};
+    my @file_paths = split /[\s\0,]+/, $CGI::values{mv_data_file_path};
+    my @file_oldfiles = split /[\s\0,]+/, $CGI::values{mv_data_file_oldfile};
+
+	if($en_col) {
+		$en_col =~ s/^\s+//;
+		$en_col =~ s/\s+$//;
+		my %col_present;
+		@col_present{ grep /\S/, split /[\s\0,]+/, $en_col } = ();
+		$col_present{$prikey} = 1;
+		for(@fields, $CGI::values{mv_blob_field}, $CGI::values{mv_blob_pointer}) {
+			next unless $_;
+			next if exists $col_present{$_};
+			next if /:/ and $::Scratch->{mv_data_enable} =~ / $_ /;
+			logError("Attempted database operation without permission:\n" .
+						 "Permission: '%s'\n" .
+						 "Table: '%s'\n" .
+						 "Fields:'%s'\n" .
+						 "Key:   '%s'\n",
+						 $::Scratch->{mv_data_enable},
+						 $CGI::values{mv_data_table},
+						 $CGI::values{mv_data_fields},
+						 $CGI::values{$CGI::values{mv_data_key}},
+				 );
+			return undef;
+		}
+	}
+	$function = 'update' unless $function;
+
+	my (%data);
+	for(@fields) {
+		$data{$_} = [];
+	}
+
+	my $count;
+	my $multi = $CGI::values{$prikey} =~ tr/\0/\0/;
+	my $max = 0;
+	my $min = 9999;
+	my ($minname, $maxname);
+
+	while (($key, $value) = each %CGI::values) {
+		next unless defined $data{$key};
+		if($CGI::values{"mv_data_prep_$key"}) {
+			$value = Vend::Interpolate::filter_value(
+						 $CGI::values{"mv_data_prep_$key"},
+						 $value
+						 );
+		}
+		$count = (@{$data{$key}} = split /\0/, $value, -1);
+		$max = $count, $maxname = $key if $count > $max;
+		$min = $count, $minname = $key if $count < $min;
+	}
+
+	if( $multi and ($max - $min) > 1 and ! $CGI::values{mv_data_force}) {
+		logError("probable bad form -- number of values min=%s (%s) max=%s (%s)", $min, $minname, $max, $maxname);
+		return;
+	}
+
+	my $autonumber;
+#::logDebug("function=$function auto_number=" . $base_db->config('_Auto_number'));
+	if ($CGI::values{mv_data_auto_number}) {
+		$autonumber = 1;
+		my $ref = $data{$prikey};
+		while (scalar @$ref < $max) {
+			push @$ref, '';
+		}
+		$base_db->config('AUTO_NUMBER', '000001')
+			if ! $base_db->config('_Auto_number');
+		$CGI::values{mv_data_return_key} = $prikey
+			unless $CGI::values{mv_data_return_key};
+	}
+	elsif($function eq 'insert' and $base_db->config('_Auto_number') ) {
+			$autonumber = 1;
+	}
+#::logDebug("autonumber=$autonumber");
+
+ 	if(@file_fields) {
+		my $Tag = new Vend::Tags;
+		my $acl_func;
+		my $outfile;
+		if($Vend::Session->{logged_in} and $Vend::admin) {
+			$acl_func = sub {
+				return $Tag->if_mm('files', shift);
+			};
+		}
+		elsif($Vend::Session->{logged_in} and ! $Vend::admin) {
+			$acl_func = sub {
+				my $file = shift;
+				return 1 if $::Scratch->{$file} == 1;
+				return $Tag->userdb(
+								function => 'check_file_acl',
+								location => $file,
+								mode => 'w'
+								);
+			};
+		}
+		else {
+			$acl_func = sub { return $::Scratch->{shift(@_)} == 1 }
+		}
+
+		for (my $i = 0; $i < @file_fields; $i++) {
+			unless (length($data{$file_fields[$i]}->[0])) {
+				# no need for a file update
+				$data{$file_fields[$i]}->[0] = $file_oldfiles[$i];
+				next;
+			}
+
+			# remove path components
+			$data{$file_fields[$i]}->[0] =~ s:.*/::; 
+			$data{$file_fields[$i]}->[0] =~ s:.*\\::; 
+
+			if (length ($file_paths[$i])) {
+				# real file upload
+				$outfile = join('/', $file_paths[$i], $data{$file_fields[$i]}->[0]);
+#::logDebug("file upload: field=$file_fields[$i] path=$file_paths[$i] outfile=$outfile");
+				my $ok;
+				if (-f $outfile) {
+					eval {
+						$ok = $acl_func->($outfile);
+					};
+				} else {
+					eval {
+						$ok = $acl_func->($file_paths[$i]);
+					};
+				}
+				if (! $ok) {
+					if($@) {
+						logError ("ACL function failed on '%s': %s", $outfile, $@);
+					}
+					else {
+						logError ("Not allowed to upload \"%s\"", $outfile);
+					}
+					next;
+				} 
+				my $err;
+				Vend::Interpolate::tag_value_extended(
+										$file_fields[$i],
+										{
+											test => 'isfile'
+										}
+										)
+					or do {
+						 logError("%s is not a file.", $data{$file_fields[$i]}->[0]);
+						 next;
+					};
+				Vend::Interpolate::tag_value_extended(
+										$file_fields[$i],
+										{
+											outfile => $outfile,
+											umask => '022',
+											yes => '1',
+										}
+										)
+					or do {
+						 logError("failed to write %s: %s", $outfile, $!);
+						 next;
+					};
+			}
+			else {
+				# preparing to dump file contents into database column
+				$data{$file_fields[$i]}->[0]
+					= Vend::Interpolate::tag_value_extended ($file_fields[$i],
+						{file_contents => 1});
+			}
+		}
+	}
+
+	if (not defined $data{$prikey}) {
+		logError("No key '%s' in field specifier %s", $prikey, 'mv_data_fields');
+		return undef;
+	}
+	elsif ( ! @{$data{$prikey}}) {
+		if($autonumber) {
+			@{$data{$prikey}} = map { '' } @{ $data{$fields[1]} };
+		}
+		else {
+			logError("No key '%s' found for function='%s' table='%s'",
+						$prikey, $function, $CGI::values{mv_data_table},
+						);
+			return undef;
+		}
+	}
+
+	my ($query,$i);
+	my (@k);
+	my (@v);
+	my (@c);
+	my (@rows_set);
+	my (@email_rows);
+
+	my $safe;
+	my $blob_field;
+	my $blob_nick;
+	my $blob_ptr;
+
+	# Fields to set in database despite mv_blob_only
+	my %blob_exception;
+
+	if($CGI::values{mv_blob_field} and $CGI::values{mv_blob_nick}) {
+#::logDebug("update_data: blob processing enabled");
+		$blob_field = $CGI::values{mv_blob_field};
+		$blob_nick  = $CGI::values{mv_blob_nick};
+		$blob_ptr   = $CGI::values{mv_blob_pointer};
+
+		%blob_exception   =
+				map { ($_, 1) } split /[\s,\0]+/, $CGI::values{mv_blob_exception};
+
+		if( ! $base_db->column_exists($blob_field) ) {
+			undef $blob_field;
+			undef $blob_nick;
+			logError("No blob field '%s' found for table='%s', skipping blob save.",
+						$CGI::values{mv_blob_field}, $CGI::values{mv_data_table},
+						);
+		}
+		elsif ($MVSAFE::Safe) {
+			$safe = $Vend::Interpolate::ready_safe;
+		}
+		else {
+			$safe = new Safe;
+		}
+		$base_db->column_exists($blob_ptr)
+			or undef $blob_ptr;
+#::logDebug("update_data: blob safe object=$safe");
+	}
+
+	my @multis;
+	my $multiqual = $CGI::values{mv_data_multiple_qual} || $prikey;
+	if($CGI::values{mv_data_multiple}) {
+		my $re = qr/^\d+_$prikey$/;
+		@multis = grep $_ =~ $re, @cgi_keys;
+		for(@multis) {
+			s/_.*//;
+		}
+		@multis = sort { $a <=> $b } @multis;
+	}
+
+#::logDebug("update_data:db=$db key=$prikey VALUES=" . ::uneval(\%CGI::values));
+#::logDebug("update_data:db=$db key=$prikey data=" . ::uneval(\%data));
+	my $select_key;
+ SETDATA: {
+	for($i = 0; $i < @{$data{$prikey}}; $i++) {
+#::logDebug("iteration of update_data:db=$db key=$prikey data=" . ::uneval(\%data));
+		@k = (); @v = ();
+		for(keys %data) {
+#::logDebug("iteration of field $_");
+
+			next unless (length($value = $data{$_}->[$i]) || $CGI::values{mv_update_empty} );
+			push(@k, $_);
+# LEGACY
+			HTML::Entities::decode($value) if $decode;
+# END LEGACY
+			if($CGI::values{"mv_data_filter_$_"}) {
+				$value = Vend::Interpolate::filter_value(
+							 $CGI::values{"mv_data_filter_$_"},
+							 $value,
+							 $i,
+							 );
+			}
+			$select_key = $value if $_ eq $prikey;
+			push(@v, $value);
+		}
+
+		if(! length($select_key) ) {
+			next if  defined $CGI::values{mv_update_empty_key}
+					 and   ! $CGI::values{mv_update_empty_key};
+		}
+
+		if($function eq 'delete') {
+			$base_db->delete_record($select_key);
+		}
+		else {
+			my $field;
+			$key = $data{$prikey}->[$i];
+			if(! length($key) and ! $autonumber) {
+				## KEY IS possibly SET HERE 
+				$key = $base_db->set_row($key);
+			}
+			push(@rows_set, $key);
+
+			# allow form submissions to go to database and to mail
+			if ($CGI::values{mv_data_email}) {
+				push( @email_rows,
+					[ errmsg("### Form Submission from %s", $key), $blob_nick, ],
+					[ $prikey, $key, ],
+				);
+			}
+
+			my $qd = {};
+			my $qf = {};
+			my $qv = {};
+			my $qret;
+
+			my $blob;
+			my $brec;
+			if($blob_field) {
+				my $string = $base_db->field($key, $blob_field);
+#::logDebug("update_data: blob string=$string");
+				$blob = $safe->reval($string);
+#::logDebug("update_data: blob object=$blob");
+				$blob = {} unless ref($blob) eq 'HASH';
+				$brec = $blob;
+				my @keys = split /::/, $blob_nick;
+				for(@keys) {
+					unless ( ref($brec->{$_}) eq 'HASH') {
+						$brec->{$_} = {};
+					}
+					$brec = $brec->{$_};
+				}
+			}
+			while($field = shift @k) {
+				$value = shift @v;
+				next if $field eq $prikey;
+				
+				## DATA IS SET HERE
+				# We are going to set the field unless it is only for
+				# storing in a blob (and possibly emailing)
+				my  ($d, $f);
+				if ($CGI::values{mv_blob_only} and ! $blob_exception{$field}) {
+#::logDebug("$field not storing, only blob");
+					$f = $field;
+				}
+				else {
+#::logDebug("storing d=$d $field blob_only=$CGI::values{mv_blob_only}");
+					($d, $f) = set_db($base_db, $field);
+#::logDebug("storing table=$table d=$d f=$f key=$key");
+					if(! defined $qd->{$d}) {
+						$qd->{$d} = $d;
+						$qf->{$d} = [$f];
+						$qv->{$d} = [$value];
+					}
+					else {
+						push @{$qf->{$d}}, $f;
+						push @{$qv->{$d}}, $value;
+					}
+					#$d->set_field($key, $f, $value);
+				}
+
+				push(@email_rows, [$f, $value])
+					if $CGI::values{mv_data_email};
+#::logDebug("update_data:db=$d key=$key field=$f value=$value");
+				$brec->{$f} = $value if $brec;
+			}
+
+			for(keys %$qd) {
+#::logDebug("update_data: Getting ready to set_slice");
+				$qret = $qd->{$_}->set_slice($key, $qf->{$_}, $qv->{$_});
+				$rows_set[$i] = $qret unless $rows_set[$i];
+			}
+			if($blob) {
+				$brec->{mv_data_fields} = join " ", @fields;
+				my $string =  uneval_it($blob);
+#::logDebug("update_data: blob saving string=$string");
+				$base_db->set_field($key, $blob_field, $string);
+				if($blob_ptr) {
+					$base_db->set_field($key, $blob_ptr, $blob_nick);
+				}
+			}
+			push(
+					@email_rows,
+					[ errmsg("### END FORM SUBMISSION %s", $key), $blob_nick, ]
+				)
+				if $CGI::values{mv_data_email};
+		}
+	}
+	if(my $new = shift(@multis)) {
+#::logDebug("Doing multi for $new");
+		last SETDATA unless length $CGI::values{"${new}_$multiqual"};
+		for(@fields) {
+			my $value = $CGI::values{$_} = $CGI::values{"${new}_$_"};
+			$data{$_} = [ $value ];
+		}
+		redo SETDATA;
+	}
+ } # end SETDATA
+
+	if($CGI::values{mv_data_return_key}) {
+		my @keys = split /\0/, $CGI::values{mv_data_return_key};
+		for(@keys) {
+#::logDebug("return_key, setting $_");
+			$CGI::values{$_} = join("\0", @rows_set);
+		}
+	}
+
+	if($CGI::values{mv_auto_export}) {
+		Vend::Data::export_database($table);
+	}
+
+	if($CGI::values{mv_data_email}) {
+		push @email_rows, [ 'mv_data_fields', \@fields ];
+		Vend::Interpolate::tag_mail('', { log_error => 1 }, \@email_rows);
+	}
+
+	# Allow setting in one then returning to another
+	if($CGI::values{mv_return_table}) {
+		$CGI::values{mv_data_table} = $CGI::values{mv_return_table};
+	}
+
+	my @reloads = grep /^mv_data_table__\d+$/, keys %CGI::values;
+	if(@reloads) {
+		@reloads = map { m/.*__(\d+)$/; $1 } @reloads;
+		@reloads = sort { $a <=> $b } @reloads;
+		my $new = shift @reloads;
+		my $this = qr{__$new$};
+		my $some = qr{__\d+$};
+#::logDebug("Reloading, new=$new this=$this some=$some");
+		my %cgiset;
+		my @death_row;
+		for(@cgi_keys) {
+			push(@death_row, $_), next unless $_ =~ $some;
+			if($_ =~ $this) {
+				my $k = $_;
+				$k =~ s/$this//;
+				$cgiset{$k} = delete $CGI::values{$_};
+			}
+		}
+
+		$::Scratch->{mv_data_enable} = delete $::Scratch->{"mv_data_enable__$new"};
+		delete $::Scratch->{mv_data_enable_key};
+
+		for(@death_row) {
+			next unless /^mv_(data|blob|update)_/ or $data{$_}; # Reprieve!
+			delete $CGI::values{$_};
+		}
+
+		@CGI::values{keys %cgiset} = values %cgiset;
+#::logDebug("Reloading, function=$CGI::values{mv_data_function}");
+		update_data();
+	}
+
+	return;
+}
+
+*dbref = \&database_exists_ref;
 
 1;
 



1.7.4.2   +119 -69   interchange/lib/Vend/DbSearch.pm


rev 1.7.4.2, prev_rev 1.7.4.1
Index: DbSearch.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/DbSearch.pm,v
retrieving revision 1.7.4.1
retrieving revision 1.7.4.2
diff -u -r1.7.4.1 -r1.7.4.2
--- DbSearch.pm	3 Dec 2000 17:25:11 -0000	1.7.4.1
+++ DbSearch.pm	25 Jan 2003 22:21:27 -0000	1.7.4.2
@@ -1,10 +1,10 @@
-# Vend/DbSearch.pm:  Search indexes with Perl
+# Vend::DbSearch - Search indexes with Interchange
 #
-# $Id: DbSearch.pm,v 1.7.4.1 2000/12/03 17:25:11 racke Exp $
+# $Id: DbSearch.pm,v 1.7.4.2 2003/01/25 22:21:27 racke Exp $
 #
-# ADAPTED FOR USE WITH INTERCHANGE from Search::TextSearch
+# Adapted for use with Interchange from Search::TextSearch
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -26,7 +26,7 @@
 
 @ISA = qw(Vend::Search);
 
-$VERSION = substr(q$Revision: 1.7.4.1 $, 10);
+$VERSION = substr(q$Revision: 1.7.4.2 $, 10);
 
 use Search::Dict;
 use strict;
@@ -34,74 +34,84 @@
 sub array {
 	my ($s, $opt) = @_;
 	$s->{mv_one_sql_table} = 1;
-	$s->{mv_list_only} = 1;
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 sub hash {
 	my ($s, $opt) = @_;
 	$s->{mv_return_reference} = 'HASH';
 	$s->{mv_one_sql_table} = 1;
-	$s->{mv_list_only} = 1;
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 sub list {
 	my ($s, $opt) = @_;
-	$s->{mv_list_only} = 1;
 	$s->{mv_return_reference} = 'LIST';
 	$s->{mv_one_sql_table} = 1;
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 my %Default = (
-        matches                 => 0,
-        mv_head_skip            => 0,
-        mv_index_delim          => "\t",
-        mv_matchlimit           => 50,
-        mv_min_string           => 1,
-        verbatim_columns        => 1,
-	);
+	matches                 => 0,
+	mv_head_skip            => 0,
+	mv_index_delim          => "\t",
+	mv_matchlimit           => 50,
+	mv_min_string           => 1,
+	verbatim_columns        => 1,
+);
 
 sub init {
 	my ($s, $options) = @_;
 
+	# autovivify references of nested data structures we use below, since they
+	# don't yet exist at daemon startup time before configuration is done
+	$Vend::Cfg->{ProductFiles}[0] or 1;
+	$::Variable->{MV_DEFAULT_SEARCH_TABLE} or 1;
+
 	@{$s}{keys %Default} = (values %Default);
-    $s->{mv_all_chars}	        = [1];
-    $s->{mv_base_directory}     = $Vend::Cfg->{ProductFiles}[0];
-    $s->{mv_begin_string}       = [];
-    $s->{mv_case}               = [];
-    $s->{mv_column_op}          = [];
-    $s->{mv_negate}             = [];
-    $s->{mv_numeric}            = [];
-    $s->{mv_orsearch}           = [];
-    $s->{mv_search_field}       = [];
-    $s->{mv_search_file}        =	[ @{
-										$::Variable->{MV_DEFAULT_SEARCH_FILE}
-										||	$Vend::Cfg->{ProductFiles}
-										} ];
-    $s->{mv_search_group}       = [];
-    $s->{mv_searchspec}         = [];
-    $s->{mv_sort_option}        = [];
-    $s->{mv_substring_match}    = [];
+	$s->{mv_all_chars}	        = [1];
+	
+	### This is a bit of a misnomer, for really it is the base table
+	### that we will use if no base=table param is specified
+	$s->{mv_base_directory}     = $Vend::Cfg->{ProductFiles}[0];
+	$s->{mv_begin_string}       = [];
+	$s->{mv_case}               = [];
+	$s->{mv_column_op}          = [];
+	$s->{mv_negate}             = [];
+	$s->{mv_numeric}            = [];
+	$s->{mv_orsearch}           = [];
+	$s->{mv_search_field}       = [];
+	$s->{mv_search_group}       = [];
+	$s->{mv_searchspec}         = [];
+	$s->{mv_sort_option}        = [];
+	$s->{mv_substring_match}    = [];
 
 	for(keys %$options) {
 		$s->{$_} = $options->{$_};
 	}
+	$s->{mv_search_file}        =	[ @{
+										$::Variable->{MV_DEFAULT_SEARCH_TABLE}
+										||	$Vend::Cfg->{ProductFiles}
+										} ]
+		unless ref($s->{mv_search_file}) and scalar(@{$s->{mv_search_file}});
 
 	return;
 }
 
 sub new {
-    my ($class, %options) = @_;
+	my ($class, %options) = @_;
 	my $s = new Vend::Search;
 	bless $s, $class;
+#::logDebug("mv_search_file initted=" . ::uneval($options{mv_search_file}));
 	$s->init(\%options);
+#::logDebug("mv_search_file now=" . ::uneval($s->{mv_search_file}));
 	return $s;
 }
 
 sub search {
-
 	my($s,%options) = @_;
 
 	my(@out);
@@ -124,16 +134,14 @@
 		s:.*/::;
 		s/\..*//;
 	}
-#::logDebug ("searching: searchfiles='@searchfiles', obj=" . ::uneval($s));
 	my $dbref = $s->{table} || undef;
-#::logDebug("before db mapping: self=" . ::Vend::Util::uneval_it({%$s}));
 
 	if( ! $dbref ) {
 		$s->{dbref} = $dbref = Vend::Data::database_exists_ref($searchfiles[0]);
 	}
 	if(! $dbref) {
 		return $s->search_error(
-			"your search file a valid database reference, was '$searchfiles[0]'."
+			"search file '$searchfiles[0]' is not a valid database reference."
 			);
 	}
 	$s->{dbref} = $dbref;
@@ -142,15 +150,6 @@
 
 	@specs = @{$s->{mv_searchspec}};
 
-    if(ref $s->{mv_range_look}) {
-        unless( scalar(@{$s->{mv_range_look}}) == scalar(@{$s->{mv_range_min}}) and
-                scalar(@{$s->{mv_range_look}}) == scalar(@{$s->{mv_range_max}}) ) {
-			$s->{mv_search_warning}
-				= "Must have min and max values for range -- aborting range look.";
-			undef $s->{mv_range_look};
-		}
-	}
-
 	@pats = $s->spec_check(@specs);
 
 	if ($s->{mv_coordinate}) {
@@ -176,17 +175,44 @@
 
 	$@  and  return $s->search_error("Function creation: $@");
 
+	if(ref $s->{mv_like_field} and ref $s->{mv_like_spec}) {
+		my $ary = [];
+		for(my $i = 0; $i < @{$s->{mv_like_field}}; $i++) {
+			my $col = $s->{mv_like_field}[$i];
+			next unless length($col);
+			my $val = $s->{mv_like_spec}[$i];
+			length($val) or next;
+			next unless defined $dbref->test_column($col);
+			$val = $dbref->quote("$val%");
+			if(
+				! $dbref->config('UPPER_COMPARE')
+					or 
+				$s->{mv_case_sensitive} and $s->{mv_case_sensitive}[0]
+				)
+			{
+				push @$ary, "$col like $val";
+			}
+			else {
+				$val = uc $val;
+				push @$ary, "UPPER($col) like $val";
+			}
+		}
+		if(@$ary) {
+			$s->{eq_specs_sql} = [] if ! $s->{eq_specs_sql};
+			push @{$s->{eq_specs_sql}}, @$ary;
+		}
+	}
+
 	my $qual;
 	if($s->{eq_specs_sql}) {
 		$qual = ' WHERE ';
-		my $joiner = ' AND ';
-		$joiner = ' OR ' if $s->{mv_orsearch}[0];
+		my $joiner = $s->{mv_orsearch}[0] ? ' OR ' : ' AND ';
 		$qual .= join $joiner, @{$s->{eq_specs_sql}};
 	}
 
 	$s->save_specs();
-#::logDebug("searchfiles=@searchfiles");
 	foreach $searchfile (@searchfiles) {
+		my $lqual = $qual || '';
 		$searchfile =~ s/\..*//;
 		my $db;
 		if (! $s->{mv_one_sql_table} ) {
@@ -197,8 +223,16 @@
 						), next;
 			
 			$dbref = $s->{dbref} = $db->ref();
+			$dbref->reset();
 			@fn = $dbref->columns();
 		}
+
+		if(! $s->{mv_no_hide} and my $hf = $dbref->config('HIDE_FIELD')) {
+#::logDebug("found hide_field $hf");
+			$lqual =~ s/^\s*WHERE\s+/ WHERE $hf != 1 AND /
+				or $lqual = " WHERE $hf != 1";
+#::logDebug("lqual now '$lqual'");
+		}
 		$s->hash_fields(\@fn);
 		my $prospect;
 		eval {
@@ -216,18 +250,21 @@
 		if(! defined $f and defined $limit_sub) {
 #::logDebug("no f, limit, dbref=$dbref");
 			local($_);
-			while($_ = join "\t", $dbref->each_nokey($qual || undef) ) {
-				next unless &$limit_sub($_);
-				push @out, &$return_sub($_);
+			my $ref;
+			while($ref = $dbref->each_nokey($lqual) ) {
+				next unless $limit_sub->($ref);
+				push @out, $return_sub->($ref);
 			}
 		}
 		elsif(defined $limit_sub) {
 #::logDebug("f and limit, dbref=$dbref");
 			local($_);
-			while($_ = join "\t", $dbref->each_nokey($qual || undef) ) {
+			my $ref;
+			while($ref = $dbref->each_nokey($lqual) ) {
+				$_ = join "\t", @$ref;
 				next unless &$f();
-				next unless &$limit_sub($_);
-				push @out, &$return_sub($_);
+				next unless $limit_sub->($ref);
+				push @out, $return_sub->($ref);
 			}
 		}
 		elsif (!defined $f) {
@@ -236,15 +273,25 @@
 		else {
 #::logDebug("f and no limit, dbref=$dbref");
 			local($_);
-			while($_ = join "\t", $dbref->each_nokey($qual || undef) ) {
+			my $ref;
+			while($ref = $dbref->each_nokey($lqual) ) {
+#::logDebug("f and no limit, ref=$ref");
+				$_ = join "\t", @$ref;
 				next unless &$f();
-				push @out, &$return_sub($_);
+				push @out, $return_sub->($ref);
 			}
 		}
 		$s->restore_specs();
 	}
 
+	# Search the results and return
+	if($s->{mv_next_search}) {
+		@out = $s->search_reference(\@out);
+#::logDebug("did next_search: " . ::uneval(\@out));
+	}
+
 	$s->{matches} = scalar(@out);
+
 #::logDebug("before delayed return: self=" . ::Vend::Util::uneval_it({%$s}));
 
 	if($delayed_return and $s->{matches} > 0) {
@@ -253,17 +300,22 @@
 		$delayed_return = $s->get_return(1);
 		@out = map { $delayed_return->($_) } @out;
 	}
-#::logDebug("after delayed return: self=" . ::Vend::Util::uneval_it({%$s}));
+#::logDebug("after delayed return: self=" . ::Vend::Util::uneval({%$s}));
 
 	if($s->{mv_unique}) {
 		my %seen;
 		@out = grep ! $seen{$_->[0]}++, @out;
-		$s->{matches} = scalar(@out);
 	}
 
-    if ($s->{matches} > $s->{mv_matchlimit}) {
-        $s->save_more(\@out)
-            or ::logError("Error saving matches: $!");
+	if($s->{mv_max_matches} > 0) {
+		splice @out, $s->{mv_max_matches};
+	}
+
+	$s->{matches} = scalar(@out);
+
+	if ($s->{matches} > $s->{mv_matchlimit} and $s->{mv_matchlimit} > 0) {
+		$s->save_more(\@out)
+			or ::logError("Error saving matches: $!");
 		if ($s->{mv_first_match}) {
 			splice(@out,0,$s->{mv_first_match}) if $s->{mv_first_match};
 			$s->{mv_next_pointer} = $s->{mv_first_match} + $s->{mv_matchlimit};
@@ -304,16 +356,14 @@
 					if $s->{mv_next_pointer} > $s->{matches};
 			}
 		}
-        $#out = $s->{mv_matchlimit} - 1;
-    }
+		$#out = $s->{mv_matchlimit} - 1;
+	}
 #::logDebug("after hash fields: self=" . ::Vend::Util::uneval_it({%$s}));
-#::logDebug("after delayed return: self=" . ::Vend::Util::uneval_it({%$s}));
 
 	if(! $s->{mv_return_reference}) {
 		$s->{mv_results} = \@out;
 	}
 	elsif($s->{mv_return_reference} eq 'LIST') {
-		my $col = scalar @{$s->{mv_return_fields}};
 		@out = map { join $s->{mv_return_delim}, @$_ } @out;
 		$s->{mv_results} = join $s->{mv_record_delim}, @out;
 	}



1.2.4.1   +3 -4      interchange/lib/Vend/Document.pm


rev 1.2.4.1, prev_rev 1.2
Index: Document.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Document.pm,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- Document.pm	12 Jul 2000 03:08:10 -0000	1.2
+++ Document.pm	25 Jan 2003 22:21:27 -0000	1.2.4.1
@@ -1,9 +1,8 @@
-#!/usr/bin/perl
-# Document.pm - Document object for embedded Perl/ASP
+# Vend::Document - Document object for Interchange embedded Perl/ASP
 # 
-# $Id: Document.pm,v 1.2 2000/07/12 03:08:10 heins Exp $
+# $Id: Document.pm,v 1.2.4.1 2003/01/25 22:21:27 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by



1.3.4.1   +34 -13    interchange/lib/Vend/Error.pm


rev 1.3.4.1, prev_rev 1.3
Index: Error.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Error.pm,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- Error.pm	12 Jul 2000 03:08:10 -0000	1.3
+++ Error.pm	25 Jan 2003 22:21:27 -0000	1.3.4.1
@@ -1,8 +1,8 @@
-# Error.pm - Handle Interchange error pages and messages
+# Vend::Error - Handle Interchange error pages and messages
 # 
-# $Id: Error.pm,v 1.3 2000/07/12 03:08:10 heins Exp $
+# $Id: Error.pm,v 1.3.4.1 2003/01/25 22:21:27 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -37,9 +37,7 @@
 
 use vars qw/$VERSION/;
 
-$VERSION = sprintf("%d.%02d", q$Revision: 1.3 $ =~ /(\d+)\.(\d+)/);
-
-my $wantref = 1;
+$VERSION = substr(q$Revision: 1.3.4.1 $, 10);
 
 sub get_locale_message {
 	my ($code, $message, @arg) = @_;
@@ -49,6 +47,12 @@
 	elsif ($Global::Locale and defined $Global::Locale->{$code}) {
 		$message = $Global::Locale->{$code};
 	}
+	elsif ($Vend::Cfg->{Locale} and -f "$Global::ConfDir/$code.html" ) {
+		$message = readfile("$Global::ConfDir/$code.$::Scratch->{mv_locale}");
+	}
+	elsif (-f "$Global::ConfDir/$code.html") {
+		$message = readfile("$Global::ConfDir/$code.html");
+	}
 	if($message !~ /\s/) {
 		if($message =~ /^http:/) {
 			$Vend::StatusLine =~ s/([^\r\n])$/$1\r\n/;
@@ -77,7 +81,8 @@
     $page = readin(find_special_page('interact'));
     if (defined $page) {
 		$page =~ s#\[message\]#$msg#ig;
-		::response(::interpolate_html($page, 1));
+		::interpolate_html($page, 1);
+		::response();
     }
 	else {
 		logError( "Missing special page: interact" , '');
@@ -104,20 +109,36 @@
 }
 
 sub full_dump {
-	my $out = minidump();
+	my $portion = shift;
+	my $out = '';
+	if($portion) {
+		$out .= "###### SESSION ($portion) #####\n";
+		$out .= uneval($Vend::Session->{$portion});
+		$out .= "\n###### END SESSION    #####\n";
+		$out =~ s/\0/\\0/g;
+		return $out;
+	}
+
+	$out = minidump();
 	local($Data::Dumper::Indent) = 2;
 	$out .= "###### ENVIRONMENT     #####\n";
-	$out .= ::uneval(::http()->{env});
+	if(my $h = ::http()) {
+		$out .= uneval($h->{env});
+	}
+	else {
+		$out .= uneval(\%ENV);
+	}
 	$out .= "\n###### END ENVIRONMENT #####\n";
 	$out .= "###### CGI VALUES      #####\n";
-	$out .= ::uneval(\%CGI::values);
+	$out .= uneval(\%CGI::values);
 	$out .= "\n###### END CGI VALUES  #####\n";
 	$out .= "###### SESSION         #####\n";
-	$out .= ::uneval($Vend::Session);
+	$out .= uneval($Vend::Session);
 	$out .= "\n###### END SESSION    #####\n";
+	$out =~ s/\0/\\0/g;
+	return $out;
 }
 
-
 sub do_lockout {
 	my ($cmd);
 	my $msg = shift || '';
@@ -128,7 +149,7 @@
 		system $cmd;
 		$msg .= errmsg("\nBad status %s from '%s': %s\n", $?, $cmd, $!)
 			if $?;
-		logGlobal( $msg);
+		logGlobal({level => 'notice'}, $msg);
 	}
 	$Vend::Cfg->{VendURL} = $Vend::Cfg->{SecureURL} = 'http://127.0.0.1';
 	logError($msg);



1.2.4.1   +3 -3      interchange/lib/Vend/External.pm


rev 1.2.4.1, prev_rev 1.2
Index: External.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/External.pm,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- External.pm	12 Jul 2000 03:08:10 -0000	1.2
+++ External.pm	25 Jan 2003 22:21:27 -0000	1.2.4.1
@@ -1,8 +1,8 @@
-# External.pm - Interchange routines rarely used or not requiring much performance
+# Vend::External - Interchange routines for calling external programs
 # 
-# $Id: External.pm,v 1.2 2000/07/12 03:08:10 heins Exp $
+# $Id: External.pm,v 1.2.4.1 2003/01/25 22:21:27 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by



1.4.4.1   +72 -72    interchange/lib/Vend/Glimpse.pm


rev 1.4.4.1, prev_rev 1.4
Index: Glimpse.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Glimpse.pm,v
retrieving revision 1.4
retrieving revision 1.4.4.1
diff -u -r1.4 -r1.4.4.1
--- Glimpse.pm	19 Sep 2000 18:58:39 -0000	1.4
+++ Glimpse.pm	25 Jan 2003 22:21:27 -0000	1.4.4.1
@@ -1,10 +1,10 @@
-# Vend/Glimpse.pm:  Search indexes with Glimpse
+# Vend::Glimpse - Search indexes with Glimpse
 #
-# $Id: Glimpse.pm,v 1.4 2000/09/19 18:58:39 zarko Exp $
+# $Id: Glimpse.pm,v 1.4.4.1 2003/01/25 22:21:27 racke Exp $
 #
-# ADAPTED FOR USE WITH INTERCHANGE from Search::Glimpse
+# Adapted for use with Interchange from Search::Glimpse
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -20,66 +20,64 @@
 # License along with this program; if not, write to the Free
 # Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 # MA  02111-1307  USA.
-#
-#
 
 package Vend::Glimpse;
 require Vend::Search;
 @ISA = qw(Vend::Search);
 
-$VERSION = substr(q$Revision: 1.4 $, 10);
+$VERSION = substr(q$Revision: 1.4.4.1 $, 10);
 use strict;
 
 sub array {
 	my ($s, $opt) = @_;
-	$s->{mv_list_only} = 1;
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 sub hash {
 	my ($s, $opt) = @_;
 	$s->{mv_return_reference} = 'HASH';
-	$s->{mv_list_only} = 1;
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 sub list {
 	my ($s, $opt) = @_;
-	$s->{mv_list_only} = 1;
 	$s->{mv_return_reference} = 'LIST';
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 my %Default = (
-        matches                 => 0,
-        mv_head_skip            => 0,
-        mv_index_delim          => "\t",
-        mv_record_delim         => "\n",
-        mv_matchlimit           => 50,
-        mv_max_matches          => 2000,
-        mv_min_string           => 4,
-	);
+		matches                 => 0,
+		mv_head_skip            => 0,
+		mv_index_delim          => "\t",
+		mv_record_delim         => "\n",
+		mv_matchlimit           => 50,
+		mv_max_matches          => 2000,
+		mv_min_string           => 4,
+);
 
 
 sub init {
 	my ($s, $options) = @_;
 
 	@{$s}{keys %Default} = (values %Default);
-    $s->{mv_base_directory}     = $Vend::Cfg->{ProductDir} || 'products',
-    $s->{mv_begin_string}       = [];
-    $s->{mv_all_chars}	        = [1];
-    $s->{mv_case}               = [];
-    $s->{mv_column_op}          = [];
-    $s->{mv_negate}             = [];
-    $s->{mv_numeric}            = [];
-    $s->{mv_orsearch}           = [];
-    $s->{mv_searchspec}	        = [];
-    $s->{mv_search_group}       = [];
-    $s->{mv_search_field}       = [];
-    $s->{mv_search_file}        = [];
-    $s->{mv_searchspec}         = [];
-    $s->{mv_sort_option}        = [];
-    $s->{mv_substring_match}    = [];
+	$s->{mv_base_directory}     = $Vend::Cfg->{ProductDir} || 'products',
+	$s->{mv_begin_string}       = [];
+	$s->{mv_all_chars}	        = [1];
+	$s->{mv_case}               = [];
+	$s->{mv_column_op}          = [];
+	$s->{mv_negate}             = [];
+	$s->{mv_numeric}            = [];
+	$s->{mv_orsearch}           = [];
+	$s->{mv_searchspec}	        = [];
+	$s->{mv_search_group}       = [];
+	$s->{mv_search_field}       = [];
+	$s->{mv_search_file}        = [];
+	$s->{mv_searchspec}         = [];
+	$s->{mv_sort_option}        = [];
+	$s->{mv_substring_match}    = [];
 	$s->{mv_field_file}         = $::Variable->{MV_DEFAULT_SEARCH_FILE}[0];
 	$s->{glimpse_cmd} = $Vend::Cfg->{Glimpse} || 'glimpse';
 
@@ -91,7 +89,7 @@
 }
 
 sub new {
-    my ($class, %options) = @_;
+	my ($class, %options) = @_;
 	my $s = new Vend::Search;
 	bless $s, $class;
 	$s->init(\%options);
@@ -124,38 +122,30 @@
 	$s->{mv_return_delim} = $s->{mv_index_delim}
 		unless defined $s->{mv_return_delim};
 
-    if(ref $s->{mv_range_look}) {
-        unless( scalar(@{$s->{mv_range_look}}) == scalar(@{$s->{mv_range_min}}) and
-                scalar(@{$s->{mv_range_look}}) == scalar(@{$s->{mv_range_max}}) ) {
-			$s->{mv_search_warning}
-				= "Must have min and max values for range -- aborting range look.";
-			undef $s->{mv_range_look};
-		}
-	}
+	return $s->search_error("Search with glimpse, no glimpse configured.")
+		if ! $s->{glimpse_cmd};
+
 	@specs = @{$s->{mv_searchspec}};
 
 	@pats = $s->spec_check(@specs);
 
-	return $s->search_error("Search with glimpse, no glimpse configured.")
-		if ! $s->{glimpse_cmd};
-
 	return undef if $s->{matches} == -1;
 
-    # Build glimpse line
+	# Build glimpse line
 	my @cmd;
-    push @cmd, $s->{glimpse_cmd};
+	push @cmd, $s->{glimpse_cmd};
 	push @cmd, "-H $s->{mv_base_directory}"
 			unless $s->{glimpse_cmd} =~ /\s+-H/;
 
-    if ($s->{mv_spelling_errors}) {
-        $s->{mv_spelling_errors} = int  $s->{mv_spelling_errors};
-        push @cmd, '-' . $s->{mv_spelling_errors};
-    }
-	
-    push @cmd, "-i" unless $s->{mv_case};
-    push @cmd, "-h" unless $s->{mv_return_file_name};
-    push @cmd, "-y -L $s->{mv_max_matches}:0:$s->{mv_max_matches}";
-    push(@cmd, "-F '$s->{mv_search_file}[0]'")
+	if ($s->{mv_spelling_errors}) {
+		$s->{mv_spelling_errors} = int  $s->{mv_spelling_errors};
+		push @cmd, '-' . $s->{mv_spelling_errors};
+	}
+
+	push @cmd, "-i" unless $s->{mv_case} and $s->{mv_case}[0];
+	push @cmd, "-h" unless $s->{mv_return_file_name};
+	push @cmd, "-y -L $s->{mv_max_matches}:0:$s->{mv_max_matches}";
+	push(@cmd, "-F '$s->{mv_search_file}[0]'")
 		if defined $s->{mv_search_file}[0];
 
 	push(@cmd, '-w') unless $s->{mv_substring_match};
@@ -214,7 +204,17 @@
 	
 	my $spec = join $joiner, @pats;
 	$spec =~ s/'/./g;
-    push @cmd, "'$spec'";
+
+	if(length($spec) < $s->{mv_min_string}) {
+		my $msg = errmsg(
+					"Glimpse search string less than minimum %s characters: %s",
+					$s->{mv_min_string},
+					$spec,
+				);
+		return $s->search_error($msg);
+	}
+
+	push @cmd, "'$spec'";
 
 	$joiner = $spec;
 	$joiner =~ s/['";,]//g;
@@ -240,18 +240,18 @@
 
 		# Get field names only if no sort (will throw it off) or
 		# not already defined
-        if($s->{mv_field_file}) {
+		if($s->{mv_field_file}) {
 			$s->{mv_field_file} =
 					::catfile($Vend::Cfg->{ProductDir}, $s->{mv_field_file})
 				unless ::file_name_is_absolute($s->{mv_field_file});
 			open(FF, "< $s->{mv_field_file}")
 				or return $s->search_error("can't open fields file");
-            chomp($field_names = <FF>);
-        }
+			chomp($field_names = <FF>);
+		}
 		if($field_names) {
 			$field_names =~ s/^\s+//;
 			my @laundry = (qw/mv_search_field mv_range_look mv_return_fields/);
-            $s->hash_fields(
+			$s->hash_fields(
 						[ split /\Q$s->{mv_index_delim}/, $field_names ],
 						@laundry,
 			);
@@ -262,14 +262,14 @@
 		my $prospect;
 
 		eval {
-			($limit_sub, $prospect) = $s->get_limit($f);
+			($limit_sub, $prospect) = $s->get_limit($f, 1);
 		};
 
 		$@  and  return $s->search_error("Limit subroutine creation: $@");
 
 		$f = $prospect if $prospect;
 
-		eval {($return_sub, $delayed_return) = $s->get_return()};
+		eval {($return_sub, $delayed_return) = $s->get_return(undef, 1)};
 
 		$@  and  return $s->search_error("Return subroutine creation: $@");
 
@@ -321,7 +321,7 @@
 		$s->hash_fields($s->{mv_field_names}, qw/mv_sort_field/);
 #::logDebug("gsearch after hash fields: self=" . ::Vend::Util::uneval_it({%$s}));
 		$s->sort_search_return(\@out);
-		$delayed_return = $s->get_return(1);
+		$delayed_return = $s->get_return(1,1);
 		@out = map { $delayed_return->($_) } @out;
 	}
 #::logDebug("after delayed return: self=" . ::Vend::Util::uneval_it({%$s}));
@@ -332,17 +332,17 @@
 		$s->{matches} = scalar(@out);
 	}
 
-    if ($s->{matches} > $s->{mv_matchlimit}) {
-        $s->save_more(\@out)
-            or ::logError("Error saving matches: $!");
+	if ($s->{matches} > $s->{mv_matchlimit} and $s->{mv_matchlimit} > 0) {
+		$s->save_more(\@out)
+			or ::logError("Error saving matches: $!");
 		if ($s->{mv_first_match}) {
 			splice(@out,0,$s->{mv_first_match});
 			$s->{mv_next_pointer} = $s->{mv_first_match} + $s->{mv_matchlimit};
 			$s->{mv_next_pointer} = 0
 				if $s->{mv_next_pointer} > $s->{matches};
 		}
-        $#out = $s->{mv_matchlimit} - 1;
-    }
+		$#out = $s->{mv_matchlimit} - 1;
+	}
 
 	if(! $s->{mv_return_reference}) {
 		$s->{mv_results} = \@out;



1.2.4.1   +11 -15    interchange/lib/Vend/Imagemap.pm


rev 1.2.4.1, prev_rev 1.2
Index: Imagemap.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Imagemap.pm,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- Imagemap.pm	12 Jul 2000 03:08:10 -0000	1.2
+++ Imagemap.pm	25 Jan 2003 22:21:27 -0000	1.2.4.1
@@ -1,16 +1,14 @@
-#!/usr/bin/perl
+# Vend::Imagemap - Interpret NCSA imagemaps in Interchange
 #
-# Imagemap.pm -- interpret NCSA imagemap in CGI program
-#
-# $Id: Imagemap.pm,v 1.2 2000/07/12 03:08:10 heins Exp $
+# $Id: Imagemap.pm,v 1.2.4.1 2003/01/25 22:21:27 racke Exp $
 #
 # This module adapted from the Perl imagemap program by:
 #
 # V. Khera <khera@kciLink.com>  7-MAR-1995
 #
-# documentation for the imagemap file follows that of the NCSA imagemap
-# program.  Each point is an x,y tuple.  Each line in the map consists of
-# one of the following formats.  Comment lines start with "#".
+# Documentation for the imagemap file follows that of the NCSA imagemap
+# program. Each point is an x,y tuple. Each line in the map consists of
+# one of the following formats. Comment lines start with "#".
 #
 #   circle action center edgepoint
 #   rect action upperleft lowerright
@@ -18,10 +16,10 @@
 #   poly action point1 point2 point3 point4 ... pointN
 #   default action
 #
-# using "point" and "default" in the same map makes no sense.  if "point"
+# Using "point" and "default" in the same map makes no sense. If "point"
 # is used, the action for the closest one is selected.
 #
-# To use, define an image submit map on your form
+# To use, define an image submit map on your form:
 #
 #   <input type=image name=mv_todo SRC="image_url">
 #   You can pass a "client-side" imagemap like this:
@@ -32,15 +30,13 @@
 #
 # If the @map passed parameter contains a NUL (\0) in the first array
 # position, the map is assumed to be null-separated and @map is built
-# by splitting it.  This allows a null-separated todo.map with
-# multiple values (parsed by a cgi-lib.pl or the like) to be
-# referenced.
+# by splitting it. This allows a null-separated todo.map with multiple
+# values (parsed by a cgi-lib.pl or the like) to be referenced.
 #
 # usage:
 #
-#   use Imagemap;
+#   use Vend::Imagemap;
 #   $action = action_map($x, $y, @map);
-#
 
 package Vend::Imagemap;
 require Exporter;
@@ -50,7 +46,7 @@
 @EXPORT = qw(action_map);
 use strict;
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.2 $, 10);
+$VERSION = substr(q$Revision: 1.2.4.1 $, 10);
 
 my $Action = "";
 my $minDistance = -1;



1.29.4.15 +2991 -1581interchange/lib/Vend/Interpolate.pm


rev 1.29.4.15, prev_rev 1.29.4.14
Index: Interpolate.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Interpolate.pm,v
retrieving revision 1.29.4.14
retrieving revision 1.29.4.15
diff -u -r1.29.4.14 -r1.29.4.15
--- Interpolate.pm	11 Aug 2001 11:31:56 -0000	1.29.4.14
+++ Interpolate.pm	25 Jan 2003 22:21:27 -0000	1.29.4.15
@@ -1,16 +1,11 @@
-#!/usr/bin/perl
-# Interpolate.pm - Interpret Interchange tags
+# Vend::Interpolate - Interpret Interchange tags
 # 
-# $Id: Interpolate.pm,v 1.29.4.14 2001/08/11 11:31:56 racke Exp $
+# $Id: Interpolate.pm,v 1.29.4.15 2003/01/25 22:21:27 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -32,7 +27,7 @@
 require Exporter;
 @ISA = qw(Exporter);
 
-$VERSION = substr(q$Revision: 1.29.4.14 $, 10);
+$VERSION = substr(q$Revision: 1.29.4.15 $, 10);
 
 @EXPORT = qw (
 
@@ -40,9 +35,44 @@
 interpolate_html
 subtotal
 tag_data
+tag_attr_list
+$Tag
+$CGI
+$Session
+$Values
 
 );
 
+=head1 NAME
+
+Vend::Interpolate -- Interchange tag interpolation routines
+
+=head1 SYNOPSIS
+
+(no external use)
+
+=head1 DESCRIPTION
+
+The Vend::Interpolate contains the majority of the Interchange Tag
+Language implementation rouines. Historically, it contained the entire
+tag language implementation for MiniVend, accounting for its name.
+
+It contains most of the handler routines pointed to by Vend::Parse, which
+accepts the parsing output of Vend::Parser. (Vend::Parser was originally based
+on HTML::Parser 1.x).
+
+There are two interpolative parsers in Vend::Interpolate,
+iterate_array_list() and iterate_hash_list() -- these routines parse
+the lists used in the widely employed [loop ..], [search-region ...],
+[item-list], and [query ..] ITL tag constructs.
+
+This module makes heavy use of precompiled regexes. You will notice variables
+being used in the regular expression constructs. For example, C<$All> is a
+a synonym for C<[\000-\377]*>, C<$Some> is equivalent to C<[\000-\377]*?>, etc.
+This is not only for clarity of the regular expression, but for speed.
+
+=cut
+
 # SQL
 push @EXPORT, 'tag_sql_list';
 # END SQL
@@ -58,10 +88,12 @@
 		$hole = new Safe::Hole;
 	};
 }
+my $tag_wrapped;
 
 use strict;
 use Vend::Util;
 use Vend::Data;
+use Vend::Form;
 require Vend::Cart;
 
 
@@ -120,48 +152,65 @@
 						/;
 	@Share_routines = qw/
 							&tag_data
+							&errmsg
 							&Log
+							&Debug
 							&uneval
+							&get_option_hash
+							&dotted_hash
 							&HTML
 							&interpolate_html
 						/;
 }
 
-use vars @Share_vars, @Share_routines, qw/$Calc_initialized $Calc_reset $ready_safe/;
-use vars qw/%Filter %Ship_handler/;
+use vars @Share_vars, @Share_routines,
+		 qw/$ready_safe $safe_safe/;
+use vars qw/%Filter %Ship_handler $Safe_data/;
 
 $ready_safe = new Safe;
+$ready_safe->trap(qw/:base_io/);
 $ready_safe->untrap(qw/sort ftfile/);
 
 sub reset_calc {
-#::logGlobal("resetting calc");
-	if(defined $Vend::Cfg->{ActionMap}{_mvsafe}) {
-#::logGlobal("already made");
+#::logDebug("reset_state=$Vend::Calc_reset -- resetting calc from " . caller);
+	if(! $Global::Foreground and $Vend::Cfg->{ActionMap}{_mvsafe}) {
+#::logDebug("already made");
 		$ready_safe = $Vend::Cfg->{ActionMap}{_mvsafe};
 	}
 	else {
-#::logGlobal("new one made");
-		$ready_safe = new Safe 'MVSAFE';
+		my $pkg = 'MVSAFE' . int(rand(100000));
+		undef $MVSAFE::Safe;
+		$ready_safe = new Safe $pkg;
+		$ready_safe->share_from('MVSAFE', ['$safe']);
+#::logDebug("new safe made=$ready_safe->{Root}");
+		$ready_safe->trap(@{$Global::SafeTrap});
 		$ready_safe->untrap(@{$Global::SafeUntrap});
 		no strict 'refs';
 		$Document   = new Vend::Document;
 		*Log = \&Vend::Util::logError;
+		*Debug = \&Vend::Util::logDebug;
 		*uneval = \&Vend::Util::uneval_it;
 		*HTML = \&Vend::Document::HTML;
 		$ready_safe->share(@Share_vars, @Share_routines);
 		$DbSearch   = new Vend::DbSearch;
 		$TextSearch = new Vend::TextSearch;
 		$Tag        = new Vend::Tags;
-		$Tmp        = {};
 	}
-	$Calc_reset = 1;
-	undef $Calc_initialized;
+	$Tmp        = {};
+	undef $s;
+	undef $q;
+	undef $item;
+	%Db = ();
+	%Sql = ();
+	undef $Shipping;
+	$Vend::Calc_reset = 1;
+	undef $Vend::Calc_initialized;
 	return $ready_safe;
 }
 
 sub init_calc {
-#::logGlobal("initting calc");
-	reset_calc() unless $Calc_reset;
+#::logDebug("reset_state=$Vend::Calc_reset init_state=$Vend::Calc_initialized -- initting calc from " . caller);
+	reset_calc() unless $Vend::Calc_reset;
 	$CGI_array                   = \%CGI::values_array;
 	$CGI        = $Safe{cgi}     = \%CGI::values;
 	$Carts      = $Safe{carts}   = $::Carts;
@@ -170,15 +219,13 @@
 	$Scratch    = $Safe{scratch} = $::Scratch;
 	$Values     = $Safe{values}  = $::Values;
 	$Session                     = $Vend::Session;
-	$Search                      = $Vend::SearchObject ||= {};
+	$Search                      = $::Instance->{SearchObject} ||= {};
 	$Variable   = $::Variable;
-	$Calc_initialized = 1;
+	$Vend::Calc_initialized = 1;
+	
 	return;
 }
 
-sub uninit_calc {
-}
-
 # Regular expression pre-compilation
 my %T;
 my %QR;
@@ -192,10 +239,10 @@
 my $Spacef = '(?:%20|\s)+';
 my $Spaceo = '(?:%20|\s)*';
 
-my $Optx = '(?:\s+)?([-\w:#=/.%]+)?';
+my $Optx = '\s*([-\w:#=/.%]+)?';
 my $Optr = '(?:\s+([^]]+))?';
 my $Mand = '\s+([-\w#/.]+)';
-my $Opt = '(?:\s+)?([-\w#/.]+)?';
+my $Opt = '\s*([-\w#/.]+)?';
 my $T    = '\]';
 my $D    = '[-_]';
 
@@ -207,13 +254,13 @@
 my $XMandf = qr{(?:%20|\s)+([-\w#/.]+)};
 my $XSpacef = qr{(?:%20|\s)+};
 my $XSpaceo = qr{(?:%20|\s)*};
-my $XOptx = qr{(?:\s+)?([-\w:#=/.%]+)?};
+my $XOptx = qr{\s*([-\w:#=/.%]+)?};
 my $XMand = qr{\s+([-\w#/.]+)};
-my $XOpt = qr{(?:\s+)?([-\w#/.]+)?};
+my $XOpt = qr{\s*([-\w#/.]+)?};
 my $XD    = qr{[-_]};
-
-my %Comment_out = ( '<' => '&lt;', '[' => '&#91;', '_' => '&#95;', );
-
+my $Gvar  = qr{\@\@([A-Za-z0-9]\w+[A-Za-z0-9])\@\@};
+my $Evar  = qr{\@_([A-Za-z0-9]\w+[A-Za-z0-9])_\@};
+my $Cvar  = qr{__([A-Za-z0-9]\w*?[A-Za-z0-9])__};
 
 
 my @th = (qw!
@@ -244,6 +291,7 @@
 		_calc
 		_change
 		_code
+		_common
 		_data
 		_description
 		_discount
@@ -256,10 +304,13 @@
 		_match
 		_modifier
 		_next
+		_options
 		_param
+		_parent
 		_pos
 		_price
 		_quantity
+		_sku
 		_subtotal
 		_sub
 		col
@@ -308,7 +359,6 @@
 	'/_last'		=> qr($T{_last}\]),
 	'/_modifier'	=> qr($T{_modifier}\]),
 	'/_next'		=> qr($T{_next}\]),
-	'/_param'		=> qr($T{_param}\]),
 	'/_pos'			=> qr($T{_pos}\]),
 	'/_sub'			=> qr($T{_sub}\]),
 	'/order'		=> qr(\[/order\])i,
@@ -325,41 +375,48 @@
 						$T{'/condition'}
 						($Some))xi,
 	'_code'			=> qr($T{_code}\]),
+	'_sku'			=> qr($T{_sku}\]),
 	'col'			=> qr(\[col(?:umn)?\s+
 				 		([^\]]+)
 				 		\]
 				 		($Some)
 				 		\[/col(?:umn)?\] )ix,
 
-	'comment'		=> qr($T{comment}\]
+	'comment'		=> qr($T{comment}(?:\s+$Some)?\]
 						(?!$All$T{comment}\])
 						$Some
 						$T{'/comment'})x,
 
 	'_description'	=> qr($T{_description}\]),
-	'_discount'		=> qr($T{_discount}(?:\s+(?:quantity=)?"?(\d+)"?)?$Optx\]),
 	'_difference'	=> qr($T{_difference}(?:\s+(?:quantity=)?"?(\d+)"?)?$Optx\]),
-	'_field'		=> qr($T{_field}$Mandf\]),
-	'_field_if'		=> qr($T{_field}$Spacef(!?)\s*($Codere)$Optr\]($Some)),
+	'_discount'		=> qr($T{_discount}(?:\s+(?:quantity=)?"?(\d+)"?)?$Optx\]),
+	'_field_if'		=> qr($T{_field}(\d*)$Spacef(!?)\s*($Codere)$Optr\]($Some)),
 	'_field_if_wo'	=> qr($T{_field}$Spacef(!?)\s*($Codere$Optr)\]),
+	'_field'		=> qr($T{_field}$Mandf\]),
+	'_common'		=> qr($T{_common}$Mandf\]),
 	'_increment'	=> qr($T{_increment}\]),
 	'_last'			=> qr($T{_last}\]\s*($Some)\s*),
 	'_line'			=> qr($T{_line}$Opt\]),
+	'_modifier_if'	=> qr($T{_modifier}(\d*)$Spacef(!?)$Spaceo($Codere)$Optr\]($Some)),
 	'_modifier'		=> qr($T{_modifier}$Spacef(\w+)\]),
-	'_modifier_if'	=> qr($T{_modifier}$Spacef(!?)$Spaceo($Codere)$Optr\]($Some)),
 	'_next'			=> qr($T{_next}\]\s*($Some)\s*),
+	'_options'		=> qr($T{_options}($Spacef[^\]]+)?\]),
+	'_param_if'		=> qr($T{_param}(\d*)$Spacef(!?)\s*($Codere)$Optr\]($Some)),
 	'_param'		=> qr($T{_param}$Mandf\]),
-	'_param_if'		=> qr($T{_param}$Spacef(!?)\s*($Codere)$Optr\]($Some)),
+	'_parent_if'	=> qr($T{_parent}(\d*)$Spacef(!?)\s*($Codere)$Optr\]($Some)),
+	'_parent'		=> qr($T{_parent}$Mandf\]),
+	'_pos_if'		=> qr($T{_pos}(\d*)$Spacef(!?)\s*(\d+)$Optr\]($Some)),
 	'_pos' 			=> qr($T{_pos}$Spacef(\d+)\]),
-	'_pos_if'		=> qr($T{_pos}$Spacef(!?)\s*(\d+)$Optr\]($Some)),
 	'_price'		=> qr!$T{_price}(?:\s+(\d+))?$Optx\]!,
 	'_quantity'		=> qr($T{_quantity}\]),
 	'_subtotal'		=> qr($T{_subtotal}$Optx\]),
+	'_tag'			=> qr([-_] tag [-_] ([-\w]+) \s+)x,
 	'condition'		=> qr($T{condition}$T($Some)$T{'/condition'}),
 	'condition_begin' => qr(^\s*$T{condition}\]($Some)$T{'/condition'}),
 	'_discount_price' => qr($T{_discount_price}(?:\s+(\d+))?$Optx\]),
 	'discount_price' => qr($T{discount_price}(?:\s+(\d+))?$Optx\]),
 	'_discount_subtotal' => qr($T{_discount_subtotal}$Optx\]),
+	'has_else'		=> qr($T{'/else'}\s*$),
 	'else_end'		=> qr($T{else}\]($All)$T{'/else'}\s*$),
 	'elsif_end'		=> qr($T{elsif}\s+($All)$T{'/elsif'}\s*$),
 	'matches'		=> qr($T{matches}\]),
@@ -383,176 +440,204 @@
 undef @th;
 undef %T;
 
-sub comment_out {
-	my ($bit) = @_;
-	$bit =~ s/([[<_])/$Comment_out{$1}/ge;
-	return '<!--' . $bit . '-->';
+sub get_joiner {
+	my ($joiner, $default) = @_;
+	return $default      unless defined $joiner and length $joiner;
+	if($joiner eq '\n') {
+		$joiner = "\n";
+	}
+	elsif($joiner =~ m{\\}) {
+		$joiner = $safe_safe->reval("qq{$joiner}");
+	}
+	return length($joiner) ? $joiner : $default;
 }
 
 sub substitute_image {
 	my ($text) = @_;
 
-	my $dir = $CGI::secure											?
-		($Vend::Cfg->{ImageDirSecure} || $Vend::Cfg->{ImageDir})	:
-		$Vend::Cfg->{ImageDir};
-
-    if ($dir) {
-        $$text =~ s#(<i\w+\s+[^>]*?src=")(?!https?:)([^/][^"]+)#
-                         $1 . $dir . $2#ige;
-        $$text =~ s#(<body\s+[^>]*?background=")(?!https?:)([^/][^"]+)#
-                         $1 . $dir . $2#ige;
-        $$text =~ s#(<t(?:[dhr]|able)\s+[^>]*?background=")(?!https?:)([^/][^"]+)#
-                         $1 . $dir . $2#ige
-            if $Vend::Cfg->{Pragma}{substitute_table_image};
-    }
+	## Allow no substitution of downloads
+	return if $::Pragma->{download};
+
+	## If post_page routine processor returns true, return. Otherwise,
+	## continue image rewrite
+	if($::Pragma->{post_page}) {
+		Vend::Dispatch::run_macro($::Pragma->{post_page}, $text)
+			and return;
+	}
+
+	unless ( $::Pragma->{no_image_rewrite} ) {
+		my $dir = $CGI::secure											?
+			($Vend::Cfg->{ImageDirSecure} || $Vend::Cfg->{ImageDir})	:
+			$Vend::Cfg->{ImageDir};
+
+		if ($dir) {
+			$$text =~ s#(<i\w+\s+[^>]*?src=")(?!\w+:)([^/'][^"]+)#
+						$1 . $dir . $2#ige;
+	        $$text =~ s#(<body\s+[^>]*?background=")(?!\w+:)([^/'][^"]+)#
+						$1 . $dir . $2#ige;
+	        $$text =~ s#(<t(?:[dhr]|able)\s+[^>]*?background=")(?!\w+:)([^/'][^"]+)#
+						$1 . $dir . $2#ige;
+		}
+	}
+
+	if ( $::Pragma->{path_adjust} ) {
+		my $dir = $Vend::Cfg->{StaticPath};
+#::logDebug("have a dir for path_adjust, $dir");
+		if ($dir) {
+			$$text =~ s{(<a(?:rea)?\s+[^>]*?href=)"(/[^"]+)"} {$1'$dir$2'}ig;
+			$$text =~ s{(<link\s+[^>]*?href=)"(/[^"]+)"}      {$1'$dir$2'}ig;
+			$$text =~ s{(<i\w+\s+[^>]*?src=)"(/[^"]*)"}       {$1'$dir$2'}ig;
+	        $$text =~ s{(<body\s+[^>]*?background=)"(/[^"]+)"}{$1'$dir$2'}ig;
+	        $$text =~ s{(<t(?:[dhr]|able)\s+[^>]*?background=)"(/[^"]+)"}
+					   {$1'$dir$2'}ig;
+		}
+	}
+
     if($Vend::Cfg->{ImageAlias}) {
 		for (keys %{$Vend::Cfg->{ImageAlias}} ) {
         	$$text =~ s#(<i\w+\s+[^>]*?src=")($_)#
                          $1 . ($Vend::Cfg->{ImageAlias}->{$2} || $2)#ige;
+        	$$text =~ s#(<body\s+[^>]*?background=")($_)#
+                         $1 . ($Vend::Cfg->{ImageAlias}->{$2} || $2)#ige;
+        	$$text =~ s#(<t(?:[dhr]|able)\s+[^>]*?background=")($_)#
+                         $1 . ($Vend::Cfg->{ImageAlias}->{$2} || $2)#ige;
 		}
     }
 }
 
-#
-# This is one entry point for page display.
-# Evaluates all of the Interchange tags. Does some basic cache management
-# for static page building.
-#
-
-sub cache_html {
-	my ($html,$wantref) = @_;
-	my ($name, @post);
-	my ($bit, %post);
-
-	# Comment facility
-
-	reset_calc() unless $Calc_reset;
+sub dynamic_var {
+	my $varname = shift;
 
-	$CacheInvalid = 0;
-
-	vars_and_comments(\$html);
-
-	1 while $html =~ s/\[pragma\s+(\w+)(?:\s+(\w+))?\]/$Vend::Cfg->{Pragma}{$1} = $2, ''/ige;
-
-	my $complete;
-	my $full = '';
-	my $parse = new Vend::Parse;
-	$parse->parse($html);
-	while($parse->{_buf}) {
-		substitute_image(\$parse->{OUT});
-		::response( \$parse->{OUT});
-		$full .= $parse->{OUT};
-		$parse->{OUT} = '';
-		$parse->parse('');
-	}
-	substitute_image(\$parse->{OUT})
-		unless $parse->{ABORT};
-	$full .= $parse->{OUT} if $full;
-	$CacheInvalid++ if $parse->{INVALID};
-	$Vend::CachePage = $CacheInvalid ? undef : 1;
-	$complete = \$full if $full;
-	if (defined $Vend::BuildingPages) {
-		return $full if $full;
-		return $parse->{OUT};
-	}
-	return (\$parse->{OUT}, $complete || undef) if defined $wantref;
-	return ($parse->{OUT});
-}
-
-## 
-## 
-##
-sub var_ui_sub {
-	my ($key, $type) = @_;
-	
-	if(! $type) {
+	return readfile($Vend::Cfg->{DirConfig}{Variable}{$varname})
+		if $Vend::Cfg->{DirConfig}
+			and defined $Vend::Cfg->{DirConfig}{Variable}{$varname};
+
+	VARDB: {
+		last VARDB if $::Pragma->{dynamic_variables_file_only};
+		last VARDB unless $Vend::Cfg->{VariableDatabase};
+		if($Vend::VarDatabase) {
+			last VARDB unless $Vend::VarDatabase->record_exists($varname);
+			return $Vend::VarDatabase->field($varname, 'Variable');
+		}
+		else {
+			$Vend::VarDatabase = database_exists_ref($Vend::Cfg->{VariableDatabase})
+				or undef $Vend::Cfg->{VariableDatabase};
+			redo VARDB;
+		}
 	}
+	return $::Variable->{$varname};
 }
 
-#
-# Substitutes in Variable values.
-# Makes [comment] [/comment] strips.
-# Translates legacy [/page] and [/order].
-#
-
 sub vars_and_comments {
 	my $html = shift;
-	# Substitute defines from configuration file
+	## We never want to interpolate vars if in restricted mode
+	return if $Vend::restricted;
 	local($^W) = 0;
+
+	# Remove Minivend 3 legacy [new] tags
 	$$html =~ s/\[new\]//g;
 
-	if($UI::Editing) {
-		$$html =~ s#
-				^\s*
-					@_
-						([A-Za-z0-9]\w*?[A-Za-z0-9])
-					_@
-				\s*$
-					
-				#	$UI::Editing->($1, $Global::Variable) #gemx; 
-		$$html =~ s#
-				^\s*
-					__
-						([A-Za-z0-9]\w*?[A-Za-z0-9])
-					__
-				\s*$
-				#	$UI::Editing->($1) #gemx; 
+	# Set whole-page pragmas from [pragma] tags
+	1 while $$html =~ s/\[pragma\s+(\w+)(?:\s+(\w+))?\]/
+		$::Pragma->{$1} = (length($2) ? $2 : 1), ''/ige;
+
+	undef $Vend::PageInit unless $::Pragma->{init_page};
+
+	if(defined $Vend::PageInit and ! $Vend::PageInit++) {
+		Vend::Dispatch::run_macro($::Pragma->{init_page}, $html);
+	}
+
+	# Substitute in Variable values
+	$$html =~ s/$Gvar/$Global::Variable->{$1}/g;
+	if($::Pragma->{dynamic_variables}) {
+		$$html =~ s/$Evar/dynamic_var($1) || $Global::Variable->{$1}/ge
+			and
+		$$html =~ s/$Evar/dynamic_var($1) || $Global::Variable->{$1}/ge;
+		$$html =~ s/$Cvar/dynamic_var($1)/ge;
+	}
+	else {
+		$$html =~ s/$Evar/$::Variable->{$1} || $Global::Variable->{$1}/ge
+			and
+		$$html =~ s/$Evar/$::Variable->{$1} || $Global::Variable->{$1}/ge;
+		$$html =~ s/$Cvar/$::Variable->{$1}/g;
+	}
 
+	if($::Pragma->{pre_page}) {
+		Vend::Dispatch::run_macro($::Pragma->{pre_page}, $html);
 	}
 
-	$$html =~ s#\@\@([A-Za-z0-9]\w+[A-Za-z0-9])\@\@#$Global::Variable->{$1}#g;
-	$$html =~ s#\@_([A-Za-z0-9]\w+[A-Za-z0-9])_\@#$::Variable->{$1} || $Global::Variable->{$1}#ge
-		and
-	$$html =~ s#\@_([A-Za-z0-9]\w+[A-Za-z0-9])_\@#$::Variable->{$1} || $Global::Variable->{$1}#ge;
-	$$html =~ s#__([A-Za-z0-9]\w*?[A-Za-z0-9])__#$::Variable->{$1}#g;
-	# Comment facility
+	# Strip out [comment] [/comment] blocks
 	1 while $$html =~ s%$QR{comment}%%go;
 
+	# Translate legacy atomic [/page] and [/order] tags
 	$$html =~ s,\[/page(?:target)?\],</A>,ig;
 	$$html =~ s,\[/order\],</A>,ig;
+
+	# Translate Interchange tags embedded in HTML comments like <!--[tag ...]-->
+	$$html =~ s/<!--+\[/[/g
+		and $$html =~ s/\]--+>/]/g;
 }
 
 sub interpolate_html {
-	my ($html, $wantref) = @_;
+	my ($html, $wantref, $opt) = @_;
+	return undef if $Vend::NoInterpolate;
 	my ($name, @post);
 	my ($bit, %post);
 
-	reset_calc() unless $Calc_reset;
-
-	defined $::Variable->{MV_AUTOLOAD}
-		and $html =~ s/^/$::Variable->{MV_AUTOLOAD}/;
-
-	1 while $html =~ s/\[pragma\s+(\w+)(?:\s+(\w+))?\]/$Vend::Cfg->{Pragma}{$1} = $2, ''/ige;
-
-#::logDebug("Vend::Cfg->{Pragma} -> " . ::uneval(\%Vend::Cfg->{Pragma}));
-
-	vars_and_comments(\$html);
+	my $toplevel;
+	if(defined $Vend::PageInit and ! $Vend::PageInit) {
+		defined $::Variable->{MV_AUTOLOAD}
+			and $html =~ s/^/$::Variable->{MV_AUTOLOAD}/;
+		$toplevel = 1;
+	}
+#::logDebug("opt=" . uneval($opt));
 
-	$html =~ s/<!--+\[/[/g
-		and $html =~ s/\]--+>/]/g;
+	vars_and_comments(\$html)
+		unless $opt and $opt->{onfly};
 
     # Returns, could be recursive
-	my $parse = new Vend::Parse;
+	my $parse = new Vend::Parse $wantref;
 	$parse->parse($html);
 	while($parse->{_buf}) {
+		if($toplevel and $parse->{SEND}) {
+			delete $parse->{SEND};
+			::response();
+			$parse->destination($parse->{_current_output});
+		}
 		$parse->parse('');
 	}
-	substitute_image(\$parse->{OUT});
-	return \$parse->{OUT} if defined $wantref;
-	return $parse->{OUT};
-
+	return $parse->{OUT} if defined $wantref;
+	return ${$parse->{OUT}};
 }
 
+*cache_html = \&interpolate_html;
+
+my $Filters_initted;
+
 sub filter_value {
-	my($filter, $value, $tag) = @_;
+	my($filter, $value, $tag, @passed_args) = @_;
+#::logDebug("filter_value: filter='$filter' value='$value' tag='$tag'");
 	my @filters = Text::ParseWords::shellwords($filter); 
 	my @args;
+
+	if(! $Filters_initted++ and my $ref = $Vend::Cfg->{CodeDef}{Filter}) {
+		while (my($k, $v) = each %{$ref->{Routine}}) {
+			$Filter{$k} = $v;
+		}
+	}
+
 	for (@filters) {
-		@args = ();
-		if(/%/) {
+		next unless length($_);
+		@args = @passed_args;
+		if(/^[^.]*%/) {
 			$value = sprintf($_, $value);
 			next;
 		}
+		if (/^(\d+)(\.?)$/) {
+			substr($value, $1) = $2 ? '...' : ''
+				if length($value) > $1;
+			next;
+		}
 		while( s/\.([^.]+)$//) {
 			unshift @args, $1;
 		}
@@ -562,99 +647,59 @@
 			next;
 		}
 		unless (defined $Filter{$_}) {
-            ::logError ("Unknown filter $_");
-            next;
-        }
+			logError ("Unknown filter '%s'", $_);
+			next;
+		}
 		unshift @args, $value, $tag;
 		$value = $Filter{$_}->(@args);
 	}
+#::logDebug("filter_value returns: value='$value'");
 	return $value;
 }
 
-sub tag_record {
-	my ($opt) = @_;
-	my $db = $Vend::Database{$opt->{table}};
-	return undef if ! $db;
-	$db = $db->ref();
-	# This can be called from Perl
-	my (@cols, @vals);
-	my $hash   = $opt->{col};
-	my $filter = $opt->{filter};
-
-	return undef unless defined $opt->{key};
-	my $key = $opt->{key};
-	return undef unless ref $hash;
-	undef $filter unless ref $filter;
-	@cols = keys %$hash;
-	@vals = values %$hash;
-
-	RESOLVE: {
-		my $i = -1;
-		for(@cols) {
-			$i++;
-			if(! defined $db->test_column($_) ) {
-				splice (@cols, $i, 1);
-				my $tmp = splice (@vals, $i, 1);
-				::logError("bad field $_ in record update, value=$_");
-				redo RESOLVE;
-			}
-			next unless defined $filter->{$_};
-			$vals[$i] = filter_value($filter->{$_}, $vals[$i], $_);
-		}
-	}
-
-	if($opt->{new}) {
-		$db->set_row($key, '');
-	}
-	elsif($opt->{create}) {
-		$db->set_row($key, '') unless $db->record_exists($key);
-	}
-	my $settor = $db->row_settor('code', @cols);
-	return undef unless $settor;
-	my $status = defined $settor->($key, @vals);
-	return $status;
-}
-
 sub try {
 	my ($label, $opt, $body) = @_;
 	$label = 'default' unless $label;
-	delete $Vend::Session->{try}{$label};
+	$Vend::Session->{try}{$label} = '';
 	my $out;
 	my $save;
 	$save = delete $SIG{__DIE__} if defined $SIG{__DIE__};
+	$Vend::Try = $label;
 	eval {
 		$out = interpolate_html($body);
 	};
+	undef $Vend::Try;
 	$SIG{__DIE__} = $save if defined $save;
-	$Vend::Session->{try}{$label} = $@ if $@;
+	if($@) {
+		$Vend::Session->{try}{$label} .= "\n" 
+			if $Vend::Session->{try}{$label};
+		$Vend::Session->{try}{$label} .= $@;
+	}
 	if ($opt->{status}) {
-		return $@ ? 0 : 1;
+		return ($Vend::Session->{try}{$label}) ? 0 : 1;
 	}
 	elsif ($opt->{hide}) {
 		return '';
 	}
-	return $out;
-}
+	elsif ($opt->{clean}) {
+		return ($Vend::Session->{try}{$label}) ? '' : $out;
+	}
 
-sub catch {
-	my ($label, $opt, $body) = @_;
-	$label = 'default' unless $label;
-	my $patt;
-	return pull_else($body) 
-		unless $patt = $Vend::Session->{try}{$label};
-	$body =~ m{\[([^\]]*$patt[^\]]*)\](.*)\[/\1\]}s
-		and return $2;
-	$body =~ s{\[([^\]]*)\].*\[/\1\]}{}s;
-	return $body;
+	return $out;
 }
 
 # Returns the text of a configurable database field or a 
-# variable
+# session variable
 sub tag_data {
 	my($selector,$field,$key,$opt,$flag) = @_;
 	$CacheInvalid = 1 if defined $Vend::Cfg->{DynamicData}->{$selector};
 
-	if ( not defined $Vend::Database{$selector}) {
+	local($Safe_data);
+	$Safe_data = 1 if $opt->{safe_data};
+	
+	my $db;
+
+	if ( not $db = database_exists_ref($selector) ) {
 		if($selector eq 'session') {
 			$CacheInvalid = 1;
 			if(defined $opt->{value}) {
@@ -688,39 +733,100 @@
 		}
 	}
 	elsif($opt->{increment}) {
-		$CacheInvalid = 1;
 #::logDebug("increment_field: key=$key field=$field value=$opt->{value}");
 		return increment_field($Vend::Database{$selector},$key,$field,$opt->{value} || 1);
 	}
 	elsif (defined $opt->{value}) {
-#::logDebug("set_field: table=$selector key=$key field=$field value=$opt->{value}");
+#::logDebug("alter table: table=$selector alter=$opt->{alter} field=$field value=$opt->{value}");
 		$CacheInvalid = 1;
-		if($opt->{filter}) {
-			$opt->{value} = filter_value($opt->{filter}, $opt->{value}, $field);
+		if ($opt->{alter}) {
+			$opt->{alter} =~ s/\W+//g;
+			$opt->{alter} = lc($opt->{alter});
+			if ($opt->{alter} eq 'change') {
+				return $db->change_column($field, $opt->{value});
+			}
+			elsif($opt->{alter} eq 'add') {
+				return $db->add_column($field, $opt->{value});
+			}
+			elsif ($opt->{alter} eq 'delete') {
+				return $db->delete_column($field, $opt->{value});
+			}
+			else {
+				logError("alter function '%s' not found", $opt->{alter});
+				return undef;
+			}
 		}
-		return set_field($selector,$key,$field,$opt->{value},$opt->{append});
+		else {
+			$opt->{value} = filter_value($opt->{filter}, $opt->{value}, $field)
+				if $opt->{filter};
+#::logDebug("set_field: table=$selector key=$key field=$field foreign=$opt->{foreign} value=$opt->{value}");
+			my $orig = $opt->{value};
+			if($opt->{serial}) {
+				$field =~ s/\.(.*)//;
+				my $hk = $1;
+				my $current = database_field($selector,$key,$field,$opt->{foreign});
+				$opt->{value} = dotted_hash($current, $hk, $orig);
+			}
+			my $result = set_field(
+							$selector,
+							$key,
+							$field,
+							$opt->{value},
+							$opt->{append},
+							$opt->{foreign},
+						);
+			return $orig if $opt->{serial};
+			return $result
+		}
+	}
+	elsif ($opt->{serial}) {
+		$field =~ s/\.(.*)//;
+		my $hk = $1;
+		return ed(
+					dotted_hash(
+						database_field($selector,$key,$field,$opt->{foreign}),
+						$hk,
+					)
+				);
 	}
 	elsif ($opt->{hash}) {
-		my $db = ::database_exists_ref($selector);
+		return undef unless $db->record_exists($key);
 		return $db->row_hash($key);
 	}
+	elsif ($opt->{filter}) {
+		return filter_value(
+			$opt->{filter},
+			ed(database_field($selector,$key,$field,$opt->{foreign})),
+			$field,
+		);
+	}
 
 	#The most common , don't enter a block, no accoutrements
-	return database_field($selector,$key,$field);
-
+	return ed(database_field($selector,$key,$field,$opt->{foreign}));
 }
 
 %Filter = (
 	
-	'value' =>	sub {
-					return $::Values->(shift);
-				},
-	'cgi' =>	sub {
-					return $CGI::values(shift);
-				},
+	'value' =>	sub { return $::Values->{$_[0]}; },
+	'cgi' =>	sub { return $CGI::values{$_[0]}; },
 	'filesafe' =>	sub {
 						return Vend::Util::escape_chars(shift);
 				},
+	'calculated' =>	sub {
+						my ($val, $tag, $table, $column, $key, $indirect) = @_;
+						$key = $CGI::values{$indirect}
+							if $indirect;
+						my $code = tag_data($table, $column, $key);
+						$code =~ s/\r/\n/g;
+#::logDebug("calculated code=$code");
+						$s = $val;
+						my $result = $ready_safe->reval($code);
+#::logDebug("calculated result='$result'");
+						return $result;
+				},
+	'mime_type' =>	sub {
+						return Vend::Util::mime_type(shift);
+				},
 	'currency' =>	sub {
 						my ($val, $tag, $locale) = @_;
 						my $convert = $locale ? 1 : 0;
@@ -768,6 +874,10 @@
 					return $val 
 						unless $val =~ m:(\d+)[-/]+(\d+)[-/]+(\d+):;
 					my ($yr, $mon, $day) = ($3, $1, $2);
+
+					my $time;
+					$val =~ /:(\d+)$/
+						and $time = $1;
 					if(length($yr) < 4) {
 						$yr =~ s/^0//;
 						$yr = $yr < 50 ? $yr + 2000 : $yr + 1900;
@@ -775,6 +885,19 @@
 					$mon =~ s/^0//;
 					$day =~ s/^0//;
 					$val = sprintf("%d%02d%02d", $yr, $mon, $day);
+					return $val unless $time;
+					$val .= sprintf('%04d', $time);
+					return $val;
+				},
+	'checkbox' =>		sub {
+					my $val = shift;
+					return length($val) ? $val : '';
+				},
+	'compress_space' =>		sub {
+					my $val = shift;
+					$val =~ s/\s+$//g;
+					$val =~ s/^\s+//g;
+					$val =~ s/\s+/ /g;
 					return $val;
 				},
 	'null_to_space' =>		sub {
@@ -809,6 +932,65 @@
 					}
 					return '';
 				},
+	'line2options' =>		sub {
+					my ($value, $tag, $delim) = @_;
+					return $value unless length $value;
+					$value =~ s/\s+$//;
+					$value =~ s/^\s+//;
+					my @opts = split /[\r\n]+/, $value;
+					for(@opts) {
+						s/^\s+//;
+						s/[,\s]+$//;
+						s/,/&#44;/g;
+					}
+					return join ",", @opts;
+				},
+	'options2line' =>		sub {
+					my ($value, $tag, $delim) = @_;
+					return $value unless length $value;
+					$value =~ s/\s+$//;
+					$value =~ s/^\s+//;
+					my @opts = split /\s*,\s*/, $value;
+					for(@opts) {
+						s/&#44;/,/g;
+					}
+					$value = return join "\n", @opts;
+					return $value;
+				},
+	'option_format' =>		sub {
+					my ($value, $tag, $delim) = @_;
+
+					return $value unless $value =~ /\0.*\0/s;
+
+					my $scrubcommas;
+					if(! length($delim) ) {
+						$delim = ',';
+						$scrubcommas = 1;
+					}
+					else {
+						$delim =~ /pipe/i and $delim = '|' 
+						 or
+						$delim =~ /semicolon/i and $delim = ';'  
+						 or
+						$delim =~ /colon/i and $delim = ':'  
+						 or
+						$delim =~ /null/i and $delim = "\0"
+						;
+					}
+
+					my @opts = split /\0/, $value;
+					my @out;
+
+					while(@opts) {
+						my ($v, $l, $d) = splice @opts, 0, 3;
+						$l = length($l) ? "=$l" : '';
+						$l =~ s/,/&#44;/g if $scrubcommas;
+						$d = $d ? '*' : '';
+						next unless length("$v$l");
+						push @out, "$v$l$d";
+					}
+					return join $delim, @out;
+				},
 	'nullselect' =>		sub {
 					my @some = split /\0+/, shift;
 					for(@some) {
@@ -820,10 +1002,6 @@
 						my @items = split /\r?\n/, shift;
 						return join "\t", @items;
 				},
-	'lc' =>		sub {
-					use locale;
-					return lc(shift);
-				},
 	'digits_dot' => sub {
 					my $val = shift;
 					$val =~ s/[^\d.]+//g;
@@ -836,7 +1014,14 @@
 				},
 	'crypt' => sub {
 					my $val = shift;
-					return crypt($val, ::random_string(2));
+					return crypt($val, random_string(2));
+				},
+	'html2text' => sub {
+					my $val = shift;
+					$val =~ s|\s*<BR>\s*|\n|gi;
+					$val =~ s|\s*<P>\s*|\n|gi;
+					$val =~ s|\s*</P>\s*||gi;
+					return $val;
 				},
 	'html2text' => sub {
 					my $val = shift;
@@ -862,6 +1047,12 @@
 					$val =~ s/\D+//g;
 					return $val;
 				},
+	'alphanumeric' =>	sub {
+					my $val = shift;
+					$val =~ s/\W+//g;
+					$val =~ s/_+//g;
+					return $val;
+				},
 	'word' =>	sub {
 					my $val = shift;
 					$val =~ s/\W+//g;
@@ -869,7 +1060,7 @@
 				},
 	'unix' =>	sub {
 					my $val = shift;
-					$val =~ s/\r?\n/\n/g;
+					$val =~ s/\r\n|\r/\n/g;
 					return $val;
 				},
 	'dos' =>	sub {
@@ -917,8 +1108,15 @@
 				},
 	'text2html' => sub {
 					my $val = shift;
-					$val =~ s|\r?\n\r?\n|<P>|g;
-					$val =~ s|\r?\n|<BR>|g;
+					$val =~ s!\r?\n\r?\n!<P>!g;
+					$val =~ s!\r\r!<P>!g;
+					$val =~ s!\r?\n!<BR>!g;
+					$val =~ s!\r!<BR>!g;
+					return $val;
+				},
+	'urldecode' => sub {
+					my $val = shift;
+					$val =~ s|\%([a-fA-F0-9][a-fA-F0-9])|chr(hex($1))|eg;
 					return $val;
 				},
 	'urlencode' => sub {
@@ -931,20 +1129,70 @@
 					return $_[0];
 				},
 	'strftime' => sub {
-					return scalar localtime(shift);
+					my $time = shift(@_);
+					shift(@_);
+					my $fmt = shift(@_);
+					while(my $add = shift(@_)) {
+						$fmt .= " $add";
+					}
+					if($fmt) {
+						return POSIX::strftime($fmt, localtime($time));
+					}
+					else {
+						return scalar localtime($time);
+					}
 				},
-	'entities' => sub {
-					return HTML::Entities::encode(shift);
+	'encode_entities' => sub {
+					return HTML::Entities::encode(shift, $ESCAPE_CHARS::std);
 				},
-	'option_format' => sub {
-					$_[0] =~ s/[,\s]*[\r\n]+/,\r/g;
-					return $_[0];
+	'decode_entities' => sub {
+					return HTML::Entities::decode(shift);
+				},
+	encrypt => sub {
+					my ($val, $tag, $key) = @_;
+					return Vend::Order::pgp_encrypt($val, $key);
+				},
+	'yesno' => sub {
+					my $val = shift(@_) ? 'Yes' : 'No';
+					return $val unless $Vend::Cfg->{Locale};
+					return $val unless defined $Vend::Cfg->{Locale}{$val};
+					return $Vend::Cfg->{Locale}{$val};
+				},
+
+	show_null => sub {
+					my $val = shift;
+					$val =~ s/\0/\\0/g;
+					return $val;
+				},
+
+	loc => sub {
+					my $val = shift;
+					return errmsg($val);
+				},
+
+	restrict_html => sub {
+					my $val = shift;
+					shift;
+					my %allowed;
+					$allowed{lc $_} = 1 for @_;
+					$val =~ s{<(/?(\w[-\w]*)[\s>])}
+						     { ($allowed{lc $2} ? '<' : '&lt;') . $1 }ge;
+					return $val;
+				},
+
+	zerofix => sub {
+					$_[0] =~ /^0*(.*)/; return $1;
 				},
 	);
 
+$Filter{upper} = $Filter{uc};
+$Filter{lower} = $Filter{lc};
+$Filter{entities} = $Filter{encode_entities};
+$Filter{e} = $Filter{encode_entities};
+
 sub input_filter_do {
 	my($varname, $opt, $routine) = @_;
-#::logDebug("filter var=$varname opt=" . ::uneval($opt));
+#::logDebug("filter var=$varname opt=" . uneval_it($opt));
 	return undef unless defined $CGI::values{$varname};
 #::logDebug("before filter=$CGI::values{$varname}");
 	$routine = $opt->{routine} || ''
@@ -969,7 +1217,7 @@
 	}
 	$opt->{routine} = $routine if $routine =~ /\S/;
 	$Vend::Session->{Filter} = {} if ! $Vend::Session->{Filter};
-	$Vend::Session->{Filter}{$varname} = $opt;
+	$Vend::Session->{Filter}{$varname} = $opt->{op} if $opt->{op};
 	return;
 }
 
@@ -998,6 +1246,11 @@
 
 #::logDebug ("cond: base=$base term=$term op=$operator comp=$comp\n");
 
+	my $total;
+	if($base eq 'total') {
+		$base = $term;
+		$total = 1;
+	}
 
 	if($base eq 'session') {
 		$CacheInvalid = 1;
@@ -1013,16 +1266,22 @@
 		$op .=	qq%	$operator $comp%
 				if defined $comp;
 	}
-	elsif($base eq 'variable') {
+	elsif($base =~ /^value/) {
 		$CacheInvalid = 1;
-		$op =	qq%$::Variable->{$term}%;
+		$op =	qq%$::Values->{$term}%;
 		$op = "q{$op}" unless defined $noop;
 		$op .=	qq%	$operator $comp%
 				if defined $comp;
 	}
-	elsif($base =~ /^value/) {
+	elsif($base eq 'cgi') {
 		$CacheInvalid = 1;
-		$op =	qq%$::Values->{$term}%;
+		$op =	qq%$CGI::values{$term}%;
+		$op = "q{$op}" unless defined $noop;
+		$op .=	qq%	$operator $comp%
+				if defined $comp;
+	}
+	elsif($base eq 'pragma') {
+		$op =	qq%$::Pragma->{$term}%;
 		$op = "q{$op}" unless defined $noop;
 		$op .=	qq%	$operator $comp%
 				if defined $comp;
@@ -1031,6 +1290,20 @@
 		undef $noop;
 		$status = $ready_safe->reval($comp);
 	}
+	elsif($base eq 'variable') {
+		$CacheInvalid = 1;
+		$op =	qq%$::Variable->{$term}%;
+		$op = "q{$op}" unless defined $noop;
+		$op .=	qq%	$operator $comp%
+				if defined $comp;
+	}
+	elsif($base eq 'global') {
+		$CacheInvalid = 1;
+		$op =	qq%$Global::Variable->{$term}%;
+		$op = "q{$op}" unless defined $noop;
+		$op .=	qq%	$operator $comp%
+				if defined $comp;
+	}
     elsif($base eq 'items') {
         $CacheInvalid = 1;
 		my $cart;
@@ -1045,13 +1318,6 @@
         $op .=  qq% $operator $comp%
                 if defined $comp;
     }
-	elsif($base eq 'cgi') {
-		$CacheInvalid = 1;
-		$op =	qq%$CGI::values{$term}%;
-		$op = "q{$op}" unless defined $noop;
-		$op .=	qq%	$operator $comp%
-				if defined $comp;
-	}
 	elsif($base eq 'data') {
 		my($d,$f,$k) = split /::/, $term;
 		$CacheInvalid = 1
@@ -1106,14 +1372,32 @@
 		$op = qq|-$op "$term"|;
 	}
 	elsif($base =~ /^errors?$/) {
-		my $err_ref = $Vend::Session->{errors}
-			or return '';
-		return scalar (keys %$err_ref);
+		my $err;
+		if(! $term or $total) {
+			$err	= is_hash($Vend::Session->{errors})
+					? scalar (keys %{$Vend::Session->{errors}})
+					: 0;
+		}
+		else {
+			$err	= is_hash($Vend::Session->{errors})
+					? $Vend::Session->{errors}{$term}
+					: 0;
+		}
+		$op = $err;
+		$op .=	qq%	$operator $comp%
+				if defined $comp;
+	}
+	elsif($base =~ /^warnings?$/) {
+		my $warn = 0;
+		if(my $ary = $Vend::Session->{warnings}) {
+			ref($ary) eq 'ARRAY' and $warn = scalar(@$ary);
+		}
+		$op = $warn;
 	}
 	elsif($base eq 'validcc') {
 		$CacheInvalid = 1;
 		no strict 'refs';
-		$status = ::validate_whole_cc($term, $operator, $comp);
+		$status = Vend::Order::validate_whole_cc($term, $operator, $comp);
 	}
     elsif($base eq 'config') {
 		$op = qq%$Vend::Cfg->{$term}%;
@@ -1147,6 +1431,7 @@
 	RUNSAFE: {
 		last RUNSAFE if defined $status;
 		last RUNSAFE if $status = ($noop && $op);
+		$ready_safe->trap(@{$Global::SafeTrap});
 		$ready_safe->untrap(@{$Global::SafeUntrap});
 		$status = $ready_safe->reval($op)
 			unless ($@ or $status);
@@ -1161,7 +1446,7 @@
 	for(@addl) {
 		my $chain = /^\[[Aa]/;
 		last if ($chain ^ $status);
-		$status = (new Vend::Parse)->parse($_)->{OUT};
+		$status = ${(new Vend::Parse)->parse($_)->{OUT}};
 	}
 #::logDebug("if status=$status");
 
@@ -1206,8 +1491,8 @@
 	$body =~ s#$QR{then}##o
 		and $then = $1;
 
-	$body =~ s#$QR{else_end}##o
-		and $else = $1;
+	$body =~ s#$QR{has_else}##o
+		and $else = find_matching_else(\$body);
 
 	$body =~ s#$QR{elsif_end}##o
 		and $elsif = $1;
@@ -1218,7 +1503,7 @@
 }
 
 sub tag_if {
-	my ($cond,$body) = @_;
+	my ($cond,$body,$negate) = @_;
 #::logDebug("Called tag_if: $cond\n$body\n");
 	my ($base, $term, $op, $operator, $comp);
 	my ($else, $elsif, $else_present, @addl);
@@ -1230,6 +1515,9 @@
 	}
 #::logDebug("tag_if: base=$base term=$term op=$operator comp=$comp");
 
+	#Handle unless
+	($base =~ s/^\W+// or $base = "!$base") if $negate;
+
 	$else_present = 1 if
 		$body =~ /\[[EeTtAaOo][hHLlNnRr][SsEeDd\s]/;
 
@@ -1252,368 +1540,512 @@
 		$out = $body;
 	}
 	elsif ($elsif) {
-		$else = '[else]' . $else . '[/else]' if $else;
+		$else = '[else]' . $else . '[/else]' if length $else;
 		$elsif =~ s#(.*?)$QR{'/elsif'}(.*)#$1${2}[/elsif]#s;
 		$out = '[if ' . $elsif . $else . '[/if]';
 	}
-	elsif ($else) {
+	elsif (length $else) {
 		$out = $else;
 	}
 	return $out;
 }
 
-sub show_current_accessory_label {
-	my($val, $choices) = @_;
-	my @choices;
-	@choices = split /\s*,\s*/, $choices;
-	for(@choices) {
-		my ($setting, $label) = split /=/, $_, 2;
-		return ($label || $setting) if $val eq $setting;
+# This generates a *session-based* Autoload routine based
+# on the contents of a preset Profile (see the Profile directive).
+#
+# Normally used for setting pricing profiles with CommonAdjust,
+# ProductFiles, etc.
+# 
+sub restore_profile {
+	my $save;
+	return unless $save = $Vend::Session->{Profile_save};
+	for(keys %$save) {
+		$Vend::Cfg->{$_} = $save->{$_};
 	}
-	return '';
+	return;
 }
 
-sub build_accessory_textarea {
-	my($name, $type, $default, $opt, @opts) = @_;
+sub tag_profile {
+	my($profile, $opt) = @_;
+#::logDebug("in tag_profile=$profile opt=" . uneval_it($opt));
 
-	my $select;
-	my $run = qq|<TEXTAREA NAME="$name"|;
+	$opt = {} if ! $opt;
+	my $tag = $opt->{tag} || 'default';
 
-	while($type =~ m/\b(row|col)(?:umn)s?[=\s'"]*(\d+)/gi) {
-		$run .= " \U$1\ES=$2";
-	}
-	if ($type =~ m/\bwrap[=\s'"]*(hard|soft|none)/i) {
-		$run .= qq{WRAP="$1"};
+	if(! $profile) {
+		if($opt->{restore}) {
+			restore_profile();
+			if(ref $Vend::Session->{Autoload}) {
+				 @{$Vend::Session->{Autoload}} = 
+					 grep $_ !~ /^$tag-/, @{$Vend::Session->{Autoload}};
+			}
+		}
+		return if ! ref $Vend::Session->{Autoload};
+		$opt->{joiner} = ' ' unless defined $opt->{joiner};
+		return join $opt->{joiner},
+			grep /^\w+-\w+$/, @{ $Vend::Session->{Autoload} };
 	}
-	$run .= '>';
-	$run .= $default;
-	$run .= '</TEXTAREA>';
-}
-
-sub build_accessory_file {
-    my($name) = @_;
 
-    qq{<INPUT TYPE="hidden" NAME="mv_data_file_field" VALUE="$name">
-<INPUT TYPE="hidden" NAME="mv_data_file_path" VALUE="">
-<INPUT TYPE="hidden" NAME="mv_data_file_oldfile" VALUE="">       
-<INPUT TYPE="file" NAME="$name" accept="text/*">};
-}
-
-sub build_accessory_select {
-	my($name, $type, $default, $opt, @opts) = @_;
-
-	my $select;
-	my $run = qq|<SELECT NAME="$name"|;
-	$run .= qq{ SIZE="$opt->{rows}"} if $opt->{rows};
-	$run .= " $opt->{js}" if $opt->{js};
-	my ($multi, $re_b, $re_e, $regex);
-	
-	if($type =~ /multiple/i) {
-		$run .= " $type ";
-		$multi = 1;
-		$re_b = '(?:[\0,\s]|^)';
-		$re_e = '(?:[\0,\s]|$)';
-	}
-	elsif ($type  =~ /^multi/i ) {
-		$run .= ' MULTIPLE';
-		$multi = 1;
-		$re_b = '(?:\0|^)';
-		$re_e = '(?:\0|$)';
-	}
-	else {
-		$re_b = '(?:\0|^)';
-		$re_e = '(?:\0|$)';
-	}
-
-	my $limit;
-	if($opt->{cols}) {
-		my $cols = $opt->{cols};
-		$limit = sub {
-			return $_[0] if length($_[0]) <= $cols;
-			return substr($_[0], 0, $cols - 2) . '..';
-		};
+	if($profile =~ s/(\w+)-//) {
+		$opt->{tag} = $1;
+		$opt->{run} = 1;
 	}
-	else {
-		$limit = sub { return $_[0] };
+	elsif (! $opt->{set} and ! $opt->{run}) {
+		$opt->{set} = $opt->{run} = 1;
 	}
 
-	$run .= '>';
-	
-	for(@opts) {
-		$run .= '<OPTION';
-		$select = '';
-		s/\*$// and $select = 1;
-		if ($default) {
-			$select = '';
-		}
-		my ($value,$label) = split /=/, $_, 2;
-		my $vvalue = $value;
-		$vvalue =~ s/"/&quot;/;
-		$run .= qq| VALUE="$vvalue"|;
-		if ($default) {
-			$regex	= qr/$re_b\Q$value\E$re_e/;
-			$default =~ $regex and $select = 1;
-		}
-		$run .= ' SELECTED' if $select;
-		$run .= '>';
-		if($label) {
-			$run .= $limit->($label);
-		}
-		else {
-			$run .= $limit->($value);
-		}
+	if( "$profile$tag" =~ /\W/ ) {
+		logError(
+			"profile: invalid characters (tag=%s profile=%s), must be [A-Za-z_]+",
+			$tag,
+			$profile,
+		);
+		return $opt->{failure};
 	}
-	$run .= '</SELECT>';
-}
 
-sub build_accessory_box {
-	my($name, $type, $default, $opt, @opts) = @_;
+	if($opt->{run}) {
+#::logDebug("running profile=$profile tag=$tag");
+		my $prof = $Vend::Cfg->{Profile_repository}{$profile};
+	    if (not $prof) {
+			logError( "profile %s (%s) non-existant.", $profile, $tag );
+			return $opt->{failure};
+		} 
+#::logDebug("found profile=$profile");
+		$Vend::Cfg->{Profile} = $prof;
+		restore_profile();
+#::logDebug("restored profile");
+		PROFSET: 
+		for my $one (keys %$prof) {
+#::logDebug("doing profile $one");
+			next unless defined $Vend::Cfg->{$one};
+			my $string;
+			my $val = $prof->{$one};
+			if( ! ref $Vend::Cfg->{$one} ) {
+				# Do nothing
+			}
+			elsif( ref($Vend::Cfg->{$one}) eq 'HASH') {
+				if( ref($val) ne 'HASH') {
+				$string = '{' .  $prof->{$one}	. '}'
+					unless	$prof->{$one} =~ /^{/
+					and		$prof->{$one} =~ /}\s*$/;
+			}
+			}
+			elsif( ref($Vend::Cfg->{$one}) eq 'ARRAY') {
+				if( ref($val) ne 'ARRAY') {
+				$string = '[' .  $prof->{$one}	. ']'
+					unless	$prof->{$one} =~ /^\[/
+					and		$prof->{$one} =~ /]\s*$/;
+			}
+			}
+			else {
+				logError( "profile: cannot handle object of type %s.",
+							$Vend::Cfg->{$one},
+							);
+				logError("profile: profile for $one not changed.");
+				next;
+			}
 
-	my ($inc, $select, $xlt, $template, $header, $footer, $row_hdr, $row_ftr);
+#::logDebug("profile value=$val, string=$string");
+			$val = $ready_safe->reval($string) if $string;
 
-	$header = $template = $footer = $row_hdr = $row_ftr = '';
+			if($@) {
+				logError( "profile: bad object %s: %s", $one, $string );
+				next;
+			}
+			$Vend::Session->{Profile_save}{$one} = $Vend::Cfg->{$one}
+				unless defined $Vend::Session->{Profile_save}{$one};
 
-	my $font;
-	my $variant = ($type =~ /check/i) ? 'checkbox' : 'radio';
-	if ($type  =~ /font(?:size)?[\s_]*(-?\d)/i ) {
-		$font = qq{<FONT SIZE="$1">};
+#::logDebug("set $one to value=$val, string=$string");
+			$Vend::Cfg->{$one} = $val;
+		}
+		return $opt->{success}
+			unless $opt->{set};
 	}
 
-	if($type =~ /nbsp/i) {
-		$xlt = 1;
-		$template = qq{<INPUT TYPE="$variant" NAME="$name" VALUE="__VALUE__"__SEL__>&nbsp;__LABEL__&nbsp;&nbsp;};
+#::logDebug("setting profile=$profile tag=$tag");
+	my $al;
+	if(! $Vend::Session->{Autoload}) {
+		# Do nothing....
 	}
-	elsif ($type  =~ /left[\s_]*(\d?)/i ) {
-		$inc = $1 || undef;
-		$header = '<TABLE>';
-		$footer = '</TABLE>';
-		$template = '<TR>' unless $inc;
-		$template .= <<EOF;
-<TD>$font<INPUT TYPE="$variant" NAME="$name" VALUE="__VALUE__"__SEL__></TD><TD>__LABEL__</TD>
-EOF
-		$template .= '</TR>' unless $inc;
-	}
-	elsif ($type  =~ /right[\s_]*(\d?)/i ) {
-		$inc = $1 || undef;
-		$header = '<TABLE>';
-		$footer = '</TABLE>';
-		$template = '<TR>' unless $inc;
-		$template .= <<EOF;
-<TD>${font}__LABEL__</TD><TD><INPUT TYPE="$variant" NAME="$name" VALUE="__VALUE__"__SEL__></TD>
-EOF
-		$template .= '</TR>' unless $inc;
+	elsif(ref $Vend::Session->{Autoload}) {
+		$al = $Vend::Session->{Autoload};
 	}
 	else {
-		$template = <<EOF;
-<INPUT TYPE="$variant" NAME="$name" VALUE="__VALUE__"__SEL__>&nbsp;__LABEL__
-EOF
-		$template =~ s/\s+$/<BR>/ if $type =~ /break/i;
+		$al = [ $Vend::Session->{Autoload} ];
 	}
-	
-	my $run = $header;
 
-	$default = '' unless defined $default;
+	if($al) {
+		@$al = grep $_ !~ m{^$tag-\w+$}, @$al;
+	}
+	$al = [] if ! $al;
+	push @$al, "$tag-$profile";
+#::logDebug("profile=$profile Autoload=" . uneval_it($al));
+	$Vend::Session->{Autoload} = $al;
 
-	my $i = 0;
-	for(@opts) {
-		$run .= '<TR>' if $inc && ! ($i % $inc);
-		$i++;
-		$run .= $template;
-		$select = '';
-		s/\*$// and $select = "CHECKED";
+	return $opt->{success};
+}
 
-		$select = '' if $default;
+sub tag_options {
+	my ($sku, $opt) = @_;
+	my $item;
+	if(ref $sku) {
+		$item = $sku;
+		$sku = $item->{mv_sku} || $item->{code};
+	}
+#::logDebug("entering tag_options for $sku");
 
-		my ($value,$label) = split /=/, $_, 2;
-		$label = $value unless $label;
+	$opt = get_option_hash($opt);
 
-		$value =~ s/"/&quot;/g;
+	my $table = $opt->{table} || $::Variable->{MV_OPTION_TABLE} || 'options';
 
-		$value eq '' and $default eq '' and $select = "CHECKED";
+	if($opt->{report}) {
+		$opt->{joiner} = ', '    if ! $opt->{joiner};
+		$opt->{separator} = ': ' if ! $opt->{separator};
+		$opt->{type} = 'display' if ! $opt->{type};
+	}
+	else {
+		$opt->{joiner} = '<BR>' if ! $opt->{joiner};
+	}
 
-		if(length $value) {
-			my $regex	= $opt->{contains}
-						? qr/\Q$value\E/ 
-						: qr/\b\Q$value\E\b/;
-			$default =~ $regex and $select = "CHECKED";
+	my $db = $Db{$table} || database_exists_ref($table);
+	$db->record_exists($sku)
+		or return;
+	my $record = $db->row_hash($sku)
+		or return;
+#::logDebug("found record for $sku in tag_options");
+
+	my $remap;
+	my %map;
+
+	my $inv_func;
+	if($opt->{inventory}) {
+		my ($t, $c) = split /[.:]+/, $opt->{inventory};
+		my $idb;
+		if($idb = database_exists_ref($t)) {
+			$inv_func = $idb->field_accessor($c);
 		}
-
-		$label =~ s/ /&nbsp;/g if $xlt;
-
-		$run =~ s/__SEL__/ $select/;
-		$run =~ s/__VALUE__/$value/;
-		$run =~ s/__LABEL__/$label/;
-		$run .= '</TR>' if $inc && ! ($i % $inc);
-		
 	}
-	$run .= $footer;
-}
-
-sub tag_price {
-	my($code,$ref) = @_;
-	my $amount = Vend::Data::item_price($ref,$ref->{quantity} || 1);
-	$amount = discount_price($ref,$amount, $ref->{quantity})
-			if $ref->{discount};
-	return currency( $amount, $ref->{noformat} );
-}
-
-sub tag_accessories {
-	my($code,$extra,$opt,$item) = @_;
 
-	# Had extra if got here
-#::logDebug("tag_accessories: code=$code opt=" . ::uneval_it($opt) . " item=" . ::uneval_it($item) . " extra=$extra");
-	my($attribute, $type, $field, $db, $name, $outboard, $passed);
-	$opt = {} if ! $opt;
-	if($extra) {
-		$extra =~ s/^\s+//;
-		$extra =~ s/\s+$//;
-		@{$opt}{qw/attribute type column table name outboard passed/} =
-			split /\s*,\s*/, $extra;
+	if($::Variable->{MV_OPTION_TABLE_MAP}) {
+		$remap = $::Variable->{MV_OPTION_TABLE_MAP};
+		$remap =~ s/^\s+//;
+		$remap =~ s/\s+$//;
+		%map = split /[,\s]+/, $remap;
+		my %rec;
+		my @del;
+		my ($k, $v);
+		while (($k, $v) = each %map) {
+			next unless defined $record->{$v};
+			$rec{$k} = $record->{$v};
+			push @del, $v;
+		}
+		delete @{$record}{@del};
+		@{$record}{keys %rec} = (values %rec);
+	}
+
+	my $rsort = '';
+	$map{o_sort} ||= 'o_sort';
+	if($opt->{sort}) {
+		$map{o_sort} = $opt->{sort_field} if $opt->{sort_field};
+
+		if(! defined $db->test_column($map{o_sort}) ) {
+			logError(
+				"item-options sort column '%s' non-existent, unsorted",
+				$map{o_sort},
+			);
+		}
+		else {
+			$rsort = " ORDER BY $map{o_sort}";
+			my $sopt = $opt->{sort_option} || '';
+			$rsort .= " DESC" if $sopt =~ /^(r(?:ev(?:erse)?)?|desc(?:ending)?)/i;
+		}
 	}
-	($attribute, $type, $field, $db, $name, $outboard, $passed) = 
-		@{$opt}{qw/attribute type column table name outboard passed/};
 
-	my $p = $opt->{prepend} || '';
-	my $a = $opt->{append} || '';
+	return if ! $record->{o_enable};
+#::logDebug("record for $sku says options enabled");
 
-	$type = 'select' unless $type;
-	$field = $attribute unless $field;
-	$code = $outboard if $outboard;
-#::logDebug("accessory type=$type db=$db field=$field code=$code attr=$attribute name=$name passed=$passed attr_value=$item->{$attribute}");
+	my $out = '';
+	my @out;
 
-	return $item->{$attribute} if $type eq 'value';
+	my @rf;
 
-	my $data;
-	if($passed) {
-		$data = $passed;
+	if($opt->{display_type}) {
+		$opt->{display_type} = lc $opt->{display_type};
 	}
-	else {
-		$data = $db ? tag_data($db, $field, $code) : product_field($field,$code);
+	elsif (! $record->{o_matrix}) {
+		# Do nothing
 	}
-
-	unless ($data || $type =~ /^text|^hidden|^file/i) {
-		return '' if $item;
-		return '' if $name;
-		return qq|<INPUT TYPE="hidden" NAME="mv_order_$attribute" VALUE="">|;
+	elsif ($record->{o_matrix} == 2) {
+		$opt->{display_type} = 'separate';
+	}
+	elsif ($record->{o_matrix}) {
+		$opt->{display_type} = 'single';
 	}
 
-	return show_current_accessory_label($item->{$attribute},$data)
-			if "\L$type" eq 'display' and $item;
-
-	return $data if "\L$type" eq 'show';
+	if($record->{o_matrix} and $opt->{display_type} eq 'separate') {
+		for(qw/code o_enable o_group o_value o_label o_widget price/) {
+			push @rf, ($map{$_} || $_);
+		}
+		my @def;
+		if($item and $item->{code}) {
+			@def = split /-/, $item->{code};
+		}
+		my $fsel = $map{sku} || 'sku';
+		my $rsel = $db->quote($sku, $fsel);
+		$rsort ||= " ORDER BY $map{o_sort}";
+		
+		my $q = "SELECT " .
+				join (",", @rf) .
+				" FROM $table where $fsel = $rsel $rsort";
+#::logDebug("tag_options separate query: $q");
+		my $ary = $db->query($q); 
+		my $ref;
+		my $i = 0;
+		my $phony = { %{$item || { }} };
+		foreach $ref (@$ary) {
 
-	my $attrib_value = $item ? $item->{$attribute} : '';
+			next unless $ref->[3];
 
-	$name = $item ? "[modifier-name $attribute]" : "mv_order_$attribute"
-		unless $name;
+			# skip based on inventory if enabled
+			if($inv_func) {
+				my $oh = $inv_func->($ref->[0]);
+				next if $oh <= 0;
+			}
 
-	return qq|$p<INPUT TYPE="hidden" NAME="$name" VALUE="$attrib_value">$a|
-		if "\L$type" eq 'hidden';
-	return qq|$p<INPUT TYPE="hidden" NAME="$name" VALUE="$attrib_value">$attrib_value$a|
-		if $type =~ /hidden/;
-	if($type =~ /^text/i) {
-		HTML::Entities::encode($attrib_value);
-		return qq|$p<TEXTAREA NAME="$name" ROWS=$1 COLS=$2>$attrib_value</TEXTAREA>$a|
-			if "\L$type" =~ /^textarea_(\d+)_(\d+)$/;
-		return qq|$p<INPUT TYPE=text NAME="$name" SIZE=$1 VALUE="$attrib_value">$a|
-			if "\L$type" =~ /^text_(\d+)$/;
-		return qq|$p<INPUT TYPE=text NAME="$name" SIZE=60 VALUE="$attrib_value">$a|
-			if "\L$type" =~ /^text/;
-	}
+			$i++;
 
-	my ($default, $label, $select, $value, $run);
-	my @opts = split /\s*,\s*/, $data;
+			# skip unless o_value
+			$phony->{mv_sku} = $def[$i];
 
-	if($item) {
-		$default = $item->{$attribute};
-	}
-	elsif ($name) {
-		$default = $::Values->{$name};
+			if ($opt->{label}) {
+				$ref->[4] = "<B>$ref->[4]</b>" if $opt->{bold};
+				push @out, $ref->[4];
+			}
+			push @out, tag_accessories(
+							$sku,
+							'',
+							{ 
+								passed => $ref->[3],
+								type => $opt->{type} || $ref->[5] || 'select',
+								attribute => 'mv_sku',
+								price_data => $ref->[6],
+								price => $opt->{price},
+								extra => $opt->{extra},
+								js => $opt->{js},
+								item => $phony,
+							},
+							$phony || undef,
+						);
+		}
+		
+		$phony->{mv_sku} = $sku;
+		my $begin = tag_accessories(
+							$sku,
+							'',
+							{ 
+								type => 'hidden',
+								attribute => 'mv_sku',
+								item => $phony,
+								default => $sku,
+							},
+							$phony,
+						);
+		if($opt->{td}) {
+			for(@out) {
+				$out .= "<td>$begin$_</td>";
+				$begin = '';
+			}
+		}
+		else {
+			$opt->{joiner} = '<BR>' if ! $opt->{joiner};
+			$out .= $begin;
+			$out .= join $opt->{joiner}, @out;
+		}
 	}
+	elsif($record->{o_matrix}) {
+		for(qw/code o_enable o_group description price weight volume differential o_widget/) {
+			push @rf, ($map{$_} || $_);
+		}
+		my $lcol = $map{sku} || 'sku';
+		my $lval = $db->quote($sku, $lcol);
 
-	# returns just list of options, no labels
-	if($type eq 'options') {
-		return join "\n", (map { s/\s*=.*//; $_ } @opts);
+		$rsort ||= " ORDER BY $map{o_sort}";
+		
+		my $q = "SELECT " . join(",", @rf);
+		$q .= " FROM $table where $lcol = $lval $rsort";
+#::logDebug("tag_options matrix query: $q");
+		my $ary = $db->query($q); 
+		my $ref;
+		my $price = {};
+		foreach $ref (@$ary) {
+			# skip unless enabled
+			next unless $ref->[1];
+			# skip unless description
+			next unless $ref->[3];
+
+			# skip based on inventory if enabled
+			if($inv_func) {
+				my $oh = $inv_func->($ref->[0]);
+				next if $oh <= 0;
+			}
+
+			$ref->[3] =~ s/,/&#44;/g;
+			$ref->[3] =~ s/=/&#61;/g;
+			$price->{$ref->[0]} = $ref->[4];
+			push @out, "$ref->[0]=$ref->[3]";
+		}
+		$out .= "<td>" if $opt->{td};
+		$out .= tag_accessories(
+							$sku,
+							'',
+							{ 
+								attribute => 'code',
+								default => undef,
+								extra => $opt->{extra},
+								item => $item,
+								js => $opt->{js},
+								name => 'mv_sku',
+								passed => join(",", @out),
+								price => $opt->{price},
+								price_data => $price,
+								type => $opt->{type} || $ref->[8] || 'select',
+							},
+							$item || undef,
+						);
+		$out .= "</td>" if $opt->{td};
+#::logDebug("matrix option returning $out");
 	}
-	# returns just list of labels, no options
-	elsif ($type eq 'labels') {
-		return join "\n", (map { s/.*?=//; $_ } @opts);
+	elsif($record->{o_modular}) {
+#::logDebug("modular options");
 	}
-
-	# Ranging type, for price breaks based on quantity
-	if ($type =~ s/^range:?(.*)//) {
-		$select = $1 || 'quantity';
-		$default = ($item && defined $item->{$select}) ? $item->{$select} : undef;
-		my $min;
-		my $max;
-		for(@opts) {
-			/^ (-?[\d.]+) - (-?[\d.]*)  \s*=\s*  (.+) /x
-				or next;
-			$min = $1;
-			$max = $2;
-			$label = $3;
-			if($label =~ s/\*$// and ! $default) {
-				$default = $min;
+	else {
+#::logDebug("simple options");
+		for(qw/code o_enable o_group o_value o_label o_widget price o_height o_width/) {
+			push @rf, ($map{$_} || $_);
+		}
+		my $fsel = $map{sku} || 'sku';
+		my $rsel = $db->quote($sku, $fsel);
+		
+		my $q = "SELECT " . join (",", @rf) . " FROM $table where $fsel = $rsel";
+		$q .= $rsort;
+#::logDebug("tag_options simple query: $q");
+		my $ary = $db->query($q); 
+		my $ref;
+		foreach $ref (@$ary) {
+			# skip unless o_value
+			next unless $ref->[3];
+			if ($opt->{label}) {
+				$ref->[4] = "<B>$ref->[4]</b>" if $opt->{bold};
+				push @out, $ref->[4];
+			}
+			my $precursor = $opt->{report}
+						  ? "$ref->[2]$opt->{separator}"
+						  : qq{<input type=hidden name="mv_item_option" value="$ref->[2]">};
+			push @out, $precursor . tag_accessories(
+							$sku,
+							'',
+							{ 
+								attribute => $ref->[2],
+								default => undef,
+								extra => $opt->{extra},
+								item => $item,
+								js => $opt->{js},
+								passed => $ref->[3],
+								price => $opt->{price},
+								price_data => $ref->[6],
+								height => $opt->{height} || $ref->[7],
+								width  => $opt->{width} || $ref->[8],
+								type => $opt->{type} || $ref->[5] || 'select',
+							},
+							$item || undef,
+						);
+		}
+		if($opt->{td}) {
+			for(@out) {
+				$out .= "<td>$_</td>";
 			}
-			next unless $default >= $min;
-			next unless $default <= $max;
-			last;
 		}
-		($item->{$attribute} = $label, return '') if $item;
-		return qq|<INPUT TYPE="hidden" NAME="$name" VALUE="$label">|;
+		else {
+			$opt->{joiner} = '<BR>' if ! $opt->{joiner};
+			$out .= join $opt->{joiner}, @out;
+		}
 	}
+#::logDebug("tag_options returns:\n\n$out\n");
+	return $out;
+}
 
-	# Building select, textarea, or radio/check box if got here
+sub produce_range {
+	my ($ary, $max) = @_;
+	$max = $Vend::Cfg->{Limit}{option_list} if ! $max;
+	my @do;
+	for (my $i = 0; $i < scalar(@$ary); $i++) {
+		$ary->[$i] =~ /^\s* ([a-zA-Z0-9]+) \s* \.\.+ \s* ([a-zA-Z0-9]+) \s* $/x
+			or next;
+		my @new = $1 .. $2;
+		if(@new > $max) {
+			logError(
+				"Refuse to add %d options to option list via range, max %d.",
+				scalar(@new),
+				$max,
+				);
+			next;
+		}
+		push @do, $i, \@new;
+	}
+	my $idx;
+	my $new;
+	while($new = pop(@do)) {
+		my $idx = pop(@do);
+		splice @$ary, $idx, 1, @$new;
+	}
+	return;
+}
+
+sub tag_accessories {
+	my($code,$extra,$opt,$item) = @_;
 
-	if ($type =~ /^(radio|check)/i) {
-		return $p . build_accessory_box($name, $type, $default, $opt, @opts) . $a;
+	my $ishash;
+	if(ref $item) {
+#::logDebug("tag_accessories: item is a hash");
+		$ishash = 1;
 	}
-	elsif($type =~ /^textarea/i) {
-		return $p . build_accessory_textarea($name, $type, $default, $opt, @opts) . $a;
+
+	# Had extra if got here
+#::logDebug("tag_accessories: code=$code opt=" . uneval_it($opt) . " item=" . uneval_it($item) . " extra=$extra");
+	my($attribute, $type, $field, $db, $name, $outboard, $passed);
+	$opt = {} if ! $opt;
+	if($extra) {
+		$extra =~ s/^\s+//;
+		$extra =~ s/\s+$//;
+		@{$opt}{qw/attribute type column table name outboard passed/} =
+			split /\s*,\s*/, $extra;
 	}
-    elsif($type =~ /^file/i) {
-        return $p . build_accessory_file($name);
-    }
-	elsif($type =~ /^combo[ _]*(?:(\d+)(?:[ _]+(\d+))?)?/i) {
-		$opt->{rows} = $opt->{rows} || $1 || 1;
-		$opt->{cols} = $opt->{cols} || $2 || 16;
-		unless($opts[0] =~ /^=/) {
-			unshift @opts, ($opt->{new} || "=&lt;-- New");
-		}
-		my $out = qq|<INPUT TYPE=text NAME="$name" SIZE=$opt->{cols} VALUE="">|;
-		$out .= build_accessory_select($name, $type, $default, $opt, @opts);
-		return "$p$out$a";
-	}
-	elsif($type =~ /^reverse_combo[ _]*(?:(\d+)(?:[ _]+(\d+))?)?/i) {
-		$opt->{rows} = $opt->{rows} || $1 || 1;
-		$opt->{cols} = $opt->{cols} || $2 || 16;
-		unless($opts[0] =~ /^=/) {
-			unshift @opts, ($opt->{new} || "=Current --&gt;");
-		}
-#warn("building reverse combo");
-		my $out = build_accessory_select($name, $type, $default, $opt, @opts);
-		$out .= qq|<INPUT TYPE=text NAME="$name" SIZE=$opt->{cols} VALUE="$default">|;
-		return "$p$out$a";
-	}
-	elsif($type =~ /^move_combo[ _]*(?:(\d+)(?:[ _]+(\d+))?)?/i) {
-		$opt->{rows} = $opt->{rows} || $1 || 1;
-		$opt->{cols} = $opt->{cols} || $2 || 16;
-		my $ejs = ",1" if $opt->{rows} > 1;
-		$opt->{js} = qq{onChange="addItem(this.form.X$name,this.form.$name$ejs)"}
-			unless $opt->{js};
-		my $out = build_accessory_select("X$name", $type, '', $opt, @opts);
-		if($opt->{rows} > 1) {
-			$out .= qq|<TEXTAREA ROWS="$opt->{rows}" WRAP=virtual COLS="$opt->{cols}" NAME="$name">$default</TEXTAREA>|;
-		}
-		else {
-			$out .= qq|<INPUT SIZE="$opt->{cols}" NAME="$name" VALUE="$default">|;
+	($attribute, $type, $field, $db, $name, $outboard, $passed) = 
+		@{$opt}{qw/attribute type column table name outboard passed/};
+
+	## Code only passed when we are a product
+	if($code) {
+		GETACC: {
+			my $col =  $opt->{column} || $opt->{attribute};
+			my $key = $opt->{outboard} || $code;
+			last GETACC if ! $col;
+			if($opt->{table}) {
+				$opt->{passed} ||= tag_data($opt->{table}, $col, $key);
+			}
+			else {
+				$opt->{passed} ||= product_field($col, $key);
+			}
 		}
-		return "$p$out$a";
-	}
-	else {
-		return $p . build_accessory_select($name, $type, $default, $opt, @opts) . $a;
+
+		return unless $opt->{passed} || $opt->{type};
+		$opt->{type} ||= 'select';
+		return unless
+			$opt->{passed}
+				or
+			$opt->{type} =~ /^(text|password|hidden)/i;
 	}
 
+	return Vend::Form::display($opt, $item);
 }
 
 # MVASP
@@ -1649,24 +2081,33 @@
 
 # END MVASP
 
-use vars qw/$ready_safe/;
-use vars qw/$Calc_initialized/;
-use vars qw/$Items/;
+$safe_safe = new Safe;
 
 sub tag_perl {
 	my ($tables, $opt,$body) = @_;
 	my ($result,@share);
-#::logDebug("tag_perl MVSAFE=$MVSAFE::Safe opts=" . ::uneval($opt));
+#::logDebug("tag_perl MVSAFE=$MVSAFE::Safe opts=" . uneval($opt));
+
+	if($Vend::NoInterpolate) {
+		logGlobal({ level => 'alert' },
+					"Attempt to interpolate perl/ITL from RPC, no permissions."
+					);
+		return undef;
+	}
 
-	return undef if $MVSAFE::Safe;
-#::logDebug("tag_perl: tables=$tables opt=" . ::uneval($opt) . " body=$body");
-#::logDebug("tag_perl initialized=$Calc_initialized: carts=" . ::uneval($::Carts));
+	if ($MVSAFE::Safe) {
+		logGlobal({ level => 'alert' }, "Attempt to call perl from within Safe.");
+		return undef;
+	}
+
+#::logDebug("tag_perl: tables=$tables opt=" . uneval($opt) . " body=$body");
+#::logDebug("tag_perl initialized=$Vend::Calc_initialized: carts=" . uneval($::Carts));
 	if($opt->{subs} || (defined $opt->{arg} and $opt->{arg} =~ /\bsub\b/)) {
 		no strict 'refs';
 		for(keys %{$Global::GlobalSub}) {
 #::logDebug("tag_perl share subs: GlobalSub=$_");
 			next if defined $Global::AdminSub->{$_}
-				and ! $Global::AllowGlobal{$Vend::Cfg->{CatalogName}};
+				and ! $Global::AllowGlobal->{$Vend::Cat};
 			*$_ = \&{$Global::GlobalSub->{$_}};
 			push @share, "&$_";
 		}
@@ -1679,41 +2120,48 @@
 
 	if($tables) {
 		my (@tab) = grep /\S/, split /\s+/, $tables;
-		for(@tab) {
-#::logDebug("tag_perl: priming table $_, current=$Db{$_}");
-			next if $Db{$_};
-#::logDebug("tag_perl: getting ref $_");
-			my $db = Vend::Data::database_exists_ref($_);
-#::logDebug("tag_perl: ref returned $db");
+		foreach my $tab (@tab) {
+			next if $Db{$tab};
+			my $db = database_exists_ref($tab);
 			next unless $db;
-#::logDebug("tag_perl: need to init table $_, ref=$db");
 			$db = $db->ref();
 			if($hole) {
-#::logDebug("tag_perl: wrapped table $_ db=$db");
-			$db = $db->ref();
-#::logDebug("recall db: db=$db");
-				$Sql{$_} = $hole->wrap($db->[$Vend::Table::DBI::DBI])
-					if $db =~ /::DBI/;
-				$Sql{$_} = $hole->wrap($db->[$Vend::Table::LDAP::TIE_HASH])
-					if $db =~ /::LDAP/;
-				$Db{$_} = $hole->wrap($db);
+				$Sql{$tab} = $hole->wrap($db->dbh())
+					if $db->can('dbh');
+				$Db{$tab} = $hole->wrap($db);
+				if($db->config('name') ne $tab) {
+					$Db{$db->config('name')} = $Db{$tab};
+				}
 			}
 			else {
-				$Sql{$_} = $db->[$Vend::Table::DBI::DBI]
+				$Sql{$tab} = $db->[$Vend::Table::DBI::DBI]
 					if $db =~ /::DBI/;
-				$Db{$_} = $db;
+				$Db{$tab} = $db;
 			}
 		}
 	}
 
-	init_calc() if ! $Calc_initialized;
+	$Tag = $hole->wrap($Tag) if $hole and ! $tag_wrapped++;
+
+	init_calc() if ! $Vend::Calc_initialized;
 	$ready_safe->share(@share) if @share;
 
+	if($Vend::Cfg->{Tie_Watch}) {
+		eval {
+			for(@{$Vend::Cfg->{Tie_Watch}}) {
+				logGlobal("touching $_");
+				my $junk = $Config->{$_};
+			}
+		};
+	}
+
+	#$hole->wrap($Tag);
+
 	$MVSAFE::Safe = 1;
 	if (
 		$opt->{global}
 			and
-		$Global::AllowGlobal->{$Vend::Cfg->{CatalogName}}
+		$Global::AllowGlobal->{$Vend::Cat}
 		)
 	{
 		$MVSAFE::Safe = 0 unless $MVSAFE::Unsafe;
@@ -1724,22 +2172,55 @@
 
 	$body =~ tr/\r//d if $Global::Windows;
 
+	$Items = $Vend::Items;
+
 	if(! $MVSAFE::Safe) {
 		$result = eval($body);
 	}
 	else {
 		$result = $ready_safe->reval($body);
 	}
+
+	undef $MVSAFE::Safe;
+
 	if ($@) {
 #::logDebug("tag_perl failed $@");
 		my $msg = $@;
-		logError( "Safe: %s\n%s\n" , $msg, $body );
-		logGlobal({}, "Safe: %s\n%s\n" , $msg, $body );
+		if($Vend::Try) {
+			$Vend::Session->{try}{$Vend::Try} .= "\n" 
+				if $Vend::Session->{try}{$Vend::Try};
+			$Vend::Session->{try}{$Vend::Try} .= $@;
+		}
+        if($opt->{number_errors}) {
+            my @lines = split("\n",$body);
+            my $counter = 1;
+            map { $_ = sprintf("% 4d %s",$counter++,$_); } @lines;
+            $body = join("\n",@lines);
+        }
+        if($opt->{trim_errors}) {
+            if($msg =~ /line (\d+)\.$/) {
+                my @lines = split("\n",$body);
+                my $start = $1 - $opt->{trim_errors} - 1;
+                my $length = (2 * $opt->{trim_errors}) + 1;
+                @lines = splice(@lines,$start,$length);
+                $body = join("\n",@lines);
+            }
+        }
+        if($opt->{eval_label}) {
+            $msg =~ s/\(eval \d+\)/($opt->{eval_label})/g;
+        }
+        if($opt->{short_errors}) {
+            chomp($msg);
+            logError( "Safe: %s" , $msg );
+            logGlobal({ level => 'debug' }, "Safe: %s" , $msg );
+        } else {
+            logError( "Safe: %s\n%s\n" , $msg, $body );
+            logGlobal({ level => 'debug' }, "Safe: %s\n%s\n" , $msg, $body );
+        }
 		return $opt->{failure};
 	}
-#::logDebug("tag_perl initialized=$Calc_initialized: carts=" . ::uneval($::Carts));
+#::logDebug("tag_perl initialized=$Vend::Calc_initialized: carts=" . uneval($::Carts));
 
-	undef $MVSAFE::Safe;
 	if ($opt->{no_return}) {
 		$Vend::Session->{mv_perl_result} = $result;
 		$result = join "", @Vend::Document::Out;
@@ -1749,6 +2230,12 @@
 	return $result;
 }
 
+sub ed {
+	return $_[0] if ! $_[0] or $Safe_data or $::Pragma->{safe_data};
+	$_[0] =~ s/\[/&#91;/g;
+	return $_[0];
+}
+
 sub show_tags {
 	my($type, $opt, $text) = @_;
 
@@ -1773,14 +2260,7 @@
 		$value = $text;
 	}
 
-	$Vend::Cfg->{Pragma}{$pragma} = $value;
-	if($pragma eq 'no_html_parse') {
-		$Vend::Cfg->{Pragma}{no_html_parse} = $value;
-		$Vend::Parse::Find_tag	= $value
-									?  qr{^([^[]+)}
-									:  qr{^([^[<]+)}
-									;
-	}
+	$::Pragma->{$pragma} = $value;
 	return;
 }
 
@@ -1795,18 +2275,71 @@
 	my $fmt = $opt->{status} || '';
 	my @status;
 
-#::logDebug("tag flag=$flag text=$text value=$value opt=". ::uneval_it($opt));
+#::logDebug("tag flag=$flag text=$text value=$value opt=". uneval_it($opt));
 	if($flag eq 'write' || $flag eq 'read') {
 		my $arg = $opt->{table} || $text;
 		$value = 0 if $flag eq 'read';
 		my (@args) = Text::ParseWords::shellwords($arg);
 		my $dbname;
 		foreach $dbname (@args) {
+			# Handle table:column:key
+			$dbname =~ s/:.*//;
 #::logDebug("tag flag write $dbname=$value");
 			$Vend::WriteDatabase{$dbname} = $value;
 			$Vend::Cfg->{DynamicData}->{$dbname} = $value;
 		}
 	}
+	elsif($flag =~ /^transactions?/i) {
+		my $arg = $opt->{table} || $text;
+		my (@args) = Text::ParseWords::shellwords($arg);
+		my $dbname;
+		foreach $dbname (@args) {
+			# Handle table:column:key
+			$dbname =~ s/:.*//;
+			$Vend::TransactionDatabase{$dbname} = $value;
+			$Vend::WriteDatabase{$dbname} = $value;
+
+			# we can't do anything else if in Safe
+			next if $MVSAFE::Safe;
+
+			# Now we close and reopen
+			my $db = database_exists_ref($dbname)
+				or next;
+			if($db->isopen()) {
+				# need to reopen in transactions mode. 
+				$db->close_table();
+				$db->suicide();
+				$db = database_exists_ref($dbname);
+				$db = $db->ref();
+			}
+			$Db{$dbname} = $db;
+			$Sql{$dbname} = $db->dbh()
+				if $db->can('dbh');
+		}
+	}
+	elsif($flag eq 'commit' || $flag eq 'rollback') {
+		my $arg = $opt->{table} || $text;
+		$value = 0 if $flag eq 'rollback';
+		my $method = $value ? 'commit' : 'rollback';
+		my (@args) = Text::ParseWords::shellwords($arg);
+		my $dbname;
+		foreach $dbname (@args) {
+			# Handle table:column:key
+			$dbname =~ s/:.*//;
+#::logDebug("tag commit $dbname=$value");
+			my $db = database_exists_ref($dbname);
+			next unless $db->isopen();
+			next unless $db->config('Transactions');
+			if( ! $db ) {
+				logError("attempt to $method on unknown database: %s", $dbname);
+				return undef;
+			}
+			if( ! $db->$method() ) {
+				logError("problem doing $method for table: %s", $dbname);
+				return undef;
+			}
+		}
+	}
 	elsif($flag eq 'build') {
 		$Vend::ForceBuild = $value;
 		$text = $opt->{name} if $opt->{name};
@@ -1866,7 +2399,7 @@
 
 	my $out;
 
-#::logDebug("mime call, opt=" . ::uneval($opt));
+#::logDebug("mime call, opt=" . uneval($opt));
 	$Vend::TIMESTAMP = POSIX::strftime("%y%m%d%H%M%S", localtime())
 		unless defined $Vend::TIMESTAMP;
 
@@ -1931,7 +2464,13 @@
 	if($file =~ s/^\s*>\s*//) {
 		$opt->{create} = 1;
 	}
+
 	$file = Vend::Util::escape_chars($file);
+	if($Global::NoAbsolute and (file_name_is_absolute($file) or $file =~ m#\.\./.*\.\.#)) {
+		::logError("Can't use file '%s' with NoAbsolute set", $file);
+		::logGlobal({ level => 'auth'}, "Can't use file '%s' with NoAbsolute set", $file);
+		return '';
+	}
 
 	$file = ">$file" if $opt->{create};
 
@@ -1958,11 +2497,14 @@
 				or last;
 		}
 	}
-	elsif($opt->{type} =~ /^error/) {
-		if($opt->{file}) {
+	elsif($opt->{type} =~ /^(?:error|debug)/) {
+		if ($opt->{file}) {
 			$data = format_log_msg($data) unless $data =~ s/^\\//;;
 			$status = Vend::Util::writefile($file, $data, $opt);
 		}
+		elsif ($opt->{type} =~ /^debug/) {
+			$status = Vend::Util::logDebug($data);
+		}
 		else {
 			$status = Vend::Util::logError($data);
 		}
@@ -1991,10 +2533,23 @@
 }
 
 sub http_header {
-	my ($op, $opt, $text) = @_;
+	shift;
+	my ($opt, $text) = @_;
 	$text =~ s/^\s+//;
+	if($opt->{name}) {
+		my $name = lc $opt->{name};
+		$name =~ s/-/_/g;
+		$name =~ s/\W+//g;
+		$name =~ tr/_/-/s;
+		$name =~ s/(\w+)/\u$1/g;
+		my $content = $opt->{content} || $text;
+		$content =~ s/^\s+//;
+		$content =~ s/\s+$//;
+		$content =~ s/[\r\n]/; /g;
+		$text = "$name: $content";
+	}
 	if($Vend::StatusLine and ! $opt->{replace}) {
-		$Vend::StatusLine =~ s/\s+$/\r\n/;
+		$Vend::StatusLine =~ s/\s*$/\r\n/;
 		$Vend::StatusLine .= $text;
 	}
 	else {
@@ -2013,16 +2568,33 @@
 		POSIX::setlocale(&POSIX::LC_TIME, $locale);
 	}
 
+	local($ENV{TZ}) = $opt->{tz} if $opt->{tz};
+	
 	my $now = $opt->{time} || time();
 	$fmt = '%Y%m%d' if $opt->{sortable};
 
 	if($opt->{adjust}) {
-		$opt->{adjust} =~ s/00$//;
-        $opt->{adjust} =~ s/^(-)?[0+]/$1/;
-        $now += (60 * 60) * $opt->{adjust};
+		my $neg = $opt->{adjust} =~ s/^\s*-\s*//;
+		my $diff;
+		$opt->{adjust} =~ s/^\s*\+\s*//;
+		if($opt->{hours}) {
+			$diff = (60 * 60) * ($opt->{adjust} || $opt->{hours});
+		}
+		elsif($opt->{adjust} !~ /[A-Za-z]/) {
+			$opt->{adjust} =~ s:(\d+)(\d[05])$:$1 + $2 / 60:e;
+			$opt->{adjust} =~ s/00$//;
+			$diff = (60 * 60) * $opt->{adjust};
+		}
+		else {
+			$diff = Vend::Config::time_to_seconds($opt->{adjust});
+		}
+		$now = $neg ? $now - $diff : $now + $diff;
 	}
+
+	$fmt ||= $opt->{format} || $opt->{fmt} || '%c';
     my $out = $opt->{gmt} ? ( POSIX::strftime($fmt, gmtime($now)    ))
                           : ( POSIX::strftime($fmt, localtime($now) ));
+	$out =~ s/\b0(\d)\b/$1/g if $opt->{zerofix};
 	POSIX::setlocale(&POSIX::LC_TIME, $current) if defined $current;
 	return $out;
 }
@@ -2040,7 +2612,7 @@
 							my $table = shift;
 							my $opt = shift;
 							$opt->{search} = "ra=yes\nst=db\nml=100000\nfi=$table";
-#::logDebug("tag each: table=$table opt=" . ::uneval($opt));
+#::logDebug("tag each: table=$table opt=" . uneval($opt));
 							return tag_loop_list('', $opt, shift);
 						},
 			MIME	=> \&mime,
@@ -2049,47 +2621,88 @@
 
 sub do_tag {
 	my $op = uc $_[0];
-#::logDebug("tag op: op=$op opt=" . ::uneval(\@_));
+#::logDebug("tag op: op=$op opt=" . uneval(\@_));
 	return $_[3] if !  defined $Tag_op_map{$op};
 	shift;
-#::logDebug("tag args now: op=$op opt=" . ::uneval(\@_));
+#::logDebug("tag args now: op=$op opt=" . uneval(\@_));
 	return &{$Tag_op_map{$op}}(@_);
 }
 
 sub tag_counter {
     my $file = shift || 'etc/counter';
 	my $opt = shift;
-#::logDebug("counter: file=$file start=$opt->{start}");
+#::logDebug("counter: file=$file start=$opt->{start} sql=$opt->{sql} caller=" . scalar(caller()) );
+	if($opt->{sql}) {
+		my ($tab, $seq) = split /:+/, $opt->{sql}, 2;
+		my $db = database_exists_ref($tab);
+		my $dbh;
+		my $dsn;
+		if($opt->{bypass}) {
+			$dsn = $opt->{dsn} || $ENV{DBI_DSN};
+			$dbh = DBI->connect(
+						$dsn,
+						$opt->{user},
+						$opt->{pass},
+						$opt->{attr},
+					);
+		}
+		elsif($db) {
+			$dbh = $db->dbh();
+			$dsn = $db->config('DSN');
+		}
+
+		my $val;
+
+		eval {
+			my $diemsg = errmsg(
+							"Counter sequence '%s' failed, using file.\n",
+							$opt->{sql},
+						);
+			if(! $dbh) {
+				die errmsg(
+						"No database handle for counter sequence '%s', using file.",
+						$opt->{sql},
+					);
+			} 
+			elsif($dsn =~ /^dbi:mysql:/i) {
+				$seq ||= $tab;
+				$dbh->do("INSERT INTO $seq VALUES (0)")		or die $diemsg;
+				my $sth = $dbh->prepare("select LAST_INSERT_ID()")
+					or die $diemsg;
+				$sth->execute()								or die $diemsg;
+				($val) = $sth->fetchrow_array;
+			}
+			elsif($dsn =~ /^dbi:Pg:/i) {
+				my $sth = $dbh->prepare("select nextval('$seq')")
+					or die $diemsg;
+				$sth->execute()
+					or die $diemsg;
+				($val) = $sth->fetchrow_array;
+			}
+			elsif($dsn =~ /^dbi:Oracle:/i) {
+				my $sth = $dbh->prepare("select $seq.nextval from dual")
+					or die $diemsg;
+				$sth->execute()
+					or die $diemsg;
+				($val) = $sth->fetchrow_array;
+			}
+
+		};
+
+		logOnce('error', $@) if $@;
+
+		return $val if defined $val;
+	}
+
     $file = $Vend::Cfg->{VendRoot} . "/$file"
         unless Vend::Util::file_name_is_absolute($file);
-    my $ctr = new File::CounterFile $file, $opt->{start} || undef;
+    my $ctr = new Vend::CounterFile $file, $opt->{start} || undef;
     return $ctr->value() if $opt->{value};
     return $ctr->dec() if $opt->{decrement};
     return $ctr->inc();
 }
 
 # Returns the text of a user entered field named VAR.
-sub tag_cgi {
-    my($var, $opt) = @_;
-    my($value);
-
-	local($^W) = 0;
-	$CGI::values->{$var} = $opt->{set} if defined $opt->{set};
-	$value = defined $CGI::values{$var} ? ($CGI::values{$var}) : '';
-    if ($value) {
-		# Eliminate any Interchange tags
-		$value =~ s~<([A-Za-z]*[^>]*\s+[Mm][Vv]\s*=\s*)~&lt;$1~g;
-		$value =~ s/\[/&#91;/g;
-    }
-	if($opt->{filter}) {
-		$value = filter_value($opt->{filter}, $value, $var);
-		$CGI::values{$var} = $value unless $opt->{keep};
-	}
-    return $value unless $opt->{hide};
-    return '';
-}
-
-# Returns the text of a user entered field named VAR.
 sub tag_value_extended {
     my($var, $opt) = @_;
 
@@ -2097,6 +2710,9 @@
 	my $no = $opt->{'no'} || '';
 
 	if($opt->{test}) {
+		$opt->{test} =~ /(?:is)?put/i
+			and
+			return defined $CGI::put_ref ? $yes : $no;
 		$opt->{test} =~ /(?:is)?file/i
 			and
 			return defined $CGI::file{$var} ? $yes : $no;
@@ -2108,13 +2724,24 @@
 		return '';
 	}
 
+	if($opt->{put_contents}) {
+		return undef if ! defined $CGI::put_ref;
+		return $$CGI::put_ref;
+	}
+
 	my $val = $CGI::values{$var} || $::Values->{$var} || return undef;
+	$val =~ s/</&lt;/g unless $opt->{enable_html};
+	$val =~ s/\[/&#91;/g unless $opt->{enable_itl};
 	
 	if($opt->{file_contents}) {
 		return '' if ! defined $CGI::file{$var};
 		return $CGI::file{$var};
 	}
 
+	if($opt->{put_ref}) {
+		return $CGI::put_ref;
+	}
+
 	if($opt->{outfile}) {
 		my $file = $opt->{outfile};
 		$file =~ s/^\s+//;
@@ -2137,7 +2764,15 @@
 				$CGI::file{$var} =~ s/\n/$replace/g;
 			}
 		}
-#::logDebug(">$file \$CGI::file{$var}" . ::uneval($opt)); 
+		if($opt->{maxsize} and length($CGI::file{$var}) > $opt->{maxsize}) {
+			logError(
+				"Uploaded file write of %s bytes greater than maxsize %s. Aborted.",
+				length($CGI::file{$var}),
+				$opt->{maxsize},
+			);
+			return $opt->{no} || '';
+		}
+#::logDebug(">$file \$CGI::file{$var}" . uneval($opt)); 
 		Vend::Util::writefile(">$file", \$CGI::file{$var}, $opt)
 			and return $opt->{yes} || '';
 		return $opt->{'no'} || '';
@@ -2169,7 +2804,7 @@
 		@ary = @$val;
 	}
 	else {
-		::logError( "value-extended %s: passed non-scalar, non-array object", $var);
+		logError( "value-extended %s: passed non-scalar, non-array object", $var);
 	}
 
 	return join " ", 0 .. $#ary if $opt->{elements};
@@ -2177,7 +2812,7 @@
 	eval {
 		@ary = @ary[$ready_safe->reval( $index eq '*' ? "0 .. $#ary" : $index )];
 	};
-	::logError("value-extend $var: bad index") if $@;
+	logError("value-extended $var: bad index") if $@;
 
 	for(@ary) {
 		# Eliminate any Interchange tags
@@ -2191,124 +2826,161 @@
 	return join $joiner, @ary;
 }
 
-sub initialize_banner_directory {
-	my ($dir, $category, $opt) = @_;
-	mkdir $dir, 0777 if ! -d $dir;
-	my $t = $opt->{table} || 'banner';
-	my $c_field;
-	my $append = '';
-	if($category) {
-		$append = ' AND ';
-		$append .= ($opt->{c_field} || 'category');
-		$category =~ s/'/''/g;
-		$append .= " = '$category'";
-	}
-	my $db = database_exists_ref($t);
-	if(! $db) {
-		my $weight_file = "$dir/total_weight";
-		return undef if -f $weight_file;
-		$t = "no banners db $t\n";
-		Vend::Util::writefile( $weight_file, $t, $opt);
-		::logError($t);
-		return undef;
+sub format_auto_transmission {
+	my $ref = shift;
+
+	## Auto-transmission from Vend::Data::update_data
+	## Looking for structure like:
+	##
+	##	[ '### BEGIN submission from', 'ckirk' ],
+	##	[ 'username', 'ckirk' ],
+	##	[ 'field2', 'value2' ],
+	##	[ 'field1', 'value1' ],
+	##	[ '### END submission from', 'ckirk' ],
+	##	[ 'mv_data_fields', [ username, field1, field2 ]],
+	##
+
+	return $ref unless ref($ref);
+
+	my $body = '';
+	my %message;
+	my $header  = shift @$ref;
+	my $fields  = pop   @$ref;
+	my $trailer = pop   @$ref;
+
+	$body .= "$header->[0]: $header->[1]\n";
+
+	for my $line (@$ref) {
+		$message{$line->[0]} = $line->[1];
+	}
+
+	my @order;
+	if(ref $fields->[1]) {
+		@order = @{$fields->[1]};
 	}
-	my $w_field = $opt->{w_field} || 'weight';
-	my $b_field = $opt->{b_field} || 'banner';
-	my $q = "select $w_field, $b_field from $t where $w_field >= 1$append";
-#::logDebug("banner query: $q");
-	my $banners = $db->query({
-							query => $q,
-							st => 'db',
-						});
-	my $i = 0;
-#::logDebug("banner query result: " . ::uneval($banners));
-	for(@$banners) {
-		my ($weight, $text) = @$_;
-		for(1 .. $weight) {
-			Vend::Util::writefile(">$dir/$i", $text, $opt);
-			$i++;
+	else {
+		@order = sort keys %message;
+	}
+
+	for (@order) {
+		$body .= "$_: ";
+		if($message{$_} =~ s/\r?\n/\n/g) {
+			$body .= "\n$message{$_}\n";
+		}
+		else {
+			$body .= $message{$_};
 		}
+		$body .= "\n";
 	}
-	Vend::Util::writefile(">$dir/total_weight", $i, $opt);
+
+	$body .= "$trailer->[0]: $trailer->[1]\n";
+	return $body;
 }
 
-sub tag_weighted_banner {
-	my ($category, $opt) = @_;
-	my $dir = catfile($Vend::Cfg->{ScratchDir}, 'Banners');
-	mkdir $dir, 0777 if ! -d $dir;
-	if($category) {
-		my $c = $category;
-		$c =~ s/\W//g;
-		$dir .= "/$c";
-	}
-#::logDebug("banner category=$category dir=$dir");
-	my $statfile =	$Vend::Cfg->{ConfDir};
-	$statfile .= "/status.$Vend::Cfg->{CatalogName}";
-#::logDebug("banner category=$category dir=$dir statfile=$statfile");
-	my $start_time;
-	if($opt->{once}) {
-		$start_time = 0;
-	}
-	elsif(! -f $statfile) {
-		Vend::Util::writefile( $statfile, "banners initialized " . time() . "\n");
-		$start_time = time();
-	}
-	else {
-		$start_time = (stat(_))[9];
-	}
-	my $weight_file = "$dir/total_weight";
-#::logDebug("banner category=$category dir=$dir statfile=$statfile wfile=$weight_file");
-	initialize_banner_directory($dir, $category, $opt)
-		if  (	
-				! -f $weight_file
-					or
-				(stat(_))[9] < $start_time
+sub tag_mail {
+    my($to, $opt, $body) = @_;
+    my($ok);
+
+	my @todo = (
+					qw/
+						From      
+						To		   
+						Subject   
+						Reply-To  
+						Errors-To 
+					/
+	);
+
+	my $abort;
+	my $check;
+
+	my $setsub = sub {
+		my $k = shift;
+		return if ! defined $CGI::values{"mv_email_$k"};
+		$abort = 1 if ! $::Scratch->{mv_email_enable};
+		$check = 1 if $::Scratch->{mv_email_enable};
+		return $CGI::values{"mv_email_$k"};
+	};
+
+	my @headers;
+	my %found;
+
+	unless($opt->{raw}) {
+		for my $header (@todo) {
+			logError("invalid email header: %s", $header)
+				if $header =~ /[^-\w]/;
+			my $key = lc $header;
+			$key =~ tr/-/_/;
+			my $val = $opt->{$key} || $setsub->($key); 
+			if($key eq 'subject' and ! length($val) ) {
+				$val = errmsg('<no subject>');
+			}
+			next unless length $val;
+			$found{$key} = $val;
+			$val =~ s/^\s+//;
+			$val =~ s/\s+$//;
+			$val =~ s/[\r\n]+\s*(\S)/\n\t$1/g;
+			push @headers, "$header: $val";
+		}
+		unless($found{to} or $::Scratch->{mv_email_enable} =~ /\@/) {
+			return
+				error_opt($opt, "Refuse to send email message with no recipient.");
+		}
+		elsif (! $found{to}) {
+			$::Scratch->{mv_email_enable} =~ s/\s+/ /g;
+			$found{to} = $::Scratch->{mv_email_enable};
+			push @headers, "To: $::Scratch->{mv_email_enable}";
+		}
+	}
+
+	if($opt->{extra}) {
+		$opt->{extra} =~ s/^\s+//mg;
+		$opt->{extra} =~ s/\s+$//mg;
+		push @headers, grep /^\w[-\w]*:/, split /\n/, $opt->{extra};
+	}
+
+	$body ||= $setsub->('body');
+	unless($body) {
+		return error_opt($opt, "Refuse to send email message with no body.");
+	}
+
+	$body = format_auto_transmission($body) if ref $body;
+
+	push(@headers, '') if @headers;
+
+	return error_opt("mv_email_enable not set, required.") if $abort;
+	if($check and $found{to} ne $Scratch->{mv_email_enable}) {
+		return error_opt(
+				"mv_email_enable to address (%s) doesn't match enable (%s)",
+				$found{to},
+				$Scratch->{mv_email_enable},
 			);
-	my $n = int( rand( readfile($weight_file) ) );
-#::logDebug("weight total n=$n, file=$dir/$n");
-	return Vend::Util::readfile("$dir/$n");
-}
-
-sub tag_banner {
-    my ($place, $opt) = @_;
-
-	return tag_weighted_banner($place, $opt) if $opt->{weighted};
-
-#::logDebug("banner, place=$place opt=" . ::uneval_it($opt));
-	my $table	= $opt->{table}		|| 'banner';
-	my $r_field	= $opt->{r_field}	|| 'rotate';
-	my $b_field	= $opt->{b_field}	|| 'banner';
-	my $sep		= $opt->{separator} || ':';
-	my $delim	= $opt->{delimiter} || "{or}";
-	$place = 'default' if ! $place;
-    my $totrot;
-    do {
-		my $banner_data;
-        $totrot = tag_data($table, $r_field, $place);
-        if(! length $totrot) {
-			# No banner present
-            unless ($place =~ /$sep/ or $place eq 'default') {
-				$place = 'default';
-				redo;
-			}
-        }
-        elsif ($totrot) {
-            my $current = $::Scratch->{"rotate_$place"}++ || 0;
-            my $data = tag_data($table, $b_field, $place);
-            my(@banners) = split /\Q$delim/, $data;
-            return '' unless @banners;
-            return $banners[$current % scalar(@banners)];
-        }
-        else {
-            return tag_data($table, $b_field, $place);
-        }
-    } while $place =~ s/(.*)$sep.*/$1/;
-	return;
+	}
+
+    SEND: {
+		$ok = send_mail(\@headers, $body);
+    }
+
+    if (!$ok) {
+		close MAIL;
+		$body = substr($body, 0, 2000) if length($body) > 2000;
+        return error_opt(
+					"Unable to send mail using %s\n%s",
+					$Vend::Cfg->{SendMailProgram},
+					join("\n", @headers, $body),
+				);
+	}
+
+	delete $Scratch->{mv_email_enable} if $check;
+	return if $opt->{hide};
+	return join("\n", @headers, $body) if $opt->{show};
+    return ($opt->{success} || $ok);
 }
 
 # Returns the text of a user entered field named VAR.
 sub tag_value {
     my($var,$opt) = @_;
+#::logDebug("called value args=" . uneval(\@_));
     my($value);
 
 	local($^W) = 0;
@@ -2326,41 +2998,11 @@
 	$::Scratch->{$var} = $value if $opt->{scratch};
 	return '' if $opt->{hide};
     return $opt->{default} if ! $value and defined $opt->{default};
+	$value =~ s/</&lt;/g
+		unless $opt->{enable_html};
     return $value;
 }
 
-# Returns the contents of a file.  Won't allow any arbitrary file unless
-# NoAbsolute is not set.
-sub tag_file {
-	my ($file, $type) = @_;
-    return readfile($file, $Global::NoAbsolute)
-		unless $type;
-	my $text = readfile($file, $Global::NoAbsolute);
-	if($type =~ /mac/i) {
-		$text =~ tr/\n/\r/;
-	}
-	elsif($type =~ /dos|window/i) {
-		$text =~ s/\n/\r\n/g;
-	}
-	elsif($type =~ /unix/i) {
-		if($text=~ /\n/) {
-			$text =~ tr/\r/\n/;
-		}
-		else {
-			$text =~ s/\r\n/\n/g;
-		}
-	}
-	return $text;
-}
-
-# Returns the text of a user entered field named VAR.
-# Same as tag value except returns 'default' if not present
-sub tag_default {
-    my($var, $default, $opt) = @_;
-	$opt->{default} = !(length $default) ? 'default' : $default;
-    return tag_value($var, $opt);
-}
-
 sub esc {
 	my $string = shift;
 	$string =~ s!(\W)!'%' . sprintf '%02x', ord($1)!eg;
@@ -2391,14 +3033,47 @@
 	}
 
 	if($scan =~ /^\s*(?:sq\s*=\s*)?select\s+/im) {
-		$scan = Vend::Scan::sql_statement($scan, $ref || $::Scratch);
+		eval {
+			$scan = Vend::Scan::sql_statement($scan, $ref || \%CGI::values)
+		};
+		if($@) {
+			my $msg = errmsg("SQL query failed: %s\nquery was: %s", $@, $scan);
+			logError($msg);
+			$scan = 'se=BAD_SQL';
+		}
 	}
 
 	return join '/', 'scan', escape_mv('/', $scan);
 }
 
+sub escape_form {
+	my $val = shift;
+
+	$val =~ s/^\s+//mg;
+	$val =~ s/\s+$//mg;
+	my @args;
+
+	## Already escaped, return
+	return $val if $val =~ /^\S+=\S+=\S*$/;
+
+	$val =~ s/^\s+//mg;
+	$val =~ s/\s+$//mg;
+	@args = split /\n+/, $val;
+	for(@args) {
+		s/^(.*?=)(.+)/$1 . Vend::Util::unhexify($2)/ge;
+	}
+
+	for(@args) {
+		next if /^[\w=]+$/;
+		s!\0!-_NULL_-!g;
+		s!([^=]+)=(.*)!esc($1) . '=' . esc($2)!eg
+			or (undef $_, next);
+	}
+	return join $Global::UrlJoiner, grep length($_), @args;
+}
+
 sub escape_mv {
-	my ($joiner, $scan, $not_scan) = @_;
+	my ($joiner, $scan, $not_scan, $esc) = @_;
 
 	my @args;
 
@@ -2417,41 +3092,15 @@
 	@args = grep $_, @args;
 	for(@args) {
 		s!/!__SLASH__!g unless defined $not_scan;
-		s!\0!__NULL__!g;
-		s!(\w\w=)(.*)!$1 . esc($2)!eg
-			or (undef $_, next);
+		s!\0!-_NULL_-!g;
+		m!\w=!
+		    or (undef $_, next);
 		s!__SLASH__!::!g unless defined $not_scan;
 	}
 	return join $joiner, grep(defined $_, @args);
 }
 
-sub form_link {
-	my ($href, $arg, $opt) = @_;
-
-	if( $href and $opt->{alias}) {
-		my $aloc = $opt->{once} ? 'one_time_path_alias' : 'path_alias';
-		$Vend::Session->{$aloc}{$href} = {}
-			if not defined $Vend::Session->{path_alias}{$href};
-		$Vend::Session->{$aloc}{$href} = $opt->{alias};
-	}
-
-	my $base = ! $opt->{secure} ? ($Vend::Cfg->{VendURL}) : $Vend::Cfg->{SecureURL};
-
-	$href = 'process' unless $href;
-	$href =~ s:^/+::;
-	$opt->{secure} = 1 if exists $Vend::Cfg->{AlwaysSecure}{$href};
-	my $base = ! $opt->{secure} ? ($Vend::Cfg->{VendURL}) : $Vend::Cfg->{SecureURL};
-	$href = "$base/$href"     unless $href =~ /^\w+:/;
-
-	my $extra = <<EOF;
-mv_session_id=$Vend::Session->{id}
-EOF
-	$arg = '' if ! $arg;
-	$arg = "mv_arg=$arg\n" if $arg && $arg !~ /\n/; 
-	$extra .= $arg . $opt->{form};
-	$extra = escape_mv('&', $extra, 1);
-	return $href . '?' . $extra;
-}
+*form_link = \&tag_area;
 
 PAGELINK: {
 
@@ -2467,7 +3116,7 @@
 #::logDebug("have cookie...");
 	return if ! $Vend::Cfg->{Static};
 #::logDebug("are static...");
-	my $key = $page;
+	my $key = Vend::Util::escape_chars_url($page);
 	if($arg) {
 		my $tmp = $arg;
 		$tmp =~ s:([^\w/]): sprintf '%%%02x', ord($1) :eg;
@@ -2492,24 +3141,16 @@
 }
 
 sub tag_page {
-    ($page, $arg, $opt) = @_;
+    my ($page, $arg, $opt) = @_;
 
-#::logDebug("tag_page opt=" . ::uneval($opt));
-	return '<A HREF="' . form_link(@_) . '">' if defined $opt and $opt->{form};
+	my $url = tag_area(@_);
 
-	if ($opt->{search}) {
-		$page = escape_scan($opt->{search});
-	}
-	elsif ($page eq 'scan') {
-		$page = escape_scan($arg);
-		undef $arg;
+	my $extra;
+	if($extra = ($opt ||= {})->{extra} || '') {
+		$extra =~ s/^(\w+)$/class=$1/;
+		$extra = " $extra";
 	}
-
-	$urlroutine = $opt->{secure} ? \&secure_vendUrl : \&vendUrl;
-
-	resolve_static();
-
-    return '<a href="' . $urlroutine->($page,$arg || undef) . '">';
+    return qq{<a href="$url"$extra>};
 }
 
 # Returns an href which will call up the specified PAGE.
@@ -2517,13 +3158,22 @@
 sub tag_area {
     ($page, $arg, $opt) = @_;
 
-	return form_link(@_) if defined $opt and $opt->{form};
-
 	$page = '' if ! defined $page;
 
+	if( $page and $opt->{alias}) {
+		my $aloc = $opt->{once} ? 'one_time_path_alias' : 'path_alias';
+		$Vend::Session->{$aloc}{$page} = {}
+			if not defined $Vend::Session->{path_alias}{$page};
+		$Vend::Session->{$aloc}{$page} = $opt->{alias};
+	}
+
 	if ($opt->{search}) {
 		$page = escape_scan($opt->{search});
 	}
+	elsif ($page =~ /^[a-z][a-z]+:/) {
+		### Javascript or absolute link
+		return $page;
+	}
 	elsif ($page eq 'scan') {
 		$page = escape_scan($arg);
 		undef $arg;
@@ -2533,7 +3183,11 @@
 
 	resolve_static();
 
-	return $urlroutine->($page, $arg);
+	my $anchor = '';
+	if($opt->{anchor}) {
+		$anchor = '#' . $opt->{anchor};
+	}
+	return $urlroutine->($page, $arg, undef, $opt) . $anchor;
 }
 
 }
@@ -2550,41 +3204,46 @@
 	my $mode = 	shift;
 	$CacheInvalid = 1 unless $mode;
 	$mode = $mode || $::Values->{mv_shipmode} || 'default';
-	return '' unless defined $Vend::Cfg->{Shipping_desc}->{$mode};
-	$Vend::Cfg->{Shipping_desc}->{$mode};
-}
-
-# Returns the href to process the completed order form or do the search.
-
-sub tag_process {
-	my($target,$secure,$opt) = @_;
-	if($opt->{order}) {
-		$secure = $Vend::Session->{secure} ? 1 : 0; 
-	}
-	my $url = $secure ? secure_vendUrl('process') : vendUrl('process');
-	return $url unless $target;
-	return qq{$url" TARGET="$target};
+	return '' unless defined $Vend::Cfg->{Shipping_desc}{$mode};
+	return $Vend::Cfg->{Shipping_desc}{$mode};
 }
 
 sub tag_calc {
 	my($body) = @_;
-	my $result = 0;
+	my $result;
+	if($Vend::NoInterpolate) {
+		logGlobal({ level => 'alert' },
+					"Attempt to interpolate perl/ITL from RPC, no permissions."
+					);
+	}
 
-	init_calc() if ! $Calc_initialized;
+	$Items = $Vend::Items;
+
+	if($MVSAFE::Safe) {
+		$result = eval($body);
+	}
+	else {
+		init_calc() if ! $Vend::Calc_initialized;
+		$result = $ready_safe->reval($body);
+	}
 
-	$result = $ready_safe->reval($body);
 	if ($@) {
-		my $msg;
-		$msg .= $@;
-		logGlobal({}, "Safe: %s\n%s\n" , $msg, $body);
+		my $msg = $@;
+		$Vend::Session->{try}{$Vend::Try} = $msg if $Vend::Try;
+		logGlobal({ level => 'debug' }, "Safe: %s\n%s\n" , $msg, $body);
 		logError("Safe: %s\n%s\n" , $msg, $body);
-		return 0;
+		return $MVSAFE::Safe ? '' : 0;
 	}
 	return $result;
 }
 
+sub tag_unless {
+	return tag_self_contained_if(@_, 1) if defined $_[4];
+	return tag_if(@_, 1);
+}
+
 sub tag_self_contained_if {
-	my($base, $term, $operator, $comp, $body) = @_;
+	my($base, $term, $operator, $comp, $body, $negate) = @_;
 
 	my ($else,$elsif,@addl);
 	
@@ -2607,6 +3266,8 @@
 		undef $comp;
 	}
 
+	($base =~ s/^\W+// or $base = "!$base") if $negate;
+
 	my $status = conditional ($base, $term, $operator, $comp, @addl);
 
 	my $out;
@@ -2614,11 +3275,11 @@
 		$out = $body;
 	}
 	elsif ($elsif) {
-		$else = '[else]' . $else . '[/else]' if $else;
+		$else = '[else]' . $else . '[/else]' if length $else;
 		$elsif =~ s#(.*?)$QR{'/elsif'}(.*)#$1${2}[/elsif]#s;
 		$out = '[if ' . $elsif . $else . '[/if]';
 	}
-	elsif ($else) {
+	elsif (length $else) {
 		$out = $else;
 	}
 	else {
@@ -2643,20 +3304,22 @@
    '!=' => sub { $_[0] != $_[1] },
    '=~' => sub { 
    				 my $re;
-				 $_[1] =~ s:^/(.*)/$:$1:;
+				 $_[1] =~ s:^/(.*)/([imsx]*)\s*$:$1:;
+				 $2 and substr($_[1], 0, 0) = "(?$2)";
    				 eval { $re = qr/$_[1]/ };
 				 if($@) {
-					::logError("bad regex %s in if-PREFIX-data", $_[1]);
+					logError("bad regex %s in if-PREFIX-data", $_[1]);
 					return undef;
 				 }
 				 return $_[0] =~ $re;
 				},
    '!~' => sub { 
    				 my $re;
-				 $_[1] =~ s:^/(.*)/$:$1:;
+				 $_[1] =~ s:^/(.*)/([imsx]*)\s*$:$1:;
+				 $2 and substr($_[1], 0, 0) = "(?$2)";
    				 eval { $re = qr/$_[1]/ };
 				 if($@) {
-					::logError("bad regex %s in if-PREFIX-data", $_[1]);
+					logError("bad regex %s in if-PREFIX-data", $_[1]);
 					return undef;
 				 }
 				 return $_[0] !~ $re;
@@ -2666,10 +3329,10 @@
 sub pull_cond {
 	my($string, $reverse, $cond, $lhs) = @_;
 #::logDebug("pull_cond string='$string' rev='$reverse' cond='$cond' lhs='$lhs'");
-	my ($op, $rhs) = split /\s+/, $cond;
+	my ($op, $rhs) = split /\s+/, $cond, 2;
 	$rhs =~ s/^(["'])(.*)\1$/$2/;
 	if(! defined $cond_op{$op} ) {
-		::logError("bad conditional operator %s in if-PREFIX-data", $op);
+		logError("bad conditional operator %s in if-PREFIX-data", $op);
 		return pull_else($string, $reverse);
 	}
 	return 	$cond_op{$op}->($lhs, $rhs)
@@ -2681,7 +3344,7 @@
 	return pull_cond(@_) if $_[2];
 	my($string, $reverse) = @_;
 	return pull_else($string) if $reverse;
-	$string =~ s:$QR{else_end}::o;
+	find_matching_else(\$string) if $string =~ s:$QR{has_else}::;
 	return $string;
 }
 
@@ -2689,7 +3352,7 @@
 	return pull_cond(@_) if $_[2];
 	my($string, $reverse) = @_;
 	return pull_if($string) if $reverse;
-	return $1 if $string =~ s:$QR{else_end}::;
+	return find_matching_else(\$string) if $string =~ s:$QR{has_else}::;
 	return;
 }
 
@@ -2727,7 +3390,7 @@
     my($opts, $list) = (@_); 
     $opts =~ s/^\s+//; 
     $opts =~ s/\s+$//; 
-#::logDebug("tag_sort_ary: opts=$opts list=" . ::uneval($list));
+#::logDebug("tag_sort_ary: opts=$opts list=" . uneval($list));
 	my @codes;
 	my $key = 0;
 
@@ -2800,7 +3463,7 @@
 	if(defined $num) {
 		splice(@codes, $num);
 	}
-#::logDebug("tag_sort_ary routine returns: " . ::uneval(\@codes));
+#::logDebug("tag_sort_ary routine returns: " . uneval(\@codes));
 	return \@codes;
 }
 
@@ -2808,7 +3471,7 @@
     my($opts, $list) = (@_); 
     $opts =~ s/^\s+//; 
     $opts =~ s/\s+$//; 
-#::logDebug("tag_sort_hash: opts=$opts list=" . ::uneval($list));
+#::logDebug("tag_sort_hash: opts=$opts list=" . uneval($list));
 	my @codes;
 	my $key = 'code';
 
@@ -2848,7 +3511,7 @@
  	}
 
 	if (! defined $list->[0]->{$key}) {
-		::logError("sort key '$key' not defined in list. Skipping sort.");
+		logError("sort key '$key' not defined in list. Skipping sort.");
 		return $list;
 	}
 
@@ -2886,7 +3549,7 @@
 	if(defined $num) {
 		splice(@codes, $num);
 	}
-#::logDebug("tag_sort_hash routine returns: " . ::uneval(\@codes));
+#::logDebug("tag_sort_hash routine returns: " . uneval(\@codes));
 	return \@codes;
 }
 
@@ -2950,22 +3613,6 @@
 	return $options || '';
 }
 
-sub tag_search_list {
-    my($opt, $text) = @_;
-	$opt->{prefix} = 'item';
-	my $obj;
-
-	$obj = $opt->{object}
-			|| $Vend::SearchObject{$opt->{label}}
-			|| perform_search()
-			|| return;
-	$text =~ s:\[if-(field\s+|data\s+):[if-item-$1:gi
-		and $text =~ s:\[/if${D}(field|data)\]:[/if-item-$1]:gi;
-	$text =~ s:\[on${D}change\b:[item-change:gi
-		and $text =~ s:\[/on${D}change\b:[/item-change:gi;
-   	return labeled_list($opt, $text, $obj);
-}
-
 # Artificial for better variable passing
 {
 	my( $next_anchor,
@@ -2981,10 +3628,24 @@
 		$page,
 		$prefix,
 		$more_id,
-		$form_arg,
 		$session,
+		$link_template,
 		);
 
+sub more_link_template {
+	my ($anchor, $arg, $form_arg) = @_;
+
+	my $url = tag_area("scan/MM=$arg", '', {
+	    form => $form_arg,
+	    secure => $CGI::secure,
+	});
+
+	my $lt = $link_template;
+	$lt =~ s/\$URL\$/$url/g;
+	$lt =~ s/\$ANCHOR\$/$anchor/g;
+	return $lt;
+}
+
 sub more_link {
 	my($inc, $pa) = @_;
 	my ($next, $last, $arg);
@@ -2993,10 +3654,14 @@
 	my $form_arg = "mv_more_ip=1\nmv_nextpage=$page";
 	$form_arg .= "\npf=$prefix" if $prefix;
 	$form_arg .= "\nmi=$prefix" if $more_id;
+	$form_arg .= "\n$opt->{form}" if $opt->{form};
 	$next = ($inc-1) * $chunk;
 #::logDebug("more_link: inc=$inc current=$current");
 	$last = $next + $chunk - 1;
 	$last = ($last+1) < $total ? $last : ($total - 1);
+	$pa =~ s/__PAGE__/$inc/g;
+	$pa =~ s/__MINPAGE__/$next + 1/eg;
+	$pa =~ s/__MAXPAGE__/$last + 1/eg;
 	if($inc == $current) {
 		$pa =~ s/__BORDER__/$border_selected || $border || ''/e;
 		$list .= qq|<STRONG>$pa</STRONG> | ;
@@ -3004,11 +3669,7 @@
 	else {
 		$pa =~ s/__BORDER__/$border/e;
 		$arg = "$session:$next:$last:$chunk";
-		$list .= '<A HREF="';
-		$list .= tag_area( "scan/MM=$arg", '', { form => $form_arg });
-		$list .= '">';
-		$list .= $pa;
-		$list .= '</A> ';
+		$list .= more_link_template($pa, $arg, $form_arg) . ' ';
 	}
 	return $list;
 }
@@ -3025,10 +3686,12 @@
 	) = @_;
 #::logDebug("more_list: opt=$opt label=$opt->{label}");
 	return undef if ! $opt;
-	$q = $opt->{object} || $Vend::SearchObject{$opt->{label}};
-	return '' unless $q->{matches} > $q->{mv_matchlimit};
+	$q = $opt->{object} || $::Instance->{SearchObject}{$opt->{label}};
+	return '' unless $q->{matches} > $q->{mv_matchlimit}
+		and $q->{mv_matchlimit} > 0;
 	my($arg,$inc,$last,$m);
 	my($adder,$pages);
+	my($first_anchor,$last_anchor);
 	my $next_tag = '';
 	my $list = '';
 	$session = $q->{mv_cache_key};
@@ -3042,10 +3705,14 @@
 	$prefix = $q->{prefix} || '';
 	my $form_arg = "mv_more_ip=1\nmv_nextpage=$page";
 	$form_arg .= "\npf=$q->{prefix}" if $q->{prefix};
+	$form_arg .= "\n$opt->{form}" if $opt->{form};
 	if($q->{mv_more_id}) {
 		$more_id = $q->{mv_more_id};
 		$form_arg .= "\nmi=$more_id";
 	}
+	else {
+		$more_id = undef;
+	}
 
 	if($r =~ s:\[border\]($All)\[/border\]::i) {
 		$border = $1;
@@ -3056,6 +3723,13 @@
 		$border =~ s/\D//g;
 	}
 
+	if ($r =~ s:\[link[-_]template\]($All)\[/link[-_]template\]::i) {
+		$link_template = $1;
+	}
+	else {
+		$link_template = q{<A HREF="$URL$">$ANCHOR$</A>};
+	}
+
 	if(! $chunk or $chunk >= $total) {
 		return '';
 	}
@@ -3070,12 +3744,28 @@
 
 	if($first) {
 		$first = 0 if $first < 0;
+
+		# First link may appear when prev link is valid
+		if($r =~ s:\[first[-_]anchor\]($All)\[/first[-_]anchor\]::i) {
+			$first_anchor = $1;
+		}
+		else {
+			$first_anchor = errmsg('First');
+		}
+		unless ($first_anchor eq 'none') {
+			$arg = $session;
+			$arg .= ':0:';
+			$arg .= $chunk - 1;
+			$arg .= ":$chunk";
+			$list .= more_link_template($first_anchor, $arg, $form_arg) . ' ';
+		}
+
 		unless ($prev_anchor) {
 			if($r =~ s:\[prev[-_]anchor\]($All)\[/prev[-_]anchor\]::i) {
 				$prev_anchor = $1;
 			}
 			else {
-				$prev_anchor = 'Previous';
+				$prev_anchor = errmsg('Previous');
 			}
 		}
 		elsif ($prev_anchor ne 'none') {
@@ -3088,24 +3778,22 @@
 			$arg .= ':';
 			$arg .= $first - 1;
 			$arg .= ":$chunk";
-			$list .= '<A HREF="';
-			$list .= tag_area( "scan/MM=$arg", '', { form => $form_arg });
-			$list .= '">';
-			$list .= $prev_anchor;
-			$list .= '</A> ';
+			$list .= more_link_template($prev_anchor, $arg, $form_arg) . ' ';
 		}
+
 	}
 	else {
-		$r =~ s:\[prev[-_]anchor\]($All)\[/prev[-_]anchor\]::i;
+		$r =~ s:\[(prev|first)[-_]anchor\]$All\[/\1[-_]anchor\]::ig;
 	}
 	
 	if($next) {
+
 		unless ($next_anchor) {
 			if($r =~ s:\[next[-_]anchor\]($All)\[/next[-_]anchor\]::i) {
 				$next_anchor = $1;
 			}
 			else {
-				$next_anchor = 'Next';
+				$next_anchor = errmsg('Next');
 			}
 		}
 		else {
@@ -3114,20 +3802,29 @@
 		$last = $next + $chunk - 1;
 		$last = $last > ($total - 1) ? $total - 1 : $last;
 		$arg = "$session:$next:$last:$chunk";
-		$next_tag .= '<A HREF="';
-		$next_tag .= tag_area( "scan/MM=$arg", '', { form => $form_arg });
-		$next_tag .= '">';
-		$next_tag .= $next_anchor;
-		$next_tag .= '</A>';
+		$next_tag .= more_link_template($next_anchor, $arg, $form_arg);
+
+ 		# Last link can appear when next link is valid
+		if($r =~ s:\[last[-_]anchor\]($All)\[/last[-_]anchor\]::i) {
+			$last_anchor = $1;
+		}
+		else {
+			$last_anchor = errmsg('Last');
+		}
+		unless ($last_anchor eq 'none') {
+			$last = $total - 1;
+			my $last_beg_idx = $total - ($total % $chunk || $chunk);
+			$arg = "$session:$last_beg_idx:$last:$chunk";
+			$next_tag .= ' ' . more_link_template($last_anchor, $arg, $form_arg);
+		}
 	}
 	else {
-		$r =~ s:\[next[-_]anchor\]($All)\[/next[-_]anchor\]::i;
+		$r =~ s:\[(last|next)[-_]anchor\]$All\[/\1[-_]anchor\]::gi;
 	}
 	
 	unless ($page_anchor) {
 		if($r =~ s:\[page[-_]anchor\]($All)\[/page[-_]anchor\]::i) {
 			$page_anchor = $1;
-			$page_anchor =~ s/\$PAGE\$/__PAGE__/i;
 		}
 		else {
 			$page_anchor = '__PAGE__';
@@ -3137,14 +3834,19 @@
 		$page_anchor = qq%<IMG SRC="$page_anchor?__PAGE__"__BORDER__>%;
 	}
 
+	$page_anchor =~ s/\$(MIN|MAX)?PAGE\$/__${1}PAGE__/g;
+
+	my $more_string = errmsg('more');
 	my ($decade_next, $decade_prev, $decade_div);
 	if( $q->{mv_more_decade} or $r =~ m:\[decade[-_]next\]:) {
 		$r =~ s:\[decade[-_]next\]($All)\[/decade[-_]next\]::i
 			and $decade_next = $1;
-		$decade_next = '<SMALL>&#91;more&gt;&gt;&#93;</SMALL>' if ! $decade_next;
+		$decade_next = "<SMALL>&#91;$more_string&gt;&gt;&#93;</SMALL>"
+			if ! $decade_next;
 		$r =~ s:\[decade[-_]prev\]($All)\[/decade[-_]prev\]::i
 			and $decade_prev = $1;
-		$decade_prev = '<SMALL>&#91;&lt;&lt;more&#93;</SMALL>' if ! $decade_prev;
+		$decade_prev = "<SMALL>&#91;&lt;&lt;$more_string&#93;</SMALL>"
+			if ! $decade_prev;
 		$decade_div = $q->{mv_more_decade} > 1 ? $q->{mv_more_decade} : 10;
 	}
 
@@ -3175,11 +3877,18 @@
 	}
 #::logDebug("more_list: pages=$pages current=$current b=$b e=$e next=$next last=$last decade_div=$decade_div");
 
-	foreach $inc ($b .. $e) {
-		last if $page_anchor eq 'none';
-		$list .= more_link($inc, $page_anchor);
+	if ($q->{mv_alpha_list}) {
+		for my $record (@{$q->{mv_alpha_list}}) {
+			$arg = "$session:$record->[2]:$record->[3]:" . ($record->[3] - $record->[2] + 1);
+			my $letters = substr($record->[0], 0, $record->[1]);
+			$list .= more_link_template($letters, $arg, $form_arg) . ' ';
+		}
+	} else {
+		foreach $inc ($b .. $e) {
+			last if $page_anchor eq 'none';
+			$list .= more_link($inc, $page_anchor);
+		}
 	}
-
 	$list .= " $decade_next " if defined $decade_next;
 	$list .= $next_tag;
 	$first = $first + 1;
@@ -3233,6 +3942,7 @@
 my $IB;
 my $IE;
 my $Prefix;
+my $Orig_prefix;
 
 sub tag_labeled_data_row {
 	my ($key, $text) = @_;
@@ -3243,11 +3953,11 @@
 		$prefix = $Prefix;
 		undef $Prefix;
 		$LdB = qr(\[$prefix[-_]data$Spacef)i;
-		$LdIB = qr(\[if[-_]$prefix[-_]data$Spacef(!?)(?:%20|\s)*)i;
-		$LdIE = qr(\[/if[-_]$prefix[-_]data\])i;
-		$LdExpr = qr{ \[(?:$prefix[-_]data|if[-_]$prefix[-_]data)
+		$LdIB = qr(\[if[-_]$prefix[-_]data(\d*)$Spacef(!?)(?:%20|\s)*)i;
+		$LdIE = qr(\[/if[-_]$prefix[-_]data)i;
+		$LdExpr = qr{ \[(?:$prefix[-_]data|if[-_]$prefix[-_]data(\d*))
 	                \s+ !?\s* ($Codere) \s
-					(?!$All\[(?:$prefix[-_]data|if[-_]$prefix[-_]data))  }xi;
+					(?!$All\[(?:$prefix[-_]data|if[-_]$prefix[-_]data\1))  }xi;
 		%Data_cache = ();
 	}
 	# Want the last one
@@ -3263,7 +3973,7 @@
 #EOF
 
     while($$text =~ $LdExpr) {
-		$table = $1;
+		$table = $2;
 		$tabRE = qr/$table/;
 		$row = $Data_cache{"$table.$key"}
 				|| ( $Data_cache{"$table.$key"}
@@ -3271,13 +3981,13 @@
 					)
 				|| {};
 		$done = 1;
-		$$text =~ s#$LdIB$tabRE$LdI$LdIE#
-					$row->{$2}	? pull_if($4,$1,$3,$row->{$2})
-								: pull_else($4,$1,$3,$row->{$2})#ge
+		$$text =~ s#$LdIB$tabRE$LdI$LdIE\1\]#
+					$row->{$3}	? pull_if($5,$2,$4,$row->{$3})
+								: pull_else($5,$2,$4,$row->{$3})#ge
 			and undef $done;
 #::logDebug("after if: table=$table 1=$1 2=$2 3=$3 $$text =~ s#$LdIB $tabRE $LdI $LdIE#");
 
-		$$text =~ s/$LdB$tabRE$LdD/$row->{$1}/g
+		$$text =~ s/$LdB$tabRE$LdD/ed($row->{$1})/eg
 			and undef $done;
 		last if $done;
 	}
@@ -3312,15 +4022,19 @@
 	return '' if ! $obj;
 
 	my $ary = $obj->{mv_results};
-	return if (! $ary or ! ref $ary or ! $text or ! defined $ary->[0]);
+	return if (! $ary or ! ref $ary or ! defined $ary->[0]);
 	
 	my $save_unsafe = $MVSAFE::Unsafe || '';
 	$MVSAFE::Unsafe = 1;
 
-	if($opt->{prefix} eq 'item') {
-#::logDebug("labeled list: opt:\n" . ::uneval($opt) . "\nobj:" . ::uneval($obj) . "text:" . substr($text,0,100));
-	}
-	$Prefix = $opt->{prefix} || 'item';
+	# This allows left brackets to be output by the data tags
+	local($Safe_data);
+	$Safe_data = 1 if $opt->{safe_data};
+
+#	if($opt->{prefix} eq 'item') {
+#::logDebug("labeled list: opt:\n" . uneval($opt) . "\nobj:" . uneval($obj) . "text:" . substr($text,0,100));
+#	}
+	$Orig_prefix = $Prefix = $opt->{prefix} || 'item';
 
 	$B  = qr(\[$Prefix)i;
 	$E  = qr(\[/$Prefix)i;
@@ -3392,7 +4106,7 @@
 			and $text =~ s,$IE$QR{'/_field'},[/if-$Prefix-data],g;
 	}
 #::logDebug("Past only products.");
-	$end =	$obj->{mv_matchlimit}
+	$end =	($obj->{mv_matchlimit} and $obj->{mv_matchlimit} > 0)
 			? $i + ($opt->{ml} || $obj->{mv_matchlimit}) - 1
 			: $#$ary;
 	$end = $#$ary if $#$ary < $end;
@@ -3404,22 +4118,15 @@
 
 	my $r;
 	if($ary->[0] =~ /HASH/) {
-		for (my $i = 0; $i < @$ary; $i++) {
-			$ary->[$i]{mv_ip} = $i;
-		}
 		$ary = tag_sort_hash($opt->{sort}, $ary) if $opt->{sort};
-		$r = iterate_hash_list($i, $end, $count, $text, $ary, $opt_select);
+		$r = iterate_hash_list($i, $end, $count, $text, $ary, $opt_select, $opt);
 	}
 	else {
 		my $fa = $obj->{mv_return_fields} || undef;
 		my $fh = $obj->{mv_field_hash}    || undef;
 		my $fn = $obj->{mv_field_names}   || undef;
-#::logDebug("fa: " . ::uneval($fa));
-#::logDebug("fh: " . ::uneval($fh));
-#::logDebug("fn: " . ::uneval($fn));
 		$ary = tag_sort_ary($opt->{sort}, $ary) if $opt->{sort};
-		if($fa) {
-#::logDebug("fa before fn: " . ::uneval($fa));
+		if ($fa and $fn) {
 			my $idx = 0;
 			$fh = {};
 			for(@$fa) {
@@ -3427,30 +4134,370 @@
 			}
 		}
 		elsif (! $fh and $fn) {
-#::logDebug("Not fh, fn: " . ::uneval($fn));
 			my $idx = 0;
 			$fh = {};
 			for(@$fn) {
 				$fh->{$_} = $idx++;
 			}
-#::logDebug("Not fh, fn: " . ::uneval($fh));
-		}
-		else {
-#::logDebug("fh is there." . ::uneval($fh));
 		}
-		$r = iterate_array_list($i, $end, $count, $text, $ary, $opt_select, $fh);
+#::logDebug("Missing mv_field_hash and/or mv_field_names in Vend::Interpolate::labeled_list") unless ref $fh eq 'HASH';
+		$r = iterate_array_list($i, $end, $count, $text, $ary, $opt_select, $fh, $opt);
 	}
 	$MVSAFE::Unsafe = $save_unsafe;
 	return $r;
 }
 
+sub tag_attr_list {
+	my ($body, $hash, $ucase) = @_;
+	if(! ref $hash) {
+		$hash = string_to_ref($hash);
+		if($@) {
+			logDebug("eval error: $@");
+		}
+		return undef if ! ref $hash;
+	}
+	if($ucase) {
+		$body =~ s!\{([A-Z_][A-Z_]+)\}!$hash->{"\L$1"}!g;
+		$body =~ s!\{([A-Z_][A-Z_]+)\?([A-Z_][A-Z_]+)\:([A-Z_][A-Z_]+)\}!
+					length($hash->{lc $1}) ? $hash->{lc $2} : $hash->{lc $3}
+				  !eg;
+		$body =~ s!\{([A-Z_][A-Z_]+)\|($Some)\}!$hash->{lc $1} || $2!eg;
+		$body =~ s!\{([A-Z_][A-Z_]+)\s+($Some)\}! $hash->{lc $1} ? $2 : ''!eg;
+		1 while $body =~ s!\{([A-Z_][A-Z_]+)\?\}($Some){/\1\?\}! $hash->{lc $1} ? $2 : ''!eg;
+		1 while $body =~ s!\{([A-Z_][A-Z_]+)\:\}($Some){/\1\:\}! $hash->{lc $1} ? '' : $2!eg;
+		$body =~ s!\{(\w+)\:+(\w+)\:+(.*?)\}! tag_data($1, $2, $3) !eg;
+	}
+	else {
+	$body =~ s!\{($Codere)\}!$hash->{$1}!g;
+	$body =~ s!\{($Codere)\?($Codere)\:($Codere)\}!
+				length($hash->{$1}) ? $hash->{$2} : $hash->{$3}
+			  !eg;
+	$body =~ s!\{($Codere)\|($Some)\}!$hash->{$1} || $2!eg;
+	$body =~ s!\{($Codere)\s+($Some)\}! $hash->{$1} ? $2 : ''!eg;
+	1 while $body =~ s!\{($Codere)\?\}($Some){/\1\?\}! $hash->{$1} ? $2 : ''!eg;
+	1 while $body =~ s!\{($Codere)\:\}($Some){/\1\:\}! $hash->{$1} ? '' : $2!eg;
+	$body =~ s!\{(\w+)\:+(\w+)\:+(.*?)\}! tag_data($1, $2, $3) !eg;
+	}
+	return $body;
+}
+
+sub tag_address {
+	my ($count, $item, $hash, $opt, $body) = @_;
+#::logDebug("in ship_address");
+	return pull_else($body) if defined $opt->{if} and ! $opt->{if};
+	return pull_else($body) if ! $Vend::username || ! $Vend::Session->{logged_in};
+#::logDebug("logged in with usernam=$Vend::username");
+	
+	my $tag = 'address';
+	my $attr = 'mv_ad';
+	my $nattr = 'mv_an';
+	my $pre = '';
+	if($opt->{billing}) {
+		$tag = 'b_address';
+		$attr = 'mv_bd';
+		$nattr = 'mv_bn';
+		$pre = 'b_';
+	}
+
+#	if($item->{$attr} and ! $opt->{set}) {
+#		my $pre = $opt->{prefix};
+#		$pre =~ s/[-_]/[-_]/g;
+#		$body =~ s:\[$pre\]($Some)\[/$pre\]:$item->{$attr}:g;
+#		return pull_if($body);
+#	}
+
+	my $nick = $opt->{nick} || $opt->{nickname} || $item->{$nattr};
+
+#::logDebug("nick=$nick");
+
+	my $user;
+	if(not $user = $Vend::user_object) {
+		 $user = new Vend::UserDB username => ($opt->{username} || $Vend::username);
+	}
+#::logDebug("user=$user");
+	! $user and return pull_else($body);
+
+	my $blob = $user->get_hash('SHIPPING')   or return pull_else($body);
+#::logDebug("blob=$blob");
+	my $addr = $blob->{$nick};
+
+	if (! $addr) {
+		%$addr = %{ $::Values };
+	}
+
+#::logDebug("addr=" . uneval($addr));
+
+	$addr->{mv_an} = $nick;
+	my @nick = sort keys %$blob;
+	my $label;
+	if($label = $opt->{address_label}) {
+		@nick = sort { $blob->{$a}{$label} cmp  $blob->{$a}{$label} } @nick;
+		@nick = map { "$_=" . ($blob->{$_}{$label} || $_) } @nick;
+		for(@nick) {
+			s/,/&#44;/g;
+		}
+	}
+	$opt->{blank} = '--select--' unless $opt->{blank};
+	unshift(@nick, "=$opt->{blank}");
+	$opt->{address_book} = join ",", @nick
+		unless $opt->{address_book};
+
+	my $joiner = get_joiner($opt->{joiner}, '<BR>');
+	if(! $opt->{no_address}) {
+		my @vals = map { $addr->{$_} }
+					grep /^address_?\d*$/ && length($addr->{$_}), keys %$addr;
+		$addr->{address} = join $joiner, @vals;
+	}
+
+	if($opt->{widget}) {
+		$addr->{address_book} = tag_accessories(
+									$item->{code},
+									undef,
+									{
+										attribute => $nattr,
+										type => $opt->{widget},
+										passed => $opt->{address_book},
+										form => $opt->{form},
+									},
+									$item
+									);
+	}
+
+	if($opt->{set} || ! $item->{$attr}) {
+		my $template = '';
+		if($::Variable->{MV_SHIP_ADDRESS_TEMPLATE}) {
+			$template .= $::Variable->{MV_SHIP_ADDRESS_TEMPLATE};
+		}
+		else {
+			$template .= "{company}\n" if $addr->{"${pre}company"};
+			$template .= <<EOF;
+{address}
+{city}, {state} {zip} 
+{country} -- {phone_day}
+EOF
+		}
+		$template =~ s/{(\w+.*?)}/{$pre$1}/g if $pre;
+		$addr->{mv_ad} = $item->{$attr} = tag_attr_list($template, $addr);
+	}
+	else {
+		$addr->{mv_ad} = $item->{$attr};
+	}
+
+	if($opt->{textarea}) {
+		$addr->{textarea} = tag_accessories(
+									$item->{code},
+									undef,
+									{
+										attribute => $attr,
+										type => 'textarea',
+										rows => $opt->{rows} || '4',
+										cols => $opt->{cols} || '40',
+									},
+									$item
+									);
+	}
+
+	$body =~ s:\[$tag\]($Some)\[/$tag\]:tag_attr_list($1, $addr):eg;
+	return pull_if($body);
+}
+
+sub tag_object {
+	my ($count, $item, $hash, $opt, $body) = @_;
+	my $param = delete $hash->{param}
+		or return undef;
+	my $method;
+	my $out = '';
+	eval {
+		if(not $method = delete $hash->{method}) {
+			$out = $item->{$param}->();
+		}
+		else {
+			$out = $item->{$param}->$method();
+		}
+	};
+	return $out;
+}
+
+my %Dispatch_hash = (
+	address => \&tag_address,
+	object  => \&tag_object,
+);
+
+sub find_matching_else {
+    my($buf) = @_;
+    my $out;
+	my $canon;
+
+    my $open  = '[else]';
+    my $close = '[/else]';
+    my $first;
+	my $pos;
+
+  	$$buf =~ s{\[else\]}{[else]}igo;
+    $first = index($$buf, $open, $pos);
+#::logDebug("first=$first");
+	return undef if $first < 0;
+	my $int     = $first;
+	my $begin   = $first;
+	$$buf =~ s{\[/else\]}{[/else]}igo
+		or $int = -1;
+
+	while($int > -1) {
+		$pos   = $begin + 1;
+		$begin = index($$buf, $open, $pos);
+		$int   = index($$buf, $close, $int + 1);
+		last if $int < 1;
+		if($begin > $int) {
+			$first = $int = $begin;
+			$int = $begin;
+		}
+#::logDebug("pos=$pos int=$int first=$first begin=$begin");
+    }
+	$first = $begin if $begin > -1;
+	substr($$buf, $first) =~ s/(.*)//s;
+	$out = $1;
+	substr($out, 0, 6) = '';
+	return $out;
+}
+
+sub tag_dispatch {
+	my($tag, $count, $item, $hash, $chunk) = @_;
+	$tag = lc $tag;
+	$tag =~ tr/-/_/;
+	my $full = lc "$Orig_prefix-tag-$tag";
+	$full =~ tr/-/_/;
+#::logDebug("tag_dispatch: tag=$tag count=$count chunk=$chunk");
+	my $attrseq = [];
+	my $attrhash = {};
+	my $eaten;
+	my $this_tag;
+
+	$eaten = Vend::Parse::_find_tag(\$chunk, $attrhash, $attrseq);
+	substr($chunk, 0, 1) = '';
+
+	$this_tag = Vend::Parse::find_matching_end($full, \$chunk);
+	
+	$attrhash->{prefix} = $tag unless $attrhash->{prefix};
+
+	my $out;
+	if(defined $Dispatch_hash{$tag}) {
+		$out = $Dispatch_hash{$tag}->($count, $item, $hash, $attrhash, $this_tag);
+	}
+	else {
+		$attrhash->{body} = $this_tag unless defined $attrhash->{body};
+#::logDebug("calling do_tag tag=$tag this_tag=$this_tag attrhash=" . uneval($attrhash));
+		$Tag ||= new Vend::Tags;
+		$out = $Tag->$tag($attrhash);
+	}
+	return $out . $chunk;
+}
+
+my $rit = 1;
+
+sub resolve_nested_if {
+	my ($where, $what) = @_;
+	$where =~ s~\[$what\s+(?!.*\[$what\s)(.*?)\[/$what\]~
+				'[' . $what . $rit . " $1" . '[/' . $what . $rit++ . ']'~seg;
+#::logDebug("resolved?\n$where\n");
+	return $where;
+}
+
+use vars qw/%Ary_code/;
+%Ary_code = (
+	accessories => \&tag_accessories,
+	common => \&Vend::Data::product_common,
+	description => \&Vend::Data::product_description,
+	field => \&Vend::Data::product_field,
+	last => \&interpolate_html,
+	next => \&interpolate_html,
+	options => \&tag_options,
+);
+
+use vars qw/%Hash_code/;
+%Hash_code = (
+	accessories => \&tag_accessories,
+	common => \&Vend::Data::item_common,
+	description => \&Vend::Data::item_description,
+	field => \&Vend::Data::item_field,
+	last => \&interpolate_html,
+	next => \&interpolate_html,
+	options => \&tag_options,
+);
+
+sub map_list_routines {
+	my($type, $opt) = @_;
+
+	### This allows mapping of new routines to 
+	##    PREFIX-options
+	##    PREFIX-accessories
+	##    PREFIX-description
+	##    PREFIX-common
+	##    PREFIX-field
+	##    PREFIX-price
+	##    PREFIX-tag
+	##    PREFIX-last
+	##    PREFIX-next
+
+	my $nc;
+
+	my $ac; 
+	for $ac ($Global::CodeDef->{$type}, $Vend::Cfg->{CodeDef}{$type}) {
+		next unless $ac and $ac->{Routine};
+		$nc ||= {};
+		for(keys %{$ac->{Routine}}) {
+			$nc->{$_} = $ac->{Routine}{$_};
+		}
+	}
+
+	if($ac = $opt->{maproutine}) {
+		$nc ||= {};
+		if(! ref($ac) ) {
+			$ac =~ s/[\s'",=>\0]+$//;
+			$ac =~ s/^[\s'",=>\0]+//;
+			$ac = { split /[\s'",=>\0]+/, $ac };
+		}
+		$ac = {} if ref($ac) ne 'HASH';
+		while( my($k,$v) = each %$ac) {
+			$nc->{$k} = $Vend::Cfg->{Sub}{$v} || $Global::GlobalSub->{$v}
+			  or do {
+				  logError("%s: non-existent mapped routine %s.", $type, $_);
+					delete $nc->{$_};
+			  };
+		}
+	}
+	return $nc;
+}
+
 sub iterate_array_list {
-	my ($i, $end, $count, $text, $ary, $opt_select, $fh) = @_;
+	my ($i, $end, $count, $text, $ary, $opt_select, $fh, $opt) = @_;
 
 	my $r = '';
+	$opt ||= {};
+
+	my $lim;
+	if($lim = $Vend::Cfg->{Limit}{list_text_size} and length($text) > $lim) {
+		my $len = length($text);
+		my $caller = join "|", caller();
+		my $msg = "Large list text encountered,  length=$len, caller=$caller";
+		logError($msg);
+		return undef if $Vend::Cfg->{Limit}{list_text_overflow} eq 'abort';
+	}
+
+	# Optimize for no-match, on-match, etc
+	if(! $opt->{iterator} and $text !~ /\[(?:if-)?$Prefix-/) {
+		for(; $i <= $end; $i++) {
+			$r .= $text;
+		}
+		return $r;
+	}
+
+	my $nc = map_list_routines('ArrayCode', $opt);
+
+	$nc and local(@Ary_code{keys %$nc}) = values %$nc;
+
 	my ($run, $row, $code, $return);
 my $once = 0;
-#::logDebug("iterating array $i to $end. count=$count opt_select=$opt_select ary=" . ::uneval($ary));
+#::logDebug("iterating array $i to $end. count=$count opt_select=$opt_select ary=" . uneval($ary));
 	if($text =~ m/^$B$QR{_line}\s*$/is) {
 		my $i = $1 || 0;
 		my $count = scalar values %$fh;
@@ -3463,7 +4510,7 @@
 		my $name = $1;
 		my $routine = $2;
 		## Not necessary?
-		## $Vend::Cfg->{Sub}{''} = sub { ::errmsg('undefined sub') }
+		## $Vend::Cfg->{Sub}{''} = sub { errmsg('undefined sub') }
 		##	unless defined $Vend::Cfg->{Sub}{''};
 		$routine = 'sub { ' . $routine . ' }' unless $routine =~ /^\s*sub\s*{/;
 		my $sub;
@@ -3471,12 +4518,49 @@
 			$sub = $ready_safe->reval($routine);
 		};
 		if($@) {
-			::logError( ::errmsg("syntax error on %s-sub %s]: $@", $B, $name) );
-			$sub = sub { ::errmsg('ERROR') };
+			logError( errmsg("syntax error on %s-sub %s]: $@", $B, $name) );
+			$sub = sub { errmsg('ERROR') };
 		}
 #::logDebug("sub $name: $sub --> $routine");
 		$Vend::Cfg->{Sub}{$name} = $sub;
 	}
+
+	my $oexec = { %$opt };
+
+	if($opt->{iterator}) {
+		my $sub;
+		$sub = $opt->{iterator}          if ref($opt->{iterator}) eq 'CODE';
+		$sub ||= $Vend::Cfg->{Sub}{$opt->{iterator}}
+				|| $Global::GlobalSub->{$opt->{iterator}};
+		if(! $sub) {
+			logError(
+				"list iterator subroutine '%s' called but not defined. Skipping.",
+				$opt->{iterator},
+			);
+			return '';
+		}
+		for( ; $i <= $end ; $i++ ) {
+			$r .= $sub->($text, $ary->[$i], $oexec);
+		}
+		return $r;
+	}
+
+	1 while $text =~ s{(\[(if[-_]$Prefix[-_][a-zA-Z]+)(?=.*\[\2)\s.*\[/\2\])}
+					  {
+					  	resolve_nested_if($1, $2)
+					  }se;
+
+	# log helpful errors if any unknown field names are
+	# used in if-prefix-param or prefix-param tags
+	my @field_msg = ('error', "Unknown field name '%s' used in tag %s");
+	$run = $text;
+	if(! $opt->{ignore_undefined}) {
+	$run =~ s#$B$QR{_param}# defined $fh->{$1} ||
+		logOnce(@field_msg, $1, "$Orig_prefix-param") #ige;
+	$run =~ s#$IB$QR{_param_if}# defined $fh->{$3} ||
+		logOnce(@field_msg, $3, "if-$Orig_prefix-param") #ige;
+	}
+
 	for( ; $i <= $end ; $i++, $count++ ) {
 		$row = $ary->[$i];
 		last unless defined $row;
@@ -3490,28 +4574,31 @@
 				  $count % ($1 || $::Values->{mv_item_alternate} || 2)
 				  							?	pull_else($2)
 											:	pull_if($2)#ige;
-		$run =~ s#$IB$QR{_param_if}$IE$QR{'/_param'}#
-				  (defined $fh->{$2} ? $row->[$fh->{$2}] : '')
-				  					?	pull_if($4,$1,$3,$row->[$2])
-									:	pull_else($4,$1,$3,$row->[$2])#ige;
-	    $run =~ s#$B$QR{_param}#defined $fh->{$1} ? $row->[$fh->{$1}] : ''#ige;
-		$run =~ s#$IB$QR{_pos_if}$IE$QR{'/_pos'}#
-				  $row->[$2] 
-						?	pull_if($4,$1,$3,$row->[$2])
-						:	pull_else($4,$1,$3,$row->[$2])#ige;
-	    $run =~ s#$B$QR{_pos}#$row->[$1]#ig;
-#::logDebug("fh: " . ::uneval($fh) . ::uneval($row)) unless $once++;
-		$run =~ s#$IB$QR{_field_if}$IE$QR{'/_field'}#
-				  my $tmp = product_field($2, $code);
-				  $tmp	?	pull_if($4,$1,$3,$tmp)
-						:	pull_else($4,$1,$3,$tmp)#ge;
+		1 while $run =~ s#$IB$QR{_param_if}$IE[-_]param\1\]#
+				  (defined $fh->{$3} ? $row->[$fh->{$3}] : '')
+				  					?	pull_if($5,$2,$4,$row->[$fh->{$3}])
+									:	pull_else($5,$2,$4,$row->[$fh->{$3}])#ige;
+	    $run =~ s#$B$QR{_param}#defined $fh->{$1} ? ed($row->[$fh->{$1}]) : ''#ige;
+		1 while $run =~ s#$IB$QR{_pos_if}$IE[-_]pos\1\]#
+				  $row->[$3] 
+						?	pull_if($5,$2,$4,$row->[$3])
+						:	pull_else($5,$2,$4,$row->[$3])#ige;
+	    $run =~ s#$B$QR{_pos}#ed($row->[$1])#ige;
+#::logDebug("fh: " . uneval($fh) . uneval($row)) unless $once++;
+		1 while $run =~ s#$IB$QR{_field_if}$IE[-_]field\1\]#
+				  my $tmp = product_field($3, $code);
+				  $tmp	?	pull_if($5,$2,$4,$tmp)
+						:	pull_else($5,$2,$4,$tmp)#ige;
 		$run =~ s:$B$QR{_line}:join "\t", @{$row}[ ($1 || 0) .. $#$row]:ige;
 	    $run =~ s:$B$QR{_increment}:$count:ig;
 		$run =~ s:$B$QR{_accessories}:
-						tag_accessories($code,$1,{}):ige;
+						$Ary_code{accessories}->($code,$1,{}):ige;
+		$run =~ s:$B$QR{_options}:
+						$Ary_code{options}->($code,$1):ige;
 		$run =~ s:$B$QR{_code}:$code:ig;
-		$run =~ s:$B$QR{_description}:product_description($code):ige;
-		$run =~ s:$B$QR{_field}:product_field($1, $code):ige;
+		$run =~ s:$B$QR{_description}:ed($Ary_code{description}->($code)):ige;
+		$run =~ s:$B$QR{_field}:ed($Ary_code{field}->($1, $code)):ige;
+		$run =~ s:$B$QR{_common}:ed($Ary_code{common}->($1, $code)):ige;
 		tag_labeled_data_row($code, \$run);
 		$run =~ s!$B$QR{_price}!
 					currency(product_price($code,$1), $2)!ige;
@@ -3520,11 +4607,22 @@
 							check_change($1,$3,undef,$2)
 											?	pull_if($4)
 											:	pull_else($4)!ige;
+		$run =~ s#$B$QR{_tag}($Some$E[-_]tag[-_]\1\])#
+						tag_dispatch($1,$count, $row, $ary, $2)#ige;
 		$run =~ s#$B$QR{_calc}$E$QR{'/_calc'}#tag_calc($1)#ige;
-		$run =~ s#$B$QR{_exec}$E$QR{'/_exec'}#init_calc() if ! $Calc_initialized;($Vend::Cfg->{Sub}{$1} || sub { 'ERROR' })->($2,$row)#ige;
+		$run =~ s#$B$QR{_exec}$E$QR{'/_exec'}#
+					init_calc() if ! $Vend::Calc_initialized;
+					(
+						$Vend::Cfg->{Sub}{$1} ||
+						$Global::GlobalSub->{$1} ||
+						sub { 'ERROR' }
+					)->($2,$row,$oexec)
+				#ige;
 		$run =~ s#$B$QR{_filter}$E$QR{'/_filter'}#filter_value($1,$2)#ige;
 		$run =~ s#$B$QR{_last}$E$QR{'/_last'}#
-                    my $tmp = interpolate_html($1);
+                    my $tmp = $Ary_code{last}->($1);
+					$tmp =~ s/^\s+//;
+					$tmp =~ s/\s+$//;
                     if($tmp && $tmp < 0) {
                         last;
                     }
@@ -3533,9 +4631,9 @@
                     }
                     '' #ixge;
 		$run =~ s#$B$QR{_next}$E$QR{'/_next'}#
-                    interpolate_html($1) != 0 ? next : '' #ixge;
+                    $Ary_code{next}->($1) != 0 ? next : '' #ixge;
 		$run =~ s/<option\s*/<OPTION SELECTED /i
-			if $opt_select and $opt_select->($code);	
+			if $opt_select and $opt_select->($code);
 
 		$r .= $run;
 		last if $return;
@@ -3544,19 +4642,91 @@
 }
 
 sub iterate_hash_list {
-	my($i, $end, $count, $text, $hash, $opt_select) = @_;
+	my($i, $end, $count, $text, $hash, $opt_select, $opt) = @_;
 
 	my $r = '';
-	my ($run, $item, $code, $return);
+	$opt ||= {};
+
+	# Optimize for no-match, on-match, etc
+	if(! $opt->{iterator} and $text !~ /\[/) {
+		for(; $i <= $end; $i++) {
+			$r .= $text;
+		}
+		return $r;
+	}
+
+	my $code_field = $opt->{code_field} || 'mv_sku';
+	my ($run, $code, $return, $item);
+
+	my $nc = map_list_routines('HashCode', $opt);
+
+	$nc and local(@Hash_code{keys %$nc}) = values %$nc;
+
+#::logDebug("iterating hash $i to $end. count=$count opt_select=$opt_select hash=" . uneval($hash));
+	while($text =~ s#$B$QR{_sub}$E$QR{'/_sub'}##i) {
+		my $name = $1;
+		my $routine = $2;
+		## Not necessary?
+		## $Vend::Cfg->{Sub}{''} = sub { errmsg('undefined sub') }
+		##	unless defined $Vend::Cfg->{Sub}{''};
+		$routine = 'sub { ' . $routine . ' }' unless $routine =~ /^\s*sub\s*{/;
+		my $sub;
+		eval {
+			$sub = $ready_safe->reval($routine);
+		};
+		if($@) {
+			logError( errmsg("syntax error on %s-sub %s]: $@", $B, $name) );
+			$sub = sub { errmsg('ERROR') };
+		}
+		$Vend::Cfg->{Sub}{$name} = $sub;
+	}
+#::logDebug("subhidden: $opt->{subhidden}");
+
+	my $oexec = { %$opt };
+
+	if($opt->{iterator}) {
+		my $sub;
+		$sub   = $opt->{iterator}          if ref($opt->{iterator}) eq 'CODE';
+		$sub ||= $Vend::Cfg->{Sub}{$opt->{iterator}}
+				|| $Global::GlobalSub->{$opt->{iterator}};
+		if(! $sub) {
+			logError(
+				"list iterator subroutine '%s' called but not defined. Skipping.",
+				$opt->{iterator},
+			);
+			return '';
+		}
+
+		for( ; $i <= $end ; $i++ ) {
+			$r .= $sub->($text, $hash->[$i], $oexec);
+		}
+		return $r;
+	}
+
+	1 while $text =~ s{(\[(if[-_]$Prefix[-_][a-zA-Z]+)(?=.*\[\2)\s.*\[/\2\])}
+					  {
+					  	resolve_nested_if($1, $2)
+					  }se;
 
-#::logDebug("iterating hash $i to $end. count=$count opt_select=$opt_select hash=" . ::uneval($hash));
 
 	for ( ; $i <= $end; $i++, $count++) {
 		$item = $hash->[$i];
+		$item->{mv_ip} = $i;
+		if($opt->{modular}) {
+			if($opt->{master}) {
+				next unless $item->{mv_mi} eq $opt->{master};
+			}
+			if($item->{mv_mp} and $item->{mv_si} and ! $opt->{subitems}) {
+#				$r .= <<EOF if $opt->{subhidden};
+#<INPUT TYPE="hidden" NAME="quantity$item->{mv_ip}" VALUE="$item->{quantity}">
+#EOF
+				next;
+			}
+		}
 		$item->{mv_cache_price} = undef;
-		$code = $item->{code};
+		$code = $item->{$code_field} || $item->{code};
 
-#::logDebug("Doing $code substitution, count $count++");
+#::logDebug("Doing $code (variant $item->{code}) substitution, count $count++");
 
 		$run = $text;
 		$run =~ s#$B$QR{_alternate}$E$QR{'/_alternate'}#
@@ -3565,22 +4735,31 @@
 											:	pull_if($2)#ge;
 		tag_labeled_data_row($code,\$run);
 		$run =~ s:$B$QR{_line}:join "\t", @{$hash}:ge;
-		$run =~ s#$IB$QR{_param_if}$IE$QR{'/_param'}#
-				  $item->{$2}	?	pull_if($4,$1,$3,$item->{$2})
-								:	pull_else($4,$1,$3,$item->{$2})#ige;
-		$run =~ s#$IB$QR{_field_if}$IE$QR{'/_field'}#
-				  my $tmp = product_field($2, $code);
-				  $tmp	?	pull_if($4,$1,$3,$tmp)
-						:	pull_else($4,$1,$3,$tmp)#ge;
-		$run =~ s#$IB$QR{_modifier_if}$IE$QR{'/_modifier'}#
-				  $item->{$2}	?	pull_if($4,$1,$3,$item->{$2})
-								:	pull_else($4,$1,$3,$item->{$2})#ge;
+		1 while $run =~ s#$IB$QR{_param_if}$IE[-_]param\1\]#
+				  $item->{$3}	?	pull_if($5,$2,$4,$item->{$3})
+								:	pull_else($5,$2,$4,$item->{$3})#ige;
+		1 while $run =~ s#$IB$QR{_parent_if}$IE[-_]parent\1\]#
+				  $item->{$3}	?	pull_if($5,$2,$4,$opt->{$3})
+								:	pull_else($5,$2,$4,$opt->{$3})#ige;
+		1 while $run =~ s#$IB$QR{_field_if}$IE[-_]field\1\]#
+				  my $tmp = item_field($item, $3);
+				  $tmp	?	pull_if($5,$2,$4,$tmp)
+						:	pull_else($5,$2,$4,$tmp)#ge;
+		1 while $run =~ s#$IB$QR{_modifier_if}$IE[-_]modifier\1\]#
+				  $item->{$3}	?	pull_if($5,$2,$4,$item->{$3})
+								:	pull_else($5,$2,$4,$item->{$3})#ge;
 		$run =~ s:$B$QR{_increment}:$i + 1:ge;
+		
 		$run =~ s:$B$QR{_accessories}:
-						tag_accessories($code,$1,{},$item):ge;
+						$Hash_code{accessories}->($code,$1,{},$item):ge;
+		$run =~ s:$B$QR{_options}:
+						$Hash_code{options}->($item,$1):ige;
+		$run =~ s:$B$QR{_sku}:$code:ig;
+		$run =~ s:$B$QR{_code}:$item->{code}:ig;
 		$run =~ s:$B$QR{_quantity}:$item->{quantity}:g;
-		$run =~ s:$B$QR{_modifier}:$item->{$1}:g;
-		$run =~ s:$B$QR{_param}:$item->{$1}:g;
+		$run =~ s:$B$QR{_modifier}:ed($item->{$1}):ge;
+		$run =~ s:$B$QR{_param}:ed($item->{$1}):ge;
+		$run =~ s:$B$QR{_parent}:ed($opt->{$1}):ge;
 		$run =~ s:$QR{quantity_name}:quantity$item->{mv_ip}:g;
 		$run =~ s:$QR{modifier_name}:$1$item->{mv_ip}:g;
 		$run =~ s!$B$QR{_subtotal}!currency(item_subtotal($item),$1)!ge;
@@ -3591,9 +4770,10 @@
 								$1
 								)!ge;
 		$run =~ s:$B$QR{_code}:$code:g;
-		$run =~ s:$B$QR{_field}:item_field($item, $1) || $item->{$1}:ge;
+		$run =~ s:$B$QR{_field}:ed($Hash_code{field}->($item, $1) || $item->{$1}):ge;
+		$run =~ s:$B$QR{_common}:ed($Hash_code{common}->($item, $1) || $item->{$1}):ge;
 		$run =~ s:$B$QR{_description}:
-							item_description($item) || $item->{description}
+							ed($Hash_code{description}->($item) || $item->{description})
 							:ge;
 		$run =~ s!$B$QR{_price}!currency(item_price($item,$1), $2)!ge;
 		$run =~ s!$B$QR{_discount_price}!
@@ -3629,10 +4809,19 @@
 							check_change($1,$3,undef,$2)
 											?	pull_if($4)
 											:	pull_else($4)!ige;
+		$run =~ s#$B$QR{_tag}($All$E[-_]tag[-_]\1\])#
+						tag_dispatch($1,$count, $item, $hash, $2)#ige;
 		$run =~ s#$B$QR{_calc}$E$QR{'/_calc'}#tag_calc($1)#ige;
-		$run =~ s#$B$QR{_exec}$E$QR{'/_exec'}#init_calc() if ! $Calc_initialized;($Vend::Cfg->{Sub}{$1} || sub { 'ERROR' })->($2,$item)#ige;
+		$run =~ s#$B$QR{_exec}$E$QR{'/_exec'}#
+					init_calc() if ! $Vend::Calc_initialized;
+					(
+						$Vend::Cfg->{Sub}{$1} ||
+						$Global::GlobalSub->{$1} ||
+						sub { 'ERROR' }
+					)->($2,$item,$oexec)
+				#ige;
 		$run =~ s#$B$QR{_filter}$E$QR{'/_filter'}#filter_value($1,$2)#ige;
-		$run =~ s#$B$QR{_last}$E$QR{'/item_last'}#
+		$run =~ s#$B$QR{_last}$E$QR{'/_last'}#
                     my $tmp = interpolate_html($1);
                     if($tmp && $tmp < 0) {
                         last;
@@ -3647,6 +4836,7 @@
 			if $opt_select and $opt_select->($code);	
 
 		$r .= $run;
+#::logDebug("item $code mv_cache_price: $item->{mv_cache_price}");
 		delete $item->{mv_cache_price};
 		last if $return;
 	}
@@ -3654,12 +4844,25 @@
 	return $r;
 }
 
+sub error_opt {
+	my ($opt, @args) = @_;
+	return undef unless ref $opt;
+	my $msg = errmsg(@args);
+	$msg = "$opt->{error_id}: $msg" if $opt->{error_id};
+	if($opt->{log_error}) {
+		logError($msg);
+	}
+	return $msg if $opt->{show_error};
+	return undef;
+}
+
 sub query {
 	if(ref $_[0]) {
 		unshift @_, '';
 	}
 	my ($query, $opt, $text) = @_;
 	$opt = {} if ! $opt;
+	$opt->{prefix} = 'sql' unless $opt->{prefix};
 	if($opt->{more} and $Vend::More_in_progress) {
 		undef $Vend::More_in_progress;
 		return region($opt, $text);
@@ -3679,23 +4882,6 @@
 	$db->query($opt, $text);
 }
 
-sub tag_item_list {
-	my($cart,$opt,$text) = @_;
-#::logDebug("tag_item_list: " . ::uneval(\@_));
-	my $obj = {
-				mv_results => $cart ? ($::Carts->{$cart} ||= [] ) : $Vend::Items,
-					};
-	return if ! $text;
-#::logDebug("tag_item_list obj=" . ::uneval($obj));
-#::logDebug("Vend::Items obj=" . ::uneval($Vend::Items));
-	$CacheInvalid = 1;
-	$opt->{prefix} = 'item' unless defined $opt->{prefix};
-# LEGACY
-	list_compat($opt->{prefix}, \$text);
-# END LEGACY
-	return labeled_list($opt, $text, $obj);
-}
-
 sub html_table {
     my($opt, $ary, $na) = @_;
 
@@ -3792,43 +4978,78 @@
 
 # SQL
 sub tag_sql_list {
-    my($text,$ary,$nh,$opt) = @_;
+    my($text,$ary,$nh,$opt,$na) = @_;
 	$opt = {} unless defined $opt;
 	$opt->{prefix}      = 'sql' if ! defined $opt->{prefix};
 	$opt->{list_prefix} = 'sql[-_]list' if ! defined $opt->{prefix};
 
-	$opt->{object} = {
+	my $object = {
 					mv_results => $ary,
 					mv_field_hash => $nh,
+					mv_return_fields => $na,
 					matches => scalar @$ary,
 				};
+
+	# Scans the option hash for more search settings if mv_more_alpha
+	# is set in [query ...] tag....
+	if($opt->{ma}) {
+		# Find the sort field and alpha options....
+		Vend::Scan::parse_profile_ref($object, $opt);
+		# We need to turn the hash reference into a search object
+		$object = new Vend::Search (%$object);
+		# Delete this so it will meet conditions for creating a more
+		delete $object->{mv_matchlimit};
+	}
+
+	$opt->{object} = $object;
     return region($opt, $text);
 }
 # END SQL
 
 # Displays a search page with the special [search-list] tag evaluated.
 
+sub opt_region {
+	my $opt = pop @_;
+#::logDebug("opt_region called, prefix=$Prefix, text=$_[-1]");
+	my $new = { %$opt };
+	my $out = iterate_hash_list(@_,[$new]);
+	$Prefix = $Orig_prefix;
+#::logDebug("opt_region prefix=$Prefix, results=$out");
+	return $out;
+}
+
 sub region {
 
 	my($opt,$page) = @_;
 
 	my $obj;
+
 	if($opt->{object}) {
+		### The caller supplies the object, no search to be done
+		#::logDebug("region: object was supplied by caller.");
 		$obj = $opt->{object};
 	}
 	else {
-#::logDebug("no object.");
+		### We need to run a search to get an object
+		#::logDebug("region: no object supplied");
 		my $c;
 		if($CGI::values{mv_more_matches} || $CGI::values{MM}) {
-#::logDebug("more object = $CGI::values{mv_more_matches}");
+
+			### It is a more function, we need to get the parameters
+			#::logDebug("more object = $CGI::values{mv_more_matches}");
+
 			find_search_params();
 			delete $CGI::values{mv_more_matches};
-#::logDebug("more object = " . ::uneval($c));
+
+#::logDebug("more object = " . uneval($c));
+
 		}
 		elsif ($opt->{search}) {
-#::logDebug("opt->search object label=$opt->{label}.");
-			if($opt->{more} and $Vend::SearchObject{''}) {
-				$obj = $Vend::SearchObject{''};
+			### Explicit search in tag parameter, run just like any
+			#::logDebug("opt->search object label=$opt->{label}.");
+			if($opt->{more} and $::Instance->{SearchObject}{''}) {
+				$obj = $::Instance->{SearchObject}{''};
+				#::logDebug("cached search");
 			}
 			else {
 				$c = {	mv_search_immediate => 1,
@@ -3836,14 +5057,19 @@
 						};
 				my $params = escape_scan($opt->{search});
 				Vend::Scan::find_search_params($c, $params);
+				#::logDebug("perform_search");
 				$obj = perform_search($c);
 			}
 		}
 		else {
-#::logDebug("try labeled object label=$opt->{label}.");
-			$obj = $Vend::SearchObject{$opt->{label}};
+			### See if we have a search already done for this label
+			#::logDebug("try labeled object label=$opt->{label}.");
+			$obj = $::Instance->{SearchObject}{$opt->{label}};
 		}
-#::logDebug("no found object") if ! $obj;
+
+		# If none of the above happen, we need to perform a search
+		# based on the passed CGI parameters
+		#::logDebug("no found object") if ! $obj;
 		if(! $obj) {
 			$obj = perform_search();
 			$obj = {
@@ -3852,15 +5078,32 @@
 				} if ! $obj;
 		}
 		finish_search($obj);
-		$Vend::SearchObject{$opt->{label}} = $opt->{object} = $obj;
-#::logDebug("labeling as '$opt->{label}'");
+
+		# Label it for future reference
+		#::logDebug("labeling as '$opt->{label}'");
+
+		$::Instance->{SearchObject}{$opt->{label}} = $opt->{object} = $obj;
+	}
+	my $lprefix;
+	my $mprefix;
+	if(defined $opt->{list_prefix}) {
+		$lprefix = $opt->{list_prefix};
+		$mprefix = "(?:$opt->{list_prefix}-)?";
+	}
+	elsif (defined $opt->{prefix}) {
+		$lprefix = "(?:$opt->{prefix}-)?list";
+		$mprefix = "(?:$opt->{prefix}-)?";
+	}
+	else {
+		$lprefix = "list";
+		$mprefix = "";
 	}
-	my $prefix = defined $opt->{list_prefix} ? $opt->{list_prefix} : 'list';
 
-#::logDebug("region: opt:\n" . ::uneval($opt) . "\npage:" . substr($page,0,100));
+#::logDebug("region: opt:\n" . uneval($opt) . "\npage:" . substr($page,0,100));
 
-	if($opt->{ml} and ! defined $obj->{mv_matchlimit}) {
+	if($opt->{ml} and ! defined $obj->{mv_matchlimit} ) {
 		$obj->{mv_matchlimit} = $opt->{ml};
+		$obj->{mv_more_decade} = $opt->{md};
 		$obj->{matches} = scalar @{$obj->{mv_results}};
 		$obj->{mv_cache_key} = generate_key(substr($page,0,100));
 		$obj->{mv_first_match} = $opt->{fm} if $opt->{fm};
@@ -3873,15 +5116,37 @@
 
 	$opt->{prefix} = $obj->{prefix} if $obj->{prefix};
 
-	$page =~ s!$QR{more_list}! tag_more_list($1,$2,$3,$4,$5,$opt,$6)!ge;
-	$page =~ s!$QR{no_match}!
-					$obj->{matches} > 0 ? '' : $1
-					!ge;
-	$page =~ s!$QR{on_match}!
-					$obj->{matches} == 0 ? '' : $1
-					!ge;
-	$page =~ s:\[$prefix\]($Some)\[/$prefix\]:labeled_list($opt,$1,$obj):ige
-		or $page = labeled_list($opt,$page,$obj) ;
+	$Orig_prefix = $Prefix = $opt->{prefix} || 'item';
+
+	$B  = qr(\[$Prefix)i;
+	$E  = qr(\[/$Prefix)i;
+	$IB = qr(\[if[-_]$Prefix)i;
+	$IE = qr(\[/if[-_]$Prefix)i;
+
+	my $new;
+	$page =~   s!
+					\[ ( $mprefix  more[-_]list )  $Optx$Optx$Optx$Optx$Optx \]
+						($Some)
+					\[/\1\]
+				!
+					tag_more_list($2,$3,$4,$5,$6,$opt,$7)
+				!xige;
+	$page =~   s!
+					\[ ( $mprefix  on[-_]match )\]
+						($Some)
+					\[/\1\]
+				!
+					$obj->{matches} > 0 ? opt_region(0,0,1,$2,$opt) : ''
+				!xige;
+	$page =~   s!
+					\[ ( $mprefix  no[-_]match )\]
+						($Some)
+					\[/\1\]
+				!
+					$obj->{matches} > 0 ? '' : opt_region(0,0,1,$2,$opt)
+				!xige;
+	$page =~ s:\[($lprefix)\]($Some)\[/\1\]:labeled_list($opt,$2,$obj):ige
+		or $page = labeled_list($opt,$page,$obj);
 #::logDebug("past labeled_list");
 
     return $page;
@@ -3892,16 +5157,14 @@
 sub tag_loop_list {
 	my ($list, $opt, $text) = @_;
 
-#::logDebug("loop list opt=" . ::uneval($opt));
 	my $fn;
 	my @rows;
 
 	$opt->{prefix} = 'loop' unless defined $opt->{prefix};
 	$opt->{label}  =  "loop" . $List_it++ . $Global::Variable->{MV_PAGE}
 						unless defined $opt->{label};
-	my $delim;
 
-#::logDebug("list is: " . ::uneval($list) );
+#::logDebug("list is: " . uneval($list) );
 
 	## Thanks to Kaare Rasmussen for this suggestion
 	## about passing embedded Perl objects to a list
@@ -3915,15 +5178,21 @@
 	#	[loop list=`$Scratch->{ary}`] [loop-code]
 	#	[/loop]
 	if (ref $list) {
-#::logDebug("opt->list in: " . ::uneval($list) );
+#::logDebug("opt->list in: " . uneval($list) );
+		unless (ref $list eq 'ARRAY' and ref $list->[0] eq 'ARRAY') {
+			logError("loop was passed invalid list=`...` argument");
+			return;
+		}
 		my ($ary, $fh, $fa) = @$list;
 		$opt->{object}{mv_results} = $ary;
+		$opt->{object}{matches} = scalar @$ary;
 		$opt->{object}{mv_field_names} = $fa if $fa;
 		$opt->{object}{mv_field_hash} = $fh if $fh;
 		return region($opt, $text);
 	}
 
-  RESOLVELOOP: {
+	my $delim;
+
 	if($opt->{search}) {
 #::logDebug("loop resolve search");
 		if($opt->{more} and $Vend::More_in_progress) {
@@ -3936,35 +5205,68 @@
 	}
 	elsif ($opt->{file}) {
 #::logDebug("loop resolve file");
-		$list = Vend::Util::readfile($opt->{file});
+		$list = Vend::Util::readfile($opt->{file}, $Global::NoAbsolute);
 		$opt->{lr} = 1 unless
 						defined $opt->{lr}
 						or $opt->{quoted};
-		redo RESOLVELOOP;
 	}
-	elsif ($opt->{lr}) {
+	elsif ($opt->{extended}) {
+		###
+		### This returns
+		###
+		my ($view, $tab, $key) = split /:+/, $opt->{extended}, 3;
+		if(! $key) {
+			$key = $tab;
+			$tab = $view;
+			undef $view;
+		}
+		my $id = $tab;
+		$id .= "::$key" if $key;
+		my $meta = Vend::Table::Editor::meta_record(
+								$id,
+								$view,
+								$opt->{table},
+								$opt->{extended_only},
+								);
+		if(! $meta) {
+			$opt->{object} = {
+					matches		=> 1,
+					mv_results	=> [],
+					mv_field_names => [],
+			};
+		}
+		else {
+			$opt->{object} = {
+					matches		=> 1,
+					mv_results	=> [ $meta ],
+			};
+		}
+		return region($opt, $text);
+	}
+
+	if ($fn = $opt->{fn} || $opt->{mv_field_names}) {
+		$fn = [ grep /\S/, split /[\s,]+/, $fn ];
+	}
+
+	if ($opt->{lr}) {
 #::logDebug("loop resolve line");
 		$list =~ s/^\s+//;
 		$list =~ s/\s+$//;
-		last RESOLVELOOP unless $list;
-		$delim	 = $opt->{delimiter} || "\t";
-		my $splittor = $opt->{record_delim} || "\n";
-		if ($splittor eq "\n") {
-			$list =~ s/\r\n/\n/g;
-		}
+		if ($list) {
+			$delim = $opt->{delimiter} || "\t";
+			my $splittor = $opt->{record_delim} || "\n";
+			if ($splittor eq "\n") {
+				$list =~ s/\r\n/\n/g;
+			}
 
-		eval {
-			@rows = map { [ split /\Q$delim/o, $_ ] } split /\Q$splittor/, $list;
-		};
+			eval {
+				@rows = map { [ split /\Q$delim/o, $_ ] } split /\Q$splittor/, $list;
+			};
+		}
 	}
 	elsif($opt->{acclist}) {
 #::logDebug("loop resolve acclist");
-		if($fn = $opt->{fn} || $opt->{mv_field_names}) {
-			$fn = [ grep /\S/, split /[\s,]+/, $fn ];
-		}
-		else {
-			$fn = [ qw/option label/ ];
-		}
+		$fn = [ qw/option label/ ] unless $fn;
 		eval {
 			my @items = split /\s*,\s*/, $list;
 			for(@items) {
@@ -3973,35 +5275,47 @@
 				push @rows, [ $o, $l ];
 			}
 		};
-#::logDebug("rows:" . ::uneval(\@rows));
+#::logDebug("rows:" . uneval(\@rows));
 	}
 	elsif($opt->{quoted}) {
 #::logDebug("loop resolve quoted");
+		my @l = Text::ParseWords::shellwords($list);
+		produce_range(\@l) if $opt->{ranges};
 		eval {
-			@rows = map { [$_] } Text::ParseWords::shellwords($list);
+			@rows = map { [$_] } @l;
 		};
 	}
 	else {
 #::logDebug("loop resolve default");
 		$delim = $opt->{delimiter} || '[,\s]+';
+		my @l =  split /$delim/, $list;
+		produce_range(\@l) if $opt->{ranges};
 		eval {
-			@rows = map { [$_] } split /$delim/, $list;
+			@rows = map { [$_] } @l;
 		};
 	}
-  }
+
 	if($@) {
-		::logError("bad split delimiter in loop list: $@");
+		logError("bad split delimiter in loop list: $@");
 #::logDebug("loop resolve error $@");
 	}
-	$opt->{object} = { } if ! $opt->{object};
+
+	# head_skip pulls rows off the top, and uses the last row to
+	# set the field names if mv_field_names/fn option was not set
 	if ($opt->{head_skip}) {
 		my $i = 0;
-		$fn = shift(@rows) while $i++ < $opt->{head_skip};
+		my $last_row;
+		$last_row = shift(@rows) while $i++ < $opt->{head_skip};
+		$fn ||= $last_row;
 	}
-	$opt->{object}{mv_results} = \@rows;
-	$opt->{object}{mv_field_names} = $fn
-		if defined $fn;
-#::logDebug("loop object: " . ::uneval($opt));
+
+	$opt->{object} = {
+			matches		=> scalar(@rows),
+			mv_results	=> \@rows,
+			mv_field_names => $fn,
+	};
+	
+#::logDebug("loop object: " . uneval($opt));
 	return region($opt, $text);
 }
 
@@ -4027,6 +5341,10 @@
     if($page) {
 		$selector = 'passed in tag';
 	}
+	elsif(	$Vend::ForceFlypage ) {
+		$selector = $Vend::ForceFlypage;
+		undef $Vend::ForceFlypage;
+	}
 	elsif(	$selector = $Vend::Cfg->{PageSelectField}
 			and db_column_exists($base,$selector)
 		)
@@ -4036,14 +5354,25 @@
 
 	$selector = find_special_page('flypage')
 		unless $selector;
-
-    $page = readin($selector) unless defined $page;
 #::logDebug("fly_page: selector=$selector");
-    if(! defined $page) {
-		logError("attempt to display code=$code with bad flypage '$selector'");
-		return undef;
+
+	unless (defined $page) {
+		if($Global::NoAbsolute and (file_name_is_absolute($selector) or $selector =~ m#\.\./.*\.\.#)) {
+			::logError("Can't use file '%s' with NoAbsolute set", $selector);
+			::logGlobal({ level => 'auth'}, "Can't use file '%s' with NoAbsolute set", $selector);
+			return '';
+		}
+		$page = readin($selector);
+		if (defined $page) {
+			vars_and_comments(\$page);
+		} else {
+			logError("attempt to display code=$code with bad flypage '$selector'");
+			return undef;
+		}
 	}
 
+	# This allows access from embedded Perl
+	$Tmp->{flycode} = $code;
 # TRACK
 	$Vend::Track->view_product($code);
 # END TRACK
@@ -4075,19 +5404,22 @@
 		$item = { code => $code, quantity => ($quantity || 1) };
 	}
 
-	$Vend::Interpolate::item = $item;
 
 	($code, $extra) = ($item->{code}, $item->{mv_discount});
 
 	$Vend::Session->{discount} = {}
-		if $extra and !$Vend::Session->{discount};
+		if $extra and ! $Vend::Session->{discount};
 
-	return $price unless defined $Vend::Session->{discount};
+	return $price unless $Vend::Session->{discount};
 
 	$quantity = $item->{quantity};
 
+	$Vend::Interpolate::item = $item;
 	$Vend::Interpolate::q = $quantity || 1;
+	$Vend::Interpolate::s = $price;
+
 	my ($discount, $return);
+
 	for($code, 'ALL_ITEMS') {
 		next unless $discount = $Vend::Session->{discount}->{$_};
 		$Vend::Interpolate::s = $return = $price;
@@ -4098,16 +5430,13 @@
 		}
         $price = $return;
     }
-	$Vend::Interpolate::s = $price;
+
 	if($extra) {
-		$Vend::Interpolate::item = $item;
-        $return = $ready_safe->reval($extra);
-		if($@) {
-			$return = $price;
-			next;
+		EXTRA: {
+			$return = $ready_safe->reval($extra);
+			last EXTRA if $@;
+			$price = $return;
 		}
-		$price = $return;
-		undef $Vend::Interpolate::item;
 	}
 	return $price;
 }
@@ -4129,12 +5458,15 @@
 
 	my $subtotal = item_subtotal($item);
 
-	init_calc() unless $Calc_initialized;
+	init_calc() unless $Vend::Calc_initialized;
 	# Calculate any formalas found
 	foreach $formula (@formulae) {
 		next unless $formula;
-		$formula =~ s/\$q\b/$item->{quantity}/g; 
-		$formula =~ s/\$s\b/$subtotal/g; 
+		$Vend::Interpolate::q = $item->{quantity};
+		$Vend::Interpolate::s = $subtotal;
+		$Vend::Interpolate::item = $item;
+#		$formula =~ s/\$q\b/$item->{quantity}/g; 
+#		$formula =~ s/\$s\b/$subtotal/g; 
 		$cost = $ready_safe->reval($formula);
 		if($@) {
 			logError
@@ -4200,61 +5532,69 @@
 				|| Vend::Util::catfile($Vend::Cfg->{ProductDir},'shipping.asc');
 	}
 
-    open(SHIPPING, "< $file") or do {
-			if ($Vend::Cfg->{CustomShipping} =~ /^select\s+/i) {
-				($Vend::Cfg->{SQL_shipping} = 1, return)
-					if $Vend::Foreground;
-				$file = "$Vend::Cfg->{ScratchDir}/shipping.asc";
-				my $ary;
-				my $query = interpolate_html($Vend::Cfg->{CustomShipping});
-				eval {
-					$ary = query($query, { wantarray => 1} );
-				};
-				if(! ref $ary) {
-					logError("Could not make shipping query %s: %s" ,
-								$Vend::Cfg->{CustomShipping},
-								$@);
-					return undef;
-				}
-				my $out;
-				for(@$ary) {
-					$out .= join "\t", @$_;
-					$out .= "\n";
-					Vend::Util::writefile(">$file", $out);
-				}
-				open(SHIPPING, "< $file") or do {
-					logError("Could not make shipping query %s: %s" ,
-								$Vend::Cfg->{CustomShipping},
-								$!);
-					return undef;
-				};
-			}
-			else {
-				logError("Could not open shipping file %s: %s" , $file, $!)
-					if $Vend::Cfg->{CustomShipping};
-				return undef;
-			}
+	my @flines = split /\n/, readfile($file);
+	if ($Vend::Cfg->{CustomShipping} =~ /^select\s+/i) {
+		($Vend::Cfg->{SQL_shipping} = 1, return)
+			if $Global::Foreground;
+		my $ary;
+		my $query = interpolate_html($Vend::Cfg->{CustomShipping});
+		eval {
+			$ary = query($query, { wantarray => 1} );
 		};
+		if(! ref $ary) {
+			logError("Could not make shipping query %s: %s" ,
+						$Vend::Cfg->{CustomShipping},
+						$@);
+			return undef;
+		}
+		my $out;
+		for(@$ary) {
+			push @flines, join "\t", @$_;
+		}
+	}
+	
 	$Vend::Cfg->{Shipping_desc} = {}
 		if ! $Vend::Cfg->{Shipping_desc};
 	my %seen;
 	my $append = '00000';
 	my @line;
+	my $prev = '';
+	my $waiting;
 	my @shipping;
 	my $first;
-    while(<SHIPPING>) {
-		chomp;
+    for(@flines) {
+
+		# Strip CR, we hope
+		s/\s+$//;
+
+		# Handle continued lines
 		if(s/\\$//) {
-			$_ .= <SHIPPING>;
-			redo;
+			$prev .= $_;
+			next;
+		}
+		elsif($waiting) {
+			if($_ eq $waiting) {
+				undef $waiting;
+				$_ = $prev;
+				$prev = '';
+				s/\s+$//;
+			}
+			else {
+				$prev .= "$_\n";
+				next;
+			}
+		}
+		elsif($prev) {
+			$_ = "$prev$_";
+			$prev = '';
 		}
-		elsif (s/<<(\w+)$//) {
-			my $mark = $1;
-			my $line = $_;
-			$line .= Vend::Config::read_here(\*SHIPPING, $mark);
-			$_ = $line;
-			redo;
+
+		if (s/<<(\w+)$//) {
+			$waiting = $1;
+			$prev .= $_;
+			next;
 		}
+
 		next unless /\S/;
 		s/\s+$//;
 		if(/^[^\s:]+\t/) {
@@ -4309,26 +5649,43 @@
 					$line[OPT]->{$k} = $v;
 				}
 			};
-			::logError(
+			logError(
 				"bad shipping index %s for mode %s in $file",
 				$k,
 				$line[0],
 				) if $@;
 		}
 	}
-    close SHIPPING;
 
 	push @shipping, [ @line ]
 		if @line;
 
+	if($waiting) {
+		logError(
+			"Failed to find end-of-line termination '%s' in shipping read",
+			$waiting,
+		);
+	}
+
 	my $row;
 	my %zones;
+	my %def_opts;
+	$def_opts{PriceDivide} = 1 if $Vend::Cfg->{Locale};
+
 	foreach $row (@shipping) {
 		my $cost = $row->[COST];
 		my $o = get_option_hash($row->[OPT]);
+		for(keys %def_opts) {
+			$o->{$_} = $def_opts{$_}
+				unless defined $o->{$_};
+		}
 		$row->[OPT] = $o;
 		my $zone;
-		if ($zone = $o->{zone} or $cost =~ s/^\s*c\s+(\w+)\s*//) {
+		if ($cost =~ s/^\s*o\s+//) {
+			$o = get_option_hash($cost);
+			%def_opts = %$o;
+		}
+		elsif ($zone = $o->{zone} or $cost =~ s/^\s*c\s+(\w+)\s*//) {
 			$zone = $1 if ! $zone;
 			next if defined $zones{$zone};
 			my $ref;
@@ -4397,7 +5754,7 @@
 			}
 			my (@zone) = grep /\S/, split /[\r\n]+/, $ref->{zone_data};
 			if($zone[0] !~ /\t/) {
-				my $len = $ref->{str_len} || 3;
+				my $len = $ref->{str_length} || 3;
 				@zone = grep /\S/, @zone;
 				@zone = grep /^[^"]/, @zone;
 				$zone[0] =~ s/[^\w,]//g;
@@ -4424,114 +5781,6 @@
 
 *custom_shipping = \&shipping;
 
-# Returns 'SELECTED' when a value is present on the form
-# Must match exactly, but NOT case-sensitive
-
-sub tag_selected {
-	my ($field,$value,$opt) = @_;
-	$value = '' unless defined $value;
-	my $ref = $opt->{cgi} ? $CGI::values{$field} : $::Values->{$field};
-	return ' SELECTED' if ! length($ref) and $opt->{default};
-
-	if(! $opt->{case}) {
-		$ref = lc($ref);
-		$value = lc($value);
-	}
-
-	my $r = '';
-
-	return ' SELECTED' if $ref eq $value;
-	if ($opt->{multiple}) {
-		my $regex = quotemeta $value;
-		return ' SELECTED' if $ref =~ /(?:^|\0)$regex(?:$|\0)/i;
-	}
-
-	return '';
-}
-
-sub tag_checked {
-	my ($field,$value,$opt) = @_;
-
-	$value = 'on' unless defined $value;
-
-	my $ref = $opt->{cgi} ? $CGI::values{$field} : $::Values->{$field};
-	return 'CHECKED' if ! length($ref) and $opt->{default};
-
-	if(! $opt->{case}) {
-		$ref = lc($ref);
-		$value = lc($value);
-	}
-
-	return 'CHECKED' if $ref eq $value;
-
-	if ($opt->{multiple}) {
-		my $regex = quotemeta $value;
-		return 'CHECKED' if $ref =~ /(?:^|\0)$regex(?:$|\0)/i;
-	}
-
-	return '';
-}
-
-# Returns an href to place an order for the product PRODUCT_CODE.
-# If AlwaysSecure is set, goes by the page accessed, otherwise 
-# if a secure order has been started (with a call to at least
-# one secure_vendUrl), then it will be given the secure URL
- 
-sub tag_order {
-    my($code,$quantity,$opt) = @_;
-	$opt = {} unless $opt;
-    my($r);
-	my @parms = (
-					"mv_action=refresh",
-				  );
-
-	push(@parms, "mv_order_item=$code");
-	push(@parms, "mv_order_mv_ib=$opt->{base}")
-		if($opt->{base});
-
-	push(@parms, "mv_order_quantity=$quantity")
-		if($quantity);
-
-	$opt->{form} = join "\n", @parms;
-
-	$opt->{page} = find_special_page('order')
-		unless $opt->{page};
-
-	return form_link($opt->{area}, $opt->{arg}, $opt)
-		if $opt->{area};
-	return tag_page($opt->{page}, $opt->{arg}, $opt);
-}
-
-# Sets the value of a discount field
-sub tag_discount {
-	my($code, $opt, $value) = @_;
-
-	# API compatibility
-	if(! ref $opt) {
-		$value = $opt;
-		$opt = {};
-	}
-
-	if($opt->{subtract}) {
-		$value = <<EOF;
-my \$tmp = \$s - $opt->{subtract};
-\$tmp = 0 if \$tmp < 0;
-return \$tmp;
-EOF
-	}
-	elsif ($opt->{level}) {
-		$value = <<EOF;
-return (\$s * \$q) if \$q < $opt->{level};
-my \$tmp = \$s / \$q;
-return \$s - \$tmp;
-EOF
-	}
-    $Vend::Session->{discount}{$code} = $value;
-	delete $Vend::Session->{discount}->{$code}
-		unless (defined $value and $value);
-	return '';
-}
-
 # Sets the value of a scratchpad field
 sub set_scratch {
 	my($var,$val) = @_;
@@ -4547,24 +5796,6 @@
 	return '';
 }
 
-# Returns the value of a scratchpad field named VAR.
-sub tag_scratchd {
-	my $var = shift;
-	return delete $::Scratch->{$var};
-}
-
-# Returns the value of a scratchpad field named VAR.
-sub tag_scratch {
-	my $var = shift;
-    return $::Scratch->{$var};
-}
-
-sub tag_lookup {
-	my($selector,$field,$key,$rest) = @_;
-	return $rest if (defined $rest and $rest);
-	return tag_data($selector,$field,$key);
-}
-
 sub timed_build {
     my $file = shift;
     my $opt = shift;
@@ -4580,11 +5811,39 @@
 		$abort = 1 if ! $saved_file || $file =~ m:MM=:;
 	}
 
-	return Vend::Interpolate::interpolate_html(shift)
-		if $abort
-		or !  $CGI::cookie
-		or $Vend::BuildingPages
-		or ! $opt->{login} && $Vend::Session->{logged_in};
+	$opt->{login} = 1 if $opt->{auto};
+
+	my $save_scratch;
+	if($opt->{new} and $Vend::new_session and !$Vend::Session->{logged_in}) {
+#::logDebug("we are new");
+		$save_scratch = $::Scratch;
+		$Vend::Cookie = 1;
+		$Vend::Session->{scratch} = { %{$Vend::Cfg->{ScratchDefault}}, mv_no_session_id => 1, mv_no_count => 1, mv_force_cache => 1 };
+		
+	}
+	else {
+		return Vend::Interpolate::interpolate_html($_[0])
+			if $abort
+			or ( ! $opt->{force}
+					and
+					(   ! $Vend::Cookie
+						or $Vend::BuildingPages
+						or ! $opt->{login} && $Vend::Session->{logged_in}
+					)
+				);
+	}
+	
+	if($opt->{auto}) {
+		$opt->{login} =    1 unless defined $opt->{login};
+		$opt->{minutes} = 60 unless defined $opt->{minutes};
+		$opt->{login} = 1;
+		my $dir = "$Vend::Cfg->{ScratchDir}/auto-timed";
+		if(! -d $dir) {
+			require File::Path;
+			File::Path::mkpath($dir);
+		}
+		$file = "$dir/" . generate_key(@_);
+	}
 
     if($opt->{noframes} and $Vend::Session->{frames}) {
         return '';
@@ -4603,7 +5862,7 @@
 		if($saved_file) {
 			$file = $saved_file;
 			$file =~ s:^scan/::;
-			$file = ::generate_key($file);
+			$file = generate_key($file);
 			$file = "scan/$file";
 		}
 		else {
@@ -4629,12 +5888,19 @@
 		$secs = Vend::Config::time_to_seconds($opt->{period});
 	}
 
+    $file = Vend::Util::escape_chars($file);
+    if(!$opt->{auto} and $Global::NoAbsolute and (file_name_is_absolute($file) or $file =~ m#\.\./.*\.\.#)) {
+		::logError("Can't use file '%s' with NoAbsolute set", $file);
+		::logGlobal({ level => 'auth'}, "Can't use file '%s' with NoAbsolute set", $file);
+		return '';
+    }
+
     if( ! -f $file or $secs && (stat(_))[9] < (time() - $secs) ) {
         my $out = Vend::Interpolate::interpolate_html(shift);
 		$opt->{umask} = '22' unless defined $opt->{umask};
         Vend::Util::writefile(">$file", $out, $opt );
 # STATICPAGE
-		if ($Vend::Cfg->{StaticDBM} and ::tie_static_dbm(1) ) {
+		if ($Vend::Cfg->{StaticDBM} and Vend::Session::tie_static_dbm(1) ) {
 			if ($opt->{scan}) {
 				$saved_file =~ s!=([^/]+)=!=$1%3d!g;
 				$saved_file =~ s!=([^/]+)-!=$1%2d!g;
@@ -4646,15 +5912,17 @@
 			}
 		}
 # END STATICPAGE
+		$Vend::Session->{scratch} = $save_scratch if $save_scratch;
         return $out;
     }
-    else {        return Vend::Util::readfile($file);    }
+	$Vend::Session->{scratch} = $save_scratch if $save_scratch;
+	return Vend::Util::readfile($file);
 }
 
 sub update {
 	my ($func, $opt) = @_;
 	if($func eq 'quantity') {
-		::update_quantity();
+		Vend::Order::update_quantity();
 	}
 	elsif($func eq 'cart') {
 		my $cart;
@@ -4665,263 +5933,27 @@
 			$cart = $Vend::Items;
 		}
 		return if ! ref $cart;
-		Vend::Cart::toss_cart($cart);
+		Vend::Cart::toss_cart($cart, $opt->{name});
 	}
 	elsif ($func eq 'process') {
-		::do_process();
+		Vend::Dispatch::do_process();
 	}
 	elsif ($func eq 'values') {
-		::update_user();
+		Vend::Dispatch::update_user();
 	}
 	elsif ($func eq 'data') {
-		::update_data();
+		Vend::Data::update_data();
 	}
 	return;
 }
 
 my $Ship_its = 0;
 
-sub tag_error {
-	my($var, $opt) = @_;
-	$Vend::Session->{errors} = {}
-		unless defined $Vend::Session->{errors};
-	my $err_ref = $Vend::Session->{errors};
-	my $text;
-	$text = $opt->{text} if $opt->{text};
-	my @errors;
-	my $found_error = '';
-#::logDebug("tag_error: var=$var text=$text opt=" . ::uneval($opt));
-#::logDebug("tag_error: var=$var text=$text");
-	if($opt->{all}) {
-		$opt->{joiner} = "\n" unless defined $opt->{joiner};
-		for(sort keys %$err_ref) {
-			my $err = $err_ref->{$_};
-			delete $err_ref->{$_} unless $opt->{keep};
-			next unless $err;
-			$found_error++;
-			my $string = '';
-			$string .= "$_: " if $opt->{show_var};
-			$string .= $err;
-			push @errors, $string;
-		}
-#::logDebug("error all=1 found=$found_error contents='@errors'");
-		return $found_error unless $text || $opt->{show_error};
-		$text .= "%s" if $text !~ /\%s/;
-		$text = pull_else($text, $found_error);
-		return sprintf $text, join($opt->{joiner}, @errors);
-	}
-	$found_error = ! (not $err_ref->{$var});
-	my $err = $err_ref->{$var} || '';
-	delete $err_ref->{$var} unless $opt->{keep};
-#::logDebug("error found=$found_error contents='$err'");
-	return !(not $found_error)
-		unless $opt->{std_label} || $text || $opt->{show_error};
-	if($opt->{std_label}) {
-		if(defined $::Variable->{MV_ERROR_STD_LABEL}) {
-			$text = $::Variable->{MV_ERROR_STD_LABEL};
-		}
-		else {
-			$text = <<EOF;
-<FONT COLOR=RED>{LABEL} <SMALL><I>(%s)</I></SMALL></FONT>
-[else]{REQUIRED <B>}{LABEL}{REQUIRED </B>}[/else]
-EOF
-		}
-		$text =~ s/{LABEL}/$opt->{std_label}/g;
-		$text =~ s/{REQUIRED\s+([^}]*)}/$opt->{required} ? $1 : ''/ge;
-	}
-	$text = '' unless defined $text;
-	$text .= '%s' unless $text =~ /\%s/;
-	$text = pull_else($text, $found_error);
-	return sprintf($text, $err);
-}
-
-sub tag_column {
-	my($spec,$text) = @_;
-	my($append,$f,$i,$line,$usable);
-	my(%def) = qw(
-					width 0
-					spacing 1
-					gutter 2
-					wrap 1
-					html 0
-					align left
-				);
-	my(%spec)	= ();
-	my(@out)	= ();
-	my(@lines)	= ();
-	
-	$spec =~ s/\n/ /g;
-	$spec =~ s/^\s+//;
-	$spec =~ s/\s+$//;
-	$spec = lc $spec;
-
-	$spec =~ s/\s*=\s*/=/;
-	$spec =~ s/^(\d+)/width=$1/;
-	%spec = split /[\s=]+/, $spec;
-
-	for(keys %def) {
-		$spec{$_} = $def{$_} unless defined $spec{$_};
-	}
-
-	if($spec{'html'} && $spec{'wrap'}) {
-		::logError("tag_column: can't have 'wrap' and 'html' specified at same time.");
-		$spec{wrap} = 0;
-	}
-
-	$text =~ s/\s+/ /g;
-
-	my $len = sub {
-		my($txt) = @_;
-		if (1 or $spec{html}) {
-			$txt =~
-			s{ <
-				   (
-					 [^>'"] +
-						|
-					 ".*?"
-						|
-					 '.*?'
-					) +
-				>
-			}{}gsx;
-		}
-		return length($txt);
-	};
-
-	$usable = $spec{'width'} - $spec{'gutter'};
-	return "BAD_WIDTH" if  $usable < 1;
-	
-	if($spec{'align'} =~ /^l/) {
-		$f = sub {
-					$_[0] .
-					' ' x ($usable - $len->($_[0])) .
-					' ' x $spec{'gutter'};
-					};
-	}
-	elsif($spec{'align'} =~ /^r/) {
-		$f = sub {
-					' ' x ($usable - $len->($_[0])) .
-					$_[0] .
-					' ' x $spec{'gutter'};
-					};
-	}
-	elsif($spec{'align'} =~ /^i/) {
-		$spec{'wrap'} = 0;
-		$usable = 9999;
-		$f = sub { @_ };
-	}
-	else {
-		return "BAD JUSTIFICATION SPECIFICATION: $spec{'align'}";
-	}
-
-	$append = '';
-	if($spec{'spacing'} > 1) {
-		$append .= "\n" x ($spec{'spacing'} - 1);
-	}
-
-	if(is_yes($spec{'wrap'}) and length($text) > $usable) {
-		@lines = wrap($text,$usable);
-	}
-	elsif($spec{'align'} =~ /^i/) {
-		$lines[0] = ' ' x $spec{'width'};
-		$lines[1] = $text . ' ' x $spec{'gutter'};
-	}
-	elsif (! $spec{'html'}) {
-		$lines[0] = substr($text,0,$usable);
-	}
-
-	foreach $line (@lines) {
-		push @out , &{$f}($line);
-		for($i = 1; $i < $spec{'spacing'}; $i++) {
-			push @out, '';
-		}
-	}
-	@out;
-}
-
-sub wrap {
-    my ($str, $width) = @_;
-    my @a = ();
-    my ($l, $b);
-
-    for (;;) {
-        $str =~ s/^ +//;
-        $l = length($str);
-        last if $l == 0;
-        if ($l <= $width) {
-            push @a, $str;
-            last;
-        }
-        $b = rindex($str, " ", $width - 1);
-        if ($b == -1) {
-            push @a, substr($str, 0, $width);
-            $str = substr($str, $width);
-        }
-        else {
-            push @a, substr($str, 0, $b);
-            $str = substr($str, $b + 1);
-        }
-    }
-    return @a;
-}
-
-sub tag_row {
-    my($width,$text) = @_;
-	my($col,$spec);
-	my(@lines);
-	my(@len);
-	my(@out);
-	my($i,$j,$k);
-	my($x,$y,$line);
-
-	$i = 0;
-	#while( $text =~ s!$QR{col}!!    ) {
-	while( $text =~ s!\[col(?:umn)?\s+
-				 		([^\]]+)
-				 		\]
-				 		([\000-\377]*?)
-				 		\[/col(?:umn)?\] !!ix    ) {
-		$spec = $1;
-		$col = $2;
-		$lines[$i] = [];
-		@{$lines[$i]} = tag_column($spec,$col);
-		# Discover X dimension
-		$len[$i] = length(${$lines[$i]}[0]);
-		if(defined ${$lines[$i]}[1] and ${$lines[$i]}[1] =~ /^<\s*input\s+/i) {
-			shift @{$lines[$i]};
-		}
-		$i++;
-	}
-	my $totlen = 0;
-	for(@len) { $totlen += $_ }
-	if ($totlen > $width) {
-		return " B A D   R O W  S P E C I F I C A T I O N - columns too wide.\n"
-	}
-
-	# Discover y dimension
-	$j = $#{$lines[0]};
-	for ($k = 1; $k < $i; $k++) {
-		$j = $#{$lines[$k]} > $j ? $#{$lines[$k]} : $j;
-	}
-
-	for($y = 0; $y <= $j; $y++) {
-		$line = '';
-		for($x = 0; $x < $i; $x++) {
-			if(defined ${$lines[$x]}[$y]) {
-				$line .= ${$lines[$x]}[$y];
-				$line =~ s/\s+$//
-					if ($i - $x) == 1;
-			}
-			elsif (($i - $x) > 1) {
-			  	$line  .= ' ' x $len[$x];
-			}
-			else {
-				$line =~ s/\s+$//;
-			}
-		}
-		push @out, $line;
-	}
-	join "\n", @out;
+sub push_warning {
+	$Vend::Session->{warnings} = [$Vend::Session->{warnings}]
+		if ! ref $Vend::Session->{warnings};
+	push @{$Vend::Session->{warnings}}, errmsg(@_);
+	return;
 }
 
 sub shipping {
@@ -4947,13 +5979,13 @@
 	else {
 		@bin = @$Vend::Items;
 	}
-#::logDebug("doing shipping, mode=$mode bin=" . ::uneval(\@bin));
+#::logDebug("doing shipping, mode=$mode bin=" . uneval(\@bin));
 
 	$Vend::Session->{ship_message} = '' if $opt->{reset_message};
 
 	my($field, $code, $i, $total, $cost, $multiplier, $formula, $error_message);
 
-	my $ref = $Vend::Cfg;
+#	my $ref = $Vend::Cfg;
 #
 #	if(defined $Vend::Cfg->{Shipping_criterion}->{$mode}) {
 #		$ref = $Vend::Cfg;
@@ -4988,16 +6020,16 @@
 	my @lines;
 	@lines = grep $_->[0] =~ /^$mode/, @{$Vend::Cfg->{Shipping_line}};
 	goto SHIPFORMAT unless @lines;
-#::logDebug("shipping lines selected: " . ::uneval(\@lines));
+#::logDebug("shipping lines selected: " . uneval(\@lines));
 	my $q;
 	if($lines[0][QUERY]) {
 		my $q = interpolate_html($lines[0][QUERY]);
 		$q =~ s/=\s+?\s*/= '$mode' /g;
 		$q =~ s/\s+like\s+?\s*/ LIKE '%$mode%' /ig;
-		my $ary = query($q);
+		my $ary = query($q, { wantarray => 1 });
 		if(ref $ary) {
 			@lines = @$ary;
-#::logDebug("shipping lines reselected with SQL: " . ::uneval(\@lines));
+#::logDebug("shipping lines reselected with SQL: " . uneval(\@lines));
 		}
 		else {
 #::logDebug("shipping lines failed reselect with SQL query '$q'");
@@ -5006,7 +6038,7 @@
 
 	my $o = get_option_hash($lines[0][OPT]) || {};
 
-#::logDebug("shipping opt=" . ::uneval($o));
+#::logDebug("shipping opt=" . uneval($o));
 
 	if($o->{limit}) {
 		$o->{filter} = '(?i)\s*[1ty]' if ! $o->{filter};
@@ -5018,7 +6050,7 @@
 
 	tag_cart('mv_shipping');
 
-#::logDebug("Check 2, must get to FINAL. Vend::Items=" . ::uneval($Vend::Items) . " main=" . ::uneval($::Carts->{main}) . " mv_shipping=" . ::uneval($::Carts->{mv_shipping}));
+#::logDebug("Check 2, must get to FINAL. Vend::Items=" . uneval($Vend::Items) . " main=" . uneval($::Carts->{main}) . " mv_shipping=" . uneval($::Carts->{mv_shipping}));
 
 	if($o->{perl}) {
 		$Vend::Interpolate::Shipping   = $lines[0];
@@ -5082,15 +6114,30 @@
 	}
 	else {
 #::logDebug("standard field selection");
-		unless (column_exists $field) {
+	    my $use_modifier;
+
+	    if ($::Variable->{MV_SHIP_MODIFIERS}){
+			my @pieces = grep {$_ = quotemeta $_} split(/[\s,|]+/,$::Variable->{MV_SHIP_MODIFIERS});
+			my $regex = join('|',@pieces);
+			$use_modifier = 1 if ($regex && $field =~ /^($regex)$/);
+	    }
+
+	    my $col_checked = 0;
+	    foreach my $item (@$Vend::Items){
+		my $value;
+		if ($use_modifier && defined $item->{$field}){
+		    $value = $item->{$field};
+		}else{
+		    unless ($col_checked++ || column_exists $field){
 			logError("Custom shipping field '$field' doesn't exist. Returning 0");
+			$total = 0;
 			goto SHIPFORMAT;
+		    }
+		    my $base = $item->{mv_ib} || $Vend::Cfg->{ProductFiles}[0];
+		    $value = tag_data($base, $field, $item->{code});
 		}
-    	foreach my $item (@$Vend::Items) {
-			my $base = $item->{mv_ib} || $Vend::Cfg->{ProductFiles}[0];
-			my $value = tag_data($base, $field, $item->{code});
-			$total += $value * $item->{quantity};
-		}
+		$total += ($value * $item->{quantity});
+	    }
 	}
 
 	# We will LAST this loop and go to SHIPFORMAT if a match is found
@@ -5164,9 +6211,6 @@
 			}
 
 			$cost = tag_ups($type,$geo,$total,$zselect,$o);
-			FIGURE: {
-				last FIGURE unless $cost;
-			}
 			$final += $cost;
 			last SHIPIT unless $o->{continue};
 		}
@@ -5233,6 +6277,9 @@
 		$Vend::Items = $save;
 #::logDebug("Check FINAL. Vend::Items=$Vend::Items main=$::Carts->{main}");
 		last SHIPFORMAT unless defined $final;
+#::logDebug("ship options: " . uneval($o) );
+		$final /= $Vend::Cfg->{PriceDivide}
+			if $o->{PriceDivide} and $Vend::Cfg->{PriceDivide} != 0;
 		unless ($o->{free}) {
 			return '' if $final == 0;
 			$o->{adder} =~ s/\bx\b/$final/g;
@@ -5255,16 +6302,15 @@
 		}
 		return $final unless $opt->{label};
 		my $number;
-		if($o->{free}) {
-			$number = $opt->{free}
-				if $final == 0;
+		if($o->{free} and $final == 0) {
+			$number = $opt->{free};
 		}
 		else {
 			return $final unless $opt->{label};
+#::logDebug("actual options: " . uneval($o));
 			$number = Vend::Util::currency( 
 											$final,
 											$opt->{noformat},
-											$row->[OPT]->{PriceDivide},
 									);
 		}
 		my $label = $opt->{format} || '<OPTION VALUE="%M"%S>%D (%F)';
@@ -5301,8 +6347,6 @@
 	return undef;
 }
 
-*custom_shipping = \&shipping;
-
 sub taxable_amount {
 	my($cart) = @_;
     my($taxable, $i, $code, $item, $tmp, $quantity);
@@ -5331,9 +6375,23 @@
 		}
     }
 
+	if (defined $Vend::Session->{discount}->{ENTIRE_ORDER}) {
+		$Vend::Interpolate::q = tag_nitems();
+		$Vend::Interpolate::s = $taxable;
+		my $cost = $Vend::Interpolate::ready_safe->reval(
+							 $Vend::Session->{discount}{ENTIRE_ORDER},
+						);
+		if($@) {
+			logError
+				"Discount ENTIRE_ORDER has bad formula. Returning normal subtotal.";
+			$cost = $taxable;
+		}
+		$taxable = $cost;
+	}
+
 	$Vend::Items = $save if defined $save;
 
-	$taxable;
+	return $taxable;
 }
 
 sub tag_handling {
@@ -5361,7 +6419,7 @@
 				? ($::Values->{mv_handling})
 				: ($::Values->{mv_shipmode} || 'default');
 	}
-	$Vend::Cfg->{shipping_line} = [] 
+	$Vend::Cfg->{Shipping_line} = [] 
 		if $opt->{reset_modes};
 	read_shipping(undef, $opt) if $Vend::Cfg->{SQL_shipping};
 	read_shipping(undef, $opt) if $opt->{add};
@@ -5375,17 +6433,32 @@
 			if tag_shipping($::Values->{mv_shipmode});
 	}
 	if($opt->{label}) {
+		$out = '';
 		for(@modes) {
 			$out .= shipping($_, $opt);
 		}
 	}
 	else {
-		$out = 0;
-		for(@modes) {
-			$out += shipping($_, $opt);
+		### If the user has assigned to shipping or handling,
+		### we use their value
+		if($Vend::Session->{assigned}) {
+			my $tag = $opt->{handling} ? 'handling' : 'shipping';
+			$out = $Vend::Session->{assigned}{$tag} 
+				if defined $Vend::Session->{assigned}{$tag} 
+				&& length( $Vend::Session->{assigned}{$tag});
+		}
+		### If no assignment has been made, we read the shipmodes
+		### and use their value
+		unless (defined $out) {
+			$out = 0;
+			for(@modes) {
+				$out += shipping($_, $opt) || 0;
+			}
 		}
 		$out = Vend::Util::round_to_frac_digits($out);
-		$out = currency($out, $opt->{noformat}, $opt->{convert});
+		## Conversion would have been done above, force to 0, as
+		## found by Frederic Steinfels
+		$out = currency($out, $opt->{noformat}, 0);
 	}
 	return $out unless $opt->{hide};
 	return;
@@ -5394,6 +6467,12 @@
 
 sub fly_tax {
 	my ($area) = @_;
+
+	if(my $country_check = $::Variable->{TAXCOUNTRY}) {
+		$country_check =~ /\b$::Values->{country}\b/
+			or return 0;
+	}
+
 	if(! $area) {
 		my $zone = $Vend::Cfg->{SalesTax};
 		while($zone =~ m/(\w+)/g) {
@@ -5430,40 +6509,178 @@
 	return $amount * $rate;
 }
 
+sub tax_vat {
+	my($type, $opt) = @_;
+#::logDebug("entering VAT, opts=" . uneval($opt));
+	my $cfield = $::Variable->{MV_COUNTRY_FIELD} || 'country';
+	my $country = $opt->{country} || $::Values->{$cfield};
+
+	return 0 if ! $country;
+	my $ctable   = $opt->{country_table}
+				|| $::Variable->{MV_COUNTRY_TABLE}
+				|| 'country';
+	my $c_taxfield   = $opt->{country_tax_field}
+				|| $::Variable->{MV_COUNTRY_TAX_FIELD}
+				|| 'tax';
+#::logDebug("ctable=$ctable c_taxfield=$c_taxfield country=$country");
+	$type ||= tag_data($ctable, $c_taxfield, $country)
+		or return 0;
+#::logDebug("tax type=$type");
+	$type =~ s/^\s+//;
+	$type =~ s/\s+$//;
+
+	my @taxes;
+
+	if($type =~ /^(\w+)$/) {
+		my $sfield = $1;
+		my $state  = $opt->{state} || $::Values->{$sfield};
+		return 0 if ! $state;
+		my $stable   = $opt->{state_table}
+					|| $::Variable->{MV_STATE_TABLE}
+					|| 'state';
+		my $s_taxfield   = $opt->{state_tax_field}
+					|| $::Variable->{MV_STATE_TAX_FIELD}
+					|| 'tax';
+		my $s_taxtype   = $opt->{tax_type_field} 
+					|| $::Variable->{MV_TAX_TYPE_FIELD}
+					|| 'tax_name';
+		my $db = database_exists_ref($stable)
+			or return 0;
+		my $addl = '';
+		if($opt->{tax_type}) {
+			$addl = " AND $s_taxtype = " .
+					$db->quote($opt->{tax_type}, $s_taxtype);
+		}
+		my $q = qq{
+						SELECT $s_taxfield FROM $stable
+						WHERE  $cfield = '$country'
+						AND    $sfield = '$state'
+						$addl
+					};
+#::logDebug("tax state query=$q");
+		my $ary;
+		eval {
+			$ary = $db->query($q);
+		};
+		if($@) {
+			logError("error on state tax query %s", $q);
+		}
+#::logDebug("query returns " . uneval($ary));
+		return 0 unless ref $ary;
+		for(@$ary) {
+			next unless $_->[0];
+			push @taxes, $_->[0];
+	}
+	}
+	else {
+		@taxes = $type;
+	}
+
+	my $total = 0;
+	foreach my $t (@taxes) {
+		$t =~ s/^\s+//;
+		$t =~ s/\s+$//;
+		if ($t =~ /simple:(.*)/) {
+			$total += fly_tax($::Values->{$1});
+			next;
+		}
+		elsif ($t =~ /handling:(.*)/) {
+		my @modes = grep /\S/, split /[\s,]+/, $1;
+		
+		my $cost = 0;
+		$cost += tag_handling($_) for @modes;
+			$total += $cost;
+			next;
+	}
+	my $tax;
+#::logDebug("tax type=$t");
+		if($t =~ /^(\d+(?:\.\d+)?)\s*(\%)$/) {
+		my $rate = $1;
+		$rate /= 100 if $2;
+		my $amount = Vend::Interpolate::taxable_amount();
+			$total += ($rate * $amount);
+	}
+	else {
+			$tax = Vend::Util::get_option_hash($t);
+	}
+#::logDebug("tax hash=" . uneval($tax));
+	my $pfield   = $opt->{tax_category_field}
+				|| $::Variable->{MV_TAX_CATEGORY_FIELD}
+				|| 'tax_category';
+	my @pfield = split /:+/, $pfield;
+
+	for my $item (@$Vend::Items) {
+			my $rhash = tag_data($item->{mv_ib}, undef, $item->{code}, { hash => 1});
+		my $cat = join ":", @{$rhash}{@pfield};
+		my $rate = defined $tax->{$cat} ? $tax->{$cat} : $tax->{default};
+#::logDebug("item $item->{code} cat=$cat rate=$rate");
+		$rate =~ s/\s*%\s*$// and $rate /= 100;
+		next if $rate <= 0;
+		my $sub = Vend::Data::item_subtotal($item);
+#::logDebug("item $item->{code} subtotal=$sub");
+		$total += $sub * $rate;
+#::logDebug("tax total=$total");
+	}
+	}
+	return $total;
+}
+
 # Calculate the sales tax
 sub salestax {
-	my($cart) = @_;
+	my($cart, $opt) = @_;
+
+	$opt ||= {};
+
 	my($save);
+	### If the user has assigned to salestax,
+	### we use their value come what may, no rounding
+	if($Vend::Session->{assigned}) {
+		return $Vend::Session->{assigned}{salestax} 
+			if defined $Vend::Session->{assigned}{salestax} 
+			&& length( $Vend::Session->{assigned}{salestax});
+	}
 
     if ($cart) {
         $save = $Vend::Items;
         tag_cart($cart);
     }
 
-	my $amount = taxable_amount();
-	my($r, $code);
-	# Make it upper case for state and overseas postal
-	# codes, zips don't matter
-	my(@code) = map { (uc $::Values->{$_}) || '' }
-					split /[,\s]+/, $Vend::Cfg->{SalesTax};
-	push(@code, 'DEFAULT');
-
+#::logDebug("salestax entered, cart=$cart");
 	my $tax_hash;
-	if($Vend::Cfg->{SalesTaxFunction}) {
+	my $cost;
+	if($Vend::Cfg->{SalesTax} eq 'multi') {
+		$cost = tax_vat($opt->{type}, $opt);
+	}
+	elsif($Vend::Cfg->{SalesTax} =~ /\[/) {
+		$cost = interpolate_html($Vend::Cfg->{SalesTax});
+	}
+	elsif($Vend::Cfg->{SalesTaxFunction}) {
 		$tax_hash = tag_calc($Vend::Cfg->{SalesTaxFunction});
-#::logDebug("found custom tax function: " . ::uneval($tax_hash));
+#::logDebug("found custom tax function: " . uneval($tax_hash));
 	}
 	else {
 		$tax_hash = $Vend::Cfg->{SalesTaxTable};
-#::logDebug("looking for tax function: " . ::uneval($tax_hash));
+#::logDebug("looking for tax function: " . uneval($tax_hash));
 	}
 
-	if(! $tax_hash) {
-		my $cost = fly_tax();
+# if we have a cost from previous routines, return it
+	if(defined $cost) {
 		$Vend::Items = $save if $save;
-		return $cost;
+		return Vend::Util::round_to_frac_digits($cost);
+	}
+
+	if(! $tax_hash) {
+		$cost = fly_tax();
 	}
-#::logDebug("got to tax function: " . ::uneval($tax_hash));
+
+#::logDebug("got to tax function: " . uneval($tax_hash));
+	my $amount = taxable_amount();
+	my($r, $code);
+	# Make it upper case for state and overseas postal
+	# codes, zips don't matter
+	my(@code) = map { (uc $::Values->{$_}) || '' }
+					split /[,\s]+/, $Vend::Cfg->{SalesTax};
+	push(@code, 'DEFAULT');
 
 	$tax_hash = { DEFAULT => } if ! ref($tax_hash) =~ /HASH/;
 
@@ -5512,11 +6729,22 @@
 sub subtotal {
 	my($cart) = @_;
 
+	### If the user has assigned to salestax,
+	### we use their value come what may, no rounding
+	if($Vend::Session->{assigned}) {
+		return $Vend::Session->{assigned}{subtotal}
+			if defined $Vend::Session->{assigned}{subtotal} 
+			&& length( $Vend::Session->{assigned}{subtotal});
+	}
+
     my($save,$subtotal, $i, $item, $tmp, $cost, $formula);
 	if ($cart) {
 		$save = $Vend::Items;
 		tag_cart($cart);
 	}
+
+	levies() unless $Vend::Levying;
+
 	my $discount = defined $Vend::Session->{discount};
     $subtotal = 0;
 	$tmp = 0;
@@ -5548,15 +6776,6 @@
     return $subtotal;
 }
 
-sub tag_subtotal {
-	my($cart, $noformat) = @_;
-	return currency( subtotal($cart), $noformat);
-}
-
-sub tag_salestax {
-	my($cart, $noformat) = @_;
-	return currency( salestax($cart), $noformat);
-}
 
 # Returns the total cost of items ordered.
 
@@ -5571,32 +6790,33 @@
 
 	$total = 0;
 
+	if($Vend::Cfg->{Levies}) {
+		$total = subtotal();
+		$total += levies();
+	}
+	else {
 	my $shipping = 0;
 	$shipping += tag_shipping()
 		if $::Values->{mv_shipmode};
 	$shipping += tag_handling()
-		if $::Values->{mv_shipmode};
+		if $::Values->{mv_handling};
     $total += subtotal();
     $total += $shipping;
     $total += salestax();
 
+	}
 	$Vend::Items = $save if defined $save;
 	$Vend::Session->{latest_total} = $total;
     return $total;
 }
 
-sub tag_total_cost {
-	my($cart, $noformat) = @_;
-	return currency( total_cost($cart), $noformat);
-}
-
 sub tag_ups {
 	my($type,$zip,$weight,$code,$opt) = @_;
 	my(@data);
 	my(@fieldnames);
 	my($i,$point,$zone);
 
-#::logDebug("tag_ups: type=$type zip=$zip weight=$weight code=$code opt=" . ::uneval($opt));
+#::logDebug("tag_ups: type=$type zip=$zip weight=$weight code=$code opt=" . uneval($opt));
 	$code = 'u' unless $code;
 
 	unless (defined $Vend::Database{$type}) {
@@ -5681,4 +6901,194 @@
 	return $cost;
 }
 
+sub levy_sum {
+	my ($set, $levies, $repos) = @_;
+
+	$set    ||= $Vend::CurrentCart || 'main';
+	$levies ||= $Vend::Cfg->{Levies};
+	$repos  ||= $Vend::Cfg->{Levy_repository};
+
+	my $icart = $Vend::Session->{carts}{$set} || [];
+
+	my @sums;
+	for(@$icart) {
+		push @sums, @{$_}{sort keys %$_};
+	}
+	my $items;
+	for(@$levies) {
+		next unless $items = $repos->{$_}{check_status};
+		push @sums, @{$::Values}{ split /[\s,\0]/, $items };
+	}
+	return generate_key(@sums);
+}
+
+sub levies {
+	my($recalc, $set, $opt) = @_;
+
+	my $levies;
+	return unless $levies = $Vend::Cfg->{Levies};
+
+
+	$opt ||= {};
+	my $repos = $Vend::Cfg->{Levy_repository};
+#::logDebug("Calling levies, recalc=$recalc group=$opt->{group}");
+
+	if(! $repos) {
+		logOnce('error', "Levies set but no levies defined! No tax or shipping.");
+		return;
+	}
+	$Vend::Levying = 1;
+	$set ||= $Vend::CurrentCart;
+	$set ||= 'main';
+
+	$Vend::Session->{levies} ||= {};
+	
+	my $lcheck = $Vend::Session->{latest_levy} ||= {};
+	$lcheck = $lcheck->{$set} ||= {};
+
+	if($Vend::LeviedOnce and ! $recalc and ! $opt->{group} and $lcheck->{sum}) {
+		my $newsum = levy_sum($set, $levies, $repos);
+#::logDebug("did levy check, new=$newsum old=$lcheck->{sum}");
+		if($newsum  eq $lcheck->{sum}) {
+			undef $Vend::Levying;
+#::logDebug("levy returning cached value");
+			return $lcheck->{total};
+		}
+	}
+
+	my $lcart = $Vend::Session->{levies}{$set} = [];
+	
+	my $run = 0;
+	for my $name (@$levies) {
+		my $l = $repos->{$name};
+#::logDebug("Levying $name, repos => " . uneval($l));
+		if(! $l) {
+			logOnce('error', "Levy '%s' called but not defined. Skipping.", $name);
+			next;
+		}
+		if(my $if = $l->{include_if}) {
+			if($if =~ /^\w+$/) {
+				next unless $::Values->{$if};
+			}
+			elsif($if =~ /__[A-Z]\w+__|[[a-zA-Z]/) {
+				next unless interpolate_html($if);
+			}
+			else {
+				next unless tag_calc($if);
+			}
+		}
+		if(my $if = $l->{exclude_if}) {
+			if($if =~ /^\w+$/) {
+				next if $::Values->{$if};
+			}
+			elsif($if =~ /__[A-Z]\w+__|[[a-zA-Z]/) {
+				next if interpolate_html($if);
+			}
+			else {
+				next if tag_calc($if);
+			}
+		}
+		my $type = $l->{type} || ($name eq 'salestax' ? 'salestax' : 'shipping');
+		my $mode;
+
+		if($l->{mode_from_values}) {
+			$mode = $::Values->{$l->{mode_from_values}};
+		}
+		elsif($l->{mode_from_scratch}) {
+			$mode = $::Scratch->{$l->{mode_from_scratch}};
+		}
+
+		$mode ||= ($l->{mode} || $name);
+		my $group = $l->{group} || $type;
+		my $cost = 0;
+		my $sort;
+		my $desc;
+		if($type eq 'salestax') {
+			my $save;
+			$sort = $l->{sort} || '010';
+			my $lab_field = $l->{label_value} || $Vend::Cfg->{SalesTax};
+			if($l->{tax_fields}) {
+				$save = $Vend::Cfg->{SalesTax};
+				$Vend::Cfg->{SalesTax} = $l->{tax_fields};
+			}
+			elsif ($l->{multi}) {
+				$save = $Vend::Cfg->{SalesTax};
+				$Vend::Cfg->{SalesTax} = 'multi';
+			}
+			$cost = salestax(undef, { tax_type => $l->{tax_type} } );
+			$desc = errmsg(
+						$l->{description} || 'Sales Tax',
+						$::Values->{$lab_field},
+					);
+			$Vend::Cfg->{SalesTax} = $save if defined $save;
+		}
+		elsif ($type eq 'shipping' or $type eq 'handling') {
+			if(not $sort = $l->{sort}) {
+				$sort = $type eq 'handling' ? 100 : 500;
+			}
+			$cost = shipping($mode);
+			$desc = $l->{description} || tag_shipping_desc($mode);
+		}
+		elsif($type eq 'custom') {
+			my $sub;
+			SUBFIND: {
+				$sub = $Vend::Cfg->{Sub}{$mode} || $Global::GlobalSub->{$mode}
+					and last SUBFIND;
+				eval {
+					$sub = $Vend::Cfg->{UserTag}{Routine}{$mode};
+				};
+				last SUBFIND if ! $@ and $sub;
+				eval {
+					$sub = $Global::UserTag->{Routine}{$mode};
+				};
+			}
+			if( ref($sub) ne 'CODE') {
+				($cost, $desc, $sort) = $sub->($opt);
+			}
+			else {
+				logError("No subroutine found for custom levy '%s'", $name);
+			}
+		}
+
+		my $cost_format;
+		unless ($cost_format = $l->{cost_format}) {
+			my $digits = errmsg('frac_digits') || 2;
+			$cost_format = "%.${digits}f";
+		}
+		my $item = {
+							code			=> $name,
+							mode			=> $mode,
+							sort			=> $sort,
+							cost			=> sprintf($cost_format,$cost),
+							currency		=> currency($cost),
+							group			=> $group,
+							label			=> $l->{label} || $desc,
+							part_number		=> $l->{part_number},
+							description		=> $desc,
+						};
+		if($cost == 0) {
+			next unless $l->{keep_if_zero};
+			$item->{free} = 1;
+			$item->{free_message} = $l->{free_message} || $cost;
+		}
+		push @$lcart, $item;
+	}
+	@$lcart = sort { $a->{sort} cmp $b->{sort} } @$lcart;
+
+	for(@$lcart) {
+		next if $opt->{group} and $opt->{group} ne $_->{group};
+		$run += $_->{cost};
+	}
+
+	$run = round_to_frac_digits($run);
+	if(! $opt->{group}) {
+		$lcheck = $Vend::Session->{latest_levy}{$set} = {};
+		$lcheck->{sum}   = levy_sum($set, $levies, $repos);
+		$lcheck->{total} = $run;
+		$Vend::LeviedOnce = 1;
+	}
+
+	undef $Vend::Levying;
+	return $run;
+}
 1;



1.12.4.4  +2166 -291 interchange/lib/Vend/MakeCat.pm


rev 1.12.4.4, prev_rev 1.12.4.3
Index: MakeCat.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/MakeCat.pm,v
retrieving revision 1.12.4.3
retrieving revision 1.12.4.4
diff -u -r1.12.4.3 -r1.12.4.4
--- MakeCat.pm	5 Dec 2000 12:47:28 -0000	1.12.4.3
+++ MakeCat.pm	25 Jan 2003 22:21:28 -0000	1.12.4.4
@@ -1,14 +1,10 @@
-# MakeCat.pm - routines for catalog configurator
+# Vend::MakeCat - Routines for Interchange catalog configurator
 #
-# $Id: MakeCat.pm,v 1.12.4.3 2000/12/05 12:47:28 racke Exp $
+# $Id: MakeCat.pm,v 1.12.4.4 2003/01/25 22:21:28 racke Exp $
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -25,49 +21,114 @@
 # Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 # MA  02111-1307  USA.
 
-## END CONFIGURABLE VARIABLES
-
 package Vend::MakeCat;
 
 use Cwd;
 use File::Find;
 use File::Copy;
 use File::Basename;
+use Sys::Hostname;
+use Vend::Util;
+require Safe;
+$Safe = new Safe;
 
 require Exporter;
 @ISA = qw(Exporter);
 @EXPORT = qw(
 
+%Conf
+%Content
+%Ever
+%History
+%IfRoot
+%Commandline
+%Postprocess
+%Prefix
+%Window
+$Force
+$Safe
+
 add_catalog
 addhistory
+applicable_directive
 can_do_suid
+check_root_execute
+compare_file
 conf_parse_http
 copy_current_to_dir
 copy_dir
 description
+debug
+directory_process
 do_msg
+error_message
+find_inet_info
 findexe
 findfiles
 get_id
 get_ids
+get_rename
+history
+inet_host
+inet_port
+install_file
+label
+prefix
 pretty
 prompt
+read_additional
+readconfig
 sethistory
+strip_na
+strip_trailing_slash
+substitute
+sum_it
+unique_ary
+validate
 
 );
 
 
 use strict;
 
-use vars qw($Force $Error $History $VERSION);
-$VERSION = substr(q$Revision: 1.12.4.3 $, 10);
+use vars qw($Safe $Force $Error $History $VERSION);
+
+$Safe->share(qw/%Conf %Ever &debug/);
+
+use vars qw/
+	%Alias
+	%Conf
+	%Content
+	%Commandline
+	%Ever
+	%History
+	%IfRoot
+	%Postprocess
+	%Special_sub
+	%Prefix
+	%Window
+/;
+
+$VERSION = substr(q$Revision: 1.12.4.4 $, 10);
 
 $Force = 0;
 $History = 0;
-my %Pretty = qw(
 
+%Alias = (
+	serverconf => {
+						linux => '/etc/httpd/conf/httpd.conf',
+					},
+);
+
+my %Watch = qw/
+		cfg_extramysql 1
+		/;
+
+my %Pretty = (
+	qw/
 	aliases				Aliases
 	basedir				BaseDir
+	catroot				CatRoot
 	catuser				CatUser
 	cgibase				CgiBase
 	cgidir				CgiDir
@@ -76,23 +137,66 @@
 	documentroot		DocumentRoot
 	imagedir			ImageDir
 	imageurl			ImageUrl
-	mailorderto			MailOrderTo
-	interchangeuser		InterchangeUser
 	interchangegroup	InterchangeGroup
+	interchangeuser		InterchangeUser
+	mailorderto			MailOrderTo
 	samplehtml			SampleHtml
-	sampledir			SampleDir
 	sampleurl			SampleUrl
 	serverconf			ServerConf
 	servername			ServerName
 	sharedir			ShareDir
 	shareurl			ShareUrl
-	catroot				CatRoot
 	vendroot			VendRoot
+/,
+	linkmode => 'Link mode',
 
 );
- 
- 
+
+my %Label = (
+	add_catalog		=> 'Add catalog to interchange.cfg',
+    aliases			=> 'Link aliases',
+	basedir			=> 'Base directory for catalogs',
+	catroot			=> 'Catalog directory',
+	catuser			=> 'Catalog user',
+	catalogname		=> 'Catalog name',
+	cgibase			=> 'CGI base URL',
+	cgidir			=> 'CGI Directory',
+	cgiurl			=> 'URL call for catalog',
+	demotype		=> 'Catalog skeleton',
+	documentroot	=> 'Document Root',
+	imagedir		=> 'Image directory',
+	imageurl		=> 'Image base URL',
+	interchangeuser	=> 'Interchange daemon username',
+	interchangegroup	=> 'Interchange daemon groupname',
+	linkhost		=> 'Link host',
+	linkmode		=> 'Link mode',
+	linkport		=> 'Link port',
+	mailorderto		=> 'Email address for orders',
+	permtype		=> 'Permission Type',
+	run_catalog		=> 'Add catalog to running server',
+	samplehtml		=> 'Catalog HTML base directory',
+	servconflist	=> 'Server config files found',
+	serverconf		=> 'Server config file',
+	serverlist		=> 'Servers in httpd.conf',
+	servername		=> 'Server name',
+	sharedir		=> 'Share Directory',
+	shareurl		=> 'Share URL',
+	win_addcatalog	=> 'Add catalog to Interchange',
+	win_catinfo		=> 'Catalog Initialization Information',
+	win_greeting	=> 'Make an Interchange Catalog',
+	win_servername	=> 'HTTP ServerName',
+	win_server		=> 'HTTP Server Information',
+	win_serverconf	=> 'HTTP Server Configuration File',
+	win_linkinfo	=> 'Link Program Information',
+	win_urls		=> 'URL and Directory Information',
+);
+
 my %Desc = (
+	add_catalog => <<EOF,
+# To make the catalog active, you must add it to the
+# interchange.cfg file. If you don't select this, then you will
+# have to manually add it later.
+EOF
 
 	aliases    =>  <<EOF,
 #
@@ -108,26 +212,52 @@
 # internal HTTP server.
 #
 EOF
+
 	basedir    =>  <<EOF,
-# 
-# DIRECTORY where the Interchange catalog directories will go. These
-# are the catalog files, such as the ASCII database source,
-# Interchange page files, and catalog.cfg file. Catalogs will
-# be an individual subdirectory of this directory.
+#
+# DIRECTORY where the Interchange catalog directories will go.
+# These are the catalog files, such as the ASCII database source,
+# Interchange page files, and catalog.cfg file. Catalogs will be
+# an individual subdirectory of this directory.
 #
 EOF
+
+	catalogname => <<EOF,
+# Select a short, mnemonic name for the catalog. This will be
+# used to set the defaults for naming the catalog, executable,
+# and directory, so you will have to type in this name
+# frequently.
+#
+# NOTE: This will be the name of 'vlink' or 'tlink', the link CGI
+#       program. Depending on your CGI setup, it may also have
+#       the extension .cgi added.
+#
+# Only the characters [-a-zA-Z0-9_] are allowed, and it is
+# strongly suggested that the catalog name be all lower case.
+#
+# If you are doing the demo for the first time, you might use
+# "foundation".
+EOF
+
+	catroot   =>  <<EOF,
+# Where the Interchange files for this catalog will go, pages,
+# products, config and all. This should not be in HTML document
+# space! Usually a 'catalogs' directory below your home directory
+# works well. Remember, you will want a test catalog and an
+# online catalog.
+EOF
+
 	catuser    =>  <<EOF,
 #
 # The user name the catalog will be owned by.
 #
 EOF
+
 	cgibase    =>  <<EOF,
 #
 # The URL-style location of the normal CGI directory.
 # Only used to set the default for the CgiUrl setting.
 # 
-# DO NOT PUT A TRAILING /.
-#
 # http://www.virtual.com/cgi-bin/prog
 #                       ^^^^^^^^
 #
@@ -135,6 +265,7 @@
 # in .cgi), leave this blank.
 #
 EOF
+
 	cgidir     =>  <<EOF,
 # The location of the normal CGI directory. This is a
 # file path, not a script alias.
@@ -143,6 +274,7 @@
 # should be the same as your HTML directory.
 #
 EOF
+
 	cgiurl     =>  <<EOF,
 # The URL location of the CGI program, without the http://
 # or server name.
@@ -154,138 +286,1293 @@
 #                       ^^^^^^^^^^^^
 #
 EOF
+
 	demotype   =>  <<EOF,
 # The type of demo catalog to use. The standard one distributed is:
 #
-#    construct
+#    foundation
 #
 # If you have defined your own custom template catalog,
 # you can enter its name.
 #
-# If you are new to Interchange and not a sophisticated web designer,
-# use "construct" to start with.
+# If you are new to Interchange, use "foundation" to start with.
 EOF
+
 	documentroot    =>  <<EOF,
 # The base directory for HTML for this (possibly virtual) domain.
 # This is a directory path name, not a URL -- it is your HTML
 # directory.
 #
 EOF
-	mailorderto  =>  <<EOF,
-# The email address where orders for this catalog should go.
-# To have a secure catalog, either this should be a local user name and
-# not go over the Internet -- or use the PGP option.
+
+	imagedir   =>  <<EOF,
+# Where the image files should be copied. A directory path
+# name, not a URL.
 #
 EOF
-	permtype  =>  <<EOF,
-# The type of permission structure for multiple user catalogs.
-# Select M for each user in own group (with interchange user in group)
-#        G for all users in group of interchange user
-#        U for all catalogs owned by interchange user (must be catuser as well)
+
+	imageurl   =>  <<EOF,
+# The URL base for the sample images. Sets the ImageDir
+# directive in the catalog configuration file. This is a URL
+# fragment, not a directory or file name.
 #
-#        M is recommended, G works for most installations.
-EOF
-	interchangeuser  =>  <<EOF,
-# The user name the Interchange server runs under on this machine. This
-# should not be the same as the user that runs the HTTP server (i.e.
-# NOT nobody).
+#         <IMG SRC="/foundation/images/icon.gif">
+#                   ^^^^^^^^^^^^^^^^^^
 #
 EOF
+
 	interchangegroup    =>  <<EOF,
-# The group name the server-owned files should be set to.  This is
-# only important if Interchange catalogs will be owned by multiple users
-# and the group to be used is not the default for the catalog user.
+# The group name the server-owned files should be set to. This is
+# only important if Interchange catalogs will be owned by
+# multiple users and the group to be used is not the default for
+# the catalog user.
 #
 # Normally this is left blank.
-# 
 EOF
-	sharedir => <<EOF,
-# This is a directory path name (not a URL) where the administration user
-# interface images from share/ should be copied to. These will normally be
-# shared by all catalogs. Often this is the same as your DocumentRoot.
-#
+
+	interchangeuser  =>  <<EOF,
+# The user name the Interchange server runs under on this
+# machine. This should not be the same as the user that runs the
+# HTTP server (i.e. NOT nobody).
 EOF
-	shareurl => <<EOF,
-# The URL base for the administration user interface images. Sets the
-# Variable UI_IMG directive in the UI configuration file, ui.cfg.
-# This is a URL fragment, not an entire URL. If you set ShareDir to be
-# the same as DocumentRoot, this would just be a '/'.
+
+	linkhost => <<EOF,
+# If you are using INET mode, you need to set the host the link
+# CGI will talk to.
 #
-#         <IMG SRC="/akopia/ui/bg.gif">
-#                   ^
+# If Interchange is running on the same server as your web
+# server, this should be "localhost". If the web server is on a
+# different machine, it is the IP address of the machine
+# Interchange is running on.
+EOF
+
+	linkmode => <<EOF,
+# Interchange can use either UNIX- or internet-domain sockets.
+# Most ISPs would prefer UNIX mode, and it is more secure.
 #
+# If you already have a program there, or use mod_interchange,
+# select NONE. You will then need to copy the program by hand or
+# otherwise ensure its presence.
 EOF
-	imagedir   =>  <<EOF,
-# Where the image files should be copied. A directory path
-# name, not a URL.
+
+	linkport => <<EOF,
+# If you are using INET mode, you need to set the port the
+# link CGI will talk to. The IANA standard for Interchange is
+# port 7786.
+EOF
+
+	mailorderto  =>  <<EOF,
+# The email address where orders for this catalog should go. To
+# have a secure catalog, either this should be a local user name
+# and not go over the Internet -- or use the PGP option.
 #
 EOF
-	imageurl   =>  <<EOF,
-# The URL base for the sample images. Sets the ImageDir
-# directive in the catalog configuration file. This is a URL
-# fragment, not a directory or file name.
+
+	permtype  =>  <<EOF,
+# The type of permission structure for multiple user catalogs.
 #
-#         <IMG SRC="/construct/images/icon.gif">
-#                   ^^^^^^^^^^^^^^^^^
+# Select:
+#    M for each user in own group (with interchange user in group)
+#    G for all users in group of interchange user
+#    U for all catalogs owned by interchange user
+#      (should be catuser as well)
+#
+#    M is recommended, G works for most installations.
+EOF
+
+	run_catalog  =>  <<EOF,
+# You can add this catalog to the running Interchange server. You
+# may not want to do this if you are using a SQL database, as you
+# will not be able to monitor the database creation activity.
 #
+# If you don't do it, then you can restart Interchange to
+# activate the new catalog.
 EOF
+
 	samplehtml =>  <<EOF,
-# Where the sample HTML files (not Interchange pages) should be installed.
-# There is a difference. Usually a subdirectory of your HTML directory.
+# Where the sample HTML files (not Interchange pages) should be
+# installed. There is a difference. Usually a subdirectory of
+# your HTML directory.
 #
 EOF
+
 	sampleurl  =>  <<EOF,
 # Our guess as to the URL to run this catalog, used for the
 # client-pull screens and an informational message, not prompted for.
 #
 EOF
+
+	servconflist =>  <<EOF,
+# A list of server configuration files automatically found.
+# When you use history to change this, it will be reflected
+# in the next field to save you entering the file name.
+#
+EOF
+
 	serverconf =>  <<EOF,
 # The server configuration file, if you are running
 # Apache or NCSA. Often:
+#                          /etc/httpd/conf/httpd.conf
 #                          /usr/local/apache/conf/httpd.conf
 #                          /usr/local/etc/httpd/conf/httpd.conf
 #
 EOF
+
 	servername =>  <<EOF,
 # The server name, something like: www.company.com
 #                                  www.company.com:8000
 #                                  www.company.com/~yourname
 #
 EOF
-	catroot   =>  <<EOF,
-# Where the Interchange files for this catalog will go, pages,
-# products, config and all.  This should not be in HTML document
-# space! Usually a 'catalogs' directory below your home directory
-# works well. Remember, you will want a test catalog and an online
-# catalog.
+
+	sharedir => <<EOF,
+# This is a directory path name (not a URL) where the administration user
+# interface images from share/ should be copied to. These will normally be
+# shared by all catalogs. Often this is the same as your DocumentRoot.
+#
+EOF
+
+	shareurl => <<EOF,
+# The URL base for the administration user interface images.
+# This is a URL fragment, not an entire URL.
+#
+#         <IMG SRC="/interchange/en_US/bg.gif">
+#                   (leave blank)
+#
+#         <IMG SRC="/~yourname/interchange/en_US/bg.gif">
+#                   ^^^^^^^^^^
+#
+EOF
+
+	vendroot  =>  <<EOF,
+# The directory where the Interchange software is installed.
+#
+EOF
+
+	win_addcatalog		=> <<EOF,
+# You should add the catalog callout to interchange.cfg, and
+# optionally can add it into the running server.
+EOF
+
+	win_catinfo		=> <<EOF,
+# We need to set base template type and directory for your catalog.
+EOF
+
+	win_greeting		=> <<EOF,
+# Welcome to Interchange!
+#
+# You can now configure a working catalog.
+#
+# You can exit by selecting the "Cancel" button below, but your
+# catalog will not be built until you complete the configuration.
+EOF
+
+	win_linkinfo		=> <<EOF,
+# We need to get information necessary for compiling the link
+# program(s).
+EOF
+
+	win_server		=> <<EOF,
+# We need to know some basic HTTP Server configuration information.
+EOF
+
+	win_serverconf		=> <<EOF,
+# If you are using Apache or another HTTP server with the same
+# type of configuration file, we can read it and set some
+# defaults based on the server name you are using.
+EOF
+
+	win_servername		=> <<EOF,
+# Since you are running Apache, we can give you a choice of the
+# server names defined in the httpd.conf file you selected. This
+# will be used to pre-set items like DocumentRoot, ScriptAlias
+# (cgi-bin), etc.
 #
+# If you don't see your server, pick the empty option and go to
+# the next screen.
+EOF
+
+	win_urls		=> <<EOF,
+# We need to set the HTML, image, and executable paths for your
+# catalog.
+EOF
+
+);
+
+my %Validate = (
+	demotype => <<EOF,
+The demotype skeleton directory must exist. In addition, if you
+are root the files must be owned by root and not be group-
+or world-writable.
+EOF
+);
+
+my %Build_error = (
+	demotype => <<EOF,
+There were errors in copying the demo files.  Cannot
+continue.  Check to see if permissions are correct.
+EOF
+
+);
+
+my $Wname = 'content00';
+
+sub readconfig {
+	my ($file, $ref) = @_;
+	return undef unless $file;
+	return undef unless -f $file;
+	$ref = {} unless ref $ref;
+	open (INICONF, "< $file")
+		or die "open $file: $!\n";
+	local($/);
+	my $data = <INICONF>;
+	close INICONF;
+	my $novirt;
+
+	my %virtual;
+
+	$data =~ s/^\s*#.*//mg;
+	$data =~ m{(\[<)}
+		or $novirt = 1;
+	my $first = $1;
+	if($first eq '<') {
+		$data =~ s!
+				<catalog\s+
+				
+					([^>\n]+)
+				\s*>\s+
+					([\000-\377]*?)
+				</catalog>!
+				$virtual{$1} = $2; ''!xieg;
+
+		$virtual{'_base'} = $data;
+	}
+	else {
+		my %recognize = ( base => '_base' );
+		my @lines = grep /\S/, split /\n/, $data;
+		my $handle;
+		for(@lines) {
+			if(/^\[(.*?)\]\s*$/) {
+				my $hh = $1;
+				if($hh =~ /^catalog\s+(\S+)/) {
+					$handle = $1;
+				}
+				elsif($recognize{$hh}) {
+					$handle = $recognize{$hh};
+				}
+				else {
+					undef $handle;
+				}
+				$virtual{$handle} = '' if ! $virtual{$handle};
+				next;
+			}
+			next unless $handle;
+			next unless /\S/;
+			$virtual{$handle} .= $_;
+		}
+	}
+
+	my $out = {};
+	foreach my $hk (keys %virtual) {
+		my $ref = $out->{$hk} = {};
+		my @lines = grep /\S/, split /\n/, $virtual{$hk};
+		for(@lines) {
+			s/^\s+//;
+			s/\s+$//;
+			my ($k, $v) = split /\s*=\s*/, $_, 2;
+			$ref->{$k} = $v;
+		}
+	}
+	return $out;
+}
+
+sub read_additional {
+	my ($file) = @_;
+
+	if (! $file) {
+		$file = "$Conf{vendroot}/$Conf{demotype}/config/additional_fields";
+		return undef unless -f $file;
+	}
+
+	my $help = $file;
+	$help =~ s/_fields$/_help/ or undef $help;
+	my $data;
+
+	SPLIT: {
+		local ($/);
+		open ADDLFIELDS, "< $file"
+			or return undef;
+		$data = <ADDLFIELDS>;
+		close ADDLFIELDS;
+	}
+
+	HELP: {
+		local($/) = "";
+		last HELP unless open  ADDLHELP, "< $help";
+		while(<ADDLHELP>) {
+			s/^[.\t ]+$//mg;
+			my ($k, $v) = split /\n/, $_, 2;
+			$Desc{lc $k} = $v;
+		}
+		close ADDLHELP;
+	}
+
+	my @chunks;
+	if($data =~ /^\s*</) {
+		@chunks = read_common_config($data);
+		return read_additional_new(@chunks);
+	}
+	else {
+		@chunks = split /\n\n+/, $data;
+		return read_additional_old(@chunks);
+	}
+}
+
+sub read_additional_old {
+	my (@chunks) = @_;
+
+	my @addl_windows;
+	my %label;
+
+	my $winref;
+
+	for(@chunks) {
+		my $noprompt = '';
+		my $grp;
+		my $realgrp;
+		my $wid;
+		my $cref = {};
+		s/\s+$//;
+		my ($var, $prompt, $default) = split /\n/, $_, 3;
+
+		($var, $realgrp, $wid) = split /\t/, $var;
+
+		$cref->{widget} = $wid if $wid;
+
+		my $label;
+		($prompt, $label) = split /\t/, $prompt, 2;
+
+		my $subcode;
+		my $mainparam;
+
+		if($var =~ s/{\s*([A-Z0-9]+)(\s*\S.*?)?\s*}\s*//) {
+			$mainparam = lc $1;
+			my $test = $2;
+			$test =~ s/'?__MVC_([A-Z0-9]+)__'?/\$Conf{\L$1}/g; 
+			$subcode = <<EOF;
+sub {
+	my \$status;
+	if(\$Conf{$mainparam} $test) {
+		\$status = 1;
+	}
+	else {
+		\$status = 0;
+	}
+	return \$status;
+}
+EOF
+
+			my $sub = eval $subcode;
+			if($@) {
+				undef $sub;
+			}
+			$cref->{conditional} = $sub;
+		}
+		$var =~ s/\s+//g;
+		$var =~ s:^!::
+			and $noprompt = 1;
+		$var =~ s/\W+//g;
+		$var = lc $var;
+debug("conditional code: $subcode") if $Watch{$var};
+
+		$cref->{help} = description($var);
+		$cref->{group} ||= $realgrp;
+		$grp = $cref->{group} || $var;
+
+		if(! $var and $cref->{group}) {
+			$Window{$cref->{group}} ||= { };
+			$Window{$cref->{group}}->{banner} = $label || $prompt;
+			$Window{$cref->{group}}->{help}    =
+			$Window{$cref->{group}}->{message} = description($cref->{group});
+			push @addl_windows, $cref->{group};
+			next;
+		}
+		elsif($grp ne $var) {
+			if (! $Window{$grp}) {
+				$Window{$grp} = { };
+				push @addl_windows, $grp;
+			}
+			elsif($mainparam) {
+				$Window{$grp}{conditional} = $cref->{conditional}
+					if !  $Window{$grp}{conditional};
+			}
+			$Window{$grp}{contents} = [] if ! $Window{$grp}{contents};
+			push @{$Window{$grp}{contents}}, $var;
+		}
+		else {
+			push @addl_windows, $var;
+		}
+
+		my (@history)  = split /\t/, $default;
+		$default = $Conf{$var} || $history[0] || '';
+
+		if($label =~ /\S/) {
+			$cref->{banner} = $prompt;
+			$cref->{label} = $label;
+		}
+		else {
+			$cref->{label} = $prompt;
+		}
+
+		my $presubcode;
+		if($default =~ s/__MVC_([A-Z0-9]+)__/\$Conf{\L$1}/g) {
+			$default =~ s/\@/\\\@/g;
+			my $presubcode = qq{
+				sub {
+					return qq[$default]
+				}
+			};
+			my $presub = eval $presubcode;
+			if($@) {
+debug("error evaling prefix sub for $var: $presubcode");
+			}
+			$cref->{prefix} = $presub;
+			$cref->{prefix_source} = $presubcode;
+		}
+		else {
+			$cref->{prefix} = $default;
+		}
+		$cref->{options} = \@history;
+		if ($noprompt) {
+			if($cref->{conditional}) {
+				my $snippet = <<EOF;
+
+	\$Conf{$var} = q{$default} if \$status;
+	return \$status;
+}
+EOF
+				# Appease vi {
+				$subcode =~ s/\s*return .*\s+}\s*$/$snippet/;
+				$cref->{conditional} = eval $subcode;
+				$cref->{conditional_source} = $subcode;
+			}
+			else {
+				$Conf{$var} = substitute($default);
+				$cref->{conditional} = sub { 0 };
+			}
+		}
+		if($mainparam || $cref->{group}) {
+			my $winref;
+			if($cref->{group}) {
+				$winref = $Window{$cref->{group}};
+			}
+			else {
+				$winref = $Content{$mainparam};
+				$winref->{additional} ||= [];
+				push @{$winref->{additional}}, $var;
+			}
+			$winref->{override} ||= {};
+			$winref->{override}{$var} = $cref;
+			$Content{$var} = $cref unless $Content{$var};
+		}
+		elsif ($Content{$var}) {
+die("generated duplicate param for $var with no group or mainparam.\n");
+debug("generated duplicate param for $var with no group or mainparam.\n");
+		}
+		else {
+			$Content{$var} = $cref;
+		}
+#debug( "ref for $var: " . ::uneval($cref));
+	}
+	close ADDLFIELDS;
+#debug("read_additional: returning: " . join ",", @addl_windows);
+	my %seen;
+
+	# Multiple conditions may define them more than once
+	@addl_windows = grep !$seen{$_}++, @addl_windows;;
+	return @addl_windows;
+}
+
+sub read_additional_new {
+	my ($help, @chunks) = @_;
+	my $winref;
+	my @addl_windows;
+	
+	foreach my $cref (@chunks) {
+		my $grp;
+		my $subcode;
+		my $mainparam;
+		my $var;
+		my $default;
+		my $cond_code;
+
+		if(! ref $cref) {
+			# Bad chunk
+			next;
+		}
+
+		$cref->{_additional} = 1;
+
+		if($cond_code = $cref->{conditional}) {
+			delete $cref->{conditional};
+			if($cond_code =~ /^sub\s+{.*}\s*$/s) {
+				$subcode = $cond_code;
+			}
+			else {
+				$cond_code =~ m{^[A-Z][A-Z0-9]+$}
+					and $cond_code = "\U__MVC_${cond_code}__";
+				$cond_code =~ m{__MVC_([A-Z0-9]+)__}
+					and $mainparam = lc $1;
+				$cond_code =~ s{(['"]?)__MVC_([A-Z0-9]+)__\1}
+							   {'$Conf{' . lc $2 . '}'   }eg;
+
+				# Appease vi }
+				$subcode = <<EOF;
+		sub {
+			my \$status;
+			if($cond_code) {
+				\$status = 1;
+			}
+			else {
+				\$status = 0;
+			}
+			return \$status;
+		}
+EOF
+			}
+		}
+
+		if($subcode) {
+			my $sub = eval $subcode;
+			if($@) {
+debug("Problem evaluating sub: $subcode");
+				undef $sub;
+			}
+			$cref->{conditional} = $sub;
+		}
+
+		for my $code (qw/callback/) {
+			my $cb = $cref->{$code}
+				or next;
+			if($cb =~ /^\s*sub\s+{/) {
+				# Appease vi }
+				local($SIG{__DIE__});
+				$cref->{$code} = eval $cb;
+				$cref->{"${code}_source"} = $cb;
+			}
+			elsif($cb =~ /^\s*\[.*\]\s*$/s) {
+				$cref->{$code} = eval($cb);
+				$cref->{"${code}_source"} = $cb;
+			}
+			elsif($cb =~ /[a-z]/) {
+				my @items = Text::ParseWords::shellwords($cref->{$code});
+				@items = map { lc $_ } @items;
+				$cref->{$code} = \@items;
+				$cref->{"${code}_source"} = $cb;
+			}
+		}
+
+		for my $code (qw/options history/) {
+			my $cb = $cref->{$code}
+				or next;
+			if($cb =~ /^\s*sub\s+{.*}\s*$/s) {
+				local($SIG{__DIE__});
+				$cref->{$code} = eval $cb;
+				$cref->{"${code}_source"} = $cb;
+			}
+			elsif($cb =~ /^\s*\[.*\]\s*$/s) {
+				$cref->{$code} = eval($cb);
+				$cref->{"${code}_source"} = $cb;
+			}
+			elsif($cb =~ /[a-z]/) {
+				my @items = Text::ParseWords::shellwords($cref->{$code});
+				$cref->{$code} = \@items;
+				$cref->{"${code}_source"} = $cb;
+			}
+		}
+
+		for my $code (qw/check_routine/) {
+			my $cb = $cref->{$code}
+				or next;
+			if($cb =~ /^\s*sub\s+{/) {
+				# Appease vi }
+				$cref->{$code} = eval $cb;
+				$cref->{"${code}_source"} = $cb;
+			}
+			else {
+				undef $cref->{$code};
+			}
+		}
+
+		$var = $cref->{name} || $Wname++;
+		$var =~ s/\s+//g;
+		$var =~ s/\W+//g;
+		$cref->{name} = $var = lc $var;
+$::Subcode{$var} = $subcode;
+debug("conditional code: $subcode") if $Watch{$var};
+
+		$grp = $cref->{group} || $var;
+
+		if($cref->{_window}) {
+			if(my $wref = $Window{$var}) {
+				for(keys %$wref) {
+					$cref->{$_} = $wref->{$_}
+						unless defined $cref->{$_};
+				}
+			}
+			$cref->{help} ||= description($var);
+			$cref->{message} ||= $cref->{help};
+			$cref->{banner}  ||= $cref->{label};
+			push @addl_windows, $var;
+			$Window{$var} = $cref;
+			next;
+		}
+		elsif($grp ne $var) {
+			if (! $Window{$grp}) {
+				$Window{$grp} = { };
+				push @addl_windows, $grp;
+			}
+			elsif($mainparam) {
+				$Window{$grp}{conditional} = $cref->{conditional}
+					if !  $Window{$grp}{conditional};
+			}
+			$Window{$grp}{contents} = [] if ! $Window{$grp}{contents};
+			push @{$Window{$grp}{contents}}, $var;
+		}
+		else {
+			push @addl_windows, $var;
+		}
+
+		if(! $cref->{default} and ref $cref->{history} eq 'ARRAY') {
+			$cref->{default} = $cref->{history}[0];
+		}
+
+		$cref->{help}    ||= description($var);
+		$cref->{message} ||= $cref->{help};
+
+		# Set default one of three ways
+		if($cref->{default}) {
+			$default = $cref->{default};
+		}
+
+		if($default =~ /\t/ and ! $cref->{history}) {
+			$cref->{history} = [ split /\t/, $default ];
+			$default =~ s/\t.*//;
+			$cref->{default} = $default;
+		}
+		$cref->{label} = $cref->{prompt} if ! $cref->{label};
+
+		my $presubcode;
+		if($cref->{default} =~ s/__MVC_([A-Z0-9]+)__/\$Conf{\L$1}/g) {
+			$cref->{default} =~ s/\@/\\\@/g;
+			my $presubcode = qq{
+				sub {
+					return qq[$cref->{default}]
+				}
+			};
+			my $presub = eval $presubcode;
+			if($@) {
+debug("error evaling prefix sub for $var: $presubcode");
+			}
+			$cref->{default} = $cref->{prefix} = $presub;
+			$cref->{default_source} = $presubcode;
+		}
+		else {
+			$cref->{default} = $cref->{prefix} = $default;
+		}
+
+		$cref->{options} = $cref->{history} if ! $cref->{options};
+		if ($cref->{noprompt}) {
+			if($cref->{conditional}) {
+				# Appease vi {
+				my $snippet = <<EOF;
+
+	\$Conf{$var} = q{$default} if \$status;
+	return \$status;
+}
+EOF
+				# Appease vi {
+				$subcode =~ s/\s*return .*\s+}\s*$/$snippet/;
+				$cref->{conditional} = eval $subcode;
+				if($@) {
+debug("Problem evaluating sub: $subcode");
+				}
+				$cref->{conditional_source} = $presubcode;
+			}
+			else {
+				$Conf{$var} = $default;
+				$cref->{conditional} = sub { 0 };
+			}
+		}
+		if($cref->{always_set}) {
+			$Conf{$var} = substitute($default);
+		}
+
+		if($mainparam || $cref->{group}) {
+			my $winref;
+			if($cref->{group}) {
+				$winref = $Window{$cref->{group}};
+			}
+			else {
+				$winref = $Content{$mainparam};
+				$winref->{additional} ||= [];
+				push @{$winref->{additional}}, $var;
+			}
+			$winref->{override} ||= {};
+			$winref->{override}{$var} = $cref;
+		}
+		elsif ($Content{$var}) {
+debug("generated duplicate param for $var with no group or mainparam.");
+die("generated duplicate param for $var with no group or mainparam.");
+		}
+		else {
+			$Content{$var} = $cref;
+			push @addl_windows, $var;
+		}
+#debug( "ref for $var: " . ::uneval($cref));
+	}
+	my %seen;
+
+	# Multiple conditions may define them more than once
+	@addl_windows = grep !$seen{$_}++, @addl_windows;;
+debug("read_additional returning windows: " . join ",", @addl_windows);
+#debug("Here is the whole shebang:\n" . uneval(\%Window) . "\ncontent:\n" . uneval(\%Content));
+	return @addl_windows;
+}
+
+sub read_common_config {
+	my $data = shift;
+#debug("read_common_config called with data=$data");
+	my @lines = split /\n/, $data;
+	my $prev = '';
+	my $waiting;
+
+	my @out;
+	my $out = \@out;
+	my $wref;
+	my $cref;
+
+	my $type;
+	for(@lines) {
+		# Strip CR, we hope
+		s/\s+$//;
+
+		# Handle continued lines
+		if(s/\\$//) {
+			$prev .= $_;
+			next;
+		}
+		elsif($waiting) {
+			if($_ eq $waiting) {
+				undef $waiting;
+				$_ = $prev;
+				$prev = '';
+				s/\s+$//;
+			}
+			else {
+				$prev .= "$_\n";
+				next;
+			}
+		}
+		elsif($prev) {
+			$_ = "$prev$_";
+			$prev = '';
+		}
+
+		if (s/<<(\w+)$//) {
+			$waiting = $1;
+			$prev .= $_;
+			next;
+		}
+
+		next unless /\S/;
+		next if /^\s*#/;
+		if(m{
+				^ \s* < 
+						(\w+)
+						(?:\s+(\w[-\w]*\w))?
+					\s*>\s*
+			}x) 
+		{
+			$type = lc $1;
+			my $name = $2 || undef;
+			if($name) {
+				$name = lc $name;
+				$name =~ tr/-/_/;
+			}
+			if(defined $cref and $cref->{_window} and $type ne 'window') {
+				$wref = $cref;
+				$out = $wref->{content_array} ||= [];
+			}
+			else {
+				push @$out, $cref if $cref;
+			}
+			$cref = { "_$type" => 1, name => $name };
+			next;
+		}
+		elsif (m{^\s*</(\w[-\w]+\w)\s*>\s*}) {
+			my $ender = lc $1;
+			$ender =~ tr/-/_/;
+			if(! $cref) {
+				push @out, $wref if $wref;
+				$out = \@out;
+				undef $type;
+				undef $wref;
+				undef $cref;
+			}
+			elsif($ender eq $type) {
+				if($type eq 'window') {
+					push @out, ($wref || $cref);
+					undef $cref;
+					undef $wref;
+					$out = \@out;
+				}
+				else {
+					push @$out, $cref;
+					undef $cref;
+				}
+			}
+			else {
+				die errmsg("Syntax error in config input: %s", $_);
+			}
+			next;
+		}
+
+		s/^\s*(\w[-\w]*\w)(\s+|$)//
+			or do {
+				die "Problem reading config reference type=$type: $_\n";
+			};
+		my $parm = lc $1;
+		$cref ||= {};
+		$parm =~ tr/-/_/;
+		$cref->{$parm} = $_;
+	}
+	push @out, $cref if $cref;
+	my @extra;
+	for my $ref (@out) {
+		if($ref->{content_array} and $ref->{_window}) {
+			for (@{delete $ref->{content_array}}) {
+				$_->{name} ||= $Wname++;
+debug("popping $_->{name} from $ref->{name} content array");
+				$_->{group} = $ref->{name};
+				push @extra, $_;
+			}
+		}
+	}
+	push @out, @extra;
+#debug("read_common_config: " . uneval(\@out) );
+	return @out;
+}
+
+sub read_commands {
+	my ($file, $wref) = @_;
+
+	my @data;
+	my @files;
+	my $pre_post;
+	if(! $file) {
+		@files = (
+			"$Conf{vendroot}/$Conf{demotype}/config/precopy_commands",
+		    "$Conf{vendroot}/$Conf{demotype}/config/postcopy_commands",
+		);
+		$pre_post = 1;
+	}
+	else {
+		@files = ($file);
+		$wref = {} unless $wref;
+	}
+
+	for (my $i = 0; $i < @files; $i++) {
+		my $fn = $files[$i];
+		next if ! $fn;
+		next if ! -f $fn;
+		open CMDFILE, "< $fn"
+			or do {
+				my $msg = errmsg(
+							"Cannot %s commands file %s: %s",
+							errmsg('open'),
+							$fn,
+							$!,
+						  );
+				die "$msg\n";
+			};
+		local ($/);
+		$data[$i] = <CMDFILE>;
+		close CMDFILE
+			or do {
+				my $msg = errmsg(
+							"Cannot %s commands file %s: %s",
+							errmsg('close'),
+							$fn,
+							$!,
+						  );
+				die "$msg\n";
+			};
+	}
+
+	my $cmd_num = "cmd000";
+
+	return undef unless @data;
+	foreach my $block (@data) {
+		my $root_msg = $> == 0 ? <<EOF : '';
+
+Because you are root, you should be very careful
+what commands you run.  If you are unsure about the
+ownership of any files, or of what the effects might
+be, please uncheck the box next to the command.
+EOF
+		if($pre_post eq '1') {
+			if(! $Window{precopy_commands}) {
+				$Window{precopy_commands} = {
+					contents => [],
+					conditional => 0,
+					message => 'Resolving catalog initialization commands',
+				};
+			}
+			$wref = $Window{precopy_commands};
+			$pre_post = 2;
+		}
+		elsif ($pre_post == 2) {
+			if(! $Window{postcopy_commands}) {
+				$Window{postcopy_commands} = {
+					contents => [],
+					banner => 'Resolving catalog finalization commands',
+				};
+			}
+			$wref = $Window{postcopy_commands};
+			$pre_post = 3;
+		}
+		next unless $block;
+
+		my @cmds;
+		if($block =~ /^\s*</) {
+			@cmds = read_common_config($block);
+		}
+		else {
+			@cmds = split /\n\n+/, $block;
+		}
+		foreach my $cmd (@cmds) {
+			my $cref;
+			my $unprompted;
+			my $subcode;
+			my $mainparam;
+			my ($command, $prompt);
+			if(ref $cmd) {
+				$cref = $cmd;
+				$cmd = '';
+			}
+			else {
+				$cmd = substitute($cmd);
+				$cmd =~ s/\\\n//g;
+				$cref = {};
+				my $prompt;
+				($command, $prompt) = split /\n/, $cmd, 2;
+				if($prompt =~ s/^\s*(\w+\s*=[^\n]*|{\s*\w+\s*=.*})\s*\n//s) {
+					my $extra = $1;
+#debug("Found command mods: $extra");
+					my $ref = get_option_hash($extra);
+#debug("Command mods: " . uneval($ref));
+					if (ref $ref) {
+						for (keys %$ref) {
+							$cref->{$_} = $ref->{$_};
+						}
+					}
+					else {
+						warn "Unsuccessful command option parse: $extra\n";
+					}
+				}
+				$cref->{help}   = $prompt if ! $cref->{help};
+			}
+			if($cref->{window_indicator}) {
+				$wref ||= $Window{$cref->{name}};
+				for(keys %$cref) {
+					$wref->{$_} = $cref->{$_};
+				}
+				next;
+			}
+			$cref->{widget} = 'yesno' if ! $cref->{widget};
+			$command = $cref->{command} if ! $command;
+			$command =~ s/^\s+//;
+			$command =~ s/\s+$//;
+			$command =~ s/^!// and $> != 0 and $cref->{unprompted} = 1;
+			delete $wref->{conditional}
+				if  $wref->{conditional} eq '0'
+				and $pre_post;
+			
+			if($command =~ s/{\s*([A-Z0-9]+)(\s*\S.*?)?\s*}\s*//) {
+				$mainparam = lc $1;
+				my $test = $2;
+				$test =~	s{(['"]?)__MVC_([A-Z0-9]+)__\1}
+							 {'\$Conf{' . lc $2 . '}'   }eg;
+				$subcode = <<EOF;
+ sub {
+	my \$status;
+#debug("conditional checking param=$mainparam testing=$test Value=\$Conf{$mainparam}");
+	if(\$Conf{$mainparam} $test) {
+		\$status = 1;
+	}
+	else {
+		\$status = 0;
+	}
+#debug("conditional routine returning \$status");
+	return \$status;
+ }
 EOF
+			}
+			elsif ( $cref->{conditional} ) {
+				$cref->{conditional} =~ s/^[A-Z0-9a-z]+$/__MVC_\U${1}__/;
+				$cref->{conditional} =~ s{(['"]?)__MVC_([A-Z0-9]+)__\1}
+										 {'\$Conf{' . lc $2 . '}'   }eg;
+				# Make vi happy: } }
+				$subcode = delete $cref->{conditional};
+			}
 
-	vendroot  =>  <<EOF,
-# The directory where the Interchange software is installed.
+#debug("read_commands:  sub=$subcode");
+			if($subcode) {
+				$subcode = "sub {\n" . $cref->{conditional} . "}"
+					unless $subcode =~ /^\s*sub\s+{/;
+				my $sub = eval $subcode;
+				if($@) {
+debug("read_commands: Problem evaluating sub: $subcode");
+					undef $sub;
+				}
+				$cref->{conditional} = $sub;
+			}
+
+			$cref->{command} = $command;
+			$cref->{label}   = $command if ! $cref->{label};
+			$cref->{name}    = $cmd_num++ unless $cref->{name};
+			my $name = $cref->{name};
+			$Content{$name} = $cref;
+			if(my $gname = $cref->{group}) {
+				$Window{$gname}->{contents} ||= [];
+				push @{$Window{$gname}->{contents}}, $name;
+			}
+			else {
+				push @{$wref->{contents}}, $name;
+			}
+		}
+	}
+	if($pre_post) {
+		return ($Window{precopy_commands}, $Window{postcopy_commands});
+	}
+	else {
+		return $wref;
+	}
+}
+
+
+# Validate a field against:
 #
-EOF
+#   check_regex -- a regular expression which must succeeed
+#   check_blank -- Just needs a non-blank value
+#   check_routine -- a subroutine which can return -1, 0, 1
+#   check_message -- a template (from errmsg) which can be used
+#
+# If the return value is -1, then the error message is assumed
+# to have been handled by the check_routine and is not returned.
+#
+sub validate {
+	my ($val, $parm) = @_;
+	my $thing = $Content{$parm};
+	if(! $parm or ! $thing) {
+		return (0, errmsg('blank'));
+	}
+
+	my $status;
+	my $message = $thing->{check_message};
+	my $errmsg;
+
+	if($thing->{check_regex}) {
+		$errmsg = errmsg('blank');
+		$status = length($val) ? 1 : 0;
+	}
+	elsif($thing->{check_regex}) {
+		my $regex = qr/$thing->{check_regex}/;
+		$status = $val =~ $regex;
+	}
+	elsif($thing->{check_routine}) {
+		($status, $errmsg) = $thing->{check_routine}->($val, $parm);
+	}
+	else {
+		$status = 1;
+	}
 
+	## This allows directly returning error and no confirm screen
+	return $status if abs($status);
+	$message = "%s (value '%s'): failed validation"
+		if ! $message;
+	my $lab = label($parm) || $parm;
+	$message = errmsg($message, $lab, $val, $parm);
+	return($status, $message);
+}
+
+sub prefix {
+	my ($parm, $nodefault, $override) = @_;
+	$parm = lc $parm;
+	if($Alias{$parm} and $Conf{$parm}) {
+		$Conf{$parm} = $Alias{$parm}{$Conf{$parm}};
+	}
+	return $Conf{$parm} if $Conf{$parm};
+	return $ENV{"MVC_\U$parm"} if $ENV{"MVC_\U$parm"};
+	return undef if $nodefault;
+	my $thing = $Content{$parm}{prefix} || $Prefix{$parm};
+	if(ref $thing eq 'CODE') { 
+		return $thing->();
+	}
+	elsif(ref $thing eq 'ARRAY') { 
+		return $thing->[0];
+	}
+	else {
+		return $thing;
+	}
+}
+
+%Special_sub= (
+	cryptpw => sub {
+		my $pw = shift;
+		return $pw if $Conf{alreadycrypt};
+		my @letters = ('A' .. 'Z', 'a' .. 'z');
+		my $salt = $letters[ int rand(scalar @letters) ];
+		$salt .= $letters[ int rand(scalar @letters) ];
+		return crypt($pw, $salt);
+	},
 );
- 
-sub findexe {
-    my($exe) = @_;
-    my($dir,$path) = ('', $ENV{PATH});
-    $path =~ s/\(\)//g;
-    $path =~ s/\s+/ /g;
-    my(@dirs) = split /[\s:]+/, $path;
-    foreach $dir (@dirs) {
-        return "$dir/$exe" if -x "$dir/$exe";
+
+sub substitute {
+	my($parm) = @_;
+	if($parm !~ /^\w+$/) {
+		$parm =~ s/__MVC_([A-Z0-9]+)__/$Conf{lc $1}/eg;
+	}
+	elsif (defined $ENV{"MVC_$parm"}) {
+		$parm = $ENV{"MVC_$parm"};
+	}
+	elsif (my $sub = $Special_sub{lc $parm}) {
+		if(ref $sub) {
+			$parm = $sub->($Conf{lc $parm});
+		}
+		else {
+			$parm = $sub;
+			$parm =~ s/__MVC_([A-Z0-9]+)__/$Conf{lc $1}/eg;
+		}
+	}
+	else {
+		$parm = $Conf{lc $parm};
+	}
+	$parm = '' unless defined $parm;
+	return $parm;
+}
+
+sub sum_it {
+	my ($file) = @_;
+	open(IT, "<$file")
+		or return undef;
+	my $data = '';
+	$data .= $_ while (<IT>);
+	close IT;
+	return unpack("%32c*", $data);
+}
+
+sub strip_na {
+	my $val = shift;
+	return '' if lc($val) eq 'n/a';
+	return $val;
+}
+
+
+sub directory_process {
+    my $dir = shift;
+    $dir =~ s:[/\s]+$::;
+    if($Conf{catuser} and $dir =~ /^~/) {
+        my $userdir = ( getpwnam( $Conf{catuser} ) )[7];
+		$dir =~ s/^~/$userdir/ if $userdir;
     }
-    return '';
+    return $dir;
 }
- 
+
+sub strip_trailing_slash {
+	my $url = shift;
+	$url =~ s:[/\s]+$::;
+	return $url;
+}
+
+
+sub inet_host {
+	return scalar find_inet_info('h');
+}
+
+sub inet_port {
+	return scalar find_inet_info('p');
+}
+
+sub find_inet_info {
+	my $type = shift;
+	my (@hosts);
+	my (@ports);
+	my $prog = "$Conf{relocate}$Conf{vendroot}/src/tlink";
+	my $the_one = sum_it($prog);
+	my $defport = '7786';
+	my $defhost = 'localhost';
+
+	my @poss = glob("$Conf{relocate}$Conf{vendroot}/src/tlink.*.*");
+	for (@poss) {
+		my $name = $_;
+		/tlink\.(.*)\.(\d+)$/
+			or next;
+		my ($h, $p) = ($1, $2);
+		push @hosts, $h;
+		push @ports, $p;
+		my $one = sum_it($_);
+		next unless $one eq $the_one;
+		$defhost = $h;
+		$defport = $p;
+	}
+
+	if(! $type) {
+		my %seen;
+		@ports = grep !$seen{$_}++, @ports;
+		%seen = ();
+		@hosts = grep !$seen{$_}++, @hosts;
+		return (\@hosts, \@ports);
+	}
+	elsif ($type =~ /^h/i) {
+		return $defhost;
+	}
+	elsif ($type =~ /^p/i) {
+		return $defport;
+	}
+}
+
+sub applicable_directive {
+	my ($direc, $routine) = @_;
+	$direc = lc($direc);
+	if($routine) {
+		return undef if ! $routine->($direc);
+	}
+	return $direc if ! defined $IfRoot{$direc};
+	return undef if $Conf{asroot} xor $IfRoot{$direc};
+	return $direc;
+}
+
+
+sub findexe {
+	my($exe) = @_;
+	my($dir,$path) = ('', $ENV{PATH});
+	$path =~ s/\(\)//g;
+	$path =~ s/\s+/ /g;
+	my(@dirs) = split /[\s:]+/, $path;
+	foreach $dir (@dirs) {
+		return "$dir/$exe" if -x "$dir/$exe";
+	}
+	return '';
+}
+
 sub findfiles {
-    my($file) = @_;
+	my($file) = @_;
 	return undef if $^O =~ /win32/i;
 	my $cmd;
 	my @files;
-    if($cmd = findexe('locate')) {
+	if($cmd = findexe('locate')) {
 		@files = `locate \\*/$file`;
 	}
 	else {
@@ -301,6 +1588,25 @@
 	return defined $Pretty{lc $parm} ? $Pretty{lc $parm} : $parm;
 }
 
+sub history {
+	my $parm = shift;
+	$parm = lc $parm;
+	return unless defined $History{$parm};
+	my @things = $History{$parm}->(@_);
+	return wantarray ? @things : \@things;
+}
+
+sub error_message {
+	my($parm) = @_;
+	$parm = lc $parm;
+	return defined $Validate{$parm} ? $Validate{$parm} : '';
+}
+
+sub label {
+	my($parm) = @_;
+	return defined $Label{lc $parm} ? $Label{lc $parm} : '';
+}
+
 sub description {
 	my($parm) = @_;
 	return defined $Desc{lc $parm} ? $Desc{lc $parm} : '';
@@ -321,14 +1627,14 @@
 
 sub get_id {
 	return 'everybody' if $^O =~ /win32/i;
-    my $file = -f "$Global::VendRoot/error.log"
-                ? "$Global::VendRoot/error.log" : '';
-    return '' unless $file;
-    my ($name);
-
-    my($uid) = (stat($file))[4];
-    $name = (getpwuid($uid))[0];
-    return $name;
+	my $file = -f "$Global::VendRoot/error.log"
+				? "$Global::VendRoot/error.log" : '';
+	return '' unless $file;
+	my ($name);
+
+	my($uid) = (stat($file))[4];
+	$name = (getpwuid($uid))[0];
+	return $name;
 }
 
 sub get_ids {
@@ -345,8 +1651,6 @@
 	return ($name,$group);
 }
 
-my $Windows = ($^O =~ /win32/i ? 1 : 0);
-
 sub get_rename {
 	my ($bn, $extra) = @_;
 	$extra = '~' unless $extra;
@@ -356,76 +1660,120 @@
 }
 
 sub compare_file {
-    my($first,$second) = @_;
-    return 0 unless -f $first && -f $second;
-    return 0 unless -s $first == -s $second;
-    local $/;
-    open(FIRST, "< $first") or return undef;
-    open(SECOND, "< $second") or (close FIRST and return undef);
-    binmode(FIRST);
-    binmode(SECOND);
-    $first = '';
-    $second = '';
-    while($first eq $second) {
-        read(FIRST, $first, 1024);
-        read(SECOND, $second, 1024);
-        last if length($first) < 1024;
-    }
-    close FIRST;
-    close SECOND;
-    $first eq $second;
+	my($first,$second) = @_;
+	return 0 unless -f $first && -f $second;
+	return 0 unless -s $first == -s $second;
+	local $/;
+	open(FIRST, "< $first") or return undef;
+	open(SECOND, "< $second") or (close FIRST and return undef);
+	binmode(FIRST);
+	binmode(SECOND);
+	$first = '';
+	$second = '';
+	while($first eq $second) {
+		read(FIRST, $first, 1024);
+		read(SECOND, $second, 1024);
+		last if length($first) < 1024;
+	}
+	close FIRST;
+	close SECOND;
+	$first eq $second;
+}
+ 
+sub set_owner {
+	return unless $> == 0;
+	my($file) = @_;
+	resolve_owner()
+		unless $Conf{interchangeuid};
+	
+	my ($user, $group) = ($Conf{interchangeuid}, $Conf{interchangegid});
+	die errmsg("Can't find info: %s", 'interchangeuid')
+		unless $Conf{interchangeuid};
+	
+	if($Conf{permtype} =~ /^m/i) {
+		$user = $Conf{catuseruid};
+		$group = $Conf{catusergid};
+	}
+	elsif($Conf{permtype} =~ /^g/i) {
+		$group = $Conf{catusergid};
+	}
+	chown($user, $group, $file)
+		or die errmsg(
+				"Couldn't set ownership to UID=%s GID=%s for %s: %s", 
+				$user,
+				$group,
+				$file,
+				$!,
+			);
 }
 
 sub install_file {
-    my ($srcdir, $targdir, $filename, $opt) = @_;
+	my ($srcdir, $targdir, $filename, $opt) = @_;
 	$opt = {} unless $opt;
+	my $save_umask;
+	if($opt->{umask} ) {
+		$save_umask = umask $opt->{umask};
+		local($SIG{__DIE__}) = sub { umask $save_umask; warn @_; exit 1 };
+	}
+
+	my $scale;
+	if($scale = $opt->{scale_call}) {
+		$scale->( 'start', $opt->{scale}, $opt->{message});
+	}
+
 	if (ref $srcdir) {
 		$opt = $srcdir;
 		$srcdir  = $opt->{Source} || die "Source dir for install_file not set.\n";
 		$targdir = $opt->{Target} || die "Target dir for install_file not set.\n";
 		$filename = $opt->{Filename} || die "File name for install_file not set.\n";
 	}
-    my $srcfile  = $srcdir . '/' . $filename;
-    my $targfile = $targdir . '/' . $filename;
-    my $mkdir = File::Basename::dirname($targfile);
-    my $extra;
-    my $perms;
-
-    if(! -d $mkdir) {
-        File::Path::mkpath($mkdir)
-            or die "Couldn't make directory $mkdir: $!\n";
-    }
+	my $srcfile  = $srcdir . '/' . $filename;
+	my $targfile = $targdir . '/' . $filename;
+	my $mkdir = File::Basename::dirname($targfile);
+	my $extra;
+	my $perms;
 
-    if (! -f $srcfile) {
-        die "Source file $srcfile missing.\n";
-    }
-    elsif (
-		$opt->{Perm_hash}
-			and $opt->{Perm_hash}->{$filename}
+
+	if(! -d $mkdir) {
+		File::Path::mkpath($mkdir, undef, $opt->{dmode} || 0777)
+			or die "Couldn't make directory $mkdir: $!\n";
+		chmod($opt->{dmode}, $mkdir) if $opt->{dmode};
+		set_owner($mkdir);
+	}
+
+	if (! -f $srcfile) {
+		die "Source file $srcfile missing.\n";
+	}
+	elsif (
+		$opt->{perm_hash}
+			and $opt->{perm_hash}->{$filename}
 		)
 	{
-        $perms = $opt->{Perm_hash}->{$filename};
+		$perms = $opt->{perm_hash}->{$filename};
 	}
-    elsif ( $opt->{Perms} =~ /^(m|g)/i ) {
-        $perms = (stat(_))[2] | 0660;
+	elsif ($opt->{fmode}) {
+		$perms = $opt->{fmode};
 	}
-    elsif ( $opt->{Perms} =~ /^u/i ) {
-        $perms = (stat(_))[2] | 0600;
+	elsif ( $opt->{Perms} =~ /^(m|g)/i ) {
+		$perms = (stat(_))[2] | 0660;
+	}
+	elsif ( $opt->{Perms} =~ /^u/i ) {
+		$perms = (stat(_))[2] | 0600;
+	}
+	else {
+		$perms = (stat(_))[2] & 0777;
 	}
-    else {
-        $perms = (stat(_))[2] & 0777;
-    }
 
-    if( ! $Windows and -f $targfile and ! compare_file($srcfile, $targfile) ) {
-        open (GETVER, "< $targfile")
-            or die "Couldn't read $targfile for version update: $!\n";
-        while(<GETVER>) {
-            /VERSION\s+=.*?\s+([\d.]+)/ or next;
-            $extra = $1;
-            $extra =~ tr/0-9//cd;
-            last;
-        }
-        $extra = '~' unless $extra;
+	if( ! $Global::Win32 and -f $targfile and ! compare_file($srcfile, $targfile) ) {
+		open (GETVER, "< $targfile")
+			or die "Couldn't read $targfile for version update: $!\n";
+		while(<GETVER>) {
+			/VERSION\s+=.*?\s+([\d.]+)/ or next;
+			$extra = $1;
+			$extra =~ tr/0-9//cd;
+			last;
+		}
+		$extra = '~' unless $extra;
 		my $rename = get_rename($targfile, $extra);
 		while (-f $rename ) {
 			$extra .= '~';
@@ -433,58 +1781,76 @@
 		}
 		rename $targfile, $rename
 			or die "Couldn't rename $targfile to $rename: $!\n";
-    }
+	}
 
-    File::Copy::copy($srcfile, $targfile)
-        or die "Copy of $srcfile to $targfile failed: $!\n";
+	File::Copy::copy($srcfile, $targfile)
+		or die "Copy of $srcfile to $targfile failed: $!\n";
 	if($opt->{Substitute}) {
 			my $bak = "$targfile.mv";
 			rename $targfile, $bak;
-			open(SOURCE, "< $bak")			or die "open $bak: $!\n";
-			open(TARGET, ">$targfile")		or die "create $targfile: $!\n";
+			open(SOURCE, "< $bak")
+				or die errmsg("%s %s: %s\n", errmsg("open"), $bak, $!);
+			open(TARGET, ">$targfile")
+				or die errmsg("%s %s: %s\n", errmsg("create"), $bak, $!);
 			local($/) = undef;
 			my $page = <SOURCE>; close SOURCE;
 
 			$page =~ s/^#>>(.*)(__MVR_(\w+)__.*)\n\1.*/#>>$1$2/mg;
 			$page =~ s/^#>>(.*__MVR_(\w+)__.*)/#>>$1\n$1/mg;
 			1 while $page =~ s/^([^#].*)__MVR_(.*)/$1__MVC_$2/mg;
-			$page =~ s/__MVC_(\w+)__/$opt->{Substitute}{lc $1}/g;
+			$page =~ s/__MV[CS]_([A-Z0-9]+)__/$opt->{Substitute}{lc $1}/g;
 
 			print TARGET $page				or die "print $targfile: $!\n";
 			close TARGET					or die "close $targfile: $!\n";
 			unlink $bak						or die "unlink $bak: $!\n";
 	}
-    chmod $perms, $targfile;
+
+	chmod $perms, $targfile;
+	$scale->('end') if $scale;
+	umask $save_umask if $save_umask;
+	return 1;
+}
+
+sub debug {
+	for(@_) {
+		print DEBUG "$_\n";
+	}
+	return;
 }
 
 sub copy_current_to_dir {
-    my($target_dir, $exclude_pattern) = @_;
+	my($target_dir, $exclude_pattern) = @_;
 	return copy_dir('.', $target_dir, $exclude_pattern);
 }
 
 sub copy_dir {
-    my($source_dir, $target_dir, $exclude_pattern) = @_;
+	my($source_dir, $target_dir, $exclude_pattern, $opt) = @_;
 	return undef unless -d $source_dir;
+	$opt = {} unless $opt;
+	my $scale;
+	if($scale = $opt->{scale_call}) {
+		$scale->('start', $opt->{scale}, $opt->{message});
+	}
 	my $orig_dir;
 	if($source_dir ne '.') {
 		$orig_dir = cwd();
 		chdir $source_dir or die "chdir: $!\n";
 	}
-    my @files; 
-    my $wanted = sub {  
-        return unless -f $_;
-        my $name = $File::Find::name;
-        $name =~ s:^\./::;
-        return if $exclude_pattern and $name =~ m{$exclude_pattern}o;
-        push (@files, $name);
-    };
-    File::Find::find($wanted, '.');  
+	my @files; 
+	my $wanted = sub {  
+		return unless -f $_;
+		my $name = $File::Find::name;
+		$name =~ s:^\./::;
+		return if $exclude_pattern and $name =~ m{$exclude_pattern}o;
+		push (@files, $name);
+	};
+	File::Find::find($wanted, '.');  
 
 	# also exclude directories that match $exclude_pattern
 	@files = grep !m{$exclude_pattern}o, @files if $exclude_pattern;
 	eval {
 		for(@files) {
-			install_file('.', $target_dir, $_);
+			install_file('.', $target_dir, $_, $opt);
 		}
 	};
 	my $msg = $@;
@@ -498,63 +1864,76 @@
 my $History_set;
 my $term;
 eval {
-    require Term::ReadLine;
-    import Term::ReadLine;
-    $term = new Term::ReadLine::Perl 'Interchange Configuration';
-	die "No Term::ReadLine::Perl" unless defined $term;
-
-	readline::rl_bind('C-B', 'catch_at');
-    $Prompt_sub = sub {
-                    my ($prompt, $default) = @_;
-					if($Force) {
-						print "$prompt SET TO --> $default\n";
-						return $default;
-					}
-                    $prompt =~ s/^\s*(\n+)/print $1/ge;
-                    $prompt =~ s/\n+//g;
-                    my $out = $term->readline($prompt, $default);
-					return '@' if ! defined $out;
-					return $out;
-                    };
-    $History_add = sub {
-                    my ($line) = @_;
-                    $term->addhistory($line)
-                        if $line =~ /\S/;
-                    };
-    $History_set = sub {
-						$term->SetHistory(@_);
-					};
+	require Term::ReadLine;
+	import Term::ReadLine;
+
+	$term = new Term::ReadLine 'Interchange Configuration';
+	die "No Term::ReadLine" unless defined $term;
+
+	readline::rl_set('CompleteAddsuffix', 'Off');
+	readline::rl_set('TcshCompleteMode', 'On');
+	$Prompt_sub = sub {
+		my ($prompt, $default) = @_;
+		if($Force) {
+			print "$prompt SET TO --> $default\n";
+			return $default;
+		}
+		$prompt =~ s/^\s*(\n+)/print $1/ge;
+		$prompt =~ s/\n+//g;
+		readline::rl_bind('C-x', 'catch-cancel');
+		readline::rl_bind('C-b', 'catch-backward');
+		readline::rl_bind('C-y', 'catch-help');
+		readline::rl_bind('C-f', 'catch-forward');
+		if(! $Conf{vi_edit_mode}) {
+			readline::rl_bind('"\M-\OP"', 'catch-help');
+			readline::rl_bind('"\M-[20"', 'catch-backward');
+			readline::rl_bind('"\M-[21"', 'catch-forward');
+			#readline::rl_bind('"\M-[1"', 'catch-cancel');
+			readline::rl_bind('"\M-[5"', 'catch-backward');
+			readline::rl_bind('"\M-[6"', 'catch-forward');
+		}
+		my $out = $term->readline($prompt, $default);
+		return "\cB" if ! defined $out;
+		return $out;
+	};
+	$History_add = sub {
+		my ($line) = @_;
+		$term->addhistory($line)
+			if $line =~ /\S/;
+	};
+	$History_set = sub {
+		$term->SetHistory(@_);
+	};
 	$History = 1;
 
 };
 
-
 sub prompt {
-    return &$Prompt_sub(@_)
-        if defined $Prompt_sub;
-    my($prompt) = shift || '? ';
-    my($default) = shift;
+	return &$Prompt_sub(@_)
+		if defined $Prompt_sub;
+	my($prompt) = shift || '? ';
+	my($default) = shift;
 	if($Force) {
 		print "$prompt SET TO --> $default\n";
 		return $default;
 	}
-    my($ans);
+	my($ans);
 
-    print $prompt;
-    print "[$default] " if $default;
+	print $prompt;
+	print "[$default] " if $default;
 	local ($/) = "\n";
-    chomp($ans = <STDIN>);
-    length($ans) ? $ans : $default;
+	chomp($ans = <STDIN>);
+	length($ans) ? $ans : $default;
 }
 
 sub addhistory {
 	return '' unless defined $History_add;
-	&{$History_add}(@_);
+	return $History_add->(@_);
 }
 
 sub sethistory {
 	return '' unless defined $History_set;
-	&{$History_set}(@_);
+	return $History_set->(@_);
 }
 
 sub do_msg {
@@ -567,66 +1946,103 @@
 	return $msg;
 }
 
-
 sub add_catalog {
-		my ($file, $directive, $configname, $value, $dynamic) = @_;
-		my ($newcfgline, $mark, @out);
-		my ($tmpfile) = "$file.$$";
-		if (-f $file) {
-			rename ($file, $tmpfile)
-				or die "Couldn't rename $file: $!\n";
-		}
-		else {
-			File::Copy::copy("$file.dist", $tmpfile);
-		}
-		open(CFG, "< $tmpfile")
-			or die "Couldn't open $tmpfile: $!\n";
-		$newcfgline = sprintf "%-19s %s\n", $directive, $value;
-		while(<CFG>) {
-			$mark = $. if /^#?\s*catalog\s+/i;
-			warn "\nDeleting old configuration $configname.\n"
-				if s/^(\s*$directive\s+$configname\s+)/#$1/io;
-			push @out, $_;
-		}
-		close CFG;
-		open(NEWCFG, ">$file")
-			or die "\nCouldn't write $file: $!\n";
-		if (defined $mark) {
-			print NEWCFG @out[0..$mark-1];
-			print NEWCFG $newcfgline;
-			print NEWCFG @out[$mark..$#out];
-		}
-		else { 
-			warn "\nNo $directive previously defined. Adding $configname at top.\n";
-			print NEWCFG $newcfgline;
-			print NEWCFG @out;
-		}
-		close NEWCFG || die "close: $!\n";
-		unlink $tmpfile;
-
-		if($dynamic and ! $Windows) {
-			my $pidfile = $dynamic;
-			$pidfile =~ s:/[^/]+$::;
-			$pidfile .= "/$Global::ExeName.pid";
-			my $pid;
-			PID: {
-				local ($/);
-				open(PID, "< $pidfile") or die "open $pidfile: $!\n";
-				$pid = <PID>;
-				$pid =~ /(\d+)/;
-				$pid = $1;
-			}
-
-			open(RESTART, "<+$dynamic") or
-				open(RESTART, ">>$dynamic") or
-					die "Couldn't write $dynamic to add catalog: $!\n";
-			Vend::Util::lockfile(\*RESTART, 1, 1) 	or die "lock $dynamic: $!\n";
-			printf RESTART "%-19s %s\n", $directive, $value;
-			Vend::Util::unlockfile(\*RESTART) 		or die "unlock $dynamic: $!\n";
-			close RESTART;
-			kill 'HUP', $pid;
-		}
-		1;
+	my ($file, $directive, $configname, $value) = @_;
+	if(! $file) {
+		$file = "$Conf{relocate}$Global::ConfigFile";
+	}
+	$configname = $Conf{catalogname} if ! $configname;
+	$directive  = 'Catalog'          if ! $directive;
+	if (! $value) {
+		$value = "$Conf{catalogname} $Conf{catroot} $Conf{cgiurl}";
+		$value .= " $Conf{aliases}" if $Conf{aliases};
+	}
+	my ($newcfgline, $mark, @out);
+	my ($tmpfile) = "$file.$$";
+	if (-f $file) {
+		rename ($file, $tmpfile)
+			or die "Couldn't rename $file: $!\n";
+	}
+	else {
+		File::Copy::copy("$file.dist", $tmpfile)
+			or die errmsg("Couldn't find interchange.cfg");
+	}
+	open(CFG, "< $tmpfile")
+		or die "Couldn't open $tmpfile: $!\n";
+	$newcfgline = sprintf "%-19s %s\n", $directive, $value;
+	while(<CFG>) {
+		$mark = $. if /^#?\s*catalog\s+/i;
+debug("\nDeleting old configuration $configname.\n") if s/^(\s*$directive\s+$configname\s+)/#$1/io;
+		push @out, $_;
+	}
+	close CFG;
+	open(NEWCFG, ">$file")
+		or die "\nCouldn't write $file: $!\n";
+	if (defined $mark) {
+		print NEWCFG @out[0..$mark-1];
+		print NEWCFG $newcfgline;
+		print NEWCFG @out[$mark..$#out];
+	}
+	else { 
+		warn "\nNo $directive previously defined. Adding $configname at top.\n";
+		print NEWCFG $newcfgline;
+		print NEWCFG @out;
+	}
+	close NEWCFG || die errmsg("%s %s: %s\n", 'close', $file, $!);
+	unlink $tmpfile;
+}
+
+sub server_running {
+	local ($/);
+debug("in server_running, pid file=$Global::PIDfile");
+	open(PID, "+< $Global::PIDfile")
+		or return undef;
+debug("opened PID file");
+	if(Vend::Util::lockfile(\*PID, 1, 0)) {
+debug("PID file not locked");
+		## Daemon not running;
+		close PID;
+		return undef;
+	}
+	my $pid = <PID>;
+debug("PID=$pid");
+	$pid =~ /(\d+)/;
+	$pid = $1;
+	return $pid;
+}
+
+sub run_catalog {
+	my ($file, $directive, $configname, $value) = @_;
+	$Conf{relocate}
+		and die errmsg("Can't add catalog to running server when relocating.");
+ 
+	if(! $file) {
+		my $fn = 'restart';
+		$file  = "$Global::RunDir/$fn";
+	}
+
+	$configname = $Conf{catalogname} if ! $configname;
+	$directive  = 'Catalog'          if ! $directive;
+	if (! $value) {
+		$value = "$Conf{catalogname} $Conf{catroot} $Conf{cgiurl}";
+		$value .= " $Conf{aliases}" if $Conf{aliases};
+	}
+	my $pid = server_running();
+	if(! defined $pid) {
+		die errmsg("Can't add %s to server: not running", $configname);
+	}
+
+	open(RESTART, "<+$file")
+		or open(RESTART, ">>$file")
+			or die errmsg("%s %s: %s\n", errmsg("write"), $file, $!);
+	Vend::Util::lockfile(\*RESTART, 1, 1)
+			or die errmsg("%s %s: %s\n", errmsg("lock"), $file, $!);
+	printf RESTART "%-19s %s\n", $directive, $value;
+	Vend::Util::unlockfile(\*RESTART) 
+		or die errmsg("%s %s: %s\n", errmsg("unlock"), $file, $!);
+	close RESTART;
+	set_owner($file);
+	kill 'HUP', $pid;
 }
 
 my %Http_hash = (
@@ -670,8 +2086,8 @@
 	close(HTTPDCONF);
 
 	
-	if($data =~ s/^\s*resourceconfig\s+(.*)//) {
-		$newfile = $1;
+	if($data =~ s/^\s*resourceconfig\s+("?)(.*)\1//i) {
+		$newfile = $2;
 	}
 
 	unless(defined $newfile) {
@@ -698,6 +2114,15 @@
 				</virtualhost>!
 				$virtual->{$1} = $2; ''!xieg;
 
+	$data =~ s!
+				<virtualhost
+				\s+
+					([^>\n]+)
+				\s*>\s+
+					([\000-\377]*?)
+				</virtualhost>!
+				$virtual->{$1} = $2; ''!xieg;
+
 	$virtual->{' '} = $data;
 
 	my @data;
@@ -726,40 +2151,46 @@
 		}
 		
 		if($handle eq ' ') {
-			$servname = `hostname` unless $servname;
+			$servname = Sys::Hostname::hostname() unless $servname;
 			$servname =~ s/\s+$//;
 			$main = $servname;
+			$servers->{$servname} = {} if ! $servers->{$servname};
+			$servers->{$servname}{Master} = 1;
 		}
 		next unless $servname;
 
-		my ($line, $directive, $param, $key, $val);
-		foreach $line (@data) {
+		my $ref = $servers->{$servname};
+
+		$ref->{servername} = $servname;
+
+		foreach my $line (@data) {
 			$line =~ s/^\s+//;
 			$line =~ s/\s+$//;
-			($directive,$param) = split /\s+/, $line, 2;
+			my ($key, $val);
+			my ($directive,$param) = split /\s+/, $line, 2;
 			$directive = lc $directive;
 			if(defined $Http_hash{$directive}) {
-				$servers->{$servname}->{$directive} = {}
-					unless defined $servers->{$servname}->{$directive};
-				($key,$val) = split /\s+/, $param, 2;
+				$ref->{$directive} = {}
+					unless defined $ref->{$directive};
+				my ($key,$val) = split /\s+/, $param, 2;
 				$val =~ s/^\s*"// and $val =~ s/"\s*$//;
 				if (defined $Http_process{$directive}) {
-					$key = &{$Http_process{$directive}}('key', $key);
-					$val = &{$Http_process{$directive}}('value', $val);
+					$key = $Http_process{$directive}->('key', $key);
+					$val = $Http_process{$directive}->('value', $val);
 				}
-				$servers->{$servname}->{$directive}->{$key} = $val;
+				$ref->{$directive}{$key} = $val;
 			}
 			elsif(defined $Http_scalar{$directive}) {
 				$param =~ s/^"// and $param =~ s/"\s*$//;
-				if (defined $servers->{$servname}->{$directive}) {
-					undef $servers->{$servname};
+				if (defined $ref->{$directive}) {
+					undef $ref;
 					$Error = "$directive defined twice in $servname, only allowed once.";
 					return undef;
 				}
 				if (defined $Http_process{$directive}) {
-					$param = &{$Http_process{$directive}}($param);
+					$param = $Http_process{$directive}->($param);
 				}
-				$servers->{$servname}->{$directive} = $param;
+				$ref->{$directive} = $param;
 			}
 		}
 	}
@@ -767,12 +2198,456 @@
 	return $servers;
 }
 
+sub substitute_cryptpw {
+	my $pw = $Conf{cryptpw};
+	return unless $pw;
+	return if $Conf{alreadycrypt}++;
+	my @letters = ('A' .. 'Z', 'a' .. 'z');
+	my $salt = $letters[ int rand(scalar @letters) ];
+	$salt .= $letters[ int rand(scalar @letters) ];
+	$Conf{cryptpw} = crypt($pw, $salt);
+}
+
+sub unique_ary {
+	my %seen;
+	%seen = ();
+	return ( grep !$seen{$_}++, @_ );
+}
+
+sub resolve_owner {
+	my $cref = shift || \%Conf;
+	die errmsg("Usage: %s", "resolve_owner({ })")
+		unless ref $cref eq 'HASH';
+	return unless $> == 0 || $cref->{asroot};
+	my @things = qw/interchangeuser interchangegroup catuser catgroup/;
+	my ($icu, $icg, $catu, $catg) = @$cref{@things};
+
+	$catu = $icu if ! $catu;
+	
+	# Default groups
+	my $icd;
+	my $catd;
+
+	my($icu_uid, $catu_uid, $icg_gid, $catg_gid);
+	$icu_uid = getpwnam($icu)
+		or die errmsg("User does not exist: %s\n", $icu);
+	$catu_uid = getpwnam($catu)
+		or die errmsg("User does not exist: %s\n", $catu);
+
+	if($cref->{permtype} =~ /^\s*m/i) {
+		$icg_gid = (getpwnam($catu))[3] if ! $icg;
+		$catg_gid = (getpwnam($catu))[3];
+	}
+	elsif($cref->{permtype} =~ /^\s*g/i) {
+		$icg_gid = (getpwnam($icu))[3] if ! $icg;
+		$catg_gid = (getpwnam($icu))[3];
+	}
+	else {
+		$icg_gid = (getpwnam($catu))[3] if ! $icg;
+		$catg_gid = (getpwnam($catu))[3];
+	}
+	$icg_gid = (getpwnam($icu))[3] if ! $icg_gid;
+	$catg_gid = (getpwnam($catu))[3] if ! $catg_gid;
+
+	@$cref{qw/
+			interchangeuid
+			interchangegid
+			catuid
+			catgid
+			/} = ($icu_uid, $icg_gid, $catu_uid, $catg_gid);
+	return $cref;
+}
+
+sub hammer_symlinks {
+	my $dir = shift;
+	File::Find::find(
+					sub {
+						return if ! -l $_;
+						unlink $_
+							or die "couldn't unlink $File::Find::name: $!\n";
+					},
+					$dir,
+	 );
+	 return 1;
+}
+
+
+
+sub check_root_execute { 
+	my $dir = shift;
+	return undef if ! -d $dir;
+	my @disc;
+	my $wanted = sub {
+		my @stat = stat($_);
+		my $type = -d _ ? 'directory' : 'file';
+		push @disc, [ $type, $File::Find::name, l('not owned by root')]
+			if $stat[4] != 0;
+		push @disc, [ $type, $File::Find::name, l('world writable')   ]
+			if (07777 & $stat[2] & 02);
+		push @disc, [ $type, $File::Find::name, l('group writable')   ]
+			if (07777 & $stat[2] & 020);
+	};
+
+	File::Find::find($wanted, $dir);
+	return 1 if ! @disc;
+	my $out = "";
+	for (@disc) {
+		$_->[1] =~ s!^$dir/!!;
+		$out .= errmsg("  %s %s is %s\n", @$_);
+	}
+	return $out;
+}
+
+sub compile_link {
+	my $cref = shift || \%Conf;
+	for( qw/linkmode cgiurl vendroot cgidir cgiurl/) {
+		die errmsg("improper reference passed, missing: %s", $_)
+			if ! $cref->{$_};
+	}
+	return 1 if $cref->{linkmode} =~ /^\s*n/i;
+	my @args;
+	my $cginame = $cref->{cgiurl};
+	$cginame =~ s:.*/::;
+	$cref->{cgifile} = $cginame = "$cref->{relocate}$cref->{cgidir}/$cginame";
+	die errmsg("%s %s: %s", 'target file', $cref->{cgifile}, 'is a directory')
+		if -e $cref->{cgifile};
+	my $exec = "$cref->{relocate}$cref->{vendroot}/bin/compile_link";
+	die errmsg("%s %s: %s", 'executable file', $exec, 'not executable')
+		if ! -x $exec;
+	push @args, (
+			$cref->{linkmode} =~ /^\s*u/i 
+			? '--unixmode'
+			: '--inetmode'
+		);
+	push @args, "--source=$cref->{relocate}$cref->{vendroot}/src";
+	push @args, "--outputfile=$cref->{relocate}$cref->{cgifile}";
+	push @args, "--port=$cref->{linkport}"
+		if $cref->{linkport};
+	push @args, "--host=$cref->{linkhost}"
+		if $cref->{linkhost};
+	push @args, "--nosuid"
+		if $cref->{cgiwrap};
+	push @args, "--nosuid"
+		if $cref->{cgiwrap};
+	for (@args) {
+		die errmsg("Improper argument: %s", $_)
+			if /"/;
+		$_ = qq{"$_"};
+	}
+	my $dir = $ENV{TMP} || '/tmp';
+	my $bdir    = "$dir/compile_link.$$";
+	my $outfile = "$bdir/build.out";
+	my $errfile = "$bdir/build.err";
+	File::Path::mkpath($bdir);
+	push @args, "--build=$bdir";
+	
+	system join " ",
+			   $exec,
+			   @args,
+			   "2>$errfile",
+			   ">$outfile";
+	
+	if($?) {
+		my $msg = `cat $errfile`;
+		die errmsg("Failed to compile and copy link:\n\n%s", $msg);
+	}
+	File::Path::rmtree($bdir);
+	unlink $errfile;
+	unlink $outfile;
+	return 1;
+}
+
+my @Action;
+
+sub evaluate_action {
+	my $act = shift;
+	ref($act) eq 'HASH' or die "usage: evaluate_action(\%action)";
+	my $orig_dir;
+	my $error;
+	eval {
+		if($act->{chdir}) {
+			$orig_dir = cwd();
+			my $dir = $act->{chdir};
+			$dir = substitute($dir) if $dir =~ /__MVC_/;
+			chdir $dir
+				or die errmsg("Unable to change directory to %s.", $dir) . "\n";
+		}
+		if($act->{from_dir} and $act->{to_dir}) {
+			if($Conf{relocate}) {
+				$act->{to_dir} = "$Conf{relocate}$act->{to_dir}";
+				$act->{from_dir} = "$Conf{relocate}$act->{from_dir}";
+			}
+			copy_dir($act->{from_dir}, $act->{to_dir}, undef, $act);
+			if($act->{delete_from}) {
+				File::Path::rmtree($act->{from_dir});
+			}
+		}
+		if(my $sub = $act->{sub}) {
+			my $args = $act->{args} || [];
+			$sub->(@$args);
+		}
+		if(my $cmd = $act->{command}) {
+			$cmd = substitute($cmd) if $cmd =~ /__MVC_/;
+			system $cmd;
+			if($?) {
+				my $status = $? >> 8;
+				die errmsg(
+						"Command %s returned status %s: %s",
+						$cmd,
+						$status,
+						$!,
+					) . "\n";
+			}
+		}
+	};
+	$error = $@ if $@;
+	chdir $orig_dir if $orig_dir;
+	die $error if $error;
+	return;
+}
+
+sub build_cat {
+	my ($scale, $die, $warn, $opt) = @_;
+debug("build_cat called scalesub=$scale");
+	
+	$opt ||= {};
+	(
+		$scale  && ! ref $scale eq 'CODE'
+			or
+		$die    && ! ref $die   eq 'CODE'
+			or
+		$warn   && ! ref $warn  eq 'CODE'
+			or
+		$opt    && ! ref $opt   eq 'HASH'
+	) and die errmsg("usage: %s", 'build_cat(\&scale,\&die,\&warn,$hashref)');
+
+	$die  = sub { die  errmsg(@_) . "\n"; } if ! $die;
+	$warn = sub { die  errmsg(@_) . "\n"; } if ! $die;
+
+	my $cref = $opt->{configuration} || \%Conf;
+
+	my @action;
+
+#	Here we create an array of hashes. The elements:
+#	structure is:
+#		
+#		from_dir       =>  directory to copy from (done before sub)
+#		to_dir         =>  directory to copy to
+#		delete_from    =>  delete from_dir when finished
+#		sub		       =>  subroutine to run
+#		args           =>  subroutine args
+#		message        =>  message for scale routine
+#		scale          =>  value to be added to scale when done
+#		error          =>  Error message if fails
+#		error_ok       =>  Ignore error if it occurs
+#		error_warn     =>  Issue conditional warning if error
+#                          (dies if in batch mode)
+#
+#   If "action_ref" option key is provided, it is used instead. (Unlikely
+#   ever to be used, obviously.)
+
+	CREATEACTION: {
+		if($opt->{action_ref}) {
+			@action = @{$opt->{action_ref}};
+			last CREATEACTION;
+		}
+
+		push @action, {
+					sub => \&substitute_cryptpw,
+					message => errmsg('Encrypting passwords'),
+					scale => 1,
+				};
+
+		push @action, {
+					sub => \&compile_link,
+					args => [ $cref ],
+					message => errmsg('Compiling link programs'),
+					scale => 4,
+				};
+
+		push @action, { 
+				sub => sub {
+					hammer_symlinks("$Conf{relocate}$Conf{catroot}"),
+				},
+				message => errmsg("Cleaning up catalog directory"),
+				scale => 1,
+		} if -d "$Conf{relocate}$Conf{catroot}";
+
+		if(my $wref = $Window{precopy_commands}) {
+			$wref->{contents} ||= [];
+			for(@{$wref->{contents}}) {
+				my $cref = $Content{$_};
+				$cref->{scale} = 1 unless defined $cref->{scale};
+				$cref->{message} = "Running $cref->{command}"
+					unless $cref->{message};
+				$cref->{error_warn} = 1
+					unless $cref->{error_ok};
+				if(! $cref->{conditional} or $cref->{conditional}->()) {
+					push @action, $cref;
+				}
+			}
+		}
+		push @action, {
+					from_dir	=> "$Conf{vendroot}/$Conf{demotype}",
+					to_dir		=>  $Conf{catroot},
+					dmode		=>  02770,
+					fmode		=>  0660,
+					Substitute  =>  \%Conf,
+					error 		=>  $Build_error{demotype},
+					message		=>  errmsg("Copying base demo skeleton"),
+					scale		=>  3,
+				};
+
+		push @action, {
+					delete_from =>  1,
+					dmode		=>  0775,
+					error 		=>  $Build_error{demotype},
+					fmode		=>  0664,
+					from_dir	=>  "$Conf{catroot}/html",
+					message		=>  errmsg("Copying public HTML files"),
+					scale		=>  1,
+					to_dir		=>  $Conf{samplehtml},
+				};
+
+		push @action, {
+					delete_from =>  1,
+					dmode		=>  0775,
+					error 		=>  $Build_error{demotype},
+					fmode		=>  0664,
+					from_dir	=>  "$Conf{catroot}/images",
+					message		=>  errmsg("Copying image files"),
+					scale		=>  2,
+					symlink_to  =>  1,
+					to_dir		=>  $Conf{imagedir},
+				};
+
+		if(my $wref = $Window{postcopy_commands}) {
+			$wref->{contents} ||= [];
+			for(@{$wref->{contents}}) {
+				my $cref = $Content{$_};
+				$cref->{scale} = 1 unless defined $cref->{scale};
+				$cref->{chdir} = $Conf{catroot} unless $cref->{chdir};
+				$cref->{message} = "Running $cref->{command}"
+					unless $cref->{message};
+				$cref->{error_warn} = 1
+					unless $cref->{error_ok};
+				if(! $cref->{conditional} or $cref->{conditional}->()) {
+					push @action, $cref;
+				}
+			}
+		}
+
+		push @action, {
+				sub => \&add_catalog,
+				message		=>  errmsg("Adding catalog to interchange.cfg"),
+				scale => 1,
+		} if $cref->{add_catalog};
+debug("run_catalog=$cref->{run_catalog} server_running=" . server_running());
+		push @action, {
+				sub => \&run_catalog,
+				message		=>  errmsg("Running catalog"),
+				scale => 1,
+		} if $cref->{run_catalog} and server_running();
+	}
+	my $total_scale = 0;
+	foreach my $act (@action) {
+		$total_scale += $act->{scale};
+	}
+
+debug("total scale amount=$total_scale scalesub=$scale");
+	## install_scale returns a closure implementing whatever scale
+	## there is....
+	my $msg = errmsg("Installing catalog: %s", $Conf{catalogname});
+	my $scale_call;
+debug("scale_call=$scale_call");
+	if(! $opt->{event_driven}) {
+		$scale_call = $scale->($total_scale, $msg)
+			if $scale;
+		foreach my $act (@action) {
+debug("action: " . uneval($act));
+			$scale_call->('start', $act->{scale}, errmsg($act->{message}))
+				if $scale_call;
+			#select(undef,undef,undef, .75);
+			my $orig_dir;
+			eval {
+				evaluate_action($act);
+			};
+			if(! $@) {
+				$scale_call->('end')
+					if $scale_call;
+			}
+			elsif($act->{error_ok}) {
+debug("action error_ok: $@");
+				my $msg = errmsg($act->{message}) . "..." . errmsg('failed') . ".";
+				$scale_call->('end', undef, $msg)
+					if $scale_call;;
+			}
+			elsif($act->{error_warn}) {
+debug("action error_warn: $@");
+				my $msg = $@;
+				$warn->($msg) 
+					or do {
+						$die->($msg);
+						return undef;
+					};
+			}
+			else {
+debug("action fatal_error: $@");
+				$die->( errmsg("Error installing catalog %s: %s"));
+				return undef;
+			}
+			chdir $orig_dir if $orig_dir;
+		}
+		$scale_call->('finish')
+			if $scale_call;
+	}
+	elsif($scale) {
+		eval {
+			$scale->($total_scale, $msg, \&evaluate_action, @action);
+		};
+		if($@) {
+debug("action fatal_error: $@");
+			$die->( errmsg("Error installing catalog %s: %s"));
+			return undef;
+		}
+	}
+	else {
+		die "Must have scale subroutine call if event-driven\n";
+	}
+
+}
+
 package readline;
 
 use vars qw/$AcceptLine/;
 
-sub F_Catch_at {
-		$AcceptLine = '@';
+sub discard_ReadKey {
+	return unless $Term::ReadKey::VERSION;
+	my $timeout = shift || '-1';
+	local($^W);
+	eval {
+			Term::ReadKey::ReadKey(-1, $readline::term_IN);
+	};
+}
+
+sub F_CatchHelp {
+		$AcceptLine = "\cY";
+}
+
+sub F_CatchCancel {
+		$AcceptLine = "\cX";
+		discard_ReadKey(1);
+}
+
+sub F_CatchBackward {
+		$AcceptLine = "\cB";
+		discard_ReadKey(1);
+}
+
+sub F_CatchForward {
+		$AcceptLine = "\cF";
+		discard_ReadKey(1);
 }
 
+1;
 __END__



1.14.4.9  +1130 -832 interchange/lib/Vend/Order.pm


rev 1.14.4.9, prev_rev 1.14.4.8
Index: Order.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Order.pm,v
retrieving revision 1.14.4.8
retrieving revision 1.14.4.9
diff -u -r1.14.4.8 -r1.14.4.9
--- Order.pm	15 Apr 2001 13:54:56 -0000	1.14.4.8
+++ Order.pm	25 Jan 2003 22:21:28 -0000	1.14.4.9
@@ -1,14 +1,11 @@
-#!/usr/bin/perl
+# Vend::Order - Interchange order routing routines
 #
-# $Id: Order.pm,v 1.14.4.8 2001/04/15 13:54:56 racke Exp $
+# $Id: Order.pm,v 1.14.4.9 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2001 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # CyberCash 3 native mode enhancements made by and
 # Copyright 1998 by Michael C. McCune <mmccune@ibm.net>
@@ -31,47 +28,281 @@
 package Vend::Order;
 require Exporter;
 
-$VERSION = substr(q$Revision: 1.14.4.8 $, 10);
+$VERSION = substr(q$Revision: 1.14.4.9 $, 10);
 
 @ISA = qw(Exporter);
 
 @EXPORT = qw (
 	add_items
+	do_order
 	check_order
 	check_required
-	cyber_charge
 	encrypt_standard_cc
 	mail_order
 	onfly
 	route_order
+	update_quantity
 	validate_whole_cc
 );
-# LEGACY4
+
 push @EXPORT, qw (
 	send_mail
 );
-# END LEGACY4
 
 use Vend::Util;
 use Vend::Interpolate;
 use Vend::Session;
 use Vend::Data;
 use Text::ParseWords;
+use Errno qw/:POSIX/;
+use strict;
+
+use autouse 'Vend::Error' => qw/do_lockout/;
+
+# Instance variables
+my (
+	@Errors,
+	$Update,
+	$Fatal,
+	$And,
+	$Final,
+	$Success,
+	$Profile,
+	$Tables,
+	$Fail_page,
+	$Success_page,
+	$No_error,
+	$OrderCheck,
+);
+
+sub reset_order_vars {
+	@Errors = ();
+	$Update = 0;
+	$Fatal = 0;
+	undef $And;
+	$Final = 0;
+	undef $Success;
+	undef $Profile;
+	undef $Tables;
+	undef $Fail_page;
+	undef $Success_page;
+	undef $No_error;
+
+	# copy global order check routines
+	$OrderCheck = { %{$Global::OrderCheck || {} }};
+
+	# overlay any catalog order check routines
+	my $r;
+	if ($r = $Vend::Cfg->{CodeDef}{OrderCheck} and $r = $r->{Routine}) {
+		for (keys %$r) {
+			$OrderCheck->{$_} = $r->{$_};
+		}
+	}
 
-my @Errors = ();
-my $Fatal = 0;
-my $Final = 0;
-my $Success;
-my $Profile;
-my $Fail_page;
-my $Success_page;
+	return;
+}
+
+my %Parse = (
+
+	'&charge'       =>	\&_charge,
+	'&credit_card'  =>	\&_credit_card,
+	'&return'       =>	\&_return,
+	'&update'      	=>	\&_update,
+	'&fatal'       	=>	\&_fatal,
+	'&and'       	=>	\&_and_check,
+	'&or'       	=>	\&_or_check,
+	'&format'		=> 	\&_format,
+	'&tables'		=> 	sub { $Tables = $_[1]; return 1; },
+	'&noerror'		=> 	sub { $No_error = $_[1] },
+	'&success'		=> 	sub { $Success_page = $_[1] },
+	'&fail'         =>  sub { $Fail_page    = $_[1] },
+	'&final'		=>	\&_final,
+	'&calc'			=>  sub { Vend::Interpolate::tag_calc($_[1]) },
+	'&perl'			=>  sub { Vend::Interpolate::tag_perl($Tables, {}, $_[1]) },
+	'&test'			=>	sub {		
+								my($ref,$params) = @_;
+								$params =~ s/\s+//g;
+								return $params;
+							},
+	'length'		=>  sub {
+							my($name, $value, $msg) = @_;
+							$msg =~ s/^(\d+)(?:\s*-(\d+))?\s*//
+								or return undef;
+							my $min = $1;
+							my $max = $2;
+							my $len = length($value);
+
+							if($len < $min) {
+								$msg = errmsg(
+										"%s length %s less than minimum length %s.",
+										$name,
+										$len,
+										$min) if ! $msg;
+								return(0, $name, $msg);
+							}
+							elsif($max and $len > $max) {
+								$msg = errmsg(
+										"%s length %s more than maximum length %s.",
+										$name,
+										$len,
+										$max) if ! $msg;
+								return(0, $name, $msg);
+							}
+							return (1, $name, '');
+						},
+	'filter'			=> sub {		
+							my($name, $value, $code) = @_;
+							my $message;
+							my $filter;
+
+							$code =~ s/\\/\\\\/g;
+							if($code =~ /(["']).+?\1$/) {
+								my @code = Text::ParseWords::shellwords($code);
+								$message = pop(@code);
+								$filter = join " ", @code;
+							}
+							else {
+								($filter, $message) = split /\s+/, $code, 2;
+							}
+
+							my $test = Vend::Interpolate::filter_value($filter, $value, $name);
+							if($test ne $value) {
+								$message ||= errmsg("%s caught by filter %s", $name, $filter);
+								return ( 0, $name, $message);
+							}
+							return (1, $name, '');
+						},
+	'regex'			=>	sub {		
+							my($name, $value, $code) = @_;
+							my $message;
+
+							$code =~ s/\\/\\\\/g;
+							my @code = Text::ParseWords::shellwords($code);
+							if($code =~ /(["']).+?\1$/) {
+								$message = pop(@code);
+							}
+
+							for(@code) {
+								my $negate;
+								s/^!\s*// and $negate = 1;
+								my $op = $negate ? "!~" :  '=~';
+								my $regex = qr($_);
+								my $status;
+								if($negate) {
+									$status = ($value !~ $regex);
+								}
+								else {
+									$status = ($value =~ $regex);
+								}
+								if(! $status) {
+									$message = errmsg(
+										"failed pattern - %s",
+										"'$value' $op $_"
+										) if ! $message;
+									return ( 0, $name, $message);
+								}
+							}
+							return (1, $name, '');
+						},
+	'unique'			=> sub {
+							my($name, $value, $code) = @_;
+
+							$code =~ s/(\w+)(:+(\w+))?\s*//;
+							my $tab = $1
+								or return (0, $name, errmsg("no table specified"));
+							my $col = $3;
+							my $msg = $code;
+
+							my $db = database_exists_ref($tab)
+								or do {
+									$msg = errmsg(
+										"Table %s doesn't exist",
+										$tab,
+									);
+									return(0, $name, $msg);
+								};
+							my $used;
+							if(! $col) {
+								$used = $db->record_exists($value);
+							}
+							else {
+#::logDebug("Doing foreign key check, tab=$tab col=$col value=$value");
+								$used = $db->foreign($value, $col);
+							}
+
+#::logDebug("Checking unique, tab=$tab col=$col, used=$used");
+							if(! $used) {
+								return (1, $name, '');
+							}
+							else {
+								$msg = errmsg(
+										"Key %s already exists in %s, try again.",
+										$value,
+										$tab,
+									) unless $msg;
+								return(0, $name, $msg);
+							}
+
+						},
+	'&set'			=>	sub {		
+								my($ref,$params) = @_;
+								my ($var, $value) = split /\s+/, $params, 2;
+								$::Values->{$var} = $value;
+							},
+	'&setcheck'			=>	sub {		
+								my($ref,$params) = @_;
+								my ($var, $value) = split /\s+/, $params, 2;
+								$::Values->{$var} = $value;
+								my $msg = errmsg("%s set failed.", $var);
+								return ($value, $var, $msg);
+							},
+	future => sub {
+							my($name, $value, $code) = @_;
+							my $message;
+
+							my @code = Text::ParseWords::shellwords($code);
+							if($code =~ /(["']).+?\1$/) {
+								$message = pop(@code);
+							}
+							my $adjust = join " ", @code;
+							if(! $message) {
+								$message = errmsg(
+											"Date must be in the future at least %s",
+											$adjust,
+											);
+							}
+							if($value =~ /\0/) {
+								$value = Vend::Interpolate::filter_value(
+											'date_change',
+											$value,
+										);
+							}
+							my $current = Vend::Interpolate::mvtime(
+													undef,
+													{ adjust => $adjust },
+													"%Y%m%d%H%M",
+													);
+#::logDebug("current time: $current input value=$value");
+							if($value lt $current) {
+								return (0, $name, $message);
+							}
+							return (1, $name, '');
+						},
+);
+
+sub _update {
+	$Update = is_yes($_[1]);
+	return 1;
+}
 
 sub _fatal {
 	$Fatal = ( defined($_[1]) && ($_[1] =~ /^[yYtT1]/) ) ? 1 : 0;
+	return 1;
 }
 
 sub _final {
 	$Final = ( defined($_[1]) && ($_[1] =~ /^[yYtT1]/) ) ? 1 : 0;
+	return 1;
 }
 
 sub _return {
@@ -83,10 +314,29 @@
 	no strict 'refs';
 	my ($routine, $var, $val) = split /\s+/, $params, 3;
 
-	return (undef, $var, "No format check routine for '$routine'")
-		unless defined &{"_$routine"};
+	my (@return);
+
+#::logDebug("OrderCheck = $OrderCheck routine=$routine");
+	my $sub;
+	my @args;
+	if( $sub = $Parse{$routine}) {
+		@args = ($var, $val, $message);
+		undef $message;
+	}
+	elsif ($OrderCheck and $sub = $OrderCheck->{$routine}) {
+#::logDebug("Using coderef OrderCheck = $sub");
+		@args = ($ref,$var,$val);
+	}
+	elsif (defined &{"_$routine"}) {
+		$sub = \&{"_$routine"};
+		@args = ($ref,$var,$val);
+	}
+	else {
+		return (undef, $var, errmsg("No format check routine for '%s'", $routine));
+	}
+
+	@return = $sub->(@args);
 
-	my (@return) = &{'_' . $routine}($ref,$var,$val);
 	if(! $return[0] and $message) {
 		$return[2] = $message;
 	}
@@ -95,58 +345,83 @@
 
 sub chain_checks {
 	my ($or, $ref, $checks, $err) = @_;
-	my ($var, $val, $mess);
+	my ($var, $val, $mess, $message);
 	my $result = 1;
 	$mess = "$checks $err";
 	while($mess =~ s/(\S+=\w+)[\s,]*//) {
 		my $check = $1;
-#::logDebug("chain check $check, remaining '$mess'");
 		($val, $var, $message) = do_check($check);
-#::logDebug("chain check $check result: var=$var val=$val mess='$mess'");
 		return undef if ! defined $var;
 		if($val and $or) {
 			1 while $mess =~ s/(\S+=\w+)[\s,]*//;
-#::logDebug("chain check $check or succeeded, returning '$val'");
 			return ($val, $var, $message)
 		}
 		elsif ($val) {
-#::logDebug("chain check $check and succeeded, remaining '$mess'");
 			$result = 1;
 			next;
 		}
 		else {
-#::logDebug("chain check $check or=$or failed, remaining '$mess'");
 			next if $or;
 			1 while $mess =~ s/(\S+=\w+)[\s,]*//;
-#::logDebug("chain check $check and returning failed, var=$var val=$val mess='$mess'");
 			return($val, $var, $mess);
 		}
 	}
-#::logDebug("chain check $check returning, var=$var val=$val mess='$mess'");
 	return ($val, $var, $mess);
 }
 
 sub _and_check {
+	if(! length($_[1]) ) {
+		$And = 1;
+		return (1);
+	}
 	return chain_checks(0, @_);
 }
 
 sub _or_check {
+	if(! length($_[1]) ) {
+		$And = 0;
+		return (1);
+	}
 	return chain_checks(1, @_);
 }
 
 sub _charge {
 	my ($ref, $params, $message) = @_;
-#::logDebug("called _charge: ref=$ref params=$params message=$message");
 	my $result;
+	my $opt;
+	if ($params =~ /^custom\s+/) {
+		$opt = {};
+	}
+	else {
+		$params =~ s/(\w+)\s*(.*)/$1/s;
+		$opt = get_option_hash($2);
+	}
+
 	eval {
-		$result = charge($params);
+		$result = Vend::Payment::charge($params, $opt);
 	};
-	if($@) {
-		::logError("Fatal error on charge operation '%s': %s", $params, $@);
-		$message = "Error on charge operation.";
+	if($result) {
+		# do nothing, OK
+	}
+	elsif($@) {
+		my $msg = errmsg("Fatal error on charge operation '%s': %s", $params, $@);
+		::logError($msg);
+		$message = $msg;
+	}
+	elsif( $Vend::Session->{payment_error} ) {
+		# do nothing, no extended messages
+		$message = errmsg(
+						"Charge failed, reason: %s",
+						$Vend::Session->{payment_error},
+					)
+			if ! $message;
 	}
-	elsif(! $result) {
-		$message = "Charge operation '$ref->{mv_cyber_mode}' failed" if ! $message;
+	else {
+		$message = errmsg(
+					"Charge operation '%s' failed.",
+					($ref->{mv_cyber_mode} || $params),
+					)
+			if ! $message;
 	}
 #::logDebug("charge result: result=$result params=$params message=$message");
 	return ($result, $params, $message);
@@ -154,24 +429,48 @@
 
 sub _credit_card {
 	my($ref, $params) = @_;
+	my $subname;
 	my $sub;
+	my $opt;
+
 	$params =~ s/^\s+//;
 	$params =~ s/\s+$//;
-	if($params =~ s/\s+keep//i) {
-		my (%cgi) = %$ref;
-		$ref = \%cgi;
-	}
-	my $accepted;
-	if($params =~ s/\s+(.*)//) {
-		$accepted = $1;
+
+	# Make a copy if we need to keep the credit card number in memory for
+	# a while
+
+	# New or Compatibility to get options
+
+	if($params =~ /=/) {		# New
+		$params =~ s/^\s*(\w+)(\s+|$)//
+			and $subname = $1;
+		$subname = 'standard' if ! $subname;
+		$opt = get_option_hash($params);
 	}
-	if(! $params || $params =~ /^standard$/i ) {
-		$sub = \&encrypt_standard_cc;
+	else {      				# Compat
+		$opt = {};
+		$opt->{keep} = 1 if $params =~ s/\s+keep//i;
+	
+		if($params =~ s/\s+(.*)//) {
+			$opt->{accepted} = $1;
+		}
+		$subname = $params;
 	}
-	elsif(! defined ($sub = $Global::GlobalSub->{$params}) ) {
-		::logError("bad credit card check GlobalSub: %s", $params);
+
+	$sub = $subname eq 'standard'
+		 ? \&encrypt_standard_cc
+		 :	$Global::GlobalSub->{$subname};
+
+	if(! $sub) {
+		::logError("bad credit card check GlobalSub: '%s'", $subname);
 		return undef;
 	}
+
+	if($opt->{keep}) {
+		my (%cgi) = %$ref;
+		$ref = \%cgi;
+	}
+
 	eval {
 		@{$::Values}{ qw/
 					mv_credit_card_valid
@@ -183,10 +482,11 @@
 					mv_credit_card_reference
 					mv_credit_card_error
 					/}
-				= $sub->($ref, undef, { accepted => $accepted } );
+				= $sub->($ref, undef, $opt );
 	};
+
 	if($@) {
-		::logError("credit card check GlobalSub %s error: %s", $params, $@);
+		::logError("credit card check (%s) error: %s", $subname, $@);
 		return undef;
 	}
 	elsif(! $::Values->{mv_credit_card_valid}) {
@@ -197,37 +497,6 @@
 	}
 }
 
-my %Parse = (
-
-	'&charge'       =>	\&_charge,
-	'&credit_card'  =>	\&_credit_card,
-	'&return'       =>	\&_return,
-	'&fatal'       	=>	\&_fatal,
-	'&and'       	=>	\&_and_check,
-	'&or'       	=>	\&_or_check,
-	'&format'		=> 	\&_format,
-	'&success'		=> 	sub { $Success_page = $_[1] },
-	'&fail'         =>  sub { $Fail_page    = $_[1] },
-	'&final'		=>	\&_final,
-	'&calc'			=>  sub { Vend::Interpolate::tag_calc($_[1]) },
-	'&test'			=>	sub {		
-								my($ref,$params) = @_;
-								$params =~ s/\s+//g;
-								return $params;
-							},
-	'&set'			=>	sub {		
-								my($ref,$params) = @_;
-								my ($var, $value) = split /\s+/, $params, 2;
-								$::Values->{$var} = $value;
-							},
-	'&setcheck'			=>	sub {		
-								my($ref,$params) = @_;
-								my ($var, $value) = split /\s+/, $params, 2;
-								$::Values->{$var} = $value;
-								return ($value, $var, "$var set failed.");
-							},
-);
-
 sub valid_exp_date {
 	my ($expire) = @_;
 	my $month;
@@ -242,7 +511,6 @@
 		$month = $CGI::values{mv_credit_card_exp_month};
 		$year = $CGI::values{mv_credit_card_exp_year};
 	}
-#::logDebug("check exp: mon=$month year=$year");
 	return '' if $month !~ /^\d+$/ || $year !~ /^\d+$/;
 	return '' if $month <1 || $month > 12;
 	$year += ($year < 70) ? 2000 : 1900 if $year < 1900;
@@ -267,91 +535,86 @@
 
 }
 
-=head1 Validate credit card routine
 
-=head1 AUTHOR
-
-Jon Orwant, from Business::CreditCard and well-known algorithms
-
-=cut
+# Validate credit card routine
+# by Jon Orwant, from Business::CreditCard and well-known algorithms
 
 sub luhn {
-    my ($number) = @_;
-    my ($i, $sum, $weight);
-
-    $number =~ s/\D//g;
+	my ($number,$min_digits) = @_;
+	my ($i, $sum, $weight);
 
-    return 0 unless length($number) >= 13 && 0+$number;
-
-    for ($i = 0; $i < length($number) - 1; $i++) {
-        $weight = substr($number, -1 * ($i + 2), 1) * (2 - ($i % 2));
-        $sum += (($weight < 10) ? $weight : ($weight - 9));
-    }
-
-    return 1 if substr($number, -1) == (10 - $sum % 10) % 10;
-    return 0;
-}
+	$min_digits ||= 13;
+	$min_digits = 2 if $min_digits < 2;
 
+	$number =~ s/\D//g;
 
-# Encrypts a credit card number with DES or the like
-# Prefers internal Des module, if was included
-sub encrypt_cc {
-	my($enclair) = @_;
-	my($encrypted, $status, $cmd);
-	my $infile    = 0;
+	return 0 unless length($number) >= $min_digits && 0+$number;
 
-	$cmd = $Vend::Cfg->{EncryptProgram};
-	$cmd = '' if "\L$cmd" eq 'none';
-
-	my $tempfile = $Vend::Cfg->{ScratchDir} . '/' . $Vend::SessionID . '.cry';
-
-	#Substitute the filename
-	if ($cmd =~ s/%f/$tempfile/) {
-		$infile = 1;
+	for ($i = 0; $i < length($number) - 1; $i++) {
+		$weight = substr($number, -1 * ($i + 2), 1) * (2 - ($i % 2));
+		$sum += (($weight < 10) ? $weight : ($weight - 9));
 	}
 
-	# Want the whole file
-	local($/) = undef;
-
-	# Send the CC to a tempfile if incoming
-	if($infile) {
-		open(CARD, ">$Vend::Cfg->{ScratchDir}/$tempfile") ||
-			die "Couldn't write $tempfile: $!\n";
-		# Put the cardnumber there, and maybe password first
-		$enclair .= "\r\n\cZ\r\n" if $Global::Windows;
-		print CARD $enclair;
-		close CARD;
+	return 1 if substr($number, -1) == (10 - $sum % 10) % 10;
+	return 0;
+}
 
-		# Encrypt the string, but key on arg line will be exposed
-		# to ps(1) for systems that allow it
-		open(CRYPT, "$cmd |") || die "Couldn't fork: $!\n";
-		chomp($encrypted = <CRYPT>);
-		close CRYPT;
-		$status = $?;
-	}
-	else {
-		$cmd = "| $cmd " if $cmd;
-		open(CRYPT, "$cmd>$tempfile ") || die "Couldn't fork: $!\n";
-		print CRYPT $enclair;
-		close CRYPT;
-		$status = $cmd ? $? : 0;
 
-		open(CARD, "< $tempfile") || warn "open $tempfile: $!\n";
-		$encrypted = <CARD>;
-		close CARD;
-	}
+sub build_cc_info {
+	my ($cardinfo, $template) = @_;
 
-	unlink $tempfile;
+	if (ref $cardinfo eq 'SCALAR') {
+		$cardinfo = { MV_CREDIT_CARD_NUMBER => $$cardinfo };
+	} elsif (! ref $cardinfo) {
+		$cardinfo = { MV_CREDIT_CARD_NUMBER => $cardinfo };
+	} elsif (ref $cardinfo eq 'ARRAY') {
+		my $i = 0;
+		my %c = map { $_ => $cardinfo->[$i++] } qw(
+			MV_CREDIT_CARD_NUMBER
+			MV_CREDIT_CARD_EXP_MONTH
+			MV_CREDIT_CARD_EXP_YEAR
+			MV_CREDIT_CARD_CVV2
+			MV_CREDIT_CARD_TYPE
+		);
+		$cardinfo = \%c;
+	} elsif (ref $cardinfo ne 'HASH') {
+		return;
+	}
+
+	$template = $template ||
+		$::Variable->{MV_CREDIT_CARD_INFO_TEMPLATE} ||
+		join("\t", qw(
+			{MV_CREDIT_CARD_TYPE}
+			{MV_CREDIT_CARD_NUMBER}
+			{MV_CREDIT_CARD_EXP_MONTH}/{MV_CREDIT_CARD_EXP_YEAR}
+			{MV_CREDIT_CARD_CVV2}
+		)) . "\n";
+
+	$cardinfo->{MV_CREDIT_CARD_TYPE} ||=
+		guess_cc_type($cardinfo->{MV_CREDIT_CARD_NUMBER});
+
+	return Vend::Interpolate::tag_attr_list($template, $cardinfo);
+}
 
-	# This means encryption failed
-	if( $status != 0 ) {
-		::logGlobal({}, "Encryption error: %s", $!);
-		return undef;
-	}
 
-	$encrypted;
+sub guess_cc_type {
+	my ($ccnum) = @_;
+	$ccnum =~ s/\D+//g;
+
+	# based on logic by Karl Moore from http://www.vb-world.net/tips/tip509.html
+	if ($ccnum eq '')										{ '' }
+	elsif ($ccnum =~ /^4(?:\d{12}|\d{15})$/)				{ 'visa' }
+	elsif ($ccnum =~ /^5[1-5]\d{14}$/)						{ 'mc' }
+	elsif ($ccnum =~ /^6011\d{12}$/)						{ 'discover' }
+	elsif ($ccnum =~ /^3[47]\d{13}$/)						{ 'amex' }
+	elsif ($ccnum =~ /^3(?:6\d{12}|0[0-5]\d{11})$/)			{ 'dinersclub' }
+	elsif ($ccnum =~ /^38\d{12}$/)							{ 'carteblanche' }
+	elsif ($ccnum =~ /^2(?:014|149)\d{11}$/)				{ 'enroute' }
+	elsif ($ccnum =~ /^(?:3\d{15}|2131\d{11}|1800\d{11})$/)	{ 'jcb' }
+	else													{ 'other' }
 }
 
+
 # Takes a reference to a hash (usually %CGI::values) that contains
 # the following:
 # 
@@ -359,6 +622,7 @@
 #    mv_credit_card_exp_all     A combined expiration MM/YY
 #    mv_credit_card_exp_month   Month only, used if _all not present
 #    mv_credit_card_exp_year    Year only, used if _all not present
+#    mv_credit_card_cvv2        CVV2 verification number from back of card
 #    mv_credit_card_type        A = Amex, D = Discover, etc. Attempts
 #                               to guess from number if not there
 #    mv_credit_card_separate    Causes mv_credit_card_info to contain only number, must
@@ -369,30 +633,30 @@
 	my($valid, $info);
 
 	$opt = {} unless ref $opt;
+	my @deletes = qw /
+					mv_credit_card_type		mv_credit_card_number
+					mv_credit_card_exp_year	mv_credit_card_exp_month
+					mv_credit_card_force	mv_credit_card_exp_reference
+					mv_credit_card_exp_all	mv_credit_card_exp_separate  
+					mv_credit_card_cvv2
+					/;
 
 	my $month	= $ref->{mv_credit_card_exp_month}	|| '';
 	my $type	= $ref->{mv_credit_card_type}		|| '';
 	my $num		= $ref->{mv_credit_card_number}		|| '';
 	my $year	= $ref->{mv_credit_card_exp_year}	|| '';
 	my $all		= $ref->{mv_credit_card_exp_all}	|| '';
+	my $cvv2	= $ref->{mv_credit_card_cvv2}		|| '';
 	my $force	= $ref->{mv_credit_card_force}		|| '';
-	my $separate = $ref->{mv_credit_card_separate}  || '';
+	my $separate = $ref->{mv_credit_card_separate}  || $opt->{separate} || '';
 
-	for ( qw (	mv_credit_card_type		mv_credit_card_number
-				mv_credit_card_exp_year	mv_credit_card_exp_month
-				mv_credit_card_exp_separate mv_credit_card_exp_reference
-				mv_credit_card_exp_all  mv_credit_card_force))
-	{
-		next unless defined $ref->{$_};
-		delete $ref->{$_} unless $nodelete;
-	}
+	delete @$ref{@deletes}        unless ($opt->{nodelete} or $nodelete);
 
 	# remove unwanted chars from card number
 	$num =~ tr/0-9//cd;
 
-#::logDebug ("encrypt_standard_cc: $num $month/$year $type");
 	# error will be pushed on this if present
-	@return = (
+	my @return = (
 				'',			# 0- Whether it is valid
 				'',			# 1- Encrypted credit card information
 				'',			# 2- Month
@@ -407,8 +671,7 @@
 		$month = $1;
 		$year  = "$2$3";
 	}
-	elsif ($month >= 1  and $month <= 12 and $year) 
-	{
+	elsif ($month >= 1  and $month <= 12 and $year) {
 		$all = "$month/$year";
 	}
 	else {
@@ -434,19 +697,7 @@
 		return @return;
 	}
 
-	$num =~ s/\D+//g;
-
-	# Get the type
-	unless ( $type ) {
-		($num =~ /^3/) and $type = 'amex';
-		($num =~ /^4/) and $type = 'visa';
-		($num =~ /^5/) and $type = 'mc';
-		($num =~ /^6/) and $type = 'discover';
-	}
-
-	if($type eq 'amex') {
-		$type = 'other' if $num !~ /^37/;
-	}
+	$type = guess_cc_type($num) unless $type;
 
 	if ($type and $opt->{accepted} and $opt->{accepted} !~ /\b$type\b/i) {
 		my $msg = errmsg("Sorry, we don't accept credit card type '%s'.", $type);
@@ -457,8 +708,8 @@
 	elsif ($type) {
 		$return[5] = $type;
 	}
-	else {
-		my $msg = errmsg("Can't figure out credit card type.");
+	elsif(! $opt->{any}) {
+		my $msg = errmsg("Can't figure out credit card type from number.");
 		$Vend::Session->{errors}{mv_credit_card_valid} = $msg;
 		push @return, $msg;
 		return @return;
@@ -475,9 +726,10 @@
 
 	my $check_string = $num;
 	$check_string =~ s/(\d\d).*(\d\d\d\d)$/$1**$2/;
-	my $encrypt_string = $separate ? $num : "$type\t$num\t$all\n";
 	
-	$info = encrypt_cc ($encrypt_string);
+	my $encrypt_string = $separate ? $num :
+		build_cc_info( [$num, $month, $year, $cvv2, $type] );
+	$info = pgp_encrypt ($encrypt_string);
 
 	unless (defined $info) {
 		my $msg = errmsg("Credit card encryption failed: %s", $! );
@@ -493,330 +745,8 @@
 
 }
 
-sub testSetServer {
-	my %options = @_;
-	my $out = '';
-	for(sort keys %options) {
-		$out .= "$_=$options{$_}\n";
-	}
-	logError("Test CyberCash SetServer:\n%s\n" , $out);
-	1;
-}
-
-sub testsendmserver {
-	my ($type, %options) = @_;
-	my $out ="type=$type\n";
-	for(sort keys %options) {
-		$out .= "$_=$options{$_}\n";
-	}
-	logError("Test CyberCash sendmserver:\n$out\n");
-	return ('MStatus', 'success', 'order-id', 1);
-}
-
-sub map_actual {
-
-	# Allow remapping of payment variables
-    my %map = qw(
-		mv_credit_card_number       mv_credit_card_number
-		name                        name
-		fname                       fname
-		lname                       lname
-		b_name                      b_name
-		b_fname                     b_fname
-		b_lname                     b_lname
-		address                     address
-		address1                    address1
-		address2                    address2
-		b_address                   b_address
-		b_address1                  b_address1
-		b_address2                  b_address2
-		city                        city
-		b_city                      b_city
-		state                       state
-		b_state                     b_state
-		zip                         zip
-		b_zip                       b_zip
-		country                     country
-		b_country                   b_country
-		mv_credit_card_exp_month    mv_credit_card_exp_month
-		mv_credit_card_exp_year     mv_credit_card_exp_year
-		cyber_mode                  mv_cyber_mode
-		amount                      amount
-    );
-
-	# Allow remapping of the variable names
-	my $remap = $::Variable->{MV_PAYMENT_REMAP} || $::Variable->{CYBER_REMAP};
-	$remap =~ s/^\s+//;
-	$remap =~ s/\s+$//;
-	my (%remap) = split /[\s=]+/, $remap;
-	for (keys %remap) {
-		$map{$_} = $remap{$_};
-	}
-
-	my %actual;
-	my $key;
-
-	# pick out the right values, need alternate billing address
-	# substitution
-	foreach $key (keys %map) {
-		$actual{$key} = $::Values->{$map{$key}} || $CGI::values{$key}
-			and next;
-		my $secondary = $key;
-		next unless $secondary =~ s/^b_//;
-		$actual{$key} = $::Values->{$map{$secondary}} ||
-						$CGI::values{$map{$secondary}};
-	}
-	$actual{b_name}		 = "$actual{b_fname} $actual{b_lname}"
-		if $actual{b_lname};
-	if($actual{b_address1}) {
-		$actual{b_address} = "$actual{b_address1}";
-		$actual{b_address} .=  ", $actual{b_address2}"
-			if $actual{b_address2};
-	}
-	return %actual;
-}
-
-sub charge {
-	my ($charge_type) = @_;
-	my (%actual) = map_actual();
-
-#::logDebug ("cyber_charge, mode val=$::Values->{mv_cyber_mode} cgi=$CGI::values{mv_cyber_mode} actual=$actual{cyber_mode}");
-    my $currency =  $::Variable->{MV_PAYMENT_CURRENCY}
-					|| $::Variable->{CYBER_CURRENCY}
-					|| 'usd';
-    $actual{mv_credit_card_exp_month} =~ s/\D//g;
-    $actual{mv_credit_card_exp_month} =~ s/^0+//;
-    $actual{mv_credit_card_exp_year} =~ s/\D//g;
-    $actual{mv_credit_card_exp_year} =~ s/\d\d(\d\d)/$1/;
-
-    $actual{mv_credit_card_number} =~ s/\D//g;
-
-    my $exp = $actual{mv_credit_card_exp_month} . '/' .
-    		  $actual{mv_credit_card_exp_year};
-
-    $actual{cyber_mode} = 'mauthcapture'
-		unless $actual{cyber_mode};
-
-    my($orderID);
-    my($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = gmtime(time());
-
-    # We'll make an order ID based on date, time, and PID
-
-    # $mon is the month index where Jan=0 and Dec=11, so we use
-    # $mon+1 to get the more familiar Jan=1 and Dec=12
-    $orderID = sprintf("%02d%02d%02d%02d%02d%05d",
-            $year + 1900,$mon + 1,$mday,$hour,$min,$$);
-
-    # The following characters are illegal in an order ID:
-    #    : < > = + @ " % = &
-    #
-    # If you want, you could use a line similar to the following
-    # to remove these illegal characters:
-
-    $orderID =~ tr/:<>=+\@\"\%\&/_/d;
-
-    #
-    # Or use something like the following line to only allow
-    # alphanumeric and dash, converting other characters to underscore:
-    #    $orderID =~ tr/A-Za-z0-9\-/_/c;
-
-    # Our test order ID only contains digits, so we don't have
-    # to strip any characters here. You might have to if you
-    # use a different scheme.
-
-	my $precision = $::Variable->{CYBER_PRECISION} || 2;
-    $amount = Vend::Interpolate::total_cost();
-	$amount = sprintf("%.${precision}f", $amount);
-    $amount = "$currency $amount";
-
-    my %result;
-
-	if($charge_type =~ /^\s*custom\s+(\w+)(?:\s+(.*))?/si) {
-		my ($sub, @args);
-		@args = Text::ParseWords::shellwords($2) if $2;
-		if(! defined ($sub = $Global::GlobalSub->{$1}) ) {
-			::logError("bad custom payment GlobalSub: %s", $1);
-			return undef;
-		}
-		%result = $sub->(@args);
-		$Vend::Session->{payment_result} =
-			$Vend::Session->{cybercash_result} = \%result;
-	}
-    elsif ($actual{cyber_mode} =~ /^minivend_test(?:_(.*))?/) {
-		my $status = $1 || 'success';
-		# Interchange test mode
-		my %payment = (
-			'host' => $::Variable->{CYBER_HOST} || 'localhost',
-			'port' => $::Variable->{CYBER_PORT} || 8000,
-			'secret' => $::Variable->{CYBER_SECRET} || '',
-			'config' => $::Variable->{CYBER_CONFIGFILE} || '',
-		);
-		&testSetServer ( %payment );
-		%result = testsendmserver(
-					$actual{cyber_mode},
-			'Order-ID'     => $orderID,
-			'Amount'       => $amount,
-			'Card-Number'  => $actual{mv_credit_card_number},
-			'Card-Name'    => $actual{b_name},
-			'Card-Address' => $actual{b_address},
-			'Card-City'    => $actual{b_city},
-			'Card-State'   => $actual{b_state},
-			'Card-Zip'     => $actual{b_zip},
-			'Card-Country' => $actual{b_country},
-			'Card-Exp'     => $exp,
-		);
-		$result{MStatus} = $status;
-		$Vend::Session->{payment_result} =
-			$Vend::Session->{cybercash_result} = \%result;
-    }
-	elsif ($Vend::CC3) {
-		# Live interface operations follow
-		$Vend::CC3server = 1;
-
-		# Cybercash 3.x libraries to be used.
-		# Initialize the merchant configuration file
-		my $status = InitConfig($::Variable->{CYBER_CONFIGFILE});
-		if ($status != 0) {
-			$Vend::Session->{cybercash_error} = MCKGetErrorMessage($status);
-			::logError(
-				"Failed to initialize CyberCash from file %s: %s",
-				$Variable->{CYBER_CONFIGFILE},
-				$Vend::Session->{cybercash_error},
-				);
-			return undef;
-		}
-
-		unless($::Variable->{CYBER_HOST}) {
-			$::Variable->{CYBER_HOST} = $Config{CCPS_HOST};
-		}
-		if($Vend::CC3server) {
-			# Cybercash 3.x server and libraries to be used.
-
-			if ($status != 0) {
-				$Vend::Session->{cybercash_error} = MCKGetErrorMessage($status);
-				return undef;
-			}
-			$sendurl = $::Variable->{CYBER_HOST} . 'directcardpayment.cgi';
-
-			my %paymentNVList;
-			$paymentNVList{'mo.cybercash-id'} = $Config{CYBERCASH_ID};
-			$paymentNVList{'mo.version'} = $MCKversion;
-
-			$paymentNVList{'mo.signed-cpi'} = "no";
-			$paymentNVList{'mo.order-id'} = $orderID;
-			$paymentNVList{'mo.price'} = $amount;
-
-			$paymentNVList{'cpi.card-number'} = $actual{mv_credit_card_number};
-			$paymentNVList{'cpi.card-exp'} = $exp;
-			$paymentNVList{'cpi.card-name'} = $actual{b_name};
-			$paymentNVList{'cpi.card-address'} = $actual{b_address};
-			$paymentNVList{'cpi.card-city'} = $actual{b_city};
-			$paymentNVList{'cpi.card-state'} = $actual{b_state};
-			$paymentNVList{'cpi.card-zip'} = $actual{b_zip};
-			$paymentNVList{'cpi.card-country'} = $actual{b_country};
-
-			my (  $POPref, $tokenlistref, %tokenlist );
-			($POPref, $tokenlistref ) = 
-							  doDirectPayment( $sendurl, \%paymentNVList );
-			
-			$result{MStatus}    = $POPref->{'pop.status'};
-			$result{MErrMsg}     = $POPref->{'pop.error-message'};
-			$result{'order-id'} = $POPref->{'pop.order-id'};
-
-			$Vend::Session->{cybercash_result} = $POPref;
-
-			# other values found in POP which might be used in some way:
-			#		$POP{'pop.auth-code'};
-			#		$POP{'pop.ref-code'};
-			#		$POP{'pop.txn-id'};
-			#		$POP{'pop.sale_date'};
-			#		$POP{'pop.sign'};
-			#		$POP{'pop.avs_code'};
-			#		$POP{'pop.price'};
-		}
-    }
-
-	if($result{MStatus} !~ /^success/) {
-		$Vend::Session->{cybercash_error} = $result{MErrMsg};
-		return undef;
-	}
-	elsif($result{MStatus} =~ /success-duplicate/) {
-		$Vend::Session->{cybercash_error} = $result{MErrMsg};
-	}
-	else {
-		$Vend::Session->{cybercash_error} = '';
-	}
-	$Vend::Session->{payment_id} =
-		$Vend::Session->{cybercash_id} = $result{'order-id'};
-	if($Vend::Cfg->{EncryptProgram} =~ /(pgp|gpg)/) {
-		$CGI::values{mv_credit_card_force} = 1;
-		(
-			$::Values->{mv_credit_card_valid},
-			$::Values->{mv_credit_card_info},
-			$::Values->{mv_credit_card_exp_month},
-			$::Values->{mv_credit_card_exp_year},
-			$::Values->{mv_credit_card_exp_all},
-			$::Values->{mv_credit_card_type},
-			$::Values->{mv_credit_card_error}
-		)	= encrypt_standard_cc(\%CGI::values);
-	}
-	::logError("Order id: %s\n", $Vend::Session->{cybercash_id});
-	return $result{'order-id'};
-}
-
-
-*cyber_charge = \&charge;
-
-
-
-sub report_field {
-    my($field_name, $seen) = @_;
-    my($field_value, $r);
-
-    $field_value = $Vend::Session->{'values'}->{$field_name};
-    if (defined $field_value) {
-		$$seen{$field_name} = 1;
-		$r = $field_value;
-    }
-	else {
-		$r = "<no input box>";
-    }
-    $r;
-}
-
-#sub create_onfly {
-#	my $opt = shift;
-#	if($opt->{create}) {
-#		delete $opt->{create};
-#		my $href = $opt->{href} || '';
-#		my $secure = $opt->{secure} || '';
-#		if(defined $split_fields) {
-#			return join $joiner, @{$opt}{ split /[\s,]+/, $split_fields };
-#		}
-#		else {
-#			my @out;
-#			my @fly;
-#			for(keys %{$opt}) {
-#				$opt->{$_} =~ s/[\0\n]/\r/g unless $v;
-#				push @fly, "$_=$opt->{$_}";
-#			}
-#			push @out, "mv_order_fly=" . join $joiner, @fly;
-#			push @out, "mv_order_item=$opt->{code}"
-#				if ! $opt->{mv_order_item} and $opt->{code};
-#			push @out, "mv_order_quantity=$opt->{quantity}"
-#				if ! $opt->{mv_order_quantity} and $opt->{quantity};
-#			push @out, "mv_todo=refresh"
-#				if ! $opt->{mv_todo};
-#		}
-#		my $form = join "\n", @out;
-#		return Vend::Interpolate::form_link( $href, '', $secure, { form => $form } );
-#	}
-#
-#}
-
 sub onfly {
 	my ($code, $qty, $opt) = @_;
-#::logDebug("called onfly");
 	my $item_text;
 	if (ref $opt) {
 		$item_text = $opt->{text} || '';
@@ -836,7 +766,7 @@
 	my @parms;
 	my @fields;
 	$joiner = quotemeta $joiner;
-	@parms = split /$joiner/, $item_text;
+	@parms = split /$joiner|\0/, $item_text;
 	my ($k, $v);
 	my $item = {};
 	if(defined $split_fields) {
@@ -856,22 +786,26 @@
 	return $item;
 }
 
-# Email the processed order.
-
+# Email the processed order. This is a legacy routine, not normally used
+# any more. Order email is normally sent via Route.
 sub mail_order {
 	my ($email, $order_no) = @_;
 	$email = $Vend::Cfg->{MailOrderTo} unless $email;
-    my($body, $ok);
-    my($subject);
+	my($body, $ok);
+	my($subject);
 # LEGACY
-    $body = readin($::Values->{mv_order_report})
-		if $::Values->{mv_order_report};
+	if ($::Values->{mv_order_report}) {
+		if($Global::NoAbsolute and (file_name_is_absolute($::Values->{mv_order_report}) or $::Values->{mv_order_report} =~ m#\.\./.*\.\.#)) {
+			::logError("Can't use file '%s' with NoAbsolute set", $::Values->{mv_order_report});
+			::logGlobal({ level => 'auth'}, "Can't use file '%s' with NoAbsolute set", $::Values->{mv_order_report});
+			return undef;
+		}
+		$body = readin($::Values->{mv_order_report})
+	}
 # END LEGACY
-#::logDebug( sprintf "found body length %s in values->mv_order_report", length($body));
-    $body = readfile($Vend::Cfg->{OrderReport})
+	$body = readfile($Vend::Cfg->{OrderReport}, $Global::NoAbsolute)
 		if ! $body;
-#::logDebug( sprintf "found body length %s in OrderReport", length($body));
-    unless (defined $body) {
+	unless (defined $body) {
 		::logError(
 			q{Cannot find order report in:
 
@@ -882,10 +816,15 @@
 				$Vend::Cfg->{OrderReport},
 				$::Values->{mv_order_report},
 			);
+		if($Global::NoAbsolute and (file_name_is_absolute($Vend::Cfg->{OrderReport}) or $Vend::Cfg->{OrderReport} =~ m#\.\./.*\.\.#)) {
+			::logError("Can't use file '%s' with NoAbsolute set", $Vend::Cfg->{OrderReport});
+			::logGlobal({ level => 'auth'}, "Can't use file '%s' with NoAbsolute set", $Vend::Cfg->{OrderReport});
+			return undef;
+		}
 		$body = readin($Vend::Cfg->{OrderReport});
 		return undef if ! $body;
 	}
-    return undef unless defined $body;
+	return undef unless defined $body;
 
 	$order_no = update_order_number() unless $order_no;
 
@@ -893,40 +832,75 @@
 
 	$body = pgp_encrypt($body) if $Vend::Cfg->{PGP};
 
-#::logDebug("Now ready to track order, number=$order_no");
 	track_order($order_no, $body);
-#::logDebug("finished track order, number=$order_no");
 
 	$subject = $::Values->{mv_order_subject} || "ORDER %n";
 
 	if(defined $order_no) {
-	    $subject =~ s/%n/$order_no/;
+		$subject =~ s/%n/$order_no/;
 	}
 	else { $subject =~ s/\s*%n\s*//g; }
 
-#::logDebug("Now ready to send mail, subject=$subject");
-
-#### change this to use Vend::Mail::send
-    $ok = send_mail($email, $subject, $body);
-    return $ok;
+	$ok = send_mail($email, $subject, $body);
+	return $ok;
 }
 
 sub pgp_encrypt {
 	my($body, $key, $cmd) = @_;
-	$cmd = $Vend::Cfg->{PGP} unless $cmd;
+#::logDebug("called pgp_encrypt key=$key cmd=$cmd");
+	$cmd = $Vend::Cfg->{EncryptProgram} unless $cmd;
+	$key = $Vend::Cfg->{EncryptKey}	    unless $key;
+
+	
+	if("\L$cmd" eq 'none') {
+		return ::errmsg("NEED ENCRYPTION ENABLED.");
+	}
+	elsif(! $key) {
+		return ::errmsg("NEED ENCRYPTION KEY POINTER.");
+	}
+	elsif($cmd =~ m{^(?:/\S+/)?\bgpg$}) {
+		$cmd .= " --batch --always-trust -e -a -r '%s'";
+	}
+	elsif($cmd =~ m{^(?:/\S+/)?pgpe$}) {
+		$cmd .= " -fat -r '%s'";
+	}
+	elsif($cmd =~ m{^(?:/\S+/)?\bpgp$}) {
+		$cmd .= " -fat - '%s'";
+	}
+
+	if($cmd =~ /[;|]/) {
+		die ::errmsg("Illegal character in encryption command: %s", $cmd);
+	}
+
 	if($key) {
 		$cmd =~ s/%%/:~PERCENT~:/g;
+		$key =~ s/'/\\'/g;
 		$cmd =~ s/%s/$key/g;
 		$cmd =~ s/:~PERCENT~:/%/g;
 	}
-	my $fpre = $Vend::Cfg->{ScratchDir} . "/pgp.$$";
-	open(PGP, "|$cmd >$fpre.out 2>$fpre.err")
+
+#::logDebug("after  pgp_encrypt key=$key cmd=$cmd");
+
+	my $fpre = $Vend::Cfg->{ScratchDir} . "/pgp.$Vend::Session->{id}.$$";
+	$cmd .= " >$fpre.out";
+	$cmd .= " 2>$fpre.err" unless $cmd =~ /2>/;
+	open(PGP, "|$cmd")
 			or die "Couldn't fork: $!";
 	print PGP $body;
 	close PGP;
+
 	if($?) {
-		logError("PGP failed with status " . $? << 8 . ": $!");
-		return 0;
+		my $errno = $?;
+		my $status = $errno;
+		if($status > 255) {
+			$status = $status >> 8;
+			$! = $status;
+		}
+		logError("PGP failed with error level %s, status %s: $!", $?, $status);
+		if($status) {
+			logError("PGP hard failure, command that failed: %s", $cmd);
+			return;
+		}
 	}
 	$body = readfile("$fpre.out");
 	unlink "$fpre.out";
@@ -936,30 +910,33 @@
 
 sub do_check {
 		local($_) = shift;
-		$parameter = $_;
-		my($var, $val, $m, $message);
 		my $ref = \%CGI::values;
+		my $vref = shift || $::Values;
+
+		my $conditional_update;
+		my $parameter = $_;
+		my($var, $val, $m, $message);
 		if (/^&/) {
 			($var,$val) = split /[\s=]+/, $parameter, 2;
 		}
 		elsif ($parameter =~ /(\w+)[\s=]+(.*)/) {
 			my $k = $1;
 			my $v = $2;
+			$conditional_update = $Update;
 			$m = $v =~ s/\s+(.*)// ? $1 : undef;
 			($var,$val) =
 				('&format',
-				  $v . ' ' . $k  . ' ' .  $::Values->{$k}
+				  $v . ' ' . $k  . ' ' .  $vref->{$k}
 				  );
 		}
 		else {
-			logError("Unknown order check '%s' in profile %s", $parameter, $profile);
+			logError("Unknown order check '%s' in profile %s", $parameter, $Profile);
 			return undef;
 		}
 		$val =~ s/&#(\d+);/chr($1)/ge;
 
-#::logDebug("checking profile $Profile: var=$var val=$val Fatal=$Fatal Final=$Final");
-		if (defined $Parse{$var}) {
-			($val, $var, $message) = &{$Parse{$var}}($ref, $val, $m || undef);
+		if ($Parse{$var}) {
+			($val, $var, $message) = $Parse{$var}->($ref, $val, $m);
 		}
 		else {
 			logError( "Unknown order check parameter in profile %s: %s=%s",
@@ -969,14 +946,56 @@
 					);
 			return undef;
 		}
-#::logDebug("profile $Profile check result: var=$var val='$val' message='$message' Fatal=$Fatal Final=$Final");
+#::logDebug("&Vend::Order::do_check returning val=$val, var=$var, message=$message");
+		if($conditional_update and $val) {
+			::update_values($var);
+		}
 		return ($val, $var, $message);
 }
 
 sub check_order {
-	my ($profile) = @_;
-    my($codere) = '[-\w_#/.]+';
+	my ($profiles, $vref) = @_;
+	reset_order_vars();
+	my $status;
+	$Vend::Session->{errors} = {}
+		unless ref $Vend::Session->{errors} eq 'HASH';
+
+	for my $profile (split /\0+/, $profiles) {
+
+		$status = check_order_each($profile, $vref);
+
+		if ($status) {
+			$CGI::values{mv_nextpage} = $Success_page
+				if $Success_page;
+		}
+		elsif ($Fail_page) {
+			$CGI::values{mv_nextpage} = $Fail_page;
+		}
+		if ($Final and ! scalar @{$Vend::Items}) {
+			$status = 0;
+			$::Values->{"mv_error_items"}		=
+				$Vend::Session->{errors}{items}	=
+					errmsg(
+						"You might want to order something! No items in cart.",
+					);
+		}
+#::logDebug("FINISH checking profile $profile: Fatal=$Fatal Final=$Final Status=$status");
+
+		# first profile to fail prevents all other profiles from running
+		last unless $status;
+
+	}
+
+	my $errors = join "\n", @Errors;
+#::logDebug("Errors after checking profile(s):\n$errors") if $errors;
+	$errors = '' unless defined $errors and ! $Success;
+	return ($status, $Final, $errors);
+}
+
+sub check_order_each {
+	my ($profile, $vref) = @_;
 	my $params;
+	$Profile = $profile;
 	if(defined $Vend::Cfg->{OrderProfileName}->{$profile}) {
 		$profile = $Vend::Cfg->{OrderProfileName}->{$profile};
 		$params = $Vend::Cfg->{OrderProfile}->[$profile];
@@ -987,26 +1006,42 @@
 	elsif(defined $::Scratch->{$profile}) {
 		$params = $::Scratch->{$profile};
 	}
-	else { return undef }
+	else {
+		::logError("Order profile %s not found", $profile);
+		return undef;
+	}
 	return undef unless $params;
-	$Profile = $profile;
 
-	my $ref = \%CGI::values;
 	$params = interpolate_html($params);
-	@Errors = ();
+	$params =~ s/\\\n//g;
+
+	$And = 1;
 	$Fatal = $Final = 0;
 
-	my($var,$val);
+	my($var,$val,$message);
 	my $status = 1;
 	my(@param) = split /[\r\n]+/, $params;
 	my $m;
 	my $join;
-	
+	my $here;
+	my $last_one = 1;
+
 	for(@param) {
+		if(/^$here$/) {
+			$_ = $join;
+			undef $here;
+			undef $join;
+		}
+		($join .= "$_\n", next) if $here;
 		if($join) {
 			$_ = "$join$_";
 			undef $join;
 		}
+		if(s/<<(\w+);?\s*$//) {
+			$here = $1;
+			$join = "$_\n";
+			next;
+		}
 		next unless /\S/;
 		next if /^\s*#/;
 		if(s/\\$//) {
@@ -1015,52 +1050,55 @@
 		}
 		s/^\s+//;
 		s/\s+$//;
-		($val, $var, $message) = do_check($_);
-#::logDebug("check returned val='$val' var=" . (defined $var ? 'DEFINED' : 'UNDEF'));
-		next if ! defined $var;
-		if ($val) {
- 			$::Values->{"mv_status_$var"} = $message
-				if defined $message and $message;
-			delete $Vend::Session->{errors}{$var};
- 			delete $::Values->{"mv_error_$var"};
+		($val, $var, $message) = do_check($_, $vref);
+		if(defined $And) {
+			if($And) {
+				$val = ($last_one && $val);
+			}
+			else {
+				$val = ($last_one || $val);
+			}
+			undef $And;
 		}
-		else {
-			$status = 0;
+		$last_one = $val;
+		$status = 0 unless $val;
+		if ($var) {
+			if ($val) {
+				$::Values->{"mv_status_$var"} = $message
+					if defined $message and $message;
+				delete $Vend::Session->{errors}{$var};
+				delete $::Values->{"mv_error_$var"};
+			}
+			else {
 # LEGACY
-			$::Values->{"mv_error_$var"} = $message;
+				$::Values->{"mv_error_$var"} = $message;
 # END LEGACY
-			$Vend::Session->{errors} = {}
-				if ! $Vend::Session->{errors};
-			$Vend::Session->{errors}{$var} = $message;
-			push @Errors, "$var: $message";
+				if( $No_error ) {
+					# do nothing
+				}
+				elsif( $Vend::Session->{errors}{$var} ) {
+					if ($message and $Vend::Session->{errors}{$var} !~ /\Q$message/) {
+						$Vend::Session->{errors}{$var} = errmsg(
+							'%s and %s',
+							$Vend::Session->{errors}{$var},
+							$message
+						);
+					}
+				}
+				else {
+					$Vend::Session->{errors}{$var} = $message ||
+						errmsg('%s: failed check', $var);
+				}
+				push @Errors, "$var: $message";
+			}
 		}
-#::logDebug("profile status now=$status");
 		if (defined $Success) {
 			$status = $Success;
 			last;
 		}
 		last if $Fatal && ! $status;
 	}
-	my $errors = join "\n", @Errors;
-	$errors = '' unless defined $errors and ! $Success;
-#::logDebug("FINISH checking profile $Profile: Fatal=$Fatal Final=$Final Status=$status");
-	if($status) {
-		$::Values->{mv_nextpage} = $CGI::values{mv_nextpage} = $Success_page
-			if $Success_page;
-	}
-	elsif ($Fail_page) {
-		$::Values->{mv_nextpage} = $CGI::values{mv_nextpage} = $Fail_page;
-	}
-	if($Final and ! scalar @{$Vend::Items}) {
-		$status = 0;
-		$::Values->{"mv_error_items"}       =
-			$Vend::Session->{errors}{items}  =
-				errmsg(
-					"You might want to order something! No items in cart.",
-				);
-
-	}
-	return ($status, $Final, $errors);
+	return $status;
 }
 
 my $state = <<EOF;
@@ -1083,7 +1121,9 @@
 		return (1, $var, '');
 	}
 	else {
-		return (undef, $var, "'$val' not a two-letter state or province code");
+		return (undef, $var,
+			errmsg( "'%s' not a two-letter state or province code", $val )
+		);
 	}
 }
 
@@ -1096,7 +1136,9 @@
 		return (1, $var, '');
 	}
 	else {
-		return (undef, $var, "'$val' not a two-letter state code");
+		return (undef, $var,
+			errmsg( "'%s' not a two-letter state code", $val )
+		);
 	}
 }
 
@@ -1108,7 +1150,9 @@
 		return (1, $var, '');
 	}
 	else {
-		return (undef, $var, "'$val' not a two-letter province code");
+		return (undef, $var,
+			errmsg( "'%s' not a two-letter province code", $val )
+		);
 	}
 }
 
@@ -1122,9 +1166,10 @@
 }
 
 sub _postcode {
+	my($ref,$var,$val) = @_;
 	((_zip(@_))[0] or (_ca_postcode(@_))[0])
-		and return (1, $_[1], '');
-	return (undef, $_[1], 'not a US or Canada postal/zip code');
+		and return (1, $var, '');
+	return (undef, $var, errmsg("'%s' not a US zip or Canadian postal code", $val));
 }
 
 sub _ca_postcode {
@@ -1134,14 +1179,14 @@
 		and
 	$val =~ /^[ABCEGHJKLMNPRSTVXYabceghjklmnprstvxy]\d[A-Za-z]\d[A-Za-z]\d$/
 		and return (1, $var, '');
-	return (undef, $var, 'not a Canadian postal code');
+	return (undef, $var, errmsg("'%s' not a Canadian postal code", $val));
 }
 
 sub _zip {
 	my($ref,$var,$val) = @_;
-	defined $val and $val =~ /^\s*\d{5}(?:[-]\d{4})?\s*$/
+	defined $val and $val =~ /^\s*\d{5}(?:-?\d{4})?\s*$/
 		and return (1, $var, '');
-	return (undef, $var, 'not a US zip code');
+	return (undef, $var, errmsg("'%s' not a US zip code", $val));
 }
 
 *_us_postcode = \&_zip;
@@ -1157,7 +1202,7 @@
 	my($ref,$var,$val) = @_;
 	defined $val and $val =~ /\d{3}.*\d{3}/
 		and return (1, $var, '');
-	return (undef, $var, 'not a phone number');
+	return (undef, $var, errmsg("'%s' not a phone number", $val));
 }
 
 sub _phone_us {
@@ -1166,7 +1211,7 @@
 		return (1, $var, '');
 	}
 	else {
-		return (undef, $var, 'not a US phone number');
+		return (undef, $var, errmsg("'%s' not a US phone number", $val));
 	}
 }
 
@@ -1176,7 +1221,7 @@
 		return (1, $var, '');
 	}
 	else {
-		return (undef, $var, 'not a US phone number with area code');
+		return (undef, $var, errmsg("'%s' not a US phone number with area code", $val));
 	}
 }
 
@@ -1186,7 +1231,9 @@
 		return (1, $var, '');
 	}
 	else {
-		return (undef, $var, 'not a US phone number with area code (strict formatting)');
+		return (undef, $var,
+			errmsg("'%s' not a US phone number with area code (strict formatting)", $val)
+		);
 	}
 }
 
@@ -1196,13 +1243,27 @@
 		return (1, $var, '');
 	}
 	else {
-		return (undef, $var, "$val not an email address");
+		return (undef, $var,
+			errmsg( "'%s' not an email address", $val )
+		);
+	}
+}
+
+sub _email_only {
+	my($ref, $var, $val) = @_;
+	if($val and $val =~ /^[\040-\176]+\@[-A-Za-z0-9.]+\.[A-Za-z]+$/) {
+		return (1, $var, '');
+	}
+	else {
+		return (undef, $var,
+			errmsg( "'%s' not an email address", $val )
+		);
 	}
 }
 
 # Contributed by Ton Verhagen -- April 15, 2000
 sub _isbn {
-	# $ref is to Vend::Session->{'values'} hash (well, actually ref to %CGI::values)
+	# $ref is to $::Values hash (well, actually ref to %CGI::values)
 	# $var is the passed name of the variable
 	# $val is current value of checked variable
 	# This routine will return 1 if isbn is ok, else returns 0
@@ -1225,7 +1286,7 @@
 	  return ( $sum%11 ? 0 : 1, $var, '' );
 	}
 	else {
-	  return (undef, $var, "not a valid isbn number");
+	  return (undef, $var, errmsg("'%s' not a valid isbn number", $val));
 	}
 }
 
@@ -1233,19 +1294,26 @@
 	my($ref,$var,$val) = @_;
 	return (1, $var, '')
 		if (defined $ref->{$var} and $ref->{$var} =~ /\S/);
-	return (undef, $var, "blank");
+	return (undef, $var, errmsg("blank"));
 }
 
 sub _true {
 	my($ref,$var,$val) = @_;
 	return (1, $var, '') if is_yes($val);
-	return (undef, $var, "false");
+	return (undef, $var, errmsg("false"));
 }
 
 sub _false {
 	my($ref,$var,$val) = @_;
 	return (1, $var, '') if is_no($val);
-	return (undef, $var, "true");
+	return (undef, $var, errmsg("true"));
+}
+
+sub _defined {
+	my($ref,$var,$val) = @_;
+	return (1, $var, '')
+		if defined $::Values->{$var};
+	return (undef, $var, errmsg("undefined"));
 }
 
 sub _required {
@@ -1254,15 +1322,21 @@
 		if (defined $val and $val =~ /\S/);
 	return (1, $var, '')
 		if (defined $ref->{$var} and $ref->{$var} =~ /\S/);
-	return (undef, $var, "blank");
+	return (undef, $var, errmsg("blank"));
+}
+
+sub _luhn {
+	my($ref, $var, $val) = @_;
+
+	return (1, $var, '') if luhn($val,2);
+	return (undef, $var, errmsg('failed the LUHN-10 check'));
 }
 
 sub counter_number {
 	my $file = shift || $Vend::Cfg->{OrderCounter};
-	$File::CounterFile::DEFAULT_DIR = $Vend::Cfg->{VendRoot}
-		unless $file =~ m!^/!;
-	my $c = new File::CounterFile $file, "000000";
-	return $c->inc;
+	my $sql = shift;
+	my $start = shift || '000000';
+	return Vend::Interpolate::tag_counter($file, { sql => $sql, start => $start });
 }
 
 sub update_order_number {
@@ -1303,12 +1377,12 @@
 	local(%SIG);
 	undef $SIG{__DIE__};
 	foreach my $c (@routes) {
-		$::Values = { %$value_save };
-#::logDebug("profile: $c");
+		$Vend::Interpolate::Values = $::Values = { %$value_save };
 		eval {
 			my $route = $Vend::Cfg->{Route_repository}{$c}
 				or do {
-					::logError("Non-existent order route %s, skipping.", $c);
+					# Change to ::logDebug because of dynamic routes
+					::logDebug("Non-existent order route %s, skipping.", $c);
 					next;
 				};
 			if($route->{profile}) {
@@ -1330,45 +1404,23 @@
 			last if $final;
 		}
 	}
-#::logDebug("profile=$c status=$status final=$final failed=$failed errors=$errors missing=$missing");
-	$::Values = $value_save;
+#::logDebug("check_only -- profile=$c status=$status final=$final failed=$failed errors=$errors missing=$missing");
+	$Vend::Interpolate::Values = $::Values = { %$value_save };
 	return (! $failed, $final, $errors);
 }
 
 sub route_order {
 	my ($route, $save_cart, $check_only) = @_;
-	my $cart = [ @$save_cart ];
-	if(! $Vend::Cfg->{Route}) {
-		$Vend::Cfg->{Route} = {
-			report		=> $Vend::Cfg->{OrderReport},
-			receipt		=> $::Values->{mv_order_receipt} || find_special_page('receipt'),
-			encrypt_program	=> '',
-			encrypt		=> 0,
-			pgp_key		=> '',
-			pgp_cc_key	=> '',
-			cyber_mode	=> $CGI::values{mv_cyber_mode} || undef,
-			credit_card	=> 1,
-			profile		=> '',
-			inline_profile		=> '',
-			email		=> $Vend::Cfg->{MailOrderTo},
-			attach		=> 0,
-			counter		=> '',
-			increment	=> 0,
-			continue	=> 0,
-			partial		=> 0,
-			supplant	=> 0,
-			track   	=> '',
-			errors_to	=> $Vend::Cfg->{MailOrderTo},
-		    locale      => 0,
-			sub         => '',
-		};
-	}
-
 	my $main = $Vend::Cfg->{Route};
+	return unless $main;
+	$route = 'default' unless $route;
+
+	my $cart = [ @$save_cart ];
 
 	my $save_mime = $::Instance->{MIME} || undef;
 
-	my $encrypt_program = $main->{encrypt_program} || 'pgpe -fat -r %s';
+	my $encrypt_program = $main->{encrypt_program};
+
 	my (@routes);
 	my $shelf = { };
 	my $item;
@@ -1392,7 +1444,8 @@
 		$shelf->{$_} = [ @$cart ];
 	}
 
-	push @routes, @main;
+	# We empty @main so that we can push more routes on with cascade option
+	push @routes, splice @main;
 
 	my ($c,@out);
 	my $status;
@@ -1400,6 +1453,8 @@
 	
 	my @route_complete;
 	my @route_failed;
+	my @route_done;
+	my $route_checked;
 
 	### This used to be the check_only
 	# Here we return if it is only a check
@@ -1407,62 +1462,131 @@
 
 	# Careful! If you set it on one order and not on another,
 	# you must delete in between.
-	if(! $check_only) {+
-		$::Values->{mv_order_number} = counter_number($main->{counter})
-				unless $Vend::Session->{mv_order_number};
+	if(! $check_only and ! $main->{no_increment} and ! $Vend::Session->{mv_order_number}) {
+		$::Values->{mv_order_number} = counter_number(
+											$main->{counter},
+											$main->{sql_counter},
+											$main->{first_order_number},
+										);
 	}
 
 	my $value_save = { %{$::Values} };
 
+	my @trans_tables;
+
+	# We aren't going to 
+	my %override_key = qw/
+		encrypt_program 1
+	/;
+
+	# Settable by user to indicate failure
+	delete $::Scratch->{mv_route_failed};
+
+	ROUTES: {
 		BUILD:
 	foreach $c (@routes) {
-		my $route = $Vend::Cfg->{Route_repository}{$c};
+		my $route = $Vend::Cfg->{Route_repository}{$c} || {};
+		$main = $route if $route->{master};
+		my $old;
+
+#::logDebug("route $c is: " . ::uneval($route));
+		##### OK, can put variables in DB all the time. It can be dynamic
+		##### from the database if $main->{dynamic_routes} is set. ITL only if
+		##### $main->{expandable}.
+		#####
+		##### The encrypt_program key cannot be dynamic. You can set the
+		##### key substition value instead.
+
+		if($Vend::Cfg->{RouteDatabase} and $main->{dynamic_routes}) {
+			my $ref = tag_data( $Vend::Cfg->{RouteDatabase},
+								undef,
+								$c, 
+								{ hash => 1 }
+								);
+#::logDebug("Read dynamic route %s from database, got: %s", $c, $ref );
+			if($ref) {
+				$old = $route;
+				$route = $ref;
+				for(keys %override_key) {
+					$route->{$_} = $old->{$_};
+				}
+			}
+		}
+
+		if(! %$route) {
+			::logError("Non-existent order routing %s, skipping.", $c);
+			next;
+		}
+
+		# Tricky, tricky
+		if($route->{extended}) {
+			my $ref = get_option_hash($route->{extended});
+			if(ref $ref) {
+				for(keys %$ref) {
+#::logDebug("setting extended $_ = $ref->{$_}");
+					$route->{$_} = $ref->{$_}
+						unless $override_key{$_};
+				}
+			}
+		}
+
+		for(keys %$route) {
+			$route->{$_} =~ s/^\s*__([A-Z]\w+)__\s*$/$::Variable->{$1}/;
+			next unless $main->{expandable};
+			next if $override_key{$_};
+			next unless $route->{$_} =~ /\[/;
+			$route->{$_} = ::interpolate_html($route->{$_});
+		}
+		#####
+		#####
+		#####
+
+		# Compatibility 
+		if($route->{cascade}) {
+			my @extra = grep /\S/, split /[\s,\0]+/, $route->{cascade};
+			for(@extra) {
+				$shelf->{$_} = [ @$cart ];
+				push @main, $_;
+			}
+		}
 
-#::logDebug($Data::Dumper::Indent = 3 and "Route $c:\n" . Data::Dumper::Dumper($route) .	"values:\n" .  Data::Dumper::Dumper($::Values));
-		$::Values = { %$value_save };
+		$Vend::Interpolate::Values = $::Values = { %$value_save };
+		$::Values->{mv_current_route} = $c;
 		my $pre_encrypted;
 		my $credit_card_info;
 
+		$Vend::Items = $shelf->{$c};
+
+		Vend::Interpolate::flag( 'write', {}, $route->{write_tables})
+			if $route->{write_tables};
+
+		Vend::Interpolate::flag( 'transactions', {}, $route->{transactions})
+			if $route->{transactions};
+
+	eval {
+
+	  PROCESS: {
 		if(! $check_only and $route->{inline_profile}) {
 			my $status;
-			eval {
-				($status, undef, $errors) = check_order($route->{inline_profile});
-				die "$errors\n" unless $status;
-			};
+			my $err;
+			($status, undef, $err) = check_order($route->{inline_profile});
+#::logDebug("inline profile returned status=$status errors=$err");
+			die "$err\n" unless $status;
 		}
 
 		if ($CGI::values{mv_credit_card_number}) {
-			if(! $CGI::values{mv_credit_card_type} and
-				 $CGI::values{mv_credit_card_number} )
-			{
-				if($CGI::values{mv_credit_card_number} =~ /\s*4/) {
-					$CGI::values{mv_credit_card_type} = 'visa';
-				}
-				elsif($CGI::values{mv_credit_card_number} =~ /\s*5/) {
-					$CGI::values{mv_credit_card_type} = 'mc';
-				}
-				elsif($CGI::values{mv_credit_card_number} =~ /\s*37/) {
-					$CGI::values{mv_credit_card_type} = 'amex';
-				}
-				else {
-					$CGI::values{mv_credit_card_type} = 'discover/other';
-				}
-			}
-			$::Values->{mv_credit_card_info} = join "\t", 
-								$CGI::values{mv_credit_card_type},
-								$CGI::values{mv_credit_card_number},
-								$CGI::values{mv_credit_card_exp_month} .
-								"/" . $CGI::values{mv_credit_card_exp_year};
+			$CGI::values{mv_credit_card_type} ||=
+				guess_cc_type($CGI::values{mv_credit_card_number});
+			my %attrlist = map { uc($_) => $CGI::values{$_} } keys %CGI::values;
+			$::Values->{mv_credit_card_info} = build_cc_info(\%attrlist);
+		}
+		elsif ($::Values->{mv_credit_card_info}) {
+			$::Values->{mv_credit_card_info} =~ /BEGIN\s+[PG]+\s+MESSAGE/
+				and $pre_encrypted = 1;
 		}
 
-		$Vend::Items = $shelf->{$c};
-		if(! defined $Vend::Cfg->{Route_repository}{$c}) {
-			logError("Non-existent order routing %s", $c);
-			next;
-		}
-	eval {
-
 		if ($check_only and $route->{profile}) {
+			$route_checked = 1;
 			my ($status, $final, $missing) = check_order($route->{profile});
 			if(! $status) {
 				die errmsg(
@@ -1475,41 +1599,23 @@
 			}
 		}
 
-#::logError("route = $c, cyber_mode=$route->{cyber_mode}, check_only=1") if $check_only;
-		if($route->{cyber_mode}) {
-			my $save = $CGI::values{mv_cyber_mode};
-			$CGI::values{mv_cyber_mode} = $route->{cyber_mode};
-			my $glob = {};
-			my (@vars) =  (qw/ CYBER_CONFIGFILE CYBER_CURRENCY CYBER_HOST
-							CYBER_PORT CYBER_REMAP CYBER_SECRET CYBER_VERSION /);
-			for(@vars) {
-				next unless $route->{$_};
-				$glob->{$_} = $::Variable->{$_};
-				$::Variable->{$_} = $route->{$_};
-			}
+	  	last PROCESS if $check_only;
+
+		if($route->{payment_mode}) {
 			my $ok;
-			my $parms;
-			my $msg;
-			eval {
-				($ok, $parms, $msg) = _charge(\%CGI::values, $route->{cyber_mode});
-			};
-#::logError("route = $c, cyber_mode=$route->{cyber_mode}, ok=$ok");
-			if(! $ok) {
-				$Vend::Session->{errors}{mv_credit_card_valid} = $msg;
-			}
-			for(@vars) {
-				next unless exists $glob->{$_};
-				$::Variable->{$_} = $glob->{$_};
-			}
-			$CGI::values{mv_cyber_mode} = $save;
-			unless ($ok) {
+			$ok = Vend::Payment::charge($route->{payment_mode});
+			if (! $ok) {
 				die errmsg("Failed online charge for routing %s: %s",
 								$c,
 								$Vend::Session->{mv_payment_error}
 							);
 			}
+			else {
+				$Vend::Session->{route_payment_id} ||= {};
+				$Vend::Session->{route_payment_id}{$c} = $Vend::Session->{payment_id};
+			}
 		}
-		elsif(  $route->{credit_card}
+		if(  $route->{credit_card}
 				and ! $pre_encrypted
 			    and $::Values->{mv_credit_card_info}
 				)
@@ -1517,7 +1623,7 @@
 			$::Values->{mv_credit_card_info} = pgp_encrypt(
 								$::Values->{mv_credit_card_info},
 								($route->{pgp_cc_key} || $route->{pgp_key}),
-								($route->{encrypt_program} || $encrypt_program),
+								($route->{encrypt_program} || $main->{encrypt_program} || $encrypt_program),
 							);
 		}
 
@@ -1527,18 +1633,27 @@
 			$::Values->{mv_order_number} = $Vend::Session->{mv_order_number};
 		}
 		elsif($route->{counter}) {
-			$::Values->{mv_order_number} = counter_number($route->{counter});
+			$::Values->{mv_order_number} = counter_number(
+												$route->{counter},
+												$route->{sql_counter},
+												$route->{first_order_number},
+											);
 		}
 		elsif($route->{increment}) {
-			$::Values->{mv_order_number} = counter_number();
+			$::Values->{mv_order_number} = counter_number(
+												$main->{counter},
+												$main->{sql_counter},
+												$main->{first_order_number},
+											);
 		}
+		my $pagefile;
 		my $page;
 		if($route->{empty} and ! $route->{report}) {
 			$page = '';
 		}
 		else {
-			$page = readfile($route->{'report'} || $main->{'report'},
-							$Global::NoAbsolute, $route->{'locale'});
+			$pagefile = $route->{'report'} || $main->{'report'};
+			$page = readfile($pagefile, $Global::NoAbsolute);
 		}
 		die errmsg(
 			"No order report %s or %s found.",
@@ -1548,48 +1663,56 @@
 
 		my $use_mime;
 		undef $::Instance->{MIME};
-		$page = interpolate_html($page) if $page;
-
-#::logDebug("MIME=$::Instance->{MIME}");
+		if(not ($route->{credit_card} || $route->{encrypt}) ) {
+			$::Values->{mv_credit_card_info}
+				=~ s/^(\s*\w+\s+)(\d\d)[\d ]+(\d\d\d\d)/$1$2 NEED ENCRYPTION $3/;
+		}
+		eval {
+			$page = interpolate_html($page) if $page;
+		};
+		if ($@) {
+			die "Error while interpolating page $pagefile:\n $@";
+		}
 		$use_mime   = $::Instance->{MIME} || undef;
 		$::Instance->{MIME} = $save_mime  || undef;
 
 		if($route->{encrypt}) {
 			$page = pgp_encrypt($page,
 								$route->{pgp_key},
-								$route->{encrypt_program} || $encrypt_program,
+								($route->{encrypt_program} || $main->{encrypt_program} || $encrypt_program),
 								);
 		}
 		my ($address, $reply, $to, $subject, $template);
 		if($route->{attach}) {
 			$Vend::Items->[0]{mv_order_report} = $page;
 		}
+		elsif ($route->{empty}) {
+			# Do nothing
+		}
 		elsif ($address = $route->{email}) {
 			$address = $::Values->{$address} if $address =~ /^\w+$/;
-			$subject = $::Values->{mv_order_subject} || 'ORDER %s';
+			$subject = $route->{subject} || $::Values->{mv_order_subject} || 'ORDER %s';
 			$subject =~ s/%n/%s/;
 			$subject = sprintf "$subject", $::Values->{mv_order_number};
 			$reply   = $route->{reply} || $main->{reply};
 			$reply   = $::Values->{$reply} if $reply =~ /^\w+$/;
 			$to		 = $route->{email};
-			my $ary = [$route->{sub}, $to, $subject, $page, $reply, $use_mime];
+			my $ary = [$to, $subject, $page, $reply, $use_mime];
 			if($route->{from}) {
 				push @$ary, "From: $route->{from}";
 			}
 			push @out, $ary;
 		}
-		elsif ($route->{empty}) {
-			# Do nothing
-		}
 		else {
-			die "Empty order routing $c (and not explicitly empty)";
+			die "Empty order routing $c (and not explicitly empty).\nEither attach or email are required in the route setting.\n";
 		}
 		if ($route->{supplant}) {
 			track_order($::Values->{mv_order_number}, $page);
 		}
 		if ($route->{track}) {
-			Vend::Util::writefile($route->{track}, $page)
-				or ::logError("route tracking error writing $route->{track}: $!");
+			my $fn = escape_chars($route->{track});
+			Vend::Util::writefile($fn, $page)
+				or ::logError("route tracking error writing %s: %s", $fn, $!);
 			my $mode = $route->{track_mode} || '';
 			if ($mode =~ s/^0+//) {
 				chmod oct($mode), $fn;
@@ -1614,39 +1737,59 @@
 				chmod $mode, $fn;
 			}
 		}
+		if($::Scratch->{mv_route_failed}) {
+			my $msg = delete $::Scratch->{mv_route_error}
+					|| ::errmsg('Route %s failed.', $c);
+			::logError($msg);
+			die $msg;
+		}
 	  } # end PROCESS
 	};
 		if($@) {
-#::logError("DIED, route = $c, cyber_mode=$route->{cyber_mode}, check_only=1") if $check_only;
+#::logDebug("route failed: $c");
 			my $err = $@;
 			$errors .=  errmsg(
 							"Error during creation of order routing %s:\n%s",
 							$c,
 							$err,
 						);
-			push @route_failed, $c;
+			if ($route->{error_ok}) {
+				push @route_complete, $c;
+				next BUILD;
+			}
 			next BUILD if $route->{continue};
+			push @route_failed, $c;
+			@out = ();
+			@route_done = @route_complete;
 			@route_complete = ();
-			last BUILD;
+			last ROUTES;
 		}
 
 		push @route_complete, $c;
 
 	} #BUILD
+
+	if(@main and ! @route_failed) {
+		@routes = splice @main;
+		redo ROUTES;
+	}
+
+  } #ROUTES
+
 	my $msg;
 
 	if($check_only) {
+		$Vend::Interpolate::Values = $::Values = $value_save;
 		$Vend::Items = $save_cart;
-		$::Values = $value_save;
-
 		if(@route_failed) {
-#::logError("DIED, route_failed=" . join ",", @route_failed) if $check_only;
 			return (0, 0, $errors);
 		}
-		else {
-#::logError("route checks all succeeded") if $check_only;
+		elsif($route_checked) {
 			return (1, 1, '');	
 		}
+		else {
+			return (1, undef, '');	
+		}
 	}
 
 	foreach $msg (@out) {
@@ -1679,11 +1822,14 @@
 	}
 
 	$::Instance->{MIME} = $save_mime  || undef;
-	$::Values = $value_save;
+	$Vend::Interpolate::Values = $::Values = $value_save;
 	$Vend::Items = $save_cart;
 
 	for(@route_failed) {
 		my $route = $Vend::Cfg->{Route_repository}{$_};
+		if($route->{transactions}) {
+			Vend::Interpolate::flag( 'rollback', {}, $route->{transactions})
+		}
 		next unless $route->{rollback};
 		Vend::Interpolate::tag_perl(
 					$route->{rollback_tables},
@@ -1691,8 +1837,12 @@
 					$route->{rollback}
 		);
 	}
+
 	for(@route_complete) {
 		my $route = $Vend::Cfg->{Route_repository}{$_};
+		if($route->{transactions}) {
+			Vend::Interpolate::flag( 'commit', {}, $route->{transactions})
+		}
 		next unless $route->{commit};
 		Vend::Interpolate::tag_perl(
 					$route->{commit_tables},
@@ -1718,24 +1868,196 @@
 		::logError("ERRORS on ORDER %s:\n%s", $::Values->{mv_order_number}, $errors);
 	}
 
+	# Get rid of this puppy
+	$::Values->{mv_credit_card_info}
+			=~ s/^(\s*\w+\s+)(\d\d)[\d ]+(\d\d\d\d)/$1$2 NEED ENCRYPTION $3/;
 	# If we give a defined value, the regular mail_order routine will not
 	# be called
+#::logDebug("route errors=$errors supplant=$main->{supplant}");
 	if($main->{supplant}) {
-		return ($status, $::Values->{mv_order_number});
+		return ($status, $::Values->{mv_order_number}, $main);
 	}
-	return (undef, $::Values->{mv_order_number});
+	return (undef, $::Values->{mv_order_number}, $main);
 }
 
+## DO ORDER
 
-sub add_items {
+# Order an item
+sub do_order {
+    my($path) = @_;
+	my $code        = $CGI::values{mv_arg};
+#::logDebug("do_order: path=$path");
+	my $cart;
+	my $page;
+# LEGACY
+	if($path =~ s:/(.*)::) {
+		$cart = $1;
+		if($cart =~ s:/(.*)::) {
+			$page = $1;
+		}
+	}
+# END LEGACY
+	if(defined $CGI::values{mv_pc} and $CGI::values{mv_pc} =~ /_(\d+)/) {
+		$CGI::values{mv_order_quantity} = $1;
+	}
+	$CGI::values{mv_cartname} = $cart if $cart;
+	$CGI::values{mv_nextpage} = $page if $page;
+# LEGACY
+	$CGI::values{mv_nextpage} = $CGI::values{mv_orderpage}
+								|| find_special_page('order')
+		if ! $CGI::values{mv_nextpage};
+# END LEGACY
+	add_items($code);
+    return 1;
+}
+
+my @Scan_modifiers = qw/
+		mv_ad
+		mv_an
+		mv_bd
+		mv_bd
+/;
+
+# Returns undef if interaction error
+sub update_quantity {
+    return 1 unless defined  $CGI::values{"quantity0"}
+		|| $CGI::values{mv_quantity_update};
+	my($h, $i, $quantity, $modifier, $cart);
+
+	if ($CGI::values{mv_cartname}) {
+		$cart = $::Carts->{$CGI::values{mv_cartname}} ||= [];
+	}
+	else {
+		$cart = $Vend::Items;
+	}
+
+	my @mods;
+	@mods = @{$Vend::Cfg->{UseModifier}} if $Vend::Cfg->{UseModifier};
+
+#::logDebug("adding modifiers");
+	push(@mods, (grep $_ !~ /^mv_/, split /\0/, $CGI::values{mv_item_option}))
+		if defined $CGI::values{mv_item_option};
+
+	my %seen;
+	push @mods, grep defined $CGI::values{"${_}0"}, @Scan_modifiers;
+	@mods = grep ! $seen{$_}++, @mods;
+
+	foreach $h (@mods) {
+		delete @{$::Values}{grep /^$h\d+$/, keys %$::Values};
+		foreach $i (0 .. $#$cart) {
+#::logDebug("updating line $i modifiers: " . ::uneval($cart->[$i]));
+#::logDebug(qq{CGI value=$CGI::values{"$h$i"}});
+			$modifier = $CGI::values{"$h$i"}
+					  || (defined $cart->[$i]{$h} ? '' : undef);
+#::logDebug("line $i modifier $h now $modifier");
+			if (defined($modifier)) {
+				$modifier =~ s/\0+/\0/g;
+				$modifier =~ s/\0$//;
+				$modifier =~ s/^\0//;
+				$modifier =~ s/\0/, /g;
+				$cart->[$i]->{$h} = $modifier;
+				$::Values->{"$h$i"} = $modifier;
+				delete $CGI::values{"$h$i"};
+			}
+		}
+	}
+
+	foreach $i (0 .. $#$cart) {
+#::logDebug("updating line $i quantity: " . ::uneval($cart->[$i]));
+		my $line = $cart->[$i];
+		$line->{mv_ip} = $i;
+    	$quantity = $CGI::values{"quantity$i"};
+    	next unless defined $quantity;
+    	if ($quantity =~ m/^\d*$/) {
+        	$line->{'quantity'} = $quantity || 0;
+    	}
+    	elsif ($quantity =~ m/^[\d.]+$/
+				and $Vend::Cfg->{FractionalItems} ) {
+        	$line->{'quantity'} = $quantity;
+    	}
+		# This allows a last-positioned input of item quantity to
+		# remove the item
+		elsif ($quantity =~ s/.*\00$/0/) {
+			$CGI::values{"quantity$i"} = $quantity;
+			redo;
+		}
+		# This allows a multiple input of item quantity to
+		# pass -- FIRST ONE CONTROLS
+		elsif ($quantity =~ s/\0.*//) {
+			$CGI::values{"quantity$i"} = $quantity;
+			redo;
+		}
+		else {
+			my $item = $line->{'code'};
+			$line->{quantity} = int $line->{quantity};
+        	$Vend::Session->{errors}{mv_order_quantity} =
+				errmsg("'%s' for item %s is not numeric/integer", $quantity, $item);
+    	}
+    	$::Values->{"quantity$i"} = delete $CGI::values{"quantity$i"};
+		SKUSET: {
+			my $sku;
+			my $found_option;
+			last SKUSET unless $sku = delete $CGI::values{"mv_sku$i"};
+			my @sku = split /\0/, $sku, -1;
+			for(@sku[1..$#sku]) {
+				if (not length $_) {
+				$_ = $::Variable->{MV_VARIANT_JOINER} || '0';
+				next;
+				}
+				$found_option++;
+			}
+
+			if(@sku > 1 and ! $found_option) {
+				splice @sku, 1;
+			}
 
+			$sku = join "-", @sku;
+
+			my $ib;
+			unless($ib 	= ::product_code_exists_tag($sku)) {
+				push @{$Vend::Session->{warnings} ||= []},
+					errmsg("Not a valid option combination: %s", $sku);
+					last SKUSET;
+			}
+
+			$line->{mv_ib} = $ib;
+
+			if($sku ne $line->{code}) {
+				if($line->{mv_mp}) {
+					$line->{mv_sku} = $line->{code} = $sku;
+				}
+				elsif (! $line->{mv_sku}) {
+					$line->{mv_sku} = $line->{code};
+					$line->{code} 	= $sku;
+				}
+				else {
+					$line->{code}	= $sku;
+				}
+			}
+		}
+    }
+#::logDebug("after update, cart is: " . ::uneval($cart));
+
+	# If the user has put in "0" for any quantity, delete that item
+    # from the order list. Handles sub-items.
+    Vend::Cart::toss_cart($cart, $CGI::values{mv_cartname});
+
+#::logDebug("after toss, cart is: " . ::uneval($cart));
+
+	1;
+
+}
+
+
+sub add_items {
 	my($items,$quantities) = @_;
 
-	$items = $CGI::values{mv_order_item} if ! defined $items;
+	$items = delete $CGI::values{mv_order_item} if ! defined $items;
 	return unless $items;
 
 	my($code,$found,$item,$base,$quantity,$i,$j,$q);
 	my(@items);
+	my(@skus);
 	my(@quantities);
 	my(@bases);
 	my(@lines);
@@ -1749,7 +2071,13 @@
 
 	::update_quantity() if ! defined $CGI::values{mv_orderline};
 
-	my $cart = Vend::Cart::get_cart($CGI::values{mv_cartname});
+	my $cart;
+	if($CGI::values{mv_cartname}) {
+		$cart = $::Carts->{$CGI::values{mv_cartname}} ||= [];
+	}
+	else {
+		$cart = $Vend::Items;
+	}
 
 	@items      = split /\0/, ($items), -1;
 	@quantities = split /\0/, ($quantities || delete $CGI::values{mv_order_quantity} || ''), -1;
@@ -1767,6 +2095,23 @@
 		}
 	}
 
+	if(defined $CGI::values{mv_item_option}) {
+		$Vend::Cfg->{UseModifier} = [] if ! $Vend::Cfg->{UseModifier};
+		my %seen;
+		my @mods = (grep $_ !~ /^mv_/, split /\0/, $CGI::values{mv_item_option});
+		@mods = grep ! $seen{$_}++, @mods;
+		push @{$Vend::Cfg->{UseModifier}}, @mods;
+	}
+
+	if($CGI::values{mv_sku}) {
+		my @sku = split /\0/, $CGI::values{mv_sku}, -1;
+		for (@sku) {
+			$_ = $::Variable->{MV_VARIANT_JOINER} || '0' if ! length($_);
+		}
+		$skus[0]   = $items[0];
+		$items[0] = join '-', @sku;
+	}
+
 	if ($Vend::Cfg->{UseModifier}) {
 		foreach $attr (@{$Vend::Cfg->{UseModifier} || []}) {
 			$attr{$attr} = [];
@@ -1775,14 +2120,18 @@
 		}
 	}
 
-    my ($group, $found_master, $mv_mi, $mv_si, @group);
+	my ($group, $found_master, $mv_mi, $mv_si, $mv_mp, @group, @modular);
 
-    @group = split /\0/, (delete $CGI::values{mv_order_group} || ''), -1;
-    for( $i = 0; $i < @group; $i++ ) {
-       $attr{mv_mi}->[$i] = $group[$i] ? ++$Vend::Session->{pageCount} : 0;
+	my $separate;
+	if( $CGI::values{mv_order_modular} ) {
+		@modular = split /\0/, delete $CGI::values{mv_order_modular};
+		for( my $i = 0; $i < @modular; $i++ ) {
+		   $attr{mv_mp}->[$i] = $modular[$i] if $modular[$i];
+		}
+		$separate = 1;
 	}
-
-	my $separate = defined $CGI::values{mv_separate_items}
+	else {
+		$separate = defined $CGI::values{mv_separate_items}
 					? is_yes($CGI::values{mv_separate_items})
 					: (
 						$Vend::Cfg->{SeparateItems} ||
@@ -1791,14 +2140,24 @@
 						 && is_yes( $Vend::Session->{scratch}->{mv_separate_items} )
 						 )
 						);
+	}
+
+	@group   = split /\0/, (delete $CGI::values{mv_order_group} || ''), -1;
+	for( my $i = 0; $i < @group; $i++ ) {
+	   $attr{mv_mi}->[$i] = $group[$i] ? ++$Vend::Session->{pageCount} : 0;
+	}
+
 	$j = 0;
 	my $set;
 	foreach $code (@items) {
-	   undef $item;
-       $quantity = defined $quantities[$j] ? $quantities[$j] : 1;
-       ($j++,next) unless $quantity;
-	   $set = $quantity =~ s/^=//;
-	    if(! $fly[$j]) {
+		undef $item;
+		$quantity = defined $quantities[$j] ? $quantities[$j] : 1;
+		$set = $quantity =~ s/^=//;
+		$quantity =~ s/^(-?)\D+/$1/;
+		$quantity =~ s/^(-?\d*)\D.*/$1/
+			unless $Vend::Cfg->{FractionalItems};
+		($j++,next) unless $quantity;
+		if(! $fly[$j]) {
 			$base = product_code_exists_tag($code, $bases[$j] || undef);
 		}
 		else {
@@ -1814,7 +2173,7 @@
 			};
 			if($@) {
 				::logError(
-				"failed on-the-fly item add with error %s for: tag=%s sku=%s, qty=%s, passed=%s",
+					"failed on-the-fly item add with error %s for: tag=%s sku=%s, qty=%s, passed=%s",
 					$@,
 					$Vend::Cfg->{OnFly},
 					$code,
@@ -1830,7 +2189,6 @@
 		}
 
 		INCREMENT: {
-
 			# Check that the item has not been already ordered.
 			# But let us order separates if so configured
 			$found = -1;
@@ -1840,7 +2198,6 @@
 			foreach $i (0 .. $#$cart) {
 				if ($cart->[$i]->{'code'} eq $code) {
 					next unless $base eq $cart->[$i]->{mv_ib};
-#::logDebug("incrementing line $i");
 					$found = $i;
 					# Increment quantity. This is different than
 					# the standard handling because we are ordering
@@ -1857,17 +2214,21 @@
 				if ! $item;
 
 			# Add the master item/sub item ids if appropriate
-          if(@group) {
-           if($attr{mv_mi}->[$j]) {
-              $item->{mv_mi} = $mv_mi = $attr{mv_mi}->[$j];
-              $item->{mv_si} = $mv_si = 0;
-           }
-           else {
-              $item->{mv_mi} = $mv_mi;
-              $item->{mv_si} = ++$mv_si;
-           }
+			if(@group) {
+				if($attr{mv_mi}->[$j]) {
+					$item->{mv_mi} = $mv_mi = $attr{mv_mi}->[$j];
+					$item->{mv_mp} = $mv_mp = $attr{mv_mp}->[$j];
+					$item->{mv_si} = $mv_si = 0;
+				}
+				else {
+					$item->{mv_mi} = $mv_mi;
+					$item->{mv_si} = ++$mv_si;
+					$item->{mv_mp} = $attr{mv_mp}->[$j] || $mv_mp;
+				}
 			}
 
+			$item->{mv_sku} = $skus[$i] if defined $skus[$i];
+
 			if($Vend::Cfg->{UseModifier}) {
 				foreach $i (@{$Vend::Cfg->{UseModifier}}) {
 					$item->{$i} = $attr{$i}->[$j];
@@ -1880,18 +2241,15 @@
 						$key = $table;
 						$table = $base;
 					}
-#::logDebug("AutoModifer fetch $key: $table :: $key :: $code");
 					$item->{$key} = tag_data($table, $key, $code);
 				}
 			}
 			if($lines[$j] =~ /^\d+$/ and defined $cart->[$lines[$j]] ) {
-#::logDebug("editing line $lines[$j]");
 				$cart->[$lines[$j]] = $item;
 			}
 			else {
-#::logDebug("adding to line");
 # TRACK
-                $Vend::Track->add_item($cart,$item);
+				$Vend::Track->add_item($cart,$item) if $Vend::Track;
 # END TRACK
 				push @$cart, $item;
 			}
@@ -1901,82 +2259,22 @@
 
 	if($Vend::Cfg->{OrderLineLimit} and $#$cart >= $Vend::Cfg->{OrderLineLimit}) {
 		@$cart = ();
-		my $msg = <<EOF;
-WARNING:
-Possible bad robot. Cart limit of $Vend::Cfg->{OrderLineLimit} exceeded.  Cart emptied.
-EOF
+		my $msg = errmsg(
+			"WARNING:\n" .
+			"Possible bad robot. Cart limit of %s exceeded. Cart emptied.\n",
+			$Vend::Cfg->{OrderLineLimit}
+		);
 		do_lockout($msg);
 	}
-	Vend::Cart::toss_cart($cart);
+	Vend::Cart::toss_cart($cart, $CGI::values{mv_cartname});
 }
 
-#### recode this in Vend::Mail as send
-# LEGACY4
-sub send_mail {
-    my($to, $subject, $body, $reply, $use_mime, @extra_headers) = @_;
-    my($ok);
-#::logDebug("send_mail: to=$to subj=$subject r=$reply mime=$use_mime\n");
-
-	unless (defined $use_mime) {
-		$use_mime = $::Instance->{MIME} || undef;
-	}
-
-	if(!defined $reply) {
-		$reply = $::Values->{mv_email}
-				?  "Reply-To: $::Values->{mv_email}\n"
-				: '';
-	}
-	elsif ($reply) {
-		$reply = "Reply-To: $reply\n"
-			unless $reply =~ /^reply-to:/i;
-		$reply =~ s/\s+$/\n/;
-	}
-
-    $ok = 0;
-	my $none;
-
-	if("\L$Vend::Cfg->{SendMailProgram}" eq 'none') {
-		$none = 1;
-		$ok = 1;
-	}
-
-    SEND: {
-		last SEND if $none;
-		open(MVMAIL,"|$Vend::Cfg->{SendMailProgram} $to") or last SEND;
-		my $mime = '';
-		$mime = Vend::Interpolate::mime('header', {}, '') if $use_mime;
-		print MVMAIL "To: $to\n", $reply, "Subject: $subject\n"
-	    	or last SEND;
-		for(@extra_headers) {
-			s/\s*$/\n/;
-			print MVMAIL $_
-				or last SEND;
-		}
-		$mime =~ s/\s*$/\n/;
-		print MVMAIL $mime
-	    	or last SEND;
-		print MVMAIL $body
-				or last SEND;
-		print MVMAIL Vend::Interpolate::do_tag('mime boundary') . '--'
-			if $use_mime;
-		print MVMAIL "\r\n\cZ" if $Global::Windows;
-		close MVMAIL or last SEND;
-		$ok = ($? == 0);
-    }
-    
-    if ($none or !$ok) {
-		logError("Unable to send mail using %s\nTo: %s\nSubject: %s\n%s\n\n%s",
-				$Vend::Cfg->{SendMailProgram},
-				$to,
-				$subject,
-				$reply,
-				$body,
-		);
-    }
 
-    $ok;
-}
-# END LEGACY4
+# Compatibility with old globalsub payment
+*send_mail = \&Vend::Util::send_mail;
+
+# Compatibility with old globalsub payment
+*map_actual = \&Vend::Payment::map_actual;
 
 1;
 



1.5.4.1   +141 -35   interchange/lib/Vend/Page.pm


rev 1.5.4.1, prev_rev 1.5
Index: Page.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Page.pm,v
retrieving revision 1.5
retrieving revision 1.5.4.1
diff -u -r1.5 -r1.5.4.1
--- Page.pm	6 Aug 2000 19:48:42 -0000	1.5
+++ Page.pm	25 Jan 2003 22:21:28 -0000	1.5.4.1
@@ -1,14 +1,11 @@
-# Page.pm - Handle Interchange page routing
+# Vend::Page - Handle Interchange page routing
 # 
-# $Id: Page.pm,v 1.5 2000/08/06 19:48:42 heins Exp $
+# $Id: Page.pm,v 1.5.4.1 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -48,21 +45,33 @@
 
 use vars qw/$VERSION/;
 
-$VERSION = sprintf("%d.%02d", q$Revision: 1.5 $ =~ /(\d+)\.(\d+)/);
+$VERSION = substr(q$Revision: 1.5.4.1 $, 10);
 
 my $wantref = 1;
 
 sub display_special_page {
-    my($name, $subject) = @_;
-    my($page);
-	
+	my($name, $subject) = @_;
+	my($page);
+
+	$name =~ m/[\[<]+/g
+		and do {
+			::logGlobal(
+					"Security violation -- scripting character in page name '%s'.",
+					$name,
+				);
+			$name = 'violation';
+		};
+
 	$subject = $subject || 'unspecified error';
 	
-    $page = readin($name);
-    die ::get_locale_message(412, "Missing special page: %s\n", $name)
+	$page = readfile($name, $Global::NoAbsolute, 1) || readin($name);
+
+	die ::get_locale_message(412, "Missing special page: %s\n", $name)
 		unless defined $page;
-    $page =~ s#\[subject\]#$subject#ig;
-    return ::response(::interpolate_html($page, 1));
+	$page =~ s#\[subject\]#$subject#ig;
+	$Vend::PageInit = 0;
+	interpolate_html($page, 1);
+	::response();
 }
 
 # Displays the catalog page NAME.  If the file is not found, displays
@@ -70,37 +79,59 @@
 # 
 
 sub display_page {
-    my($name) = @_;
-    my($page);
+	my($name) = @_;
+	my($page);
+
+	$name =~ m/[\[<]+/g
+		and do {
+			::logGlobal(
+					"Security violation -- scripting character in page name '%s'.",
+					$name,
+				);
+			$name = 'violation';
+			return display_special_page($name);
+		};
 
 	$name = $CGI::values{mv_nextpage} unless $name;
-#::logDebug("display_page: $name");
+
 	if($Vend::Cfg->{ExtraSecure} and
 		$Vend::Cfg->{AlwaysSecure}->{$name}
 		and !$CGI::secure) {
 		$name = find_special_page('violation');
 	}
 
-    $page = readin($name);
+	$page = readin($name);
 # TRACK
 	if (defined $page) {
 		$Vend::Track->view_page($name);
 	}
 # END TRACK	
 		
+	my $opt;
 	# Try for on-the-fly if not there
 	if(! defined $page) {
-		$page = Vend::Interpolate::fly_page($name);
+		$page = Vend::Interpolate::fly_page($name)
+			and $opt->{onfly} = 1;
 	}
 
-    if (defined $page) {
-		::response(::interpolate_html($page, 1));
+	# Try one last time for page with index
+	if(! defined $page and $Vend::Cfg->{DirectoryIndex}) {
+		my $try = $name;
+		$try =~ s!/*$!/$Vend::Cfg->{DirectoryIndex}!;
+		$page = readin($try);
+	}
+
+	if (defined $page) {
+		$Vend::PageInit = 0;
+		interpolate_html($page, 1, $opt);
+		::response();
 		return 1;
-    }
+	}
 	else {
+		HTML::Entities::encode($name, $ESCAPE_CHARS::std);
 		display_special_page(find_special_page('missing'), $name);
 		return 0;
-    }
+	}
 }
 
 
@@ -108,15 +139,13 @@
 
 sub do_page {
 	display_page();
-	put_session();
 }
 
 ## DO SEARCH
 sub do_search {
 	my($c) = \%CGI::values;
 	::update_user();
-	::put_session();
-#::logDebug($more);
+
 	if ($c->{mv_more_matches}) {
 		$Vend::Session->{last_search} = "scan/MM=$c->{mv_more_matches}";
 		$c->{mv_more_matches} =~ m/([a-zA-Z0-9])+/;
@@ -129,8 +158,8 @@
 	$c->{mv_cache_key} = generate_key($Vend::Session->{last_search})
 			unless defined $c->{mv_cache_key};
 
-	$Vend::SearchObject{''} = perform_search($c);
-	$CGI::values{mv_nextpage}	= $Vend::SearchObject{''}->{mv_search_page}
+	$::Instance->{SearchObject}{''} = perform_search($c);
+	$CGI::values{mv_nextpage}	= $::Instance->{SearchObject}{''}->{mv_search_page}
 							 	|| find_special_page('search')
 		if ! $CGI::values{mv_nextpage};
 	return 1;
@@ -142,7 +171,6 @@
 	my($path) = @_;
 	my ($key,$page);
 
-	put_session();
 	my $c = {};
 	$Vend::ScanPassed = "scan/$path";
 	find_search_params($c,$path);
@@ -150,8 +178,8 @@
 	if ($c->{mv_more_matches}) {
 		$Vend::Session->{last_search} = "scan/MM=$c->{mv_more_matches}";
 		$Vend::More_in_progress = 1;
-		$c->{mv_more_matches} =~ m/([a-zA-Z0-9])+/;
 		$c->{mv_more_id} = $CGI::values{mv_more_id} || undef;
+		$c->{mv_more_matches} =~ m/([a-zA-Z0-9])+/;
 		$c->{mv_cache_key} = $1;
 		$CGI::values{mv_nextpage} = $c->{mv_nextpage}
 			if ! defined $CGI::values{mv_nextpage};
@@ -160,12 +188,90 @@
 		$c->{mv_cache_key} = generate_key(create_last_search($c));
 	}
 
-	$Vend::SearchObject{''} = perform_search($c);
-	put_session();
-	$CGI::values{mv_nextpage} = $Vend::SearchObject{''}->{mv_search_page}
+	$::Instance->{SearchObject}{''} = perform_search($c);
+	$CGI::values{mv_nextpage} = $::Instance->{SearchObject}{''}->{mv_search_page}
 							 	|| find_special_page('search')
 		if ! $CGI::values{mv_nextpage};
 	return 1;
+}
+
+sub output_test {
+	my ($tag) = @_;
+	my $ary;
+	return '' unless $ary = $Vend::OutPtr{lc $tag};
+	for(@$ary) {
+		next unless $Vend::Output[$_];
+		next unless length(${$Vend::Output[$_]});
+		return 1;
+	}
+	return '';
+}
+
+sub output_cat {
+	my ($tag) = @_;
+	my $ary;
+	return '' unless $ary = $Vend::OutPtr{lc $tag};
+	my $out = '';
+	for(@$ary) {
+		next unless $Vend::Output[$_];
+		$out .= ${$Vend::Output[$_]};
+		undef $Vend::Output[$_];
+	}
+	return $out;
+}
+
+sub output_ary {
+	my ($tag) = @_;
+	my $ary;
+	return '' unless $ary = $Vend::OutPtr{lc $tag};
+	my @out;
+	for(@$ary) {
+		next unless $Vend::Output[$_];
+		push @out, ${$Vend::Output[$_]};
+		undef $Vend::Output[$_];
+	}
+	return \@out;
+}
+
+sub output_rest {
+	my ($tag) = @_;
+	my $out = '';
+	for(@$Vend::Output) {
+		next unless $_;
+		$out .= ${$Vend::Output[$_]};
+		undef $Vend::Output[$_];
+	}
+	return $out;
+}
+
+sub templatize {
+	my ($template) = @_;
+	$template ||= $Vend::Cfg->{PageTemplate} || '{:REST}';
+#::logDebug("Templatizing, template length=" . length($template));
+	my $body = $template;
+
+	$body =~ s!\{\{\@([A-Z][A-Z_]*[A-Z])\}\}(.*?)\{\{/\@\1\}\}!
+					my $tag = lc $1;
+					my $ary;
+					return '' unless $ary = $Vend::OutPtr{$tag};
+					my $tpl = $2;
+					my $out = '';
+					for(@$ary) {
+						my $ref = $Vend::Output[$_]
+							or next;
+						my $chunk = $tpl;
+						$chunk =~ s/\{$tag\}/$$ref/;
+						undef $Vend::Output[$_];
+						$out .= $chunk;
+					}
+					$out;
+				!sge;
+	1 while $body =~ s!\{\{([A-Z][A-Z_]*[A-Z])\?\}\}(.*?)\{\{/\1\?\}\}! output_test(lc $1) ? $2 : ''!egs;
+	1 while $body =~ s!\{\{([A-Z][A-Z_]*[A-Z])\:\}\}(.*?)\{\{/\1\:\}\}! output_test(lc $1) ? '' : $2!egs;
+	$body =~ s!\{\{([A-Z][A-Z_]*[A-Z])\}\}!output_cat($1)!eg;
+	$body =~ s!\{\{:DEFAULT\}\}!output_cat('')!e;
+	$body =~ s!\{\{:REST\}\}!output_rest('')!e;
+	@Vend::Output = (\$body);
 }
 
 1;



1.9.4.5   +339 -965  interchange/lib/Vend/Parse.pm


rev 1.9.4.5, prev_rev 1.9.4.4
Index: Parse.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Parse.pm,v
retrieving revision 1.9.4.4
retrieving revision 1.9.4.5
diff -u -r1.9.4.4 -r1.9.4.5
--- Parse.pm	7 Feb 2001 15:59:20 -0000	1.9.4.4
+++ Parse.pm	25 Jan 2003 22:21:28 -0000	1.9.4.5
@@ -1,14 +1,11 @@
-# Parse.pm - Parse Interchange tags
+# Vend::Parse - Parse Interchange tags
 # 
-# $Id: Parse.pm,v 1.9.4.4 2001/02/07 15:59:20 racke Exp $
+# $Id: Parse.pm,v 1.9.4.5 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -26,14 +23,8 @@
 # MA  02111-1307  USA.
 
 package Vend::Parse;
-
-# $Id: Parse.pm,v 1.9.4.4 2001/02/07 15:59:20 racke Exp $
-
 require Vend::Parser;
 
-
-$VERSION = sprintf("%d.%02d", q$Revision: 1.9.4.4 $ =~ /(\d+)\.(\d+)/);
-
 use Safe;
 use Vend::Util;
 use Vend::Interpolate;
@@ -44,7 +35,7 @@
 
 @ISA = qw(Exporter Vend::Parser);
 
-$VERSION = substr(q$Revision: 1.9.4.4 $, 10);
+$VERSION = substr(q$Revision: 1.9.4.5 $, 10);
 @EXPORT = ();
 @EXPORT_OK = qw(find_matching_end);
 
@@ -56,251 +47,39 @@
 my(@SavedSearch, @SavedCode, @SavedDB, @SavedWith, @SavedItem);
 
 my %PosNumber =	( qw!
-                    
+
+				bounce           2
+				label            1
+				if               1
+				unless           1
 				and              1
-                accessories      2
-                area             2
-				banner           1
-                bounce           2
-                cart             1
-                cgi              1
-                checked          2
-                counter          1
-                currency         2
-                data             3
-				dump			 0
-                default          2
-                discount         1
-                description      2
-				ecml			 2
-				either			 0
-                error            1
-                export           1
-                field            2
-                file             2
-                filter           1
-				flag			 1
-                fly_tax          1
-                fly_list         1
-                goto             2
-				harness          0
-                html_table       0
-                if               1
-                import           2
-                include          2
-                input_filter     1
-                index            1
-                label            1
-                loop             1
-                log              1
-                mvasp            1
-                nitems           1
-                onfly            2
-                order            2
-				or				 1
-                page             2
-                perl             1
-                price            1
-				query			 1
-                row              1
-                salestax         2
-                scratch          1
-                scratchd         1
-				record			 0
-                region		     0
-                selected         2
-                set              1
-                seti             1
-                setlocale        2
-                search_region    0
-                handling         1
-                shipping         1
-                shipping_desc    1
-                sql              2
-                strip            0
-                subtotal         2
-                tag              2
-				time			 1
-				timed_build      1
-				tmp				 1
-				try				 1
-                total_cost       2
-                userdb           1
-                value            2
-                value_extended   1
+				or               1
 
 			! );
 
 my %Order =	(
-
-				accessories		=> [qw( code arg )],
-				area			=> [qw( href arg )],
-				banner          => [qw( category )],
 				bounce			=> [qw( href if )],
-				calc			=> [],
-				cart			=> [qw( name  )],
-				catch			=> [qw( label )],
-				cgi				=> [qw( name  )],
-				'currency'		=> [qw( convert noformat )],
-				checked			=> [qw( name value )],
-				counter			=> [qw( file )],
-				data			=> [qw( table field key )],
-				default			=> [qw( name default )],
-				dump			=> [qw( )],
-				description		=> [qw( code base )],
-				discount		=> [qw( code  )],
-				ecml			=> [qw( name function )],
-				either		    => [qw( )],
-                error           => [qw( name )],
-				export			=> [qw( table )],
-				field			=> [qw( name code )],
-				file			=> [qw( name type )],
-				filter			=> [qw( op )],
-				flag			=> [qw( type )],
-				time			=> [qw( locale )],
-				fly_tax			=> [qw( area )],
-				fly_list		=> [qw( code )],
-				'goto'			=> [qw( name if)],
-				harness		    => [qw( )],
-				html_table	    => [qw( )],
-				'if'			=> [qw( type term op compare )],
-				'or'			=> [qw( type term op compare )],
-				'and'			=> [qw( type term op compare )],
-				'index'			=> [qw( table )],
-				import 			=> [qw( table type )],
-				input_filter 	=> [qw( name )],
-				include			=> [qw( file locale )],
-				item_list		=> [qw( name )],
+				goto			=> [qw( name if)],
 				label			=> [qw( name )],
-				log				=> [qw( file )],
-				loop			=> [qw( list )],
-				nitems			=> [qw( name  )],
-				onfly			=> [qw( code quantity )],
-				order			=> [qw( code quantity )],
-				page			=> [qw( href arg )],
-				perl			=> [qw( tables )],
-				mvasp			=> [qw( tables )],
-				price			=> [qw( code )],
-				process      	=> [qw( target secure )],
-				query			=> [qw( sql )],
-				read_cookie		=> [qw( name )],
-				row				=> [qw( width )],
-				'salestax'		=> [qw( name noformat)],
-				scratch			=> [qw( name  )],
-				scratchd		=> [qw( name  )],
-				search_region	=> [qw( arg   )],
-				region			=> [qw( )],
-				record			=> [qw( )],
-				selected		=> [qw( name value )],
-				set_cookie		=> [qw( name value expire )],
-				setlocale		=> [qw( locale currency )],
-				set				=> [qw( name )],
-				seti			=> [qw( name )],
-				tmp 			=> [qw( name )],
-				'shipping'		=> [qw( mode )],
-				'handling'		=> [qw( mode )],
-				shipping_desc	=> [qw( mode )],
-# SQL
-				sql				=> [qw( type query)],
-# END SQL
-				strip			=> [],
-				'subtotal'		=> [qw( name noformat )],
-				tag				=> [qw( op arg )],
-				timed_build		=> [qw( file )],
-				total_cost		=> [qw( name noformat )],
-				try				=> [qw( label )],
-				userdb          => [qw( function ) ],
-				update          => [qw( function ) ],
-				value			=> [qw( name )],
-				value_extended  => [qw( name )],
-
+				if				=> [qw( type term op compare )],
+				unless			=> [qw( type term op compare )],
+				or				=> [qw( type term op compare )],
+				and				=> [qw( type term op compare )],
+				restrict		=> [qw( enable )],
 			);
 
 my %addAttr = (
 				qw(
-					accessories     1
-					area            1
-					banner          1
-					catch           1
-					checked         1
-					counter         1
-					data			1
-					default			1
-					ecml            1
-					error           1
-					export          1
-					flag            1
-					fly_list        1
-					harness         1
-					html_table      1
-					import          1
-					index           1
-					input_filter    1
-					item_list       1
-					loop			1
-					onfly			1
-					page            1
-					mvasp           1
-				    nitems			1
-					perl            1
-					price			1
-					process         1
-					query			1
-                    sql             1
-					selected        1
-					setlocale       1
-                    record          1
-                    region          1
-                    search_region   1
-					shipping        1
-					handling        1
-                    tag             1
-                    log             1
-					time			1
-					timed_build     1
-                    try             1
-					update          1
-					userdb          1
-					value           1
-					value_extended  1
+					restrict		1
 				)
 			);
 
 my %hasEndTag = (
 
 				qw(
-                        calc            1
-						catch           1
-                        currency        1
-                        discount        1
-                        filter	        1
-                        fly_list        1
-						either          1
-						harness         1
-                        html_table      1
-                        if              1
-                        import          1
-                        input_filter    1
-                        item_list       1
-                        loop            1
-                        mvasp           1
-                        perl            1
-                        query           1
-                        row             1
-                        region          1
-                        search_region   1
-                        set             1
-                        set             1
-                        seti            1
-                        sql             1
-                        strip           1
-                        tag             1
-                        log             1
-                        try             1
-                        tmp             1
-                        time			1
-                        timed_build     1
-
+					if              1
+					unless          1
+					restrict		1
 				)
 			);
 
@@ -308,52 +87,26 @@
 my %InvalidateCache = (
 
 			qw(
-				cgi			1
-				cart		1
-				checked		1
-				counter		1
-				default		1
-				discount	1
-				export  	1
-				flag        1
-				item_list	1
-				import		1
-				index		1
-				input_filter		1
-				if          1
-				mvasp		1
-				nitems		1
-				perl		1
-				'salestax'	1
-				scratch		1
-				scratchd	1
-				selected	1
-				read_cookie 1
-				set_cookie  1
-				set			1
-				tmp			1
-				seti		1
-				'shipping'	1
-				'handling'	1
-				sql			1
-				subtotal	1
-				total_cost	1
-				userdb		1
-				update	    1
-				value		1
-				value_extended 1
-
+                if          1
+                unless      1
 			   )
 			);
 
 my %Implicit = (
 
-			'data' =>		{ qw( increment increment ) },
-			'checked' =>	{ qw( multiple	multiple default	default ) },
-			'page'    =>	{ qw( secure	secure ) },
-			'area'    =>	{ qw( secure	secure ) },
-
-			'if' =>		{ qw(
+			unless =>		{ qw(
+								!=		op
+								!~		op
+								<=		op
+								==		op
+								=~		op
+								>=		op
+								eq		op
+								gt		op
+								lt		op
+								ne		op
+					   )},
+			if =>		{ qw(
 								!=		op
 								!~		op
 								<=		op
@@ -366,7 +119,7 @@
 								ne		op
 					   )},
 
-			'and' =>		{ qw(
+			and =>		{ qw(
 								!=		op
 								!~		op
 								<=		op
@@ -379,7 +132,7 @@
 								ne		op
 					   )},
 
-			'or' =>		{ qw(
+			or =>		{ qw(
 								!=		op
 								!~		op
 								<=		op
@@ -395,185 +148,85 @@
 			);
 
 my %PosRoutine = (
-				'or'			=> sub { return &Vend::Interpolate::tag_if(@_, 1) },
-				'and'			=> sub { return &Vend::Interpolate::tag_if(@_, 1) },
-				'if'			=> \&Vend::Interpolate::tag_if,
+				or			=> sub { return &Vend::Interpolate::tag_if(@_, 1) },
+				and			=> sub { return &Vend::Interpolate::tag_if(@_, 1) },
+				if			=> \&Vend::Interpolate::tag_if,
+				unless		=> \&Vend::Interpolate::tag_unless,
 			);
 
+my %Special = qw/
+				goto	1
+				bounce	1
+				output 	1
+			  /;
 my %Routine = (
 
-				accessories		=> \&Vend::Interpolate::tag_accessories,
-				area			=> \&Vend::Interpolate::tag_area,
-				banner			=> \&Vend::Interpolate::tag_banner,
+				output          => sub { return '' },
 				bounce          => sub { return '' },
-				calc			=> \&Vend::Interpolate::tag_calc,
-				cart			=> \&Vend::Interpolate::tag_cart,
-				catch			=> \&Vend::Interpolate::catch,
-				cgi				=> \&Vend::Interpolate::tag_cgi,
-				checked			=> \&Vend::Interpolate::tag_checked,
-				counter			=> \&Vend::Interpolate::tag_counter,
-				'currency'		=> sub {
-										my($convert,$noformat,$amount) = @_;
-										return &Vend::Util::currency(
-														$amount,
-														$noformat,
-														$convert);
-									},
-				data			=> \&Vend::Interpolate::tag_data,
-				default			=> \&Vend::Interpolate::tag_default,
-				dump			=> \&::full_dump,
-				description		=> \&Vend::Data::product_description,
-				discount		=> \&Vend::Interpolate::tag_discount,
-				ecml			=> sub {
-											require Vend::ECML;
-											return Vend::ECML::ecml(@_);
-										},
-				either			=> sub {
-											my @ary = split /\[or\]/, shift;
-											my $result;
-											while(@ary) {
-												$result = interpolate_html(shift @ary);
-												$result =~ s/^\s+//;
-												$result =~ s/\s+$//;
-												return $result if $result;
-											}
-											return;
-										},
-				error			=> \&Vend::Interpolate::tag_error,
-				export			=> \&Vend::Interpolate::export,
-				field			=> \&Vend::Data::product_field,
-				file			=> \&Vend::Interpolate::tag_file,
-				filter			=> \&Vend::Interpolate::filter_value,
-				flag			=> \&Vend::Interpolate::flag,
-				fly_tax			=> \&Vend::Interpolate::fly_tax,
-				fly_list		=> \&Vend::Interpolate::fly_page,
-				harness			=> \&harness,
-				html_table		=> \&Vend::Interpolate::html_table,
-				'index'			=> \&Vend::Data::index_database,
-				import 			=> \&Vend::Data::import_text,
-				include			=> sub {
-									&Vend::Interpolate::interpolate_html(
-										&Vend::Util::readfile
-											($_[0], $Global::NoAbsolute, $_[1])
-										  );
-									},
-				input_filter	=> \&Vend::Interpolate::input_filter,
-				item_list		=> \&Vend::Interpolate::tag_item_list,
-				'if'			=> \&Vend::Interpolate::tag_self_contained_if,
-				'or'			=> sub { return &Vend::Interpolate::tag_self_contained_if(@_, 1) },
-				'and'			=> sub { return &Vend::Interpolate::tag_self_contained_if(@_, 1) },
-				'goto'			=> sub { return '' },
+				if				=> \&Vend::Interpolate::tag_self_contained_if,
+				unless			=> \&Vend::Interpolate::tag_unless,
+				or				=> sub { return &Vend::Interpolate::tag_self_contained_if(@_, 1) },
+				and				=> sub { return &Vend::Interpolate::tag_self_contained_if(@_, 1) },
+				goto			=> sub { return '' },
 				label			=> sub { return '' },
-				log				=> \&Vend::Interpolate::log,
-				loop			=> \&Vend::Interpolate::tag_loop_list,
-				nitems			=> \&Vend::Util::tag_nitems,
-				onfly			=> \&Vend::Order::onfly,
-				order			=> \&Vend::Interpolate::tag_order,
-				page			=> \&Vend::Interpolate::tag_page,
-				perl			=> \&Vend::Interpolate::tag_perl,
-# MVASP
-				mvasp			=> \&Vend::Interpolate::mvasp,
-# END MVASP
-				price        	=> \&Vend::Interpolate::tag_price,
-				process      	=> \&Vend::Interpolate::tag_process,
-				query			=> \&Vend::Interpolate::query,
-				read_cookie     => \&Vend::Util::read_cookie,
-				row				=> \&Vend::Interpolate::tag_row,
-				'salestax'		=> \&Vend::Interpolate::tag_salestax,
-				scratch			=> \&Vend::Interpolate::tag_scratch,
-				scratchd		=> \&Vend::Interpolate::tag_scratchd,
-				record			=> \&Vend::Interpolate::tag_record,
-				region			=> \&Vend::Interpolate::region,
-				search_region	=> \&Vend::Interpolate::tag_search_region,
-				selected		=> \&Vend::Interpolate::tag_selected,
-				setlocale		=> \&Vend::Util::setlocale,
-				set_cookie		=> \&Vend::Util::set_cookie,
-				set				=> \&Vend::Interpolate::set_scratch,
-				seti			=> \&Vend::Interpolate::set_scratch,
-				'shipping'		=> \&Vend::Interpolate::tag_shipping,
-				'handling'		=> \&Vend::Interpolate::tag_handling,
-				shipping_desc	=> \&Vend::Interpolate::tag_shipping_desc,
-				sql				=> \&Vend::Data::sql_query,
-				'subtotal'		=> \&Vend::Interpolate::tag_subtotal,
-				strip			=> sub {
-										local($_) = shift;
-										s/^\s+//;
-										s/\s+$//;
-										return $_;
-									},
-				tag				=> \&Vend::Interpolate::do_tag,
-				tmp				=> \&Vend::Interpolate::set_tmp,
-				try				=> \&Vend::Interpolate::try,
-				'time'			=> \&Vend::Interpolate::mvtime,
-				timed_build		=> \&Vend::Interpolate::timed_build,
-				total_cost		=> \&Vend::Interpolate::tag_total_cost,
-				userdb			=> \&Vend::UserDB::userdb,
-				update			=> \&Vend::Interpolate::update,
-				value			=> \&Vend::Interpolate::tag_value,
-				value_extended	=> \&Vend::Interpolate::tag_value_extended,
 
 			);
 
+## Put here because we need to call keys %Routine
+## Restricts execution of tags by tagname
+$Routine{restrict} = sub {
+	my ($enable, $opt, $body) = @_;
+	my $save = $Vend::Cfg->{AdminSub};
+
+	my $save_restrict = $Vend::restricted;
+
+	$opt->{log} ||= 'all';
+
+	my $default;
+	if("\L$opt->{policy}" eq 'allow') {
+		# Accept all, deny only ones defined in disable
+		$default = undef;
+		$opt->{policy} = 'allow';
+	}
+	else {
+		# This is default, deny all except enabled
+		$default = 1;
+		$opt->{policy} = 'deny';
+	}
+	my @enable  = split /[\s,\0]+/, $enable;
+	my @disable = split /[\s,\0]+/, $opt->{disable};
+
+	for(@enable, @disable) {
+		$_ = lc $_;
+		tr/-/_/;
+	}
+
+	my %restrict;
+	for(keys %Routine) {
+		$restrict{$_} = $default;
+	}
+
+	$restrict{$_} = undef for @enable;
+	$restrict{$_} = 1     for @disable;
+	$restrict{$_} = 1     for keys %$save;
+
+	$Vend::Cfg->{AdminSub} = \%restrict;
+	$Vend::restricted = join " ",
+			'default=' . $opt->{policy},
+			'enable=' . join(",", @enable),
+			'disable=' . join(",", @disable),
+			'log=' . $opt->{log},
+			;
+	my $out;
+	eval {
+		$out = Vend::Interpolate::interpolate_html($body);
+	};
+	$Vend::restricted = $save_restrict;
+	$Vend::Cfg->{AdminSub} = $save;
+	return $out;
+};
+
 my %attrAlias = (
-	 counter        => { 'name' => 'file' },
-	 query          => { 'query' => 'sql' },
-	 perl          	=> { 'table' => 'tables' },
-	 mvasp         	=> { 'table' => 'tables' },
-	 price         	=> { 'base' => 'mv_ib' },
-	 page          	=> {
-	 						'base' => 'arg',
-						},
-	 record          	=> { 
-	 						'column' => 'col',
-	 						'code' => 'key',
-	 						'field' => 'col',
-						},
-	 flag          	=> { 
-	 						'flag' => 'type',
-	 						'name' => 'type',
-						},
-	 field          	=> { 
-	 						'field' => 'name',
-	 						'column' => 'name',
-	 						'col' => 'name',
-	 						'key' => 'code',
-	 						'row' => 'code',
-						},
-	 'index'          	=> { 
-	 						'database' => 'table',
-	 						'base' => 'table',
-						},
-	 import          	=> { 
-	 						'database' => 'table',
-	 						'base' => 'table',
-						},
-	 input_filter          	=> { 
-	 						'ops' => 'op',
-	 						'var' => 'name',
-	 						'variable' => 'name',
-						},
-	 accessories    => { 
-	 						'database' => 'table',
-	 						'db' => 'table',
-	 						'base' => 'table',
-	 						'field' => 'column',
-	 						'col' => 'column',
-	 						'key' => 'code',
-	 						'row' => 'code',
-						},
-	 export          	=> { 
-	 						'database' => 'table',
-	 						'base' => 'table',
-						},
-	 data          	=> { 
-	 						'database' => 'table',
-	 						'base' => 'table',
-	 						'name' => 'field',
-	 						'column' => 'field',
-	 						'col' => 'field',
-	 						'code' => 'key',
-	 						'row' => 'key',
-						},
 	 'or'			=> { 
 	 						'comp' => 'compare',
 	 						'operator' => 'op',
@@ -584,42 +237,18 @@
 	 						'operator' => 'op',
 	 						'base' => 'type',
 						},
-	 'userdb'		=> {
-	 						'table' => 'db',
-	 						'name' => 'nickname',
+	 'unless'			=> { 
+	 						'comp' => 'compare',
+	 						'condition' => 'compare',
+	 						'operator' => 'op',
+	 						'base' => 'type',
 						},
-	 'shipping'			=> {
-	 							'name' => 'mode',
-	 							'tables' => 'table',
-	 							'modes' => 'mode',
-	 							'carts' => 'cart',
-							},
-	 'handling'			=> {	
-	 							'name' => 'mode',
-	 							'tables' => 'table',
-	 							'modes' => 'mode',
-	 							'carts' => 'cart',
-							},
-	 'salestax'			=> { 'cart' => 'name', },
-	 'subtotal'			=> { 'cart' => 'name', },
-	 'total_cost'		=> { 'cart' => 'name', },
 	 'if'			=> { 
 	 						'comp' => 'compare',
 	 						'condition' => 'compare',
 	 						'operator' => 'op',
 	 						'base' => 'type',
 						},
-	 search_region		=> { search => 'arg',
-	 						 params => 'arg',
-	 						 args => 'arg', },
-	 region			   	=> { search => 'arg',
-	 						 params => 'arg',
-	 						 args => 'arg', },
-	 loop	          	=> { args => 'list',
-	 						 arg => 'list', },
-	 item_list	       	=> { cart => 'name', },
-	 tag		       	=> { description => 'arg', },
-	 log		       	=> { arg => 'file', },
 );
 
 my %Alias = (
@@ -628,90 +257,24 @@
 						url				urldecode
 						urld			urldecode
 						href			area
+						warning			warnings
 						shipping_description	shipping_desc
-						a				page
 						process_target	process
+						process_order	process
 				),
+					getlocale		=> 'setlocale get=1',
 					process_search		=> 'area href=search',
-					process_order		=> 'process order=1',
 					buzzard		=> 'data table=products column=artist key=',
 			);
 
-my %replaceHTML = (
-				qw(
-					del .*
-					pre .*
-					xmp .*
-					script .*
-				)
-			);
-
-my %replaceAttr = (
-					area			=> { qw/ a 	href form action/},
-					process			=> { qw/ form action		/},
-					checked			=> { qw/ input checked		/},
-					selected		=> { qw/ option selected	/},
-			);
-
-my %insertHTML = (
-				qw(
-
-				form	process|area
-				a 		area
-				input	checked
-				option  selected
-				)
-			);
-
-my %lookaheadHTML = (
-				qw(
-
-				if 		then|elsif|else
-				)
-			);
-
-my %rowfixHTML = (	qw/
-						td	item_list|loop|sql_list
-					/	 );
-# Only for containers
-my %insideHTML = (
-				qw(
-					select	loop|item_list|tag
-				)
-
-				);
-
-# Only for containers
-my %endHTML = (
-				qw(
-
-				tr 		.*
-				td 		.*
-				th 		.*
-				del 	.*
-				script 	.*
-				table 	if
-				object 	perl
-				param 	perl
-				font 	if
-				a 		if
-				)
-			);
-
 my %Interpolate = (
 
 				qw(
-						calc		1
-						currency	1
-						import		1
-						row			1
-						seti		1
-						tmp			1
 				)
 			);
 
 my %NoReparse = ( qw/
-					mvasp			1
+					restrict		1
 				/ );
 
 my %Gobble = ( qw/
@@ -719,41 +282,7 @@
 					mvasp			1
 				/ );
 
-my $Tags_added = 0;
-
-my $Initialized = 0;
-
-my $Test = 'test001';
-sub harness {
-	my ($opt, $input) = @_;
-	my $not;
-	my $expected =  $opt->{expected} || 'OK';
-	$input =~ s:^\s+::;
-	$input =~ s:\s+$::;
-	$input =~ s:\s*\[expected\](.*)\[/expected\]\s*::s
-		and $expected = $1;
-	$input =~ s:\[not\](.*)\[/not\]::s
-		and $not = $1;
-	my $name = $Test++;
-	$name = $opt->{name}
-		if defined $opt->{name};
-	my $result;
-	eval {
-		$result = Vend::Interpolate::interpolate_html($input);
-	};
-	if($@) {
-		my $msg = "DIED in test $name. \$\@: $@";
-#::logDebug($msg);
-		return $msg;
-	}
-	if($expected) {
-		return "NOT OK $name: $result!=$expected" unless $result =~ /$expected/;
-	}
-	if($not) {
-		return "NOT OK $name: $result==$not" unless $result !~ /$not/;
-	}
-	return "OK $name";
-}
+my $Initialized;
 
 sub global_init {
 		add_tags($Global::UserTag);
@@ -768,19 +297,92 @@
 
 sub new {
     my $class = shift;
+	my $opt = shift;
     my $self = new Vend::Parser;
 	$self->{INVALID} = 0;
 
 	add_tags($Vend::Cfg->{UserTag})
-		unless $Tags_added++;
-
-	$self->{TOPLEVEL} = 1 if ! $Initialized;
+		unless $Vend::Tags_added++;
 
-	$self->{OUT} = '';
     bless $self, $class;
-	$Initialized = $self;
+
+	if($opt) {
+		$self->destination('');
+	}
+	else {
+		my $string = '';
+		$self->{OUT} = $self->{DEFAULT_OUT} = \$string;
+	}
+#::logDebug("OUT=$self->{OUT}");
+
+	if (! $Initialized) {
+		$Initialized = $self;
+		$self->{TOPLEVEL} = 1;
+	}
+
+	return $self;
 }
 
+sub destination {
+	my ($s, $name, $attr) = @_;
+	$s->{_outname} ||= [];
+
+	if(! defined $name) {
+		pop @{$s->{_outname}};
+		$name = pop  @{$s->{_outname}};
+	}
+	else {
+		$name = lc $name;
+		push @{$s->{_outname}}, $name;
+	}
+
+#::logDebug("destination set to '$name'");
+	$name ||= '';
+
+	my $string = '';
+	$s->{OUT} = \$string;
+	push @Vend::Output, $s->{OUT};
+
+	my $nary = $Vend::OutPtr{$name} ||= [];
+	push @$nary, $#Vend::Output;
+
+	return unless $attr;
+#::logDebug("destination extended output settings");
+
+	my $fary = $Vend::OutFilter{$name};
+
+	if ($name) {
+		$Vend::MultiOutput = 1;
+		if(! $Vend::OutFilter{''}) {
+			my $ary = [];
+			push @$ary, \&Vend::Interpolate::substitute_image
+				unless $::Pragma->{no_image_rewrite};
+			$Vend::OutFilter{''} = $ary;
+		}
+
+		if(! $fary) {
+			$fary = $Vend::OutFilter{$name} = [];
+			if($attr->{output_filter}) {
+				my $filt = $attr->{output_filter};
+				push @$fary, sub {
+					my $ref = shift;
+					$$ref = Vend::Interpolate::filter_value($filt, $$ref);
+					return;
+				};
+			}
+			if (! $attr->{no_image_parse} and ! $::Pragma->{no_image_rewrite}) {
+				push @$fary, \&Vend::Interpolate::substitute_image;
+			}
+			if ($attr->{output_extended}) {
+				$Vend::OutExtended{$name} = $attr;
+			}
+		}
+	}
+	return $s->{OUT};
+}
+
+my %noRearrange = qw//;
+
 my %Documentation;
 use vars '%myRefs';
 
@@ -789,27 +391,41 @@
      addAttr         => \%addAttr,
      attrAlias       => \%attrAlias,
 	 Documentation   => \%Documentation,
-	 endHTML         => \%endHTML,
 	 hasEndTag       => \%hasEndTag,
+	 NoReparse       => \%NoReparse,
+	 noRearrange     => \%noRearrange,
 	 Implicit        => \%Implicit,
-	 insertHTML	     => \%insertHTML,
-	 insideHTML	     => \%insideHTML,
 	 Interpolate     => \%Interpolate,
 	 InvalidateCache => \%InvalidateCache,
-	 lookaheadHTML   => \%lookaheadHTML,
 	 Order           => \%Order,
 	 PosNumber       => \%PosNumber,
 	 PosRoutine      => \%PosRoutine,
-	 replaceAttr     => \%replaceAttr,
-	 replaceHTML     => \%replaceHTML,
 	 Routine         => \%Routine,
 );
 
+my @myRefs = keys %myRefs;
+
 sub do_tag {
 	my $tag = shift;
-#::logDebug("Parse-do_tag: tag=$tag caller=" . caller());
+#::logDebug("Parse-do_tag: tag=$tag caller=" . caller() . " args=" . ::uneval_it(\@_) );
+	if (defined $Vend::Cfg->{AdminSub}{$tag}) { 
+
+		if($Vend::restricted) {
+			die errmsg(
+					"Tag '%s' in execution-restricted area: %s",
+					$tag,
+					$Vend::restricted,
+				);
+		}
+		elsif (! $Vend::admin) {
+			die errmsg("Unauthorized for admin tag %s", $tag)
+		}
+
+	}
+
 	die errmsg("Unauthorized for admin tag %s", $tag)
-		if defined $Vend::Cfg->{AdminSub}{$tag} and ! $Vend::admin;
+		if defined $Vend::Cfg->{AdminSub}{$tag} and
+			($Vend::restricted or ! $Vend::admin);
 	
 	if (! defined $Routine{$tag}) {
         if (! $Alias{$tag}) {
@@ -818,12 +434,24 @@
         }
         $tag = $Alias{$tag};
 	};
-	if(ref($_[-1]) =~ /HASH/ && scalar @{$Order{$tag}} > scalar @_) {
+	if($Special{$tag}) {
+		my $ref = pop(@_);
+		my @args = @$ref{ @{$Order{$tag}} };
+		push @args, $ref if $addAttr{$tag};
+#::logDebug("Parse-do_tag: args now=" . ::uneval_it(\@args) );
+		$Initialized->start($tag, $ref);
+		return;
+	}
+	elsif(
+		( ref($_[-1]) && scalar @{$Order{$tag}} > scalar @_ and ! $noRearrange{$tag}) 
+	)
+	{
 		my $text;
 		my $ref = pop(@_);
 		$text = shift if $hasEndTag{$tag};
 		my @args = @$ref{ @{$Order{$tag}} };
 		push @args, $ref if $addAttr{$tag};
+#::logDebug("Parse-do_tag: args now=" . ::uneval_it(\@args) );
 		return &{$Routine{$tag}}(@args, $text || undef);
 	}
 	else {
@@ -833,12 +461,14 @@
 
 sub resolve_args {
 	my $tag = shift;
+#::logDebug("resolving args for $tag, attrAlias = $attrAlias{$tag}");
 	return @_ unless defined $Routine{$tag};
 	my $ref = shift;
 	my @list;
 	if(defined $attrAlias{$tag}) {
 		my ($k, $v);
 		while (($k, $v) = each %{$attrAlias{$tag}} ) {
+#::logDebug("checking alias $k -> $v");
 			next unless defined $ref->{$k};
 			$ref->{$v} = $ref->{$k};
 		}
@@ -852,9 +482,10 @@
 sub add_tags {
 	return unless @_;
 	my $ref = shift;
+	return unless $ref->{Routine} or $ref->{Alias};
 	my $area;
 	no strict 'refs';
-	foreach $area (keys %myRefs) {
+	foreach $area (@myRefs) {
 		next unless $ref->{$area};
 		if($area eq 'Routine') {
 			for (keys %{$ref->{$area}}) {
@@ -887,7 +518,7 @@
 
 sub text {
     my($self, $text) = @_;
-	$self->{OUT} .= $text;
+	${$self->{OUT}} .= $text;
 }
 
 my %Monitor = ( qw( tag_ary 1 ) );
@@ -936,348 +567,59 @@
 		$$buf = '';
 		return;
 	}
-	while($$buf =~ s!  .+?
-							(
-								(?:
-								\[ label \s+ (?:name \s* = \s* ["']?)?	|
-								<[^>]+? \s+ mv.label \s*=\s*["']?		|
-								<[^>]+? \s+
-									mv \s*=\s*["']? label
-									[^>]*? \s+ mv.name\s*=\s*["']?		|
-								<[^>]+? \s+ mv \s*=\s*["']? label  \s+  |
-								)
-								(\w+)
-							|
-								</body\s*>
-							)
-					!$1!ixs )
-	{
-			last if $name eq $2;
-	}
+	$$buf =~ s!.*?\[label\s+(?:name\s*=\s*(?:["'])?)?($name)['"]*\s*\]!!is
+		and return;
+	$$buf =~ s:.*?</body\s*>::is
+		and return;
+	$$buf = '';
 	return;
 	# syntax color "'
 }
 
-sub html_start {
-    my($self, $tag, $attr, $attrseq, $origtext, $end_tag) = @_;
-#::logDebug("HTML tag=$tag Interp='$Interpolate{$tag}' origtext=$origtext attributes:\n" . ::uneval($attr));
-	$tag =~ tr/-/_/;   # canonical
+sub eval_die {
+	my $msg = shift;
+	$msg =~ s/\(eval\s+\d+/(tag '$Vend::CurrentTag'/;
+	die($msg, @_);
+}
 
-	if (defined $Vend::Cfg->{AdminSub}{$tag} and ! $Vend::admin) {
-		$Vend::StatusLine = "Status: 403\nContent-Type: text/html";
-		::response( errmsg("Unauthorized for admin tag %s", $tag) );
-		return ($self->{ABORT} = 1);
-	}
+# syntax color '"
 
-	$end_tag = lc $end_tag;
+sub start {
+    my($self, $tag, $attr, $attrseq, $origtext, $empty_container) = @_;
+	$tag =~ tr/-/_/;   # canonical
+	$Vend::CurrentTag = $tag = lc $tag;
+#::logDebug("start tag=$tag");
 	my $buf = \$self->{_buf};
-#::logDebug("tag=$tag end_tag=$end_tag buf length " . length($$buf)) if $Monitor{$tag};
-#::logDebug("attributes: ", %{$attr}) if $Monitor{$tag};
-	my($tmpbuf);
-    # $attr is reference to a HASH, $attrseq is reference to an ARRAY
-	my($return_html);
-
-	unless (defined $Routine{$tag}) {
-		if(defined $Alias{$tag}) {
-#::logDebug("origtext: $origtext");
-			my $alias = $Alias{$tag};
-			$tag =~ s/_/[-_]/g;
-			$origtext =~ s/$tag/$alias/i
-				or return 0;
-			$$buf = $origtext . $$buf;
-			return 1;
-		}
-		elsif ($tag eq 'urldecode') {
-			$attr->{urldecode} = 1;
-			$return_html = $origtext;
-			$return_html =~ s/\s+.*//s;
-		}
-		else {
-			$self->{OUT} .= $origtext;
-			return 1;
-		}
-	}
-
-	if(defined $InvalidateCache{$tag} and !$attr->{cache}) {
-		$self->{INVALID} = 1;
-	}
 
-	my $trib;
-	foreach $trib (@$attrseq) {
-		# Attribute aliases
-		if(defined $attrAlias{$tag} and $attrAlias{$tag}{$trib}) {
-			my $new = $attrAlias{$tag}{$trib} ;
-			$attr->{$new} = delete $attr->{$trib};
-			$trib = $new;
-		}
-		elsif (0 and defined $Alias{$trib}) {
-			my $new = $Alias{$trib} ;
-			$attr->{$new} = delete $attr->{$trib};
-			$trib = $new;
-		}
-		# Parse tags within tags, only works if the [ is the
-		# first character.
-		$attr->{$trib} =~ s/%([A-Fa-f0-9]{2})/chr(hex($1))/eg if $attr->{urldecode};
-		next unless $attr->{$trib} =~ /\[\w+[-\w]*\s*[\000-\377]*\]/;
-
-		my $p = new Vend::Parse;
-		$p->parse($attr->{$trib});
-		$attr->{$trib} = $p->{OUT};
-		$self->{INVALID} += $p->{INVALID};
-	}
-
-	if($tag eq 'urldecode') {
-		$self->{OUT} .= build_html_tag($return_html, $attr, $attrseq);
-		return 1;
-	}
-
-	$attr->{'decode'} = 1 unless defined $attr->{'decode'};
-	$attr->{'reparse'} = 1 unless	defined $NoReparse{$tag}
-								||	defined $attr->{'reparse'};
-	$attr->{'true'} = 1;
-	$attr->{'false'} = 0;
-	$attr->{'undef'} = undef;
-
-	my ($routine,@args);
-
-	if ($attr->{OLD}) {
-	# HTML old-style tag
-		$attr->{interpolate} = 1 if defined $Interpolate{$tag};
-		if(defined $PosNumber{$tag}) {
-			if($PosNumber{$tag} > 1) {
-				@args = split /\s+/, $attr->{OLD}, $PosNumber{$tag};
-				push(@args, undef) while @args < $PosNumber{$tag};
-			}
-			elsif ($PosNumber{$tag}) {
-				@args = $attr->{OLD};
-			}
-		}
-		@{$attr}{ @{ $Order{$tag} } } = @args;
-		$routine =  $PosRoutine{$tag} || $Routine{$tag};
-	}
-	else {
-	# New style tag, HTML or otherwise
-		$routine = $Routine{$tag};
-		$attr->{interpolate} = 1
-			if defined $Interpolate{$tag} and ! defined $attr->{interpolate};
-		@args = @{$attr}{ @{ $Order{$tag} } };
-	}
-	$args[scalar @{$Order{$tag}}] = $attr if $addAttr{$tag};
+	my($tmpbuf);
+	if (defined $Vend::Cfg->{AdminSub}{$tag}) { 
 
-	if($tag =~ /^[gb]o/) {
-		if($tag eq 'goto') {
-			return 1 if resolve_if_unless($attr);
-			if(! $args[0]) {
-				$$buf = '';
-				$Initialized->{_buf} = '';
-				$self->{ABORT} = 1
-					if $attr->{abort};
-				return ($self->{SEND} = 1);
+		if($Vend::restricted) {
+			my $log = 'all';
+			$Vend::restricted =~ /\blog=(\w+)/ and $log = lc $1;
+			undef $log if $log eq 'none' or
+				($log eq 'once' and $Vend::restricted_err{$origtext}++);
+			if ($log) {
+				::logError(
+					"Restricted tag (%s) attempted during restriction '%s'",
+					$origtext,
+					$Vend::restricted,
+				);
 			}
-			goto_buf($args[0], \$Initialized->{_buf});
-			$self->{ABORT} = 1;
+			${$self->{OUT}} .= $origtext;
 			return 1;
 		}
-		elsif($tag eq 'bounce') {
-			return 1 if resolve_if_unless($attr);
-			if(! $attr->{href} and $attr->{page}) {
-				$attr->{href} = Vend::Interpolate::tag_area($attr->{page});
-			}
-			$Vend::StatusLine = '' if ! $Vend::StatusLine;
-			$Vend::StatusLine .= <<EOF;
-Status: 302 moved
-Location: $attr->{href}
-EOF
-			$$buf = '';
-			$Initialized->{_buf} = '';
-			return ($self->{SEND} = 1);
-		}
-	}
-
-#::logDebug("tag=$tag end_tag=$end_tag attributes:\n" . Vend::Util::uneval($attr)) if$Monitor{$tag};
-
-	my $prefix = '';
-	my $midfix = '';
-	my $postfix = '';
-	my @out;
-
-	if($insertHTML{$end_tag}
-		and ! $attr->{noinsert}
-		and $tag =~ /^($insertHTML{$end_tag})$/) {
-		$origtext =~ s/>\s*$//;
-		@out = Text::ParseWords::shellwords($origtext);
-		shift @out;
-		@out = grep $_ !~ /^[Mm][Vv][=.]/, @out
-			unless $attr->{showmv};
-		if (defined $replaceAttr{$tag}
-			and $replaceAttr{$tag}->{$end_tag}
-			and	! $attr->{noreplace})
-		{
-			my $t = $replaceAttr{$tag}->{$end_tag};
-			@out = grep $_ !~ /^($t)\b/i, @out;
-			unless(defined $implicitHTML{$t}) {
-				$out[0] .= qq{ \U$t="};
-				$out[1] = defined $out[1] ? qq{" } . $out[1] : '"';
-			}
-			else { $midfix = ' ' }
-		}
-		else {
-			$out[0] = " " . $out[0] . " "
-				if $out[0];
-		}
-		if (@out) {
-			$out[$#out] .= '>';
-		}
-		else {
-			@out = '>';
-		}
-#::logDebug("inserted " . join "|", @out);
-	}
-
-	if($hasEndTag{$tag}) {
-		my $rowfix;
-		# Handle embedded tags, but only if interpolate is 
-		# defined (always if using old tags)
-		if (defined $replaceHTML{$end_tag}
-			and $tag =~ /^($replaceHTML{$end_tag})$/
-			and ! $attr->{noreplace} )
-		{
-			$origtext = '';
-			$tmpbuf = find_html_end($end_tag, $buf);
-			$tmpbuf =~ s:</$end_tag\s*>::;
-			HTML::Entities::decode($tmpbuf) if $attr->{decode};
-			$tmpbuf =~ tr/\240/ /;
-		}
-		else {
-			@out = Text::ParseWords::shellwords($origtext);
-			($attr->{showmv} and
-					@out = map {s/^[Mm][Vv]\./mv-/} @out)
-				or @out = grep ! /^[Mm][Vv][=.]/, @out;
-			$out[$#out] =~ s/([^>\s])\s*$/$1>/;
-			$origtext = join " ", @out;
-
-			if (defined $lookaheadHTML{$tag} and ! $attr->{nolook}) {
-				$tmpbuf = $origtext . find_html_end($end_tag, $buf);
-				while($$buf =~ s~^\s*(<([A-Za-z][-A-Z.a-z0-9]*)[^>]*)\s+
-								[Mm][Vv]\s*=\s*
-								(['"]) \[?
-									($lookaheadHTML{$tag})\b(.*?)
-								\]?\3~~ix ) 
-				{
-					my $orig = $1;
-					my $enclose = $4;
-					my $adder = $5;
-					my $end = lc $2;
-					$tmpbuf .= "[$enclose$adder]"	.  $orig	.
-								find_html_end($end, $buf)	.
-								"[/$enclose]";
-				}
-			}
-			# Syntax color '" 
-			# GACK!!! No table row attributes in some editors????
-			elsif (defined $rowfixHTML{$end_tag}
-				and $tag =~ /^($rowfixHTML{$end_tag})$/
-				and $attr->{rowfix} )
-			{
-				$rowfix = 1;
-				$tmpbuf = '<tr>' . $origtext . find_html_end('tr', $buf);
-#::logDebug("Tmpbuf: $tmpbuf");
-			}
-			elsif (defined $insideHTML{$end_tag}
-					and ! $attr->{noinside}
-					and $tag =~ /^($insideHTML{$end_tag})$/i) {
-				$prefix = $origtext;
-				$tmpbuf = find_html_end($end_tag, $buf);
-				$tmpbuf =~ s:</$end_tag\s*>::;
-				$postfix = "</$end_tag>";
-				HTML::Entities::decode($tmpbuf) if $attr->{'decode'};
-				$tmpbuf =~ tr/\240/ / if $attr->{'decode'};
-			}
-			else {
-				$tmpbuf = $origtext . find_html_end($end_tag, $buf);
-			}
-		}
-
-		$tmpbuf =~ s/%([A-Fa-f0-9]{2})/chr(hex($1))/eg if $attr->{urldecode};
-
-		if ($attr->{interpolate}) {
-			my $p = new Vend::Parse;
-			$p->parse($tmpbuf);
-			$tmpbuf =  $p->{OUT};
-		}
-
-		$tmpbuf =  $attr->{prepend} . $tmpbuf if defined $attr->{prepend};
-		$tmpbuf .= $attr->{append}            if defined $attr->{append};
-
-		if (! $attr->{reparse}) {
-			$self->{OUT} .= $prefix . &{$routine}(@args,$tmpbuf) . $postfix;
-		}
-		elsif (! defined $rowfix) {
-			$$buf = $prefix . &{$routine}(@args,$tmpbuf) . $postfix . $$buf
-		}
-		else {
-			$tmpbuf = &{$routine}(@args,$tmpbuf);
-			$tmpbuf =~ s|<tr>||i;
-			$$buf = $prefix . $tmpbuf . $postfix . $$buf;
+		elsif (! $Vend::admin) {
+			::response(
+						get_locale_message (
+							403,
+							"Unauthorized for admin tag %s",
+							$tag,
+							)
+						);
+			return ($self->{ABORT} = 1);
 		}
 
-
-	}
-	else {
-		if(! @out and $attr->{prepend} or $attr->{append}) {
-			my @tmp;
-			@tmp = Text::ParseWords::shellwords($origtext);
-			shift @tmp;
-			@tmp = grep $_ !~ /^[Mm][Vv][=.]/, @tmp
-				unless $attr->{showmv};
-			$postfix = $attr->{prepend} ? "<\U$end_tag " . join(" ", @tmp) : '';
-			$prefix = $attr->{append} ? "<\U$end_tag " . join(" ", @tmp) : '';
-		}
-		if(! $attr->{interpolate}) {
-			if(@out) {
-				$self->{OUT} .= "<\U$end_tag ";
-				if 		($out[0] =~ / > \s*$ /x ) { }   # End of tag, do nothing
-				elsif	($out[0] =~ / ^[^"]*"$/x ) {     # End of tag
-					$self->{OUT} .= shift(@out);
-				}
-				else {
-					unshift(@out, '');
-				}
-			}
-			$self->{OUT} .= $prefix . &$routine( @args ) . $midfix;
-			$self->{OUT} .= join(" ", @out) . $postfix;
-		}
-		else {
-			if(@out) {
-				$$buf = "<\U$end_tag " . &$routine( @args ) . $midfix . join(" ", @out) . $$buf;
-			}
-			else {
-				$$buf = $prefix . &$routine( @args ) . $postfix . $$buf;
-			}
-		}
-	}
-
-	$self->{SEND} = $attr->{'send'} || undef;
-#::logDebug("Returning from $tag");
-	return 1;
-
-}
-
-# syntax color '"
-
-sub start {
-	return html_start(@_) if $_[0]->{HTML};
-    my($self, $tag, $attr, $attrseq, $origtext) = @_;
-	$tag =~ tr/-/_/;   # canonical
-	$tag = lc $tag;
-	my $buf = \$self->{_buf};
-#::logDebug("tag=$tag buf length " . length($$buf));
-#::logDebug("tag=$tag Interp='$Interpolate{$tag}' origtext=$origtext attributes:\n" . ::uneval($attr));
-	my($tmpbuf);
-	if (defined $Vend::Cfg->{AdminSub}{$tag} and ! $Vend::admin) {
-		$Vend::StatusLine = "Status: 403\nContent-Type: text/html";
-		::response( errmsg("Unauthorized for admin tag %s", $tag) );
-		return ($self->{ABORT} = 1);
 	}
 
     # $attr is reference to a HASH, $attrseq is reference to an ARRAY
@@ -1292,7 +634,8 @@
 			return 1;
 		}
 		else {
-			$self->{OUT} .= $origtext;
+#::logDebug("no alias. origtext: $origtext");
+			${$self->{OUT}} .= $origtext;
 			return 1;
 		}
 	}
@@ -1315,15 +658,13 @@
 
 		my $p = new Vend::Parse;
 		$p->parse($attr->{$trib});
-		$attr->{$trib} = $p->{OUT};
+		$attr->{$trib} = ${$p->{OUT}};
 		$self->{INVALID} += $p->{INVALID};
 	}
 
-	$attr->{'reparse'} = 1
+	$attr->{enable_html} = 1 if $Vend::Cfg->{Promiscuous};
+	$attr->{reparse} = 1
 		unless (defined $NoReparse{$tag} || defined $attr->{'reparse'});
-	$attr->{'true'} = 1;
-	$attr->{'false'} = 0;
-	$attr->{'undef'} = undef;
 
 	my ($routine,@args);
 
@@ -1362,30 +703,25 @@
 #interpolate=$attr->{interpolate}
 #EOF
 
-	if($tag =~ /^[gb]o/) {
-		if($tag eq 'goto') {
-			return 1 if resolve_if_unless($attr);
-			if(! $args[0]) {
-				$$buf = '';
-				$Initialized->{_buf} = '';
-				$self->{ABORT} = 1
-					if $attr->{abort};
-				return ($self->{SEND} = 1);
-			}
-			goto_buf($args[0], \$Initialized->{_buf});
-			$self->{ABORT} = 1;
-			$self->{SEND} = 1 if ! $Initialized->{_buf};
+	if($Special{$tag}) {
+		if($tag eq 'output') {
+			$self->destination($attr->{name}, $attr);
 			return 1;
 		}
 		elsif($tag eq 'bounce') {
+#::logDebug("bouncing...");
 			return 1 if resolve_if_unless($attr);
 			if(! $attr->{href} and $attr->{page}) {
 				$attr->{href} = Vend::Interpolate::tag_area($attr->{page});
 			}
 			$Vend::StatusLine = '' if ! $Vend::StatusLine;
 			$Vend::StatusLine .= "\n" if $Vend::StatusLine !~ /\n$/;
+			$Vend::StatusLine .= <<EOF if $attr->{target};
+Window-Target: $attr->{target}
+EOF
+			$attr->{status} ||= '302 moved';
 			$Vend::StatusLine .= <<EOF;
-Status: 302 moved
+Status: $attr->{status}
 Location: $attr->{href}
 EOF
 			$$buf = '';
@@ -1393,28 +729,47 @@
 			$self->{SEND} = 1;
 			return 1;
 		}
+		elsif($tag eq 'goto') {
+			return 1 if resolve_if_unless($attr);
+			if(! $args[0]) {
+				$$buf = '';
+				$Initialized->{_buf} = '';
+				$self->{ABORT} = 1
+					if $attr->{abort};
+				return ($self->{SEND} = 1);
+			}
+			goto_buf($args[0], $buf);
+			$self->{ABORT} = 1;
+			$self->{SEND} = 1 if ! $$buf;
+			return 1;
+		}
 	}
 
+	local($SIG{__DIE__}) = \&eval_die;
+
+#::logDebug("output attr=$attr->{_output}");
+	$self->destination($attr->{_output}) if $attr->{_output};
+
 	if($hasEndTag{$tag}) {
 		# Handle embedded tags, but only if interpolate is 
 		# defined (always if using old tags)
 #::logDebug("look end for $tag, buf=" . length($$buf) );
-		$tmpbuf = find_matching_end($tag, $buf);
+		$tmpbuf = $empty_container ? '' : find_matching_end($tag, $buf);
 #::logDebug("FOUND end for $tag\nBuf " . length($$buf) . ":\n" . $$buf . "\nTmpbuf:\n$tmpbuf\n");
-		if ($attr->{interpolate}) {
+		if ($attr->{interpolate} and !$empty_container) {
 			my $p = new Vend::Parse;
 			$p->parse($tmpbuf);
-			$tmpbuf = $p->{ABORT} ? '' : $p->{OUT};
+			$tmpbuf = $p->{ABORT} ? '' : ${$p->{OUT}};
 		}
 		if($attr->{reparse} ) {
-			$$buf = ($routine->(@args,$tmpbuf) || '') . $$buf;
+			$$buf = ($routine->(@args,$tmpbuf)) . $$buf;
 		}
 		else {
-			$self->{OUT} .= &{$routine}(@args,$tmpbuf);
+			${$self->{OUT}} .= &{$routine}(@args,$tmpbuf);
 		}
 	}
 	elsif(! $attr->{interpolate}) {
-		$self->{OUT} .= &$routine( @args );
+		${$self->{OUT}} .= &$routine( @args );
 	}
 	else {
 		$$buf = &$routine( @args ) . $$buf;
@@ -1422,6 +777,7 @@
 
 	$self->{SEND} = $attr->{'send'} || undef;
 #::logDebug("Returning from $tag");
+	$self->destination() if $attr->{_output};
 	return 1;
 }
 
@@ -1429,7 +785,7 @@
     my($self, $tag) = @_;
 	my $save = $tag;
 	$tag =~ tr/-/_/;   # canonical
-	$self->{OUT} .= "[/$save]";
+	${$self->{OUT}} .= "[/$save]";
 }
 
 sub find_html_end {
@@ -1509,6 +865,7 @@
 	while ($$buf =~ s|^(([a-zA-Z][-a-zA-Z0-9._]*)\s*)||) {
 		$eaten .= $1;
 		my $attr = lc $2;
+		$attr =~ tr/-/_/;
 		my $val;
 		$old = 0;
 		# The attribute might take an optional value (first we
@@ -1518,10 +875,27 @@
 			$val = $2;
 			HTML::Entities::decode($val);
 		# or quoted by " or ' 
-		} elsif ($$buf =~ s|(^=\s*([\"\'])(.*?)\2\s*)||s) {
+		} elsif ($$buf =~ s~(^=\s*([\"\'\`\|])(.*?)\2\s*)~~s) {
 			$eaten .= $1;
+			my $q = $2;
 			$val = $3;
 			HTML::Entities::decode($val);
+			if ($q eq "`") {
+				$val = Vend::Interpolate::tag_calc($val);
+			}
+			else {
+				$q eq '|'
+			    	and do {
+						$val =~ s/^\s+//;
+						$val =~ s/\s+$//;
+					};
+				$val =~ /__[A-Z]\w*[A-Za-z]__|\[.*\]/s
+					and do {
+						my $p = new Vend::Parse;
+						$p->parse($val);
+						$val = ${$p->{OUT}};
+					};
+			}
 		# truncated just after the '=' or inside the attribute
 		} elsif ($$buf =~ m|^(=\s*)$| or
 				 $$buf =~ m|^(=\s*[\"\'].*)|s) {
@@ -1542,18 +916,18 @@
 	return ($eaten);
 }
 
-# checks for implicit tags
-# INT is special in that it doesn't get pushed on @attrseq
+# Implicit tag attributes
+# These are deprecated. Please do not document them,
+# as they may go away in the future.
 sub implicit {
 	my($self, $tag, $attr) = @_;
+	# 'int' is special in that it doesn't get pushed on @attrseq
 	return ('interpolate', 1, 1) if $attr eq 'int';
 	return ($attr, undef) unless defined $Implicit{$tag} and $Implicit{$tag}{$attr};
 	my $imp = $Implicit{$tag}{$attr};
 	return ($attr, $imp) if $imp =~ s/^$attr=//i;
 	return ( $Implicit{$tag}{$attr}, $attr );
 }
-
-$Tags_added = 0;
 
 1;
 __END__



1.2.4.2   +36 -176   interchange/lib/Vend/Parser.pm


rev 1.2.4.2, prev_rev 1.2.4.1
Index: Parser.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Parser.pm,v
retrieving revision 1.2.4.1
retrieving revision 1.2.4.2
diff -u -r1.2.4.1 -r1.2.4.2
--- Parser.pm	23 Mar 2001 13:34:46 -0000	1.2.4.1
+++ Parser.pm	25 Jan 2003 22:21:28 -0000	1.2.4.2
@@ -1,13 +1,11 @@
-package Vend::Parser;
-
-# $Id: Parser.pm,v 1.2.4.1 2001/03/23 13:34:46 racke Exp $
-#
 # Vend::Parser - Interchange parser class
-# Copyright 1997-2001 by Michael J. Heins <heins@akopia.com>
+#
+# $Id: Parser.pm,v 1.2.4.2 2003/01/25 22:21:28 racke Exp $
+#
+# Copyright (C) 1997-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # Based on HTML::Parser
 # Copyright 1996 Gisle Aas. All rights reserved.
-#
 
 =head1 NAME
 
@@ -49,7 +47,7 @@
 
 =head1 COPYRIGHT
 
-Copyright 1997-2001 Akopia, Inc.  
+Copyright 1997-2002 Red Hat, Inc.  
 Original HTML::Parser module copyright 1996 Gisle Aas.
 
 This library is free software; you can redistribute it and/or
@@ -57,18 +55,18 @@
 
 =head1 AUTHORS
 
-Vend::Parser - Mike Heins <heins@akopia.com>  
+Vend::Parser - Mike Heins <mheins@redhat.com>  
 HTML::Parser - Gisle Aas <aas@sn.no>
 
 =cut
 
+package Vend::Parser;
 
 use strict;
 
 use HTML::Entities ();
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.2.4.1 $, 10);
-
+$VERSION = substr(q$Revision: 1.2.4.2 $, 10);
 
 sub new
 {
@@ -83,9 +81,6 @@
 	shift->parse(undef);
 }
 
-
-use vars qw/$Find_tag/;
-
 sub parse
 {
 	my $self = shift;
@@ -97,19 +92,20 @@
 		return $self;
 	}
 	$$buf .= $_[0];
-	$Find_tag	= $Vend::Cfg->{Pragma}{no_html_parse}
-				?  qr{^([^[]+)}
-				:  qr{^([^[<]+)}
-				;
-#::logDebug("no_html_parse=$Vend::Cfg->{Pragma}{no_html_parse} Find_tag=$Find_tag");
 
 	my $eaten;
 	# Parse html text in $$buf.  The strategy is to remove complete
 	# tokens from the beginning of $$buf until we can't deside whether
 	# it is a token or not, or the $$buf is empty.
 	while (1) {  # the loop will end by returning when text is parsed
-		# First we try to pull off any plain text (anything before a "<" char)
-		if ($$buf =~ s/$Find_tag// ) {
+		# If a preceding routine sent the response, stop 
+		if ($Vend::Sent) {
+			${$self->{OUT}} = $self->{_buf} = '';
+			@Vend::Output = ();
+			return $self;
+		}
+		# We try to pull off any plain text (anything before a '[')
+		if ($$buf =~ s/^([^[]+)// ) {
 #my $eat = $1;
 #::logDebug("plain eat='$eat'");
 #$self->text($eat);
@@ -130,13 +126,9 @@
 			$self->{HTML} = 0 if ! defined $self->{HTML};
 #::logDebug("do [ tag");
 
-			# This first thing we must find is a tag name.  RFC1866 says:
-			#   A name consists of a letter followed by letters,
-			#   digits, periods, or hyphens. The length of a name is
-			#   limited to 72 characters by the `NAMELEN' parameter in
-			#   the SGML declaration for HTML, 9.5, "SGML Declaration
-			#   for HTML".  In a start-tag, the element name must
-			#   immediately follow the tag open delimiter `<'.
+			# First find a tag name. It must immediately follow the
+			# opening '[', then start with a letter, and be followed by
+			# letters, numbers, dot, or underscore.
 			if ($$buf =~ s|^(([a-zA-Z][-a-zA-Z0-9._]*)\s*)||) {
 				$eaten .= $1;
 
@@ -150,37 +142,38 @@
 #::logDebug("tag='$tag' eat='$eaten'");
 
 				# Then we would like to find some attributes
-				#
-				# Arrgh!! Since stupid Netscape violates RCF1866 by
-				# using "_" in attribute names (like "ADD_DATE") of
-				# their bookmarks.html, we allow this too.
-				while (	$$buf =~ s|^(([a-zA-Z][-a-zA-Z0-9._]*)\s*)|| or
+				while (	$$buf =~ s|^(([_a-zA-Z][-a-zA-Z0-9._]*)\s*)|| or
 					 	$$buf =~ s|^(([=!<>][=~]?)\s+)||                 )
 				{
 					$eaten .= $1;
 					my $attr = lc $2;
+					$attr =~ tr/-/_/;
 #::logDebug("in parse, eaten=$eaten");
 					$attr =~ s/\.(.*)//
 						and $element = $1;
 						
 					my $val;
 					
-					# The attribute might take an optional value (first we
-					# check for an unquoted value)
+					# The attribute might take an optional value.
+					# First we check for an unquoted value
 					if ($$buf =~ s~(^=\s*([^\|\"\'\`\]\s][^\]>\s]*)\s*)~~) {
 						$eaten .= $1;
 						next unless defined $attr;
 						$val = $2;
-					# or quoted by " or ' or # or $ or |
+					# or quoted by " or '
 					} elsif ($$buf =~ s~(^=\s*(["\'])(.*?)\2\s*)~~s) {
 						$eaten .= $1;
 						next unless defined $attr;
 						$val = $3;
 						HTML::Entities::decode($val) if $attr{entities};
-					# or quoted by `` to send to [calc]
 					} elsif ($$buf =~ s~(^=\s*([\`\|])(.*?)\2\s*)~~s) {
 						$eaten .= $1;
-						if    ($2 eq '`') { $val = Vend::Interpolate::tag_calc($3); }
+						# or quoted by ` to send to [calc]
+						if    ($2 eq '`') {
+							$val = Vend::Interpolate::tag_calc($3)
+								unless defined $Vend::Cfg->{AdminSub}{calc};
+						}
+						# or quoted by | to strip leading & trailing whitespace
 						elsif ($2 eq '|') {
 								$val = $3;
 								$val =~ s/^\s+//;
@@ -195,9 +188,8 @@
 						$$buf = "$eaten$1";
 						return $self;
 					} elsif (!$old) {
-						# assume attribute with implicit value, but
-						# if not,no value is set and the
-						# eaten value is grown
+						# assume attribute with implicit value, but if not,
+						# no value is set and the eaten value is grown
 						undef $nopush;
 						($attr,$val,$nopush) = $self->implicit($tag,$attr);
 						$old = 1 unless $val;
@@ -238,9 +230,12 @@
 					push(@attrseq, $attr) unless $nopush;
 				}
 
-				# At the end there should be a closing "\] or >"
+				# At the end there should be a closing ']'
 				if ($$buf =~ s|^\]|| ) {
 					$self->start($tag, \%attr, \@attrseq, "$eaten]");
+				} elsif ($$buf =~ s|^/\s*\]||) {
+					# XML-style empty container tag like [this /]
+					$self->start($tag, \%attr, \@attrseq, "$eaten]", 1);
 				} elsif ($$buf =~ s|^([^\]\n]+\])||) {
 					$eaten .= $1;
 					$self->start($tag, {}, [], $eaten);
@@ -260,141 +255,6 @@
 				$$buf = $eaten;  # need more data to parse
 				return $self;
 			}
-		} elsif ($$buf =~ s|^<||) {
-			# start tag
-			$eaten = '<';
-#::logDebug("do < tag") if ! $Vend::DoneDebug++;
-
-			# This first thing we must find is a tag name.  RFC1866 says:
-			#   A name consists of a letter followed by letters,
-			#   digits, periods, or hyphens. The length of a name is
-			#   limited to 72 characters by the `NAMELEN' parameter in
-			#   the SGML declaration for HTML, 9.5, "SGML Declaration
-			#   for HTML".  In a start-tag, the element name must
-			#   immediately follow the tag open delimiter `<'.
-			if ($$buf =~ s|^(([a-zA-Z][-a-zA-Z0-9._]*)((?:\s+[^>]+)?\s+[mM][Vv]\s*=)\s*)||) {
-#::logDebug("REALLY do < tag") if ! $Vend::DoneDebug++;
-				$eaten .= $1;
-				$self->{HTML} = 1;
-
-				my ($tag, $end_tag);
-				my ($nopush, $element);
-				my %attr;
-				my @attrseq;
-				my $old;
-
-				$end_tag = $2;
-#::logDebug("end_tag='$end_tag' eat='$eaten'");
-				( $$buf =~ s|^((['"])(.*?)\2\s*)||s and $tag = $3 )
-				or
-				( $$buf =~ s|^(([a-zA-Z][-a-zA-Z0-9._]*)\s*)|| and $tag = $2)
-				or ($self->text($eaten), next);
-				$eaten .= $1;
-				if( index($tag, " ") != -1 ) {
-					($tag, $attr{OLD}) = split /\s+/, $tag, 2;
-				}
-#::logDebug("< tag='$tag' eat='$eaten'");
-				$tag = lc $tag;
-
-				# Then we would like to find some attributes
-				#
-				# Arrgh!! Since stupid Netscape violates RCF1866 by
-				# using "_" in attribute names (like "ADD_DATE") of
-				# their bookmarks.html, we allow this too.
-				while (	$$buf =~ s|^(([a-zA-Z][-a-zA-Z0-9._]*)\s*)|| ) {
-					$eaten .= $1;
-#::logDebug("in parse, eaten=$eaten");
-					my $attr = lc $2;
-					$attr =~ s/^mv\.?//
-						or $tag =~ /^urld/
-						or undef $attr;
-					$attr =~ s/\.(.*)//
-						and $element = $1;
-						
-					my $val;
-					
-					# The attribute might take an optional value (first we
-					# check for an unquoted value)
-					if ($$buf =~ s~(^=\s*([^\!\|\@\"\'\`\]\s][^\]>\s]*)\s*)~~) {
-						$eaten .= $1;
-						next unless defined $attr;
-						$val = $2;
-					# or quoted by " or ' or # or $ or |
-					} elsif ($$buf =~ s~(^=\s*(["\'])(.*?)\2\s*)~~s) {
-						$eaten .= $1;
-						next unless defined $attr;
-						$val = $3;
-						HTML::Entities::decode($val) if $attr{entities};
-					# or quoted by `` to send to [calc]
-					} elsif ($$buf =~ s~(^=\s*([\`\|]?)(.*?)\2\s*)~~s) {
-						$eaten .= $1;
-						if    ($2 eq '`') { $val =Vend::Interpolate::tag_calc($4); }
-						elsif ($2 eq '|') {
-								$val = $3;
-								$val =~ s/^\s+//;
-								$val =~ s/\s+$//;
-						}
-						else {
-							die "parse error!";
-						}
-					# truncated just after the '=' or inside the attribute
-					} elsif ($$buf =~ m|^(=\s*)$|s or
-							 $$buf =~ m|^(=\s*[\"\'].*)|s) {
-#::logDebug("Truncated? eaten=$eateni buf=$$buf");
-						$$buf = "$eaten$1";
-						return $self;
-					} 
-
-					if(defined $element) {
-#::logDebug("Found element: $element val=$val");
-						if(! ref $attr{$attr}) {
-							if ($element =~ /[A-Za-z]/) {
-								$attr{$attr} = { $element => $val };
-							}
-							else {
-								$attr{$attr} = [ ];
-								$attr{$attr}->[$element] = $val;
-							}
-							push (@attrseq, $attr);
-						}
-						elsif($attr{$attr} =~ /ARRAY/) {
-							if($element =~ /\D/) {
-								push @{$attr{$attr}}, $val;
-							}
-							else {
-								$attr{$attr}->[$element] = $val;
-							}
-						}
-						elsif ($attr{$attr} =~ /HASH/) {
-							$attr{$attr}->{$element} = $val;
-						}
-						undef $element;
-						next;
-					}
-					$attr{$attr} = $val;
-					push(@attrseq, $attr) unless $nopush;
-				}
-
-				# At the end there should be a closing "\] or >"
-				if ($$buf =~ s|^>|| ) {
-					$self->start($tag, \%attr, \@attrseq, "$eaten>", $end_tag);
-				} elsif (length $$buf) {
-#::logDebug("not conforming, eaten $eaten");
-					# Not a conforming start tag, regard it as normal text
-					$self->text($eaten);
-				} else {
-					$$buf = $eaten;  # need more data to know
-					return $self;
-				}
-
-			} elsif (length $$buf) {
-#::logDebug("eaten $eaten");
-				$self->text($eaten);
-			} else {
-				#$$buf = $eaten;  # need more data to parse
-				return $self;
-			}
-
 		} elsif (length $$buf) {
 			::logDebug("remaining: $$buf");
 			die $$buf; # This should never happen



1.5.4.4   +276 -266  interchange/lib/Vend/Scan.pm


rev 1.5.4.4, prev_rev 1.5.4.3
Index: Scan.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Scan.pm,v
retrieving revision 1.5.4.3
retrieving revision 1.5.4.4
diff -u -r1.5.4.3 -r1.5.4.4
--- Scan.pm	2 Dec 2000 21:13:41 -0000	1.5.4.3
+++ Scan.pm	25 Jan 2003 22:21:28 -0000	1.5.4.4
@@ -1,8 +1,8 @@
-# Vend/Scan.pm:  Prepare searches for Interchange
+# Vend::Scan - Prepare searches for Interchange
 #
-# $Id: Scan.pm,v 1.5.4.3 2000/12/02 21:13:41 racke Exp $
+# $Id: Scan.pm,v 1.5.4.4 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -29,185 +29,202 @@
 			perform_search
 			);
 
-$VERSION = substr(q$Revision: 1.5.4.3 $, 10);
+$VERSION = substr(q$Revision: 1.5.4.4 $, 10);
 
 use strict;
 use Vend::Util;
 use Vend::Interpolate;
 use Vend::Data qw(product_code_exists_ref column_index);
+use Vend::TextSearch;
+use Vend::DbSearch;
+use Vend::RefSearch;
 
 my @Order = ( qw(
-					mv_dict_look
-					mv_searchspec
-					mv_search_file
-					mv_base_directory
-					mv_field_names
-                    mv_field_file
-					mv_verbatim_columns
-					mv_range_look
-					mv_cache_key
-					mv_profile
-					mv_case
-					mv_negate
-					mv_numeric
-                    mv_column_op
-					mv_begin_string
-					mv_coordinate
-					mv_nextpage
-					mv_dict_end
-					mv_dict_fold
-					mv_dict_limit
-					mv_dict_order
-					mv_failpage
-					mv_first_match
-					mv_all_chars
-					mv_return_all
-					mv_exact_match
-					mv_head_skip
-					mv_index_delim
-					mv_list_only
-					mv_matchlimit
-                    mv_more_decade
-                    mv_more_id
-					mv_min_string
-					mv_max_matches
-					mv_orsearch
-					mv_range_min
-					mv_range_max
-					mv_range_alpha
-					mv_record_delim
-					mv_return_delim
-					mv_return_fields
-					mv_return_file_name
-					mv_return_reference
-					mv_substring_match
-					mv_start_match
-					mv_return_spec
-					mv_spelling_errors
-					mv_search_field
-					mv_search_group
-					mv_search_label
-					mv_search_page
-					mv_search_relate
-					mv_sort_field
-					mv_sort_option
-					mv_searchtype
-					mv_unique
-					mv_more_matches
-					mv_value
-					prefix
-
+	mv_dict_look
+	mv_searchspec
+	mv_search_file
+	mv_base_directory
+	mv_field_names
+	mv_field_file
+	mv_verbatim_columns
+	mv_range_look
+	mv_cache_key
+	mv_profile
+	mv_case
+	mv_negate
+	mv_numeric
+	mv_column_op
+	mv_begin_string
+	mv_coordinate
+	mv_nextpage
+	mv_dict_end
+	mv_dict_fold
+	mv_dict_limit
+	mv_dict_order
+	mv_failpage
+	mv_first_match
+	mv_all_chars
+	mv_return_all
+	mv_exact_match
+	mv_head_skip
+	mv_index_delim
+	mv_list_only
+	mv_matchlimit
+	mv_more_alpha
+	mv_more_alpha_chars
+	mv_more_decade
+	mv_more_id
+	mv_min_string
+	mv_max_matches
+	mv_no_hide
+	mv_orsearch
+	mv_range_min
+	mv_range_max
+	mv_range_alpha
+	mv_record_delim
+	mv_return_delim
+	mv_return_fields
+	mv_return_file_name
+	mv_return_reference
+	mv_substring_match
+	mv_small_data
+	mv_start_match
+	mv_return_spec
+	mv_spelling_errors
+	mv_like_field
+	mv_like_spec
+	mv_search_field
+	mv_search_group
+	mv_search_label
+	mv_search_page
+	mv_search_relate
+	mv_sort_field
+	mv_sort_option
+	mv_searchtype
+	mv_unique
+	mv_more_matches
+	mv_value
+	mv_next_search
+	mv_search_reference
+	prefix
 ));
 
 my %Scan = ( qw(
-
-                    ac  mv_all_chars
-                    bd  mv_base_directory
-                    bs  mv_begin_string
-                    ck  mv_cache_key
-                    co  mv_coordinate
-                    cs  mv_case
-                    cv  mv_verbatim_columns
-                    de  mv_dict_end
-                    df  mv_dict_fold
-                    di  mv_dict_limit
-                    dl  mv_dict_look
-                    DL  mv_raw_dict_look
-                    do  mv_dict_order
-                    dr  mv_record_delim
-                    em  mv_exact_match
-                    er  mv_spelling_errors
-                    ff  mv_field_file
-                    fi  mv_search_file
-                    fm  mv_first_match
-                    fn  mv_field_names
-                    hs  mv_head_skip
-                    ix  mv_index_delim
-                    lb  mv_search_label
-                    lo  mv_list_only
-                    lr  mv_search_line_return
-                    md  mv_more_decade
-                    mi  mv_more_id
-                    ml  mv_matchlimit
-                    mm  mv_max_matches
-                    MM  mv_more_matches
-                    mp  mv_profile
-                    ms  mv_min_string
-                    ne  mv_negate
-                    ng  mv_negate
-                    np  mv_nextpage
-                    nu  mv_numeric
-                    op  mv_column_op
-                    os  mv_orsearch
-					pf  prefix
-                    ra  mv_return_all
-                    rd  mv_return_delim
-                    rf  mv_return_fields
-                    rg  mv_range_alpha
-                    rl  mv_range_look
-                    rm  mv_range_min
-                    rn  mv_return_file_name
-                    rr  mv_return_reference
-                    rs  mv_return_spec
-                    rx  mv_range_max
-                    SE  mv_raw_searchspec
-                    se  mv_searchspec
-                    sf  mv_search_field
-                    sg  mv_search_group
-                    si  mv_search_immediate
-                    sm  mv_start_match
-                    sp  mv_search_page
-                    sq  mv_sql_query
-                    sr  mv_search_relate
-                    st  mv_searchtype
-                    su  mv_substring_match
-                    tf  mv_sort_field
-                    to  mv_sort_option
-                    un  mv_unique
-                    va  mv_value
-
-				) );
+	ac  mv_all_chars
+	bd  mv_base_directory
+	bs  mv_begin_string
+	ck  mv_cache_key
+	co  mv_coordinate
+	cs  mv_case
+	cv  mv_verbatim_columns
+	de  mv_dict_end
+	df  mv_dict_fold
+	di  mv_dict_limit
+	dl  mv_dict_look
+	DL  mv_raw_dict_look
+	do  mv_dict_order
+	dr  mv_record_delim
+	em  mv_exact_match
+	er  mv_spelling_errors
+	ff  mv_field_file
+	fi  mv_search_file
+	fm  mv_first_match
+	fn  mv_field_names
+	hs  mv_head_skip
+	ix  mv_index_delim
+	lb  mv_search_label
+	lf  mv_like_field
+	lo  mv_list_only
+	lr  mv_search_line_return
+	ls  mv_like_spec
+	ma  mv_more_alpha
+	mc  mv_more_alpha_chars
+	md  mv_more_decade
+	mi  mv_more_id
+	ml  mv_matchlimit
+	mm  mv_max_matches
+	MM  mv_more_matches
+	mp  mv_profile
+	ms  mv_min_string
+	ne  mv_negate
+	ng  mv_negate
+	nh  mv_no_hide
+	np  mv_nextpage
+	ns  mv_next_search
+	nu  mv_numeric
+	op  mv_column_op
+	os  mv_orsearch
+	pf  prefix
+	ra  mv_return_all
+	rd  mv_return_delim
+	re	mv_search_reference
+	rf  mv_return_fields
+	rg  mv_range_alpha
+	rl  mv_range_look
+	rm  mv_range_min
+	rn  mv_return_file_name
+	rr  mv_return_reference
+	rs  mv_return_spec
+	rx  mv_range_max
+	sd  mv_small_data
+	se  mv_searchspec
+	sf  mv_search_field
+	sg  mv_search_group
+	si  mv_search_immediate
+	sm  mv_start_match
+	sp  mv_search_page
+	sq  mv_sql_query
+	sr  mv_search_relate
+	st  mv_searchtype
+	su  mv_substring_match
+	tf  mv_sort_field
+	to  mv_sort_option
+	un  mv_unique
+	va  mv_value
+) );
 
 my @ScanKeys = keys %Scan;
 my %RevScan;
 %RevScan = reverse %Scan;
 
 my %Parse = (
-
-    mv_search_group         =>  \&_array,
-    mv_search_field         =>  \&_array,
-    mv_all_chars            =>  \&_yes_array,
-    mv_begin_string         =>  \&_yes_array,
-    mv_case                 =>  \&_yes_array,
-    mv_negate               =>  \&_yes_array,
-    mv_numeric              =>  \&_yes_array,
-    mv_orsearch             =>  \&_yes_array,
-    mv_substring_match      =>  \&_yes_array,
-    mv_column_op            =>  \&_array,
-    mv_coordinate           =>  \&_yes,
+	mv_search_group         =>  \&_array,
+	mv_search_field         =>  \&_array,
+	mv_all_chars            =>  \&_yes_array,
+	mv_begin_string         =>  \&_yes_array,
+	mv_case                 =>  \&_yes_array,
+	mv_negate               =>  \&_yes_array,
+	mv_numeric              =>  \&_yes_array,
+	mv_orsearch             =>  \&_yes_array,
+	mv_substring_match      =>  \&_yes_array,
+	mv_column_op            =>  \&_array,
+	mv_coordinate           =>  \&_yes,
+	mv_no_hide              =>  \&_yes,
 
 	mv_field_names          =>	\&_array,
 	mv_spelling_errors      => 	sub { my $n = int($_[1]); $n < 8 ? $n : 1; },
-    mv_dict_limit           =>  \&_dict_limit,
-    mv_exact_match          =>  \&_yes,
-    mv_head_skip            =>  \&_number,
-    mv_matchlimit           =>  sub { $_[1] =~ /(\d+)/ ? $1 : 50 },
-    mv_max_matches          =>  sub { $_[1] =~ /(\d+)/ ? $1 : 2000 },
-    mv_min_string           =>  sub { $_[1] =~ /(\d+)/ ? $1 : 1 },
-    mv_profile              =>  \&parse_profile,
-    mv_range_alpha          =>  \&_array,
-    mv_range_look           =>  \&_array,
-    mv_range_max            =>  \&_array,
-    mv_range_min            =>  \&_array,
-    mv_return_all           =>  \&_yes,
-    mv_return_fields        =>  \&_array,
-    mv_return_file_name     =>  \&_yes,
-    mv_save_context         =>  \&_array,
-    mv_searchspec           =>  \&_verbatim_array,
-    mv_sort_field           =>  \&_array,
-    mv_sort_option          =>  \&_opt,
-    mv_unique               =>  \&_yes,
-    mv_value                =>  \&_value,
+	mv_dict_limit           =>  \&_dict_limit,
+	mv_exact_match          =>  \&_yes,
+	mv_head_skip            =>  \&_number,
+	mv_matchlimit           =>  \&_matchlimit,
+	mv_max_matches          =>  sub { $_[1] =~ /(\d+)/ ? $1 : -1 },
+	mv_min_string           =>  sub { $_[1] =~ /(\d+)/ ? $1 : 1 },
+	mv_profile              =>  \&parse_profile,
+	mv_range_alpha          =>  \&_array,
+	mv_range_look           =>  \&_array,
+	mv_range_max            =>  \&_array,
+	mv_range_min            =>  \&_array,
+	mv_return_all           =>  \&_yes,
+	mv_return_fields        =>  \&_array,
+	mv_return_file_name     =>  \&_yes,
+	mv_save_context         =>  \&_array,
+	mv_searchspec           =>  \&_verbatim_array,
+	mv_like_field           =>  \&_array,
+	mv_like_spec            =>  \&_verbatim_array,
+	mv_sort_field           =>  \&_array,
+	mv_sort_option          =>  \&_opt,
+	mv_unique               =>  \&_yes,
+	mv_value                =>  \&_value,
 	mv_sql_query			=>  sub {
 								my($ref, $val) = @_;
 								my $p = Vend::Interpolate::escape_scan($val, $ref);
@@ -217,7 +234,8 @@
 	base_directory      	=> 	\&_dir_security_scalar,
 	mv_field_file          => 	\&_file_security_scalar,
 	mv_search_file         => 	\&_file_security,
-
+	mv_more_alpha           =>  \&_yes,
+	mv_more_alpha_chars     =>   sub { $_[1] =~ /(\d+)/ ? $1 : 3 },
 );
 
 sub create_last_search {
@@ -245,7 +263,7 @@
 		$c = \%CGI::values;
 	}
 	else {
-		$param =~ s/__NULL__/\0/g;
+		$param =~ s/-_NULL_-/\0/g;
 		@args = split m:/:, $param;
 	}
 
@@ -255,7 +273,6 @@
 		($var,$val) = split /=/, $_, 2;
 		next unless defined $Scan{$var};
 		$val =~ s!::!/!g;
-		$val =~ s/%([A-Fa-f0-9][A-Fa-f0-9])/chr(hex($1))/ge;
 		$c->{$Scan{$var}} = defined $c->{$Scan{$var}}
 							? ($c->{$Scan{$var}} . "\0$val" )
 							: $val;
@@ -275,16 +292,16 @@
 	if(index($map, "\n") != -1) {
 		$params = $map;
 	}
-    elsif(defined $Vend::Cfg->{SearchProfileName}->{$map}) {
-        $map = $Vend::Cfg->{SearchProfileName}->{$map};
-        $params = $Vend::Cfg->{SearchProfile}->[$map];
-    }
-    elsif($map =~ /^\d+$/) {
-        $params = $Vend::Cfg->{SearchProfile}->[$map];
-    }
-    elsif(defined $::Scratch->{$map}) {
-        $params = $::Scratch->{$map};
-    }
+	elsif(defined $Vend::Cfg->{SearchProfileName}->{$map}) {
+		$map = $Vend::Cfg->{SearchProfileName}->{$map};
+		$params = $Vend::Cfg->{SearchProfile}->[$map];
+	}
+	elsif($map =~ /^\d+$/) {
+		$params = $Vend::Cfg->{SearchProfile}->[$map];
+	}
+	elsif(defined $::Scratch->{$map}) {
+		$params = $::Scratch->{$map};
+	}
 	
 	return undef unless $params;
 
@@ -308,9 +325,9 @@
 }
 
 sub parse_profile_ref {
-    my ($ref, $profile) = @_;
-    my ($var, $p);
-    foreach $p (keys %$profile) {
+	my ($ref, $profile) = @_;
+	my ($var, $p);
+	foreach $p (keys %$profile) {
 		next unless
 			$var = $Scan{$p}
 					or
@@ -318,24 +335,24 @@
 		$ref->{$var} = $profile->{$p}, next
 			if ref $profile->{$p} || ! defined $Parse{$var};
 		$ref->{$var} = &{$Parse{$var}}($ref,$profile->{$p});
-    }
-    return;
+	}
+	return;
 }
 
 sub parse_profile {
 	my($ref,$profile) = @_;
 	return undef unless defined $profile;
 	my($params);
-    if(defined $Vend::Cfg->{SearchProfileName}->{$profile}) {
-        $profile = $Vend::Cfg->{SearchProfileName}->{$profile};
-        $params = $Vend::Cfg->{SearchProfile}->[$profile];
-    }
-    elsif($profile =~ /^\d+$/) {
-        $params = $Vend::Cfg->{SearchProfile}->[$profile];
-    }
-    elsif(defined $::Scratch->{$profile}) {
-        $params = $::Scratch->{$profile};
-    }
+	if(defined $Vend::Cfg->{SearchProfileName}->{$profile}) {
+		$profile = $Vend::Cfg->{SearchProfileName}->{$profile};
+		$params = $Vend::Cfg->{SearchProfile}->[$profile];
+	}
+	elsif($profile =~ /^\d+$/) {
+		$params = $Vend::Cfg->{SearchProfile}->[$profile];
+	}
+	elsif(defined $::Scratch->{$profile}) {
+		$params = $::Scratch->{$profile};
+	}
 	
 	return undef unless $params;
 
@@ -364,25 +381,24 @@
 }
 
 sub finish_search {
-    my($q) = @_;
+	my($q) = @_;
 #::logDebug("finishing up search spec=" . ::uneval($q));
-    my $matches = $q->{'matches'};
-    $::Values->{mv_search_match_count}    = $matches;
+	my $matches = $q->{'matches'};
+	$::Values->{mv_search_match_count}    = $matches;
 	delete $::Values->{mv_search_error};
 	$::Values->{mv_search_error} = $q->{mv_search_error}
 		if $q->{mv_search_error};
-    $::Values->{mv_matchlimit}     = $q->{mv_matchlimit};
-    $::Values->{mv_first_match}    = $q->{mv_first_match}
+	$::Values->{mv_matchlimit}     = $q->{mv_matchlimit};
+	$::Values->{mv_first_match}    = $q->{mv_first_match}
 			if defined $q->{mv_first_match};
-    $::Values->{mv_searchspec} 	   = $q->{mv_searchspec};
-    $::Values->{mv_raw_searchspec} = $q->{mv_raw_searchspec} || undef;
-    $::Values->{mv_raw_dict_look}  = $q->{mv_raw_dict_look}  || undef;
-    $::Values->{mv_dict_look}      = $q->{mv_dict_look} || undef;
+	$::Values->{mv_searchspec} 	   = $q->{mv_searchspec};
+	$::Values->{mv_raw_dict_look}  = $q->{mv_raw_dict_look}  || undef;
+	$::Values->{mv_dict_look}      = $q->{mv_dict_look} || undef;
 }
 
 # Search for an item with glimpse or text engine
 sub perform_search {
-    my($c,$more_matches,$pre_made) = @_;
+	my($c,$more_matches,$pre_made) = @_;
 #::logDebug('searching....');
 	if (!$c) {
 		return undef unless $Vend::Session->{search_params};
@@ -393,15 +409,15 @@
 		}
 	}
 	elsif ($c->{mv_search_immediate}) {
-        unless($c->{mv_cache_key}) {
-            undef $c->{mv_search_immediate};
-            Vend::Scan::create_last_search($c);
-            $c->{mv_cache_key} = generate_key($Vend::Session->{last_search});
-        }
+		unless($c->{mv_cache_key}) {
+			undef $c->{mv_search_immediate};
+			Vend::Scan::create_last_search($c);
+			$c->{mv_cache_key} = generate_key($Vend::Session->{last_search});
+		}
 	}
 
 	my($v) = $::Values;
-    my($param);
+	my($param);
 	my(@fields);
 	my(@specs);
 	my($out);
@@ -465,13 +481,12 @@
 #::logDebug("Options after parse: " . ::uneval(\%options));
 
 # GLIMPSE
- 	if (defined $options{mv_searchtype} && $options{mv_searchtype} eq 'glimpse') {
+	if (defined $options{mv_searchtype} && $options{mv_searchtype} eq 'glimpse') {
 		undef $options{mv_searchtype} if ! $Vend::Cfg->{Glimpse};
 	}
 # END GLIMPSE
 
-  SEARCH: {
-
+	SEARCH: {
 		$options{mv_return_all} = 1
 			if $options{mv_dict_look} and ! $options{mv_searchspec};
 	
@@ -489,6 +504,9 @@
 		elsif (! $options{mv_searchtype} or $options{mv_searchtype} eq 'text') {
 			$q = new Vend::TextSearch %options;
 		}
+		elsif ( $options{mv_searchtype} eq 'ref'){
+			$q = new Vend::RefSearch %options;
+		}
 # GLIMPSE
 		elsif ( $options{mv_searchtype} eq 'glimpse'){
 			$q = new Vend::Glimpse %options;
@@ -516,7 +534,7 @@
 
 #::logDebug(::uneval($q));
 		$out = $q->search();
-  } # last SEARCH
+	} # last SEARCH
 
 	if($q->{mv_list_only}) {
 		return $q->{mv_results};
@@ -569,7 +587,7 @@
 	}
 
 	die "SQL is not enabled for Interchange. Get the SQL::Statement module.\n"
-		unless $INC{'SQL/Statement.pm'};
+		unless defined &SQL::Statement::new;
 
 	my $parser = SQL::Parser->new('Ansi');
 
@@ -588,8 +606,9 @@
 		};
 	}
 	if($@) {
-		::logError("Bad SQL statement: $@\nQuery was: $text.\n");
-		return "se=BAD_SQL";
+		my $msg = ::errmsg("Bad SQL statement: %s\nQuery was: %s", $@, $text);
+		logError($msg) unless $Vend::Try;
+		Carp::croak($msg);
 	}
 
 	my $nuhash;
@@ -597,15 +616,6 @@
 
 	my $update = $stmt->command();
 	undef $update if $update eq 'SELECT';
-#	CODECHECK: {
-#		last CODECHECK if ! $update;
-#		my $i = 0;
-#		for($stmt->columns()) {
-#			($stmt->{MV_VALUE_RELOCATE} = $i, last)
-#				if $_ eq $codename || $_ eq '0';
-#			$i++;
-#		}
-#	}
 
 	for($stmt->tables()) {
 		my $t = $_->name();
@@ -615,7 +625,7 @@
 		if($db) {
 			$codename = $db->config('KEY') || 'code';
 			$nuhash = $db->config('NUMERIC') || undef;
-			push_spec( 'fi', $Vend::Cfg->{Database}{$t}{'file'}, $ary, $hash);
+			push_spec( 'fi', $db->config('file'), $ary, $hash);
 		}
 # GLIMPSE
 		elsif ("\L$t" eq 'glimpse') {
@@ -634,21 +644,11 @@
 
 	for($stmt->columns()) {
 		my $name = $_->name();
-		#($stmt->{MV_VALUE_RELOCATE} = 0, last) if $name eq '*';
 		push_spec('rf', $name, $ary, $hash);
 		last if $name eq '*';
 #::logDebug("column name=" . $_->name() . " table=" . $_->table());
 	}
-#	if(! $update) {
-#		# do nothing
-#	}
-#	elsif ($stmt->{mv_value_relocate}) {
-#		splice(@{$hash->{rf}}, $stmt->{mv_value_relocate}, 1);
-#	}
-#	elsif ($update eq 'insert') {
-#		$stmt->{mv_value_relocate} = 0 if ! $stmt->columns();
-#	}
-#
+
 	my @order;
 
 	@order = $stmt->order();
@@ -663,7 +663,9 @@
 	my @where;
 	my $numeric;
 	@where = $stmt->where();
-	if(defined $where[0]) {
+# Account for undocumented behavior in SQL::Statement
+# Fix by Kestutis Lasys
+	if(CORE::ref $where[0]) {
 	  my $or;
 	  push_spec('co', 'yes', $ary, $hash);
 	  do {
@@ -689,7 +691,7 @@
 #::logDebug("where col=$col spec=$spec");
 				$spec = $ref->{$spec->name()}		if ref $spec;
 
-				last OP unless $spec;
+				last OP unless defined $spec;
 
 				# Column name is a variable if a string
 				$col = $where->arg1();
@@ -707,11 +709,11 @@
 #::logDebug("where col=$col spec=$spec");
 
 #::logDebug("numeric for $col=$numeric");
-                push_spec('nu', ($numeric || 0),      $ary, $hash); 
-                push_spec('se', $spec,                $ary, $hash);
-                push_spec('op', $op,                  $ary, $hash);
-                push_spec('sf', $col,                 $ary, $hash);
-                push_spec('ne', ($where->neg() || 0), $ary, $hash);
+				push_spec('nu', ($numeric || 0),      $ary, $hash); 
+				push_spec('se', $spec,                $ary, $hash);
+				push_spec('op', $op,                  $ary, $hash);
+				push_spec('sf', $col,                 $ary, $hash);
+				push_spec('ne', ($where->neg() || 0), $ary, $hash);
 
 				
 			}
@@ -847,6 +849,7 @@
 	my @fields;
 #::logDebug("receiving verbatim_array: " . ::uneval (\@_));
 	@fields = ref $_[1] ? @{$_[1]} : split /\0/, $_[1], -1;
+	@fields = ('') if ! @fields;
 	unshift(@fields, @{$_[2]}) if $_[2];
 	return \@fields;
 }
@@ -871,37 +874,37 @@
 	defined $_[1] ? $_[1] : '';
 }
 
-my $Pat = ($^O =~ /win32/i) ? '([A-Za-z]:)?[\\/]' : '/';
-
 sub _file_security {
-    my ($junk, $param, $passed) = @_;
-    $passed = [] unless $passed;
-    my(@files) = grep /\S/, split /\s*[,\0]\s*/, $param, -1;
-    for(@files) {
-        my $ok = (m:^$Pat:o || /\.\./) ? 0 : 1;
-        if(!$ok) {
-            $ok = 1 if $_ eq $::Variable->{MV_SEARCH_FILE};
-            $ok = 1 if $::Scratch->{$_};
-        }
-		if($_ !~ /\./) {
-			$_ = $Vend::Cfg->{Database}{$_}{'file'}
-				if defined $Vend::Cfg->{Database}{$_}{'file'};
-		}
-		$ok &&= $_ !~ /$Vend::Cfg->{NoSearch}/
-			if $Vend::Cfg->{NoSearch};
-        push @$passed, $_ if $ok;
-    }
-    return $passed if @$passed;
+	my ($junk, $param, $passed) = @_;
+	$passed = [] unless $passed;
+	my(@files) = grep /\S/, split /\s*[,\0]\s*/, $param, -1;
+	for(@files) {
+		my $ok = (file_name_is_absolute($_) or /\.\./) ? 0 : 1;
+		if(!$ok) {
+			$ok = 1 if $_ eq $::Variable->{MV_SEARCH_FILE};
+			$ok = 1 if $::Scratch->{$_};
+		}
+		if(/^\w+$/ and ! $::Variable->{MV_DEFAULT_SEARCH_DB}) {
+			$_ = $Vend::Cfg->{Database}{$_}{file}
+				if defined $Vend::Cfg->{Database}{$_};
+		}
+		if ($ok and $Vend::Cfg->{NoSearch} and /$Vend::Cfg->{NoSearch}/) {
+			::logError("Search of '%s' denied by NoSearch directive", $_);
+			$ok = 0;
+		}
+		push @$passed, $_ if $ok;
+	}
+	return $passed if @$passed;
 	return [];
 }
 
 sub _dir_security_scalar {
-    return undef if ! -d $_->[0];
+	return undef if ! -d $_->[0];
 	return $_->[0];
 }
 
 sub _file_security_scalar {
-    my $result = _file_security(@_);
+	my $result = _file_security(@_);
 	return $result->[0];
 }
 
@@ -930,9 +933,16 @@
 	my ($ref,$limit) = @_;
 	return undef unless	defined $ref->{mv_dict_look};
 	$limit = -1 if $limit =~ /^[^-0-9]/;
-    $ref->{mv_dict_end} = $ref->{mv_dict_look};
-    substr($ref->{mv_dict_end},$limit,1) =~ s/(.)/chr(ord($1) + 1)/e;
+	$ref->{mv_dict_end} = $ref->{mv_dict_look};
+	substr($ref->{mv_dict_end},$limit,1) =~ s/(.)/chr(ord($1) + 1)/e;
 	return $_[1];
+}
+
+sub _matchlimit {
+	shift;
+	my $val = lc(shift);
+	return -1 if $val eq 'none' or $val eq 'all';
+	return int($val) || $::Variable->{MV_DEFAULT_MATCHLIMIT} || 50;
 }
 
 1;



1.6.4.5   +199 -90   interchange/lib/Vend/Search.pm


rev 1.6.4.5, prev_rev 1.6.4.4
Index: Search.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Search.pm,v
retrieving revision 1.6.4.4
retrieving revision 1.6.4.5
diff -u -r1.6.4.4 -r1.6.4.5
--- Search.pm	5 Dec 2000 20:37:31 -0000	1.6.4.4
+++ Search.pm	25 Jan 2003 22:21:28 -0000	1.6.4.5
@@ -1,10 +1,8 @@
-#!/usr/bin/perl -w
+# Vend::Search - Base class for search engines
 #
-# $Id: Search.pm,v 1.6.4.4 2000/12/05 20:37:31 racke Exp $
+# $Id: Search.pm,v 1.6.4.5 2003/01/25 22:21:28 racke Exp $
 #
-# Vend::Search -- Base class for search engines
-#
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -20,13 +18,10 @@
 # License along with this program; if not, write to the Free
 # Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 # MA  02111-1307  USA.
-#
 
-#
-#
 package Vend::Search;
 
-$VERSION = substr(q$Revision: 1.6.4.4 $, 10);
+$VERSION = substr(q$Revision: 1.6.4.5 $, 10);
 
 use strict;
 use vars qw($VERSION);
@@ -96,6 +91,25 @@
 
 my (@hashable) = (qw/mv_return_fields mv_range_look mv_search_field mv_sort_field/);
 
+sub search_reference {
+	my ($s, $ref) = @_;
+	my $c = { mv_searchtype => 'ref', label => ref($s), mv_search_file => '__none__' };
+
+	my $ns = $s->{mv_next_search};
+	$ns = $::Scratch->{$ns} unless $ns =~ /=/;
+	my $params = Vend::Interpolate::escape_scan($ns);
+#::logDebug("search_params: $params");
+	Vend::Scan::find_search_params($c, $params);
+
+	$c->{mv_return_filtered} = 1;
+	$c->{mv_return_fields} = '*';
+	$c->{mv_field_names} = $s->{mv_field_names};
+	$c->{mv_search_reference} = $ref;
+#::logDebug("Ref ready to search: " . ::uneval($c));
+	my $o = Vend::Scan::perform_search($c);
+	return @{$o->{mv_results} || []};
+}
+
 sub hash_fields {
 	my ($s, $fn, @laundry) = @_;
 	my %fh;
@@ -135,10 +149,10 @@
 
 sub escape {
     my($s, @text) = @_;
-#::logDebug( "text=@text");
+#::logDebug( "escaped text=" . ::uneval(\@text));
 	return @text if ! $s->{mv_all_chars}[0];
 	@text = map {quotemeta $_} @text;
-#::logDebug( "text=@text");
+#::logDebug( "escaped text=" . ::uneval(\@text));
     return @text;
 }
 
@@ -199,15 +213,15 @@
 			$msg,
             $s->{mv_coordinate},
 			scalar @$specs,
-			::uneval($specs),
+			Vend::Util::uneval($specs),
 			scalar @{$s->{mv_search_field}},
-			::uneval($s->{mv_search_field}),
+			Vend::Util::uneval($s->{mv_search_field}),
 			scalar @{$s->{mv_column_op}},
-			::uneval($s->{mv_column_op}),
+			Vend::Util::uneval($s->{mv_column_op}),
 			scalar @{$s->{mv_numeric}},
-			::uneval($s->{mv_numeric}),
+			Vend::Util::uneval($s->{mv_numeric}),
 			scalar @{$s->{mv_negate}},
-			::uneval($s->{mv_negate}),
+			Vend::Util::uneval($s->{mv_negate}),
 			;
 }
 
@@ -227,8 +241,8 @@
 	my $all_chars = $s->{mv_all_chars}[0];
 
 	while ($i < @specs) {
-#::logDebug("i=$i specs=$#specs");
-		if($#specs and length($specs[$i]) == 0) { # should add a switch
+#::logDebug("i=$i specs=$#specs mv_min_string=$s->{mv_min_string}");
+		if($#specs and length($specs[$i]) == 0 and $s->{mv_min_string} != 0) { # should add a switch
 			if($s->{mv_coordinate}) {
 		        splice(@{$s->{mv_search_group}}, $i, 1);
 		        splice(@{$s->{mv_search_field}}, $i, 1);
@@ -243,14 +257,6 @@
 		    splice(@specs, $i, 1);
 		}
 		else {
-			if(length($specs[$i]) < $s->{mv_min_string}) {
-				my $msg = <<EOF;
-Search strings must be at least $s->{mv_min_string} characters.
-You had '$specs[$i]' as one of your search strings.
-EOF
-				$s->{matches} = -1;
-				return undef;
-			}
 			COLOP: {
 				last COLOP unless $s->{mv_coordinate};
 #::logDebug("i=$i, begin_string=$s->{mv_begin_string}[$i]");
@@ -260,9 +266,9 @@
 				if(	$s->{mv_column_op}[$i] =~ /([=][~]|rm|em)/ ) {
 					$specs[$i] = quotemeta $specs[$i]
 						if $s->{mv_all_chars}[$i];
-					$s->{regex_specs} = []
-						unless $s->{regex_specs};
 					last COLOP if $s->{mv_begin_string}[$i];
+					last COLOP if $s->{mv_column_op}[$i] eq 'em';
+					$s->{regex_specs} ||= [];
 					$specs[$i] =~ /(.*)/;
 					push @{$s->{regex_specs}}, $1
 				}
@@ -283,6 +289,7 @@
 	}
 
 #::logDebug("regex_specs=" . ::uneval($s->{regex_specs}));
+#::logDebug("eq_specs_sql=" . ::uneval($s->{eq_specs_sql}));
 
 	if ( ! $s->{mv_exact_match} and ! $s->{mv_coordinate}) {
 		my $string = join ' ', @specs;
@@ -365,41 +372,107 @@
 	return $obj;
 }
 
+sub more_alpha {
+	my ($s, $out) = @_;
+	my ($sfpos, $letter, $sortkey, $last, @alphaspecs, $i);
+	my $alphachars = $s->{mv_more_alpha_chars} || 3;
+
+	# determine position of sort field within results
+	for ($i = 0; $i < @{$s->{mv_return_fields}}; $i++) {
+		last if $s->{mv_return_fields}->[$i] eq $s->{mv_sort_field}->[0];
+	}
+	$sfpos = $i;
+	
+	# add dummy record
+	@alphaspecs = (['']);
+		
+	$last = 0;
+	for ($i = 0; $i < @$out; $i++) {
+		$sortkey = $out->[$i]->[$sfpos];
+		$letter = substr($sortkey,0,1);
+
+		if ($letter ne substr($alphaspecs[$last]->[0],0,1)) {
+			# add record if first letter has changed
+			push (@alphaspecs, [$sortkey, 1, $i]);
+			# add last pointer to previous record
+			push (@{$alphaspecs[$last++]}, $i - 1);
+		} elsif ($alphachars > 1
+				 && $i - $alphaspecs[$last]->[2] >= $s->{mv_matchlimit}) {
+			# add record if match limit is exceeded and significant
+			# letters are different
+			for (my $c = 2; $c <= $alphachars; $c++) {
+				if (substr($sortkey,0,$c)
+					ne substr($alphaspecs[$last]->[0],0,$c)) {
+					push (@alphaspecs, [$sortkey, $c, $i]);
+					# add last pointer to previous record
+					push (@{$alphaspecs[$last++]}, $i - 1);
+					last;
+				}
+			}
+		}
+			
+	}
+	# add last pointer to last record
+	push (@{$alphaspecs[$last]}, $i - 1);
+	# remove dummy record
+	shift (@alphaspecs);
+	$s->{mv_alpha_list} = \@alphaspecs;
+}
+
 # Returns a field weeding function based on the search specification.
 # Input is the raw line and the delimiter, output is the fields
 # specified in the return_field specification
+# If we get a third parameter, $makeref, we need to build a reference
 sub get_return {
-	my($s, $final) = @_;
+	my($s, $final, $makeref) = @_;
 	my ($return_sub);
 
-	# We will pick out the return fields later if sorting
-	if(! $final and $s->{mv_sort_field}) {
-		return ( sub {@_}, 1);
-	}
+	if($makeref) {
+		# Avoid the hash key lookup, it is a closure
+		my $delim = $s->{mv_index_delim};
 
-	if(! $s->{mv_return_fields}) {
-		my $delim = $s->{mv_index_delim} || "\t";
-#::logDebug("code return. delim='$delim'");
-		$return_sub = sub {
-				$_[0] =~ s/$delim.*//s;
-				my $ary = [ $_[0] ];
-#::logDebug("ary is:" . ::uneval($ary));
-				return $ary;
-				};
+		# We will pick out the return fields later if sorting
+		# This returns
+		if( $s->{mv_sort_field} || $s->{mv_next_search}) {
+			return ( 
+				sub {
+					[ split /$delim/o, shift(@_) ]
+				},
+				1,
+			);
+		}
+		elsif($s->{mv_return_fields}) {
+			my @fields = @{$s->{mv_return_fields}};
+			$return_sub = sub {
+							return [ (split /$delim/o, shift(@_))[@fields] ]
+						};
+		}
+		else {
+			$return_sub = sub {
+							$_[0] =~ s/$delim.*//s;
+							return [ $_[0] ];
+					};
+		}
 	}
 	else {
-		my $delim = $s->{mv_index_delim};
-#::logDebug("rf[0]='$s->{mv_return_fields}[0]'");
-		my @fields = @{$s->{mv_return_fields}};
-#::logDebug("delim='$delim' fields='@fields'");
-		$return_sub = sub {
-			chomp($_[0]);
-			my $ary = [
-				(split /\Q$delim/o, $_[0])[@fields]
-				];
-#::logDebug("line is:$_[0]\nary is:" . ::uneval($ary));
-				return $ary;
-		};
+		# We will pick out the return fields later if sorting
+		# This returns
+		if(! $final and $s->{mv_sort_field} || $s->{mv_next_search}) {
+			return ( sub { [ @{ shift(@_) } ] }, 1);
+		}
+
+		if(! $s->{mv_return_fields}) {
+			$return_sub = sub {
+								return [ $_[0]->[0] ];
+						};
+		}
+		else {
+			my @fields = @{$s->{mv_return_fields}};
+			$return_sub = sub {
+				my $ref = [ @{$_[0]}[@fields] ];
+				return $ref;
+			};
+		}
 	}
 	return $return_sub;
 }
@@ -477,15 +550,36 @@
 	$out .= ' ) ';
 }
 
+sub create_field_hash {
+	my $s = shift;
+	my $fn = $s->{mv_field_names}
+		or return;
+	my $fh = {};
+	my $idx = 0;
+	for(@$fn) {
+		$fh->{$idx} = $idx;
+		$fh->{$_} = $idx++;
+	}
+	return $fh;
+}
+
 # Returns a screening function based on the search specification.
 # The $f is a reference to previously created search function which does
 # a pattern match on the line.
+# Makeref says we have to build a reference from the supplied text line
 sub get_limit {
-	my($s, $f) = @_;
+	my($s, $f, $makeref) = @_;
 	my $limit_sub;
 	my $range_code = '';
 	my $rd = $s->{mv_record_delim} || '\n';
-	my $code       = "sub {\nmy \$line = shift; chomp \$line; \$line =~ tr/$rd//d;\n";
+	my $code;
+	if($makeref) {
+		$code       = "sub {\nmy \$line = [split /$s->{mv_index_delim}/, shift(\@_)];\n";
+	}
+	else {
+		$code       = "sub {\nmy \$line = shift;\n";
+	}
+	$code .= "my \@fields = \@\$line;\n";
 	my $join_key;
 	$join_key = defined $s->{mv_return_fields} ? $s->{mv_return_fields}[0] : 0;
 	$join_key = 0 if $join_key eq '*';
@@ -516,33 +610,37 @@
 	}
 	# Add the code to get the join data if it is there
 	if(@join_fields) {
+		$s->{mv_field_hash} = create_field_hash($s) 
+			unless $s->{mv_field_hash};
 		$code .= <<EOF;
-my \$key = (split m{$s->{mv_index_delim}}, \$line)[$join_key];
+my \$key = \$line->[$join_key];
 EOF
 		for(@join_fields) {
 			my ($table, $col) = split /:+/, $_, 2;
 			if($table) {
 				$wild_card = 0;
 				$code .= <<EOF;
-\$line .= qq{$s->{mv_index_delim}} .
-		  Vend::Data::database_field('$table', \$key, '$col');
+push \@fields, Vend::Data::database_field('$table', \$key, '$col');
 EOF
 			}
 			elsif ($col =~ tr/:/,/) {
 				$col =~ tr/ \t//d;
+				my @col = map { $s->{mv_field_hash}{$_} } split /,/, $col;
+				@col = grep defined $_, @col;
+				$col = join ",", @col;
+				next unless $col;
 				$wild_card = 1;
 				$col =~ s/[^\d,.]//g;
 			$code .= <<EOF;
-my \$addl = join " ", (split m{\Q$s->{mv_index_delim}\E}, \$line)[$col];
-\$line .= qq{$s->{mv_index_delim}} . \$addl;
+my \$addl = join " ", \@fields[$col];
+push \@fields, \$addl;
 EOF
 			}
 			else {
 				$wild_card = 1;
 				$code .= <<EOF;
-my \$addl = \$line;
-\$addl =~ tr/$s->{mv_index_delim}/ /;
-\$line .= qq{$s->{mv_index_delim}} . \$addl;
+my \$addl = join " ", \@fields;
+push \@fields, \$addl;
 EOF
 			}
 		}
@@ -552,7 +650,7 @@
 
 	if ( ref $s->{mv_range_look} )  {
 		$range_code = <<EOF;
-return $joiner \$s->range_check(qq{$s->{mv_index_delim}},\$line);
+return $joiner \$s->range_check(\$line);
 EOF
 	}
 	if ( $s->{mv_coordinate} ) {
@@ -563,10 +661,12 @@
 		 }
 		 my $callchar = $fields =~ /,/ ? '@' : '$';
 		 $code .= <<EOF;
-	my \@fields = split /\\Q$s->{mv_index_delim}/, \$line;
 	\@fields = ${callchar}fields[$fields];
-#::logDebug("fields=" . join "|", \@fields);
 EOF
+		$code .= <<EOF if $Global::DebugFile and $CGI::values{debug};
+   ::logDebug("fields=" . join "|", \@fields);
+EOF
+
 		my @specs;
 		# For a limiting function, can't if orsearch
 
@@ -652,12 +752,14 @@
 #::logDebug("coderef=" . ::uneval_it(\@code));
 
 		undef $f if $s->{mv_search_relate} =~ s/\bor\b/or/ig;
+		undef $f unless $s->{regex_specs} or $s->{eq_specs};
 		DOLIMIT: {
 #::logDebug(::uneval_it({%$s}));
 #::logDebug("do_limit.");
 			last DOLIMIT if $f;
 #::logDebug("do_limit past f.");
 			last DOLIMIT if $s->{mv_small_data};
+			last DOLIMIT if $s->{eq_specs_sql};
 			last DOLIMIT if (grep $_, @{$s->{mv_orsearch}});
 			last DOLIMIT if defined $s->{mv_search_relate}
 							&& $s->{mv_search_relate} =~ s/\bor\b/or/i;
@@ -681,7 +783,8 @@
 			};
 			undef $f if $@;
 		}
-#::logDebug("filter function code is: $f");
+		::logDebug("filter function code is: $f")
+			if $Global::DebugFile and $CGI::values{debug};
 		use locale;
 		$f = eval $f if $f and ! ref $f;
 		die($@) if $@;
@@ -707,11 +810,12 @@
 		}
 		$code .= $relate;
 		$code .= "\n}\n";
-#::logDebug("coordinate search code is:\n$code");
+		::logDebug("coordinate search code is:\n$code")
+			if $Global::DebugFile and $CGI::values{debug};
 	}
 	elsif ( @{$s->{mv_search_field}} )  {
 		if(! $s->{mv_begin_string}[0]) {
-#::logDebug("Not begin, sub=f");
+#::logDebug("Not begin, sub=$f");
 			$sub = $f;
 		}
 		elsif (! $s->{mv_orsearch}[0] ) {
@@ -734,10 +838,8 @@
 		}
 		 $code .= $range_code;
 		 $code .= <<EOF;
-	my \@fields = (split /\\Q$s->{mv_index_delim}/, \$line)[$fields];
-	my \$field = join q{$s->{mv_index_delim}}, \@fields;
-	\$_ = \$field;
-	return(\$_ = \$line) if &\$sub();
+	local(\$_) = join q{$s->{mv_index_delim}}, \@\$line[$fields];
+	return(1) if &\$sub();
 	return undef;
 }
 EOF
@@ -765,8 +867,8 @@
 # Check to see if the fields specified in the range_look array
 # meet the criteria
 sub range_check {
-	my($s,$index_delim,$line) = @_;
-	my @fields = (split /\Q$index_delim/, $line)[@{$s->{mv_range_look}}];
+	my($s,$line) = @_;
+	my @fields = @$line[@{$s->{mv_range_look}}];
 	my $i = 0;
 	for(@fields) {
 		no strict 'refs';
@@ -888,7 +990,7 @@
 	for (@save) {
 		$return->{$_} = $s->{$_};
 	}
-	::uneval_fast($return);
+	Vend::Util::uneval_fast($return);
 }
 
 sub dump_options {
@@ -898,15 +1000,16 @@
 		$Data::Dumper::Indent = 3;
 		$Data::Dumper::Terse = 1;
 	}
-	return ::uneval($s);
+	return Vend::Util::uneval($s);
 }
 
 sub search_error {
-	my ($s, $msg) = @_;
+	my ($s, $msg, @args) = @_;
 	$s->{mv_search_error} = [] if ! $s->{mv_search_error};
+	$msg = ::errmsg($msg, @args);
 	push @{$s->{mv_search_error}}, $msg;
 	$s->{matches} = -1;
-	::logError ("search error: $msg");
+	::logError ("search error: %s", $msg);
 	return undef;
 }
 
@@ -917,10 +1020,20 @@
 	delete $s->{dbref} if defined $s->{dbref};
 	my $id = $s->{mv_more_id} || $Vend::SessionID;
 	$id .= ".$s->{mv_cache_key}";
-	if ($s->{matches} > $s->{mv_matchlimit}) {
+	if ($s->{matches} > $s->{mv_matchlimit} and $s->{mv_matchlimit} > 0) {
 		$s->{overflow} = 1;
 		$s->{mv_next_pointer} = $s->{mv_matchlimit};
 	}
+	if ($s->{mv_more_alpha}) {
+		unless ($s->{mv_sort_field} and @{$s->{mv_sort_field}}) {
+			return $s->search_error("mv_sort_field required for mv_more_alpha");
+		}
+		unless ($s->{mv_return_fields}
+				and grep {$_ eq $s->{mv_sort_field}->[0]} @{$s->{mv_return_fields}}) {
+					return $s->search_error("mv_sort_field missing in mv_return_fields (required for mv_more_alpha)");
+		}
+		more_alpha($s,$out);
+	}
 	
 	$file = Vend::Util::get_filename($id,undef,undef,$Vend::Cfg->{StaticScratch}); 
 #::logDebug("save_more: $id to $file.");
@@ -954,7 +1067,7 @@
 sub sort_search_return {
     my ($s, $target) = @_;
 
-	@Flds	= @{$s->{mv_sort_field}};
+	@Flds	= @{$s->{mv_sort_field} || []};
 	for(@Flds) {
 		next if /^\d+$/;
 		$_ = $s->{field_hash}{$_}
@@ -978,18 +1091,13 @@
 	rn	=> sub { $_[1] <=> $_[0]			},
 );
 
-	my $last = 'none';
 	my $i;
 	my $max = 0;
 	for($i = 0; $i < @Flds; $i++) {
 		$max = $Flds[$i] if $Flds[$i] > $max;
-		if (! $Opts[$i]) {
-			$Opts[$i] = $last;
-			next;
-		}
+		$Opts[$i] = 'none', next unless $Opts[$i];
 		$Opts[$i] = lc $Opts[$i];
 		$Opts[$i] = 'none' unless defined $Sort_field{$Opts[$i]};
-		$last = $Opts[$i];
 	}
 #::logDebug("sort_search_return: flds='@Flds' opts='@Opts'");
 
@@ -998,8 +1106,8 @@
 	my $delim = quotemeta $s->{mv_index_delim};
 	my $code = <<EOF;
 sub {
-	my \@a = (split /$delim/, \$a, $max)[$f_string];
-	my \@b = (split /$delim/, \$b, $max)[$f_string];
+	my \@a = \@{\$a}[$f_string];
+	my \@b = \@{\$b}[$f_string];
 	my \$r;
 EOF
 #::logDebug("No define of Sort_field") if ! defined $Sort_field{'none'};
@@ -1037,6 +1145,7 @@
 
 	# Prime sort routine
 	use locale;
+	local($^W);
 	sort { $routine } ('30','31') or 1;
 
 	@$target = sort { &$routine } @$target;



1.7.4.4   +1593 -495 interchange/lib/Vend/Server.pm


rev 1.7.4.4, prev_rev 1.7.4.3
Index: Server.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Server.pm,v
retrieving revision 1.7.4.3
retrieving revision 1.7.4.4
diff -u -r1.7.4.3 -r1.7.4.4
--- Server.pm	15 Apr 2001 13:57:52 -0000	1.7.4.3
+++ Server.pm	25 Jan 2003 22:21:28 -0000	1.7.4.4
@@ -1,14 +1,11 @@
-# Server.pm:  listen for cgi requests as a background server
+# Vend::Server - Listen for Interchange CGI requests as a background server
 #
-# $Id: Server.pm,v 1.7.4.3 2001/04/15 13:57:52 racke Exp $
+# $Id: Server.pm,v 1.7.4.4 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -28,61 +25,80 @@
 package Vend::Server;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.7.4.3 $, 10);
+$VERSION = substr(q$Revision: 1.7.4.4 $, 10);
 
 use POSIX qw(setsid strftime);
 use Vend::Util;
 use Fcntl;
+use Errno qw/:POSIX/;
 use Config;
 use Socket;
+use Symbol;
 use strict;
 
 sub new {
     my ($class, $fh, $env, $entity) = @_;
-	if(@Global::argv > 1) {
-		(
-			$CGI::script_name,
-			$CGI::values{mv_session_id}, 
-			$CGI::post_input
-		) = @Global::argv;
-		map_cgi();
-		$Global::FastMode = 1;
-		return bless { fh => $fh }, $class;
-	}
     populate($env);
     my $http = {
 					fh => $fh,
 					entity => $entity,
 					env => $env,
 				};
-	map_cgi($http);
+	eval {
+		map_cgi($http);
+	};
+	if($@) {
+		my $msg = errmsg("CGI mapping error: %s", $@);
+		::logGlobal({ level => 'error' }, $msg);
+		return undef;
+	}
     bless $http, $class;
 }
 
-my @Map =
-    (
-     'authorization' => 'AUTHORIZATION',
-     'content_length' => 'CONTENT_LENGTH',
-     'content_type' => 'CONTENT_TYPE',
-     'content_encoding' => 'HTTP_CONTENT_ENCODING',
-     'cookie' => 'HTTP_COOKIE',
-     'http_host' => 'HTTP_HOST',
-     'path_info' => 'PATH_INFO',
-     'path_translated' => 'PATH_TRANSLATED',
-     'pragma' => 'HTTP_PRAGMA',
-     'query_string' => 'QUERY_STRING',
-     'referer' => 'HTTP_REFERER',
-     'remote_addr' => 'REMOTE_ADDR',
-     'remote_host' => 'REMOTE_HOST',
-     'remote_user' => 'REMOTE_USER',
-     'request_method', => 'REQUEST_METHOD',
-     'script_name' => 'SCRIPT_NAME',
-     'secure' => 'HTTPS',
-     'server_name' => 'SERVER_NAME',
-     'server_host' => 'HTTP_HOST',
-     'server_port' => 'SERVER_PORT',
-     'useragent' => 'HTTP_USER_AGENT',
-);
+my @Map = qw/
+    authorization      AUTHORIZATION
+    content_length     CONTENT_LENGTH
+    content_type       CONTENT_TYPE
+    content_encoding   HTTP_CONTENT_ENCODING
+    cookie             HTTP_COOKIE
+    http_host          HTTP_HOST
+    path_info          PATH_INFO
+    pragma             HTTP_PRAGMA
+    query_string       QUERY_STRING
+    referer            HTTP_REFERER
+    remote_addr        REMOTE_ADDR
+    remote_host        REMOTE_HOST
+    remote_user        REMOTE_USER
+    request_method     REQUEST_METHOD
+    script_name        SCRIPT_NAME
+    secure             HTTPS
+    server_name        SERVER_NAME
+    server_host        HTTP_HOST
+    server_port        SERVER_PORT
+    useragent          HTTP_USER_AGENT
+/;
+
+my @RedirMap = qw/
+    path_info          REDIRECT_URL
+    query_string       REDIRECT_QUERY_STRING
+    error_notes        REDIRECT_ERROR_NOTES
+    redirect_status    REDIRECT_STATUS
+    request_method     REDIRECT_REQUEST_METHOD
+/;
+
+### This is to account for some bad Socket.pm implementations
+### which don't set SOMAXCONN, I think SCO is the big one
+
+my $SOMAXCONN;
+if(defined &SOMAXCONN) {
+	$SOMAXCONN = SOMAXCONN;
+}
+else {
+	$SOMAXCONN = 128;
+}
+
+###
+###
 
 sub populate {
     my ($cgivar) = @_;
@@ -100,6 +116,66 @@
         ${"CGI::$field"} = $cgivar->{$cgi} if defined $cgivar->{$cgi};
 #::logDebug("CGI::$field=" . ${"CGI::$field"});
     }
+
+	# try to get originating host's IP address if request was
+	# forwarded through a trusted proxy
+	my $ip;
+	if ($Global::TrustProxy
+		and ($CGI::remote_addr =~ $Global::TrustProxy
+			or $CGI::remote_host =~ $Global::TrustProxy)
+		and $ip = $cgivar->{HTTP_X_FORWARDED_FOR}) {
+		# trim off intermediate proxies in comma-separated list
+		$ip =~ s/,.*//;
+		$ip =~ s/^\s+//; $ip =~ s/\s+$//;
+		if ($ip =~ /^\d\d?\d?\.\d\d?\d?\.\d\d?\d?\.\d\d?\d?$/) {
+			$CGI::remote_addr = $ip;
+			undef $CGI::remote_host;
+		}
+		else {
+			::logGlobal(
+				{ level => 'info' },
+				"Unknown HTTP_X_FORWARDED_FOR header set from trusted proxy %s: '%s'",
+				$CGI::remote_addr,
+				$cgivar->{HTTP_X_FORWARDED_FOR},
+			);
+		}
+	}
+}
+
+sub log_http_data {
+	return unless $Global::Logging > 4;
+	my $ref = shift;
+	my @parms = split /\s+/,
+	 ($Global::Syslog->{http_items} ||
+		q{
+			REQUEST_URI
+			HTTP_COOKIE
+			SERVER_NAME
+			REMOTE_ADDR
+			HTTP_HOST
+			HTTP_USER_AGENT
+			REMOTE_USER
+		});
+	my $string = 'access: ';
+	for(@parms) {
+		next unless $ref->{env}{$_};
+		$string .= " $_=$ref->{env}{$_}";
+	}
+	::logGlobal( { level => 'info' }, $string);
+	return unless $Global::Logging > 5;
+	my $ent = $ref->{entity};
+	return unless $$ent;
+	::logGlobal( { level => 'debug' }, "POST=" . $$ent);
+	return;
+}
+
+sub map_misc_cgi {
+	$CGI::host = $CGI::remote_host || $CGI::remote_addr;
+	$CGI::user = $CGI::remote_user;
+
+	$CGI::script_path = $CGI::script_name;
+	$CGI::script_name = $CGI::server_host . $CGI::script_path
+		if $Global::FullUrl;
 }
 
 sub map_cgi {
@@ -107,27 +183,74 @@
     die "REQUEST_METHOD is not defined" unless defined $CGI::request_method
 		or @Global::argv;
 
-	if($h) {
-		$CGI::user = $CGI::remote_user;
-		$CGI::host = $CGI::remote_host || $CGI::remote_addr;
-
-		$CGI::script_path = $CGI::script_name;
-		$CGI::script_name = $CGI::server_host . $CGI::script_path
-			if $Global::FullUrl;
-		if ("\U$CGI::request_method" eq 'POST') {
-			$CGI::post_input = $h->{'entity'};
-		}
-		else {
-			$CGI::post_input = $CGI::query_string;
-		}
-	}
-	my $g = $Global::Selector{$CGI::script_name} || undef;
-	($::IV, $::VN, $::SV) = defined $g->{VarName}
+	map_misc_cgi() if $h;
+
+	my $g = $Global::Selector{$CGI::script_name}
+		or do {
+			my $msg = ::get_locale_message(
+						404,
+						"Undefined catalog: %s",
+						$CGI::script_name,
+						);
+			my $content_type = $msg =~ /<html/i ? 'text/html' : 'text/plain';
+			my $len = length($msg);
+			$Vend::StatusLine = <<EOF;
+Status: 404 Not found
+Content-Type: $content_type
+Content-Length: $len
+EOF
+			respond('', \$msg);
+			die($msg);
+		};
+
+	($::IV, $::VN, $::SV) = $g->{VarName}
 			? ($g->{IV}, $g->{VN}, $g->{IgnoreMultiple})
 			: ($Global::IV, $Global::VN, $Global::IgnoreMultiple);
-		
-	parse_post();
 
+	# Vend::ModPerl has already handled GET/POST parsing
+	return if $Global::mod_perl;
+
+#::logDebug("CGI::query_string=" . $CGI::query_string);
+#::logDebug("entity=" . ${$h->{entity}});
+
+	if ("\U$CGI::request_method" eq 'POST') {
+		parse_post(\$CGI::query_string)
+			if $Global::TolerateGet;
+		parse_post($h->{entity});
+	}
+	elsif ("\U$CGI::request_method" eq 'PUT') {
+#::logDebug("Put operation.");
+		parse_post(\$CGI::query_string);
+		$CGI::put_ref = $h->{entity};
+#::logDebug("Put contents: $$CGI::put_ref");
+		$$CGI::put_ref =~ s/^\s*--+\s+begin\s+content\s+--+\r?\n//i;
+		$$CGI::put_ref =~ s/^\r?\n--+\s+end\s+content\s+--+\s*$//i;
+	}
+	else {
+		 parse_post(\$CGI::query_string);
+	}
+
+	return if $CGI::values{mv_tmp_session};
+
+#::logDebug("Check robot UA=$Global::RobotUA IP=$Global::RobotIP");
+	if ($Global::RobotUA and $CGI::useragent =~ $Global::RobotUA) {
+#::logDebug("It is a robot by UA!");
+		$CGI::values{mv_tmp_session} = 1;
+	}
+	elsif ($Global::RobotIP and $CGI::remote_addr =~ $Global::RobotIP) {
+#::logDebug("It is a robot by IP!");
+		$CGI::values{mv_tmp_session} = 1;
+	}
+	elsif ($Global::HostnameLookups && $Global::RobotHost) {
+		if (!$CGI::remote_host && $CGI::remote_addr) {
+			$CGI::remote_host = gethostbyaddr(Socket::inet_aton($CGI::remote_addr),Socket::AF_INET);
+			$CGI::host = $CGI::remote_host || $CGI::remote_addr;
+		}
+		if ($CGI::remote_host && $CGI::remote_host =~ $Global::RobotHost) {
+#::logDebug("It is a robot by host!");
+			$CGI::values{mv_tmp_session} = 1;
+		}
+	}
 }
 
 # This is called by parse_multipart
@@ -146,20 +269,20 @@
 }
 
 sub parse_post {
+	my $sref = shift;
 	my(@pairs, $pair, $key, $value);
-	undef %CGI::values;
-	return unless defined $CGI::post_input;
+	return unless length $$sref;
 	if ($CGI::content_type =~ /^multipart/i) {
-		return parse_multipart() if  $CGI::useragent !~ /MSIE\s+5/i;
+		return parse_multipart($sref) if $CGI::useragent !~ /MSIE\s+5/i;
 		# try and work around an apparent IE5 bug that sends the content type
 		# of the next POST after a multipart/form POST as multipart also -
 		# even though it's sent as non-multipart data
 		# Contributed by Bill Randle
 		my ($boundary) = $CGI::content_type =~ /boundary=\"?([^\";]+)\"?/;
-		$boundary = "--$boundary";
-		return parse_multipart() if $CGI::post_input =~ /^\s*$boundary\s+/;
+		$boundary = '--' . quotemeta $boundary;
+		return parse_multipart($sref) if $$sref =~ /^\s*$boundary\s+/;
 	}
-	@pairs = split(/&/, $CGI::post_input);
+	@pairs = split($Global::UrlSplittor, $$sref);
 	if( defined $pairs[0] and $pairs[0] =~ /^	(\w{8,32})? ; /x)  {
 		@CGI::values{qw/ mv_session_id mv_arg mv_pc /}
 			= split /;/, $pairs[0], 3;
@@ -176,7 +299,18 @@
   	# This loop semi-duplicated in store_cgi_kv
 	foreach $pair (@pairs) {
 		($key, $value) = ($pair =~ m/([^=]+)=(.*)/)
-			or die "Syntax error in post input:\n$pair\n";
+			or do {
+				if ($Global::TolerateGet) {
+					$key = $pair;
+					$value = undef;
+				}
+				elsif($CGI::request_method =~ /^post$/i) {
+					die ::errmsg("Syntax error in POST input: %s\n%s", $pair, $$sref);
+				}
+				else {
+					die ::errmsg("Syntax error in GET input: %s\n", $pair);
+				}
+			};
 
 #::logDebug("incoming --> $key");
 		$key = $::IV->{$key} if defined $::IV->{$key};
@@ -195,7 +329,7 @@
 		}
 	}
 	if (! $redo and "\U$CGI::request_method" eq 'POST') {
-		@pairs = split(/&/, $CGI::query_string);
+		@pairs = split $Global::UrlSplittor, $CGI::query_string;
 		if( defined $pairs[0] and $pairs[0] =~ /^	(\w{8,32}) ; /x)  {
 			my (@old) = split /;/, $pairs[0], 3;
 			$CGI::values{mv_session_id} = $old[0]
@@ -213,17 +347,19 @@
 }
 
 sub parse_multipart {
+	my $sref = shift;
 	my ($boundary) = $CGI::content_type =~ /boundary=\"?([^\";]+)\"?/;
+	$boundary = quotemeta $boundary;
 #::logDebug("got to multipart");
 	# Stolen from CGI.pm, thanks Lincoln
 	$boundary = "--$boundary"
 		unless $CGI::useragent =~ /MSIE 3\.0[12];  Mac/i;
-	unless ($CGI::post_input =~ s/^\s*$boundary\s+//) {
-		die errmsg("multipart/form-data sent incorrectly\n");
+	unless ($$sref =~ s/^\s*$boundary\s+//) {
+		die ::errmsg("multipart/form-data sent incorrectly:\n%s\n", $$sref);
 	}
 
 	my @parts;
-	@parts = split /\r?\n$boundary/, $CGI::post_input;
+	@parts = split /\r?\n$boundary/, $$sref;
 	
 #::logDebug("multipart: " . scalar @parts . " parts");
 
@@ -248,7 +384,7 @@
 			my($filename) = $header{'Content-Disposition'}=~/ filename="?([^\";]*)"?/;
 #::logDebug("param='$param' filename='$filename'" );
 			if(! $param) {
-				::logGlobal({}, "unsupported multipart header: \n%s\n", $header);
+				::logGlobal({ level => 'debug' }, "unsupported multipart header: \n%s\n", $header);
 				next;
 			}
 
@@ -267,21 +403,29 @@
 
 sub create_cookie {
 	my($domain,$path) = @_;
-	my ($name, $value, $out, $expire, $cookie);
+	my  $out;
+	return '' if $Vend::tmp_session;
 	my @jar;
-	@jar = ['MV_SESSION_ID', $Vend::SessionName, $Vend::Expire || undef];
+	push @jar, [
+				($::Instance->{CookieName} || 'MV_SESSION_ID'),
+				defined $::Instance->{ClearCookie} ? '' : $Vend::SessionName,
+				$Vend::Expire || undef,
+			]
+		unless $Vend::CookieID;
 	push @jar, ['MV_STATIC', 1] if $Vend::Cfg->{Static};
 	push @jar, @{$::Instance->{Cookies}}
 		if defined $::Instance->{Cookies};
 	$out = '';
-	foreach $cookie (@jar) {
-		($name, $value, $expire) = @$cookie;
+	foreach my $cookie (@jar) {
+		my ($name, $value, $expire, $d, $p) = @$cookie;
+		$d = $domain if ! $d;
+		$p = $path   if ! $p;
 #::logDebug("create_cookie: name=$name value=$value expire=$expire");
 		$value = Vend::Interpolate::esc($value) 
 			if $value !~ /^[-\w:.]+$/;
 		$out .= "Set-Cookie: $name=$value;";
-		$out .= " path=$path;";
-		$out .= " domain=" . $domain . ";" if $domain;
+		$out .= " path=$p;";
+		$out .= " domain=" . $d . ";" if $d;
 		if (defined $expire or $Vend::Expire) {
 			my $expstring;
 			if(! $expire) {
@@ -306,20 +450,25 @@
 	$_ = shift;
 	s:^\s+::;
 	s:\s+$::;
-	s:\s*\n:\r\n:mg;
+	s:\s*\n\s*:\r\n:g;
 	return "$_\r\n";
 }
 
 sub respond {
 	# $body is now a reference
     my ($s, $body) = @_;
-
+#show_times("begin response send") if $Global::ShowTimes;
 	my $status;
+	return if $Vend::Sent;
 	if($Vend::StatusLine) {
 		$status = $Vend::StatusLine =~ /(?:^|\n)Status:\s+(.*)/i
 				? "$1"
 				: "200 OK";
 	}
+
+	$$body =~ s/^\s+//
+		if ! $Vend::ResponseMade and $::Pragma->{strip_white};
+
 	if(! $s and $Vend::StatusLine) {
 		$Vend::StatusLine = "HTTP/1.0 $status\r\n$Vend::StatusLine"
 			if defined $Vend::InternalHTTP
@@ -327,15 +476,17 @@
 		$Vend::StatusLine .= ($Vend::StatusLine =~ /^Content-Type:/im)
 							? '' : "\r\nContent-Type: text/html\r\n";
 # TRACK
-        $Vend::StatusLine .= "X-Track: " . $Vend::Track->header() . "\r\n";
+        $Vend::StatusLine .= "X-Track: " . $Vend::Track->header() . "\r\n"
+			if $Vend::Track;
 # END TRACK        
         $Vend::StatusLine .= "Pragma: no-cache\r\n"
 			if delete $::Scratch->{mv_no_cache};
-		print Vend::Server::MESSAGE canon_status($Vend::StatusLine);
-		print Vend::Server::MESSAGE "\r\n";
-		print Vend::Server::MESSAGE $$body;
+		print MESSAGE canon_status($Vend::StatusLine);
+		print MESSAGE "\r\n";
+		print MESSAGE $$body;
 		undef $Vend::StatusLine;
 		$Vend::ResponseMade = 1;
+#show_times("end response send") if $Global::ShowTimes;
 		return;
 	}
 
@@ -350,6 +501,7 @@
 
 	if($Vend::ResponseMade || $CGI::values{mv_no_header} ) {
 		print $fh $$body;
+#show_times("end response send") if $Global::ShowTimes;
 		return 1;
 	}
 
@@ -373,7 +525,7 @@
 		else { print $fh "HTTP/1.0 $status\r\n"; }
 	}
 
-	if ( (	! $CGI::cookie && ! $::Instance->{CookiesSet}
+	if ( (	! $Vend::CookieID && ! $::Instance->{CookiesSet}
 			or defined $Vend::Expire
 			or defined $::Instance->{Cookies}
 		  )
@@ -390,9 +542,9 @@
 		my @paths;
 		@paths = ('/');
 		if($Global::Mall) {
-			my $ref = $Global::Catalog{$Vend::Cfg->{CatalogName}};
-			@paths = ($ref->{'script'});
-			push (@paths, @{$ref->{'alias'}}) if defined $ref->{'alias'};
+			my $ref = $Global::Catalog{$Vend::Cat};
+			@paths = ($ref->{script});
+			push (@paths, @{$ref->{alias}}) if defined $ref->{alias};
 			if ($Global::FullUrl) {
 				# remove domain from script
 				for (@paths) { s:^[^/]+/:/: ; }
@@ -414,27 +566,27 @@
 	elsif(! $Vend::ResponseMade) {        
 		print $fh canon_status("Content-Type: text/html");
 # TRACK        
-        print $fh canon_status("X-Track: " . $Vend::Track->header() . "\r\n");
+        print $fh canon_status("X-Track: " . $Vend::Track->header())
+			if $Vend::Track;
 # END TRACK
 	}
+	print $fh canon_status("Pragma: no-cache")
+		if delete $::Scratch->{mv_no_cache};
 
     print $fh "\r\n";
     print $fh $$body;
+#show_times("end response send") if $Global::ShowTimes;
     $Vend::ResponseMade = 1;
 }
 
-sub read_entity_body {
-    my ($s) = @_;
-    $s->{entity};
-}
-
 sub _read {
-    my ($in) = @_;
+    my ($in, $fh) = @_;
+	$fh = \*MESSAGE if ! $fh;
     my ($r);
     
     do {
-        $r = sysread(Vend::Server::MESSAGE, $$in, 512, length($$in));
-    } while (!defined $r and $! =~ m/^Interrupted/);
+        $r = sysread($fh, $$in, 512, length($$in));
+    } while (!defined $r and $!{eintr});
     die "read: $!" unless defined $r;
     die "read: closed" unless $r > 0;
 }
@@ -460,10 +612,7 @@
 
 my $HTTP_enabled;
 my $Remote_addr;
-my $Remote_host;
 my %CGImap;
-my %CGIspecial;
-my %MIME_type;
 
 BEGIN {
 	eval {
@@ -502,22 +651,9 @@
 
 					/
 		);
-		%CGIspecial = ();
-
-		%MIME_type = (qw|
-							jpg		image/jpeg
-							gif		image/gif
-							JPG		image/jpeg
-							GIF		image/gif
-							JPEG	image/jpeg
-							jpeg	image/jpeg
-							htm		text/html
-							html	text/html
-						|
-		);
 	};
-										 
-}                                    
+
+}
 
 sub http_log_msg {
 	my($status, $env, $request) = @_;
@@ -538,15 +674,17 @@
 	return join " ", @params;
 }
 
-sub http_server {
-	my($status_line, $in, $argv, $env, $entity) = @_;
+sub http_soap {
+	my($fh, $env, $entity) = @_;
 
+	my $in = '';
 	die "Need URI::URL for this functionality.\n"
 		unless defined $HTTP_enabled;
 
-	$Vend::InternalHTTP = 1;
-	my ($header, $request, $block);
+	my ($real_header, $header, $request, $block);
 	my $waiting = 0;
+	my $status_line = _find(\$in, "\n");
+#::logDebug("status_line: $status_line");
 	($$env{REQUEST_METHOD},$request) = split /\s+/, $status_line;
 	for(;;) {
         $block = _find(\$in, "\n");
@@ -556,14 +694,14 @@
 			last;
 		}
 		if ( $block =~ s/^([^:]+):\s*//) {
+			$real_header = $1;
 			$header = lc $1;
+			
 			if(defined $CGImap{$header}) {
+#::logDebug("setting env{$CGImap{$header}} to: $block");
 				$$env{$CGImap{$header}} = $block;
 			}
-			elsif(defined $CGIspecial{$header}) {
-				&{$CGIspecial{$header}}($env, $block);
-			}
-			# else { throw_away() }
+			$$env{$real_header} = $block;
 			next;
 		}
 		else {
@@ -574,93 +712,56 @@
 
 	if ($$env{CONTENT_LENGTH}) {
 		_read(\$in) while length($in) < $$env{CONTENT_LENGTH};
+#::logDebug("read entity: $in");
 	}
 	$in =~ s/\s+$//;
 	$$entity = $in;
 
 #::logDebug("exiting loop");
 	my $url = new URI::URL $request;
-	@{$argv} = $url->keywords();
 
 	(undef, $Remote_addr) =
-				sockaddr_in(getpeername(Vend::Server::MESSAGE));
+				sockaddr_in(getpeername($fh));
 	$$env{REMOTE_HOST} = gethostbyaddr($Remote_addr, AF_INET);
 	$Remote_addr = inet_ntoa($Remote_addr);
 
-	$$env{QUERY_STRING} = $url->equery();
 	$$env{REMOTE_ADDR} = $Remote_addr;
 
 	my (@path) = $url->path_components();
-	my $path = $url->path();
 	my $doc;
 	my $status = 200;
 
 	shift(@path);
-	my $cat = "/" . shift(@path);
+	my $catname = '/'.shift(@path);
+	$$env{SESSION_ID} = shift(@path);
 
-	if ($Global::TcpMap->{$Global::TcpPort} =~ /^\w+/) {
-		$cat = $Global::TcpMap->{$Global::TcpPort};
-		$cat = "/$cat" unless index($cat, '/') == 0;
-	}
+#::logDebug("catname is $catname");
 
-	if($cat eq '/mv_admin') {
-#::logDebug("found mv_admin");
+	if($Global::Selector{$catname} and $Global::AllowGlobal->{$catname}) {
 		if ($$env{AUTHORIZATION}) {
 			$$env{REMOTE_USER} =
 					Vend::Util::check_authorization( delete $$env{AUTHORIZATION} );
 		}
-		if (! $$env{REMOTE_USER}) {
-			$Vend::StatusLine = <<EOF;
-HTTP/1.0 401 Unauthorized
-WWW-Authenticate: Basic realm="Interchange Admin"
-EOF
-			$doc = "Requires correct username and password.\n";
-			$path = '';
-		}
-	}
-
-	if($Global::Selector{$cat} || $Global::SelectorAlias{$cat}) {
-#::logDebug("found direct catalog $cat");
-		$$env{SCRIPT_NAME} = $cat;
-		$$env{PATH_INFO} = join "/", '', @path;
-	}
-	elsif(-f "$Global::VendRoot/doc$path") {
-#::logDebug("found doc file");
-		$Vend::StatusLine = "HTTP/1.0 200 OK";
-		$doc = readfile("$Global::VendRoot/doc$path");
-	}
-	else {
-#::logDebug("not found");
-		$status = 404;
-		$Vend::StatusLine = "HTTP/1.0 404 Not found";
-		$doc = "$path not a Interchange catalog or help file.\n";
+		return undef if ! $$env{REMOTE_USER};
 	}
 
-	if($$env{REQUEST_METHOD} eq 'HEAD') {
-		$Vend::StatusLine = "HTTP/1.0 200 OK\nLast-modified: "
-			. Vend::Util::logtime;
-		$doc = '';
+	my $ref;
+	if($ref = $Global::Selector{$catname} || $Global::SelectorAlias{$catname}) {
+#::logDebug("found catalog $catname");
+		$$env{SCRIPT_NAME} = $catname;
 	}
 
 	logData("$Global::VendRoot/etc/access_log",
 			http_log_msg(
-						$status,
+						"SOAP$status",
 						$env,
 						($$env{REQUEST_METHOD} .  " " .  $request),
 						)
 		);
 
-	if (defined $doc) {
-		$path =~ /\.([^.]+)$/;
-		$Vend::StatusLine = '' unless defined $Vend::StatusLine;
-		$Vend::StatusLine .= "\r\nContent-type: " . ($MIME_type{$1} || "text/plain");
-		respond(
-					'',
-					\$doc,
-				);
-		return;
-	}
-	return 1;
+	populate($env);
+	map_misc_cgi();
+	return $ref;
 }
 
 sub read_cgi_data {
@@ -670,29 +771,27 @@
 
     for (;;) {
         $block = _find(\$in, "\n");
-        if ($block =~ m/^[GPH]/) {
-           	return http_server($block, $in, @_);
-		}
-		elsif ($block =~ s/^ipc ([-\w]+)$//) {
-			my $cat = $1;
-		}
-		elsif (($n) = ($block =~ m/^arg (\d+)$/)) {
-            $#$argv = $n - 1;
-            foreach $i (0 .. $n - 1) {
-                $$argv[$i] = _string(\$in);
-            }
-        } elsif (($n) = ($block =~ m/^env (\d+)$/)) {
+		if (($n) = ($block =~ m/^env (\d+)$/)) {
             foreach $i (0 .. $n - 1) {
                 $e = _string(\$in);
                 if (($key, $value) = ($e =~ m/^([^=]+)=(.*)$/s)) {
                     $$env{$key} = $value;
                 }
             }
-        } elsif ($block =~ m/^entity$/) {
-            $$entity = _string(\$in);
-        } elsif ($block =~ m/^end$/) {
+        }
+		elsif ($block =~ m/^end$/) {
             last;
-        } else {
+        }
+		elsif ($block =~ m/^entity$/) {
+            $$entity = _string(\$in);
+		}
+		elsif (($n) = ($block =~ m/^arg (\d+)$/)) {
+            $#$argv = $n - 1;
+            foreach $i (0 .. $n - 1) {
+                $$argv[$i] = _string(\$in);
+            }
+        }
+		else {
 			die "Unrecognized block: $block\n";
         }
     }
@@ -707,28 +806,70 @@
 	return 1;
 }
 
+
 sub connection {
     my (%env, $entity);
-    my $http;
-#::logDebug ("begin connection: " . (join " ", times()) . "\n");
+
+  ### This resets all $Vend::variable settings so we start
+  ### completely initialized. It only affects the Vend package,
+  ### not any Vend::XXX packages.
+	reset_vars();
+
+	if($Global::ShowTimes) {
+		@Vend::Times = times();
+		::logDebug ("begin connection. Summary time set to zero");
+	}
     read_cgi_data(\@Global::argv, \%env, \$entity)
     	or return 0;
-	$http = new Vend::Server \*Vend::Server::MESSAGE, \%env, $entity;
-#::logGlobal ("begin dispatch: " . (join " ", times()) . "\n");
-    ::dispatch($http);
-#::logDebug ("end connection: " . (join " ", times()) . "\n");
-	undef $Vend::ResponseMade;
-	undef $Vend::InternalHTTP;
+    show_times('end cgi read') if $Global::ShowTimes;
+
+    my $http = new Vend::Server \*MESSAGE, \%env, \$entity;
+
+	# Can log all CGI inputs
+	log_http_data($http) if $Global::Logging;
+
+	show_times("begin dispatch") if $Global::ShowTimes;
+    ::dispatch($http) if $http;
+	show_times("end connection") if $Global::ShowTimes;
+	undef $Vend::Cfg;
 }
 
 ## Signals
 
 my $Signal_Terminate;
-my $Signal_Debug;
 my $Signal_Restart;
 my %orig_signal;
 my @trapped_signals = qw(INT TERM);
-$Vend::Server::Num_servers = 0;
+
+
+my $ipc;
+my $tick;
+
+my %fh_map;
+my %vec_map;
+
+my %s_vec_map;
+my %s_fh_map;
+
+my %ipc_socket;
+my %unix_socket;
+
+use vars qw(
+			$Num_servers
+			$Page_servers
+			%Page_pids
+			$SOAP_servers
+			%SOAP_pids
+			$vector
+			$p_vector
+			$s_vector
+			$ipc_vector
+			);
+BEGIN {
+	$s_vector = '';
+}
+$Num_servers = 0;
+$SOAP_servers = 0;
 
 # might also trap: QUIT
 
@@ -737,18 +878,43 @@
 
 unless ($Global::Windows) {
 	push @trapped_signals, qw(HUP USR1 USR2);
-	$Routine_USR1 = sub { $SIG{USR1} = $Routine_USR1; $Vend::Server::Num_servers++};
-	$Routine_USR2 = sub { $SIG{USR2} = $Routine_USR2; $Vend::Server::Num_servers--};
+	$Routine_USR1 = sub { $SIG{USR1} = $Routine_USR1; $Num_servers++};
+	$Routine_USR2 = sub { $SIG{USR2} = $Routine_USR2; $Num_servers--};
 	$Routine_HUP  = sub { $SIG{HUP} = $Routine_HUP; $Signal_Restart = 1};
 }
 
 $Routine_TERM = sub { $SIG{TERM} = $Routine_TERM; $Signal_Terminate = 1 };
 $Routine_INT  = sub { $SIG{INT} = $Routine_INT; $Signal_Terminate = 1 };
 
+sub reset_vars {
+	package Vend;
+	reset 'A-Z';
+	reset 'a-z';
+	package CGI;
+	reset 'A-Z';
+	reset 'a-z';
+	srand();
+#::logDebug("Reset vars");
+}
+
+sub reset_per_fork {
+	%Vend::Table::DBI::DBI_connect_cache = ();
+	%Vend::Table::DBI::DBI_connect_bad = ();
+}
+
+sub clean_up_after_fork {
+	for(values %Vend::Table::DBI::DBI_connect_cache) {
+		next if ! ref $_;
+		$_->disconnect();
+	}
+	%Vend::Table::DBI::DBI_connect_cache = ();
+	%Vend::Table::DBI::DBI_connect_bad = ();
+}
+
 sub setup_signals {
     @orig_signal{@trapped_signals} =
         map(defined $_ ? $_ : 'DEFAULT', @SIG{@trapped_signals});
-    $Signal_Terminate = $Signal_Debug = '';
+    $Signal_Terminate = '';
     $SIG{PIPE} = 'IGNORE';
 
 	if ($Global::Windows) {
@@ -759,8 +925,8 @@
 		$SIG{INT}  = sub { $Signal_Terminate = 1; };
 		$SIG{TERM} = sub { $Signal_Terminate = 1; };
 		$SIG{HUP}  = sub { $Signal_Restart = 1; };
-		$SIG{USR1} = sub { $Vend::Server::Num_servers++; };
-		$SIG{USR2} = sub { $Vend::Server::Num_servers--; };
+		$SIG{USR1} = sub { $Num_servers++; };
+		$SIG{USR2} = sub { $Num_servers--; };
 	}
 
 	if(! $Global::MaxServers) {
@@ -782,36 +948,79 @@
 # Reconfigure any catalogs that have requested it, and 
 # check to make sure we haven't too many running servers
 sub housekeeping {
-	my ($tick) = @_;
+	my ($interval) = @_;
 	my $now = time;
-	rand();
 
-	return if defined $tick and ($now - $Last_housekeeping < $tick);
+#::logDebug("called housekeeping");
+	return if defined $interval and ($now - $Last_housekeeping < $interval);
 
+#::logDebug("actually doing housekeeping interval=$interval now=$now last=$Last_housekeeping");
+	rand();
 	$Last_housekeeping = $now;
 
 	my ($c, $num,$reconfig, $restart, @files);
 	my @pids;
 
-		opendir(Vend::Server::CHECKRUN, $Global::ConfDir)
-			or die "opendir $Global::ConfDir: $!\n";
+		if($Global::PreFork) {
+			my @bad_pids;
+			my (@pids) = sort keys %Page_pids;
+			my $count = scalar @pids;
+			while ($count > ($Global::StartServers + 1) ) {
+#::logDebug("too many pids");
+				my ($bad) = shift(@pids);
+#::logDebug("scheduling %s for death", $bad);
+				push @bad_pids, $bad;
+				$count--;
+			}
+
+			foreach my $pid (@pids) {
+				kill(0, $pid) and next;
+#::logDebug("Unresponsive server at PID %s", $pid);
+				push @bad_pids, $pid;
+			}
+
+			while($count < $Global::StartServers) {
+#::logDebug("Spawning page server to reach StartServers");
+				start_page(undef,$Global::PreFork,1);
+				$count++;
+			}
+			for my $pid (@bad_pids) {
+#::logDebug("Killing excess or unresponsive server at PID %s", $pid);
+				if(kill 'TERM', $pid) {
+#::logDebug("Server at PID %s terminated OK", $pid);
+					# This is OK
+				}
+				elsif (kill 'TERM', $pid) {
+					::logGlobal("page server pid %s required KILL", $pid);
+				}
+				else {
+					::logGlobal("page server pid %s won't die!", $pid);
+				}
+				delete $Page_pids{$pid};
+			}
+		}
+
+		opendir(Vend::Server::CHECKRUN, $Global::RunDir)
+			or die "opendir $Global::RunDir: $!\n";
 		@files = readdir Vend::Server::CHECKRUN;
 		closedir(Vend::Server::CHECKRUN)
-			or die "closedir $Global::ConfDir: $!\n";
+			or die "closedir $Global::RunDir: $!\n";
 		($reconfig) = grep $_ eq 'reconfig', @files;
 		($restart) = grep $_ eq 'restart', @files
 			if $Signal_Restart || $Global::Windows;
 		if($Global::PIDcheck) {
-			$Vend::Server::Num_servers = 0;
+			$Num_servers = 0;
 			@pids = grep /^pid\.\d+$/, @files;
 		}
-		#scalar grep($_ eq 'stop_the_server', @files) and exit;
+
+		my $respawn;
+
 		if (defined $restart) {
 			$Signal_Restart = 0;
-			open(Vend::Server::RESTART, "+<$Global::ConfDir/restart")
-				or die "open $Global::ConfDir/restart: $!\n";
+			open(Vend::Server::RESTART, "+<$Global::RunDir/restart")
+				or die "open $Global::RunDir/restart: $!\n";
 			lockfile(\*Vend::Server::RESTART, 1, 1)
-				or die "lock $Global::ConfDir/restart: $!\n";
+				or die "lock $Global::RunDir/restart: $!\n";
 			while(<Vend::Server::RESTART>) {
 				chomp;
 				my ($directive,$value) = split /\s+/, $_, 2;
@@ -819,7 +1028,7 @@
 					my $mark = $1;
 					$value = Vend::Config::read_here(\*Vend::Server::RESTART, $mark);
 					unless (defined $value) {
-						::logGlobal({}, <<EOF, $mark);
+						::logGlobal({ level => 'notice'}, <<EOF, $mark);
 Global reconfig ERROR
 Can't find string terminator "%s" anywhere before EOF.
 EOF
@@ -838,48 +1047,62 @@
 					{
 						::remove_catalog($1);
 					}
+					elsif( $directive =~ /^cron$/i) {
+						my ($cat, @jobs) = grep /\S/, split /[\s,\0]+/, $value;
+#::logGlobal("restart line found value='$value'");
+						run_cron($cat, @jobs);
+					}
 					else {
 						::change_global_directive($directive, $value);
 					}
 				};
 				if($@) {
-					::logGlobal({}, $@);
+					::logGlobal({ level => 'notice' }, $@);
 					last;
 				}
 			}
 			unlockfile(\*Vend::Server::RESTART)
-				or die "unlock $Global::ConfDir/restart: $!\n";
+				or die "unlock $Global::RunDir/restart: $!\n";
 			close(Vend::Server::RESTART)
-				or die "close $Global::ConfDir/restart: $!\n";
-			unlink "$Global::ConfDir/restart"
-				or die "unlink $Global::ConfDir/restart: $!\n";
+				or die "close $Global::RunDir/restart: $!\n";
+			unlink "$Global::RunDir/restart"
+				or die "unlink $Global::RunDir/restart: $!\n";
+			$respawn = 1;
 		}
 		if (defined $reconfig) {
-			open(Vend::Server::RECONFIG, "+<$Global::ConfDir/reconfig")
-				or die "open $Global::ConfDir/reconfig: $!\n";
+			open(Vend::Server::RECONFIG, "+<$Global::RunDir/reconfig")
+				or die "open $Global::RunDir/reconfig: $!\n";
 			lockfile(\*Vend::Server::RECONFIG, 1, 1)
-				or die "lock $Global::ConfDir/reconfig: $!\n";
+				or die "lock $Global::RunDir/reconfig: $!\n";
 			while(<Vend::Server::RECONFIG>) {
 				chomp;
-				my ($script_name,$build) = split /\s+/, $_;
+				my ($script_name,$table,$cfile) = split /\s+/, $_, 3;
 				my $select = $Global::SelectorAlias{$script_name} || $script_name;
                 my $cat = $Global::Selector{$select};
                 unless (defined $cat) {
-                    ::logGlobal({}, "Bad script name '%s' for reconfig." , $script_name );
+                    ::logGlobal({ level => 'notice' }, "Bad script name '%s' for reconfig." , $script_name );
                     next;
                 }
-				$c = ::config_named_catalog($cat->{CatalogName},
-                                    "from running server ($$)", $build);
+
+				eval {
+					$c = Vend::Config::config_named_catalog(
+									$cat->{CatalogName},
+                                    "from running server ($$)",
+									$table,
+									$cfile
+								);
+				};
+
 				if (defined $c) {
 					$Global::Selector{$select} = $c;
 					for(sort keys %Global::SelectorAlias) {
 						next unless $Global::SelectorAlias{$_} eq $select;
 						$Global::Selector{$_} = $c;
 					}
-					::logGlobal({}, "Reconfig of %s successful.", $c->{CatalogName});
+					::logGlobal({ level => 'notice' }, "Reconfig of %s successful.", $c->{CatalogName});
 				}
 				else {
-					::logGlobal({},
+					::logGlobal({ level => 'warn' },
 						 "Error reconfiguring catalog %s from running server (%s)\n%s",
 						 $script_name,
 						 $$,
@@ -888,34 +1111,76 @@
 				}
 			}
 			unlockfile(\*Vend::Server::RECONFIG)
-				or die "unlock $Global::ConfDir/reconfig: $!\n";
+				or die "unlock $Global::RunDir/reconfig: $!\n";
 			close(Vend::Server::RECONFIG)
-				or die "close $Global::ConfDir/reconfig: $!\n";
-			unlink "$Global::ConfDir/reconfig"
-				or die "unlink $Global::ConfDir/reconfig: $!\n";
+				or die "close $Global::RunDir/reconfig: $!\n";
+			unlink "$Global::RunDir/reconfig"
+				or die "unlink $Global::RunDir/reconfig: $!\n";
+			$respawn = 1;
+			
 		}
+
+		if($respawn) {
+			if($Global::PreFork) {
+				# We need to respawn all the servers to pick up the new config
+				my @pids = keys %Page_pids;
+				for(@pids) {
+					::logGlobal(
+						{ level => 'info' },
+						"respawning page server pid %s to pick up config change",
+						$_,
+					);
+					(kill 'TERM', $_ and delete $Page_pids{$_})
+						or ::logGlobal(
+								"page server pid %s won't terminate: %s",
+								$_,
+								$!,
+							);
+					start_page(undef,$Global::PreFork,1);
+				}
+			}
+			if($Global::SOAP) {
+				# We need to respawn all the SOAP servers to pick up the new config
+				my @pids = keys %SOAP_pids;
+				for(@pids) {
+					::logGlobal(
+						{ level => 'info' },
+						"respawning SOAP server pid %s to pick up config change",
+						$_,
+					);
+					(kill 'TERM', $_ and delete $SOAP_pids{$_})
+						or ::logGlobal(
+								"SOAP server pid %s won't terminate: %s",
+								$_,
+								$!,
+							);
+					start_soap(undef,1);
+				}
+			}
+		}
+
         for (@pids) {
-            $Vend::Server::Num_servers++;
-            my $fn = "$Global::ConfDir/$_";
-            ($Vend::Server::Num_servers--, next) if ! -f $fn;
+            $Num_servers++;
+            my $fn = "$Global::RunDir/$_";
+            ($Num_servers--, next) if ! -f $fn;
             my $runtime = $now - (stat(_))[9];
             next if $runtime < $Global::PIDcheck;
             s/^pid\.//;
             if(kill 9, $_) {
-                unlink $fn and $Vend::Server::Num_servers--;
-                ::logGlobal({}, "hammered PID %s running %s seconds", $_, $runtime);
+                unlink $fn and $Num_servers--;
+                ::logGlobal({ level => 'error' }, "hammered PID %s running %s seconds", $_, $runtime);
             }
             elsif (! kill 0, $_) {
-				unlink $fn and $Vend::Server::Num_servers--;
-                ::logGlobal({},
+				unlink $fn and $Num_servers--;
+                ::logGlobal({ level => 'error' },
 					"Spurious PID file for process %s supposedly running %s seconds",
 						$_,
 						$runtime,
 				);
 			}
             else {
-				unlink $fn and $Vend::Server::Num_servers--;
-                ::logGlobal({},
+				unlink $fn and $Num_servers--;
+                ::logGlobal({ level => 'crit' },
 					"PID %s running %s seconds would not die!",
 						$_,
 						$runtime,
@@ -926,272 +1191,965 @@
 
 }
 
-# The servers for both are now combined
-# Can have both INET and UNIX on same system
-sub server_both {
-    my ($socket_filename) = @_;
-    my ($n, $rin, $rout, $pid, $tick);
-
-	$Vend::MasterProcess = $$;
-
-	$tick        = $Global::HouseKeeping || 60;
-
-    setup_signals();
+sub server_start_message {
+	my ($fmt, $reverse) = @_;
+	$fmt = 'START server (%s) (%s)' unless $fmt; 
+	my @types;
+	push (@types, 'INET') if $Global::Inet_Mode;
+	push (@types, 'UNIX') if $Global::Unix_Mode;
+	push (@types, 'SOAP') if $Global::SOAP;
+	push (@types, 'mod_perl') if $Global::mod_perl;
+	my $server_type = join(" and ", @types);
+	my $pid = read_pidfile();
+	my @args = $reverse ? ($server_type, $pid) : ($pid, $server_type);
+	return ::errmsg ($fmt , @args );
+}
 
-	my ($host, $port);
-	if($Global::Inet_Mode) {
-		$host = $Global::TcpHost || '127.0.0.1';
-		my @hosts;
-		$Global::TcpHost =~ s/\./\\./g;
-		$Global::TcpHost =~ s/\*/\\S+/g;
-		@hosts = grep /\S/, split /\s+/, $Global::TcpHost;
-		$Global::TcpHost = join "|", @hosts;
-		::logGlobal({}, "Accepting connections from %s", $Global::TcpHost);
-	}
+sub map_unix_socket {
+	my ($vec, $vec_map, $fh_map, @files) = @_;
 
-	my $proto = getprotobyname('tcp');
+	my @made;
 
-#::logDebug("Starting server socket file='$socket_filename' tcpport=$port hosts='$host'\n");
-	unlink $socket_filename;
+	foreach my $sockfn (@files) {
+		my $fh = gensym();
 
-	my $vector = '';
-	my $spawn;
+#::logDebug("starting to parse file socket $sockfn, fh created: $fh");
 
-	my $so_max;
-	if(defined &SOMAXCONN) {
-		$so_max = SOMAXCONN;
-	}
-	else {
-		$so_max = 128;
-	}
+		eval {
+			socket($fh, AF_UNIX, SOCK_STREAM, 0) || die "socket: $!";
 
-	unlink "$Global::ConfDir/mode.inet", "$Global::ConfDir/mode.unix";
+			setsockopt($fh, SOL_SOCKET, SO_REUSEADDR, pack("l", 1));
 
-	if($Global::Unix_Mode) {
-		socket(Vend::Server::USOCKET, AF_UNIX, SOCK_STREAM, 0) || die "socket: $!";
-
-		setsockopt(Vend::Server::USOCKET, SOL_SOCKET, SO_REUSEADDR, pack("l", 1));
+			bind($fh, pack("S", AF_UNIX) . $sockfn . chr(0))
+				or die "Could not bind (open as a socket) '$sockfn':\n$!\n";
+			listen($fh,$SOMAXCONN) or die "listen: $!";
+		};
 
-		bind(Vend::Server::USOCKET, pack("S", AF_UNIX) . $socket_filename . chr(0))
-			or die "Could not bind (open as a socket) '$socket_filename':\n$!\n";
-		listen(Vend::Server::USOCKET,$so_max) or die "listen: $!";
-
-		$rin = '';
-		vec($rin, fileno(Vend::Server::USOCKET), 1) = 1;
-		$vector |= $rin;
-		open(Vend::Server::INET_MODE_INDICATOR, ">$Global::ConfDir/mode.unix")
-			or die "creat $Global::ConfDir/mode.unix: $!";
-		close(Vend::Server::INET_MODE_INDICATOR);
-
-		chmod $Global::SocketPerms, $socket_filename;
-		if($Global::SocketPerms & 077) {
-			::logGlobal({},
-							"ALERT: %s socket permissions are insecure; are you sure you want permssions %o?",
-							$Global::SocketFile,
-							$Global::SocketPerms,
-						);
+		if($@) {
+			::logGlobal({ level => 'error' }, 
+					"Could not bind to UNIX socket file %s: %s",
+					$sockfn,
+					$!,
+				  );
+			next;
 		}
-	}
 
-	use Symbol;
-	my %fh_map;
-	my %vec_map;
-	my $made_at_least_one;
+#::logDebug("made socket $sockfn");
+		my $rin = '';
+		vec($rin, fileno($fh), 1) = 1;
+		$$vec |= $rin;
+		$vec_map->{$sockfn} = fileno($fh);
+		$fh_map->{$sockfn} = $fh;
+		push @made, $sockfn;
+	}
+	return @made;
+}
 
-	my @types;
-	push (@types, 'INET') if $Global::Inet_Mode;
-	push (@types, 'UNIX') if $Global::Unix_Mode;
-	my $server_type = join(" and ", @types);
-	::logGlobal({}, "START server (%s) (%s)" , $$, $server_type );
+sub map_inet_socket {
+	my ($vec, $vec_map, $fh_map, @ports) = @_;
 
-	if($Global::Inet_Mode) {
+	my $proto = getprotobyname('tcp');
+	my @made;
 
-	  foreach $port (keys %{$Global::TcpMap}) {
+	for(@ports) {
 		my $fh = gensym();
 		my $bind_addr;
+		my $bind_port;
 		my $bind_ip;
-#::logDebug("starting to parse port $port, fh created: $fh");
-		if ($port =~ s/^([-\w.]+):(\d+)$/$2/) {
+#::logDebug("starting to parse port $_, fh created: $fh");
+		if (/^([-\w.]+):(\d+)$/) {
 			$bind_ip  = $1;
+			$bind_port = $2;
 			$bind_addr = inet_aton($bind_ip);
 		}
-		else {
+		elsif (/^\d+$/) {
 			$bind_ip  = '0.0.0.0';
 			$bind_addr = INADDR_ANY;
+			$bind_port = $_;
 		}
-#::logDebug("Trying to run server on ip=$bind_ip port=$port");
-	    if(! $bind_addr) {
-			::logGlobal({},
+		else {
+			::logGlobal({ level => 'error' }, 
+					"Unrecognized port type '%s'",
+					$bind_port,
+					$!,
+				  );
+		}
+#::logDebug("Trying to run server on ip=$bind_ip port=$bind_port");
+		if(! $bind_addr) {
+			::logGlobal({ level => 'error' }, 
 					"Could not bind to IP address %s on port %s: %s",
 					$bind_ip,
-					$port,
+					$bind_port,
 					$!,
 				  );
-			next;
+			return undef;
 		}
 		eval {
 			socket($fh, PF_INET, SOCK_STREAM, $proto)
 					|| die "socket: $!";
 			setsockopt($fh, SOL_SOCKET, SO_REUSEADDR, pack("l", 1))
 					|| die "setsockopt: $!";
-			bind($fh, sockaddr_in($port, $bind_addr))
+			bind($fh, sockaddr_in($bind_port, $bind_addr))
 					|| die "bind: $!";
-			listen($fh,$so_max)
+			listen($fh,$SOMAXCONN)
 					|| die "listen: $!";
-			$made_at_least_one = 1;
 		};
 
-
-		if (! $@) {
-			$rin = '';
-			vec($rin, fileno($fh), 1) = 1;
-			$vector |= $rin;
-			$vec_map{"$bind_ip:$port"} = fileno($fh);
-			$fh_map{"$bind_ip:$port"} = $fh;
-		}
-		else {
-		  ::logGlobal({},
+		if ($@) {
+		  ::logGlobal({ level => 'error' },
 					"INET mode server failed to start on port %s: %s",
-					$port,
+					$bind_port,
 					$@,
 				  );
+		  next;
+		}
+
+		my $rin = '';
+		vec($rin, fileno($fh), 1) = 1;
+		$$vec |= $rin;
+		my $port_ptr = "$bind_ip:$bind_port"; 
+		$vec_map->{$port_ptr} = fileno($fh);
+		$fh_map->{$port_ptr} = $fh;
+		push @made, $port_ptr;
+#::logDebug( "Made port $bind_ip:$bind_port\n");
+	}
+	return @made;
+}
+
+sub create_host_pattern {
+		my $host = shift;
+		my @hosts = grep /\S/, split /[,\s\|]+/, $host;
+		for (@hosts) {
+			s/\./\\./g;
+			s/\*/[-\\w.]+/g;
+		}
+		return join "|", @hosts;
+}
+
+sub unlink_sockets {
+	my @to_unlink;
+	for (@_) {
+		if(ref($_)) {
+			push @to_unlink, @$_;
+		}
+		else {
+			push @to_unlink, $_;
+		}
+	}
+	
+	for(@to_unlink) {
+		unlink $_ if -S $_;
+		if(-S $_) {
+			unlink $_ 
+				or 
+				::logGlobal(
+					{level => 'error'},
+					"Socket file %s cannot be unlinked: %s",
+					$_,
+					$!,
+				);
+		}
+		elsif(-e _) {
+			::logGlobal(
+				{level => 'error'},
+				"Socket file %s exists and is not a socket, possible error",
+				$_,
+			);
+		}
+	}
+}
+
+sub start_page {
+
+	my ($do_message, $no_fork, $number) = @_;
+#::logDebug("starting soap");
+
+	$number = $Global::StartServers if ! $number; 
+	if ($number > 50) {
+		  die ::errmsg(
+		   "Ridiculously large number of StartServers: %s",
+		   $number,
+		   );
+	}
+	for (1 .. $number) {
+		my $pid;
+		if(! defined ($pid = fork) ) {
+			my $msg = ::errmsg("Can't fork: %s", $!);
+			::logGlobal({ level => 'crit' },  $msg );
+			die ("$msg\n");
+		}
+		elsif (! $pid) {
+			unless( $pid = fork ) {
+				$Global::Foreground = 1 if $no_fork;
+
+				if($do_message) {
+					::logGlobal(
+						{ level => 'info'},
+						server_start_message(
+							"Interchange page server started (process id %s)",
+						 ),
+					 ) unless $Vend::Quiet;
+				}
+
+				send_ipc("register page $$");
+
+				my $next;
+				$::Instance = {};
+
+				reset_per_fork();
+				eval { 
+					$next = server_page($no_fork);
+				};
+				if ($@) {
+					my $msg = ::errmsg("Server spawn error: %s", $@);
+					::logGlobal({ level => 'error' }, $msg);
+					logError($msg)
+						if defined $Vend::Cfg->{ErrorFile};
+				}
+
+				clean_up_after_fork();
+				send_ipc("respawn page $$")		if $next;
+				
+				undef $::Instance;
+				exit(0);
+			}
+			exit(0);
+		}
+		wait;
+	}
+	return 1;
+}
+
+sub start_soap {
+
+	my $do_message = shift;
+	my $number = shift;
+#::logDebug("starting soap");
+
+	$number = $Global::SOAP_StartServers if ! $number; 
+	if ($number > 50) {
+		  die ::errmsg(
+		   "Ridiculously large number of SOAP_StartServers: %s",
+		   $number,
+		   );
+	}
+	for (1 .. $number) {
+		my $pid;
+		if(! defined ($pid = fork) ) {
+			my $msg = ::errmsg("Can't fork: %s", $!);
+			::logGlobal({ level => 'crit' },  $msg );
+			die ("$msg\n");
+		}
+		elsif (! $pid) {
+			unless( $pid = fork ) {
+				setup_debug_log();
+
+				$Global::Foreground = 1;
+
+				if($do_message) {
+					::logGlobal(
+						{ level => 'info'},
+						server_start_message(
+							"Interchange SOAP server started (process id %s)",
+						 ),
+					 ) unless $Vend::Quiet;
+				}
+
+				send_ipc("register soap $$");
+
+				reset_per_fork();
+				my $next;
+				$::Instance = {};
+				eval { 
+					$next = server_soap(@_);
+				};
+				if ($@) {
+					my $msg = $@;
+					::logGlobal({ level => 'error' }, "Runtime error: %s" , $msg);
+					logError("Runtime error: %s", $msg)
+						if defined $Vend::Cfg->{ErrorFile};
+				}
+
+				clean_up_after_fork();
+				send_ipc("respawn soap $$")		if $next;
+				
+				undef $::Instance;
+				exit(0);
+			}
+			exit(0);
+		}
+		wait;
+	}
+	return 1;
+}
+
+sub server_page {
+
+	my ($no_fork) = @_;
+
+	my $c = 0;
+	my $cycle;
+	my $rin;
+	my $rout;
+	my $pid;
+	my $spawn;
+	my $handled = 0;
+	
+	$Global::Foreground ||= $no_fork;
+
+    for (;;) {
+
+	  my $n;
+	  $c++;
+	  my ($ok, $p, $v);
+	  my $i = 0;
+	  $c++;
+	  eval {
+		$rin = $p_vector;
+		
+my $pretty_vector = unpack('b*', $rin);
+
+		undef $spawn;
+		do {
+			$n = select($rout = $rin, undef, undef, $tick);
+		} while $n == -1 && $!{EINTR} && ! $Signal_Terminate;
+
+#::logDebug("pid=$$ cycle=$c handled=$handled tick=$tick vector=$pretty_vector n=$n num_servers=$Num_servers");
+        if ($n == -1) {
+			last if $Signal_Terminate;
+			my $msg = $!;
+			$msg = ::errmsg("error '%s' from select, n=$n." , $msg );
+			die "$msg";
+        }
+		elsif($n == 0) {
+			undef $spawn;
+			#indiv_housekeeping();
+			next;
+		}
+        else {
+
+            my ($ok, $p, $v);
+			while (($p, $v) = each %vec_map) {
+#::logDebug("PAGE trying p=$p v=$v vec=" . vec($rout,$v,1) . " pid=$$ c=$c i=" . $i++ );
+        		next unless vec($rout, $v, 1);
+#::logDebug("PAGE accepting p=$p v=$v pid=$$ c=$c i=" . $i++);
+				$Global::TcpPort = $p;
+				$ok = accept(MESSAGE, $fh_map{$p});
+				last;
+			}
+
+#::logDebug("PAGE port $Global::TcpPort handled=$handled n=$n v=$v error=$! p=$p unix=$unix_socket{$p} ipc=$ipc_socket{$p} pid=$$ c=$c i=" . $i++);
+
+			unless (defined $ok) {
+#::logDebug("PAGE redo accept on error=$! n=$n v=$v p=$p unix=$unix_socket{$p} pid=$$ c=$c i=" . $i++);
+				redo;
+				#die ("accept: $! ok=$ok pid=$$ n=$n c=$c i=" . $i++);
+			}
+
+			CHECKHOST: {
+				undef $Global::OnlyInternalHTTP;
+				last CHECKHOST if $unix_socket{$p};
+				my $connector;
+				(undef, $ok) = sockaddr_in($ok);
+				$connector = inet_ntoa($ok);
+				last CHECKHOST if $connector =~ /$Global::TcpHost/;
+				my $dns_name;
+				(undef, $dns_name) = gethostbyaddr($ok, AF_INET);
+				$dns_name = "UNRESOLVED_NAME" if ! $dns_name;
+				last CHECKHOST if $dns_name =~ /$Global::TcpHost/;
+				$Global::OnlyInternalHTTP = "$dns_name/$connector";
+			}
+			$spawn = 1;
 		}
-		next if $made_at_least_one;
-		open(Vend::Server::INET_MODE_INDICATOR, ">$Global::ConfDir/mode.inet")
-			or die "creat $Global::ConfDir/mode.inet: $!";
-		close(Vend::Server::INET_MODE_INDICATOR);
+	  };
+
+	  if($@) {
+	  	my $msg = $@;
+		$msg =~ s/\s+$//;
+#::logDebug("Died in select, retrying: $msg");
+	    ::logGlobal({ level => 'error' },  "Died in select, retrying: %s", $msg);
 	  }
+
+#::logDebug ("Past connect, spawn=$spawn");
+
+	  eval {
+		SPAWN: {
+			last SPAWN unless defined $spawn;
+#::logDebug ("Spawning connection, " .  ($no_fork ? 'no fork, ' : 'forked, ') .  scalar localtime());
+			if($no_fork) {
+				### Careful, returns after MaxRequests or terminate signal
+				$::Instance = {};
+				$handled++;
+#::logDebug("begin non-forked ::connection()");
+				connection();
+#::logDebug("end non-forked ::connection()");
+				undef $::Instance;
+			}
+			elsif(! defined ($pid = fork) ) {
+				my $msg = ::errmsg("Can't fork: %s", $!);
+				::logGlobal({ level => 'crit' },  $msg );
+				die ("$msg\n");
+			}
+			elsif (! $pid) {
+				#fork again
+				unless ($pid = fork) {
+#::logDebug("forked connection");
+					$::Instance = {};
+					eval { 
+						touch_pid() if $Global::PIDcheck;
+						&$Sig_inc;
+						connection();
+					};
+					if ($@) {
+						my $msg = $@;
+						::logGlobal({ level => 'error' }, "Runtime error: %s" , $msg);
+						logError("Runtime error: %s", $msg)
+							if defined $Vend::Cfg->{ErrorFile};
+					}
+
+					undef $::Instance;
+					select(undef,undef,undef,0.050) until getppid == 1;
+					&$Sig_dec and unlink_pid();
+					exit(0);
+				}
+				exit(0);
+			}
+			close MESSAGE;
+			last SPAWN if $no_fork;
+			wait;
+		}
+	  };
+
+		# clean up dies during spawn
+		if ($@) {
+			my $msg = $@;
+			::logGlobal({ level => 'error' }, "Died in server spawn: %s", $msg );
+
+			Vend::Session::close_session();
+			$Vend::Cfg = { } if ! $Vend::Cfg;
+
+			my $content;
+			if($content = ::get_locale_message(500, '', $msg)) {
+				print MESSAGE canon_status("Content-type: text/html");
+				print MESSAGE $content;
+			}
+
+			close MESSAGE;
+
+		}
+
+		return 1
+			if $no_fork
+			and $Global::MaxRequestsPerChild
+			and $handled >= $Global::MaxRequestsPerChild;
+
+		return if $Signal_Terminate;
+
+    }
+}
+
+sub server_soap {
+#::logDebug("Entering soap server program");
+	my $rin;
+	my $rout;
+
+	my $c = 0;
+	my $handled = 0;
+my $pretty_vector = unpack('b*', $s_vector);
+#::logDebug("SOAP server $$ begun, vector=$pretty_vector servers=$SOAP_servers");
+    for (;;) {
+
+	  my $n;
+	  $c++;
+	  my ($ok, $p, $v);
+	  eval {
+		$rin = $s_vector;
+
+		do {
+			$n = select($rout = $rin, undef, undef, $tick);
+		} while $n == -1 && $!{EINTR} && ! $Signal_Terminate;
+
+        if ($n == -1) {
+			last if $!{EINTR} and $Signal_Terminate;
+			my $msg = $!;
+			$msg = ::errmsg("error '%s' from select, n=%s.", $msg, $n );
+			die "$msg";
+        }
+		elsif($n == 0) {
+			#soap_housekeeping();
+			next;
+		}
+        else {
+			while (($p, $v) = each %s_vec_map) {
+        		next unless vec($rout, $v, 1);
+				$Global::TcpPort = $p;
+				$ok = accept(MESSAGE, $s_fh_map{$p});
+				last;
+			}
+
+
+
+	  };
+
+	  last if $Signal_Terminate;
+
+	  if($@) {
+	  	my $msg = $@;
+		$msg =~ s/\s+$//;
+#::logDebug("SOAP died in select, retrying: $msg");
+	    ::logGlobal({ level => 'error' },  "SOAP died in select, retrying: %s", $msg);
+	  }
+
+	  unless (defined $ok) {
+#::logDebug("redo accept on error=$! n=$n p=$p unix=$unix_socket{$p} pid=$$ c=$c");
+		  redo;
+	  }
+
+
+	  eval {
+			my $connector;
+			my $dns_name;
+
+			CHECKHOST: {
+				last CHECKHOST if $unix_socket{$p};
+				(undef, $ok) = sockaddr_in($ok);
+				$connector = inet_ntoa($ok);
+				last CHECKHOST if $connector =~ /$Global::TcpHost/;
+				(undef, $dns_name) = gethostbyaddr($ok, AF_INET);
+				$dns_name = $connector if ! $dns_name;
+				last CHECKHOST if $dns_name =~ /$Global::TcpHost/;
+				$Global::OnlyInternalHTTP = "$dns_name/$connector";
+			}
+
+			$handled++;
+			my %env;
+			my $entity;
+			
+			reset_vars();
+
+			$Vend::OnlyInternalHTTP = $Global::OnlyInternalHTTP;
+
+			$Vend::Cfg = http_soap(\*MESSAGE, \%env, \$entity);
+			$Vend::Cat = $Vend::Cfg->{CatalogName};
+
+			my $result;
+			my $error;
+			if(! $Vend::Cfg) {
+#::logDebug("we have no catalog");
+				$result = Vend::SOAP::Transport::Server
+					->new( error => 'Catalog not found' )
+					->dispatch_to('', 'Vend::SOAP::Error')
+					->handle();
+			}
+			elsif(! $Vend::Cfg->{SOAP}) {
+#::logDebug("we have no SOAP enable");
+				$result = Vend::SOAP::Transport::Server
+					->new( error => 'SOAP not enabled' )
+					->dispatch_to('', 'Vend::SOAP::Error')
+					->handle();
+			}
+			else {
+#::logDebug("we have our SOAP enable, entity is $entity");
+				($Vend::SessionID, $CGI::cookiehost) = split /:/, $env{SESSION_ID};
+#::logDebug("Received ID=$Vend::SessionID, host='$CGI::cookiehost'");
+				$Vend::NoInterpolate = 1
+					unless $Vend::Cfg->{SOAP_Enable}->{interpolate};
+				$result = Vend::SOAP::Transport::Server
+					->new( in => $entity )
+					->dispatch_to('', 'Vend::SOAP')
+					->handle;
+			}
+
+			unless ($Vend::StatusLine =~ m{^HTTP/}) {
+				my $status = $Vend::StatusLine =~ /(?:^|\n)Status:\s+(.*)/i
+					? "$1" : "200 OK";
+				$Vend::StatusLine = "HTTP/1.0 $status\r\n" . $Vend::StatusLine;
+			}
+			$Vend::StatusLine .= "\r\nContent-Type: text/xml\r\n"
+				unless $Vend::StatusLine =~ /^Content-Type:/im;
+
+			print MESSAGE canon_status($Vend::StatusLine);
+			print MESSAGE $result;
+			undef $Vend::StatusLine;
+			$Vend::ResponseMade = 1;
+			close MESSAGE;
+#::logDebug("SOAP port=$p n=$n unix=$unix_socket{$p} pid=$$ c=$c time=" . join '|', times);
+		}
+	  };	
+
+	  if($@) {
+	  	my $msg = $@;
+		$msg =~ s/\s+$//;
+#::logDebug("SOAP died in processing: $msg");
+	    ::logGlobal({ level => 'error' },  "SOAP died in processing: %s", $msg);
+		close MESSAGE;
+	  }
+
+	  return if $Signal_Terminate;
+	  return 1 if $handled > ($Global::SOAP_MaxRequests || 10);
+	  ::put_session() if $Vend::HaveSession;
+	  undef $Vend::Session;
+	  undef $Vend::HaveSession;
+    }
+
+}
+
+sub process_ipc {
+	my $fh = shift;
+#::logDebug("pid $$: processing ipc response $fh");
+	my $thing = <$fh>;
+#::logDebug("pid $$: thing is $thing");
+	if($thing =~ /^\d+$/) {
+		close $fh;
+		$Num_servers--;
+	}
+	elsif ($thing =~ /^register page (\d+)/) {
+		$Page_pids{$1} = 1;
+#::logDebug("registered Page pid $1");
+		$Page_servers++;
+	}
+	elsif ($thing =~ /^respawn page (\d+)/) {
+		delete $Page_pids{$1};
+#::logDebug("deleted Page pid $1");
+		$Page_servers--;
+		start_page(undef,$Global::PreFork,1);
+	}
+	elsif ($thing =~ /^register soap (\d+)/) {
+		$SOAP_pids{$1} = 1;
+#::logDebug("registered SOAP pid $1");
+		$SOAP_servers++;
+	}
+	elsif ($thing =~ /^respawn soap (\d+)/) {
+		delete $SOAP_pids{$1};
+#::logDebug("deleted SOAP pid $1");
+		$SOAP_servers--;
+		start_soap(undef, 1);
+	}
+	elsif($thing =~ /^\d+$/) {
+		close $fh;
+		$Num_servers++;
+	}
+	return;
+}
+
+sub send_ipc {
+	my $msg = shift;
+	socket(SOCK, PF_UNIX, SOCK_STREAM, 0)	or die "socket: $!\n";
+
+	my $ok;
+
+	do {
+	   $ok = connect(SOCK, sockaddr_un($Global::IPCsocket));
+	} while ( ! defined $ok and ! $!{EINTR});
+
+	print SOCK $msg;
+#::logDebug("pid $$: sent ipc $msg");
+	close SOCK;
+}
+
+sub setup_debug_log {
+	if ($Global::DebugFile) {
+		open(Vend::DEBUG, ">>$Global::DebugFile");
+		select Vend::DEBUG;
+		$| = 1;
+		print "Start DEBUG at " . localtime() . "\n";
 	}
+	elsif (!$Global::DEBUG) {
+		# May as well turn warnings off, not going anywhere
+		$^W = 0;
+		open (Vend::DEBUG, ">/dev/null") unless $Global::Windows;
+	}
+
+	close(STDIN);
+	close(STDOUT);
+	close(STDERR);
 
-	if (! $made_at_least_one and $Global::Inet_Mode) {
-		my $msg;
-		if ($Global::Unix_Mode) {
-			$msg = errmsg("Continuing in UNIX MODE ONLY" );
-			::logGlobal($msg);
-			print "$msg\n";
+	open(STDOUT, ">&Vend::DEBUG");
+	select(STDOUT);
+	$| = 1;
+
+	open(STDERR, ">&Vend::DEBUG");
+	select(STDERR);
+	$| = 1;
+}
+
+# The servers for both are now combined
+# Can have both INET and UNIX on same system
+sub server_both {
+    my ($socket_filename) = @_;
+    my ($n, $rin, $rout, $pid);
+
+	::logGlobal({ level => 'info' }, server_start_message());
+
+	$Vend::MasterProcess = $$;
+
+	$tick        = $Global::HouseKeeping || 60;
+
+    setup_signals();
+
+#::logDebug("Starting server socket file='$socket_filename' hosts='$host'\n");
+
+	my $spawn;
+
+	for (qw/mode.inet mode.unix mode.soap/) {
+		unlink "$Global::RunDir/$_";
+	}
+
+	# We always unlink our file-based sockets
+	unlink_sockets($Global::SocketFile);
+	if($Global::IPCsocket) {
+#::logDebug("Creating IPC socket $Global::IPCsocket");
+		unlink_sockets($Global::IPCsocket);
+		## This is a scalar, not an array like Global::SocketFile
+		($ipc) = map_unix_socket(\$vector, \%vec_map, \%fh_map, $Global::IPCsocket );
+		$ipc_socket{$ipc} = $ipc;
+		$unix_socket{$ipc} = $ipc;
+		$ipc_vector = $vector;
+	}
+
+	# Make UNIX-domain sockets if applicable. The sockets are mapped into the
+	# vector map and file handle map, socket permissions are set, etc.  The
+	# socket labels are marked with %unix_socket so that INET-specific
+	# processing like determining IP address are not done.
+	if($Global::Unix_Mode) {
+		my @made =
+			map_unix_socket(\$vector, \%vec_map, \%fh_map, @$Global::SocketFile);
+		if (scalar @made) {
+			@unix_socket{@made} = @made;
+			open(UNIX_MODE_INDICATOR, ">$Global::RunDir/mode.unix")
+				or die "create $Global::RunDir/mode.unix: $!";
+			print UNIX_MODE_INDICATOR join " ", @made;
+			close(UNIX_MODE_INDICATOR);
+			# So that other apps can read if appropriate
+			chmod $Global::SocketPerms, "$Global::RunDir/mode.unix";
+		}
+		else { # The error condition
+			my $msg;
+			if ($Global::Inet_Mode) {
+				$msg = errmsg("Failed to make any UNIX sockets, continuing in INET MODE ONLY" );
+				::logGlobal({ level => 'warn' }, $msg);
+				print "$msg\n";
+				undef $Global::Unix_Mode;
+			}
+			else {
+				$msg = errmsg( "No sockets -- INTERCHANGE SERVER TERMINATING\a" );
+				::logGlobal( {level => 'alert'}, $msg );
+				print "$msg\n";
+				exit 1;
+			}
+		}
+		
+		for(@made) {
+			chmod $Global::SocketPerms, $_;
+			if($Global::SocketPerms & 033) {
+				::logGlobal( {
+					level => 'warn' },
+					"ALERT: %s socket permissions are insecure; are you sure you want permissions %o?",
+					$_,
+					$Global::SocketPerms,
+				);
+			}
+		}
+	}
+
+	# Make SOAP-IPC sockets if applicable. The sockets are mapped into a
+	# separate vector map and file handle map. The require of the SOAP
+	# module is done here so that memory footprint will not be greater
+	# if SOAP is not used.
+
+	if($Global::SOAP) {
+		eval {
+			require Vend::SOAP;
+		};
+		if($@) {
+			::logGlobal( {
+				level => 'warn' },
+				"SOAP enabled, but Vend::SOAP will not load: %s",
+				$@,
+			);
 		}
 		else {
-			$msg = errmsg( "No sockets -- INTERCHANGE SERVER TERMINATING\a" );
-			::logGlobal( {level => 'alert'}, $msg );
-			print "$msg\n";
-			exit 1;
+			my @made;
+			my @unix_soap = grep m{/}, @{$Global::SOAP_Socket};
+			my @inet_soap = grep $_ !~ m{/}, @{$Global::SOAP_Socket};
+			if(@unix_soap) {
+				unlink_sockets(@unix_soap);
+				push @made,
+					map_unix_socket(\$s_vector, \%s_vec_map, \%s_fh_map, @unix_soap);
+				chmod $Global::SOAP_Perms, @made;
+				@unix_socket{@made} = @made;
+			}
+			if(@inet_soap) {
+				push @made,
+					map_inet_socket(\$s_vector, \%s_vec_map, \%s_fh_map, @inet_soap);
+			}
 		}
 	}
 
+	# Make INET-domain sockets if applicable. The sockets are added into
+	# $vector for select(,,,) monitoring, and mapped into the vector map and
+	# file handle map.
+	if($Global::Inet_Mode) {
+		$Global::TcpHost = create_host_pattern($Global::TcpHost);
+		::logGlobal(
+				{ level => 'info' },
+				"Accepting connections from %s",
+				$Global::TcpHost,
+				);
+		my @made =
+			map_inet_socket(\$vector, \%vec_map, \%fh_map, keys %{$Global::TcpMap});
+		if (! scalar @made) {
+			my $msg;
+			if ($Global::Unix_Mode) {
+				$msg = errmsg("Continuing in UNIX MODE ONLY" );
+				::logGlobal({ level => 'warn' }, $msg);
+				print "$msg\n";
+				undef $Global::Inet_Mode;
+			}
+			else {
+				$msg = errmsg( "No sockets -- INTERCHANGE SERVER TERMINATING\a" );
+				::logGlobal( {level => 'alert'}, $msg );
+				print "$msg\n";
+				exit 1;
+			}
+		}
+		else {
+			open(INET_MODE_INDICATOR, ">$Global::RunDir/mode.inet")
+				or die "create $Global::RunDir/mode.inet: $!";
+			print INET_MODE_INDICATOR join " ", @made;
+			close(INET_MODE_INDICATOR);
+			# So that other apps can read if appropriate
+			chmod $Global::SocketPerms, "$Global::RunDir/mode.inet";
+		}
+	}
+
+	::logGlobal({ level => 'info' }, server_start_message() );
+
 	my $no_fork;
 	if($Global::Windows or $Global::DEBUG ) {
 		$no_fork = 1;
-		$Vend::Foreground = 1;
-		::logGlobal("Running in foreground, OS=$^O, debug=$Global::DEBUG\n");
+		$Global::Foreground = 1;
+		::logGlobal({ level => 'info' }, "Running in foreground, OS=$^O, debug=$Global::DEBUG\n");
 	}
 	else {
-		close(STDIN);
-		close(STDOUT);
-		close(STDERR);
-
-		if ($Global::DebugFile) {
-			open(Vend::DEBUG, ">>$Global::DebugFile");
-			select Vend::DEBUG;
-			$| =1;
-			print "Start DEBUG at " . localtime() . "\n";
-		}
-		elsif (!$Global::DEBUG) {
-			# May as well turn warnings off, not going anywhere
-			$^W = 0;
-			open (Vend::DEBUG, ">/dev/null") unless $Global::Windows;
+		setup_debug_log();
+#::logDebug("s_vector=" . unpack('b*', $s_vector));
+		if($s_vector) {
+			start_soap(1);
 		}
-
-		open(STDOUT, ">&Vend::DEBUG");
-		select(STDOUT);
-		$| = 1;
-		open(STDERR, ">&Vend::DEBUG");
-		select(STDERR); $| = 1; select(STDOUT);
-		$Vend::Foreground = 0;
 	}
 
+	my $master_ipc = 0;
+	if($Global::StartServers) {
+		$master_ipc = 1;
+		$p_vector = $vector ^ $ipc_vector;
+		start_page(1,$Global::PreFork);
+	}
 
+	my $c = 0;
+	my $only_ipc = $master_ipc;
+	my $checked_soap;
+	my $cycle;
     for (;;) {
 
+	  my $i = 0;
+	  $c++;
 	  eval {
-        $rin = $vector;
+        if($only_ipc) {
+			$rin = $ipc_vector;
+			$cycle = 0.100;
+		}
+		else {
+			$rin = $vector;
+			$cycle = $tick;
+		}
+my $pretty_vector = unpack('b*', $rin);
 		undef $spawn;
-        $n = select($rout = $rin, undef, undef, $tick);
+		undef $checked_soap;
+		do {
+			$n = select($rout = $rin, undef, undef, $cycle);
+		} while $n == -1 && $!{EINTR} && ! $Signal_Terminate;
 
 		undef $Vend::Cfg;
 
+#::logDebug("cycle=$c tick=$cycle vector=$pretty_vector n=$n num_servers=$Num_servers");
         if ($n == -1) {
-            if ($! =~ m/^Interrupted/) {
-                if ($Signal_Terminate) {
-                    last;
-                }
-            }
-            else {
-				my $msg = $!;
-				$msg = ::errmsg("error '%s' from select." , $msg );
-				::logGlobal({}, $msg );
-                die "$msg\n";
-            }
+			last if $Signal_Terminate;
+			my $msg = $!;
+			$msg = ::errmsg("error '%s' from select, n=%s." , $msg, $n);
+			die "$msg";
         }
-
-        elsif (	$Global::Unix_Mode && vec($rout, fileno(Vend::Server::USOCKET), 1) ) {
-			undef $Vend::OnlyInternalHTTP;
-            my $ok = accept(Vend::Server::MESSAGE, Vend::Server::USOCKET);
-            die "accept: $!" unless defined $ok;
-			$spawn = 1;
-		}
 		elsif($n == 0) {
-			undef $spawn;
-			housekeeping();
+			# Do nothing, timed out
 		}
-        elsif (	$Global::Inet_Mode ) {
+        else {
+
             my ($ok, $p, $v);
 			while (($p, $v) = each %vec_map) {
+#::logDebug("trying p=$p v=$v vec=" . vec($rout,$v,1) . " pid=$$ c=$c i=" . $i++ );
         		next unless vec($rout, $v, 1);
+#::logDebug("accepting p=$p v=$v pid=$$ c=$c i=" . $i++);
 				$Global::TcpPort = $p;
-				$ok = accept(Vend::Server::MESSAGE, $fh_map{$p});
+				$ok = accept(MESSAGE, $fh_map{$p});
+				last;
 			}
-#::logDebug("port $Global::TcpPort");
-            die "accept: $!" unless defined $ok;
-			my $connector;
-			(undef, $ok) = sockaddr_in($ok);
-		CHECKHOST: {
-			undef $Vend::OnlyInternalHTTP;
-			$connector = inet_ntoa($ok);
-			last CHECKHOST if $connector =~ /$Global::TcpHost/;
-			my $dns_name;
-			(undef, $dns_name) = gethostbyaddr($ok, AF_INET);
-			$dns_name = "UNRESOLVED_NAME" if ! $dns_name;
-			last CHECKHOST if $dns_name =~ /$Global::TcpHost/;
-			$Vend::OnlyInternalHTTP = "$dns_name/$connector";
-		}
-			$spawn = 1;
+
+#::logDebug("port $Global::TcpPort n=$n v=$v error=$! p=$p unix=$unix_socket{$p} ipc=$ipc_socket{$p} pid=$$ c=$c i=" . $i++);
+
+			unless (defined $ok) {
+#::logDebug("redo accept on error=$! n=$n v=$v p=$p unix=$unix_socket{$p} pid=$$ c=$c i=" . $i++);
+				redo;
+				#die ("accept: $! ok=$ok pid=$$ n=$n c=$c i=" . $i++);
+			}
+
+			if ($ipc_socket{$p}) {
+				process_ipc(\*MESSAGE);
+				$only_ipc = 1;
+			}
+
+			CHECKHOST: {
+				undef $Vend::OnlyInternalHTTP;
+				last CHECKHOST if $unix_socket{$p};
+				my $connector;
+				(undef, $ok) = sockaddr_in($ok);
+				$connector = inet_ntoa($ok);
+				last CHECKHOST if $connector =~ /$Global::TcpHost/;
+				my $dns_name;
+				(undef, $dns_name) = gethostbyaddr($ok, AF_INET);
+				$dns_name = "UNRESOLVED_NAME" if ! $dns_name;
+				last CHECKHOST if $dns_name =~ /$Global::TcpHost/;
+				$Vend::OnlyInternalHTTP = "$dns_name/$connector";
+			}
+			$spawn = 1 unless $only_ipc;
 		}
-        else {
-            die "Why did select return with $n? Can we even get here?";
-        }
 	  };
-	  ::logGlobal({}, "Died in select, retrying: %s", $@) if $@;
+
+	  if($@) {
+	  	my $msg = $@;
+		$msg =~ s/\s+$//;
+#::logDebug("Died in select, retrying: $msg");
+	    ::logGlobal({ level => 'error' },  "Died in select, retrying: %s", $msg);
+	  }
 
 	  eval {
 		SPAWN: {
 			last SPAWN unless defined $spawn;
-#::logDebug #("Spawning connection, " .  ($no_fork ? 'no fork, ' : 'forked, ') .  scalar localtime() . "\n");
+#::logDebug("Spawning connection, " .  ($no_fork ? 'no fork, ' : 'forked, ') .  scalar localtime() . "\n");
 			if(defined $no_fork) {
-				$Vend::NoFork = {};
 				$::Instance = {};
 				connection();
-				undef $Vend::NoFork;
 				undef $::Instance;
 			}
 			elsif(! defined ($pid = fork) ) {
 				my $msg = ::errmsg("Can't fork: %s", $!);
-				::logGlobal({}, $msg );
+				::logGlobal({ level => 'crit' },  $msg );
 				die ("$msg\n");
 			}
 			elsif (! $pid) {
 				#fork again
 				unless ($pid = fork) {
 
+					reset_per_fork();
 					$::Instance = {};
 					eval { 
 						touch_pid() if $Global::PIDcheck;
@@ -1200,14 +2158,18 @@
 					};
 					if ($@) {
 						my $msg = $@;
-						::logGlobal({}, "Runtime error: %s" , $msg);
+						::logGlobal({ level => 'error' }, "Runtime error: %s" , $msg);
 						logError("Runtime error: %s", $msg)
 							if defined $Vend::Cfg->{ErrorFile};
 					}
+					clean_up_after_fork();
 
 					undef $::Instance;
 					select(undef,undef,undef,0.050) until getppid == 1;
-					if ($Global::PIDcheck) {
+					if ($Global::IPCsocket) {
+						&$Sig_dec and unlink_pid();
+					}
+					elsif ($Global::PIDcheck) {
 						unlink_pid() and &$Sig_dec;
 					}
 					else {
@@ -1217,7 +2179,7 @@
 				}
 				exit(0);
 			}
-			close Vend::Server::MESSAGE;
+			close MESSAGE;
 			last SPAWN if $no_fork;
 			wait;
 		}
@@ -1225,120 +2187,262 @@
 
 		# clean up dies during spawn
 		if ($@) {
-			::logGlobal({}, "Died in server spawn: %s", $@ ) if $@;
+			my $msg = $@;
+			::logGlobal({ level => 'error' }, "Died in server spawn: %s", $msg );
 
-			# Below only happens with Windows or foreground debugs.
-			# Prevent corruption of changed $Vend::Cfg entries
-			# (only VendURL/SecureURL at this point).
-			if($Vend::Save and $Vend::Cfg) {
-				Vend::Util::copyref($Vend::Save, $Vend::Cfg);
-				undef $Vend::Save;
+			Vend::Session::close_session();
+			$Vend::Cfg = { } if ! $Vend::Cfg;
+
+			my $content;
+			if($content = ::get_locale_message(500, '', $msg)) {
+				print MESSAGE canon_status("Content-type: text/html");
+				print MESSAGE $content;
 			}
-			undef $Vend::Cfg;
+
+			close MESSAGE;
 		}
 
-		last if $Signal_Terminate || $Signal_Debug;
+		last if $Signal_Terminate;
+	  	$only_ipc = $master_ipc;
 
 	  eval {
-        for(;;) {
-		   housekeeping($tick);
-           last if ! $Global::MaxServers or $Vend::Server::Num_servers < $Global::MaxServers;
-           select(undef,undef,undef,0.100);
-           last if $Signal_Terminate || $Signal_Debug;
-        }
+		    housekeeping($tick);
+		    if ($Global::MaxServers and $Num_servers > $Global::MaxServers) {
+			   $only_ipc = $ipc;
+			}
+			if( $rin = $s_vector and select($rin, undef, undef, 0) >= 1 ) {
+				start_soap(undef,1)
+					unless $SOAP_servers > $Global::SOAP_MaxServers;
+			}
 	  };
-	  ::logGlobal({}, "Died in housekeeping, retry: %s", $@ ) if $@;
-
+	  ::logGlobal({ level => 'crit' }, "Died in housekeeping, retry: %s", $@ ) if $@;
     }
 
     restore_signals();
 
    	if ($Signal_Terminate) {
-       	::logGlobal({}, "STOP server (%s) on signal TERM", $$ );
-       	return 'terminate';
+       	::logGlobal({ level => 'info' }, "STOP server (%s) on signal TERM", $$ );
+#::logDebug("SOAP pids: " . ::uneval(\%SOAP_pids));
+		my @pids = keys %SOAP_pids;
+		if(@pids) {
+			::logGlobal(
+				{ level => 'info' },
+				"STOP SOAP servers (%s) on signal TERM",
+				join ",", keys %SOAP_pids,
+			);
+			kill 'TERM', @pids;
+		}
+		@pids = keys %Page_pids;
+		if(@pids) {
+			::logGlobal(
+				{ level => 'info' },
+				"STOP page servers (%s) on signal TERM",
+				join ",", keys %Page_pids,
+			);
+			kill 'TERM', @pids;
+		}
    	}
 
     return '';
 }
 
 sub touch_pid {
-	open(TEMPPID, ">>$Global::ConfDir/pid.$$") 
-		or die "creat PID file $$: $!\n";
+	open(TEMPPID, ">>$Global::RunDir/pid.$$") 
+		or die "create PID file $$: $!\n";
 	lockfile(\*TEMPPID, 1, 0)
 		or die "PID $$ conflict: can't lock\n";
 }
 
+sub cron_job {
+	my ($cat, @jobs) = @_;
+	for my $job (@jobs) {
+		Vend::Dispatch::run_in_catalog($cat, $job);
+	}
+}
+
+sub run_cron {
+	my ($cat, @jobs) = @_;
+
+#::logGlobal("Vend::Server::run_cron: run cron cat=cat jobs=@jobs");
+	my $pid;
+	if($Global::Foreground) {
+		$::Instance = {};
+		eval {
+			cron_job($cat, @jobs);
+		};
+		if($@) {
+			my $msg = $@;
+			::logGlobal({ level => 'error' }, "Runtime error: %s" , $msg);
+			logError("Runtime cron error: %s", $msg)
+				if defined $Vend::Cfg->{ErrorFile};
+		}
+		clean_up_after_fork();
+		undef $::Instance;
+	}
+	elsif(! defined ($pid = fork) ) {
+		my $msg = ::errmsg("Can't fork: %s", $!);
+		::logGlobal({ level => 'crit' },  $msg );
+		die ("$msg\n");
+	}
+	elsif (! $pid) {
+		#fork again
+		unless ($pid = fork) {
+
+			reset_per_fork();
+			$::Instance = {};
+			eval { 
+				touch_pid() if $Global::PIDcheck;
+				&$Sig_inc;
+				cron_job($cat, @jobs);
+			};
+			if ($@) {
+				my $msg = $@;
+				::logGlobal({ level => 'error' }, "Runtime error: %s" , $msg);
+				logError("Runtime cron error: %s", $msg)
+					if defined $Vend::Cfg->{ErrorFile};
+			}
+			clean_up_after_fork();
+
+			undef $::Instance;
+			select(undef,undef,undef,0.050) until getppid == 1;
+			if ($Global::PIDcheck) {
+				unlink_pid() and &$Sig_dec;
+			}
+			else {
+				&$Sig_dec;
+			}
+			exit(0);
+		}
+		exit(0);
+	}
+	wait unless $Global::Foreground;
+}
+
 sub unlink_pid {
 	close(TEMPPID);
-	unlink("$Global::ConfDir/pid.$$");
+	unlink("$Global::RunDir/pid.$$");
 	1;
 }
 
 sub grab_pid {
-    my $ok = lockfile(\*Vend::Server::Pid, 1, 0);
+	my $fh = shift
+		or return;
+    my $ok = lockfile($fh, 1, 0);
     if (not $ok) {
-        chomp(my $pid = <Vend::Server::Pid>);
+        chomp(my $pid = <$fh>);
         return $pid;
     }
     {
         no strict 'subs';
-        truncate(Vend::Server::Pid, 0) or die "Couldn't truncate pid file: $!\n";
+        truncate($fh, 0) or die "Couldn't truncate pid file: $!\n";
     }
-    print Vend::Server::Pid $$, "\n";
+    print $fh ($Global::mod_perl ? getppid : $$), "\n";
     return 0;
 }
 
-
-
 sub open_pid {
-
-    open(Vend::Server::Pid, "+>>$Global::PIDfile")
-        or die "Couldn't open '$Global::PIDfile': $!\n";
-    seek(Vend::Server::Pid, 0, 0);
-    my $o = select(Vend::Server::Pid);
+	my $fn = shift || $Global::PIDfile;
+	my $fh = gensym();
+    open($fh, "+>>$fn")
+        or die ::errmsg("Couldn't open '%s': %s\n", $fn, $!);
+    seek($fh, 0, 0);
+    my $o = select($fh);
     $| = 1;
-    {
-        no strict 'refs';
-        select($o);
-    }
+	select($o);
+	return $fh;
+}
+
+sub read_pidfile {
+	my $fn = shift || $Global::PIDfile;
+	my $fh = gensym();
+	open $fh, "<$fn" or return;
+	chomp (my $pid = <$fh>);
+	close $fh;
+	return $pid;
 }
 
 sub run_server {
     my $next;
-    my $pid;
 	
-    open_pid();
+    my $pidh = open_pid($Global::PIDfile);
 
-	unless($Global::Inet_Mode || $Global::Unix_Mode || $Global::Windows) {
-		$Global::Inet_Mode = $Global::Unix_Mode = 1;
+	if($Global::AcceptRedirect) {
+		push @Map, @RedirMap
+			unless grep $_ eq 'REDIRECT_URL', @Map;
+	}
+
+	if ($Global::mod_perl) {
+		undef $Global::Unix_Mode;
+		undef $Global::Inet_Mode;
+		undef $Global::StartServers;
+		undef $Global::PreFork;
+		undef $Global::SOAP;
+		undef $Global::IPCsocket;
 	}
 	elsif ( $Global::Windows ) {
 		$Global::Inet_Mode = 1;
 	}
+	elsif (! $Global::Inet_Mode and ! $Global::Unix_Mode) {
+		$Global::Inet_Mode = $Global::Unix_Mode = 1;
+	}
 
-	my @types;
-	push (@types, 'INET') if $Global::Inet_Mode;
-	push (@types, 'UNIX') if $Global::Unix_Mode;
-	my $server_type = join(" and ", @types);
-	::logGlobal({}, "START server (%s) (%s)" , $$, $server_type );
+	if($Global::mod_perl || $Global::PreFork || $Global::DEBUG || $Global::Windows) {
+		eval {
+			require Tie::ShadowHash;
+		};
+		if($@) {
+			my $reason;
+			if($Global::mod_perl)	{ $reason = 'under mod_perl' }
+			elsif($Global::PreFork)	{ $reason = 'in PreFork mode' }
+			elsif($Global::DEBUG)	{ $reason = 'in DEBUG mode' }
+			elsif($Global::Windows)	{ $reason = 'under Windows' }
+			die ::errmsg("Running $reason requires Tie::ShadowHash module.") . "\n";
+		}
+	}
 
-    if ($Global::Windows) {
-        $pid = grab_pid();
-        if ($pid) {
+	if ($Global::mod_perl) {
+		my $running = grab_pid($pidh);
+		if ($running) {
 			print errmsg(
 				"The Interchange server is already running (process id %s)\n",
-				$pid,
+				$running,
+			);
+			undef $Global::mod_perl;
+			return;
+		}
+		# throw away pidfile -- Apache hasn't forked yet, so pid is wrong
+		unlockfile($pidh);
+		unlink $Global::PIDfile;
+		print server_start_message("Interchange server started (%s)\n", 1);
+		::logGlobal(
+			{ level => 'info' },
+			Vend::Server::server_start_message('START server (%s)', 1),
+		);
+		setup_debug_log();
+		# all done; now wait for Apache to call Vend::ModPerl::handler
+		return;
+	}
+
+	if ($Global::Windows || $Global::DEBUG) {
+        my $running = grab_pid($pidh);
+        if ($running) {
+			print errmsg(
+				"The Interchange server is already running (process id %s)\n",
+				$running,
 				);
 			exit 1;
         }
 
-        print errmsg("Interchange server started (%s) (%s)\n", $$, $server_type);
-		$next = server_both($Global::SocketFile);
+        print server_start_message("Interchange server started (%s) (%s)\n");
+		$next = server_both();
     }
     else {
 
-        fcntl(Vend::Server::Pid, F_SETFD, 0)
-            or die "Can't fcntl close-on-exec flag for '$Global::PIDfile': $!\n";
+        fcntl($pidh, F_SETFD, 0)
+            or die ::errmsg(
+					"Can't fcntl close-on-exec flag for '%s': %s\n",
+					$Global::PIDfile, $!,
+					);
         my ($pid1, $pid2);
         if ($pid1 = fork) {
             # parent
@@ -1365,40 +2469,34 @@
                 # child 2
                 sleep 1 until getppid == 1;
 
-                $pid = grab_pid();
-                if ($pid) {
+                my $running = grab_pid($pidh);
+                if ($running) {
                     print errmsg(
 						"The Interchange server is already running (process id %s)\n",
-						$pid,
+						$running,
 						);
                     exit 1;
                 }
-                print errmsg(
+                print server_start_message(
 						"Interchange server started in %s mode(s) (process id %s)\n",
-						$server_type,
-						$$,
+						1,
 					 ) unless $Vend::Quiet;
 
                 setsid();
 
-                fcntl(Vend::Server::Pid, F_SETFD, 1)
+                fcntl($pidh, F_SETFD, 1)
                     or die "Can't fcntl close-on-exec flag for '$Global::PIDfile': $!\n";
 
-				$next = server_both($Global::SocketFile);
+				$next = server_both();
 
-				unlockfile(\*Vend::Server::Pid);
-				opendir(CONFDIR, $Global::ConfDir) 
-					or die "Couldn't open directory $Global::ConfDir: $!\n";
-				my @running = grep /^mvrunning/, readdir CONFDIR;
-				for(@running) {
-					unlink "$Global::ConfDir/$_" or die
-						"Couldn't unlink status file $Global::ConfDir/$_: $!\n";
-				}
+				unlockfile($pidh);
+				opendir(RUNDIR, $Global::RunDir) 
+					or die "Couldn't open directory $Global::RunDir: $!\n";
 				unlink $Global::PIDfile;
                 exit 0;
             }
         }
-    }                
+    }
 }
 
 1;



1.6.4.2   +108 -33   interchange/lib/Vend/Session.pm


rev 1.6.4.2, prev_rev 1.6.4.1
Index: Session.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Session.pm,v
retrieving revision 1.6.4.1
retrieving revision 1.6.4.2
diff -u -r1.6.4.1 -r1.6.4.2
--- Session.pm	27 Nov 2000 02:34:34 -0000	1.6.4.1
+++ Session.pm	25 Jan 2003 22:21:28 -0000	1.6.4.2
@@ -1,14 +1,11 @@
-# Session.pm - Interchange Sessions
+# Vend::Session - Interchange session routines
 #
-# $Id: Session.pm,v 1.6.4.1 2000/11/27 02:34:34 racke Exp $
+# $Id: Session.pm,v 1.6.4.2 2003/01/25 22:21:28 racke Exp $
 # 
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -24,13 +21,12 @@
 # License along with this program; if not, write to the Free
 # Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 # MA  02111-1307  USA.
-#
 
 package Vend::Session;
 require Exporter;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.6.4.1 $, 10);
+$VERSION = substr(q$Revision: 1.6.4.2 $, 10);
 
 @ISA = qw(Exporter);
 
@@ -39,11 +35,15 @@
 check_save
 dump_sessions
 expire_sessions
+close_session
 get_session
 init_session
+is_retired
 new_session
 put_session
+retire_id
 session_name
+tie_static_dbm
 
 );
 
@@ -138,10 +138,19 @@
 # SESSIONS implemented using DBM
 
 sub get_session {
+	my $seed = shift;
+
+	if($seed and ! $Vend::SessionID) {
+#::logDebug("received seed=$seed");
+		$Vend::SessionID = $seed;
+	}
+	$Vend::SessionName = session_name() if ! $Vend::SessionName;
+#::logDebug("session name now $Vend::SessionName");
+
 	$Vend::HaveSession = 0;
 	open_session();
 	my $new;
-	$new = read_session() unless $Vend::ExternalProgram;
+	$new = read_session($seed) unless $Vend::ExternalProgram;
 	unless($File_sessions) {
 		lock_session();
 		close_session();
@@ -151,6 +160,7 @@
 }
 
 sub put_session {
+	return unless $Vend::HaveSession;
 	unless($File_sessions) {
 		open_session();
 		write_session();
@@ -194,22 +204,44 @@
 		my $grace = time() - ($Global::Variable->{MV_ROBOT_EXPIRE} || 86400);
 		unlink $fn if -M $fn < $grace;
 	}
-	return File::CounterFile->new($fn)->inc() if $inc;
-	return File::CounterFile->new($fn)->value();
+	return Vend::CounterFile->new($fn)->inc() if $inc;
+	return Vend::CounterFile->new($fn)->value();
 }
 
+sub is_retired {
+	my $id = shift;
+	mkdir "$Vend::Cfg->{ScratchDir}/retired", 0777
+		unless -d "$Vend::Cfg->{ScratchDir}/retired";
+	my $fn = Vend::Util::get_filename($id, 2, 1, "$Vend::Cfg->{ScratchDir}/retired");
+	return -f $fn ? 1 : 0;
+}
+
+sub retire_id {
+	my $id = shift;
+	return unless $id =~ /^\w+$/;
+	mkdir "$Vend::Cfg->{ScratchDir}/retired", 0777
+		unless -d "$Vend::Cfg->{ScratchDir}/retired";
+	my $fn = Vend::Util::get_filename($id, 2, 1, "$Vend::Cfg->{ScratchDir}/retired");
+	open(TMPRET, ">$fn")
+		or die "retire id open: $!\n";
+	close(TMPRET);
+	return;
+}
 
 sub new_session {
     my($seed) = @_;
     my($name);
 
-#::logDebug ("new session id=$Vend::SessionID  name=$Vend::SessionName\n");
+#::logDebug ("new session id=$Vend::SessionID  name=$Vend::SessionName seed=$seed");
 	open_session();
     for (;;) {
-		$Vend::SessionID = random_string() unless defined $seed;
+		unless (defined $seed) {
+			$Vend::SessionID = random_string();
+			undef $Vend::CookieID;
+		}
 		undef $seed;
-		if (::is_retired($Vend::SessionID)) {
-			::retire_id($Vend::SessionID);
+		if (is_retired($Vend::SessionID)) {
+			retire_id($Vend::SessionID);
 			next;
 		}
 		$name = session_name();
@@ -220,8 +252,9 @@
 			last unless exists $Vend::SessionDBM{$name};
 		}
     }
+	$Vend::new_session = 1;
 	count_ip(1);
-	$CGI::cookie = $Vend::Cookie = '';
+	undef $Vend::Cookie;
     $Vend::SessionName = $name;
     init_session();
 #::logDebug("init_session $Vend::SessionName is: " . ::uneval($Vend::Session));
@@ -234,13 +267,15 @@
 }
 
 sub close_session {
-#::logDebug ("close session id=$Vend::SessionID  name=$Vend::SessionName\n");
-	return 1 if ! defined $Vend::SessionOpen;
+#::logDebug ("try to close session id=$Vend::SessionID  name=$Vend::SessionName");
+	return 0 if ! defined $Vend::SessionOpen;
 
 	unless($DB_sessions) {
+#::logDebug ("close session id=$Vend::SessionID  name=$Vend::SessionName");
 		undef $DB_object;
 		untie %Vend::SessionDBM
 			or die "Could not close $Vend::Cfg->{SessionDatabase}: $!\n";
+		undef $Vend::SessionOpen;
 	}
 	
 	return 1 unless $Lock_sessions;
@@ -250,6 +285,7 @@
     close(Vend::SessionLock)
 		or die "Could not close '$Vend::Cfg->{SessionLockFile}': $!\n";
 	undef $Vend::SessionOpen;
+	return 1;
 }
 
 sub write_session {
@@ -257,15 +293,14 @@
 #::logDebug ("write session id=$Vend::SessionID  name=$Vend::SessionName\n");
 	my $time = time;
     $Vend::Session->{'time'} = $time;
-    my $save = $Vend::Session->{'user'};
-    undef $Vend::Session->{'user'};
-    #undef $Vend::Session->{'arg'};
+	delete $Vend::Session->{values}->{mv_credit_card_number};
+    my $save = delete $Vend::Session->{'user'};
 	for(@Vend::TmpScratch) {
-#::logDebug ("delete TmpScratch=$_");
 		delete $::Scratch->{$_};
 	}
 	$Vend::Session->{username} = $Vend::username;
 	$Vend::Session->{admin} = $Vend::admin;
+	$Vend::Session->{superuser} = $Vend::superuser;
     $s = ! $File_sessions ? uneval_fast($Vend::Session) : $Vend::Session;
     $Vend::SessionDBM{$Vend::SessionName} = $s or 
 		die "Data was not stored in SessionDBM\n";
@@ -334,6 +369,7 @@
 }
 
 sub read_session {
+	my $seed = shift;
     my($s);
 
 #::logDebug ("read session id=$Vend::SessionID  name=$Vend::SessionName\n");
@@ -352,7 +388,7 @@
 		};
 		
 #::logDebug ("Session:\n$s\n");
-	return new_session() unless $s;
+	return new_session($seed) unless $s;
     $Vend::Session = ref $s ? $s : evalr($s);
     die "Could not eval '$s' from session dbm: $@\n" if $@;
 
@@ -360,12 +396,15 @@
 
 	$Vend::username = $Vend::Session->{username};
 	$Vend::admin    = $Vend::Session->{admin};
+	$Vend::superuser   = $Vend::Session->{superuser};
 
 	$Vend::Session->{arg}  = $Vend::Argument;
 
-    $::Values	= $Vend::Session->{'values'};
+    $::Values	= $Vend::Session->{values};
     $::Scratch	= $Vend::Session->{scratch};
     $::Carts	= $Vend::Session->{carts};
+    $Vend::Interpolate::Tmp ||= {};
+    $::Control	= $Vend::Interpolate::Tmp->{control} = [];
 	tie $Vend::Items, 'Vend::Cart';
 }
 
@@ -377,13 +416,15 @@
 sub session_name {
     my($host, $user, $fn, $proxy);
 
+	return $Vend::SessionID if $::Instance->{ExternalCookie};
+
 	if(defined $CGI::user and $CGI::user) {
 		$host = escape_chars($CGI::user);
 	}
-	elsif(defined $CGI::cookieuser) {
+	elsif($CGI::cookieuser) {
 		$host = $CGI::cookieuser;
 	}
-	elsif(defined $CGI::cookiehost) {
+	elsif($CGI::cookiehost) {
 		$host = $CGI::cookiehost;
 	}
 	else {
@@ -406,16 +447,17 @@
 		'arg'		=> $Vend::Argument,
 		'browser'	=> $CGI::useragent,
 		'referer'	=> $CGI::referer,
+		'spider'	=> $CGI::values{mv_tmp_session},
 		'scratch'	=> { %{$Vend::Cfg->{ScratchDefault}} },
 		'values'	=> { %{$Vend::Cfg->{ValuesDefault}} },
 		'carts'		=> {main => []},
+		'levies'	=> {main => []},
     };
 	$Vend::Session->{shost} = $CGI::remote_addr
 		if $CGI::secure;
-	$::Values     = $Vend::Session->{'values'};
+	$::Values     = $Vend::Session->{values};
 	$::Scratch	  = $Vend::Session->{scratch};
-	$::Scratch->{mv_locale} = $Vend::Cfg->{DefaultLocale}
-		if ! $::Scratch->{mv_locale} and $Vend::Cfg->{DefaultLocale};
+	$::Scratch->{mv_locale} ||= $Vend::Cfg->{DefaultLocale};
 	$::Carts	  = $Vend::Session->{carts};
 	tie $Vend::Items, 'Vend::Cart';
 	$::Values->{mv_shipmode} = $Vend::Cfg->{DefaultShipping}
@@ -509,8 +551,8 @@
 
 	$time = $time || time();
 
-	if(defined $Vend::Session->{'values'}->{mv_expire_time}) {
-		$expire = $Vend::Session->{'values'}->{mv_expire_time};
+	if(defined $::Values->{mv_expire_time}) {
+		$expire = $::Values->{mv_expire_time};
 		unless($expire =~ /^\d{6,}$/) {
 			$expire = Vend::Config::time_to_seconds($expire);
 		}
@@ -521,6 +563,39 @@
 
 	return ($expire > $time);
 }	
+
+sub tie_static_dbm {
+	my $rw = shift;
+	untie(%Vend::StaticDBM) if $rw;
+	if($Global::GDBM) {
+        my $flags = $rw ? &GDBM_WRITER : &GDBM_READER;
+        $flags = &GDBM_NEWDB
+            if $rw && (! -f "$Vend::Cfg->{StaticDBM}.gdbm");
+        tie(%Vend::StaticDBM,
+            'GDBM_File',
+            "$Vend::Cfg->{StaticDBM}.gdbm",
+            $flags,
+            $Vend::Cfg->{'FileCreationMask'},
+        )
+        or $Vend::Cfg->{SaveStaticDBM} = delete $Vend::Cfg->{StaticDBM};
+	}
+	elsif ($Global::DB_File) {
+		tie(%Vend::StaticDBM,
+			'DB_File',
+			"$Vend::Cfg->{StaticDBM}.db",
+			($rw ? &O_RDWR | &O_CREAT : &O_RDONLY),
+			$Vend::Cfg->{'FileCreationMask'},
+			)
+		or undef $Vend::Cfg->{StaticDBM};
+	}
+	else {
+        $Vend::Cfg->{SaveStaticDBM} = delete $Vend::Cfg->{StaticDBM};
+	}
+	::logError("Failed to create StaticDBM %s", $Vend::Cfg->{StaticDBM})
+		if $rw && ! $Vend::Cfg->{StaticDBM};
+	return $Vend::Cfg->{StaticDBM} || undef;
+}
+
 
 1;
 



1.2.4.1   +5 -8      interchange/lib/Vend/SessionDB.pm


rev 1.2.4.1, prev_rev 1.2
Index: SessionDB.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/SessionDB.pm,v
retrieving revision 1.2
retrieving revision 1.2.4.1
diff -u -r1.2 -r1.2.4.1
--- SessionDB.pm	12 Jul 2000 03:08:11 -0000	1.2
+++ SessionDB.pm	25 Jan 2003 22:21:28 -0000	1.2.4.1
@@ -1,8 +1,8 @@
-# SessionDB.pm:  stores session information in files
+# Vend::SessionDB - Stores Interchange session information in files
 #
-# $Id: SessionDB.pm,v 1.2 2000/07/12 03:08:11 heins Exp $
+# $Id: SessionDB.pm,v 1.2.4.1 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -19,9 +19,6 @@
 # Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 # MA  02111-1307  USA.
 
-
-# $Id: SessionDB.pm,v 1.2 2000/07/12 03:08:11 heins Exp $
-
 package Vend::SessionDB;
 require Tie::Hash;
 @ISA = qw(Tie::Hash);
@@ -30,7 +27,7 @@
 use Vend::Util;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.2 $, 10);
+$VERSION = substr(q$Revision: 1.2.4.1 $, 10);
 
 my $SessionDB;
 my $SessionLock;
@@ -103,7 +100,7 @@
 	$self->{DB}->set_row($key) unless $self->{DB}->record_exists($key);
 	return $self->{DB}->set_field($key, 'sessionlock', $val) if $locking;
 	$self->{DB}->set_field( $key, 'session', $val);
-    return 1;
+	return 1;
 }
 	
 1;



1.3.4.2   +26 -109   interchange/lib/Vend/SessionFile.pm


rev 1.3.4.2, prev_rev 1.3.4.1
Index: SessionFile.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/SessionFile.pm,v
retrieving revision 1.3.4.1
retrieving revision 1.3.4.2
diff -u -r1.3.4.1 -r1.3.4.2
--- SessionFile.pm	27 Nov 2000 02:35:37 -0000	1.3.4.1
+++ SessionFile.pm	25 Jan 2003 22:21:28 -0000	1.3.4.2
@@ -1,8 +1,8 @@
-# SessionFile.pm:  stores session information in files
+# Vend::SessionFile - Stores Interchange session information in files
 #
-# $Id: SessionFile.pm,v 1.3.4.1 2000/11/27 02:35:37 racke Exp $
+# $Id: SessionFile.pm,v 1.3.4.2 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -19,9 +19,6 @@
 # Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 # MA  02111-1307  USA.
 
-
-# $Id: SessionFile.pm,v 1.3.4.1 2000/11/27 02:35:37 racke Exp $
-
 package Vend::SessionFile;
 require Tie::Hash;
 @ISA = qw(Tie::Hash);
@@ -31,7 +28,7 @@
 use Vend::Util;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.3.4.1 $, 10);
+$VERSION = substr(q$Revision: 1.3.4.2 $, 10);
 
 my $SessionDir;
 my $CommDir;
@@ -40,10 +37,7 @@
 my $SessionLock;
 my %Unlinks;
 my %HaveLock;
-my $Li;
-my $Fi;
 my $Lh;
-my $Fh;
 my $Last;
 my @Each;
 
@@ -52,6 +46,7 @@
 	die "Vend::SessionFile: directory name\n"
 		unless $dir;
 	$SessionDir = $dir;
+	%HaveLock = ();
 	if($nfs) {
 		*lockfile = \*Vend::Util::fcntl_lock;
 		*unlockfile = \*Vend::Util::fcntl_unlock;
@@ -63,67 +58,22 @@
 	return Vend::Util::get_filename(shift, 2, 1, $SessionDir);
 }
 
-sub comm_keyname {
-	my $file = shift;
-	$file =~ m{(.*/(\w+))};
-	return $Vend::Cfg->{IPCdir}
-			? ( Vend::Util::get_filename($2, 2, 1, $Vend::Cfg->{IPCdir} ) )
-			: $1;
-}
-
 sub FETCH {
 	my($self, $key) = @_;
-#::logDebug("fetch $key");
-    $SessionFile = keyname($key);
-    $SessionLock = $SessionFile . ".lock";
+	$SessionFile = keyname($key);
+	$SessionLock = $SessionFile . ".lock";
 	return undef unless -f $SessionFile;
 	my $str;
+#::logDebug("fetch session=$key HaveLock=$HaveLock{$SessionFile}");
 	unless ($HaveLock{$SessionFile}) {
 		$Lh = gensym();
 		open($Lh, "+>>$SessionLock")
 			or die "Can't open '$SessionLock': $!\n";
-		lockfile($Lh, 1, 1);
+		lockfile($Lh, 1, 1)
+			or die "lock $SessionLock: $!\n";
+		$HaveLock{$SessionFile} = 1;
 	}
 	my $ref = Vend::Util::eval_file($SessionFile);
-	if($Vend::Cfg->{IPC}) {
-		$CommDir	= comm_keyname($SessionFile);
-#::logDebug("fetch CommDir=$CommDir");
-		$CommLock = "$CommDir/lock";
-		my $currmask;
-		unless (-d $CommDir) {
-			undef $HaveLock{$SessionFile};
-			$currmask = umask($Vend::Cfg->{IPCmode} ^ 0777);
-			Vend::Util::exists_filename(
-								$SessionFile,
-								2,
-								1,
-								$Vend::Cfg->{IPCdir} || $SessionDir,
-			);
-			mkdir $CommDir, 0777
-				or die "mkdir $CommDir: $!\n";
-		}
-		unless($HaveLock{$SessionFile}) {
-			$Li = gensym();
-			open($Li, "+>>$CommLock")
-				or die "Can't open '$CommLock': $!\n";
-			lockfile($Li, 1, 1)
-				or die "lock $CommLock: $!\n";
-			chmod($CommLock, $Vend::Cfg->{IPCmode} || 0777);
-		}
-		# We know directory pre-existed if $currmask is not defined
-		$ref = {} if ! $ref;
-		if(! defined $currmask) {
-			opendir(COMMDIR, $CommDir);
-			my @handles = grep defined $Vend::Cfg->{IPCkeys}{$_}, readdir COMMDIR;
-			my $ary = $Unlinks{$SessionFile} = [];
-			for(@handles) {
-				$ref->{$_} = Vend::Util::eval_file("$CommDir/$_");
-				push @$ary, "$CommDir/$_";
-			}
-			umask($currmask);
-		}
-	}
-	$HaveLock{$SessionFile} = 1;
 #::logDebug("retrieving from $SessionFile: " . ::uneval($ref));
 	return $ref;
 }
@@ -158,75 +108,42 @@
 # IPC not handled yet
 sub DELETE {
 	my($self,$key) = @_;
-    my $filename = keyname($key);
+	my $filename = keyname($key);
 	unlink $filename;
 	return 1 if $Global::Windows;
-    my $lockname = $filename . ".lock";
+	my $lockname = $filename . ".lock";
 	unlink $lockname;
 }
 
 sub STORE {
 	my($self, $key, $ref) = @_;
 #::logDebug("store $key");
-    $SessionFile = keyname($key);
-    $SessionLock = $SessionFile . ".lock";
-    unlink $SessionFile;
+	$SessionFile = keyname($key);
+	$SessionLock = $SessionFile . ".lock";
+	unlink $SessionFile;
+#::logDebug("store session=$key HaveLock=$HaveLock{$SessionFile}");
 	unless ($HaveLock{$SessionFile}) {
 		$Lh = gensym();
 		open($Lh, "+>>$SessionLock")
 			or die "Can't open '$SessionLock': $!\n";
 		lockfile($Lh, 1, 1)
 			or die "lock $SessionLock: $!\n";
-		
+		$HaveLock{$SessionFile} = 1;
+#::logDebug("locked $SessionFile");
 	}
-	if($Vend::Cfg->{IPC}) {
-		$CommDir = comm_keyname($SessionFile);
-#::logDebug("CommDir=$CommDir exists=" . -d $CommDir);
-		my $currmask = umask($Vend::Cfg->{IPCmode} ^ 0777);
-		unless(-d $CommDir) {
-			Vend::Util::exists_filename(
-								$SessionFile,
-								2,
-								1,
-								$Vend::Cfg->{IPCdir} || $SessionDir,
-			);
-#::logDebug("mkdir $CommDir at store");
-			undef $HaveLock{$SessionFile};
-			mkdir $CommDir, 0777
-				or die "mkdir $CommDir: $!\n";
-		}
-#::logDebug("CommDir=$CommDir exists=" . -d $CommDir);
-		unless ($HaveLock{$SessionFile}) {
-			$CommLock = "$CommDir/lock";
-			$Li = gensym();
-			open($Li, "+>>$CommLock")
-				or die "creat $CommLock: $!\n";
-			lockfile($Li, 1, 1)
-				or die "lock '$CommLock': $!\n";
-			chmod($CommLock, $Vend::Cfg->{IPCmode} || 0777);
-#::logDebug("locked $CommLock");
-		}
-		elsif ($Unlinks{$SessionFile})  {
-#::logDebug("unlinking unlinks");
-			unlink(@{$Unlinks{$SessionFile}});
-		}
-		if($Vend::Cfg->{IPCdir}) {
-#::logDebug("creating IPC copy");
-			Vend::Util::uneval_file($ref,"$CommDir/Session");
-		}
-		umask($currmask);
-	}
-	$HaveLock{$SessionFile} = 1;
 #::logDebug("storing in $SessionFile: " . ::uneval($ref));
 	Vend::Util::uneval_file($ref,$SessionFile);
 }
 	
 sub DESTROY {
 	my($self) = @_;
-	unlockfile($Li) and close($Li)
-		if $Li;
-	unlockfile($Lh)
-		and delete $HaveLock{$SessionFile};
+#::logDebug("Destroy, have_lock=$HaveLock{$SessionFile}");
+	if($HaveLock{$SessionFile}) {
+		unlockfile($Lh)
+			or die "cannot unlock file: $!";
+#::logDebug("Destroy unlocked $SessionFile");
+		delete $HaveLock{$SessionFile};
+	}
 	close($Lh);
 	undef $self;
 }



1.2.4.2   +3 -4      interchange/lib/Vend/Tags.pm


rev 1.2.4.2, prev_rev 1.2.4.1
Index: Tags.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Tags.pm,v
retrieving revision 1.2.4.1
retrieving revision 1.2.4.2
diff -u -r1.2.4.1 -r1.2.4.2
--- Tags.pm	20 Oct 2000 10:18:43 -0000	1.2.4.1
+++ Tags.pm	25 Jan 2003 22:21:28 -0000	1.2.4.2
@@ -1,9 +1,8 @@
-#!/usr/bin/perl
-# Tags.pm - Interpret Interchange tags for Safe
+# Vend::Tags - Interpret Interchange tags for Safe
 # 
-# $Id: Tags.pm,v 1.2.4.1 2000/10/20 10:18:43 racke Exp $
+# $Id: Tags.pm,v 1.2.4.2 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by



1.7.4.1   +81 -81    interchange/lib/Vend/TextSearch.pm


rev 1.7.4.1, prev_rev 1.7
Index: TextSearch.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/TextSearch.pm,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- TextSearch.pm	27 Sep 2000 22:17:06 -0000	1.7
+++ TextSearch.pm	25 Jan 2003 22:21:28 -0000	1.7.4.1
@@ -1,10 +1,10 @@
-# Vend/TextSearch.pm:  Search indexes with Perl
+# Vend::TextSearch - Search indexes with Perl
 #
-# $Id: TextSearch.pm,v 1.7 2000/09/27 22:17:06 heins Exp $
+# $Id: TextSearch.pm,v 1.7.4.1 2003/01/25 22:21:28 racke Exp $
 #
-# ADAPTED FOR USE WITH INTERCHANGE from Search::TextSearch
+# Adapted for use with Interchange from Search::TextSearch
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -28,37 +28,37 @@
 use vars qw(@ISA);
 @ISA = qw(Vend::Search);
 
-$VERSION = substr(q$Revision: 1.7 $, 10);
+$VERSION = substr(q$Revision: 1.7.4.1 $, 10);
 
 use Search::Dict;
 use strict;
 
 sub array {
 	my ($s, $opt) = @_;
-	$s->{mv_list_only} = 1;
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 sub hash {
 	my ($s, $opt) = @_;
 	$s->{mv_return_reference} = 'HASH';
-	$s->{mv_list_only} = 1;
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 sub list {
 	my ($s, $opt) = @_;
-	$s->{mv_list_only} = 1;
 	$s->{mv_return_reference} = 'LIST';
-	Vend::Scan::perform_search($opt, undef, $s);
+	$s->{mv_list_only} = 1; # makes perform_search only return results array
+	return Vend::Scan::perform_search($opt, undef, $s);
 }
 
 my %Default = (
-        matches                 => 0,
-        mv_head_skip            => 1,
-        mv_index_delim          => "\t",
-        mv_matchlimit           => 50,
-        mv_min_string           => 1,
+		matches                 => 0,
+		mv_head_skip            => 1,
+		mv_index_delim          => "\t",
+		mv_matchlimit           => 50,
+		mv_min_string           => 1,
 	);
 
 
@@ -66,22 +66,22 @@
 	my ($s, $options) = @_;
 
 	@{$s}{keys %Default} = (values %Default);
-    $s->{mv_base_directory}     = $Vend::Cfg->{ProductDir} || 'products',
-    $s->{mv_begin_string}       = [];
-    $s->{mv_all_chars}	        = [1];
-    $s->{mv_case}               = [];
-    $s->{mv_column_op}          = [];
-    $s->{mv_negate}             = [];
-    $s->{mv_numeric}            = [];
-    $s->{mv_orsearch}           = [];
-    $s->{mv_searchspec}	        = [];
-    $s->{mv_search_group}       = [];
-    $s->{mv_search_field}       = [];
-    $s->{mv_search_file}        = $::Variable->{MV_DEFAULT_SEARCH_FILE}
+	$s->{mv_base_directory}     = $Vend::Cfg->{ProductDir} || 'products',
+	$s->{mv_begin_string}       = [];
+	$s->{mv_all_chars}	        = [1];
+	$s->{mv_case}               = [];
+	$s->{mv_column_op}          = [];
+	$s->{mv_negate}             = [];
+	$s->{mv_numeric}            = [];
+	$s->{mv_orsearch}           = [];
+	$s->{mv_searchspec}	        = [];
+	$s->{mv_search_group}       = [];
+	$s->{mv_search_field}       = [];
+	$s->{mv_search_file}        = $::Variable->{MV_DEFAULT_SEARCH_FILE}
 									|| ['products.asc'];
-    $s->{mv_searchspec}         = [];
-    $s->{mv_sort_option}        = [];
-    $s->{mv_substring_match}    = [];
+	$s->{mv_searchspec}         = [];
+	$s->{mv_sort_option}        = [];
+	$s->{mv_substring_match}    = [];
 
 	for(keys %$options) {
 		$s->{$_} = $options->{$_};
@@ -91,7 +91,7 @@
 }
 
 sub new {
-    my ($class, %options) = @_;
+	my ($class, %options) = @_;
 	my $s = new Vend::Search;
 	bless $s, $class;
 	$s->init(\%options);
@@ -140,20 +140,10 @@
 	$s->{mv_return_delim} = $s->{mv_index_delim}
 		unless defined $s->{mv_return_delim};
 
-    if(ref $s->{mv_range_look}) {
-        unless( scalar(@{$s->{mv_range_look}}) == scalar(@{$s->{mv_range_min}}) and
-                scalar(@{$s->{mv_range_look}}) == scalar(@{$s->{mv_range_max}}) ) {
-			$s->{mv_search_warning}
-				= "Must have min and max values for range -- aborting range look.";
-			undef $s->{mv_range_look};
-		}
-	}
 	@specs = @{$s->{mv_searchspec}};
 
 	@pats = $s->spec_check(@specs);
 
-	return undef if $s->{matches} == -1;
-
 	if ($s->{mv_coordinate}) {
 		undef $f;
 	}
@@ -194,19 +184,19 @@
 
 		# Get field names only if no sort (will throw it off) or
 		# not already defined
-        if($s->{mv_head_skip} == 1) {
-            chomp($field_names = <SEARCH>);
-        }
-        elsif($s->{mv_head_skip} > 1) {
-            while(<SEARCH>) {
+		if($s->{mv_head_skip} == 1) {
+			chomp($field_names = <SEARCH>);
+		}
+		elsif($s->{mv_head_skip} > 1) {
+			while(<SEARCH>) {
 				chomp($field_names = $_);
-                last if $. >= $s->{mv_head_skip};
-            }
-        }
+				last if $. >= $s->{mv_head_skip};
+			}
+		}
 		if($field_names) {
 			$field_names =~ s/^\s+//;
 			my @laundry = (qw/mv_search_field mv_range_look mv_return_fields/);
-            $s->hash_fields(
+			$s->hash_fields(
 						[ split /\Q$s->{mv_index_delim}/, $field_names ],
 						@laundry,
 			);
@@ -216,14 +206,15 @@
 		my $prospect;
 
 		eval {
-			($limit_sub, $prospect) = $s->get_limit($f);
+			# 1 refers to fact you have to make ref from line
+			($limit_sub, $prospect) = $s->get_limit($f, 1);
 		};
 
 		$@  and  return $s->search_error("Limit subroutine creation: $@");
 
 		$f = $prospect if $prospect;
 
-		eval {($return_sub, $delayed_return) = $s->get_return()};
+		eval {($return_sub, $delayed_return) = $s->get_return( undef, 1 )};
 
 		$@  and  return $s->search_error("Return subroutine creation: $@");
 
@@ -267,59 +258,62 @@
 
 		if($s->{mv_dict_end} && defined $limit_sub) {
 			while(<SEARCH>) {
-#::logDebug("$_");
-				last if &$dict_limit($_);
-				next unless ! defined $f or &$f();
-				next unless &$limit_sub($_);
+				last if $dict_limit->($_);
+				next unless $limit_sub->($_);
+				chomp;
 				(push @out, $searchfile and last)
 					if $s->{mv_return_file_name};
-				push @out, &$return_sub($_);
+				push @out, $return_sub->($_);
 			}
 		}
 		elsif($s->{mv_dict_end}) {
 			while(<SEARCH>) {
-				last if &$dict_limit($_);
+				last if $dict_limit->($_);
 				next unless &$f();
+				chomp;
 				(push @out, $searchfile and last)
 					if $s->{mv_return_file_name};
-				push @out, &$return_sub($_);
+				push @out, $return_sub->($_);
 			}
 		}
-		elsif(! defined $f and defined $limit_sub) {
+		elsif($limit_sub) {
+#::logDebug("limit_sub");
 			while(<SEARCH>) {
-				next unless &$limit_sub($_);
+				next unless $limit_sub->($_);
+				chomp;
 				(push @out, $searchfile and last)
 					if $s->{mv_return_file_name};
-				push @out, &$return_sub($_);
+				push @out, $return_sub->($_);
 			}
 		}
-		elsif(defined $limit_sub) {
-			while(<SEARCH>) {
-				next unless &$f();
-				next unless &$limit_sub($_);
-				(push @out, $searchfile and last)
-					if $s->{mv_return_file_name};
-				push @out, &$return_sub($_);
-			}
-		}
-		elsif (!defined $f) {
+		elsif (! $f) {
 			return $s->search_error('No search definition');
 		}
 		else {
+#::logDebug("no limit_sub");
 			while(<SEARCH>) {
 				next unless &$f();
+				chomp;
 				(push @out, $searchfile and last)
 					if $s->{mv_return_file_name};
-				push @out, &$return_sub($_);
+				push @out, $return_sub->($_);
 			}
 		}
 		close SEARCH;
 		$s->restore_specs();
 	}
 
+#::logDebug("before delayed return: self=" . ::Vend::Util::uneval_it({%$s}));
+#::logDebug("before delayed return: out=" . ::Vend::Util::uneval_it(\@out));
+
+	# Search the results and return
+	if($s->{mv_next_search}) {
+		@out = $s->search_reference(\@out);
+#::logDebug("did next_search: " . ::uneval(\@out));
+	}
+
 	$s->{matches} = scalar(@out);
 
-#::logDebug("before delayed return: self=" . ::Vend::Util::uneval_it({%$s}));
 	if($delayed_return and $s->{matches} > 0) {
 		$s->hash_fields($s->{mv_field_names}, qw/mv_sort_field/);
 #::logDebug("after hash fields: self=" . ::Vend::Util::uneval_it({%$s}));
@@ -328,16 +322,22 @@
 		@out = map { $delayed_return->($_) } @out;
 	}
 #::logDebug("after delayed return: self=" . ::Vend::Util::uneval_it({%$s}));
+#::logDebug("after delayed return: out=" . ::Vend::Util::uneval_it(\@out));
 
 	if($s->{mv_unique}) {
 		my %seen;
 		@out = grep ! $seen{$_->[0]}++, @out;
-		$s->{matches} = scalar(@out);
 	}
 
-    if ($s->{matches} > $s->{mv_matchlimit}) {
-        $s->save_more(\@out)
-            or ::logError("Error saving matches: $!");
+	if($s->{mv_max_matches} > 0) {
+		splice @out, $s->{mv_max_matches};
+	}
+
+	$s->{matches} = scalar(@out);
+
+	if ($s->{matches} > $s->{mv_matchlimit} and $s->{mv_matchlimit} > 0) {
+		$s->save_more(\@out)
+			or ::logError("Error saving matches: $!");
 		if ($s->{mv_first_match}) {
 			splice(@out,0,$s->{mv_first_match});
 			$s->{mv_next_pointer} = $s->{mv_first_match} + $s->{mv_matchlimit};
@@ -378,8 +378,8 @@
 					if $s->{mv_next_pointer} > $s->{matches};
 			}
 		}
-        $#out = $s->{mv_matchlimit} - 1;
-    }
+		$#out = $s->{mv_matchlimit} - 1;
+	}
 
 	if(! $s->{mv_return_reference}) {
 		$s->{mv_results} = \@out;



1.3.4.4   +3 -3      interchange/lib/Vend/Track.pm


rev 1.3.4.4, prev_rev 1.3.4.3
Index: Track.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Track.pm,v
retrieving revision 1.3.4.3
retrieving revision 1.3.4.4
diff -u -r1.3.4.3 -r1.3.4.4
--- Track.pm	11 Sep 2001 10:14:25 -0000	1.3.4.3
+++ Track.pm	25 Jan 2003 22:21:28 -0000	1.3.4.4
@@ -1,8 +1,8 @@
 # Vend::Track - Interchange User Tracking
 #
-# $Id: Track.pm,v 1.3.4.3 2001/09/11 10:14:25 racke Exp $
+# $Id: Track.pm,v 1.3.4.4 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 2000 by Stefan Hornburg <racke@linuxia.de>
+# Copyright (C) 2000-2002 by Stefan Hornburg <racke@linuxia.de>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -35,7 +35,7 @@
 require Exporter;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.3.4.3 $, 10);
+$VERSION = substr(q$Revision: 1.3.4.4 $, 10);
 
 @ISA = qw(Exporter);
 



1.13.4.6  +483 -140  interchange/lib/Vend/UserDB.pm


rev 1.13.4.6, prev_rev 1.13.4.5
Index: UserDB.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/UserDB.pm,v
retrieving revision 1.13.4.5
retrieving revision 1.13.4.6
diff -u -r1.13.4.5 -r1.13.4.6
--- UserDB.pm	18 May 2001 18:11:52 -0000	1.13.4.5
+++ UserDB.pm	25 Jan 2003 22:21:28 -0000	1.13.4.6
@@ -1,16 +1,29 @@
-#!/usr/bin/perl
+# Vend::UserDB - Interchange user database functions
 #
-# $Id: UserDB.pm,v 1.13.4.5 2001/05/18 18:11:52 racke Exp $
+# $Id: UserDB.pm,v 1.13.4.6 2003/01/25 22:21:28 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# **** ALL RIGHTS RESERVED ****
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
 
 package Vend::UserDB;
 
-$VERSION = substr(q$Revision: 1.13.4.5 $, 10);
+$VERSION = substr(q$Revision: 1.13.4.6 $, 10);
 
-use vars qw! $VERSION @S_FIELDS @B_FIELDS @P_FIELDS @I_FIELDS %S_to_B %B_to_S!;
+use vars qw!
+	$VERSION
+	@S_FIELDS @B_FIELDS @P_FIELDS @I_FIELDS
+	%S_to_B %B_to_S
+	$USERNAME_GOOD_CHARS
+!;
 
 use Vend::Data;
 use Vend::Util;
@@ -184,7 +197,6 @@
 
 @B_FIELDS = ( 
 qw!
-
 	b_nickname
 	b_name
 	b_fname
@@ -215,8 +227,8 @@
 
 =cut
 
-# valid characters in user names
-my $GOOD_CHARS = '[-A-Za-z0-9_@.]';
+# user name and password restrictions
+$USERNAME_GOOD_CHARS = '[-A-Za-z0-9_@.]';
 
 @P_FIELDS = qw ( p_nickname email fax email_copy phone_night mail_list fax_order );
 
@@ -276,15 +288,18 @@
 		@I_FIELDS = split /[\s,]+/, $options{ignore};
 	}
 	my $self = {
-			USERNAME  	=>	$options{username}	||
-							$Vend::Session->{username} ||
-							$CGI::values{mv_username} || '',
+			USERNAME  	=> $options{username}	||
+						   $Vend::username		||
+						   $CGI::values{mv_username} ||
+						   '',
 			OLDPASS  	=> $options{oldpass}	|| $CGI::values{mv_password_old} || '',
 			PASSWORD  	=> $options{password}	|| $CGI::values{mv_password} || '',
 			VERIFY  	=> $options{verify}		|| $CGI::values{mv_verify}	 || '',
 			NICKNAME   	=> $options{nickname}	|| '',
 			PROFILE   	=> $options{profile}	|| '',
 			LAST   		=> '',
+			USERMINLEN	=> $options{userminlen}	|| 2,
+			PASSMINLEN	=> $options{passminlen}	|| 4,
 			CRYPT  		=> defined $options{'crypt'}
 							? $options{'crypt'}
 							: ! $::Variable->{MV_NO_CRYPT},
@@ -292,16 +307,21 @@
 			PRESENT		=>	{ },
 			DB_ID		=>	$options{database} || 'userdb',
 			OPTIONS		=>	\%options,
+			OUTBOARD	=>  $options{outboard}	|| '',
 			LOCATION	=>	{
 						USERNAME	=> $options{user_field} || 'username',
 						BILLING		=> $options{bill_field} || 'accounts',
 						SHIPPING	=> $options{addr_field} || 'address_book',
 						PREFERENCES	=> $options{pref_field} || 'preferences',
+						FEEDBACK	=> $options{feedback_field}   || 'feedback',
+						PRICING		=> $options{pricing_field} || 'price_level',
 						ORDERS     	=> $options{ord_field}  || 'orders',
 						CARTS		=> $options{cart_field} || 'carts',
 						PASSWORD	=> $options{pass_field} || 'password',
 						LAST		=> $options{time_field} || 'mod_time',
 						EXPIRATION	=> $options{expire_field} || 'expiration',
+						OUTBOARD_KEY=> $options{outboard_key_col},
+						SUPER		=> $options{super_field}|| 'super',
 						ACL			=> $options{acl}		|| 'acl',
 						FILE_ACL	=> $options{file_acl}	|| 'file_acl',
 						DB_ACL		=> $options{db_acl}		|| 'db_acl',
@@ -314,9 +334,9 @@
 
 	return $self if $options{no_open};
 
-	set_db($self) or die "user database $self->{DB_ID} does not exist.\n";
+	set_db($self) or die ::errmsg("user database %s does not exist.", $self->{DB_ID}) . "\n";
 
-	return $self;
+	return $Vend::user_object = $self;
 }
 
 sub create_db {
@@ -408,12 +428,12 @@
 	my ($self,%options) = @_;
 
 	if(! defined $self->{PRESENT}{$self->{LOCATION}{ACL}}) {
-		$self->{ERROR} = 'No ACL field present.';
+		$self->{ERROR} = ::errmsg('No ACL field present.');
 		return undef;
 	}
 
 	if(not $options{location}) {
-		$self->{ERROR} = 'No location to check.';
+		$self->{ERROR} = ::errmsg('No location to check.');
 		return undef;
 	}
 
@@ -426,12 +446,12 @@
 	my ($self,%options) = @_;
 
 	if(!$self->{PRESENT}{$self->{LOCATION}{ACL}}) {
-		$self->{ERROR} = 'No ACL field present.';
+		$self->{ERROR} = ::errmsg('No ACL field present.');
 		return undef;
 	}
 
 	if(!$options{location}) {
-		$self->{ERROR} = 'No location to set.';
+		$self->{ERROR} = ::errmsg('No location to set.');
 		return undef;
 	}
 
@@ -480,7 +500,7 @@
 	else {
 		$f->{$options{location}} = $options{mode} || 'rw';
 	}
-	my $return = $self->{DB}->set_field( $self->{USERNAME}, $loc, Vend::Util::uneval_it($f) );
+	my $return = $self->{DB}->set_field( $self->{USERNAME}, $loc, uneval_it($f) );
 	return $return if $options{show};
 	return;
 }
@@ -568,15 +588,24 @@
 	if($self->{OPTIONS}->{scratch}) {
 		my (@s) = split /[\s,]+/, $self->{OPTIONS}{scratch} ;
 		@scratch{@s} = @s;
-#::logError("scratch ones: " . join " ", @s);
 	}
 
 	for(@fields) {
 		if($scratch{$_}) {
-			delete $::Scratch->{$_};
+			if (exists $Vend::Cfg->{ScratchDefault}->{$_}) {
+				$::Scratch->{$_} = $Vend::Cfg->{ScratchDefault}->{$_};
+			}
+			else {
+				delete $::Scratch->{$_};
+			}
 		}
 		else {
-			delete $::Values->{$_};
+			if (exists $Vend::Cfg->{ValuesDefault}->{$_}) {
+				$::Values->{$_} = $Vend::Cfg->{ValuesDefault}->{$_};
+			}
+			else{
+				delete $::Values->{$_};
+			}
 			delete $CGI::values{$_};
 		}
 	}
@@ -589,8 +618,11 @@
 
 	@fields = @{ $self->{DB_FIELDS} } unless @fields;
 
-	unless ( $self->{DB}->record_exists($self->{USERNAME}) ) {
-		$self->{ERROR} = "username $self->{USERNAME} does not exist.";
+	my $db = $self->{DB}
+		or die ::errmsg("No user database found.");
+
+	unless ( $db->record_exists($self->{USERNAME}) ) {
+		$self->{ERROR} = ::errmsg("username %s does not exist.", $self->{USERNAME});
 		return undef;
 	}
 
@@ -601,21 +633,45 @@
 		$ignore{$_} = 1;
 	}
 
+	my %outboard;
+	if($self->{OUTBOARD}) {
+		%outboard = split /[\s=,]+/, $self->{OUTBOARD};
+		push @fields, keys %outboard;
+	}
+
 	if($self->{OPTIONS}->{scratch}) {
 		my (@s) = split /[\s,]+/, $self->{OPTIONS}{scratch} ;
 		@scratch{@s} = @s;
 #::logError("scratch ones: " . join " ", @s);
 	}
+
+	my @needed;
+	my $row = $db->row_hash($self->{USERNAME});
+	my $outkey = $self->{LOCATION}->{OUTBOARD_KEY}
+				 ? $row->{$self->{LOCATION}->{OUTBOARD_KEY}}
+				 : $self->{USERNAME};
+
+
 	for(@fields) {
 		if($ignore{$_}) {
 			$self->{PRESENT}->{$_} = 1;
 			next;
 		}
+		my $val;
+		if ($outboard{$_}) {
+			my ($t, $c, $k) = split /:+/, $outboard{$_};
+			$val = ::tag_data($t, ($c || $_), $outkey, { foreign => $k });
+		}
+		else {
+			$val = $row->{$_};
+		}
+
 		if($scratch{$_}) {
-			$::Scratch->{$_} = $self->{DB}->field($self->{USERNAME}, $_);	
+			$::Scratch->{$_} = $val;
 			next;
 		}
-		$::Values->{$_} = $self->{DB}->field($self->{USERNAME}, $_);	
+		$::Values->{$_} = $val;
+
 	}
 
 	my $area;
@@ -623,7 +679,7 @@
 		my $f = $self->{LOCATION}->{$area};
 		if ($self->{PRESENT}->{$f}) {
 			my $s = $self->get_hash($area);
-			die "Bad structure in $f: $@" if $@;
+			die ::errmsg("Bad structure in %s: %s", $f, $@) if $@;
 			$::Values->{$f} = join "\n", sort keys %$s;
 		}
 	}
@@ -640,8 +696,10 @@
 
 	@fields = @{$self->{DB_FIELDS}};
 
-	unless ( $self->{DB}->record_exists($self->{USERNAME}) ) {
-		$self->{ERROR} = "username $self->{USERNAME} does not exist.";
+	my $db = $self->{DB};
+
+	unless ( $db->record_exists($self->{USERNAME}) ) {
+		$self->{ERROR} = ::errmsg("username %s does not exist.", $self->{USERNAME});
 		return undef;
 	}
 	my %scratch;
@@ -651,17 +709,87 @@
 		@scratch{@s} = @s;
 	}
 
+	my $val;
+	my %outboard;
+	if($self->{OUTBOARD}) {
+		%outboard = split /[\s=,]+/, $self->{OUTBOARD};
+		push @fields, keys %outboard;
+	}
+
+	my @bfields;
+	my @bvals;
+
+  eval {
 	for( @fields ) {
 #::logDebug("set_values saving $_ as $::Values->{$_}\n");
+		my $val;
 		if ($scratch{$_}) {
-			$self->{DB}->set_field($user, $_, $::Scratch->{$_})
+			$val = $::Scratch->{$_}
 				if defined $::Scratch->{$_};	
-			next;
 		}
-		$self->{DB}->set_field($user, $_, $::Values->{$_})
-			if defined $::Values->{$_};	
+		else {
+			$val = $::Values->{$_}
+				if defined $::Values->{$_};	
+		}
+
+		next if ! defined $val;
+
+		if($outboard{$_}) {
+			my ($t, $c, $k) = split /:+/, $outboard{$_};
+			::tag_data($t, ($c || $_), $self->{USERNAME}, { value => $val, foreign => $k });
+		}
+		elsif ($db->test_column($_)) {
+			push @bfields, $_;
+			push @bvals, $val;
+		}
+		else {
+			::logDebug( ::errmsg(
+							"cannot set unknown userdb field $_ to: %s",
+							$_,
+							$val,
+						)
+					);
+		}
 	}
-	1;
+	
+	if(@bfields) {
+		$db->set_slice($user, \@bfields, \@bvals);
+	}
+  };
+
+	if($@) {
+	  my $msg = ::errmsg("error saving values in userdb: %s", $@);
+	  $self->{ERROR} = $msg;
+	  ::logError($msg);
+	  return undef;
+	}
+
+# Changes made to support Accounting Interface.
+
+	if(my $l = $Vend::Cfg->{Accounting}) {
+		my %hashvar;
+		my $indexvar = 0;
+		while ($indexvar <= (scalar @bfields)) {
+			$hashvar{ $bfields[$indexvar] } = $bvals[$indexvar];
+			$indexvar++;
+		};
+		my $obj;
+		my $class = $l->{Class};
+		eval {
+			$obj = $class->new;
+		};
+
+		if($@) {
+			die errmsg(
+				"Failed to save customer data with accounting system %s: %s",
+				$class,
+				$@,
+				);
+		}
+		my $returnval = $obj->save_customer_data($user, \%hashvar);
+	}
+
+	return 1;
 }
 
 sub set_billing {
@@ -770,18 +898,16 @@
 
 	my $nick_field = shift @fields;
 	my $nick = $self->{NICKNAME} || $::Values->{$nick_field};
-	$nick =~ s/^[\0\s]+//;
-	$nick =~ s/[\0\s]+.*//;
 
 	delete $self->{$name}{$nick};
 
 	my $field_name = $self->{LOCATION}->{$name};
 	unless($self->{PRESENT}->{$field_name}) {
-		$self->{ERROR} = '$field_name field not present to set $name';
+		$self->{ERROR} = ::errmsg('%s field not present to set %s', $field_name, $name);
 		return undef;
 	}
 
-	my $s = ::uneval_it($self->{$name});
+	my $s = uneval_it($self->{$name});
 
 	$self->{DB}->set_field( $self->{USERNAME}, $field_name, $s);
 
@@ -815,11 +941,11 @@
 
 	my $field_name = $self->{LOCATION}->{$name};
 	unless($self->{PRESENT}->{$field_name}) {
-		$self->{ERROR} = '$field_name field not present to set $name';
+		$self->{ERROR} = ::errmsg('%s field not present to set %s', $field_name, $name);
 		return undef;
 	}
 
-	my $s = ::uneval_it($self->{$name});
+	my $s = uneval_it($self->{$name});
 
 	$self->{DB}->set_field( $self->{USERNAME}, $field_name, $s);
 
@@ -841,13 +967,13 @@
 
 		if($s) {
 			$self->{$name} = $ready->reval($s);
-			die "Bad structure in $field_name: $@" if $@;
+			die ::errmsg("Bad structure in %s: %s", $field_name, $@) if $@;
 		}
 		else {
 			$self->{$name} = {};
 		}
 
-		die "eval failed?"				unless ref $self->{$name};
+		die ::errmsg("eval failed?") . "\n"		unless ref $self->{$name};
 	};
 
 	if($@) {
@@ -864,7 +990,7 @@
 		$nick =~ s/[\0\s]+.*//;
 		$::Values->{$nick_field} = $nick;
 		$CGI::values{$nick_field} = $nick if $self->{CGI};
-		die "no nickname?" unless $nick;
+		die ::errmsg("no nickname?") unless $nick;
 	};
 
 	if($@) {
@@ -892,12 +1018,12 @@
 		if ref $_[0];
 
 	my(%options) = @_;
+	my ($user_data, $pw);
 
-	# Note that this trailing newline is important! The string is used in a
-	# die() statement, and without a trailing newline, Perl will append path
-	# and line info, which should be avoided.
-	my $stock_error = ::errmsg("Invalid user name or password.\n");
-
+	# Show this generic error message on login page to avoid
+	# helping would-be intruders
+	my $stock_error = ::errmsg("Invalid user name or password.");
+	
 	eval {
 		unless($self) {
 			$self = new Vend::UserDB %options;
@@ -920,37 +1046,108 @@
 		# We specifically check for login attempts with group names to see if
 		# anyone is trying to exploit a former vulnerability in the demo catalog.
 		if ($self->{USERNAME} =~ /^:/) {
-			logError("Attempted login with group name '%s'",
+			logError("Denied attempted login with group name '%s'",
 				$self->{USERNAME});
-			die $stock_error;
+			die $stock_error, "\n";
 		}
-		if ($self->{USERNAME} !~ m{^$GOOD_CHARS+$}) {
-			logError("Attempted login with illegal user name '%s'",
-				$self->{USERNAME});
-			die $stock_error;
+
+		# Username must be long enough
+		if (length($self->{USERNAME}) < $self->{USERMINLEN}) {
+			logError("Denied attempted login for user name '%s'; must have at least %s characters",
+				$self->{USERNAME}, $self->{USERMINLEN});
+			die $stock_error, "\n";
 		}
-		unless ($self->{DB}->record_exists($self->{USERNAME})) {
-			logError("Attempted login with nonexistent user name '%s'",
+
+		# Username must contain only valid characters
+		if ($self->{USERNAME} !~ m{^$USERNAME_GOOD_CHARS+$}) {
+			logError("Denied attempted login for user name '%s' with illegal characters",
 				$self->{USERNAME});
-			die $stock_error;
+			die $stock_error, "\n";
 		}
-		my $db_pass = $self->{DB}->field(
-						$self->{USERNAME},
-						$self->{LOCATION}{PASSWORD},
-						);
-		my $pw = $self->{PASSWORD};
-		if ($pw =~ /^\s*$/) {
-			logError("Attempted login by user '%s' with empty password",
-				$self->{USERNAME});
-			die $stock_error;
+
+		# Fail if password is too short
+		if (length($self->{PASSWORD}) < $self->{PASSMINLEN}) {
+			logError("Denied attempted login with user name '%s' and password less than %s characters",
+				$self->{USERNAME}, $self->{PASSMINLEN});
+			die $stock_error, "\n";
+		}
+
+		# Allow entry to global AdminUser without checking access database
+		ADMINUSER: {
+			if ($Global::AdminUser) {
+				my $pwinfo = $Global::AdminUser;
+				$pwinfo =~ s/^\s+//; $pwinfo =~ s/\s+$//;
+				my ($adminuser, $adminpass) = split /[\s:]+/, $pwinfo;
+				last ADMINUSER unless $adminuser eq $self->{USERNAME};
+				unless ($adminpass) {
+					logError("Refusing to use AdminUser variable with user '%s' and empty password", $adminuser);
+					last ADMINUSER;
+				}
+				my $test = $Global::Variable->{MV_NO_CRYPT}
+						 ? $self->{PASSWORD}
+						 : crypt($self->{PASSWORD}, $adminpass);
+				if ($test eq $adminpass) {
+					$user_data = {};
+					$Vend::admin = $Vend::superuser = 1;
+					logError("Successful superuser login by AdminUser '%s'", $adminuser);
+				} else {
+					logError("Password given with user name '%s' didn't match AdminUser password", $adminuser);
+				}
+			}
 		}
-		if($self->{CRYPT}) {
-			$self->{PASSWORD} = crypt($pw,$db_pass);
+
+		my $udb = $self->{DB};
+		my $foreign = $self->{OPTIONS}{indirect_login};
+
+		if($foreign) {
+			my $uname = ($self->{PASSED_USERNAME} ||= $self->{USERNAME});
+			my $ufield = $self->{LOCATION}{USERNAME};
+			$uname = $udb->quote($uname);
+			my $q = "select $ufield from $self->{DB_ID} where $foreign = $uname";
+#::logDebug("indirect login query: $q");
+			my $ary = $udb->query($q)
+				or do {
+					my $msg = ::errmsg( "Database access error for query: %s", $q);
+					die "$msg\n";
+				};
+			@$ary == 1
+				or do {
+					logError(
+						"Denied attempted login with nonexistent (indirect from %s) user name %s",
+						$foreign,
+						$uname,
+						$self->{USERNAME},
+					);
+					die $stock_error, "\n";
+				};
+			$self->{USERNAME} = $ary->[0][0];
 		}
-		unless ($self->{PASSWORD} eq $db_pass) {
-			logError("Attempted login by user '%s' with incorrect password",
-				$self->{USERNAME});
-			die $stock_error;
+
+		# If not superuser, an entry must exist in access database
+		unless ($Vend::superuser) {
+			unless ($udb->record_exists($self->{USERNAME})) {
+				logError("Denied attempted login with nonexistent user name '%s'",
+					$self->{USERNAME});
+				die $stock_error, "\n";
+			}
+			unless ($user_data = $udb->row_hash($self->{USERNAME})) {
+				logError("Login denied after failed fetch of user data for user '%s'",
+					$self->{USERNAME});
+				die $stock_error, "\n";
+			}
+			my $db_pass = $user_data->{ $self->{LOCATION}{PASSWORD} };
+			unless ($db_pass) {
+				logError("Refusing to use blank password from '%s' database for user '%s'", $self->{DB_ID}, $self->{USERNAME});
+				die $stock_error, "\n";
+			}
+			$pw = $self->{PASSWORD};
+			$self->{PASSWORD} = crypt($pw, $db_pass) if $self->{CRYPT};
+			unless ($self->{PASSWORD} eq $db_pass) {
+				logError("Denied attempted login by user '%s' with incorrect password",
+					$self->{USERNAME});
+				die $stock_error, "\n";
+			}
+			logError("Successful login by user '%s'", $self->{USERNAME});
 		}
 
 		if($self->{PRESENT}->{ $self->{LOCATION}{EXPIRATION} } ) {
@@ -958,7 +1155,7 @@
 			my $cmp = $now;
 			$cmp = POSIX::strftime("%Y%m%d%H%M", localtime($now))
 				unless $self->{OPTIONS}->{unix_time};
-			my $exp = $self->{DB}->field(
+			my $exp = $udb->field(
 						$self->{USERNAME},
 						$self->{LOCATION}{EXPIRATION},
 						);
@@ -972,20 +1169,29 @@
 		username_cookies($self->{USERNAME}, $pw) 
 			if $Vend::Cfg->{CookieLogin};
 
-		$self->{DB}->set_field( $self->{USERNAME},
-								$self->{LOCATION}{LAST},
-								time()
-								)
-			if $self->{LOCATION}{LAST} ne 'none';
+		if ($self->{LOCATION}{LAST} ne 'none') {
+			eval {
+				$udb->set_field( $self->{USERNAME},
+										$self->{LOCATION}{LAST},
+										time()
+									  );
+			};
+			if ($@) {
+				my $msg = ::errmsg("Failed to record timestamp in UserDB: %s", $@);
+				::logError($msg);
+				die $msg, "\n";
+			}
+		}
 		$self->log('login') if $options{'log'};
 		
-		$self->get_values();
+		$self->get_values() unless $self->{OPTIONS}{no_get};
 	};
 
+	scrub();
+
 	if($@) {
 		if(defined $self) {
 			$self->{ERROR} = $@;
-#::logDebug( "Vend::UserDB error: %s\n", $@ );
 		}
 		else {
 			::logError( "Vend::UserDB error: %s\n", $@ );
@@ -993,6 +1199,18 @@
 		return undef;
 	}
 
+	PRICING: {
+		my $pprof;
+		last PRICING
+			unless	$self->{LOCATION}{PRICING}
+			and		$pprof = $user_data->{ $self->{LOCATION}{PRICING} };
+
+		Vend::Interpolate::tag_profile(
+								$pprof,
+								{ tag => $self->{OPTIONS}{profile} },
+								);
+	}
+
 	$Vend::Session->{login_table} = $self->{DB_ID};
 	$Vend::username = $Vend::Session->{username} = $self->{USERNAME};
 	$Vend::Session->{logged_in} = 1;
@@ -1000,35 +1218,74 @@
 	1;
 }
 
+sub scrub {
+	for(qw/ mv_password mv_verify mv_password_old /) {
+		delete $CGI::values{$_};
+		delete $::Values->{$_};
+	}
+}
+
 sub change_pass {
 
-	my $self;
+	my ($self, $original_self);
 
 	$self = shift
 		if ref $_[0];
 
 	my(%options) = @_;
 	
+	if ($self->{OPTIONS}{ignore_case}) {
+	   $self->{USERNAME} = lc $self->{USERNAME};
+	   $self->{OLDPASS} = lc $self->{OLDPASS};
+	   $self->{PASSWORD} = lc $self->{PASSWORD};
+	   $self->{VERIFY} = lc $self->{VERIFY};
+	}
+
 	eval {
+		my $super = $Vend::superuser || (
+			$Vend::admin and
+			$self->{DB}->field($Vend::username, $self->{LOCATION}{SUPER})
+		);
+
+		if ($self->{USERNAME} ne $Vend::username or
+			defined $CGI::values{mv_username} and
+			$self->{USERNAME} ne $CGI::values{mv_username}
+		) {
+			if ($super) {
+				if ($CGI::values{mv_username} and
+					$CGI::values{mv_username} ne $self->{USERNAME}) {
+					$original_self = $self;
+					$options{username} = $CGI::values{mv_username};
+					undef $self;
+				}
+			} else {
+				::logError("Unprivileged user '%s' attempted to change password of user '%s'",
+					$Vend::username, $self->{USERNAME}) if $options{log};
+				die ::errmsg("You are not allowed to change another user's password.") . "\n";
+			}
+		}
+
 		unless($self) {
 			$self = new Vend::UserDB %options;
 		}
 
-		die "Bad object.\n" unless defined $self;
+		die ::errmsg("Bad object.") unless defined $self;
 
-		die "$self->{USERNAME} not a user\n"
+		die ::errmsg("'%s' not a user.", $self->{USERNAME}) . "\n"
 			unless $self->{DB}->record_exists($self->{USERNAME});
-		my $db_pass = $self->{DB}->field($self->{USERNAME}, $self->{LOCATION}{PASSWORD});
 
-		if($self->{CRYPT}) {
-			$self->{OLDPASS} = crypt($self->{OLDPASS},$db_pass);
+		unless ($super and $self->{USERNAME} ne $Vend::username) {
+			my $db_pass = $self->{DB}->field($self->{USERNAME}, $self->{LOCATION}{PASSWORD});
+			$self->{OLDPASS} = crypt($self->{OLDPASS}, $db_pass)
+				if $self->{CRYPT};
+			die ::errmsg("Must have old password.") . "\n"
+				if $self->{OLDPASS} ne $db_pass;
 		}
 
-		die "Must have old password\n"
-			if	$self->{OLDPASS} ne $db_pass;
-		die "Must enter at least 4 characters for password.\n"
-			unless length($self->{PASSWORD}) > 3;
-		die "Password and check value don't match.\n"
+		die ::errmsg("Must enter at least %s characters for password.",
+			$self->{PASSMINLEN}) . "\n"
+			if length($self->{PASSWORD}) < $self->{PASSMINLEN}; 
+		die ::errmsg("Password and check value don't match.") . "\n"
 			unless $self->{PASSWORD} eq $self->{VERIFY};
 
 		if($self->{CRYPT}) {
@@ -1043,14 +1300,18 @@
 						$self->{LOCATION}{PASSWORD},
 						$self->{PASSWORD}
 						);
-		die "Database access error.\n" unless defined $pass;
-		$self->log('change password') if $options{'log'};
+		die ::errmsg("Database access error.") . "\n" unless defined $pass;
+		$self->log(::errmsg('change password')) if $options{'log'};
 	};
 
+	scrub();
+
+	$self = $original_self if $original_self;
+
 	if($@) {
 		if(defined $self) {
 			$self->{ERROR} = $@;
-			$self->log('change password failed') if $options{'log'};
+			$self->log(::errmsg('change password failed')) if $options{'log'};
 		}
 		else {
 			logError( "Vend::UserDB error: %s", $@ );
@@ -1063,11 +1324,40 @@
 
 sub assign_username {
 	my $self = shift;
-	my $file = shift || $self->{OPTIONS}{'counter'};
+	my $file = shift || $self->{OPTIONS}{counter};
 	my $start = $self->{OPTIONS}{username} || 'U00000';
 	$file = './etc/username.counter' if ! $file;
-	my $ctr = File::CounterFile->new($file, $start);
-	return $ctr->inc();
+
+	my $o = { start => $start, sql => $self->{OPTIONS}{sql_counter} };
+
+	my $custno;
+
+	if(my $l = $Vend::Cfg->{Accounting}) {
+
+		my $class = $l->{Class};
+
+		my $assign = defined $l->{assign_username} ? $l->{assign_username} : 1;
+
+		if($assign) {
+#::logDebug("Accounting class is $class");
+		my $obj;
+		eval {
+				$obj = $class->new;
+		};
+#::logDebug("Accounting object is $obj");
+
+		if($@) {
+			die errmsg(
+				"Failed to assign new customer number with accounting system %s",
+				$class,
+				);
+		}
+		$custno = $obj->assign_customer_number();
+		}
+#::logDebug("assigned new customer number $custno");
+	}
+
+	return $custno || Vend::Interpolate::tag_counter($file, $o);
 }
 
 sub new_account {
@@ -1083,16 +1373,17 @@
 		unless($self) {
 			$self = new Vend::UserDB %options;
 		}
-		die "Bad object.\n" unless defined $self;
+		die ::errmsg("Bad object.") . "\n" unless defined $self;
 
-		die "Already logged in. Log out first.\n"
+		die ::errmsg("Already logged in. Log out first.") . "\n"
 			if $Vend::Session->{logged_in};
-		die "Sorry, reserved user name.\n"
+		die ::errmsg("Sorry, reserved user name.") . "\n"
 			if $self->{OPTIONS}{username_mask} 
 				and $self->{USERNAME} =~ m!$self->{OPTIONS}{username_mask}!;
-		die "Must enter at least 4 characters for password.\n"
-			unless length($self->{PASSWORD}) > 3;
-		die "Password and check value don't match.\n"
+		die ::errmsg("Must enter at least %s characters for password.",
+			$self->{PASSMINLEN}) . "\n"
+			if length($self->{PASSWORD}) < $self->{PASSMINLEN};
+		die ::errmsg("Password and check value don't match.") . "\n"
 			unless $self->{PASSWORD} eq $self->{VERIFY};
 
 		if ($self->{OPTIONS}{ignore_case}) {
@@ -1110,26 +1401,59 @@
 			};
 		}
 	
+		my $udb = $self->{DB};
+
 		if($self->{OPTIONS}{assign_username}) {
+			$self->{PASSED_USERNAME} = $self->{USERNAME};
 			$self->{USERNAME} = $self->assign_username();
 			$self->{USERNAME} = lc $self->{USERNAME}
 				if $self->{OPTIONS}{ignore_case};
 		}
-		die "Must have longer username.\n" unless length($self->{USERNAME}) > 1;
-		die "Can't have '$self->{USERNAME}' as username, unsafe characters.\n"
-			if $self->{USERNAME} !~ m{^$GOOD_CHARS+$};
-#::logDebug("new_account username: '$self->{USERNAME}'");
-		if ($self->{DB}->record_exists($self->{USERNAME})) {
-#::logDebug("new_account username: '$self->{USERNAME}' exists");
-			die "Username already exists.\n"
+		die ::errmsg("Can't have '%s' as username; it contains illegal characters.",
+			$self->{USERNAME}) . "\n"
+			if $self->{USERNAME} !~ m{^$USERNAME_GOOD_CHARS+$};
+		die ::errmsg("Must have at least %s characters in username.",
+			$self->{USERMINLEN}) . "\n"
+			if length($self->{USERNAME}) < $self->{USERMINLEN};
+
+		# Here we put the username in a non-primary key field, checking
+		# for existence
+		my $foreign = $self->{OPTIONS}{indirect_login};
+		if ($foreign) {
+			my $uname = ($self->{PASSED_USERNAME} ||= $self->{USERNAME});
+			$uname = $udb->quote($uname);
+			my $q = "select username from $self->{DB_ID} where $foreign = $uname";
+			my $ary = $udb->query($q)
+				or do {
+					my $msg = ::errmsg( "Database access error for query: %s", $q);
+					die "$msg\n";
+				};
+			@$ary == 0
+				or do {
+					my $msg = ::errmsg( "Username already exists (indirect).");
+					die "$msg\n";
+				};
 		}
-#::logDebug("new_account username: '$self->{USERNAME}' doesn't exist");
-		my $pass = $self->{DB}->set_field(
+
+		if ($udb->record_exists($self->{USERNAME})) {
+			die ::errmsg("Username already exists.") . "\n";
+		}
+
+		my $pass = $udb->set_field(
 						$self->{USERNAME},
 						$self->{LOCATION}{PASSWORD},
 						$pw,
 						);
-		die "Database access error.\n" unless defined $pass;
+		die ::errmsg("Database access error.") . "\n" unless defined $pass;
+
+		if($foreign) {
+			 $udb->set_field(
+						$self->{USERNAME},
+						$foreign,
+						$self->{PASSED_USERNAME},
+						)
+				or die ::errmsg("Database access error.");
+		}
 
 		username_cookies($self->{USERNAME}, $pw) 
 			if $Vend::Cfg->{CookieLogin};
@@ -1137,9 +1461,11 @@
 		$self->log('new account') if $options{'log'};
 		$self->set_values();
 		$self->login()
-			or die "Cannot log in after new account creation: $self->{ERROR}";
+			or die ::errmsg("Cannot log in after new account creation: %s", $self->{ERROR});
 	};
 
+	scrub();
+
 	if($@) {
 		if(defined $self) {
 			$self->{ERROR} = $@;
@@ -1185,28 +1511,28 @@
 		$to = $Vend::Items;
 	}
 
-#::logDebug ("to=$to nick=$options{target} from=$from cart=" . ::uneval($from));
+#::logDebug ("to=$to nick=$options{target} from=$from cart=" . ::uneval_it($from));
 
 	my $field_name = $self->{LOCATION}->{CARTS};
 	my $cart = [];
 
 	eval {
-		die "no from cart name?"				unless $from;
-		die "$field_name field not present to get $from\n"
+		die ::errmsg("no from cart name?")				unless $from;
+		die ::errmsg("%s field not present to get %s", $field_name, $from) . "\n"
 										unless $self->{PRESENT}->{$field_name};
 
 		my $s = $self->{DB}->field( $self->{USERNAME}, $field_name);
 
-		die "no saved carts.\n" unless $s;
+		die ::errmsg("no saved carts.") . "\n" unless $s;
 
 		my @carts = split /\0/, $from;
 		my $d = $ready->reval($s);
-#::logDebug ("saved carts=" . ::uneval($d));
+#::logDebug ("saved carts=" . ::uneval_it($d));
 
-		die "eval failed?"				unless ref $d;
+		die ::errmsg("eval failed?")				unless ref $d;
 
 		for(@carts) {
-			die "source cart '$from' does not exist.\n" unless ref $d->{$_};
+			die ::errmsg("source cart '%s' does not exist.", $from) . "\n" unless ref $d->{$_};
 			push @$cart, @{$d->{$_}};
 		}
 
@@ -1216,9 +1542,14 @@
 		$self->{ERROR} = $@;
 		return undef;
 	}
-#::logDebug ("to=$to nick=$options{target} from=$from cart=" . ::uneval($cart));
-	@$to = @$cart;
+#::logDebug ("to=$to nick=$options{target} from=$from cart=" . ::uneval_it($cart));
 
+	if($options{merge}) {
+		$to = [] unless ref $to;
+		push(@$to,@$cart);
+	} else {
+		@$to = @$cart;
+	}
 }
 
 sub set_cart {
@@ -1237,15 +1568,15 @@
 	my ($cart,$s,$d);
 
 	eval {
-		die "no to cart name?\n"					unless $to;
-		die "$field_name field not present to save $from\n"
+		die ::errmsg("no to cart name?") . "\n"					unless $to;
+		die ::errmsg('%s field not present to set %s', $field_name, $from) . "\n"
 										unless $self->{PRESENT}->{$field_name};
 
 		$d = $ready->reval( $self->{DB}->field( $self->{USERNAME}, $field_name) );
 
 		$d = {} unless $d;
 
-		die "eval failed?"				unless ref $d;
+		die ::errmsg("eval failed?")				unless ref $d;
 
 		if($options{merge}) {
 			$d->{$to} = [] unless ref $d->{$to};
@@ -1290,10 +1621,9 @@
 		delete $Vend::Session->{username};
 		undef $Vend::username;
 		undef $Vend::admin;
-		::put_session();
 		$user = new Vend::UserDB %options;
 		unless (defined $user) {
-			$Vend::Session->{failure} = "Unable to access user database.";
+			$Vend::Session->{failure} = ::errmsg("Unable to access user database.");
 			return undef;
 		}
 		if ($status = $user->login(%options) ) {
@@ -1302,10 +1632,8 @@
 				$Vend::Cfg->{AdminUserDB}{$user->{PROFILE}}
 				)
 			{
-#::logDebug("logged in $Vend::username via $user->{DB_ID} -- ADMIN");
 				$Vend::admin = 1;
 			}
-#::logDebug("logged in $Vend::username via $user->{DB_ID}");
 			undef $Vend::Cookie
 				unless $Vend::Cfg->{StaticLogged};
 			::update_user();
@@ -1314,7 +1642,7 @@
 	elsif($function eq 'new_account') {
 		$user = new Vend::UserDB %options;
 		unless (defined $user) {
-			$Vend::Session->{failure} = "Unable to access user database.";
+			$Vend::Session->{failure} = ::errmsg("Unable to access user database.");
 			return undef;
 		}
 		if($status = $user->new_account(%options)) {
@@ -1326,30 +1654,44 @@
 	}
 	elsif($function eq 'logout') {
 		$user = new Vend::UserDB %options;
+		scrub();
 		unless (defined $user) {
-			$Vend::Session->{failure} = "Unable to access user database.";
+			$Vend::Session->{failure} = ::errmsg("Unable to access user database.");
 			return undef;
 		}
 		if( is_yes($options{clear}) ) {
 			$user->clear_values();
 		}
+		Vend::Interpolate::tag_profile("", { restore => 1 });
 		delete $Vend::Session->{logged_in};
+		undef $Vend::admin;
+		undef $Vend::superuser;
 		delete $Vend::Session->{login_table};
 		delete $Vend::Session->{username};
 		delete $CGI::values{mv_username};
 		undef $Vend::username;
 		delete $::Values->{mv_username};
 		$user->log('logout') if $options{'log'};
-		$user->{MESSAGE} = 'Logged out.';
+		$user->{MESSAGE} = ::errmsg('Logged out.');
+		if ($user->{OPTIONS}{clear_cookie}) {
+			my @cookies = split /[\s,\0]+/, $user->{OPTIONS}{clear_cookie};
+			my $exp = time() + $Vend::Cfg->{SaveExpire};
+			for(@cookies) {
+				Vend::Util::set_cookie($_, '', $exp);
+			}
+		}
+		if ($user->{OPTIONS}{clear_session}) {
+			Vend::Session::init_session();
+		}
 	}
 	elsif (! $Vend::Session->{logged_in}) {
-		$Vend::Session->{failure} = "Not logged in.";
+		$Vend::Session->{failure} = ::errmsg("Not logged in.");
 		return undef;
 	}
 	elsif($function eq 'save') {
 		$user = new Vend::UserDB %options;
 		unless (defined $user) {
-			$Vend::Session->{failure} = "Unable to access user database.";
+			$Vend::Session->{failure} = ::errmsg("Unable to access user database.");
 			return undef;
 		}
 		$status = $user->set_values();
@@ -1357,7 +1699,7 @@
 	elsif($function eq 'load') {
 		$user = new Vend::UserDB %options;
 		unless (defined $user) {
-			$Vend::Session->{failure} = "Unable to access user database.";
+			$Vend::Session->{failure} = ::errmsg("Unable to access user database.");
 			return undef;
 		}
 		$status = $user->get_values();
@@ -1365,22 +1707,23 @@
 	else {
 		$user = new Vend::UserDB %options;
 		unless (defined $user) {
-			$Vend::Session->{failure} = "Unable to access user database.";
+			$Vend::Session->{failure} = ::errmsg("Unable to access user database.");
 			return undef;
 		}
-		$status = $user->$function(%options);
+		eval {
+			$status = $user->$function(%options);
+		};
+		$user->{ERROR} = $@ if $@;
 	}
 	
 	if(defined $status) {
 		delete $Vend::Session->{failure};
-#::logDebug("userdb success=$user->{ERROR}\n");
 		$Vend::Session->{success} = $user->{MESSAGE};
 		if($options{show_message}) {
 			$status = $user->{MESSAGE};
 		}
 	}
 	else {
-#::logDebug("userdb failure=$user->{ERROR}\n");
 		$Vend::Session->{failure} = $user->{ERROR};
 		if($options{show_message}) {
 			$status = $user->{ERROR};



1.10.4.6  +895 -209  interchange/lib/Vend/Util.pm


rev 1.10.4.6, prev_rev 1.10.4.5
Index: Util.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Util.pm,v
retrieving revision 1.10.4.5
retrieving revision 1.10.4.6
diff -u -r1.10.4.5 -r1.10.4.6
--- Util.pm	15 Apr 2001 14:07:08 -0000	1.10.4.5
+++ Util.pm	25 Jan 2003 22:21:28 -0000	1.10.4.6
@@ -1,14 +1,11 @@
-# Util.pm - Interchange utility functions
+# Vend::Util - Interchange utility functions
 #
-# $Id: Util.pm,v 1.10.4.5 2001/04/15 14:07:08 racke Exp $
+# $Id: Util.pm,v 1.10.4.6 2003/01/25 22:21:28 racke Exp $
 # 
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -35,49 +32,60 @@
 	check_security
 	copyref
 	currency
+	dbref
 	dump_structure
 	errmsg
 	escape_chars
 	evalr
+	dotted_hash
 	file_modification_time
 	file_name_is_absolute
 	find_special_page
 	format_log_msg
 	generate_key
 	get_option_hash
+	hash_string
+	hexify
+	is_hash
 	is_no
 	is_yes
+	l
 	lockfile
 	logData
 	logDebug
 	logError
 	logGlobal
+	logOnce
 	logtime
 	random_string
 	readfile
 	readin
+	round_to_frac_digits
 	secure_vendUrl
+	send_mail
 	setup_escape_chars
+	set_lock_type
+	show_times
+	string_to_ref
 	tag_nitems
 	uneval
 	uneval_it
 	uneval_fast
+	unhexify
 	unlockfile
 	vendUrl
 );
 
-# LEGACY4
-push @EXPORT, qw(
-	send_mail
-);
-# END LEGACY4
-
 use strict;
 use Config;
 use Fcntl;
+use Errno;
+use Text::ParseWords;
+require HTML::Entities;
+use Safe;
 use subs qw(logError logGlobal);
 use vars qw($VERSION @EXPORT @EXPORT_OK);
-$VERSION = substr(q$Revision: 1.10.4.5 $, 10);
+$VERSION = substr(q$Revision: 1.10.4.6 $, 10);
 
 BEGIN {
 	eval {
@@ -102,9 +110,31 @@
 		'-:_.$/'
 	;
 
+$ESCAPE_CHARS::ok_in_url =
+		'ABCDEFGHIJKLMNOPQRSTUVWXYZ' .
+		'abcdefghijklmnopqrstuvwxyz' .
+		'0123456789'				 .
+		'-_./~='
+	;
+
+## This is an alias for a commonly-used function
+sub dbref {
+	return Vend::Data::database_exists_ref(@_);
+}
+
+## This is a character class for HTML::Entities
+$ESCAPE_CHARS::std = "^\n\t !\#\$%\'-;=?-Z\\\]-~";
+
+my $need_escape;
+
 sub setup_escape_chars {
     my($ok, $i, $a, $t);
 
+	## HTML::Entities caches this, let's get it cached right away so
+	## each child doesn't have to re-eval
+	my $junk = ">>>123<<<";
+	HTML::Entities::encode($junk, $ESCAPE_CHARS::std);
+
     foreach $i (0..255) {
         $a = chr($i);
         if (index($ESCAPE_CHARS::ok_in_filename,$a) == -1) {
@@ -114,7 +144,17 @@
 			$t = $a;
         }
         $ESCAPE_CHARS::translate[$i] = $t;
+        if (index($ESCAPE_CHARS::ok_in_url,$a) == -1) {
+			$t = '%' . sprintf( "%02X", $i );
+        }
+		else {
+			$t = $a;
+        }
+        $ESCAPE_CHARS::translate_url[$i] = $t;
     }
+
+	my $string = "[^$ESCAPE_CHARS::ok_in_url]";
+	$need_escape = qr{$string};
 }
 
 # Replace any characters that might not be safe in a filename (especially
@@ -130,8 +170,23 @@
     }
 
     # safe now
-    $r =~ /(.*)/;
-    $r = $1;
+    return $r;
+}
+
+# Replace any characters that might not be safe in an URL
+# with the %HH notation.
+
+sub escape_chars_url {
+    my($in) = @_;
+	return $in unless $in =~ $need_escape;
+    my($c, $r);
+
+    $r = '';
+    foreach $c (split(//, $in)) {
+		$r .= $ESCAPE_CHARS::translate_url[ord($c)];
+    }
+
+    # safe now
     return $r;
 }
 
@@ -182,7 +237,7 @@
 	push @params, logtime();
 
 	# Catalog name
-	my $string = ! defined $Vend::Cfg ? '-' : ($Vend::Cfg->{CatalogName} || '-');
+	my $string = ! defined $Vend::Cfg ? '-' : ($Vend::Cat || '-');
 	push @params, $string;
 
 	# Path info and script
@@ -202,7 +257,8 @@
 		# use what we were given
 	}
 	elsif ( $Vend::Cfg->{Locale} ) {
-		$digits = $Vend::Cfg->{Locale}{frac_digits} || 2;
+		$digits = $Vend::Cfg->{Locale}{frac_digits};
+		$digits = 2 if ! defined $digits;
 	}
 	else {
 		$digits = 2;
@@ -221,9 +277,41 @@
 		$int++;
 		$frac = 0 x $digits;
 	}
+	$frac .= '0' while length($frac) < $digits;
 	return "$int.$frac";
 }
 
+use vars qw/%MIME_type/;
+%MIME_type = (qw|
+			jpg		image/jpeg
+			gif		image/gif
+			jpeg	image/jpeg
+			png		image/png
+			xpm		image/xpm
+			htm		text/html
+			html	text/html
+			txt		text/plain
+			asc		text/plain
+			csv		text/plain
+			xls		application/vnd.ms-excel
+			default application/octet-stream
+		|
+		);
+# Return a mime type based on either catalog configuration or some defaults
+sub mime_type {
+	my ($val) = @_;
+	$val =~ s:.*\.::s;
+
+	! length($val) and return $Vend::Cfg->{MimeType}{default} || 'text/plain';
+
+	$val = lc $val;
+
+	return $Vend::Cfg->{MimeType}{$val}
+				|| $MIME_type{$val}
+				|| $Vend::Cfg->{MimeType}{default}
+				|| $MIME_type{default};
+}
+
 # Return AMOUNT formatted as currency.
 sub commify {
     local($_) = shift;
@@ -277,6 +365,16 @@
     my ($locale, $currency, $opt) = @_;
 #::logDebug("original locale " . (defined $locale ? $locale : 'undef') );
 #::logDebug("default locale  " . (defined $::Scratch->{mv_locale} ? $::Scratch->{mv_locale} : 'undef') );
+
+	if($opt->{get}) {
+	    my $loc     = $Vend::Cfg->{Locale_repository} or return;
+	    my $currloc = $Vend::Cfg->{Locale} or return;
+	    for(keys %$loc) {
+			return $_ if $loc->{$_} eq $currloc;
+	    }
+	    return;
+	}
+
     $locale = $::Scratch->{mv_locale} unless defined $locale;
 #::logDebug("locale is now   " . (defined $locale ? $locale : 'undef') );
 
@@ -328,21 +426,44 @@
             $Vend::Cfg->{$_} = $curr->{$_}
                 if defined $curr->{$_};
         }
-        @{$Vend::Cfg->{Locale}}{@Vend::Config::Locale_keys_currency} =
-                @{$curr}{@Vend::Config::Locale_keys_currency};
     }
 
-    $::Scratch->{mv_locale}   = $locale    if $opt->{persist} and $locale;
-    $::Scratch->{mv_currency} = $currency  if $opt->{persist} and $currency;
+	if(my $ref = $Vend::Cfg->{CodeDef}{LocaleChange}) {
+		$ref = $ref->{Routine};
+		if($ref->{all}) {
+			$ref->{all}->($locale, $opt);
+		}
+		if($ref->{lc $locale}) {
+			$ref->{lc $locale}->($locale, $opt);
+		}
+	}
+
+    if($opt->{persist}) {
+		$::Scratch->{mv_locale}   = $locale		if $locale;
+		delete $::Scratch->{mv_currency_tmp};
+		delete $::Scratch->{mv_currency};
+		$::Scratch->{mv_currency} = $currency if $currency;
+	}
+	elsif($currency) {
+		Vend::Interpolate::set_tmp('mv_currency_tmp')
+			unless defined $::Scratch->{mv_currency_tmp};
+		$::Scratch->{mv_currency_tmp} = $currency;
+	}
+	else {
+		delete $::Scratch->{mv_currency_tmp};
+		delete $::Scratch->{mv_currency};
+	}
+
     return '';
 }
 
 
 sub currency {
 	my($amount, $noformat, $convert, $opt) = @_;
-#::logDebug("currency called: amount=$amount no=$noformat convert=$convert");
 	$opt = {} unless $opt;
-	$amount = $amount / $Vend::Cfg->{PriceDivide} if $convert;
+	
+	$amount = $amount / $Vend::Cfg->{PriceDivide}
+		if $convert and $Vend::Cfg->{PriceDivide} != 0;
 	return $amount if $noformat;
 	my $loc;
 	my $sep;
@@ -350,7 +471,22 @@
 	my $fmt;
 	my $precede = '';
 	my $succede = '';
-	if ($loc = $opt->{locale} || $Vend::Cfg->{Locale}) {
+	my $loc = $opt->{locale}
+			|| $::Scratch->{mv_currency_tmp}
+			|| $::Scratch->{mv_currency}
+			|| $Vend::Cfg->{Locale};
+
+	if(ref($loc)) {
+		## Do nothing, is a hash reference
+	}
+	elsif($loc) {
+		$loc = $Vend::Cfg->{Locale_repository}{$loc};
+	}
+	
+	if (! $loc) {
+		$fmt = "%.2f";
+	}
+	else {
 		$sep = $loc->{mon_thousands_sep} || $loc->{thousands_sep} || ',';
 		$dec = $loc->{mon_decimal_point} || $loc->{decimal_point} || '.';
 		return picture_format($amount, $loc->{price_picture}, $sep, $dec)
@@ -368,9 +504,6 @@
 			}
 		}
 	}
-	else {
-		$fmt = "%.2f";
-	}
 
 	$amount = safe_sprintf($fmt, $amount);
 	$amount =~ s/\./$dec/ if defined $dec;
@@ -409,7 +542,6 @@
 if(! $@) {
 	$Md = new Digest::MD5;
 	$Keysub = sub {
-#::logDebug("key gen args: '@_'");
 					@_ = time() unless @_;
 					$Md->reset();
 					$Md->add(@_);
@@ -443,6 +575,15 @@
     return $s;
 }
 
+*unescape_chars = \&unhexify;
+
+sub unescape_full {
+    my $url = shift;
+    $url =~ tr/+/ /;
+    $url =~ s/<!--.*?-->//sg;
+    return unhexify($url);
+}
+
 ## UNEVAL
 
 # Returns a string representation of an anonymous array, hash, or scaler
@@ -637,8 +778,8 @@
 
 
 sub file_modification_time {
-    my ($fn) = @_;
-    my @s = stat($fn) or die "Can't stat '$fn': $!\n";
+    my ($fn, $tolerate) = @_;
+    my @s = stat($fn) or ($tolerate and return 0) or die "Can't stat '$fn': $!\n";
     return $s[9];
 }
 
@@ -692,13 +833,10 @@
 
 	my $gate;
 	if ($gate = readfile("$gatedir/.access_gate") ) {
-#::logDebug("found access_gate");
 		$f =~ s:.*/::;
 		$gate = Vend::Interpolate::interpolate_html($gate);
-#::logDebug("f=$f gate=$gate");
 		if($gate =~ m!^$f(?:\.html?)?[ \t]*:!m ) {
 			$gate =~ s!.*(\n|^)$f(?:\.html?)?[ \t]*:!!s;
-#::logDebug("gate=$gate");
 			$gate =~ s/\n[\S].*//s;
 			$gate =~ s/^\s+//;
 		}
@@ -712,26 +850,96 @@
 	return $gate;
 }
 
-sub get_option_hash {
-	if (ref $_[0]) {
-		return $_[0] unless ref $_[1];
-		for(keys %{$_[1]}) {
-			$_[0]->{$_} = $_[1]->{$_}
-				unless defined $_[0]->{$_};
+sub string_to_ref {
+	my ($string) = @_;
+	if(! $Vend::Cfg->{ExtraSecure} and $MVSAFE::Safe) {
+		return eval $string;
+	}
+	elsif ($MVSAFE::Safe) {
+		die errmsg("not allowed to eval in Safe mode.");
+	}
+	my $safe = $Vend::Interpolate::safe_safe || new Safe;
+	return $safe->reval($string);
+}
+
+sub is_hash {
+	return ref($_[0]) eq 'HASH';
+}
+
+sub dotted_hash {
+	my($hash, $key, $value, $delete_empty) = @_;
+	$hash = get_option_hash($hash) unless is_hash($hash);
+	unless (is_hash($hash)) {
+		return undef unless defined $value;
+		$hash = {};
+	}
+	my @keys = split /[\.:]+/, $key;
+	my $final;
+	my $ref;
+
+	if(! defined $value) {
+		# Retrieving
+		$ref = $hash->{shift @keys};
+		for(@keys) {
+			return undef unless is_hash($ref);
+			$ref = $ref->{$_};
 		}
+		return $ref;
 	}
-	return {} unless $_[0] =~ /\S/;
+
+	# Storing
+	$final = pop @keys;
+	$ref = $hash;
+
+	for(@keys) {
+		$ref->{$_} = {} unless is_hash($ref->{$_});
+		$ref = $ref->{$_};
+	}
+
+	if($delete_empty and ! length($value)) {
+		delete $ref->{$final};
+	}
+	else {
+		$ref->{$final} = $value;
+	}
+
+	$hash = uneval_it($hash);
+	return $hash;
+}
+
+sub get_option_hash {
 	my $string = shift;
 	my $merge = shift;
+	if (ref $string) {
+		return $string unless ref $merge;
+		for(keys %{$merge}) {
+			$string->{$_} = $merge->{$_}
+				unless defined $string->{$_};
+		}
+		return $string;
+	}
+	return {} unless $string =~ /\S/;
 	$string =~ s/^\s+//;
 	$string =~ s/\s+$//;
 	if($string =~ /^{/ and $string =~ /}/) {
-		return $Vend::Interpolate::ready_safe->reval($string);
+		return string_to_ref($string);
 	}
-	my @opts = split /\s*,\s*/, $string;
+
+	my @opts;
+	unless ($string =~ /,/) {
+		@opts = grep $_ ne "=", Text::ParseWords::shellwords($string);
+		for(@opts) {
+			s/^(\w[-\w]*\w)=(["'])(.*)\2$/$1$3/;
+		}
+	}
+	else {
+		@opts = split /\s*,\s*/, $string;
+	}
+
 	my %hash;
 	for(@opts) {
 		my ($k, $v) = split /[\s=]+/, $_, 2;
+		$k =~ s/-/_/g;
 		$hash{$k} = $v;
 	}
 	if($merge) {
@@ -744,6 +952,26 @@
 	return \%hash;
 }
 
+## This simply returns a hash of words, which may be quoted shellwords
+## Replaces most of parse_hash in Vend::Config
+sub hash_string {
+	my($settings, $ref) = @_;
+
+	return $ref if ! $settings or $settings !~ /\S/;
+
+	$ref ||= {};
+
+	$settings =~ s/^\s+//;
+	$settings =~ s/\s+$//;
+	my(@setting) = Text::ParseWords::shellwords($settings);
+
+	my $i;
+	for ($i = 0; $i < @setting; $i += 2) {
+		$ref->{$setting[$i]} = $setting[$i + 1];
+	}
+	return $ref;
+}
+
 ## READIN
 
 my $Lang;
@@ -751,13 +979,59 @@
 sub find_locale_bit {
 	my $text = shift;
 	$Lang = $::Scratch->{mv_locale} unless defined $Lang;
-#::logDebug("find_locale: $Lang");
 	$text =~ m{\[$Lang\](.*)\[/$Lang\]}s
 		and return $1;
 	$text =~ s{\[(\w+)\].*\[/\1\].*}{}s;
 	return $text;
 }
 
+sub parse_locale {
+	my ($input) = @_;
+
+	# avoid copying big strings
+	my $r = ref($input) ? $input : \$input;
+	
+	if($Vend::Cfg->{Locale}) {
+		my $key;
+		$$r =~ s~\[L(\s+([^\]]+))?\]([\000-\377]*?)\[/L\]~
+						$key = $2 || $3;		
+						defined $Vend::Cfg->{Locale}{$key}
+						?  ($Vend::Cfg->{Locale}{$key})	: $3 ~eg;
+		$$r =~ s~\[LC\]([\000-\377]*?)\[/LC\]~
+						find_locale_bit($1) ~eg;
+		undef $Lang;
+	}
+	else {
+		$$r =~ s~\[L(?:\s+[^\]]+)?\]([\000-\377]*?)\[/L\]~$1~g;
+	}
+
+	# return scalar string if one get passed initially
+	return ref($input) ? $input : $$r;
+}
+
+sub teleport_name {
+	my ($file, $teleport, $table) = @_;
+	my $db;
+	return $file
+		unless	 $teleport
+			and  $db = Vend::Data::database_exists_ref($table);
+
+	my @f = qw/code base_code expiration_date show_date page_text/;
+	my ($c, $bc, $ed, $sd, $pt) = @{$Vend::Cfg->{PageTableMap}}{@f};
+	my $q = qq{
+		SELECT $c from $table
+		WHERE  $bc = '$file'
+		AND    $ed <  $teleport
+		AND    $sd >= $teleport
+		ORDER BY $sd DESC
+	};
+	my $ary = $db->query($q);
+	if($ary and $ary->[0]) {
+		$file = $ary->[0][0];
+	}
+	return $file;
+}
+
 # Reads in a page from the page directory with the name FILE and ".html"
 # appended. If the HTMLsuffix configuration has changed (because of setting in
 # catalog.cfg or Locale definitions) it will substitute that. Returns the
@@ -765,7 +1039,11 @@
 # Substitutes Locale bits as necessary.
 
 sub readin {
-    my($file, $only) = @_;
+    my($file, $only, $locale) = @_;
+
+	## We don't want to try if we are forcing a flypage
+	return undef if $Vend::ForceFlypage;
+
     my($fn, $contents, $gate, $pathdir, $dir, $level);
     local($/);
 
@@ -773,21 +1051,48 @@
 		if defined $Global::Variable->{MV_PAGE};
 	$Global::Variable->{MV_PAGE} = $file;
 
+	$file =~ s#^\s+##;
+	$file =~ s#\s+$##;
 	$file =~ s#\.html?$##;
 	if($file =~ m{\.\.} and $file =~ /\.\..*\.\./) {
 		::logError( "Too many .. in file path '%s' for security.", $file );
 		$file = find_special_page('violation');
 	}
+	$file =~ s#//+#/#g;
+	$file =~ s#/+$##g;
 	($pathdir = $file) =~ s#/[^/]*$##;
 	$pathdir =~ s:^/+::;
 	my $try;
 	my $suffix = $Vend::Cfg->{HTMLsuffix};
+	my $db_tried;
+	$locale = 1 unless defined $locale;
+	my $record;
   FINDPAGE: {
-	foreach $try (
-					$Vend::Cfg->{PageDir},
-					@{$Vend::Cfg->{TemplateDir}},
-					@{$Global::TemplateDir}          )
-	{
+  	## If PageTables is set, we try to find the page in the table first
+	## but only once, without the suffix
+  	if(! $db_tried++ and $Vend::Cfg->{PageTables}) {
+		my $teleport = $Vend::Session->{teleport};
+		my $field = $Vend::Cfg->{PageTableMap}{page_text};
+		foreach my $t (@{$Vend::Cfg->{PageTables}}) {
+			my $db = Vend::Data::database_exists_ref($t);
+			if($teleport) {
+				$file = teleport_name($file, $teleport, $t);
+			}
+			$record = $db->row_hash($file)
+				or next;
+			$contents = $record->{$field};
+			last FINDPAGE if length $contents;
+			undef $contents;
+		}
+	}
+
+	my @dirs = ($Vend::Cfg->{PreviewDir},
+				$Vend::Cfg->{PageDir},
+				@{$Vend::Cfg->{TemplateDir}},
+				@{$Global::TemplateDir});
+
+	foreach $try (@dirs) {
+		next unless $try;
 		$dir = $try . "/" . $pathdir;
 		if (-f "$dir/.access") {
 			if (-s _) {
@@ -806,13 +1111,13 @@
 		}
 
 		if( defined $level and ! check_security($file, $level, $gate) ){
-			my $realm = $::Variable->{COMPANY} || $Vend::Cfg->{CatalogName};
+			my $realm = $::Variable->{COMPANY} || $Vend::Cat;
 			$Vend::StatusLine = <<EOF if $Vend::InternalHTTP;
 HTTP/1.0 401 Unauthorized
 WWW-Authenticate: Basic realm="$realm"
 EOF
-			if(-f "$try/violation.$suffix") {
-				$fn = "$try/violation.$suffix";
+			if(-f "$try/violation$suffix") {
+				$fn = "$try/violation$suffix";
 			}
 			else {
 				$file = find_special_page('violation');
@@ -837,42 +1142,44 @@
 		$suffix = '.html';
 		redo FINDPAGE;
 	}
-	elsif($Vend::Cfg->{Locale}) {
-		my $key;
-		$contents =~ s~\[L(\s+([^\]]+))?\]([\000-\377]*?)\[/L\]~
-						$key = $2 || $3;		
-						defined $Vend::Cfg->{Locale}{$key}
-						?  ($Vend::Cfg->{Locale}{$key})	: $3 ~eg;
-		$contents =~ s~\[LC\]([\000-\377]*?)\[/LC\]~
-						find_locale_bit($1) ~eg;
-		undef $Lang;
+  }
+
+	if(! defined $contents) {
+		$contents = readfile_db("pages/$file");
 	}
-	else {
-		$contents =~ s~\[L(?:\s+[^\]]+)?\]([\000-\377]*?)\[/L\]~$1~g;
+
+	return unless defined $contents;
+	
+	parse_locale(\$contents);
+
+	return $contents unless wantarray;
+	return ($contents, $record);
+}
+
+sub readfile_db {
+	my ($name) = @_;
+	return unless $Vend::Cfg->{FileDatabase};
+	my ($tab, $col) = split /:+/, $Vend::Cfg->{FileDatabase};
+	my $db = $Vend::Interpolate::Db{$tab} || ::database_exists_ref($tab)
+		or return undef;
+#::logDebug("tab=$tab exists, db=$db");
+
+	# I guess this is the best test
+	if($col) {
+		return undef unless $db->column_exists($col);
 	}
-  }
-  if($Vend::Cfg->{HTMLmirror}) {
-  	my $mir = $fn;
-  	$mir =~ s:([^/]+)$:.$1:;
-#::logDebug("mirror $mir");
-  	if	(
-			-f $mir
-				and 
-			file_modification_time($fn) <= file_modification_time($mir)
-		)
-	{
-		return $contents;
+	elsif ( $col = $Global::Variable->{LANG} and $db->column_exists($col) ) {
+		#do nothing
 	}
 	else {
-		# We want to work anyway
-		open (MIR, ">$mir")
-			or return $contents;
-		Vend::Interpolate::vars_and_comments(\$contents, 1);
-		print MIR $contents;
-		close MIR;
+		$col = 'default';
+		return undef unless $db->column_exists($col);
 	}
-  }
-  $contents;
+
+#::logDebug("col=$col exists, db=$db");
+	return undef unless $db->record_exists($name);
+#::logDebug("ifile=$name exists, db=$db");
+	return $db->field($name, $col);
 }
 
 # Reads in an arbitrary file.  Returns the entire contents,
@@ -880,80 +1187,164 @@
 # Careful, needs the full path, or will be read relative to
 # VendRoot..and will return binary. Should be tested by
 # the user.
+
+# Will also look in the *global* TemplateDir. (No need for the
+# extra overhead of local TemplateDir, probably also insecure.)
 #
-# To ensure security in multiple catalog setups, leading
-# / is not allowed unless $Global::NoAbsolute is set.
-#
+# To ensure security in multiple catalog setups, leading /
+# is not allowed if the second subroutine argument passed
+# (caller usually sends $Global::NoAbsolute) is true.
+
+# If catalog FileDatabase is enabled and there are no contents, we can retrieve
+# the file from the database.
+
 sub readfile {
-    my($file, $no, $loc) = @_;
+    my($ifile, $no, $loc) = @_;
     my($contents);
     local($/);
 
-	if($no and (::file_name_is_absolute($file) or $file =~ m#\.\./.*\.\.#)) {
-		::logError("Can't read file '%s' with NoAbsolute set" , $file);
-		::logGlobal({}, "Can't read file '%s' with NoAbsolute set" , $file );
+	if($no and (file_name_is_absolute($ifile) or $ifile =~ m#\.\./.*\.\.#)) {
+		::logError("Can't read file '%s' with NoAbsolute set" , $ifile);
+		::logGlobal({ level => 'auth'}, "Can't read file '%s' with NoAbsolute set" , $ifile );
 		return undef;
 	}
 
-    return undef if ! -f $file;
-    return undef if ! open(READIN, "< $file");
+	my $file;
 
-	$Global::Variable->{MV_FILE} = $file;
+	if (file_name_is_absolute($ifile) and -f $ifile) {
+		$file = $ifile;
+	}
+	else {
+		for( ".", @{$Global::TemplateDir} ) {
+			next if ! -f "$_/$ifile";
+			$file = "$_/$ifile";
+			last;
+		}
+	}
 
-	binmode(READIN) if $Global::Windows;
-	undef $/;
-	$contents = <READIN>;
-	close(READIN);
+	if(! $file) {
+		$contents = readfile_db($ifile);
+		return undef unless defined $contents;
+	}
+	else {
+		return undef unless open(READIN, "< $file");
+		$Global::Variable->{MV_FILE} = $file;
 
-	if ($Vend::Cfg->{Locale} and ($loc or $Vend::Cfg->{Locale}->{readfile}) ) {
-		my $key;
-		$contents =~ s~\[L(\s+([^\]]+))?\]([\000-\377]*?)\[/L\]~
-						$key = $2 || $3;		
-						defined $Vend::Cfg->{Locale}->{$key}
-						?  ($Vend::Cfg->{Locale}->{$key})	: $3 ~eg;
-		$contents =~ s~\[LC\]([\000-\377]*?)\[/LC\]~
-						find_locale_bit($1) ~eg;
-		undef $Lang;
+		binmode(READIN) if $Global::Windows;
+		undef $/;
+		$contents = <READIN>;
+		close(READIN);
+	}
+
+	if (
+		$Vend::Cfg->{Locale}
+			and
+		(defined $loc ? $loc : $Vend::Cfg->{Locale}->{readfile} )
+		)
+	{
+		parse_locale(\$contents);
 	}
     return $contents;
 }
 
 sub is_yes {
-    return( defined($_[$[]) && ($_[$[] =~ /^[yYtT1]/));
+    return( defined($_[0]) && ($_[0] =~ /^[yYtT1]/));
 }
 
 sub is_no {
-	return( !defined($_[$[]) || ($_[$[] =~ /^[nNfF0]/));
+	return( !defined($_[0]) || ($_[0] =~ /^[nNfF0]/));
 }
 
 # Returns a URL which will run the ordering system again.  Each URL
 # contains the session ID as well as a unique integer to avoid caching
 # of pages by the browser.
 
+my @scratches = qw/
+				add_dot_html
+				add_source
+				link_relative
+				match_security
+				/;
+
 sub vendUrl {
-    my($path, $arguments, $r) = @_;
+    my($path, $arguments, $r, $opt) = @_;
     $r = $Vend::Cfg->{VendURL}
 		unless defined $r;
 
+	my $secure;
+	my $can_cache = ! $Vend::Cfg->{NoCache}{$path};
 	my @parms;
 
 	if(exists $Vend::Cfg->{AlwaysSecure}{$path}) {
 		$r = $Vend::Cfg->{SecureURL};
 	}
 
+	$opt ||= {};
+	my %skip = qw/form 1 href 1 reparse 1/;
+
+	for(@scratches) {
+		next if defined $opt->{$_};
+		next unless defined $::Scratch->{"mv_$_"};
+		$skip{$_} = 1;
+		$opt->{$_} = $::Scratch->{"mv_$_"};
+	}
+
+	my $extra;
+	if($opt->{form}) {
+		$path = 'process' unless $path;
+		if($opt->{form} eq 'auto') {
+			my $form = '';
+			while( my ($k, $v) = each %$opt) {
+				next if $skip{$k};
+				$k =~ s/^__//;
+				$form .= "$k=$v\n";
+			}
+			$opt->{form} = $form;
+		}
+		push @parms, Vend::Interpolate::escape_form($opt->{form});
+	}
+
 	my($id, $ct);
 	$id = $Vend::SessionID
-		unless $CGI::cookie && $::Scratch->{mv_no_session_id};
+		unless $opt->{no_session_id}
+		or     ($Vend::Cookie and $can_cache and $::Scratch->{mv_no_session_id});
 	$ct = ++$Vend::Session->{pageCount}
-		unless $::Scratch->{mv_no_count};
+		unless $opt->{no_count} or ($can_cache && $::Scratch->{mv_no_count});
+
+	if($opt->{match_security}) {
+		$opt->{secure} = $CGI::secure;
+	}
+
+	if($opt->{no_session}) {
+		undef $id;
+		undef $ct;
+	}
 
+	if($opt->{link_relative}) {
+		my $cur = $Global::Variable->{MV_PAGE};
+		$cur =~ s{/[^/]+$}{}
+			and $path = "$cur/$path";
+	}
+
+	if($opt->{secure} or exists $Vend::Cfg->{AlwaysSecure}{$path}) {
+		$r = $Vend::Cfg->{SecureURL};
+	}
+
+	$path = escape_chars_url($path)
+		if $path =~ $need_escape;
     $r .= '/' . $path;
-	$r .= '.html' if $::Scratch->{mv_add_dot_html} and $r !~ /\.html?$/;
-	push @parms, "$::VN->{mv_session_id}=$id"			 	if defined $id;
-	push @parms, "$::VN->{mv_arg}=" . hexify($arguments)	if defined $arguments;
-	push @parms, "$::VN->{mv_pc}=$ct"                 	if defined $ct;
-	push @parms, "$::VN->{mv_cat}=$Vend::Cfg->{CatalogName}"
-														if defined $Vend::VirtualCat;
+	$r .= '.html' if $opt->{add_dot_html} and $r !~ /\.html?$/;
+
+	if($opt->{add_source} and $Vend::Session->{source}) {
+		my $sn = hexify($Vend::Session->{source});
+		push @parms, "$::VN->{mv_source}=$sn";
+	}
+
+	push @parms, "$::VN->{mv_session_id}=$id"			 if $id;
+	push @parms, "$::VN->{mv_arg}=" . hexify($arguments) if defined $arguments;
+	push @parms, "$::VN->{mv_pc}=$ct"                 	 if $ct;
+	push @parms, "$::VN->{mv_cat}=$Vend::Cat"            if $Vend::VirtualCat;
+
 	if($Vend::AccumulatingLinks) {
 		my $key = $path;
 		$key =~ s/\.html?$//;
@@ -965,20 +1356,36 @@
 		push(@Vend::Links, [$key, $value]) unless $Vend::LinkFound{$key}++;
 
 	}
-	return $r unless @parms;
-    return $r . '?' . join("&", @parms);
+
+    $r .= '?' . join($Global::UrlJoiner, @parms) if @parms;
+	if($opt->{anchor}) {
+		$opt->{anchor} =~ s/^#//;
+		$r .= $opt->{anchor};
+	}
+	return $r;
 } 
 
 sub secure_vendUrl {
-	return vendUrl($_[0], $_[1], $Vend::Cfg->{SecureURL});
+	return vendUrl($_[0], $_[1], $Vend::Cfg->{SecureURL}, $_[3]);
 }
 
+my %strip_vars;
+my $strip_init;
+
 sub change_url {
 	my $url = shift;
-	return $url if $url =~ m{^(?:\w+:)?/};
-#::logDebug("changed $url");
+	return $url if $url =~ m{^\w+:};
+	return $url if $url =~ m{^/};
+	if(! $strip_init) {
+		for(qw/mv_session_id mv_pc/) {
+			$strip_vars{$_} = 1;
+			$strip_vars{$::IV->{$_}} = 1;
+		}
+	}
+	my $arg;
 	my @args;
-	($url, @args) = split /[?&]/, $url;
+	($url, $arg) = split /[?&]/, $url, 2;
+	@args = grep ! $strip_vars{$_}, split $Global::UrlSplittor, $arg;
 	return Vend::Interpolate::tag_area( $url, '', {
 											form => join "\n", @args,
 										} );
@@ -990,8 +1397,6 @@
 	return $html;
 }
 
-my $use = undef;
-
 ### flock locking
 
 # sys/file.h:
@@ -1010,10 +1415,8 @@
     }
     else {
         if (! flock($fh, $flag | $flock_LOCK_NB)) {
-            if ($! =~ m/^Try again/
-                or $! =~ m/^Resource temporarily unavailable/
-                or $! =~ m/^Operation would block/) {
-                return 0;
+            if ($!{EAGAIN} or $!{EWOULDBLOCK}) {
+				return 0;
             }
             else {
                 die "Could not lock file: $!\n";
@@ -1041,9 +1444,7 @@
     }
     else {
         if (fcntl($fh, $op, $struct) < 0) {
-            if ($! =~ m/^Try again/
-                or $! =~ m/^Resource temporarily unavailable/
-                or $! =~ m/^Operation would block/) {
+            if ($!{EAGAIN} or $!{EWOULDBLOCK}) {
                 return 0;
             }
             else {
@@ -1058,9 +1459,7 @@
     my ($fh) = @_;
 	my $struct = pack('sslli', F_UNLCK, 0, 0, 0, $$);
 	if (fcntl($fh, F_SETLK, $struct) < 0) {
-		if ($! =~ m/^Try again/
-                or $! =~ m/^Resource temporarily unavailable/
-                or $! =~ m/^Operation would block/) {
+		if ($!{EAGAIN} or $!{EWOULDBLOCK}) {
 			return 0;
 		}
 		else {
@@ -1070,29 +1469,27 @@
 	return 1;
 }
 
-### Select based on os, vestigial
+my $lock_function = \&flock_lock;
+my $unlock_function = \&flock_unlock;
 
-my $lock_function;
-my $unlock_function;
-
-unless (defined $use) {
-    my $os = $Vend::Util::Config{'osname'};
-	$use = 'flock';
-	if ($os =~ /win32/i) {
-        $use = 'none';
-	}
-}
-        
-if ($use eq 'none') {
-    print "using NO locking\n";
-    $lock_function = sub {1};
-    $unlock_function = sub {1};
-}
-else {
-    $lock_function = \&flock_lock;
-    $unlock_function = \&flock_unlock;
+sub set_lock_type {
+	if ($Global::LockType eq 'none') {
+		logDebug("using NO locking");
+		$lock_function = sub {1};
+		$unlock_function = sub {1};
+	}
+	elsif ($Global::LockType =~ /fcntl/i) {
+		logDebug("using fcntl(2) locking");
+		$lock_function = \&fcntl_lock;
+		$unlock_function = \&fcntl_unlock;
+	}
+	else {
+		$lock_function = \&flock_lock;
+		$unlock_function = \&flock_unlock;
+	}
+	return; # VOID
 }
-    
+ 
 sub lockfile {
     &$lock_function(@_);
 }
@@ -1101,6 +1498,14 @@
     &$unlock_function(@_);
 }
 
+### Still necessary, sad to say.....
+if($Global::Windows) {
+	set_lock_type('none');
+}
+elsif($^O =~ /hpux/) {
+	set_lock_type('fcntl');
+}
+
 # Returns the total number of items ordered.
 # Uses the current cart if none specified.
 
@@ -1120,9 +1525,10 @@
 	if($opt->{qualifier}) {
 		$attr = $opt->{qualifier};
 		my $qr;
-		$qr = qr{$opt->{compare}}
-			if $opt->{compare};
-		if($opt->{compare}) {
+		eval { 
+			$qr = qr{$opt->{compare}} if $opt->{compare};
+		};
+		if($qr) {
 			$sub = sub { 
 							$_[0] =~ $qr;
 						};
@@ -1181,7 +1587,7 @@
 	}
 	else {
 		$pwinfo = $Vend::Cfg->{UserDatabase} unless $pwinfo;
-		undef $use_crypt unless $::Variable->{MV_USE_CRYPT};
+		undef $use_crypt if $::Variable->{MV_NO_CRYPT};
 		$cmp_pw = Vend::Interpolate::tag_data($pwinfo, 'password', $user)
 			if defined $Vend::Cfg->{Database}{$pwinfo};
 	}
@@ -1243,7 +1649,6 @@
 	}
 	elsif ($reconfig eq '2') {
 		$msg = "access protected database $item";
-#::logDebug("passed gate of $gate");
 		return 1 if is_yes($gate);
 	}
 	elsif ($reconfig eq '3') {
@@ -1266,7 +1671,7 @@
 	SCRIPT_NAME  %s
 	PATH_INFO    %s
 EOF
-		logGlobal ({}, $fmt,
+		logGlobal ({level => 'auth'}, $fmt,
 						$msg,
 						$CGI::script_name,
 						$CGI::host,
@@ -1287,7 +1692,7 @@
 		ne  $Vend::Cfg->{Password})
 	{
 		::logGlobal(
-				{},
+				{level => 'auth'},
 				"ALERT: Password mismatch, attempt to %s at %s from %s",
 				$msg,
 				$CGI::script_name,
@@ -1311,7 +1716,9 @@
 	PATH_INFO    %s
 EOF
 
-		::logGlobal($fmt,
+		::logGlobal(
+			{level => 'auth'},
+			$fmt,
 			$CGI::script_name,
 			$msg,
 			$CGI::remote_host,
@@ -1338,7 +1745,9 @@
 	SCRIPT_NAME  %s
 	PATH_INFO    %s
 EOF
-		::logGlobal ($fmt,
+		::logGlobal (
+				{level => 'auth'},
+				$fmt,
 				$msg,
 				$CGI::script_name,
 				$CGI::host,
@@ -1355,15 +1764,6 @@
 	return 1;
 }
 
-# Replace the escape notation %HH with the actual characters.
-#
-sub unescape_chars {
-    my($in) = @_;
-
-    $in =~ s/%(..)/chr(hex($1))/ge;
-    $in;
-}
-
 
 # Checks the Locale for a special page definintion mv_special_$key and
 # returns it if found, otherwise goes to the default Vend::Cfg->{Special} array
@@ -1381,7 +1781,7 @@
 
 sub logDebug {
 	return unless $Global::DebugFile;
-	print caller() . ':debug: ', @_, "\n";
+	print caller() . ':debug: ', errmsg(@_), "\n";
 }
 
 sub errmsg {
@@ -1393,18 +1793,31 @@
 	elsif($Global::Locale and defined $Global::Locale->{$fmt}) {
 	 	$location = $Global::Locale;
 	}
-	return sprintf $fmt, @strings if ! $location;
-	if(ref $location->{$fmt}) {
-		$fmt = $location->{$fmt}[0];
-		@strings = @strings[ @{ $location->{$fmt}[1] } ];
+	if($location) {
+		if(ref $location->{$fmt}) {
+			$fmt = $location->{$fmt}[0];
+			@strings = @strings[ @{ $location->{$fmt}[1] } ];
+		}
+		else {
+			$fmt = $location->{$fmt};
+		}
 	}
-	else {
-		$fmt = $location->{$fmt};
+	return scalar(@strings) ? sprintf $fmt, @strings : $fmt;
+}
+
+*l = \&errmsg;
+
+sub show_times {
+	my $message = shift || 'time mark';
+	my @times = times();
+	for( my $i = 0; $i < @times; $i++) {
+		$times[$i] -= $Vend::Times[$i];
 	}
-	return sprintf $fmt, @strings;
+	logDebug("$message: " . join " ", @times);
 }
 
 sub logGlobal {
+	return 1 if $Vend::ExternalProgram;
     my($msg) = shift;
 	my $opt;
 	if(ref $msg) {
@@ -1421,34 +1834,39 @@
 	if($opt and $Global::SysLog) {
 		$fn = "|" . ($Global::SysLog->{command} || 'logger');
 
-		my $leveled;
+		my $prioritized;
+		my $tagged;
+		my $facility = 'local3';
 		if($opt->{level} and defined $Global::SysLog->{$opt->{level}}) {
-			$fn .= " -p $Global::SysLog->{$opt->{level}}";
-			$leveled = 1;
+			my $stuff =  $Global::SysLog->{$opt->{level}};
+			if($stuff =~ /\./) {
+				$facility = $stuff;
+			}
+			else {
+				$facility .= ".$stuff";
+			}
+			$prioritized = 1;
 		}
 
-		my $tag = '';
-		if($Global::SysLog->{tag}) {
-			$tag = " -t $Global::SysLog->{tag}"
-				unless "\L$Global::Syslog->{tag}" eq 'none';
-		}
-		else {
-			$tag = " -t interchange";
-		}
-		$tag .= ".$opt->{level}" if $tag and ! $leveled;
+		my $tag = $Global::SysLog->{tag} || 'interchange';
 
-		$fn .= $tag;
+		$facility .= ".info" unless $prioritized;
+
+		$fn .= " -p $facility";
+		$fn .= " -t $tag" unless "\L$tag" eq 'none';
 
 		if($opt->{socket}) {
 			$fn .= " -u $opt->{socket}";
 		}
 	}
 
-	print "$msg\n" if $Vend::Foreground and ! $Vend::Log_suppress && ! $Vend::Quiet;
+	my $nl = ($opt and $opt->{strip}) ? '' : "\n";
+
+	print "$msg$nl" if $Global::Foreground and ! $Vend::Log_suppress && ! $Vend::Quiet;
 
 	$fn =~ s/^([^|>])/>>$1/
 		or $nolock = 1;
-#::logDebug("logging with $fn");
+
     $msg = format_log_msg($msg) if ! $nolock;
 
 	$Vend::Errors .= $msg if $Global::DisplayErrors;
@@ -1485,7 +1903,7 @@
 		$msg = errmsg($msg, @_);
 	}
 
-	print "$msg\n" if $Vend::Foreground and ! $Vend::Log_suppress && ! $Vend::Quiet;
+	print "$msg\n" if $Global::Foreground and ! $Vend::Log_suppress && ! $Vend::Quiet;
 
 	$Vend::Session->{last_error} = $msg;
 
@@ -1505,7 +1923,8 @@
     };
     if ($@) {
 		chomp $@;
-		logGlobal ("Could not %s error file %s: %s\nto report this error: %s",
+		logGlobal ({ level => 'info' },
+					"Could not %s error file %s: %s\nto report this error: %s",
 					$@,
 					$Vend::Cfg->{ErrorFile},
 					$!,
@@ -1514,12 +1933,44 @@
     }
 }
 
+# Front-end to log routines that ignores repeated identical
+# log messages after the first occurrence
+my %logOnce_cache;
+my %log_sub_map = (
+	data	=> \&logData,
+	debug	=> \&logDebug,
+	error	=> \&logError,
+	global	=> \&logGlobal,
+);
+
+# First argument should be log type (see above map).
+# Rest of arguments are same as if calling log routine directly.
+sub logOnce {
+	return if exists $logOnce_cache{"@_"};
+	my $log_sub = $log_sub_map{ lc(shift) } || $log_sub_map{error};
+	$log_sub->(@_) and ++$logOnce_cache{"@_"};
+}
+
+
 # Here for convenience in calls
 sub set_cookie {
-    my ($name, $value, $expire) = @_;
-    $::Instance->{Cookies} = []
-        if ! $::Instance->{Cookies};
-    @{$::Instance->{Cookies}} = [$name, $value, $expire];
+    my ($name, $value, $expire, $domain, $path) = @_;
+
+    # Set expire to now + some time if expire string is something like
+    # "30 days" or "7 weeks" or even "60 minutes"
+	if($expire =~ /^\s*\d+[\s\0]*[A-Za-z]\S*\s*$/) {
+		my $add = Vend::Config::time_to_seconds($expire);
+		$expire = time() + $add if $add;
+	}
+
+	if (! $::Instance->{Cookies}) {
+		$::Instance->{Cookies} = []
+	}
+	else {
+		@{$::Instance->{Cookies}} =
+			grep $_->[0] ne $name, @{$::Instance->{Cookies}};
+	}
+    push @{$::Instance->{Cookies}}, [$name, $value, $expire, $domain, $path];
     return;
 }
 
@@ -1690,16 +2141,251 @@
 	return &{$canonpath_routine}(@_);
 }
 
-# LEGACY4
-*send_mail = \&Vend::Order::send_mail;
-# END LEGACY4
-
 #print "catfile a b c --> " . catfile('a', 'b', 'c') . "\n";
 #print "catdir a b c --> " . catdir('a', 'b', 'c') . "\n";
 #print "canonpath a/b//../../c --> " . canonpath('a/b/../../c') . "\n";
 #print "file_name_is_absolute a/b/c --> " . file_name_is_absolute('a/b/c') . "\n";
 #print "file_name_is_absolute a:b/c --> " . file_name_is_absolute('a:b/c') . "\n";
 #print "file_name_is_absolute /a/b/c --> " . file_name_is_absolute('/a/b/c') . "\n";
+
+#my $MIME_Lite;
+#eval {
+#	require MIME::Lite;
+#	$MIME_Lite = 1;
+#	require Net::SMTP;
+#};
+#
+#sub mime_lite_send {
+#	my ($opt, $body) = @_;
+#
+#	if(! $MIME_Lite) {
+#		return send_mail(
+#			$opt->{to},
+#			$opt->{subject},
+#			$body,
+#			$opt->{reply},
+#			undef,
+#			split /\n+/, $opt->{extra}
+#			);
+#	}
+#
+#	my %special = qw/
+#		as_string 1
+#		internal  1
+#	/;
+#	my $mime = new MIME::Lite;;
+#
+#	my @ary;
+#	my $popt = {};
+#	my $mopt = {};
+#	for(keys %$opt) {
+#		if(ref $opt->{$_}) {
+#			push @ary, [ $_, delete $opt->{$_} ];
+#		}
+#		if($special{$_}) {
+#			$popt->{$_} = delete $opt->{$_};
+#		}
+#		my $m = $_;
+#		s/_/-/g;
+#		s/(\w+)/\L\u$1/g;
+#		s/-/_/g;
+#		$mopt->{$_} = $opt->{$m};
+#	}
+#
+#}
+
+sub send_mail {
+	my($to, $subject, $body, $reply, $use_mime, @extra_headers) = @_;
+
+	my @headers;
+	if(ref $to) {
+		my $head = $to;
+		$body = $subject;
+		undef $subject;
+		for(@$head) {
+			if( /^To:\s*(.+)/ ) {
+				$to = $1;
+			}
+			elsif (/Reply-to:\s*(.+)/) {
+				$reply = $_;
+			}
+			elsif (/^subj(?:ect)?:\s*(.+)/i) {
+				$subject = $1;
+			}
+			elsif($_) {
+				push @extra_headers, $_;
+			}
+		}
+	}
+
+
+	my($ok);
+#::logDebug("send_mail: to=$to subj=$subject r=$reply mime=$use_mime\n");
+
+	unless (defined $use_mime) {
+		$use_mime = $::Instance->{MIME} || undef;
+	}
+
+	if(!defined $reply) {
+		$reply = $::Values->{mv_email}
+				?  "Reply-To: $::Values->{mv_email}\n"
+				: '';
+	}
+	elsif ($reply) {
+		$reply = "Reply-To: $reply\n"
+			unless $reply =~ /^reply-to:/i;
+		$reply =~ s/\s+$/\n/;
+	}
+
+	$ok = 0;
+	my $none;
+	my $using = $Vend::Cfg->{SendMailProgram};
+
+	if($using =~ /^(none|Net::SMTP)$/i) {
+		$none = 1;
+		$ok = 1;
+	}
+
+	SEND: {
+#::logDebug("testing sendmail send none=$none");
+		last SEND if $none;
+#::logDebug("in Sendmail send $using");
+		open(MVMAIL,"|$Vend::Cfg->{SendMailProgram} -t") or last SEND;
+		my $mime = '';
+		$mime = Vend::Interpolate::mime('header', {}, '') if $use_mime;
+		print MVMAIL "To: $to\n", $reply, "Subject: $subject\n"
+			or last SEND;
+		for(@extra_headers) {
+			s/\s*$/\n/;
+			print MVMAIL $_
+				or last SEND;
+		}
+		$mime =~ s/\s*$/\n/;
+		print MVMAIL $mime
+			or last SEND;
+		print MVMAIL $body
+				or last SEND;
+		print MVMAIL Vend::Interpolate::do_tag('mime boundary') . '--'
+			if $use_mime;
+		print MVMAIL "\r\n\cZ" if $Global::Windows;
+		close MVMAIL or last SEND;
+		$ok = ($? == 0);
+	}
+
+	SMTP: {
+		my $mhost = $::Variable->{MV_SMTPHOST} || $Global::Variable->{MV_SMTPHOST};
+		my $helo =  $Global::Variable->{MV_HELO};
+		last SMTP unless $none and $mhost;
+		eval {
+			require Net::SMTP;
+		};
+		last SMTP if $@;
+		$ok = 0;
+		$using = "Net::SMTP (mail server $mhost)";
+#::logDebug("using $using");
+		undef $none;
+
+		my $smtp = new Net::SMTP $mhost;
+		$smtp->hello($helo) if $helo;
+#::logDebug("smtp object $smtp");
+
+		my $from = $::Variable->{MV_MAILFROM}
+				|| $Global::Variable->{MV_MAILFROM}
+				|| $Vend::Cfg->{MailOrderTo};
+		
+		for(@extra_headers) {
+			s/\s*$/\n/;
+			next unless /^From:\s*(\S.+)$/mi;
+			$from = $1;
+		}
+		my $mime = '';
+		$mime = Vend::Interpolate::mime('header', {}, '') if $use_mime;
+		$smtp->mail($from)
+			or last SMTP;
+#::logDebug("smtp accepted from=$from");
+
+		my @to;
+		my @addr = split /\s*,\s*/, $to;
+		for (@addr) {
+			if(/\s/) {
+				## Uh-oh. Try to handle
+				if ( m{( <.+?> | [^\s,]+\@[^\s,]+ ) }x ) {
+					push @to, $1
+				}
+				else {
+					logError("Net::SMTP sender skipping unparsable address %s", $_);
+				}
+			}
+			else {
+				push @to, $_;
+			}
+		}
+		
+		@addr = $smtp->recipient(@to, { SkipBad => 1 });
+		if(scalar(@addr) != scalar(@to)) {
+			logError(
+				"Net::SMTP not able to send to all addresses of %s",
+				join(", ", @to),
+			);
+		}
+
+#::logDebug("smtp accepted to=" . join(",", @addr));
+
+		$smtp->data();
+
+		push @extra_headers, $reply if $reply;
+		for ("To: $to", "Subject: $subject", @extra_headers) {
+			next unless $_;
+			s/\s*$/\n/;
+#::logDebug(do { my $it = $_; $it =~ s/\s+$//; "datasend=$it" });
+			$smtp->datasend($_)
+				or last SMTP;
+		}
+
+		if($use_mime) {
+			$mime =~ s/\s*$/\n/;
+			$smtp->datasend($mime)
+				or last SMTP;
+		}
+		$smtp->datasend("\n");
+		$smtp->datasend($body)
+			or last SMTP;
+		$smtp->datasend(Vend::Interpolate::do_tag('mime boundary') . '--')
+			if $use_mime;
+		$smtp->dataend()
+			or last SMTP;
+		$ok = $smtp->quit();
+	}
+
+	if ($none or !$ok) {
+		logError("Unable to send mail using %s\nTo: %s\nSubject: %s\n%s\n\n%s",
+				$using,
+				$to,
+				$subject,
+				$reply,
+				$body,
+		);
+	}
+
+	$ok;
+}
+
+sub get_cfg_header {
+	my ($file) = @_;
+	my $cfg = {};
+	local ($_, *IN);
+	unless (open IN, "<$file") {
+		my @msg = ("Can't open config file '%s': %s\n", $file, $!);
+		logError(@msg);
+		return { error => errmsg(@msg) };
+	}
+	while (<IN>) {
+		($cfg->{position} = $1, last) if /^\s*#\s*position\s*:\s*(\d+)/i;
+	}
+	close IN;
+	return $cfg;
+}
+
 
 1;
 __END__



No                   revision



No                   revision



2.2.2.1   +2 -2      interchange/lib/Vend/Accounting.pm


rev 2.2.2.1, prev_rev 2.2
Index: Accounting.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Accounting.pm,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1
--- Accounting.pm	16 Sep 2002 23:06:31 -0000	2.2
+++ Accounting.pm	25 Jan 2003 22:21:27 -0000	2.2.2.1
@@ -1,6 +1,6 @@
 # Vend::Accounting - Interchange payment processing routines
 #
-# $Id: Accounting.pm,v 2.2 2002/09/16 23:06:31 mheins Exp $
+# $Id: Accounting.pm,v 2.2.2.1 2003/01/25 22:21:27 racke Exp $
 #
 # Copyright (C) 2002 Mike Heins, <mike@heins.net>
 #
@@ -21,7 +21,7 @@
 
 package Vend::Accounting;
 
-$VERSION = substr(q$Revision: 2.2 $, 10);
+$VERSION = substr(q$Revision: 2.2.2.1 $, 10);
 
 use Vend::Util;
 use LWP::UserAgent;



1.1.2.1   +2 -2      interchange/lib/Vend/CounterFile.pm


rev 1.1.2.1, prev_rev 1.1
Index: CounterFile.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/CounterFile.pm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- CounterFile.pm	4 Feb 2002 03:08:16 -0000	1.1
+++ CounterFile.pm	25 Jan 2003 22:21:27 -0000	1.1.2.1
@@ -1,6 +1,6 @@
 # This -*-perl -*- module implements a persistent counter class.
 #
-# $Id: CounterFile.pm,v 1.1 2002/02/04 03:08:16 mheins Exp $
+# $Id: CounterFile.pm,v 1.1.2.1 2003/01/25 22:21:27 racke Exp $
 #
 
 package Vend::CounterFile;
@@ -97,7 +97,7 @@
 };
 
 sub Version { $VERSION; }
-$VERSION = sprintf("%d.%02d", q$Revision: 1.1 $ =~ /(\d+)\.(\d+)/);
+$VERSION = sprintf("%d.%02d", q$Revision: 1.1.2.1 $ =~ /(\d+)\.(\d+)/);
 
 $MAGIC           = "#COUNTER-1.0\n";   # first line in counter files
 $DEFAULT_INITIAL = 0;                  # default initial counter value



1.9.2.1   +1 -1      interchange/lib/Vend/Dispatch.pm


rev 1.9.2.1, prev_rev 1.9
Index: Dispatch.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Dispatch.pm,v
retrieving revision 1.9
retrieving revision 1.9.2.1
diff -u -r1.9 -r1.9.2.1
--- Dispatch.pm	23 Jan 2003 19:18:47 -0000	1.9
+++ Dispatch.pm	25 Jan 2003 22:21:27 -0000	1.9.2.1
@@ -1,6 +1,6 @@
 # Vend::Dispatch - Handle Interchange page requests
 #
-# $Id: Dispatch.pm,v 1.9 2003/01/23 19:18:47 mheins Exp $
+# $Id: Dispatch.pm,v 1.9.2.1 2003/01/25 22:21:27 racke Exp $
 #
 # Copyright (C) 2002 ICDEVGROUP <interchange@icdevgroup.org>
 # Copyright (C) 2002 Mike Heins <mike@perusion.net>
@@ -26,7 +26,7 @@
 package Vend::Dispatch;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.9 $, 10);
+$VERSION = substr(q$Revision: 1.9.2.1 $, 10);
 
 use POSIX qw(strftime);
 use Vend::Util;
@@ -983,7 +983,7 @@
 
 	chdir $Vend::Cfg->{VendRoot} 
 		or die "Couldn't change to $Vend::Cfg->{VendRoot}: $!\n";
-	POSIX::setlocale(POSIX::LC_ALL, $Vend::Cfg->{ExecutionLocale});
+	POSIX::setlocale('LC_ALL', $Vend::Cfg->{ExecutionLocale});
 	set_file_permissions();
 # STATICPAGE
 	tie_static_dbm() if $Vend::Cfg->{StaticDBM};



2.23.2.1  +2 -2      interchange/lib/Vend/Form.pm


rev 2.23.2.1, prev_rev 2.23
Index: Form.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Form.pm,v
retrieving revision 2.23
retrieving revision 2.23.2.1
diff -u -r2.23 -r2.23.2.1
--- Form.pm	12 Dec 2002 03:18:57 -0000	2.23
+++ Form.pm	25 Jan 2003 22:21:27 -0000	2.23.2.1
@@ -1,6 +1,6 @@
 # Vend::Form - Generate Form widgets
 # 
-# $Id: Form.pm,v 2.23 2002/12/12 03:18:57 mheins Exp $
+# $Id: Form.pm,v 2.23.2.1 2003/01/25 22:21:27 racke Exp $
 #
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -37,7 +37,7 @@
 require Exporter;
 @ISA = qw(Exporter);
 
-$VERSION = substr(q$Revision: 2.23 $, 10);
+$VERSION = substr(q$Revision: 2.23.2.1 $, 10);
 
 @EXPORT = qw (
 	display



2.22.2.1  +2 -2      interchange/lib/Vend/Menu.pm


rev 2.22.2.1, prev_rev 2.22
Index: Menu.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Menu.pm,v
retrieving revision 2.22
retrieving revision 2.22.2.1
diff -u -r2.22 -r2.22.2.1
--- Menu.pm	20 Jan 2003 16:50:28 -0000	2.22
+++ Menu.pm	25 Jan 2003 22:21:28 -0000	2.22.2.1
@@ -1,6 +1,6 @@
 # Vend::Menu - Interchange menu processing routines
 #
-# $Id: Menu.pm,v 2.22 2003/01/20 16:50:28 mheins Exp $
+# $Id: Menu.pm,v 2.22.2.1 2003/01/25 22:21:28 racke Exp $
 #
 # Copyright (C) 2002 Mike Heins, <mike@perusion.net>
 #
@@ -21,7 +21,7 @@
 
 package Vend::Menu;
 
-$VERSION = substr(q$Revision: 2.22 $, 10);
+$VERSION = substr(q$Revision: 2.22.2.1 $, 10);
 
 use Vend::Util;
 use strict;



2.4.2.1   +2 -2      interchange/lib/Vend/ModPerl.pm


rev 2.4.2.1, prev_rev 2.4
Index: ModPerl.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/ModPerl.pm,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1
--- ModPerl.pm	10 Dec 2002 20:25:22 -0000	2.4
+++ ModPerl.pm	25 Jan 2003 22:21:28 -0000	2.4.2.1
@@ -1,6 +1,6 @@
 # Vend::ModPerl - Run Interchange inside Apache and mod_perl
 #
-# $Id: ModPerl.pm,v 2.4 2002/12/10 20:25:22 jon Exp $
+# $Id: ModPerl.pm,v 2.4.2.1 2003/01/25 22:21:28 racke Exp $
 #
 # Copyright (C) 2002 Red Hat, Inc. and Jon Jensen <jon@icdevgroup.org>
 #
@@ -20,7 +20,7 @@
 
 package Vend::ModPerl;
 
-$VERSION = substr(q$Revision: 2.4 $, 10);
+$VERSION = substr(q$Revision: 2.4.2.1 $, 10);
 
 use Apache::Constants qw(:common);
 use Apache::Request ();



2.9.2.1   +2 -2      interchange/lib/Vend/Payment.pm


rev 2.9.2.1, prev_rev 2.9
Index: Payment.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment.pm,v
retrieving revision 2.9
retrieving revision 2.9.2.1
diff -u -r2.9 -r2.9.2.1
--- Payment.pm	13 Dec 2002 03:22:27 -0000	2.9
+++ Payment.pm	25 Jan 2003 22:21:28 -0000	2.9.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment - Interchange payment processing routines
 #
-# $Id: Payment.pm,v 2.9 2002/12/13 03:22:27 ramoore Exp $
+# $Id: Payment.pm,v 2.9.2.1 2003/01/25 22:21:28 racke Exp $
 #
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -22,7 +22,7 @@
 package Vend::Payment;
 require Exporter;
 
-$VERSION = substr(q$Revision: 2.9 $, 10);
+$VERSION = substr(q$Revision: 2.9.2.1 $, 10);
 
 @ISA = qw(Exporter);
 



2.5.2.1   +2 -2      interchange/lib/Vend/RefSearch.pm


rev 2.5.2.1, prev_rev 2.5
Index: RefSearch.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/RefSearch.pm,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1
--- RefSearch.pm	15 Jul 2002 13:41:12 -0000	2.5
+++ RefSearch.pm	25 Jan 2003 22:21:28 -0000	2.5.2.1
@@ -1,6 +1,6 @@
 # Vend::DbSearch - Search indexes with Interchange
 #
-# $Id: RefSearch.pm,v 2.5 2002/07/15 13:41:12 mheins Exp $
+# $Id: RefSearch.pm,v 2.5.2.1 2003/01/25 22:21:28 racke Exp $
 #
 # Adapted for use with Interchange from Search::TextSearch
 #
@@ -26,7 +26,7 @@
 
 @ISA = qw(Vend::Search);
 
-$VERSION = substr(q$Revision: 2.5 $, 10);
+$VERSION = substr(q$Revision: 2.5.2.1 $, 10);
 
 use strict;
 



2.3.2.1   +2 -2      interchange/lib/Vend/SOAP.pm


rev 2.3.2.1, prev_rev 2.3
Index: SOAP.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/SOAP.pm,v
retrieving revision 2.3
retrieving revision 2.3.2.1
diff -u -r2.3 -r2.3.2.1
--- SOAP.pm	18 Nov 2002 16:55:15 -0000	2.3
+++ SOAP.pm	25 Jan 2003 22:21:28 -0000	2.3.2.1
@@ -1,6 +1,6 @@
 # Vend::SOAP - Handle SOAP connections for Interchange
 #
-# $Id: SOAP.pm,v 2.3 2002/11/18 16:55:15 mheins Exp $
+# $Id: SOAP.pm,v 2.3.2.1 2003/01/25 22:21:28 racke Exp $
 #
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -34,7 +34,7 @@
 use strict;
 
 use vars qw($VERSION @ISA $AUTOLOAD);
-$VERSION = substr(q$Revision: 2.3 $, 10);
+$VERSION = substr(q$Revision: 2.3.2.1 $, 10);
 @ISA = qw/SOAP::Server/;
 
 my %Allowed_tags;



1.1.2.1   +2 -2      interchange/lib/Vend/Swish.pm


rev 1.1.2.1, prev_rev 1.1
Index: Swish.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Swish.pm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- Swish.pm	17 Oct 2002 04:03:13 -0000	1.1
+++ Swish.pm	25 Jan 2003 22:21:28 -0000	1.1.2.1
@@ -1,6 +1,6 @@
 # Vend::Swish - Search indexes with Swish-e
 #
-# $Id: Swish.pm,v 1.1 2002/10/17 04:03:13 mheins Exp $
+# $Id: Swish.pm,v 1.1.2.1 2003/01/25 22:21:28 racke Exp $
 #
 # Adapted from Vend::Glimpse
 #
@@ -25,7 +25,7 @@
 require Vend::Search;
 @ISA = qw(Vend::Search);
 
-$VERSION = substr(q$Revision: 1.1 $, 10);
+$VERSION = substr(q$Revision: 1.1.2.1 $, 10);
 use strict;
 
 sub array {



No                   revision



No                   revision



1.7.2.1   +0 -0      interchange/lib/Vend/Accounting/SQL_Ledger.pm


rev 1.7.2.1, prev_rev 1.7
Index: SQL_Ledger.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Accounting/SQL_Ledger.pm,v
retrieving revision 1.7
retrieving revision 1.7.2.1
diff -u -r1.7 -r1.7.2.1



No                   revision



No                   revision



2.7.2.1   +2 -2      interchange/lib/Vend/Payment/AuthorizeNet.pm


rev 2.7.2.1, prev_rev 2.7
Index: AuthorizeNet.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/AuthorizeNet.pm,v
retrieving revision 2.7
retrieving revision 2.7.2.1
diff -u -r2.7 -r2.7.2.1
--- AuthorizeNet.pm	17 Dec 2002 02:39:04 -0000	2.7
+++ AuthorizeNet.pm	25 Jan 2003 22:21:30 -0000	2.7.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::AuthorizeNet - Interchange AuthorizeNet support
 #
-# $Id: AuthorizeNet.pm,v 2.7 2002/12/17 02:39:04 kwalsh Exp $
+# $Id: AuthorizeNet.pm,v 2.7.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -38,7 +38,7 @@
 
 =head1 Interchange AuthorizeNet Support
 
-Vend::Payment::AuthorizeNet $Revision: 2.7 $
+Vend::Payment::AuthorizeNet $Revision: 2.7.2.1 $
 
 =head1 SYNOPSIS
 



1.4.2.1   +2 -2      interchange/lib/Vend/Payment/BoA.pm


rev 1.4.2.1, prev_rev 1.4
Index: BoA.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/BoA.pm,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -u -r1.4 -r1.4.2.1
--- BoA.pm	28 Mar 2002 15:54:20 -0000	1.4
+++ BoA.pm	25 Jan 2003 22:21:30 -0000	1.4.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::BoA - Interchange BoA support
 #
-# $Id: BoA.pm,v 1.4 2002/03/28 15:54:20 jon Exp $
+# $Id: BoA.pm,v 1.4.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -33,7 +33,7 @@
 
 =head1 Interchange BoA Support
 
-Vend::Payment::BoA $Revision: 1.4 $
+Vend::Payment::BoA $Revision: 1.4.2.1 $
 
 =head1 SYNOPSIS
 



2.1.2.1   +2 -2      interchange/lib/Vend/Payment/CCVS.pm


rev 2.1.2.1, prev_rev 2.1
Index: CCVS.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/CCVS.pm,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1
--- CCVS.pm	17 Jun 2002 22:24:11 -0000	2.1
+++ CCVS.pm	25 Jan 2003 22:21:30 -0000	2.1.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::CCVS - Interchange CCVS support
 #
-# $Id: CCVS.pm,v 2.1 2002/06/17 22:24:11 jon Exp $
+# $Id: CCVS.pm,v 2.1.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -25,7 +25,7 @@
 
 =head1 Interchange CCVS support
 
-Vend::Payment::CCVS $Revision: 2.1 $
+Vend::Payment::CCVS $Revision: 2.1.2.1 $
 
 =head1 SYNOPSIS
 



2.1.2.1   +3 -3      interchange/lib/Vend/Payment/CyberCash.pm


rev 2.1.2.1, prev_rev 2.1
Index: CyberCash.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/CyberCash.pm,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1
--- CyberCash.pm	17 Jun 2002 22:24:11 -0000	2.1
+++ CyberCash.pm	25 Jan 2003 22:21:30 -0000	2.1.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::CyberCash - Interchange CyberCash support
 #
-# $Id: CyberCash.pm,v 2.1 2002/06/17 22:24:11 jon Exp $
+# $Id: CyberCash.pm,v 2.1.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2002 Red Hat, Inc. <interchange@redhat.com>
 
@@ -24,11 +24,11 @@
 
 package Vend::Payment::CyberCash;
 
-$VERSION = substr(q$Revision: 2.1 $, 10);
+$VERSION = substr(q$Revision: 2.1.2.1 $, 10);
 
 =head1 Interchange CyberCash Support
 
-Vend::Payment::CyberCash $Revision: 2.1 $
+Vend::Payment::CyberCash $Revision: 2.1.2.1 $
 
 =head1 SYNOPSIS
 



1.3.2.1   +2 -2      interchange/lib/Vend/Payment/ECHO.pm


rev 1.3.2.1, prev_rev 1.3
Index: ECHO.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/ECHO.pm,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1
--- ECHO.pm	27 Aug 2002 05:12:52 -0000	1.3
+++ ECHO.pm	25 Jan 2003 22:21:30 -0000	1.3.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::ECHO - Interchange ECHO support
 #
-# $Id: ECHO.pm,v 1.3 2002/08/27 05:12:52 kwalsh Exp $
+# $Id: ECHO.pm,v 1.3.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 2002 
 #      Electric Pulp. <info@electricpulp.com> 
@@ -34,7 +34,7 @@
 
 =head1 Interchange ECHO Support
 
-Vend::Payment::ECHO $Revision: 1.3 $
+Vend::Payment::ECHO $Revision: 1.3.2.1 $
 
 =head1 AUTHOR
 



1.2.2.1   +3 -3      interchange/lib/Vend/Payment/MCVE.pm


rev 1.2.2.1, prev_rev 1.2
Index: MCVE.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/MCVE.pm,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1
--- MCVE.pm	16 Sep 2002 23:06:32 -0000	1.2
+++ MCVE.pm	25 Jan 2003 22:21:30 -0000	1.2.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::MCVE - Interchange MCVE support
 #
-# $Id: MCVE.pm,v 1.2 2002/09/16 23:06:32 mheins Exp $
+# $Id: MCVE.pm,v 1.2.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Author: Tom Friedel (tom@readyink.com) for Carlc Internet Services (http://www.carlc.com)
 #
@@ -22,11 +22,11 @@
 package Vend::Payment::MCVE;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.2 $, 10);
+$VERSION = substr(q$Revision: 1.2.2.1 $, 10);
 
 =head1 Interchange MCVE support
 
-Vend::Payment::MCVE $Revision: 1.2 $
+Vend::Payment::MCVE $Revision: 1.2.2.1 $
 
 =head1 SYNOPSIS
 



2.5.2.1   +2 -2      interchange/lib/Vend/Payment/Signio.pm


rev 2.5.2.1, prev_rev 2.5
Index: Signio.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/Signio.pm,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1
--- Signio.pm	21 Jan 2003 03:51:10 -0000	2.5
+++ Signio.pm	25 Jan 2003 22:21:30 -0000	2.5.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::Signio - Interchange support for Signio/Verisign Payflow Pro
 #
-# $Id: Signio.pm,v 2.5 2003/01/21 03:51:10 jon Exp $
+# $Id: Signio.pm,v 2.5.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2003 Red Hat, Inc. and Interchange Development Group
 #
@@ -23,7 +23,7 @@
 
 =head1 Interchange support for Signio/Verisign Payflow Pro
 
-Vend::Payment::Signio $Revision: 2.5 $
+Vend::Payment::Signio $Revision: 2.5.2.1 $
 
 =head1 SYNOPSIS
 



2.4.2.1   +2 -2      interchange/lib/Vend/Payment/Skipjack.pm


rev 2.4.2.1, prev_rev 2.4
Index: Skipjack.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/Skipjack.pm,v
retrieving revision 2.4
retrieving revision 2.4.2.1
diff -u -r2.4 -r2.4.2.1
--- Skipjack.pm	4 Sep 2002 16:06:51 -0000	2.4
+++ Skipjack.pm	25 Jan 2003 22:21:30 -0000	2.4.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::Skipjack - Interchange Skipjack support
 #
-# $Id: Skipjack.pm,v 2.4 2002/09/04 16:06:51 mheins Exp $
+# $Id: Skipjack.pm,v 2.4.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -27,7 +27,7 @@
 
 =head1 Interchange Skipjack Support
 
-Vend::Payment::Skipjack $Revision: 2.4 $
+Vend::Payment::Skipjack $Revision: 2.4.2.1 $
 
 =head1 SYNOPSIS
 



1.1.2.1   +2 -2      interchange/lib/Vend/Payment/TCLink.pm


rev 1.1.2.1, prev_rev 1.1
Index: TCLink.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/TCLink.pm,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- TCLink.pm	24 Jul 2002 15:36:05 -0000	1.1
+++ TCLink.pm	25 Jan 2003 22:21:30 -0000	1.1.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::TCLink - Interchange TrustCommerce TCLink support
 #
-# $Id: TCLink.pm,v 1.1 2002/07/24 15:36:05 kwalsh Exp $
+# $Id: TCLink.pm,v 1.1.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 2002 TrustCommerce <developer@trustcommerce.com>
 #
@@ -30,7 +30,7 @@
 
 =head1 Interchange TrustCommerce Support
 
-Vend::Payment::TCLink $Revision: 1.1 $
+Vend::Payment::TCLink $Revision: 1.1.2.1 $
 
 =head1 SYNOPSIS
 



1.3.2.1   +3 -3      interchange/lib/Vend/Payment/TestPayment.pm


rev 1.3.2.1, prev_rev 1.3
Index: TestPayment.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/TestPayment.pm,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1
--- TestPayment.pm	18 Oct 2002 06:56:24 -0000	1.3
+++ TestPayment.pm	25 Jan 2003 22:21:30 -0000	1.3.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::TestPayment - Interchange payment test module
 #
-# $Id: TestPayment.pm,v 1.3 2002/10/18 06:56:24 mheins Exp $
+# $Id: TestPayment.pm,v 1.3.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 2002 Cursor Software Limited.
 # All Rights Reserved.
@@ -27,7 +27,7 @@
 
 =head1 Interchange payment test module
 
-Vend::Payment::TestPayment $Revision: 1.3 $
+Vend::Payment::TestPayment $Revision: 1.3.2.1 $
 
 =head1 SYNOPSIS
 
@@ -190,7 +190,7 @@
 	unless $Vend::Quiet;
 }
 
-$VERSION = substr(q$Revision: 1.3 $,10);
+$VERSION = substr(q$Revision: 1.3.2.1 $,10);
 
 package Vend::Payment;
 



1.3.2.1   +2 -2      interchange/lib/Vend/Payment/WellsFargo.pm


rev 1.3.2.1, prev_rev 1.3
Index: WellsFargo.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/WellsFargo.pm,v
retrieving revision 1.3
retrieving revision 1.3.2.1
diff -u -r1.3 -r1.3.2.1
--- WellsFargo.pm	18 Nov 2002 16:55:15 -0000	1.3
+++ WellsFargo.pm	25 Jan 2003 22:21:30 -0000	1.3.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::WellsFargo - Interchange WellsFargo support
 #
-# $Id: WellsFargo.pm,v 1.3 2002/11/18 16:55:15 mheins Exp $
+# $Id: WellsFargo.pm,v 1.3.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -33,7 +33,7 @@
 
 =head1 Interchange WellsFargo Support
 
-Vend::Payment::WellsFargo $Revision: 1.3 $
+Vend::Payment::WellsFargo $Revision: 1.3.2.1 $
 
 =head1 SYNOPSIS
 



2.2.2.1   +2 -2      interchange/lib/Vend/Payment/iTransact.pm


rev 2.2.2.1, prev_rev 2.2
Index: iTransact.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Payment/iTransact.pm,v
retrieving revision 2.2
retrieving revision 2.2.2.1
diff -u -r2.2 -r2.2.2.1
--- iTransact.pm	17 Jun 2002 22:24:11 -0000	2.2
+++ iTransact.pm	25 Jan 2003 22:21:30 -0000	2.2.2.1
@@ -1,6 +1,6 @@
 # Vend::Payment::iTransact - Interchange iTransact Support
 #
-# $Id: iTransact.pm,v 2.2 2002/06/17 22:24:11 jon Exp $
+# $Id: iTransact.pm,v 2.2.2.1 2003/01/25 22:21:30 racke Exp $
 #
 # Copyright (C) 1999-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -27,7 +27,7 @@
 
 =head1 Interchange iTransact Support
 
-Vend::Payment::iTransact $Revision: 2.2 $
+Vend::Payment::iTransact $Revision: 2.2.2.1 $
 
 =head1 SYNOPSIS
 



No                   revision



No                   revision



2.1.2.1   +2 -2      interchange/lib/Vend/SOAP/Transport.pm


rev 2.1.2.1, prev_rev 2.1
Index: Transport.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/SOAP/Transport.pm,v
retrieving revision 2.1
retrieving revision 2.1.2.1
diff -u -r2.1 -r2.1.2.1
--- Transport.pm	17 Jun 2002 22:24:11 -0000	2.1
+++ Transport.pm	25 Jan 2003 22:21:31 -0000	2.1.2.1
@@ -1,6 +1,6 @@
 # SOAP::Transport - Handle Interchange SOAP connections
 #
-# $Id: Transport.pm,v 2.1 2002/06/17 22:24:11 jon Exp $
+# $Id: Transport.pm,v 2.1.2.1 2003/01/25 22:21:31 racke Exp $
 #
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -31,7 +31,7 @@
 
 use strict;
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 2.1 $, 10);
+$VERSION = substr(q$Revision: 2.1.2.1 $, 10);
 
 # ======================================================================
 



No                   revision



No                   revision



1.15.4.2  +358 -104  interchange/lib/Vend/Table/Common.pm


rev 1.15.4.2, prev_rev 1.15.4.1
Index: Common.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/Common.pm,v
retrieving revision 1.15.4.1
retrieving revision 1.15.4.2
diff -u -r1.15.4.1 -r1.15.4.2
--- Common.pm	27 Nov 2000 02:39:22 -0000	1.15.4.1
+++ Common.pm	25 Jan 2003 22:21:31 -0000	1.15.4.2
@@ -1,14 +1,12 @@
-# Table/Common.pm: Common access methods for Interchange Databases
+# Vend::Table::Common - Common access methods for Interchange databases
 #
-# $Id: Common.pm,v 1.15.4.1 2000/11/27 02:39:22 racke Exp $
+# $Id: Common.pm,v 1.15.4.2 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
+# Copyright (C) 2003 ICDEVGROUP <interchange@icdevgroup.org>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -25,12 +23,13 @@
 # Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 # MA  02111-1307  USA.
 
-$VERSION = substr(q$Revision: 1.15.4.1 $, 10);
+$VERSION = substr(q$Revision: 1.15.4.2 $, 10);
 use strict;
 
 package Vend::Table::Common;
 require Vend::DbSearch;
 require Vend::TextSearch;
+require Vend::CounterFile;
 use Vend::Util;
 
 use Exporter;
@@ -137,11 +136,15 @@
 sub autonumber {
 	my $s = shift;
 	my $start;
-	return '' if not $start = $s->[$CONFIG]->{AUTO_NUMBER};
+	my $cfg = $s->[$CONFIG];
+
+	return $s->autosequence() if $cfg->{AUTO_SEQUENCE};
+
+	return '' if not $start = $cfg->{AUTO_NUMBER};
 	local($/) = "\n";
 	my $c = $s->[$CONFIG];
 	if(! defined $c->{AutoNumberCounter}) {
-		$c->{AutoNumberCounter} = new File::CounterFile
+		$c->{AutoNumberCounter} = new Vend::CounterFile
 									"$c->{DIR}/$c->{name}.autonumber", $start;
 	}
 	my $num;
@@ -151,6 +154,10 @@
 	return $num;
 }
 
+# These don't work in non-DBI databases
+sub commit   { 1 }
+sub rollback { 0 }
+
 sub numeric {
 	return exists $_[0]->[$CONFIG]->{NUMERIC}->{$_[1]};
 }
@@ -241,9 +248,16 @@
     return $r;
 }
 
+sub name {
+	my ($s) = shift;
+	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
+	return $s->[$CONFIG]{name};
+}
+
 sub row_hash {
     my ($s, $key) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
+	return undef unless $s->record_exists($key);
 	my %row;
     @row{ @{$s->[$COLUMN_NAMES]} } = $s->row($key);
 	return \%row;
@@ -252,7 +266,8 @@
 sub unstuff_row {
     my ($s, $key) = @_;
     my $line = $s->[$TIE_HASH]{"k$key"};
-    die "There is no row with index '$key'" unless defined $line;
+    die "There is no row with index '$key' in database $s->[$FILENAME]"
+		unless defined $line;
     return map(unstuff($_), split(/\t/, $line, 9999))
 		unless $s->[$CONFIG]{FILTER_FROM};
 	my @f = map(unstuff($_), split(/\t/, $line, 9999));
@@ -305,6 +320,69 @@
     };
 }
 
+sub get_slice {
+    my ($s, $key, $fary) = @_;
+	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
+
+	return undef unless $s->record_exists($key);
+
+	if(ref $fary ne 'ARRAY') {
+		shift; shift;
+		$fary = [ @_ ];
+	}
+
+	my @result = ($s->row($key))[ map { $s->column_index($_) } @$fary ];
+	return wantarray ? @result : \@result;
+}
+
+sub set_slice {
+    my ($s, $key, $fary, $vary) = @_;
+	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
+
+    if($s->[$CONFIG]{Read_only}) {
+		::logError(
+			"Attempt to set slice of %s in read-only table %s",
+			$key,
+			$s->[$CONFIG]{name},
+		);
+		return undef;
+	}
+
+	if(ref $fary ne 'ARRAY') {
+		my $href = $fary;
+		if(ref $href ne 'HASH') {
+			$href = { $fary, $vary, @_ }
+		}
+		$vary = [ values %$href ];
+		$fary = [ keys   %$href ];
+	}
+
+	my $keyname = $s->[$CONFIG]{KEY};
+
+	my ($found_key) = grep $_ eq $keyname, @$fary;
+
+	if(! $found_key) {
+		unshift @$fary, $keyname;
+		unshift @$vary, $key;
+	}
+
+	my @current;
+
+	@current = $s->row($key)
+		if $s->record_exists($key);
+
+	@current[ map { $s->column_index($_) } @$fary ] = @$vary;
+
+	$key = $s->set_row(@current);
+	length($key) or
+		::logError(
+			"Did set_slice with empty key on table %s",
+			$s->[$CONFIG]{name},
+		);
+
+	return $key;
+}
+
 sub field_settor {
     my ($s, $column) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
@@ -317,11 +395,38 @@
     };
 }
 
+sub clone_row {
+	my ($s, $old, $new) = @_;
+	return undef unless $s->record_exists($old);
+	my @ary = $s->row($old);
+	$ary[$s->[$KEY_INDEX]] = $new;
+	$s->set_row(@ary);
+	return $new;
+}
+
+sub clone_set {
+	my ($s, $col, $old, $new) = @_;
+	return unless $s->column_exists($col);
+	my $sel = $s->quote($old, $col);
+	my $name = $s->[$CONFIG]{name};
+	my ($ary, $nh, $na) = $s->query("select * from $name where $col = $sel");
+	my $fpos = $nh->{$col} || return undef;
+	$s->config('AUTO_NUMBER', '000001') unless $s->config('AUTO_NUMBER');
+	for(@$ary) {
+		my $line = $_;
+		$line->[$s->[$KEY_INDEX]] = '';
+		$line->[$fpos] = $new;
+		$s->set_row(@$line);
+	}
+	return $new;
+}
+
 sub stuff_row {
     my ($s, @fields) = @_;
 	my $key = $fields[$s->[$KEY_INDEX]];
+#::logDebug("stuff key=$key");
 	$fields[$s->[$KEY_INDEX]] = $key = $s->autonumber()
-		if ! $key;
+		if ! length($key);
 	$s->filter(\@fields, $s->[$COLUMN_INDEX], $s->[$CONFIG]{FILTER_TO})
 		if $s->[$CONFIG]{FILTER_TO};
     $s->[$TIE_HASH]{"k$key"} = join("\t", map(stuff($_), @fields));
@@ -333,7 +438,7 @@
 	my $key = $fields[$s->[$KEY_INDEX]];
 #::logDebug("freeze key=$key");
 	$fields[$s->[$KEY_INDEX]] = $key = $s->autonumber()
-		if ! $key;
+		if ! length($key);
 	$s->filter(\@fields, $s->[$COLUMN_INDEX], $s->[$CONFIG]{FILTER_TO})
 		if $s->[$CONFIG]{FILTER_TO};
 	$s->[$TIE_HASH]{"k$key"} = Storable::freeze(\@fields);
@@ -349,6 +454,18 @@
 	*row = \&unstuff_row;
 }
 
+sub foreign {
+    my ($s, $key, $foreign) = @_;
+	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
+	$key = $s->quote($key, $foreign);
+    my $q = "select $s->[$CONFIG]{KEY} from $s->[$CONFIG]{name} where $foreign = $key";
+#::logDebug("foreign key query = $q");
+    my $ary = $s->query({ sql => $q });
+#::logDebug("foreign key query returned" . ::uneval($ary));
+	return undef unless $ary and $ary->[0];
+	return $ary->[0][0];
+}
+
 sub field {
     my ($s, $key, $column) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
@@ -391,6 +508,10 @@
     return $value;
 }
 
+sub create_sql {
+    return undef;
+}
+
 sub touch {
     my ($s) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
@@ -451,19 +572,28 @@
 my $sup;
 my $restrict;
 my $rfield;
+my $hfield;
 my $rsession;
 
 sub each_nokey {
-    my ($s) = @_;
+    my ($s, $qual) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
     my ($key);
 
-	if (
-		! defined $restrict
-		and 
-		$restrict = ($Vend::Cfg->{TableRestrict}{$s->config('name')} || 0)
-		)
-	{
+	if (! defined $restrict) {
+		# Support hide_field
+		if($qual) {
+#::logDebug("Found qual=$qual");
+			$hfield = $qual;
+			if($hfield =~ s/^\s+WHERE\s+(\w+)\s*!=\s*1($|\s+)//) {
+				my $hf = $1;
+#::logDebug("Found hf=$hf");
+				$s->test_column($hf) and $hfield = $s->column_index($hf);
+			}
+#::logDebug("hf index=$hfield");
+		}
+		if($restrict = ($Vend::Cfg->{TableRestrict}{$s->config('name')} || 0)) {
+#::logDebug("restricted?");
 		$sup =  ! defined $Global::SuperUserFunction
 					||
 				$Global::SuperUserFunction->();
@@ -477,6 +607,8 @@
 			$rsession = $Vend::Session->{$rsession};
 		}
 	}
+		$restrict = 1 if $hfield and $s->[$CONFIG]{HIDE_FIELD} eq $hfield;
+	}
 
     for (;;) {
         $key = each %{$s->[$TIE_HASH]};
@@ -488,14 +620,22 @@
 		$key =~ s/^k// or next;
 		if($restrict) {
 			my (@row) = $s->row($key);
-##::logDebug("each_nokey: '$row[$rfield]' eq '$rsession' ??");
-			next if $row[$rfield] ne $rsession;
-			return @row;
+#::logDebug("each_nokey: rfield='$row[$rfield]' eq '$rsession' ??") if defined $rfield;
+#::logDebug("each_nokey: hfield='$row[$hfield]'") if defined $hfield;
+			next if defined $hfield and $row[$hfield];
+			next if defined $rfield and $row[$rfield] ne $rsession;
+			return \@row;
 		}
-		return $s->row($key);
+		return [ $s->row($key) ];
     }
 }
 
+sub suicide { 1 }
+
+sub isopen {
+	return defined $_[0]->[$TIE_HASH];
+}
+
 sub delete_record {
     my ($s, $key) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
@@ -514,11 +654,19 @@
 	return sprintf $query, @$fields;
 }
 
+sub hash_query {
+	my ($s, $query, $opt) = @_;
+	$opt ||= {};
+	$opt->{query} = $query;
+	$opt->{hashref} = 1;
+	return scalar $s->query($opt);
+}
+
 sub query {
     my($s, $opt, $text, @arg) = @_;
 
     if(! CORE::ref($opt)) {
-        unshift @arg, $text;
+        unshift @arg, $text if defined $text;
         $text = $opt;
         $opt = {};
     }
@@ -526,7 +674,7 @@
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
 	$opt->{query} = $opt->{sql} || $text if ! $opt->{query};
 
-#::logDebug("receieved query. object=" . ::uneval($opt));
+#::logDebug("receieved query. object=" . ::uneval_it($opt));
 
 	if(defined $opt->{values}) {
 		# do nothing
@@ -554,6 +702,7 @@
 	my $update;
 	my %nh;
 	my @na;
+	my @update_fields;
 	my @out;
 
 	if($opt->{STATEMENT}) {
@@ -565,8 +714,10 @@
 		eval {
 			($spec, $stmt) = Vend::Scan::sql_statement($query, $ref);
 		};
-		if(! CORE::ref $spec) {
-			::logError("Bad SQL, query was: $query");
+		if($@) {
+			my $msg = ::errmsg("SQL query failed: %s\nquery was: %s", $@, $query);
+			Carp::croak($msg) if $Vend::Try;
+			::logError($msg);
 			return ($opt->{failure} || undef);
 		}
 		my @additions = grep length($_) == 2, keys %$opt;
@@ -578,7 +729,19 @@
 	for (@tabs) {
 		s/\..*//;
 	}
-	if (! defined $s || $tabs[0] ne $s->[$CONFIG]{name}) {
+
+	my $reroute;
+	my $tname = $s->[$CONFIG]{name};
+	if ($tabs[0] ne $tname) {
+		if("$tabs[0]_txt" eq $tname or "$tabs[0]_asc" eq $tname) {
+			$tabs[0] = $spec->{fi}[0] = $tname;
+		}
+		else {
+			$reroute = 1;
+		}
+	}
+
+	if($reroute) {
 		unless ($s = $Vend::Database{$tabs[0]}) {
 			::logError("Table %s not found in databases", $tabs[0]);
 			return $opt->{failure} || undef;
@@ -601,14 +764,37 @@
 	
 	@na = @{$spec->{rf}}     if $spec->{rf};
 
+	$spec->{ml} = $opt->{ml} || '1000';
 	$spec->{fn} = [$s->columns];
-	if(! @na) {
-		@na = ! $update || $update eq 'INSERT' ? '*' : $codename;
+
+	my $sub;
+
+	if($update eq 'INSERT') {
+		@update_fields = $spec->{rf} ? @{$spec->{rf}} : @{$spec->{fn}};
+		@na = $codename;
+		$sub = $s->row_settor(@update_fields);
+	}
+	elsif($update eq 'UPDATE') {
+		@update_fields = @{$spec->{rf}};
+#::logDebug("update fields: " . uneval(\@update_fields));
+		my $key = $s->config('KEY');
+		@na = ($codename);
+		$sub = sub {
+					my $key = shift;
+					$s->set_slice($key, [@update_fields], \@_);
+				};
 	}
-	@na = @{$spec->{fn}}       if $na[0] eq '*';
+	elsif($update eq 'DELETE') {
+		@na = $codename;
+		$sub = sub { delete_record($s, @_) };
+	}
+	else {
+		@na = @{$spec->{fn}}   if ! scalar(@na) || $na[0] eq '*';
+	}
+
 	$spec->{rf} = [@na];
 
-#::logDebug("tabs='@tabs' columns='@na' vals='@vals' update=$update"); 
+#::logDebug("tabs='@tabs' columns='@na' vals='@vals' uf=@update_fields update=$update"); 
 
     my $search;
     if (! defined $opt->{st} or "\L$opt->{st}" eq 'db' ) {
@@ -616,11 +802,11 @@
 			s/\..*//;
 		}
         $search = new Vend::DbSearch;
-#::logDebug("created DbSearch object: " . ::uneval($search));
+#::logDebug("created DbSearch object: " . ::uneval_it($search));
 	}
 	else {
         $search = new Vend::TextSearch;
-#::logDebug("created TextSearch object: " . ::uneval($search));
+#::logDebug("created TextSearch object: " . ::uneval_it($search));
     }
 
 	my %fh;
@@ -629,46 +815,28 @@
 	$i = 0;
 	%fh = map { ($_, $i++) } @{$spec->{fn}};
 
-#::logDebug("field hash: " . Vend::Util::uneval(\%fh)); 
+#::logDebug("field hash: " . Vend::Util::uneval_it(\%fh)); 
 	for ( qw/rf sf/ ) {
 		next unless defined $spec->{$_};
 		map { $_ = $fh{$_} } @{$spec->{$_}};
 	}
 
 	if($update) {
-#::logDebug("Updating, update=$update");
-#		$relocate = $stmt->{MV_VALUE_RELOCATE}
-#			if defined $stmt->{MV_VALUE_RELOCATE};
 		$opt->{row_count} = 1;
 		die "Reached update query without object"
 			if ! $s;
-#		if($relocate) {
-#			my $code = splice(@vals, $stmt->{MV_VALUE_RELOCATE}, 1);
-#			unshift(@vals, $code) if $update ne 'UPDATE';
-##::logDebug("relocating values col=$relocate: columns='@na' vals='@vals'"); 
-#		}
-#		elsif (!defined $relocate) {
-#			die "Must have code field to insert"
-#				 if $update eq 'INSERT';
-#			unshift(@na, $codename);
-##::logDebug("NOT defined relocating values col=$relocate: columns='@na' vals='@vals'"); 
-#		}
-		my $sub = $update eq 'DELETE'
-					? sub { delete_record($s, @_) }
-					: $s->row_settor(@na);
 #::logDebug("Update operation is $update, sub=$sub");
 		die "Bad row settor for columns @na"
 			if ! $sub;
 		if($update eq 'INSERT') {
-			&$sub(@vals);
-			$ref = [$vals[0]];
+			$sub->(@vals);
+			$ref = [[ $vals[0] ]];
 		}
 		else {
-#::logDebug("Supposed to search..., spec=" . ::uneval($spec));
 			$ref = $search->array($spec);
-#::logDebug("Returning ref=" . ::uneval($ref));
-			for(@{$ref}) {
-				&$sub($_->[0], @vals);
+			for(@$ref) {
+#::logDebug("returned =" . uneval($_) . ", update values: " . uneval(\@vals));
+				$sub->($_->[0], @vals);
 			}
 		}
 	}
@@ -691,9 +859,15 @@
 		$return = $opt->{failure} || undef;
 	}
 
-	return scalar @{$ref || []}
-		if $opt->{row_count};
-	return Vend::Interpolate::region($opt, $text)
+	if ($opt->{row_count}) {
+		my $rc = $ref ? scalar @$ref : 0;
+		return $rc unless $opt->{list};
+		$ref = [ [ $rc ] ];
+		@na = [ 'row_count' ];
+		%nh = ( 'rc' => 0, 'count' => 0, 'row_count' => 0 );
+	}
+
+	return Vend::Interpolate::tag_sql_list($text, $ref, \%nh, $opt, \@na)
 		if $opt->{list};
 	return Vend::Interpolate::html_table($opt, $ref, \@na)
 		if $opt->{html};
@@ -740,9 +914,29 @@
 		$format = 'NONE';
 	}
 
-    open(IN, "+<$infile")
-		or die "Couldn't open '$infile' read/write: $!\n";
-	lockfile(\*IN, 1, 1) or die "lock\n";
+	my $realfile;
+	if($options->{PRELOAD}) {
+		if (-f $infile and $options->{PRELOAD_EMPTY_ONLY}) {
+			# Do nothing, no preload
+		}
+		else {
+			$realfile = -f $infile ? $infile : '';
+			$infile = $options->{PRELOAD};
+			$infile = "$Global::VendRoot/$infile" if ! -f $infile;
+			($infile = $realfile, undef $realfile) if ! -f $infile;
+		}
+	}
+
+	if(! defined $realfile) {
+		open(IN, "+<$infile")
+			or die ::errmsg("Couldn't open '%s' read/write: %s", $infile, $!);
+		lockfile(\*IN, 1, 1)
+			or die ::errmsg("lock '%s': %s", $infile, $!);
+	}
+	else {
+		open(IN, "<$infile")
+			or die ::errmsg("Couldn't open '%s' for read: %s", $infile, $!);
+	}
 
 	my $field_hash;
 	my $para_sep;
@@ -875,11 +1069,11 @@
 	my @i;  # Array of field names for sort
 	my @o;  # Array of sort options
 	my %comma;
-	if($options->{INDEX}) {
+	if($options->{INDEX} and ! $options->{NO_ASCII_INDEX}) {
 		my @f; my $f;
 		my @n;
 		my $i;
-		@f = split /[\s,]+/, $options->{INDEX};
+		@f = @{$options->{INDEX}};
 		foreach $f (@f) {
 			my $found = 0;
 			$i = 0;
@@ -1069,7 +1263,33 @@
 );
 
     eval $format{$format};
-    die $@ if $@;
+	die ::errmsg("$options->{name} import failed: %s", $@) if $@;
+    if($realfile) {
+		close IN
+			or die ::errmsg("close preload file %s: %s", $infile, $!) . "\n";
+		if(-f $realfile) {
+			open(IN, "+<$realfile")
+				or die ::errmsg(
+					"Couldn't open user file %s read/write: %s",
+					$realfile,
+					$!) . "\n";
+			lockfile(\*IN, 1, 1) or die "lock\n";
+			<IN>;
+			eval $format{$format};
+			die ::errmsg("%s import failed: %s", $options->{name}, $@) if $@;
+		}
+		elsif (! open(IN, ">$realfile") ) {
+				warn ::errmsg(
+					"can't create %s import failed: %s",
+									$options->{file}, $@
+								);
+		} 
+		else {
+			print IN join($options->{DELIMITER}, @field_names);
+			print IN $/;
+			close IN;
+		}
+	}
 	if(@fh) {
 		my $no_sort;
 		my $sort_sub;
@@ -1105,11 +1325,14 @@
 			File::Copy::copy(@{$_});
 		}
 	}
+	$out->commit() if $out->config('HAS_TRANSACTIONS');
 	delete $out->[$CONFIG]{Clean_start};
+	delete $out->[$CONFIG]{_Dirty};
 	unlockfile(\*IN) or die "unlock\n";
     close(IN);
+	my $dot = $out->[$CONFIG]{HIDE_AUTO_FILES} ? '.' : '';
 	if($numeric_guess) {
-		my $fn = Vend::Util::catfile($out->[$CONFIG]{DIR}, $out->[$CONFIG]{file});
+		my $fn = Vend::Util::catfile($out->[$CONFIG]{DIR}, "$dot$out->[$CONFIG]{file}");
 		Vend::Util::writefile(
 					">$fn.numeric",
 					join " ", map { $field_names[$_] } @possible,
@@ -1118,6 +1341,66 @@
     return $out;
 }
 
+sub import_from_ic_db {
+    my ($infile, $options, $table_name) = @_;
+
+	my $tname = $options->{MIRROR}
+		or die errmsg(
+				"Memory mirror table not specified for table %s.",
+				$table_name,
+			);
+#::logDebug("Importing mirrored $table_name from $tname");
+
+	$Vend::Database{$tname} =
+		Vend::Data::import_database($Vend::Cfg->{Database}{$tname})
+			unless $Vend::Database{$tname};
+
+	my $idb = Vend::Data::database_exists_ref($tname)
+		or die errmsg(
+				"Memory mirror table %s does not exist (yet) to create mirror %s.\n",
+				$tname,
+				$table_name,
+			);
+
+	my @field_names = $idb->columns;
+
+	my $odb;
+
+	if($options->{ObjectType}) {
+		no strict 'refs';
+		$odb = &{"$options->{ObjectType}::create"}(
+									$options->{ObjectType},
+									$options,
+									\@field_names,
+									$table_name,
+								);
+	}
+	else {
+		$odb = $options->{Object};
+	}
+
+#::logDebug("idb=$idb odb=$odb");
+	eval {
+		my $f;
+		while($f = $idb->each_nokey($options->{MIRROR_QUAL})) {
+#::logDebug("importing key=$f->[0]");
+			$odb->set_row(@$f);
+		}
+	};
+
+	if($@) {
+		die ::errmsg(
+				"Problem with mirror import from source %s to target %s\n",
+				$tname,
+				$table_name,
+				);
+	}
+	
+	$odb->[$CONFIG]{Mirror_complete} = 1;
+	delete $odb->[$CONFIG]{Clean_start};
+    return $odb;
+}
+
 my $white = ' \t';
 
 sub read_quoted_fields {
@@ -1165,39 +1448,10 @@
     return @a;
 }
 
-eval join('',<DATA>) || die $@ unless caller();
-1;
-
-__DATA__
-
-my @tests =
-  (
-   '' => [''],
-   ',' => ['', ''],
-   'a' => ['a'],
-   ',a' => ['', 'a'],
-   'a,' => ['a', ''],
-   ',,' => ['', '', ''],
-   ' a , b , c ' => ['a', 'b', 'c'],
-   '""' => [''],
-   '" a , b "' => [' a , b '],
-   "1,\t2, 3 " => ['1', '2', '3'],
-   ' a b c , d e f ' => ['a b c', 'd e f'],
-   ' " a"",b ",c' => [' a",b ', 'c'],
-   );
-
-my $errors = 0;
-my ($in, $out, @a, @b);
-while (($in, $out) = splice(@tests, 0, 2)) {
-    @a = @$out;
-    @b = parse($in);
-    if (@a != @b or grep($_ ne shift @a, @b)) {
-        print "'$in' parsed as ",
-              join(' ',map("<$_>",@b)),
-              " instead of the expected ",
-              join(' ',map("<$_>",@$out)), "\n";
-        ++$errors;
-    }
+sub reset {
+	undef $restrict;
 }
-print "All tests successful\n" unless $errors;
+
 1;
+
+__END__



1.19.4.10 +1292 -239 interchange/lib/Vend/Table/DBI.pm


rev 1.19.4.10, prev_rev 1.19.4.9
Index: DBI.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/DBI.pm,v
retrieving revision 1.19.4.9
retrieving revision 1.19.4.10
diff -u -r1.19.4.9 -r1.19.4.10
--- DBI.pm	2 Nov 2001 08:32:15 -0000	1.19.4.9
+++ DBI.pm	25 Jan 2003 22:21:31 -0000	1.19.4.10
@@ -1,8 +1,8 @@
-# Table/DBI.pm: access a table stored in an DBI/DBD Database
+# Vend::Table::DBI - Access a table stored in an DBI/DBD database
 #
-# $Id: DBI.pm,v 1.19.4.9 2001/11/02 08:32:15 racke Exp $
+# $Id: DBI.pm,v 1.19.4.10 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -20,7 +20,7 @@
 # MA  02111-1307  USA.
 
 package Vend::Table::DBI;
-$VERSION = substr(q$Revision: 1.19.4.9 $, 10);
+$VERSION = substr(q$Revision: 1.19.4.10 $, 10);
 
 use strict;
 
@@ -41,9 +41,9 @@
 			$DBI
 			$EACH
 			$TIE_HASH
-			$Set_handle
             %DBI_connect_cache
             %DBI_connect_count
+            %DBI_connect_bad
 		 /;
 
 ($CONFIG, $TABLE, $KEY, $NAME, $TYPE, $DBI, $EACH) = (0 .. 6);
@@ -51,9 +51,11 @@
 $TIE_HASH = $DBI;
 
 my %Cattr = ( qw(
+					RAISEERROR     	RaiseError
 					PRINTERROR     	PrintError
 					AUTOCOMMIT     	AutoCommit
 				) );
+my @Cattr = keys %Cattr;
 
 my %Dattr = ( qw(
 					WARN			Warn
@@ -66,6 +68,7 @@
 					LONGTRUNCOK    	LongTruncOk
 					LONGREADLEN    	LongReadLen
 				) );
+my @Dattr = keys %Dattr;
 
 sub find_dsn {
 	my ($config) = @_;
@@ -75,18 +78,29 @@
 	foreach $param (qw! DSN USER PASS !) {
 		$out[$i++] = $config->{ $param } || undef;
 	}
-	foreach $param (keys %$config) {
-		if(defined $Dattr{$param}) {
-			$dattr = { AutoCommit => 1, PrintError => 1 }
-				unless defined $dattr;
-			$dattr->{$Dattr{$param}} = $config->{$param};
-		}
-		next unless defined $Cattr{$param};
-		$cattr = {} unless defined $cattr;
-		$cattr->{$Cattr{$param}} = $config->{$param};
+
+	if ($config->{Transactions} and $config->{HAS_TRANSACTIONS}) {
+#::logDebug("table $config->{name} should be opened in transaction mode");
+		$config->{AUTOCOMMIT} = 0;
+		undef $config->{dsn_id};
+	}
+
+	my @other = grep defined $config->{$_}, @Dattr;
+	
+	if(@other) {
+		$dattr = { };
+		$cattr = { };
+		for(@other) {
+			$dattr->{$Dattr{$_}} = $config->{$_};
+			$cattr->{$Cattr{$_}} = $config->{$_}
+				if defined $Cattr{$_};
+		}
 	}
+	
 	$out[3] = $cattr || undef;
 	$out[4] = $dattr || undef;
+#::logDebug("out# = " . scalar(@out));
+#::logDebug("$config->{name} find_dsn dump= " . ::uneval(\@out));
 	@out;
 }
 
@@ -106,11 +120,183 @@
 	return $db;
 }
 
-my $Info;
+my %known_capability = (
+	AUTO_INDEX_PRIMARY_KEY => {
+		Oracle	=> 1,
+	},
+	HAS_TRANSACTIONS => {
+		Sybase	=> 1,
+		DB2		=> 1,
+		Pg		=> 1,
+		Oracle	=> 1,
+	},
+	HAS_DESCRIBE => {
+		mysql	=> 1,
+		Pg		=> 0,
+		Oracle	=> 0,
+	},
+	DESCRIBE_TABLE => {
+		mysql	=> sub {
+			my $s = shift;
+			my $q = "show create table $s->[$TABLE]";
+#::logDebug("describe query: $q");
+			my $sth = $s->[$DBI]->prepare($q);
+			$sth->execute();
+			my $out = '';
+			my $ary;
+			while($ary = $sth->fetchrow_arrayref()) {
+				$out .= $ary->[1];
+				$out .= "\n";
+			}
+#::logDebug("describe query returns: $out");
+			return $out;
+		},
+		Pg		=> 0,
+		Oracle	=> 0,
+	},
+	HAS_LIMIT => {
+		mysql	=> 1,
+		Pg		=> 1,
+	},
+	ALTER_DELETE => { 
+		mysql => 'ALTER TABLE _TABLE_ DROP _COLUMN_',
+	},
+	ALTER_CHANGE => { 
+		mysql => 'ALTER TABLE _TABLE_ CHANGE COLUMN _COLUMN_ _COLUMN_ _DEF_',
+		Pg => 'ALTER TABLE _TABLE_ CHANGE COLUMN _COLUMN_ _COLUMN_ _DEF_',
+	},
+	ALTER_ADD	 => { 
+		mysql => 'ALTER TABLE _TABLE_ ADD COLUMN _COLUMN_ _DEF_',
+		Pg => 'ALTER TABLE _TABLE_ ADD COLUMN _COLUMN_ _DEF_',
+	},
+	ALTER_INDEX	 => { 
+		mysql => 'CREATE _UNIQUE_ INDEX $TABLE$_$COLUMN$ ON _TABLE_ (_COLUMN_)',
+		Pg => 'CREATE _UNIQUE_ INDEX $TABLE$_$COLUMN$ ON _TABLE_ (_COLUMN_)',
+		default => 'CREATE _UNIQUE_ INDEX $TABLE$_$COLUMN$ ON _TABLE_ (_COLUMN_)',
+	},
+	SEQUENCE_CREATE	 => { 
+		Oracle => "CREATE SEQUENCE _SEQUENCE_NAME_",
+		Pg => "CREATE SEQUENCE _SEQUENCE_NAME_",
+	},
+	SEQUENCE_QUERY	 => { 
+		Oracle => "SELECT _SEQUENCE_NAME_.nextval FROM dual",
+		Pg => "SELECT nextval('_SEQUENCE_NAME_')",
+	},
+	SEQUENCE_VAL	 => { 
+		mysql => undef,
+	},
+	SEQUENCE_KEY	 => { 
+		mysql	=> 'INT PRIMARY KEY AUTO_INCREMENT',
+		Pg	=> 'INT NOT NULL PRIMARY KEY',
+		Oracle	=> 'INT NOT NULL PRIMARY KEY',
+	},
+	SEQUENCE_VALUE_FUNCTION	 => { 
+		Pg => "SELECT currval('_SEQUENCE_NAME_')",
+		Oracle => "SELECT _SEQUENCE_NAME_.currval FROM dual",
+	},
+	SEQUENCE_LAST_FUNCTION	 => { 
+		mysql => 'select last_insert_id()',
+		## These use explicit
+		Pg => undef,
+		Oracle => undef,
+	},
+	UPPER_COMPARE	 => { 
+		Oracle => 1,
+		Pg	   => 1,
+	},
+	MAX_FIELD_LENGTH  => {
+	    Pg    => "SELECT a.attnum,t.typname,a.attlen,a.atttypmod,a.attname FROM pg_class c,pg_attribute a,pg_type t WHERE c.relname='_TABLE_' AND a.attnum > 0 AND a.attrelid = c.oid AND a.atttypid = t.oid ORDER BY a.attnum;",
+        },
+);
+
+sub check_capability {
+	my ($config, $driver_name) = @_;
+	return if $config->{_Checked_capability}++;
+
+	$driver_name = $config->{BASE_CAPABILITY}
+		if $config->{BASE_CAPABILITY};
+
+	if($driver_name =~ /^dbi:+(.*?):/) {
+		$driver_name = $1;
+	}
+
+	my ($k, $known);
+	while ( ($k, $known) = each %known_capability ) {
+		if(! defined $config->{$k} ) {
+#::logDebug("checking $driver_name cap $k: $known->{$driver_name}");
+			$config->{$k} = $known->{$driver_name}
+				if defined $known->{$driver_name};
+		}
+	}
+}
+
+sub create_sql {
+	my ($s, $tablename, $config, $columns) = @_;
+
+#::logDebug("create_sql called, tablename=$tablename config=$config columns=$columns");
+	if($s) {
+		$config = $s->[$CONFIG];
+		my @col = $s->columns();
+		$columns = \@col;
+	}
+	elsif(! $config) {
+		return undef;
+	}
+
+	if($s and $config->{HAS_DESCRIBE}) {
+#::logDebug("attempting DESCRIBE_TABLE=$config->{DESCRIBE_TABLE}");
+		return $config->{DESCRIBE_TABLE}->($s);
+	}
+	my $key = $config->{KEY} || $columns->[0];
+
+	my @cols;
+	my $keycol;
+
+	my $def_type = $config->{DEFAULT_TYPE} || 'char(128)';
+#::logDebug("columns coming in: @{$columns}");
+    for (my $i = 0;  $i < @$columns;  $i++) {
+        $cols[$i] = $$columns[$i];
+#::logDebug("checking column '$cols[$i]'");
+		if(defined $key) {
+			$keycol = $i if $cols[$i] eq $key;
+		}
+		if(defined $config->{COLUMN_DEF}->{$cols[$i]}) {
+			$cols[$i] .= " " . $config->{COLUMN_DEF}->{$cols[$i]};
+		}
+		else {
+			$cols[$i] .= " $def_type";
+		}
+		$$columns[$i] = $cols[$i];
+		$$columns[$i] =~ s/\s+.*//;
+    }
+
+	$keycol = 0 unless defined $keycol;
+	$config->{KEY_INDEX} ||= $keycol;
+	$config->{KEY} ||= $key;
+
+	if ( not defined $config->{COLUMN_DEF}->{$key} ) {
+		if($config->{AUTO_SEQUENCE} and $config->{SEQUENCE_KEY}) {
+			$cols[$keycol] =~ s/\s+.*/ $config->{SEQUENCE_KEY}/;
+		}
+		else {
+			$cols[$keycol] =~ s/\s+.*/ char(16) NOT NULL/;
+		}
+	}
+
+	my $query = "create table $tablename ( \n";
+	$query .= join ",\n", @cols;
+	$query .= "\n)\n";
+	return $query;
+}
 
 sub create {
     my ($class, $config, $columns, $tablename) = @_;
 #::logDebug("trying create table $tablename");
+
+	local($config->{Transactions});
+	check_capability($config, $config->{DSN});
+	$config->{Transactions} = 1 if $config->{HAS_TRANSACTIONS};
+
 	my @call = find_dsn($config);
 	my $dattr = pop @call;
 
@@ -133,15 +319,20 @@
 		die "connect failed (create) -- $msg\n";
 	}
 
+	# Allow multiple tables in different DBs to have same local name
+	$tablename = $config->{REAL_NAME}
+		if $config->{REAL_NAME};
+	
+	# Used so you can do query() and nothing else
 	if($config->{HANDLE_ONLY}) {
 		return bless [$config, $tablename, undef, undef, undef, $db], $class;
 	}
 
+	check_capability($config, $db->{Driver}{Name});
+
     die "columns argument $columns is not an array ref\n"
         unless CORE::ref($columns) eq 'ARRAY';
 
-	my $oracle = 1 if $db->{Driver}->{Name} =~ /Oracle/;
-
 	if(defined $dattr) {
 		for(keys %$dattr) {
 			$db->{$_} = $dattr->{$_};
@@ -152,64 +343,104 @@
 	my(@cols);
 
 	$key = $config->{KEY} || $columns->[0];
-
-	my $def_type = $config->{DEFAULT_TYPE} || 'char(128)';
-#::logDebug("columns coming in: @{$columns}");
-    for ($i = 0;  $i < @$columns;  $i++) {
-        $cols[$i] = $$columns[$i];
-#::logDebug("checking column '$cols[$i]'");
-		if(defined $key) {
-			$keycol = $i if $cols[$i] eq $key;
-		}
-		if(defined $config->{COLUMN_DEF}->{$cols[$i]}) {
-			$cols[$i] .= " " . $config->{COLUMN_DEF}->{$cols[$i]};
-		}
-		else {
-			$cols[$i] .= " $def_type";
-		}
-		$$columns[$i] = $cols[$i];
-		$$columns[$i] =~ s/\s+.*//;
-    }
-
 	$keycol = 0 unless defined $keycol;
 	$config->{KEY_INDEX} = $keycol;
 	$config->{KEY} = $key;
 
-	$cols[$keycol] =~ s/\s+.*/ char(16) NOT NULL/
-			unless defined $config->{COLUMN_DEF}->{$key};
-
-	my $query = "create table $tablename ( \n";
-	$query .= join ",\n", @cols;
-	$query .= "\n)\n";
+	if(ref $config->{PRECREATE}) {
+		for(@{$config->{PRECREATE}} ) {
+			$db->do($_) 
+				or ::logError(
+								"DBI: Prior creation query '%s' failed: %s" ,
+								$_,
+								$DBI::errstr,
+					);
+		}
+	}
 
-	# test creation of table
-	TESTIT: {
-		my $q = $query;
+	if($config->{CREATE_SQL}) {
+#::logDebug("Trying to create with specified CREATE_SQL:\n$config->{CREATE_SQL}");
 		eval {
-			$db->do("drop table ic_test_create")
+			$db->do($config->{CREATE_SQL});
+			$db->commit() if $config->{Transactions};
 		};
-		$q =~ s/create\s+table\s+\S+/create table ic_test_create/;
-		if(! $db->do($q) ) {
-			::logError(
-						"bad table creation statement:\n%s\n\nError: %s",
-						$query,
-						$DBI::errstr,
+		if($@) {
+			 die ::errmsg(
+				"DBI: Create table '%s' failed, explicit CREATE_SQL. Error: %s\n",
+				$tablename,
+				$DBI::errstr,
 			);
-			warn "$DBI::errstr\n";
-			return undef;
 		}
-		$db->do("drop table ic_test_create")
 	}
+	else {
+		# test creation of table
+		my $query = create_sql(undef, $tablename, $config, $columns);
+
+		eval {
+			$db->do("drop table $tablename")
+				and $config->{Clean_start} = 1
+				or warn "$DBI::errstr\n";
+			$db->commit() if $config->{Transactions};
+		};
 
-	eval {
-		$db->do("drop table $tablename")
-			and $config->{Clean_start} = 1
-			or warn "$DBI::errstr\n";
-	};
 #::logDebug("Trying to create with:$query");
-	$db->do($query)
-		or warn "DBI: Create table '$tablename' failed: $DBI::errstr\n";
-	::logError("table %s created: %s" , $tablename, $query );
+		eval {
+			$db->do($query);
+			$db->commit() if $config->{Transactions};
+		};
+		if($@) {
+			warn "DBI: Create table '$tablename' failed: $DBI::errstr\n";
+		}
+		else {
+			::logError("table %s created: %s" , $tablename, $query );
+		}
+	}
+
+#::logDebug("seq: $config->{AUTO_SEQUENCE} create: $config->{SEQUENCE_CREATE}");
+	if($config->{AUTO_SEQUENCE} and my $q = $config->{SEQUENCE_CREATE}) {
+		if($config->{AUTO_SEQUENCE_DROP}) {
+			my $dq = $config->{SEQUENCE_DROP} || 'DROP SEQUENCE _SEQUENCE_NAME_';
+			$dq =~ s/_SEQUENCE_NAME_/$config->{AUTO_SEQUENCE}/g;
+#::logDebug("dropping sequence with query: $dq");
+			eval {
+				$db->do($dq)
+					or warn("drop sequence failed: $dq");
+				$db->commit() if $config->{Transactions};
+			};
+		}
+		$q =~ s/_SEQUENCE_NAME_/$config->{AUTO_SEQUENCE}/g;
+		$q =~ s/_SEQUENCE_START_/$config->{AUTO_SEQUENCE_START} || 1/eg;
+		$q =~ s/_SEQUENCE_CACHE_/$config->{AUTO_SEQUENCE_CACHE} || 1/eg;
+		$q =~ s/_SEQUENCE_MINVAL_/$config->{AUTO_SEQUENCE_MINVAL} || 1/eg;
+		$q =~ s/_SEQUENCE_MAXVAL_/$config->{AUTO_SEQUENCE_MAXVAL} || 2147483647/eg;
+#::logDebug("create query: $q");
+		eval {
+			$db->do($q)
+				or warn("create sequence failed: $q");
+			$db->commit() if $config->{Transactions};
+		};
+	}
+
+	my @index;
+	if(ref $config->{INDEX}) {
+		for my $def (@{$config->{INDEX}}) {
+			my $uniq = '';
+			$uniq = 'UNIQUE' if $def =~ s/^\s*unique\s+//i;
+			$def =~ s/:\w+//g;
+			my $col = $def;
+			$col =~ s/\W.*//s;
+			my $template = $config->{ALTER_INDEX}
+						|| $known_capability{ALTER_INDEX}{default};
+			$template =~ s/\b_TABLE_\b/$tablename/g;
+			$template =~ s/\b_COLUMN_\b/$col/g;
+			$template =~ s/\b_DEF_\b/$def/g;
+			$template =~ s/\$TABLE\$/$tablename/g;
+			$template =~ s/\$DEF\$/$def/g;
+			$template =~ s/\$COLUMN\$/$col/g;
+			$template =~ s/\b_UNIQUE_(\w+_)?/$uniq ? ($1 || $uniq) : ''/eg;
+			push @index, $template;
+		}
+	}
 
 	if(ref $config->{POSTCREATE}) {
 		for(@{$config->{POSTCREATE}} ) {
@@ -219,17 +450,50 @@
 								$_,
 								$DBI::errstr,
 					);
+			$db->commit() if $config->{Transactions};
 		}
-	} elsif ($oracle and ($config->{COLUMN_DEF}->{$key} =~ /PRIMARY\s+KEY/i)) {
+	} elsif ($config->{AUTO_INDEX_PRIMARY_KEY}) {
 		# Oracle automatically creates indexes on primary keys,
 		# so we don't need to do it again
 	} else {
 		$db->do("create index ${tablename}_${key} on $tablename ($key)")
 			or ::logError("table %s index failed: %s" , $tablename, $DBI::errstr);
+		$db->commit() if $config->{Transactions};
 	}
 
-	if($config->{GUESS_NUMERIC}) {
-		list_fields($db, $tablename, $config);
+	for(@index) {
+#::logDebug("Running: $_");
+		$db->do($_) 
+			or ::logError(
+							"DBI: Post creation query '%s' failed: %s" ,
+							$_,
+							$DBI::errstr,
+				);
+		$db->commit() if $config->{Transactions};
+	}
+
+	if(! defined $config->{EXTENDED}) {
+		## side-effects here -- sets $config->{NUMERIC},
+		## $config->{_Numeric_ary}, reads GUESS_NUMERIC
+
+		$config->{_Auto_number} = $config->{AUTO_SEQUENCE} || $config->{AUTO_NUMBER};
+		
+		if(! $config->{NAME}) {
+			$config->{NAME} = list_fields($db, $tablename, $config);
+		}
+		else {
+			list_fields($db, $tablename, $config);
+		}
+
+		## side-effects here -- sets $config->{_Default_ary} if needed
+		$config->{COLUMN_INDEX} = fields_index($config->{NAME}, $config, $db)
+			if ! $config->{COLUMN_INDEX};
+
+		$config->{EXTENDED} =	defined($config->{FIELD_ALIAS}) 
+							||	defined $config->{FILTER_FROM}
+							||	defined $config->{FILTER_TO}
+							||	$config->{UPPERCASE}
+							||	'';
 	}
 
 	$config->{NAME} = $columns;
@@ -246,42 +510,104 @@
 sub open_table {
     my ($class, $config, $tablename) = @_;
 	
-    my @call = find_dsn($config);
-    my $dattr = pop @call;
+	my $dot = $config->{HIDE_AUTO_FILES} ? '.' : '';
+
+	$config->{PRINTERROR} = 0 if ! defined $config->{PRINTERROR};
+	$config->{RAISEERROR} = 1 if ! defined $config->{RAISEERROR};
+    my @call;
+    my $dattr;
     my $db;
+  DOCONNECT: {
+    @call = find_dsn($config);
+    $dattr = pop @call;
+
+    if (! $config->{AUTO_SEQUENCE} and ! defined $config->{AutoNumberCounter}) {
+	    eval {
+			$config->{AutoNumberCounter} = new Vend::CounterFile
+									"$config->{DIR}/$dot$config->{name}.autonumber",
+									$config->{AUTO_NUMBER} || '00001';
+		};
+		if($@) {
+			::logError("Cannot create AutoNumberCounter: %s", $@);
+			$config->{AutoNumberCounter} = '';
+		}
+    }
 
-	unless($config->{dsn_id}) {
+	unless ($config->{dsn_id}) {
 		$config->{dsn_id} = join "_", grep ! ref($_), @call;
-    	if($Global::HotDBI->{$Vend::Cfg->{CatalogName}}) {
-			$config->{hot_dbi} = 1;
-			$DBI_connect_count{$config->{dsn_id}}++;
+		$config->{dsn_id} .= "_transact" if $config->{Transactions};
+	}
+
+	$db = $DBI_connect_cache{ $config->{dsn_id} };
+	if($db and ! defined $DBI_connect_bad{$config->{dsn_id}} ) {
+		my $status;
+		eval {
+			$status = $db->ping();
+		};
+#::logDebug("checking connection on $config->{dsn_id} status=$status");
+		if(! $status) {
+			undef $db;
+			$DBI_connect_bad{ $config->{dsn_id} } = 1;
+			undef $DBI_connect_cache{ $config->{dsn_id} };
+		}
+		else {
+			$DBI_connect_bad{ $config->{dsn_id} } = 0;
 		}
 	}
-#::logDebug("db_file: $config->{db_file}");
-#::logDebug("db_file_extended: $config->{db_file_extended}");
-	unless ($db = $DBI_connect_cache{ $config->{dsn_id} }) {
+
+	my $bad =  $DBI_connect_bad{$config->{dsn_id}};
+	my $alt_index = 0;
+
+	if (! $db or $bad ) {
+#::logDebug("bad=$bad connecting to $call[0]");
 		eval {
-			$db = DBI->connect( @call );
+			$db = DBI->connect( @call ) unless $bad;
+			$db->trace($Global::DataTrace, $Global::DebugFile)
+				if $Global::DataTrace and $Global::DebugFile;
 		};
+#::logDebug("$config->{name}: DBI didn't die, bad=$bad");
 		if(! $db) {
-			my $msg = $@ || $DBI::errstr;
-			if(! $msg) {
-				my($dname);
-				(undef, $dname) = split /:+/, $config->{DSN};
-				eval {
-					DBI->install_driver($dname);
-				};
-				$msg = $@ || $DBI::errstr || "unknown error. Driver '$dname' installed?";
+			$DBI_connect_bad{$config->{dsn_id}} = 1;
+			if($config->{ALTERNATE_DSN}[$alt_index]) {
+				for(qw/DSN USER PASS/) {
+					$config->{$_} = $config->{"ALTERNATE_$_"}[$alt_index];
+				}
+				$alt_index++;
+				undef $config->{dsn_id};
+				redo DOCONNECT;
+			}
+			else {
+				my $msg = $@ || $DBI::errstr;
+				if(! $msg) {
+					my($dname);
+					(undef, $dname) = split /:+/, $config->{DSN};
+					eval {
+						DBI->install_driver($dname);
+					};
+					$msg = $@ || $DBI::errstr || "unknown error. Driver '$dname' installed?";
+				}
+				die "connect failed -- $msg\n";
 			}
-			die "connect failed -- $msg\n";
 		}
+		$DBI_connect_bad{$config->{dsn_id}} = 0;
 		$DBI_connect_cache{$config->{dsn_id}} = $db;
-#::logDebug("connected to $config->{dsn_id}");
+#::logDebug("$config->{name} connected to $config->{dsn_id}");
 	}
+	else {
+#::logDebug("$config->{name} using cached connection $config->{dsn_id}");
+	}
+  }
 
-#	if(! $Info and ($Info = $db->table_info()) ) {
-#::logDebug("$tablename table_info: " . ::uneval($Info->fetchall_arrayref()));
-#	}
+	# Allow multiple tables in different DBs to have same local name
+	$tablename = $config->{REAL_NAME}
+		if $config->{REAL_NAME};
+
+	# Used so you can do query() and nothing else
+	if($config->{HANDLE_ONLY}) {
+		return bless [$config, $tablename, undef, undef, undef, $db], $class;
+	}
+
+	check_capability($config, $db->{Driver}{Name});
 
     unless ($config->{hot_dbi}) {
 		$DBI_connect_count{$config->{dsn_id}}++;
@@ -303,10 +629,22 @@
 	}
 
 	if(! defined $config->{EXTENDED}) {
-		$config->{NAME} = list_fields($db, $tablename, $config)
-			if ! $config->{NAME};
-		$config->{COLUMN_INDEX} = fields_index($config->{NAME}, $config)
+		## side-effects here -- sets $config->{NUMERIC},
+		## $config->{_Numeric_ary}, reads GUESS_NUMERIC
+
+		$config->{_Auto_number} = $config->{AUTO_SEQUENCE} || $config->{AUTO_NUMBER};
+
+		if(! $config->{NAME}) {
+			$config->{NAME} = list_fields($db, $tablename, $config);
+		}
+		else {
+			list_fields($db, $tablename, $config);
+		}
+
+		## side-effects here -- sets $config->{_Default_ary} if needed
+		$config->{COLUMN_INDEX} = fields_index($config->{NAME}, $config, $db)
 			if ! $config->{COLUMN_INDEX};
+
 		$config->{EXTENDED} =	defined($config->{FIELD_ALIAS}) 
 							||	defined $config->{FILTER_FROM}
 							||	defined $config->{FILTER_TO}
@@ -314,14 +652,10 @@
 							||	'';
 	}
 
-	if($config->{GUESS_NUMERIC} and ! $config->{NUMERIC}) {
-		list_fields($db, $tablename, $config);
-	}
 
-	$config->{NUMERIC} = {} unless $config->{NUMERIC};
 
 	die "DBI: no column names returned for $tablename\n"
-			unless defined $config->{NAME}[1];
+			unless defined $config->{NAME}[0];
 
 	# Check if we have a non-first-column key
 	if($config->{KEY}) {
@@ -333,33 +667,95 @@
 	$config->{KEY_INDEX} = $config->{COLUMN_INDEX}{lc $key}
 		if ! $config->{KEY_INDEX};
 	die ::errmsg("Bad key specification: %s"  .
-					::uneval($config->{NAME}) .
-					::uneval($config->{COLUMN_INDEX}),
+					Vend::Util::uneval_it($config->{NAME}) .
+					Vend::Util::uneval_it($config->{COLUMN_INDEX}),
 					$key
 		)
 		if ! defined $config->{KEY_INDEX};
 
+    if ( $config->{MAX_FIELD_LENGTH}
+			and
+		  $config->{LENGTH_EXCEPTION_DEFAULT}
+			and 
+		  ! $config->{FIELD_LENGTH_DATA}
+		)
+			{
+		my $ssql = $config->{MAX_FIELD_LENGTH};
+		$ssql =~ s/_TABLE_/$tablename/g;
+		my $osth = $db->prepare($ssql);
+		$osth->execute;
+	
+		$config->{FIELD_LENGTH_DATA} = {};
+
+		while (my @ores = $osth->fetchrow_array) {
+			my $stype   = $ores[1];
+			my $slen    = $ores[2];
+			my $slenvar = $ores[3];
+			my $scfg = $config->{FIELD_LENGTH_DATA}{$ores[4]} = {};
+	    
+			$scfg->{TYPE} = $stype;
+
+			if( $stype=~/numeric/i  or $stype=~/varbit/i ){  
+				$scfg->{LENGTH} = $slenvar;
+			}
+			else {
+				if ($slen > 0) {
+					$scfg->{LENGTH} = $slen;
+				}
+				elsif ($slenvar>0) {
+					$scfg->{LENGTH} = ($slenvar-4);
+				}
+				else {
+					$scfg->{LENGTH} = 'var';
+				}
+			}
+	    }
+
+		$osth->finish;
+    }
+
     my $s = [$config, $tablename, $key, $config->{NAME}, $config->{EXTENDED}, $db];
 	bless $s, $class;
 }
 
+sub suicide {
+	my $s = shift;
+	undef $s->[$DBI];
+}
+
 sub close_table {
 	my $s = shift;
 	return 1 if ! defined $s->[$DBI];
-	undef $s->[$CONFIG]{_Insert_h};
-	undef $s->[$CONFIG]{Update_handle};
-    undef $s->[$CONFIG]{Exists_handle};
-    return 1 if $s->[$CONFIG]{hot_dbi};
-#::logDebug("connect count close: " . ($DBI_connect_count{$s->[$CONFIG]->{dsn_id}} - 1));
-	return 1 if --$DBI_connect_count{$s->[$CONFIG]->{dsn_id}} > 0;
-	undef $DBI_connect_cache{$s->[$CONFIG]->{dsn_id}};
+	my $cfg = $s->[$CONFIG];
+	undef $DBI_connect_bad{$cfg->{dsn_id}};
+	undef $cfg->{_Insert_h};
+	undef $cfg->{Update_handle};
+    undef $cfg->{Exists_handle};
+    undef $s->[$EACH];
+#::logDebug("connect count close: " . ($DBI_connect_count{$cfg->{dsn_id}} - 1));
+	return 1 if --$DBI_connect_count{$cfg->{dsn_id}} > 0;
+	return 1 if $Global::HotDBI->{$Vend::Cat};
+	undef $DBI_connect_cache{$cfg->{dsn_id}};
 	$s->[$DBI]->disconnect();
 }
 
+sub dbh {
+	my ($s) = shift;
+	$s = $s->import_db() if ! defined $s->[$DBI];
+	return $s->[$DBI];
+}
+
+sub name {
+	my ($s) = shift;
+	$s = $s->import_db() if ! defined $s->[$DBI];
+	return $s->[$CONFIG]{REAL_NAME} || $s->[$CONFIG]{name};
+}
+
 sub columns {
 	my ($s) = shift;
 	$s = $s->import_db() if ! defined $s->[$DBI];
-    return @{$s->[$NAME]};
+	return unless ref $s->[$NAME] eq 'ARRAY';
+	return @{$s->[$NAME]};
 }
 
 sub test_column {
@@ -371,9 +767,12 @@
 sub quote {
 	my($s, $value, $field) = @_;
 	$s = $s->import_db() if ! defined $s->[$DBI];
+	return $s->[$DBI]->quote($value) unless $field;
+	return 'NULL'	if ! length($value)
+					and exists $s->[$CONFIG]->{PREFER_NULL}{$field};
 	return $s->[$DBI]->quote($value)
-		unless $field and $s->numeric($field);
-	return 0 unless $value =~ /\d/;
+					unless exists $s->[$CONFIG]->{NUMERIC}{$field};
+	$value = 0 if ! length($value);
 	return $value;
 }
 
@@ -410,6 +809,59 @@
     $value;
 }
 
+sub commit {
+    my ($s) = @_;
+#::logDebug("committing $s->[$TABLE], dsn_id=$s->[$CONFIG]{dsn_id}");
+
+	# This is pretty harmless, no?
+	return undef if ! defined $s->[$DBI];
+	unless ($s->[$CONFIG]{HAS_TRANSACTIONS}) {
+		::logError(
+			"commit attempted on non-transaction database, returning success"
+		);
+		return 1;
+	}
+
+#	if (! defined $s->[$DBI]) {
+#		::logError(
+#			"commit attempted on non-open database handle for table: %s",
+#			$s->[$TABLE],
+#			);
+#		return undef;
+#	}
+
+	my $status;
+	eval {
+		$status = $s->[$DBI]->commit();
+	};
+	if($@) {
+		::logError("%s commit failed: %s", $s->[$TABLE], $@);
+	}
+	return $status;
+}
+
+sub rollback {
+    my ($s) = @_;
+
+#::logDebug("rolling back $s->[$TABLE], dsn_id=$s->[$CONFIG]{dsn_id}");
+	# This is pretty harmless, no?
+	return undef if ! defined $s->[$DBI];
+
+#	if (! defined $s->[$DBI]) {
+#		::logError(
+#			"rollback attempted on non-open database handle for table: %s",
+#			$s->[$TABLE],
+#		);
+#		return undef;
+#	}
+
+	return $s->[$DBI]->rollback();
+}
+
+sub isopen {
+	return defined $_[0]->[$DBI];
+}
+
 sub column_index {
     my ($s, $column) = @_;
 	$s = $s->import_db() if ! defined $s->[$DBI];
@@ -440,82 +892,528 @@
 }
 
 sub bind_entire_row {
-	my($s, $sth, $key, @fields) = @_;
+	my($s, $sth, @fields) = @_;
 #::logDebug("bind_entire_row=" . ::uneval(\@_));
+#::logDebug("bind_entire_row=" . ::uneval(\@fields));
 	my $i;
-	my $numeric = $s->[$CONFIG]->{NUMERIC};
+	my $numeric = $s->[$CONFIG]->{_Numeric_ary}
+		or die ::errmsg("improperly set up database, no numeric array.");
 	my $name = $s->[$NAME];
 	my $j = 1;
+
+	my $ki;
+
 	for($i = 0; $i < scalar @$name; $i++, $j++) {
 #::logDebug("bind $j=$fields[$i]");
 		$sth->bind_param(
 			$j,
 			$fields[$i],
-			(! exists $numeric->{$name->[$i]} ? undef : DBI::SQL_INTEGER),
+			$numeric->[$i],
 			);
 	}
-	$sth->bind_param(
-			$j,
-			$key,
-			(! exists $numeric->{$name->[$i]} ? undef : DBI::SQL_INTEGER),
-			)
-		if $key;
+#::logDebug("last bind $j=$fields[$i]");
 	return;
 }
 
+sub autosequence {
+	my $s = shift;
+
+	my $cfg = $s->[$CONFIG];
+	# Like MySQL, get sequence number *after* insert
+	return $cfg->{SEQUENCE_VAL} if $cfg->{SEQUENCE_LAST_FUNCTION};
+
+	# Like Oracle or Pg, get it now then return passed value later
+	my $q = $cfg->{SEQUENCE_QUERY} || "select nextval('_SEQUENCE_NAME_')";
+	$q =~ s/_SEQUENCE_NAME_/$cfg->{AUTO_SEQUENCE}/g;
+	my $sth = $s->[$DBI]->prepare($q)
+		or die ::errmsg('prepare %s: %s', $q, $DBI::errstr);
+	$sth->execute()
+		or die ::errmsg('execute %s: %s', $q, $DBI::errstr);
+	my $k = $sth->fetchrow_arrayref->[0];
+	return $k;
+}
+
+sub add_column {
+	my ($s, $column, $def) = @_;
+	return $s->alter_column($column, $def, 'ALTER_ADD');
+}
+
+sub rename_table {
+	my ($s, $column, $def) = @_;
+	return $s->alter_column($column, $def, 'ALTER_RENAME');
+}
+
+sub copy_table {
+	my ($s, $column, $def) = @_;
+	return $s->alter_column($column, $def, 'ALTER_COPY');
+}
+
+sub change_column {
+	my ($s, $column, $def) = @_;
+	return $s->alter_column($column, $def, 'ALTER_CHANGE');
+}
+
+sub delete_column {
+	my ($s, $column, $def) = @_;
+	return $s->alter_column($column, $def, 'ALTER_DELETE');
+}
+
+sub index_column {
+	my ($s, $column, $def) = @_;
+	return $s->alter_column($column, $def, 'ALTER_INDEX');
+}
+
+sub alter_column {
+	my ($s, $column, $def, $function) = @_;
+	$s = $s->import_db() if ! defined $s->[$DBI];
+	$function = 'ALTER_CHANGE' unless $function;
+	my $template = $s->config($function);
+	if(! $template) {
+		::logError(
+			$s->config(
+				'last_error',
+				::errmsg(
+					"No %s template defined for table %s. Skipping.",
+					$function,
+					$s->[$TABLE],
+				),
+			),
+		);
+		return undef;
+	}
+
+	if($function =~ /^(ALTER_CHANGE)$/ and ! $s->column_exists($column) ) {
+		::logError(
+			$s->config(
+				'last_error',
+				::errmsg(
+					"Column '%s' doesn't exist in table %s. Skipping.",
+					$column,
+					$s->[$TABLE],
+				),
+			),
+		);
+		return undef;
+	}
+
+	$template =~ s/\b_BACKUP_\b/"bak_$s->[$TABLE]"/g;
+	$template =~ s/\b_TABLE_\b/$s->[$TABLE]/g;
+	$template =~ s/\b_COLUMN_\b/$column/g;
+	$template =~ s/\b_DEF_\b/$def/g;
+	$template =~ s/\$BACKUP\$/"bak_$s->[$TABLE]"/g;
+	$template =~ s/\$TABLE\$/$s->[$TABLE]/g;
+	$template =~ s/\$COLUMN\$/$column/g;
+	$template =~ s/\$DEF\$/$def/g;
+
+	my $rc;
+	eval {
+		$rc = $s->[$DBI]->do($template);
+	};
+
+	if($@) {
+		::logError(
+			$s->config(
+				'last_error',
+				::errmsg(
+					"'%s' failed. Error: %s",
+					$template,
+				),
+			),
+		);
+		return undef;
+	}
+
+	return $rc;
+}
+
+sub clone_row {
+	my ($s, $old, $new, $change) = @_;
+#::logDebug("called clone_row old=$old new=$new change=$change");
+	$s = $s->ref();
+	return undef unless $s->record_exists($old);
+	my @ary = $s->row($old);
+#::logDebug("called clone_row ary=" . join "|", @ary);
+	if($change and ref $change) {
+		for (keys %$change) {
+			my $pos = $s->column_index($_) 
+				or next;
+			$ary[$pos] = $change->{$_};
+		}
+	}
+	$ary[$s->[$CONFIG]{KEY_INDEX}] = $new;
+#::logDebug("called clone_row now=" . join "|", @ary);
+	my $k = $s->set_row(@ary);
+#::logDebug("cloned, key=$k");
+	return $k;
+}
+
+sub clone_set {
+	my ($s, $col, $old, $new) = @_;
+#::logDebug("called clone_set col=$col old=$old new=$new");
+	return unless $s->column_exists($col);
+	my $sel = $s->quote($old, $col);
+	my $name = $s->[$CONFIG]{name};
+	my ($ary, $nh, $na) = $s->query("select * from $name where $col = $sel");
+	my $fpos = $nh->{$col} || return undef;
+	$s->config('AUTO_NUMBER', '000001') unless $s->config('AUTO_NUMBER');
+	for(@$ary) {
+		my $line = $_;
+		$line->[$s->[$CONFIG]{KEY_INDEX}] = '';
+		$line->[$fpos] = $new;
+		my $k = $s->set_row(@$line);
+#::logDebug("cloned, key=$k");
+	}
+	return $new;
+}
+
+sub length_exception {
+	my ($s, $fname, $data) = @_;
+
+	my $fcfg = $s->[$CONFIG]{FIELD_LENGTH_DATA}{$fname}
+		or return $data;
+	my $action = $s->[$CONFIG]{LENGTH_EXCEPTION}{$fname}
+			   || $s->[$CONFIG]{LENGTH_EXCEPTION_DEFAULT};
+
+	my $slen = $fcfg->{LENGTH};
+
+	my $errout;
+	if( $action =~ /^truncate(?:_(\w+))$/i) {
+		my $errout = lc $1;
+		$data = substr($data,0,$slen);			      
+	}
+	elsif ($action =~ /^filter/i){
+		my $faction = $action;
+		$faction =~ s/^filter\s+//i;
+		my @filters = Text::ParseWords::shellwords($faction);
+		for my $filt (@filters) {
+			if ($filt eq 'truncate') {
+				$data = substr($data,0,$slen);
+			}
+			else {
+				$data = Vend::Interpolate::filter_value($filt, $data);
+			}
+		}    
+	}
+
+	if($errout) {
+		my $caller = caller();
+		my $msg1 = errmsg(
+				"%s - Length Exception! - Data length: %s Field length: %s",
+				$caller,
+				length($data),
+				$slen,
+			);
+		my $msg2 = errmsg(
+				"%s - Length Exception - Table: %s, Field: %s. Action to take: %s",
+				$caller,
+				$s->[$TABLE],
+				$action,
+			);
+		if($errout eq 'debug') {
+			::logDebug($msg1);
+			::logDebug($msg2);
+		}
+		elsif($errout eq 'log') {
+			::logError($msg1);
+			::logError($msg2);
+		}
+	}
+	return $data;
+}
+
+sub get_slice {
+    my ($s, $key, $fary) = @_;
+	$s = $s->import_db() if ! defined $s->[$DBI];
+
+	my $tkey;
+	my $sql;
+	return undef unless $s->record_exists($key);
+
+	$tkey = $s->quote($key, $s->[$KEY]);
+#::logDebug("tkey now $tkey");
+
+	# Better than failing on a bad ref...
+	if(ref $fary ne 'ARRAY') {
+		shift; shift;
+		$fary = [ @_ ];
+	}
+
+	my $fstring = join ",", @$fary;
+	$sql = "SELECT $fstring from $s->[$TABLE] WHERE $s->[$KEY] = $tkey";
+
+#::logDebug("get_slice query: $sql");
+#::logDebug("get_slice key/fields:\nkey=$key\n" . ::uneval($fary));
+	my $sth;
+	my $ary;
+	eval {
+		$sth = $s->[$DBI]->prepare($sql)
+			or die ::errmsg("prepare %s: %s", $sql, $DBI::errstr);
+		$sth->execute();
+	};
+
+	if($@) {
+		my $msg = $@;
+		::logError("failed %s::%s routine: %s", __PACKAGE__, 'get_slice', $msg);
+		return undef;
+	}
+
+	return wantarray ? $sth->fetchrow_array() : $sth->fetchrow_arrayref();
+}
+
+sub set_slice {
+    my ($s, $key, $fary, $vary) = @_;
+	$s = $s->import_db() if ! defined $s->[$DBI];
+
+    if($s->[$CONFIG]{Read_only}) {
+		::logError(
+			"Attempt to set slice of %s in read-only table %s",
+			$key,
+			$s->[$CONFIG]{name},
+		);
+		return undef;
+	}
+
+	my $tkey;
+	my $sql;
+
+	if(ref $fary ne 'ARRAY') {
+		my $href = $fary;
+		if(ref $href ne 'HASH') {
+			$href = { $fary, $vary, @_ }
+		}
+		$vary = [ values %$href ];
+		$fary = [ keys   %$href ];
+	}
+
+	if ($s->[$CONFIG]->{PREFER_NULL}) {
+		my $prefer_null = $s->[$CONFIG]->{PREFER_NULL};
+		my $i = 0;
+		for (@$fary) {
+			undef $vary->[$i]
+				if exists $prefer_null->{$_} and $vary->[$i] eq '';
+			++$i;
+		}
+	}
+
+    if($s->[$CONFIG]->{LENGTH_EXCEPTION_DEFAULT}) {
+
+		my $lcfg   = $s->[$CONFIG]{FIELD_LENGTH_DATA}
+			or die "No field length data!";
+		my $ecfg   = $s->[$CONFIG]{LENGTH_EXCEPTION} || {};
+		my $edefault = $s->[$CONFIG]{LENGTH_EXCEPTION_DEFAULT};
+
+		for (my $i=0; $i < @$fary; $i++){
+			next unless defined $lcfg->{$fary->[$i]};
+
+			$vary->[$i] = $s->length_exception($fary->[$i], $vary->[$i])
+				if length($vary->[$i]) > $lcfg->{$fary->[$i]}{LENGTH};
+
+		}
+    }
+
+	$tkey = $s->quote($key, $s->[$KEY]) if defined $key;
+#::logDebug("tkey now $tkey");
+
+
+	if ( defined $tkey and $s->record_exists($key) ) {
+		my $fstring = join ",", map { "$_=?" } @$fary;
+		$sql = "update $s->[$TABLE] SET $fstring WHERE $s->[$KEY] = $tkey";
+	}
+	else {
+		my $found;
+		if(! length($key)) {
+			$key = $s->autonumber();
+		}
+		for(my $i = 0; $i < @$fary; $i++) {
+			next unless $fary->[$i] eq $s->[$KEY];
+			splice @$fary, $i, 1;
+			splice @$vary, $i, 1;
+			last;
+		}
+			unshift @$fary, $s->[$KEY];
+			unshift @$vary, $key;
+		my $fstring = join ",", @$fary;
+		my $vstring = join ",", map {"?"} @$vary;
+		$sql = "insert into $s->[$TABLE] ($fstring) VALUES ($vstring)";
+	}
+
+#::logDebug("set_slice query: $sql");
+#::logDebug("set_slice key/fields/values:\nkey=$key\n" . ::uneval($fary, $vary));
+
+	my $val;
+	eval {
+		my $sth = $s->[$DBI]->prepare($sql)
+			or die ::errmsg("prepare %s: %s", $sql, $DBI::errstr);
+		my $rc = $sth->execute(@$vary)
+			or die ::errmsg("execute %s: %s", $sql, $DBI::errstr);
+
+		$val	= $s->[$CONFIG]->{AUTO_SEQUENCE}
+				? $s->last_sequence_value($key)
+				: $key;
+	};
+
+	if($@) {
+		my $caller = caller();
+		::logGlobal(
+			"%s error as called by %s: %s\nquery was:%s\nvalues were:'%s'",
+			'select_slice',
+			$caller,
+			$@,
+			$sql,
+			join("','", @$vary),
+			);
+		return undef;
+	}
+
+	return $val;
+}
+
 sub set_row {
     my ($s, @fields) = @_;
 	$s = $s->import_db() if ! defined $s->[$DBI];
 	my $cfg = $s->[$CONFIG];
+	my $ki = $cfg->{KEY_INDEX};
+
 	$s->filter(\@fields, $s->[$CONFIG]{COLUMN_INDEX}, $s->[$CONFIG]{FILTER_TO})
-		if $s->[$CONFIG]{FILTER_TO};
+		if $cfg->{FILTER_TO};
+
+	if ($cfg->{PREFER_NULL}) {
+		for (keys %{$cfg->{PREFER_NULL}}) {
+			my $i = $cfg->{COLUMN_INDEX}{$_};
+			undef $fields[$i] if $fields[$i] eq '';
+		}
+	}
+
 	my $val;
+
 	if(scalar @fields == 1) {
-		if(! $fields[0] and $s->[$CONFIG]{AUTO_NUMBER}) {
-			$fields[0] = $s->autonumber();
+		 return if $cfg->{AUTO_SEQUENCE};
+		 $fields[0] = $s->autonumber()
+			if ! length($fields[0]);
+		$val = $s->quote($fields[0], $s->[$KEY]);
+		my $key_string;
+		my $val_string;
+		my $ary;
+		my @flds = $s->[$KEY];
+		my @vals = $val;
+		if($cfg->{_Default_ary} || $cfg->{_Default_session_ary}) {
+			my $ary = $cfg->{_Default_ary} || [];
+			my $sary = $cfg->{_Default_session_ary} || [];
+			my $max = $#$ary > $#$sary ? $#$ary : $#$sary;
+			for (my $i = 0; $i <= $max; $i++) {
+				if($sary->[$i]) {
+					push @flds, $s->[$NAME][$i];
+					push @vals, $sary->[$i]->($s);
+					next;
+				}
+				next unless defined $ary->[$i];
+				push @flds, $s->[$NAME][$i];
+				push @vals, $ary->[$i];
+			}
+			$key_string = join ",", @flds;
+			$val_string = join ",", @vals;
+		}
+		else {
+			$key_string = $s->[$KEY];
+			$val_string = $val;
 		}
+#::logDebug("def_ary query will be: insert into $s->[$TABLE] ($key_string) VALUES ($val_string)");
 		eval {
-			$val = $s->quote($fields[0], $s->[$KEY]);
-			if($s->[$CONFIG]{AUTO_NUMBER}) {
-				my $ctr
-			}
-			$s->[$DBI]->do("delete from $s->[$TABLE] where $s->[$KEY] = $val");
-			$s->[$DBI]->do("insert into $s->[$TABLE] ($s->[$KEY]) VALUES ($val)");
+			$s->[$DBI]->do("delete from $s->[$TABLE] where $s->[$KEY] = $val")
+				if $s->record_exists();
+			$s->[$DBI]->do("insert into $s->[$TABLE] ($key_string) VALUES ($val_string)");
 		};
 		die "$DBI::errstr\n" if $@;
-		return $val;
+		return $fields[0];
+	}
+
+	if(! length($fields[$ki]) ) {
+		$fields[$ki] = $s->autonumber();
+	}
+	elsif (	! $s->[$CONFIG]{Clean_start}
+			and defined $fields[$ki]
+			and $s->record_exists($fields[$ki])
+		)
+	{
+		eval {
+			$val = $s->quote($fields[$ki], $s->[$KEY]);
+			$s->[$DBI]->do("delete from $s->[$TABLE] where $s->[$KEY] = $val");
+		};
 	}
+
+#::logDebug("set_row fields='" . join(',', @fields) . "'" );
 	if(! $cfg->{_Insert_h}) {
 		my (@ins_mark);
 		my $i = 0;
 		for(@{$s->[$NAME]}) {
 			push @ins_mark, '?';
-			$cfg->{_Key_column} = $i if $s->[$KEY] eq $_;
 			$i++;
 		}
-		die "set_row init for $s->[$TABLE]: No key column found."
-			unless defined $cfg->{_Key_column};
+		my $fstring = '';
+
 		my $ins_string = join ", ",  @ins_mark;
-		my $query = "INSERT INTO $s->[$TABLE] VALUES ($ins_string)";
+		my $query = "INSERT INTO $s->[$TABLE]$fstring VALUES ($ins_string)";
 #::logDebug("set_row query=$query");
 		$cfg->{_Insert_h} = $s->[$DBI]->prepare($query);
 		die "$DBI::errstr\n" if ! defined $cfg->{_Insert_h};
 	}
 
-	unless ($s->[$CONFIG]{Clean_start}) {
-		eval {
-			$val = $s->quote($fields[$cfg->{_Key_column}], $s->[$KEY]);
-			$s->[$DBI]->do("delete from $s->[$TABLE] where $s->[$KEY] = $val")
-				unless $s->[$CONFIG]{Clean_start};
-		};
-	}
-    $s->bind_entire_row($cfg->{_Insert_h}, undef, @fields);
-	$val = $fields[$cfg->{_Key_column}];
-	$cfg->{_Insert_h}->execute()
+#::logDebug("set_row fields='" . join(',', @fields) . "'" );
+    $s->bind_entire_row($cfg->{_Insert_h}, @fields);
+
+	my $rc = $cfg->{_Insert_h}->execute()
 		or die "$DBI::errstr\n";
+
+	$val	= $cfg->{AUTO_SEQUENCE}
+			?  $s->last_sequence_value($fields[$ki])
+			: $fields[$ki];
+
+#::logDebug("set_row rc=$rc key=$val");
 	return $val;
 }
 
+sub last_sequence_value {
+	my $s = shift;
+	my $passed = shift;
+	my $cfg = $s->[$CONFIG];
+	my $q = $cfg->{SEQUENCE_LAST_FUNCTION};
+
+	if (! $q) {
+		return $passed if $passed;
+		$q = $cfg->{SEQUENCE_VALUE_FUNCTION};
+	}
+
+	$q =~ s/_SEQUENCE_NAME_/$s->[$CONFIG]{AUTO_SEQUENCE}/g;
+	$q =~ s/_TABLE_/$s->[$TABLE]/g;
+	$q =~ s/_COLUMN_/$s->[$KEY]/g;
+	my $sth = $s->[$DBI]->prepare($q)
+		or die ::errmsg("prepare %s: %s", $q, $DBI::errstr);
+	my $rc = $sth->execute()
+		or die ::errmsg("execute %s: %s", $q, $DBI::errstr);
+	my $aref = $sth->fetchrow_arrayref();
+
+	if (! $aref) {
+		die ::errmsg("missing return value from %s: %s", $q, $sth->err());
+	}
+	elsif ($aref->[0] !~ /^\d+$/) {
+		die ::errmsg("bogus return value from %s: %s", $q, $aref->[0]);
+	}
+	return $aref->[0];
+}
+
+sub row {
+    my ($s, $key) = @_;
+	$s = $s->import_db() if ! defined $s->[$DBI];
+	$key = $s->[$DBI]->quote($key)
+		unless exists $s->[$CONFIG]{NUMERIC}{$s->[$KEY]};
+    my $sth = $s->[$DBI]->prepare(
+		"select * from $s->[$TABLE] where $s->[$KEY] = $key");
+    $sth->execute()
+		or die("execute error: $DBI::errstr");
+
+	return @{$sth->fetchrow_arrayref()};
+}
+
 sub row_hash {
     my ($s, $key) = @_;
 	$s = $s->import_db() if ! defined $s->[$DBI];
@@ -612,16 +1510,37 @@
 sub field_settor {
     my ($s, $column) = @_;
 	$s = $s->import_db() if ! defined $s->[$DBI];
+	my $q = "update $s->[$TABLE] SET $column = ? where $s->[$KEY] = ?";
+	my $sth = $s->[$DBI]->prepare($q)
+		or Carp::croak errmsg("Unable to prepare query for field_settor: %s", $q);
     return sub {
         my ($key, $value) = @_;
-		$value = $s->[$DBI]->quote($value)
-			unless exists $s->[$CONFIG]->{NUMERIC}->{$column};
-		$key = $s->[$DBI]->quote($key)
-			unless exists $s->[$CONFIG]{NUMERIC}{$s->[$KEY]};
-        $s->[$DBI]->do("update $s->[$TABLE] SET $column=$value where $s->[$KEY] = $key");
+        $sth->execute($value, $key);
     };
 }
 
+sub foreign {
+    my ($s, $key, $foreign) = @_;
+	$s = $s->import_db() if ! defined $s->[$DBI];
+	my $idx;
+	if( $s->[$TYPE] and $idx = $s->column_index($foreign) )  {
+		$foreign = $s->[$NAME][$idx];
+	}
+	$key = $s->[$DBI]->quote($key)
+		unless exists $s->[$CONFIG]{NUMERIC}{$foreign};
+	my $query = "select $s->[$KEY] from $s->[$TABLE] where $foreign = $key";
+#::logDebug("DBI field: key=$key query=$query");
+    my $sth;
+	eval {
+		$sth = $s->[$DBI]->prepare($query);
+		$sth->execute();
+	};
+	return '' if $@;
+	my $data = ($sth->fetchrow_array())[0];
+	return '' unless $data =~ /\S/;
+	return $data;
+}
+
 sub field {
     my ($s, $key, $column) = @_;
 	$s = $s->import_db() if ! defined $s->[$DBI];
@@ -653,15 +1572,33 @@
 					);
 		return undef;
 	}
+
+	$key = $s->autonumber()  if ! length($key);
+
+	undef $value if $value eq '' and exists $s->[$CONFIG]{PREFER_NULL}{$column};
+
 	my $rawkey = $key;
 	my $rawval = $value;
+
 	$key   = $s->quote($key, $s->[$KEY]);
 	$value = $s->quote($value, $column);
+
 	my $query;
 	if(! $s->record_exists($rawkey)) {
-		$s->set_row($rawkey);
+		if( $s->[$CONFIG]{AUTO_SEQUENCE} ) {
+			$key = 0 if ! $key;
+			$query = qq{
+				INSERT INTO $s->[$TABLE]
+				($s->[$KEY], $column)
+				VALUES ($key, $value)
+				};
+		}
+		else {
+#::logDebug("creating key '$rawkey' in table $s->[$TABLE]");
+			$s->set_row($rawkey);
+		}
 	}
-	$query = <<EOF;
+	$query = <<EOF unless $query;
 update $s->[$TABLE] SET $column = $value where $s->[$KEY] = $key
 EOF
 	$s->[$DBI]->do($query)
@@ -682,6 +1619,10 @@
     my ($s, $key) = @_;
     $s = $s->import_db() if ! defined $s->[$DBI];
     my $query;
+
+	# Does any SQL allow empty key?
+	return '' if ! length($key) and ! $s->[$CONFIG]{ALLOW_EMPTY_KEY};
+
     $query = $s->[$CONFIG]{Exists_handle}
         or
 	    $query = $s->[$DBI]->prepare(
@@ -714,15 +1655,57 @@
 }
 
 sub fields_index {
-	my($fields, $config) = @_;
+	my($fields, $config, $dbh) = @_;
 	my %idx;
 	my $alias = $config->{FIELD_ALIAS} || {};
-	for( my $i = 0; $i < @$fields; $i++) {
+	my $fc = scalar @$fields;
+	for( my $i = 0; $i < $fc; $i++) {
 		$idx{lc $fields->[$i]} = $i;
 		next unless defined $alias->{lc $fields->[$i]};
 #::logDebug("alias found: $fields->[$i] = $alias->{lc $fields->[$i]} = $i");
 		$idx{ $alias->{ lc $fields->[$i] } } = $i;
 	}
+	if($config->{DEFAULT}) {
+		my $def = $config->{DEFAULT};
+		my $def_ary = [];
+		for(keys %$def) {
+			my $k = lc $_;
+#::logDebug("DBI default: checking $k=$_, idx=$idx{$k}");
+			$def_ary->[$idx{$k}] =	exists($config->{NUMERIC}{$k})
+									? $def->{$_}
+									: $dbh->quote($def->{$_});
+#::logDebug("DBI default: checking $k=$def_ary->[$idx[$k]]");
+		}
+		$config->{_Default_ary} = $def_ary;
+	}
+	if($config->{DEFAULT_SESSION}) {
+		my $def_session = $config->{DEFAULT_SESSION};
+		my $def_session_ary = [];
+		for(keys %$def_session) {
+			my $k = lc $_;
+			my $v = $def_session->{$_};
+			my $text_default;
+			$v =~ /\s*\|+\s*(.*)/
+				and $text_default = $1;
+#::logDebug("DBI session default: checking $k=$_, idx=$idx{$k}");
+			my $n = exists($config->{NUMERIC}{$k});
+			
+			my $sub = sub {
+				my $self = shift;
+				for(\%CGI::values, $::Values) {
+					next unless defined $_->{$v};
+					return $_->{$v} if $n;
+					return $self->quote($_->{$v});
+				}
+				return length($text_default) ? $text_default : 0
+					if $n;
+				return $self->quote($text_default);
+			};
+			$def_session_ary->[$idx{$k}] = $sub;
+#::logDebug("DBI  sessiondefault: checking $k=$def_session_ary->[$idx{$k}]");
+		}
+		$config->{_Default_session_ary} = $def_session_ary;
+	}
 	return \%idx;
 }
 
@@ -745,8 +1728,8 @@
 		die "Couldn't determine field names for $name: $DBI::errstr";
 	}
 	@fld = @{$sth->{NAME}};
+	$config->{NUMERIC} = {} if ! $config->{NUMERIC};
 	if($config->{GUESS_NUMERIC}) {
-		$config->{NUMERIC} = {} if ! $config->{NUMERIC};
 		eval {
 			for (my $i = 0; $i < @fld; $i++) {
 				my $info =
@@ -758,16 +1741,14 @@
 			}
 		};
 	}
+	my @num = map { exists $config->{NUMERIC}{$_} ? DBI::SQL_INTEGER : undef } @fld;
+	$config->{_Numeric_ary} = \@num;
 	if($config->{UPPERCASE}) {
 		@fld = map { lc $_ } @fld;
 	}
 	return \@fld;
 }
 
-# OLDSQL
-
-# END OLDSQL
-
 sub touch {
 	return ''
 }
@@ -784,14 +1765,13 @@
 
 # Now supported, including qualification
 sub each_record {
-    my ($s, $qual) = @_;
-#::logDebug("each_record qual=$qual");
-	$qual = '' if ! $qual;
-	$qual .= $s->[$CONFIG]{Export_order} 
-		if $s->[$CONFIG]{Export_order};
+    my $s = shift;
 	$s = $s->import_db() if ! defined $s->[$DBI];
     my ($table, $db, $each);
     unless(defined $s->[$EACH]) {
+		my $qual = shift || '';
+		$qual .= $s->[$CONFIG]{Export_order} 
+			if $s->[$CONFIG]{Export_order};
 		($table, $db, $each) = @{$s}[$TABLE,$DBI,$EACH];
 		my $query = $db->prepare("select * from $table $qual")
             or die $DBI::errstr;
@@ -815,14 +1795,13 @@
 
 # Now supported, including qualification
 sub each_nokey {
-    my ($s, $qual) = @_;
-#::logDebug("each_nokey qual=$qual");
-	$qual = '' if ! $qual;
-	$qual .= $s->[$CONFIG]{Export_order} 
-		if $s->[$CONFIG]{Export_order};
+    my $s = shift;
 	$s = $s->import_db() if ! defined $s->[$DBI];
     my ($table, $db, $each);
     unless(defined $s->[$EACH]) {
+		my $qual = shift || '';
+		$qual .= $s->[$CONFIG]{Export_order} 
+			if $s->[$CONFIG]{Export_order};
 		($table, $db, $each) = @{$s}[$TABLE,$DBI,$EACH];
 		my $restrict;
 		if($restrict = $Vend::Cfg->{TableRestrict}{$table}
@@ -834,7 +1813,6 @@
 			) {
 			$qual = $qual ? "$qual AND " : 'WHERE ';
 			my ($rfield, $rsession) = split /\s*=\s*/, $restrict;
-#::logDebug("qual=$qual");
 			$qual .= "$rfield = '$Vend::Session->{$rsession}'";
 		}
 		my $query = $db->prepare("select * from $table " . ($qual || '') )
@@ -844,17 +1822,17 @@
 		$each = sub {
 			my $ref = $query->fetchrow_arrayref()
 				or return undef;
-			return ($ref);
+			return $ref;
 		};
         push @$s, $each;
     }
-	my ($return) = $s->[$EACH]->();
+	my $return = $s->[$EACH]->();
 	if(! defined $return->[0]) {
 		pop @$s;
 		delete $s->[$CONFIG]{Export_order};
 		return ();
 	}
-    return (@$return);
+    return $return;
 }
 
 sub sprintf_substitute {
@@ -870,6 +1848,14 @@
 	return sprintf $query, @$fields;
 }
 
+sub hash_query {
+	my ($s, $query, $opt) = @_;
+	$opt ||= {};
+	$opt->{query} = $query;
+	$opt->{hashref} = 1;
+	return scalar $s->query($opt);
+}
+
 sub query {
     my($s, $opt, $text, @arg) = @_;
 
@@ -882,9 +1868,12 @@
 	$s = $s->import_db() if ! defined $s->[$DBI];
 	$opt->{query} = $opt->{sql} || $text if ! $opt->{query};
 
+	if($opt->{type}) {
+		$opt->{$opt->{type}} = 1 unless defined $opt->{$opt->{type}};
+	}
+
 #::logDebug("\$db->query=$opt->{query}");
 	if(defined $opt->{values}) {
-		# do nothing
 		@arg = $opt->{values} =~ /['"]/
 				? ( Text::ParseWords::shellwords($opt->{values})  )
 				: (grep /\S/, split /\s+/, $opt->{values});
@@ -899,7 +1888,6 @@
 	my $codename = $s->[$CONFIG]{KEY};
 	my $ref;
 	my $relocate;
-	my $return;
 	my $spec;
 	my $stmt;
 	my $sth;
@@ -910,66 +1898,76 @@
 	my @out;
 	my $db = $s->[$DBI];
 
-    if ( 0 and "\L$opt->{st}" eq 'db') {
-		eval {
-			($spec, $stmt) = Vend::Scan::sql_statement($query, $ref);
-		};
-		if(! CORE::ref $spec) {
-			::logError("Bad SQL, query was: %s", $query);
-			return ($opt->{failure} || undef);
-		}
-		my @additions = grep length($_) == 2, keys %$opt;
-		if(@additions) {
-			@{$spec}{@additions} = @{$opt}{@additions};
-		}
-	}
-	else {
-		$update = 1 if $query !~ /^\s*select\s+/i;
+	$update = 1 if $query !~ /^\s*select\s+/i;
 
-		eval {
-			if($update and $s->[$CONFIG]{Read_only}) {
-				my $msg = errmsg(
-							"Attempt to do update on read-only table.\nquery: %s",
-							$query,
-						  );
-				::logError($msg);
-				die "$msg\n";
-			}
-			$opt->{row_count} = 1 if $update;
-			$sth = $db->prepare($query);
-			$rc = $sth->execute();
-			
-			if ($opt->{hashref}) {
-				my @ary;
-				while ( defined (my $rowhashref = $sth->fetchrow_hashref) ) {
-					if ($s->config('UPPERCASE')) {
-						$rowhashref->{lc $_} = $rowhashref->{$_} for (keys %$rowhashref);
-					}
-					push @ary, $rowhashref;
+	eval {
+		if($update and $s->[$CONFIG]{Read_only}) {
+			my $msg = ::errmsg(
+						"Attempt to do update on read-only table.\nquery: %s",
+						$query,
+					  );
+			::logError($msg);
+			die "$msg\n";
+		}
+		$opt->{row_count} = 1 if $update;
+		$sth = $db->prepare($query) or die $DBI::errstr;
+#::logDebug("Query prepared OK. sth=$sth");
+		$rc = $sth->execute() or die $DBI::errstr;
+#::logDebug("Query executed OK. rc=" . (defined $rc ? $rc : 'undef'));
+		
+		if ($update) {
+			$ref = $Vend::Interpolate::Tmp->{$opt->{hashref} ?
+				$opt->{hashref} : $opt->{arrayref}} = [];
+		}
+		elsif ($opt->{hashref}) {
+			my @ary;
+			while ( defined (my $rowhashref = $sth->fetchrow_hashref) ) {
+				if ($s->config('UPPERCASE')) {
+					$rowhashref->{lc $_} = $rowhashref->{$_} for (keys %$rowhashref);
 				}
-				die $DBI::errstr if $sth->err();
-				$ref = $Vend::Interpolate::Tmp->{$opt->{hashref}} = \@ary;
+				push @ary, $rowhashref;
 			}
-			else {
-				my $i = 0;
-				@na = @{$sth->{NAME} || []};
-				%nh = map { (lc $_, $i++) } @na;
-				$ref = $Vend::Interpolate::Tmp->{$opt->{arrayref}}
-					= $sth->fetchall_arrayref()
-					 or die $DBI::errstr;
-			}
-		};
-		if($@) {
-			if(! $sth) {
-				# query failed, probably because no table
-				# Do nothing but log to debug and fall through to MVSEARCH
-				::logDebug(qq{query "$query" failed: $@});
-			}
-			else {
-				::logError("SQL query failed: %s\nquery was: %s", $@, $query);
-				$return = $opt->{failure} || undef;
+			die $DBI::errstr if $sth->err();
+			$ref = $Vend::Interpolate::Tmp->{$opt->{hashref}} = \@ary;
+		}
+		else {
+			my $i = 0;
+			@na = @{$sth->{NAME} || []};
+			%nh = map { (lc $_, $i++) } @na;
+			$ref = $Vend::Interpolate::Tmp->{$opt->{arrayref}}
+				= $sth->fetchall_arrayref()
+				 or die $DBI::errstr;
+		}
+	};
+	if($@) {
+		if(! $sth or ! defined $rc) {
+			# query failed, probably because no table
+			# Do nothing but log to debug and fall through to MVSEARCH
+			eval {
+				($spec, $stmt) = Vend::Scan::sql_statement($query, $ref);
+				my @additions = grep length($_) == 2, keys %$opt;
+				if(@additions) {
+					@{$spec}{@additions} = @{$opt}{@additions};
+				}
+			};
+			if($@) {
+				my $msg = ::errmsg(
+						qq{Query rerouted from table %s failed: %s\nQuery was: %s},
+						$s->[$TABLE],
+						$@,
+						$query,
+					);
+				Carp::croak($msg) if $Vend::Try;
+				::logError($msg);
+				return undef;
 			}
 		}
+		else {
+			my $msg = ::errmsg("SQL query failed: %s\nquery was: %s", $@, $query);
+			Carp::croak($msg) if $Vend::Try;
+			::logError($msg);
+			return undef;
+		}
 	}
 
 MVSEARCH: {
@@ -1027,14 +2025,11 @@
 		map { $_ = $fh{$_} } @{$spec->{$_}};
 	}
 
-	if($update) {
-		die "DBI tables must be updated natively.\n";
-	}
-	elsif ($opt->{hashref}) {
-		$ref = $Vend::Interplate::Tmp->{$opt->{hashref}} = $search->hash($spec);
+	if ($opt->{hashref}) {
+		$ref = $Vend::Interpolate::Tmp->{$opt->{hashref}} = $search->hash($spec);
 	}
 	else {
-		$ref = $Vend::Interplate::Tmp->{$opt->{arrayref}} = $search->array($spec);
+		$ref = $Vend::Interpolate::Tmp->{$opt->{arrayref}} = $search->array($spec);
 	}
 };
 #::logDebug("search spec: " . Vend::Util::uneval($spec));
@@ -1042,18 +2037,29 @@
 #::logDebug("ref returned: " . Vend::Util::uneval($ref));
 #::logDebug("opt is: " . Vend::Util::uneval($opt));
 	if($@) {
-		::logError("MVSQL query failed for %s: %s\nquery was: %s",
-					$opt->{table},
+		::logError("SQL query failed for %s: %s\nQuery was: %s",
+					$s->[$TABLE],
 					$@,
 					$query,
 					);
-		$return = $opt->{failure} || undef;
+		return undef;
 	}
 } # MVSEARCH
 #::logDebug("finished query, rc=$rc ref=$ref arrayref=$opt->{arrayref} Tmp=$Vend::Interpolate::Tmp->{$opt->{arrayref}}");
-	return $rc
-		if $opt->{row_count};
-	return Vend::Interpolate::tag_sql_list($text, $ref, \%nh, $opt)
+
+	if ($rc < 1 and CORE::ref($ref) and scalar(@$ref) ) {
+		$rc = scalar(@$ref);
+	}
+	# force to numeric, to handle DBI "0E0"-type results
+	$::Values->{mv_search_match_count} = $rc + 0;
+	if ($opt->{row_count}) {
+		return $rc unless $opt->{list};
+		$ref = [ [ $rc ] ];
+		@na = [ 'row_count' ];
+		%nh = ( 'rc' => 0, 'count' => 0, 'row_count' => 0 );
+	}
+
+	return Vend::Interpolate::tag_sql_list($text, $ref, \%nh, $opt, \@na)
 		if $opt->{list};
 	return Vend::Interpolate::html_table($opt, $ref, \@na)
 		if $opt->{html};
@@ -1061,6 +2067,53 @@
 		if $opt->{textref};
 	return wantarray ? ($ref, \%nh, \@na) : $ref;
 }
+
+sub auto_config {
+	my $string = shift;
+	my ($dsn, $user, $pass) = Text::ParseWords::shellwords($string);
+	my $handle = DBI->connect($dsn, $user, $pass)
+		or ::logDebug(::errmsg("DatabaseAuto DSN '%s' does not connect.", $dsn));
+	my $schema;
+	my @tabs;
+	my @out;
+	eval {
+		require DBIx::DBSchema;
+		$schema = new_native DBIx::DBSchema $handle;
+	};
+
+	my $sth;
+	eval {
+		$sth = $handle->table_info()
+			or die "Table info not enabled for this driver.\n";
+		while(my $ref = $sth->fetchrow_arrayref) {
+			next unless $ref->[3] eq 'TABLE';
+			push @tabs, $ref->[2];
+		}
+	};
+
+	my %found;
+	return undef unless @tabs;
+	for my $t (@tabs) {
+		$found{$t} = 1;
+		push @out, [$t, "$t.txt $dsn"];
+		push @out, [$t, "USER $user"] if $user;
+		push @out, [$t, "PASS $pass"] if $pass;
+	}
+
+	if($schema) {
+		for my $create ($schema->sql($handle)) {
+			$create =~ /^CREATE\s+TABLE\s+(\w+)\s+/
+				or next;
+			my $t = $1;
+			next unless $found{$t};
+			push @out, [ $t, "CREATE_SQL $create"];
+		}
+	}
+	return @out;
+}
+
+*reset = \&Vend::Table::Common::reset;
+*autonumber = \&Vend::Table::Common::autonumber;
 
 1;
 



1.3.4.1   +69 -45    interchange/lib/Vend/Table/DB_File.pm


rev 1.3.4.1, prev_rev 1.3
Index: DB_File.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/DB_File.pm,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- DB_File.pm	23 Sep 2000 21:09:09 -0000	1.3
+++ DB_File.pm	25 Jan 2003 22:21:31 -0000	1.3.4.1
@@ -1,14 +1,11 @@
-# Table/DB_File.pm: access a table stored in a DB file hash
+# Vend::Table::DB_File - Access an Interchange table stored in a DB file hash
 #
-# $Id: DB_File.pm,v 1.3 2000/09/23 21:09:09 heins Exp $
+# $Id: DB_File.pm,v 1.3.4.1 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -26,7 +23,6 @@
 # MA  02111-1307  USA.
 
 package Vend::Table::DB_File;
-$VERSION = substr(q$Revision: 1.3 $, 10);
 use strict;
 use Fcntl;
 use DB_File;
@@ -34,35 +30,35 @@
 use Vend::Table::Common;
 
 @ISA = qw(Vend::Table::Common);
-$VERSION = substr(q$Revision: 1.3 $, 10);
+$VERSION = substr(q$Revision: 1.3.4.1 $, 10);
 
 sub create {
-    my ($class, $config, $columns, $filename) = @_;
+	my ($class, $config, $columns, $filename) = @_;
 
-    $config = {} unless defined $config;
-    my $File_permission_mode = $config->{File_permission_mode} || 0666;
+	$config = {} unless defined $config;
+	my $File_permission_mode = $config->{File_permission_mode} || 0666;
 
-    die "columns argument $columns is not an array ref\n"
-        unless CORE::ref($columns) eq 'ARRAY';
+	die "columns argument $columns is not an array ref\n"
+		unless CORE::ref($columns) eq 'ARRAY';
 
-    # my $column_file = "$filename.columns";
-    # my @columns = @$columns;
-    # open(COLUMNS, ">$column_file")
-    #    or die "Couldn't create '$column_file': $!";
-    # print COLUMNS join("\t", @columns), "\n";
-    # close(COLUMNS);
+	# my $column_file = "$filename.columns";
+	# my @columns = @$columns;
+	# open(COLUMNS, ">$column_file")
+	#    or die "Couldn't create '$column_file': $!";
+	# print COLUMNS join("\t", @columns), "\n";
+	# close(COLUMNS);
 
-    my $column_index = Vend::Table::Common::create_columns($columns, $config);
+	my $column_index = Vend::Table::Common::create_columns($columns, $config);
 
-    my $tie = {};
-    my $flags = O_RDWR | O_CREAT;
+	my $tie = {};
+	my $flags = O_RDWR | O_CREAT;
 
-    my $dbm = tie(%$tie, 'DB_File', $filename, $flags, $File_permission_mode)
-        or die "Could not create '$filename': $!";
+	my $dbm = tie(%$tie, 'DB_File', $filename, $flags, $File_permission_mode)
+		or die "Could not create '$filename': $!";
 
-    $tie->{'c'} = join("\t", @$columns);
+	$tie->{'c'} = join("\t", @$columns);
 
-    my $s = [
+	my $s = [
 				$config,
 				$filename,
 				$columns,
@@ -71,7 +67,7 @@
 				$tie,
 				$dbm
 			];
-    bless $s, $class;
+	bless $s, $class;
 }
 
 sub new {
@@ -81,27 +77,49 @@
 
 
 sub open_table {
-    my ($class, $config, $filename) = @_;
-    my ($Read_only) = $config->{Read_only};
+	my ($class, $config, $filename) = @_;
+
+	my $tie = {};
 
-    my $tie = {};
+	my $flags = O_RDONLY;
 
-    my $flags;
-    if ($Read_only) {
-        $flags = O_RDONLY;
-    }
-    else {
-        $flags = O_RDWR;
-    }
+	if (! $config->{Read_only}) {
+		undef $config->{Transactions};
+		$config->{_Auto_number} = 1 if $config->{AUTO_NUMBER};
+		$flags = O_RDWR;
+		if(! defined $config->{AutoNumberCounter}) {
+			eval {
+				$config->{AutoNumberCounter} = new Vend::CounterFile
+											"$config->{DIR}/$config->{name}.autonumber",
+											$config->{AUTO_NUMBER} || '00001';
+			};
+			if($@) {
+				::logError("Cannot create AutoNumberCounter: %s", $@);
+				$config->{AutoNumberCounter} = '';
+			}
+		}
+	}
+
+	my $dbm;
+	my $failed = 0;
+
+	my $retry = $Vend::Cfg->{Limit}{dbm_open_retries} || 10;
+
+	while( $failed < $retry ) {
+		$dbm = tie(%$tie, 'DB_File', $filename, $flags, 0600)
+			and undef($failed), last;
+		$failed++;
+		select(undef,undef,undef,$failed * .100);
+	}
 
-    my $dbm = tie(%$tie, 'DB_File', $filename, $flags, 0600)
-        or die "Could not open '$filename': $!";
+	die ::errmsg("%s could not tie to '%s': %s", 'DB_File', $filename, $!)
+		unless $dbm;
 
-    my $columns = [split(/\t/, $tie->{'c'})];
+	my $columns = [split(/\t/, $tie->{'c'})];
 
-    my $column_index = Vend::Table::Common::create_columns($columns, $config);
+	my $column_index = Vend::Table::Common::create_columns($columns, $config);
 
-    my $s = [
+	my $s = [
 				$config,
 				$filename,
 				$columns,
@@ -110,13 +128,14 @@
 				$tie,
 				$dbm
 			];
-    bless $s, $class;
+	bless $s, $class;
 }
 
 # Unfortunate hack need for Safe searches
 *column_index	= \&Vend::Table::Common::column_index;
 *column_exists	= \&Vend::Table::Common::column_exists;
 *columns		= \&Vend::Table::Common::columns;
+*commit			= \&Vend::Table::Common::commit;
 *config			= \&Vend::Table::Common::config;
 *delete_record	= \&Vend::Table::Common::delete_record;
 *each_record	= \&Vend::Table::Common::each_record;
@@ -124,15 +143,20 @@
 *field_accessor	= \&Vend::Table::Common::field_accessor;
 *field_settor	= \&Vend::Table::Common::field_settor;
 *inc_field		= \&Vend::Table::Common::inc_field;
+*isopen			= \&Vend::Table::Common::isopen;
+*name			= \&Vend::Table::Common::name;
 *numeric		= \&Vend::Table::Common::numeric;
 *quote			= \&Vend::Table::Common::quote;
 *record_exists	= \&Vend::Table::Common::record_exists;
 *ref			= \&Vend::Table::Common::ref;
+*rollback		= \&Vend::Table::Common::rollback;
 *row			= \&Vend::Table::Common::row;
 *row_hash		= \&Vend::Table::Common::row_hash;
 *row_settor		= \&Vend::Table::Common::row_settor;
 *set_field		= \&Vend::Table::Common::set_field;
+*set_slice		= \&Vend::Table::Common::set_slice;
 *set_row  		= \&Vend::Table::Common::set_row;
+*suicide		= \&Vend::Table::Common::suicide;
 *test_column	= \&Vend::Table::Common::test_column;
 *test_record	= \&Vend::Table::Common::record_exists;
 *touch			= \&Vend::Table::Common::touch;



1.3.4.1   +75 -56    interchange/lib/Vend/Table/GDBM.pm


rev 1.3.4.1, prev_rev 1.3
Index: GDBM.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/GDBM.pm,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -u -r1.3 -r1.3.4.1
--- GDBM.pm	23 Sep 2000 21:09:09 -0000	1.3
+++ GDBM.pm	25 Jan 2003 22:21:31 -0000	1.3.4.1
@@ -1,14 +1,11 @@
-# Table/GDBM.pm: access a table stored in a GDBM file
+# Vend::Table::GDBM - Access an Interchange table stored in a GDBM file
 #
-# $Id: GDBM.pm,v 1.3 2000/09/23 21:09:09 heins Exp $
+# $Id: GDBM.pm,v 1.3.4.1 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -32,7 +29,7 @@
 use Vend::Table::Common;
 
 @ISA = qw(Vend::Table::Common);
-$VERSION = substr(q$Revision: 1.3 $, 10);
+$VERSION = substr(q$Revision: 1.3.4.1 $, 10);
 
 sub new {
 	my ($class, $obj) = @_;
@@ -40,35 +37,35 @@
 }
 
 sub create {
-    my ($class, $config, $columns, $filename) = @_;
+	my ($class, $config, $columns, $filename) = @_;
 
-    $config = {} unless defined $config;
-    my ($File_permission_mode, $Fast_write)
-        = @$config{'File_permission_mode', 'Fast_write'};
-    $File_permission_mode = 0666 unless defined $File_permission_mode;
-    $Fast_write = 1 unless defined $Fast_write;
-
-    die "columns argument $columns is not an array ref\n"
-        unless CORE::ref($columns) eq 'ARRAY';
-
-    # my $column_file = "$filename.columns";
-    # my @columns = @$columns;
-    # open(COLUMNS, ">$column_file")
-    #    or die "Couldn't create '$column_file': $!";
-    # print COLUMNS join("\t", @columns), "\n";
-    # close(COLUMNS);
-
-    my $column_index = Vend::Table::Common::create_columns($columns, $config);
-
-    my $tie = {};
-    my $flags = GDBM_NEWDB;
-    $flags |= GDBM_FAST if $Fast_write;
-    my $dbm = tie(%$tie, 'GDBM_File', $filename, $flags, $File_permission_mode)
-        or die "Could not create '$filename': $!";
+	$config = {} unless defined $config;
+	my ($File_permission_mode, $Fast_write)
+		= @$config{'File_permission_mode', 'Fast_write'};
+	$File_permission_mode = 0666 unless defined $File_permission_mode;
+	$Fast_write = 1 unless defined $Fast_write;
+
+	die "columns argument $columns is not an array ref\n"
+		unless CORE::ref($columns) eq 'ARRAY';
+
+	# my $column_file = "$filename.columns";
+	# my @columns = @$columns;
+	# open(COLUMNS, ">$column_file")
+	#    or die "Couldn't create '$column_file': $!";
+	# print COLUMNS join("\t", @columns), "\n";
+	# close(COLUMNS);
+
+	my $column_index = Vend::Table::Common::create_columns($columns, $config);
+
+	my $tie = {};
+	my $flags = GDBM_NEWDB;
+	$flags |= GDBM_FAST if $Fast_write;
+	my $dbm = tie(%$tie, 'GDBM_File', $filename, $flags, $File_permission_mode)
+		or die "Could not create '$filename': $!";
 
-    $tie->{'c'} = join("\t", @$columns);
+	$tie->{'c'} = join("\t", @$columns);
 
-    my $s = [
+	my $s = [
 				$config,
 				$filename,
 				$columns,
@@ -77,37 +74,53 @@
 				$tie,
 				$dbm
 			];
-    bless $s, $class;
+	bless $s, $class;
 }
 
 sub open_table {
-    my ($class, $config, $filename) = @_;
+	my ($class, $config, $filename) = @_;
 	my @caller = caller();
 #::logDebug("opening table class=$class filename=$filename config=" . ::uneval($config) . " caller=@caller");
-    my $tie = {};
+	my $tie = {};
 
-    my $flags = GDBM_WRITER;
+	my $flags = GDBM_READER;
 
-    if ($config->{Read_only}) {
-        $flags = GDBM_READER;
-    }
+	if (! $config->{Read_only}) {
+		undef $config->{Transactions};
+		$config->{_Auto_number} = 1 if $config->{AUTO_NUMBER};
+		$flags = GDBM_WRITER;
+		if(! defined $config->{AutoNumberCounter}) {
+			eval {
+				$config->{AutoNumberCounter} = new Vend::CounterFile
+											"$config->{DIR}/$config->{name}.autonumber",
+											$config->{AUTO_NUMBER} || '00001';
+			};
+			if($@) {
+				::logError("Cannot create AutoNumberCounter: %s", $@);
+				$config->{AutoNumberCounter} = '';
+			}
+		}
+	}
 
 	my $dbm;
-    my $failed = 0;
+	my $failed = 0;
+
+	my $retry = $Vend::Cfg->{Limit}{dbm_open_retries} || 10;
+
+	while( $failed < $retry ) {
+		$dbm = tie(%$tie, 'GDBM_File', $filename, $flags, 0777)
+			and undef($failed), last;
+		$failed++;
+		select(undef,undef,undef,$failed * .100);
+	}
+
+	die ::errmsg("%s could not tie to '%s': %s", 'GDBM', $filename, $!)
+		unless $dbm;
 
-    while( $failed < 10 ) {
-        $dbm = tie(%$tie, 'GDBM_File', $filename, $flags, 0777)
-            and undef($failed), last;
-        $failed++;
-        select(undef,undef,undef,$failed * .100);
-    }
-
-    die ::errmsg("Could not tie to '%s': %s", $filename, $!)
-        if $failed;
-    my $columns = [split(/\t/, $tie->{'c'})];
-    my $column_index = Vend::Table::Common::create_columns($columns, $config);
+	my $columns = [split(/\t/, $tie->{'c'})];
+	my $column_index = Vend::Table::Common::create_columns($columns, $config);
 
-    my $s = [
+	my $s = [
 				$config,
 				$filename,
 				$columns,
@@ -116,13 +129,14 @@
 				$tie,
 				$dbm
 			];
-    bless $s, $class;
+	bless $s, $class;
 }
 
 # Unfortunate hack need for Safe searches
 *column_index	= \&Vend::Table::Common::column_index;
 *column_exists	= \&Vend::Table::Common::column_exists;
 *columns		= \&Vend::Table::Common::columns;
+*commit			= \&Vend::Table::Common::commit;
 *config			= \&Vend::Table::Common::config;
 *delete_record	= \&Vend::Table::Common::delete_record;
 *each_record	= \&Vend::Table::Common::each_record;
@@ -130,15 +144,20 @@
 *field_accessor	= \&Vend::Table::Common::field_accessor;
 *field_settor	= \&Vend::Table::Common::field_settor;
 *inc_field		= \&Vend::Table::Common::inc_field;
+*isopen			= \&Vend::Table::Common::isopen;
+*name			= \&Vend::Table::Common::name;
 *numeric		= \&Vend::Table::Common::numeric;
 *quote			= \&Vend::Table::Common::quote;
 *record_exists	= \&Vend::Table::Common::record_exists;
 *ref			= \&Vend::Table::Common::ref;
+*rollback		= \&Vend::Table::Common::rollback;
 *row			= \&Vend::Table::Common::row;
 *row_hash		= \&Vend::Table::Common::row_hash;
 *row_settor		= \&Vend::Table::Common::row_settor;
 *set_field		= \&Vend::Table::Common::set_field;
+*set_slice		= \&Vend::Table::Common::set_slice;
 *set_row  		= \&Vend::Table::Common::set_row;
+*suicide		= \&Vend::Table::Common::suicide;
 *test_record	= \&Vend::Table::Common::record_exists;
 *touch			= \&Vend::Table::Common::touch;
 *test_column	= \&Vend::Table::Common::test_column;



1.3.4.2   +81 -69    interchange/lib/Vend/Table/InMemory.pm


rev 1.3.4.2, prev_rev 1.3.4.1
Index: InMemory.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/InMemory.pm,v
retrieving revision 1.3.4.1
retrieving revision 1.3.4.2
diff -u -r1.3.4.1 -r1.3.4.2
--- InMemory.pm	3 Apr 2001 07:55:33 -0000	1.3.4.1
+++ InMemory.pm	25 Jan 2003 22:21:31 -0000	1.3.4.2
@@ -1,14 +1,11 @@
-# Table/InMemory.pm: store a table in memory
+# Vend::Table::InMemory - Store an Interchange table in memory
 #
-# $Id: InMemory.pm,v 1.3.4.1 2001/04/03 07:55:33 racke Exp $
+# $Id: InMemory.pm,v 1.3.4.2 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -26,9 +23,9 @@
 # MA  02111-1307  USA.
 
 package Vend::Table::InMemory;
-use Vend::Table::Common;
+use Vend::Table::Common qw(!config !columns);
 @ISA = qw/Vend::Table::Common/;
-$VERSION = substr(q$Revision: 1.3.4.1 $, 10);
+$VERSION = substr(q$Revision: 1.3.4.2 $, 10);
 use strict;
 
 # 0: column names
@@ -67,17 +64,20 @@
 }
 
 sub create {
-    my ($class, $config, $columns) = @_;
+	my ($class, $config, $columns) = @_;
+
+	$config = {} unless defined $config;
 
-    $config = {} unless defined $config;
+	undef $config->{Transactions};
 
-    die "columns argument $columns is not an array ref\n"
-        unless CORE::ref($columns) eq 'ARRAY';
+	die "columns argument $columns is not an array ref\n"
+		unless CORE::ref($columns) eq 'ARRAY';
 
-    my $column_index = Vend::Table::Common::create_columns($columns, $config);
+	my $column_index = Vend::Table::Common::create_columns($columns, $config);
+	$config->{_Auto_number} = 1 if $config->{AUTO_NUMBER};
 
-    my $tie = {};
-    my $s = [
+	my $tie = {};
+	my $s = [
 				$config,
 				undef,
 				$columns,
@@ -87,7 +87,7 @@
 				1
 			];
 #::logDebug("Create database $config->{name}: " . ::uneval($s));
-    bless $s, $class;
+	bless $s, $class;
 }
 
 sub new {
@@ -96,119 +96,128 @@
 }
 
 sub close_table {
-	1;
+	my $s = shift;
+	return 1 unless $s->[$CONFIG]{_Dirty};
+	Vend::Data::export_database($s->[$CONFIG]{name});
+	delete $s->[$CONFIG]{_Dirty};
 }
 
 sub row {
-    my ($s, $key) = @_;
-    my $a = $s->[$TIE_HASH]{$key};
-    die "There is no row with index '$key'" unless defined $a;
-    return @$a;
+	my ($s, $key) = @_;
+	my $a = $s->[$TIE_HASH]{$key};
+	die "There is no row with index '$key'" unless defined $a;
+	return @$a;
 }
 
 sub row_hash {
-    my ($s, $key) = @_;
-    my $a = $s->[$TIE_HASH]{$key};
+	my ($s, $key) = @_;
+	my $a = $s->[$TIE_HASH]{$key}
+		or return undef;
 #::logDebug("here is row $key: " . ::uneval($a));
-    die "There is no row with index '$key'" unless defined $a;
 	my %row;
 	@row{ @{$s->[$COLUMN_NAMES]} } = @$a;
-    return \%row;
+	return \%row;
 }
 
 *row_array = \&row;
 
 sub columns {
-    my ($s) = @_;
-    return @{$s->[$COLUMN_NAMES]};
+	my ($s) = @_;
+	return @{$s->[$COLUMN_NAMES]};
 }
 
 
 sub field_settor {
-    my ($s, $column) = @_;
-    my $index = $s->column_index($column);
-    return sub {
-        my ($key, $value) = @_;
-        my $a = $s->[$TIE_HASH]{$key};
-        $a = $s->[$TIE_HASH]{$key} = [] unless defined $a;
-        $a->[$index] = $value;
-        return undef;
-    };
+	my ($s, $column) = @_;
+	my $index = $s->column_index($column);
+	return sub {
+		my ($key, $value) = @_;
+		my $a = $s->[$TIE_HASH]{$key};
+		$a = $s->[$TIE_HASH]{$key} = [] unless defined $a;
+		$a->[$index] = $value;
+		$s->[$CONFIG]{_Dirty} = 1;
+		return undef;
+	};
 }
 
 sub set_row {
-    my ($s, @fields) = @_;
+	my ($s, @fields) = @_;
 	my $key = $fields[$s->[$KEY_INDEX]];
-    $s->[$TIE_HASH]{$key} = [@fields];
+	$s->[$CONFIG]{_Dirty} = 1;
+	$s->[$TIE_HASH]{$key} = [@fields];
 }
 
 sub inc_field {
-    my ($s, $key, $column, $adder) = @_;
-    my $a = $s->[$TIE_HASH]{$key};
-    $a = $s->[$TIE_HASH]{$key} = [] unless defined $a;
-    $a->[$s->column_index($column)] += $adder;
+	my ($s, $key, $column, $adder) = @_;
+	my $a = $s->[$TIE_HASH]{$key};
+	$a = $s->[$TIE_HASH]{$key} = [] unless defined $a;
+	$a->[$s->column_index($column)] += $adder;
 }
 
 sub each_record {
-    my ($s) = @_;
-    my $key;
+	my ($s) = @_;
+	my $key;
 
 #::logDebug("reached each_record InMemory");
 	return $s->each_sorted() if defined $s->[$EACH];
-    for (;;) {
-        $key = each %{$s->[$TIE_HASH]};
+	for (;;) {
+		$key = each %{$s->[$TIE_HASH]};
 		return () unless defined $key;
 		return ($key, $s->row($key));
-    }
+	}
 }
 
 sub each_nokey {
-    my ($s) = @_;
+	my ($s) = @_;
 #::logDebug("reached each_nokey InMemory");
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
-    my $key;
+	my $key;
 
-    for (;;) {
-        $key = each %{$s->[$TIE_HASH]};
+	for (;;) {
+		$key = each %{$s->[$TIE_HASH]};
 		return () unless defined $key;
-		return ($s->row($key));
-    }
+		return [ $s->row($key) ];
+	}
 }
 
 
 #sub each_record {
-#    my ($s) = @_;
-#    my @e = each %{$s->[$TIE_HASH]};
-#    if (@e) {
-#        return ($e[0], @{$e[1]});
-#    }
-#    else {
-#        return ();
-#    }
+#	my ($s) = @_;
+#	my @e = each %{$s->[$TIE_HASH]};
+#	if (@e) {
+#		return ($e[0], @{$e[1]});
+#	}
+#	else {
+#		return ();
+#	}
 #}
 
 sub record_exists {
-    my ($s, $key) = @_;
+	my ($s, $key) = @_;
 #::logDebug("$key exist test");
-    return exists($s->[$TIE_HASH]{$key});
+	return exists($s->[$TIE_HASH]{$key});
 }
 
 *test_record = \&record_exists;
 
 sub delete_record {
-    my ($s, $key) = @_;
-    delete($s->[$TIE_HASH]{$key});
+	my ($s, $key) = @_;
+	delete($s->[$TIE_HASH]{$key});
 }
 
 sub clear_table {
-    my ($s) = @_;
-    %{$s->[$TIE_HASH]} = ();
+	my ($s) = @_;
+	%{$s->[$TIE_HASH]} = ();
 }
 
 sub touch {
 	1
 }
 
+sub isopen {
+	1
+}
+
 sub ref {
 	return $_[0];
 }
@@ -217,7 +226,10 @@
 *test_column	= \&Vend::Table::Common::test_column;
 *column_index	= \&Vend::Table::Common::column_index;
 *field			= \&Vend::Table::Common::field;
+*name			= \&Vend::Table::Common::name;
 *numeric		= \&Vend::Table::Common::numeric;
 *set_field		= \&Vend::Table::Common::set_field;
+*suicide		= \&Vend::Table::Common::suicide;
+*set_slice		= \&Vend::Table::Common::set_slice;
 
 1;



1.6.4.1   +110 -78   interchange/lib/Vend/Table/LDAP.pm


rev 1.6.4.1, prev_rev 1.6
Index: LDAP.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/LDAP.pm,v
retrieving revision 1.6
retrieving revision 1.6.4.1
diff -u -r1.6 -r1.6.4.1
--- LDAP.pm	29 Sep 2000 17:45:59 -0000	1.6
+++ LDAP.pm	25 Jan 2003 22:21:31 -0000	1.6.4.1
@@ -1,14 +1,11 @@
-# Table/LDAP.pm: LDAP pseudo-table
+# Vend::Table::LDAP - Interchange LDAP pseudo-table access
 #
-# $Id: LDAP.pm,v 1.6 2000/09/29 17:45:59 heins Exp $
+# $Id: LDAP.pm,v 1.6.4.1 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -27,7 +24,7 @@
 
 package Vend::Table::LDAP;
 @ISA = qw/Vend::Table::Common/;
-$VERSION = substr(q$Revision: 1.6 $, 10);
+$VERSION = substr(q$Revision: 1.6.4.1 $, 10);
 use strict;
 
 use vars qw(
@@ -72,18 +69,38 @@
 #::logDebug("closing LDAP table");
 	return 1 if ! defined $s->[$TIE_HASH];
 #::logDebug("closing LDAP table $s->[$FILENAME]");
-	$s->[$TIE_HASH]->unbind;
+	my $do = $s->[$TIE_HASH]->unbind;
+	undef $s->[$TIE_HASH];
+	return $do;
 }
 
 sub open_table {
 	my ($class, $config, $tablename) = @_;
 #::logDebug("LDAP open_table $tablename" . ::uneval($config));
 	$tablename = $config->{name} || $tablename;
+	my $ldap;
+	my $column_index;
+	my $columns;
+
+	# LDAP doesn't do these
+	undef $config->{Transactions};
+	$config->{_Auto_number} = 1 if $config->{AUTO_NUMBER};
+  DOCONNECT: {
 	my $base = $config->{BASE_DN};
 	my $host = $config->{LDAP_HOST};
 	my $port = 389;
+	my $alt_index = 0;
 	($host, $port) = split /:/, $host if ($host =~ /:/);
-	my $ldap = Net::LDAP->new($host, port => $port) or die "Unable to connect to LDAP server $host:$port\n";
+	unless( $ldap = Net::LDAP->new($host, port => $port) ) {
+		if($config->{ALTERNATE_LDAP_HOST}[$alt_index]) {
+			for(qw/LDAP_HOST BASE_DN BIND_DN BIND_PW/) {
+				$config->{$_} = $config->{"ALTERNATE_$_"}[$alt_index] || $config->{$_};
+			}
+			$alt_index++;
+			redo DOCONNECT;
+		}
+		die "Unable to connect to LDAP server $host:$port\n";
+	}
 	$ldap->bind(
 		dn => $config->{BIND_DN},
 		password => $config->{BIND_PW},
@@ -99,12 +116,13 @@
 #	die "Unable to find database $tablename count=$c code=$co)" unless ($m->count > 0);
 	my $e = $m->entry(0);
 #::logDebug('after entry e=' . ::uneval($e));
-	my $columns = $e->get('columns');
+	$columns = $e->get('columns');
 	my $ki = $e->get('key');
 	unshift @$columns, pop @$ki;
 	@$columns = map { lc $_ } @$columns;
 #::logDebug('columns=' . ::uneval($columns));
-    my $column_index = Vend::Table::Common::create_columns($columns, $config);
+	$column_index = Vend::Table::Common::create_columns($columns, $config);
+  }
 	my $s = [
 				$config,
 				$config->{name},
@@ -117,17 +135,17 @@
 }
 
 sub create {
-    my ($class, $config, $columns, $tablename) = @_;
+	my ($class, $config, $columns, $tablename) = @_;
 
-    $config = {} unless defined $config;
+	$config = {} unless defined $config;
 
-    die "columns argument $columns is not an array ref\n"
-        unless CORE::ref($columns) eq 'ARRAY';
+	die "columns argument $columns is not an array ref\n"
+		unless CORE::ref($columns) eq 'ARRAY';
 	my $base = $config->{BASE_DN};
 	my $host = $config->{LDAP_HOST};
 	my $port = 389;
 	($host, $port) = split /:/, $host if ($host =~ /:/);
-    my $column_index = Vend::Table::Common::create_columns($columns, $config);
+	my $column_index = Vend::Table::Common::create_columns($columns, $config);
 	my $ldap = Net::LDAP->new($host, port => $port) or die "Unable to connect to LDAP server $host:$port\n";
 #::logDebug("created object " . ::uneval($ldap));
 	$ldap->bind(
@@ -147,7 +165,7 @@
 	);
 	my $m = $ldap->add($e);
 #::logDebug("added entry");
-    my $s = [
+	my $s = [
 				$config,
 				$config->{name},
 				$columns,
@@ -157,7 +175,7 @@
 			];
 #::logDebug("Created database $config->{name}" . ::uneval($s));
 #::logDebug("Created database $config->{name}");
-    bless $s, $class;
+	bless $s, $class;
 }
 
 sub new {
@@ -183,26 +201,26 @@
 }
 
 sub row {
-    my ($s, $key) = @_;
+	my ($s, $key) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
 	my $rh = row_hash($key);
 	my @a = ();
 	@a = @$rh->{@{$s->[$COLUMN_NAMES]}};
-    return @a;
+	return @a;
 }
 
 sub row_hash {
-    my ($s, $key) = @_;
+	my ($s, $key) = @_;
 #::logDebug("LDAP row_hash $key");
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
 	my $ki = $s->[$CONFIG]->{KEY};
-   	my $n = $s->[$FILENAME];
+	my $n = $s->[$FILENAME];
 	my $b = $s->[$CONFIG]->{BASE_DN};
 	my $m = $s->[$TIE_HASH]->search(
 		base => "db=$n, $b",
 		filter => "(&(objectclass=mv_data)($ki=$key))",
 	);
-    die "There is no row with index '$key'" unless ($m->count > 0);
+	die "There is no row with index '$key'" unless ($m->count > 0);
 	my $e = $m->entry(0);
 	my %row;
 	my $c;
@@ -211,29 +229,29 @@
 		my $d = $e->get($c);
 		$row{$c} = pop @$d;
 	}
-    return \%row;
+	return \%row;
 }
 
 *row_array = \&row;
 
 sub columns {
-    my ($s) = @_;
+	my ($s) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
-    return @{$s->[$COLUMN_NAMES]};
+	return @{$s->[$COLUMN_NAMES]};
 }
 
 
 sub field_settor {
-    my ($s, $column) = @_;
+	my ($s, $column) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
-    return sub {
-        my ($key, $value) = @_;
+	return sub {
+		my ($key, $value) = @_;
 		my $n = $s->[$FILENAME];
 		my $b = $s->[$CONFIG]->{BASE_DN};
 		my $ki = $s->[$CONFIG]->{KEY};
 		my $code;
 		if ($s->record_exists($key)) {
-        	my $m = $s->[$TIE_HASH]->modify(
+			my $m = $s->[$TIE_HASH]->modify(
 				dn => "$ki=$key, db=$n, $b",
 				modify => [ $column => $value ],
 			);
@@ -251,17 +269,35 @@
 		}
 		$code and die "Failed to set row $ki=$key: $code";
 		return undef;
-    };
+	};
+}
+
+sub set_slice {
+	my ($s, $key, $fary, $vary) = @_;
+	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
+	if($s->[$CONFIG]{Read_only}) {
+		::logError(
+			"Attempt to set %s in read-only table %s",
+			$key,
+			$s->[$CONFIG]{name},
+		);
+		return undef;
+	}
+
+	for( my $i = 0; $i < @$fary; $i++) {
+		$s->set_field($key, $fary->[$i], $vary->[$i]);
+	}
+	return 1;
 }
 
 sub set_field {
-    my ($s, $key, $column, $value) = @_;
+	my ($s, $key, $column, $value) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
-    if($s->[$CONFIG]{Read_only}) {
+	if($s->[$CONFIG]{Read_only}) {
 		::logError("Attempt to set $s->[$CONFIG]{name}::${column}::$key in read-only table");
 		return undef;
 	}
-    my %row;
+	my %row;
 	my $code;
 	my $ki = $s->[$CONFIG]->{KEY};
 	my $n = $s->[$CONFIG]{name};
@@ -292,7 +328,7 @@
 }
 
 sub set_row {
-    my ($s, @fields) = @_;
+	my ($s, @fields) = @_;
 #	my $x = 0;
 #	my $subname;
 #	while ((undef, undef, undef, $subname) = caller($x++))
@@ -335,7 +371,7 @@
 }
 
 sub inc_field {
-    my ($s, $key, $column, $adder) = @_;
+	my ($s, $key, $column, $adder) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
 	my $f = field($key, $column);
 	$f += $adder;
@@ -343,9 +379,9 @@
 }
 
 sub each_record {
-    my ($s) = @_;
+	my ($s) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
-    my $key;
+	my $key;
 	my @r;
 	my $ki = $s->[$CONFIG]->{KEY};
 	unless (defined $s->[$EACH]) {
@@ -368,7 +404,7 @@
 			my $k = $data->get($ki)->[0];
 			my (@record) = $k;
 			for(@names) {
-				push @record, $data->get($_);
+				push @record, $data->get($_)->[0];
 			}
 			push @repos, \@record;
 		}
@@ -384,16 +420,16 @@
 }
 
 sub each_nokey {
-    my (@ary) = each_record(@_);
+	my (@ary) = each_record(@_);
 	shift @ary;
-	return @ary;
+	return \@ary;
 }
 
 sub record_exists {
-    my ($s, $key) = @_;
+	my ($s, $key) = @_;
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
 	my $ki = $s->[$CONFIG]->{KEY};
-   	my $n = $s->[$CONFIG]{name};
+	my $n = $s->[$CONFIG]{name};
 	my $b = $s->[$CONFIG]->{BASE_DN};
 	my $m = $s->[$TIE_HASH]->search(
 		base => "db=$n, $b",
@@ -403,19 +439,22 @@
 	{
 #::logDebug("$ki=$key, db=$n, $b exists");
 	}
-    return $m->count;
+	return $m->count;
 }
 
 *test_record = \&record_exists;
 
 sub delete_record {
-    my ($s, $key) = @_;
-#    delete($s->[$TIE_HASH]{$key});
-#::logDebug("delete $key not impl.");
+	my ($s, $key) = @_;
+        $s = $s->import_db() if ! defined $s->[$TIE_HASH];
+        my $ki = $s->[$CONFIG]->{KEY};
+        my $n = $s->[$CONFIG]{name};
+        my $b = $s->[$CONFIG]->{BASE_DN};
+        my $m = $s->[$TIE_HASH]->delete("$ki=$key,db=$n,$b");
 }
 
 sub clear_table {
-    my ($s) = @_;
+	my ($s) = @_;
 #::logDebug("clear table not impl.");
 }
 
@@ -430,13 +469,13 @@
 }
 
 sub query {
-    my($s, $opt, $text, @arg) = @_;
+	my($s, $opt, $text, @arg) = @_;
 
-    if(! CORE::ref($opt) ) {
-        unshift @arg, $text;
-        $text = $opt;
-        $opt = {};
-    }
+	if(! CORE::ref($opt) ) {
+		unshift @arg, $text;
+		$text = $opt;
+		$opt = {};
+	}
 
 	$s = $s->import_db() if ! defined $s->[$TIE_HASH];
 	$opt->{query} = $opt->{sql} || $text if ! $opt->{query};
@@ -456,7 +495,7 @@
 	}
 
 	my $query;
-    $query = ! scalar @arg
+	$query = ! scalar @arg
 			? $opt->{query}
 			: sprintf_substitute ($s, $opt->{query}, \@arg);
 
@@ -480,8 +519,10 @@
 		eval {
 			($spec, $stmt) = Vend::Scan::sql_statement($query, $ref);
 		};
-		if(! CORE::ref $spec) {
-			::logError("Bad SQL, query was: $query");
+		if($@) {
+			my $msg = ::errmsg("SQL query failed: %s\nquery was: %s", $@, $query);
+			Carp::croak($msg) if $Vend::Try;
+			::logError($msg);
 			return ($opt->{failure} || undef);
 		}
 		my @additions = grep length($_) == 2, keys %$opt;
@@ -525,18 +566,18 @@
 
 #::logDebug("tabs='@tabs' columns='@na' vals='@vals' update=$update"); 
 
-    my $search;
-    if ("\L$opt->{st}" eq 'db' ) {
+	my $search;
+	if ("\L$opt->{st}" eq 'db' ) {
 		for(@tabs) {
 			s/\..*//;
 		}
-        $search = new Vend::DbSearch;
+		$search = new Vend::DbSearch;
 #::logDebug("created DbSearch object: " . ::uneval($search));
 	}
 	else {
-        $search = new Vend::TextSearch;
+		$search = new Vend::TextSearch;
 #::logDebug("created TextSearch object: " . ::uneval($search));
-    }
+	}
 
 	my %fh;
 	my $i = 0;
@@ -552,22 +593,9 @@
 
 	if($update) {
 #::logDebug("Updating, update=$update");
-#		$relocate = $stmt->{MV_VALUE_RELOCATE}
-#			if defined $stmt->{MV_VALUE_RELOCATE};
 		$opt->{row_count} = 1;
 		die "Reached update query without object"
 			if ! $s;
-#		if($relocate) {
-#			my $code = splice(@vals, $stmt->{MV_VALUE_RELOCATE}, 1);
-#			unshift(@vals, $code) if $update ne 'UPDATE';
-##::logDebug("relocating values col=$relocate: columns='@na' vals='@vals'"); 
-#		}
-#		elsif (!defined $relocate) {
-#			die "Must have code field to insert"
-#				 if $update eq 'INSERT';
-#			unshift(@na, $codename);
-##::logDebug("NOT defined relocating values col=$relocate: columns='@na' vals='@vals'"); 
-#		}
 		my $sub = $update eq 'DELETE'
 					? sub { delete_record($s, @_) }
 					: $s->row_settor(@na);
@@ -600,7 +628,7 @@
 #::logDebug("search spec: " . Vend::Util::uneval($spec));
 #::logDebug("name hash: " . Vend::Util::uneval(\%nh));
 #::logDebug("ref returned: " . substr(Vend::Util::uneval($ref), 0, 100));
-e:logDebug("opt is: " . Vend::Util::uneval($opt));
+#:logDebug("opt is: " . Vend::Util::uneval($opt));
 	if($@) {
 		::logError("MVSQL query failed for $opt->{table}: $@\nquery was: $query");
 		$return = $opt->{failure} || undef;
@@ -620,7 +648,11 @@
 # Unfortunate hack need for Safe searches
 *column_index	= \&Vend::Table::Common::column_index;
 *column_exists	= \&Vend::Table::Common::column_exists;
+*name			= \&Vend::Table::Common::name;
 *numeric		= \&Vend::Table::Common::numeric;
+*isopen			= \&Vend::Table::Common::isopen;
+*reset			= \&Vend::Table::Common::reset;
+*suicide		= \&Vend::Table::Common::suicide;
 *test_column	= \&Vend::Table::Common::test_column;
 
 1;



No                   revision



No                   revision



1.23.2.1  +2 -2      interchange/lib/Vend/Table/Editor.pm


rev 1.23.2.1, prev_rev 1.23
Index: Editor.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/Editor.pm,v
retrieving revision 1.23
retrieving revision 1.23.2.1
diff -u -r1.23 -r1.23.2.1
--- Editor.pm	15 Jan 2003 14:32:48 -0000	1.23
+++ Editor.pm	25 Jan 2003 22:21:31 -0000	1.23.2.1
@@ -1,6 +1,6 @@
 # Vend::Table::Editor - Swiss-army-knife table editor for Interchange
 #
-# $Id: Editor.pm,v 1.23 2003/01/15 14:32:48 racke Exp $
+# $Id: Editor.pm,v 1.23.2.1 2003/01/25 22:21:31 racke Exp $
 #
 # Copyright (C) 2002 ICDEVGROUP <interchange@icdevgroup.org>
 # Copyright (C) 2002 Mike Heins <mike@perusion.net>
@@ -26,7 +26,7 @@
 package Vend::Table::Editor;
 
 use vars qw($VERSION);
-$VERSION = substr(q$Revision: 1.23 $, 10);
+$VERSION = substr(q$Revision: 1.23.2.1 $, 10);
 
 use Vend::Util;
 use Vend::Interpolate;



2.5.2.1   +3 -3      interchange/lib/Vend/Table/SDBM.pm


rev 2.5.2.1, prev_rev 2.5
Index: SDBM.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/SDBM.pm,v
retrieving revision 2.5
retrieving revision 2.5.2.1
diff -u -r2.5 -r2.5.2.1
--- SDBM.pm	13 Jan 2003 23:06:28 -0000	2.5
+++ SDBM.pm	25 Jan 2003 22:21:31 -0000	2.5.2.1
@@ -1,6 +1,6 @@
 # Vend::Table::SDBM - Access an Interchange table stored in Perl's internal SDBM
 #
-# $Id: SDBM.pm,v 2.5 2003/01/13 23:06:28 mheins Exp $
+# $Id: SDBM.pm,v 2.5.2.1 2003/01/25 22:21:31 racke Exp $
 #
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
@@ -23,7 +23,7 @@
 # MA  02111-1307  USA.
 
 package Vend::Table::SDBM;
-$VERSION = substr(q$Revision: 2.5 $, 10);
+$VERSION = substr(q$Revision: 2.5.2.1 $, 10);
 use strict;
 use Fcntl;
 use SDBM_File;
@@ -31,7 +31,7 @@
 use Vend::Table::Common;
 
 @ISA = qw(Vend::Table::Common);
-$VERSION = substr(q$Revision: 2.5 $, 10);
+$VERSION = substr(q$Revision: 2.5.2.1 $, 10);
 
 sub create {
 	my ($class, $config, $columns, $filename) = @_;



1.19.2.1  +2 -2      interchange/lib/Vend/Table/Shadow.pm


rev 1.19.2.1, prev_rev 1.19
Index: Shadow.pm
===================================================================
RCS file: /var/cvs/interchange/lib/Vend/Table/Shadow.pm,v
retrieving revision 1.19
retrieving revision 1.19.2.1
diff -u -r1.19 -r1.19.2.1
--- Shadow.pm	3 Jan 2003 11:55:22 -0000	1.19
+++ Shadow.pm	25 Jan 2003 22:21:31 -0000	1.19.2.1
@@ -1,6 +1,6 @@
 # Vend::Table::Shadow - Access a virtual "Shadow" table
 #
-# $Id: Shadow.pm,v 1.19 2003/01/03 11:55:22 racke Exp $
+# $Id: Shadow.pm,v 1.19.2.1 2003/01/25 22:21:31 racke Exp $
 #
 # Copyright (C) 2002-2003 Stefan Hornburg (Racke) <racke@linuxia.de>
 #
@@ -20,7 +20,7 @@
 # MA  02111-1307  USA.
 
 package Vend::Table::Shadow;
-$VERSION = substr(q$Revision: 1.19 $, 10);
+$VERSION = substr(q$Revision: 1.19.2.1 $, 10);
 
 # TODO
 #



No                   revision



No                   revision



1.1.1.1.4.2 +4 -1      interchange/scripts/.cvsignore


rev 1.1.1.1.4.2, prev_rev 1.1.1.1.4.1
Index: .cvsignore
===================================================================
RCS file: /var/cvs/interchange/scripts/.cvsignore,v
retrieving revision 1.1.1.1.4.1
retrieving revision 1.1.1.1.4.2
diff -u -r1.1.1.1.4.1 -r1.1.1.1.4.2
--- .cvsignore	14 Oct 2000 14:48:05 -0000	1.1.1.1.4.1
+++ .cvsignore	25 Jan 2003 22:21:31 -0000	1.1.1.1.4.2
@@ -1,15 +1,18 @@
+chkcat
 compile_link
 configdump
 config_prog
 dump
 expire
 expireall
+findtags
+ic_mod_perl
 initp.pl
 interchange
 localize
 makecat
 minivend
+newcat
 offline
 restart
 update
-



1.6.4.3   +32 -58    interchange/scripts/compile_link.PL


rev 1.6.4.3, prev_rev 1.6.4.2
Index: compile_link.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/compile_link.PL,v
retrieving revision 1.6.4.2
retrieving revision 1.6.4.3
diff -u -r1.6.4.2 -r1.6.4.3
--- compile_link.PL	14 Nov 2000 21:23:02 -0000	1.6.4.2
+++ compile_link.PL	25 Jan 2003 22:21:31 -0000	1.6.4.3
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange link program configurator
 #
-# $Id: compile_link.PL,v 1.6.4.2 2000/11/14 21:23:02 racke Exp $
+# $Id: compile_link.PL,v 1.6.4.3 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# See the file 'Changes' for information.
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -56,34 +32,38 @@
 use File::Copy;
 use Getopt::Long;
 
+use vars qw/$Self/;
+
 Getopt::Long::config(qw/permute/);
 
-my $Self = {
-	LINK_HOST      => 'localhost',
-	LINK_PORT      => 7786,
-	LINK_TIMEOUT   => 30,
-	LINK_FILE      => '/usr/local/interchange/etc/socket',
-#	LINK_FILE      => '~_~INSTALLARCHLIB~_~/etc/socket',
-	SRC_DIR        => '/usr/local/interchange/src',
-#	SRC_DIR        => '~_~INSTALLARCHLIB~_~/src',
-	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLPRIVLIB => '~_~INSTALLPRIVLIB~_~',
-	INSTALLARCHLIB => '/usr/local/interchange',
-#	INSTALLARCHLIB => '~_~INSTALLARCHLIB~_~',
-	INSTALLMAN1DIR => '/usr/local/interchange/doc',
-#	INSTALLMAN1DIR => '~_~INSTALLMAN1DIR~_~',
-	INSTALLSCRIPT => '/usr/local/interchange/bin',
-#	INSTALLSCRIPT => '~_~INSTALLARCHLIB~_~/bin',
-	INSTALLBIN => '/usr/local/interchange/bin',
-#	INSTALLBIN => '~_~INSTALLBIN~_~',
-};
+BEGIN {
+	$::Self = {
+		LINK_HOST      => 'localhost',
+		LINK_PORT      => 7786,
+		LINK_TIMEOUT   => 30,
+		LINK_FILE      => '/usr/local/interchange/etc/socket',
+#		LINK_FILE      => '~_~INSTALLARCHLIB~_~/etc/socket',
+		SRC_DIR        => '/usr/local/interchange/src',
+#		SRC_DIR        => '~_~INSTALLARCHLIB~_~/src',
+		INSTALLPRIVLIB => '/usr/local/interchange/lib',
+#		INSTALLPRIVLIB => '~_~INSTALLPRIVLIB~_~',
+		INSTALLARCHLIB => '/usr/local/interchange',
+#		INSTALLARCHLIB => '~_~INSTALLARCHLIB~_~',
+		INSTALLMAN1DIR => '/usr/local/interchange/doc',
+#		INSTALLMAN1DIR => '~_~INSTALLMAN1DIR~_~',
+		INSTALLSCRIPT => '/usr/local/interchange/bin',
+#		INSTALLSCRIPT => '~_~INSTALLARCHLIB~_~/bin',
+		INSTALLBIN => '/usr/local/interchange/bin',
+#		INSTALLBIN => '~_~INSTALLBIN~_~',
+	};
+}
 
 ### END CONFIGURATION VARIABLES
 
 my $prog = $0;
 $prog =~ s:.*/::;
 my $USAGE = <<EOF;
-usage: $prog [-t tcp_port] [-s sockfile] [-h host] [-w secs] \
+usage: $prog [-p tcp_port] [-s sockfile] [-h host] [-w secs] \
              [--perl] [-o outputfile] [--suid]
 
 Configures Interchange link program.
@@ -173,7 +153,7 @@
 	return "$preamble$replace$postamble$template";
 }
 
-if($Build_dir) {
+if($Build_dir and $Build_dir ne $Self->{SRC_DIR}) {
 	if (-e $Build_dir and (! -d _ or ! -w _)) {
 		die "Cannot use $Build_dir for build directory.\n";
 	}
@@ -206,6 +186,9 @@
 
 foreach my $targ (@edit_files) {
 	my $src = "$targ.tmp";
+	die "Source file $src doesn't exist\n" if ! -e $targ;
+	die "Can't edit a directory\n"         if -d $targ;
+	die "Can't edit a directory\n"         if -d $src;
 	rename $targ, $src
 		or die "Couldn't rename $targ to $src: $!\n";
 	open (IN, "< $src")
@@ -383,18 +366,9 @@
 
 =head1 SEE ALSO
 
-makecat(1), http://www.akopia.com/
+makecat(1), http://interchange.redhat.com/
 
 =head1 AUTHOR
 
-Mike Heins, <heins@akopia.com>
+Mike Heins, <mheins@redhat.com>
 
-
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.6.4.1   +23 -54    interchange/scripts/config_prog.PL


rev 1.6.4.1, prev_rev 1.6
Index: config_prog.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/config_prog.PL,v
retrieving revision 1.6
retrieving revision 1.6.4.1
diff -u -r1.6 -r1.6.4.1
--- config_prog.PL	4 Oct 2000 23:36:31 -0000	1.6
+++ config_prog.PL	25 Jan 2003 22:21:31 -0000	1.6.4.1
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange program configurator
 #
-# $Id: config_prog.PL,v 1.6 2000/10/04 23:36:31 heins Exp $
+# $Id: config_prog.PL,v 1.6.4.1 2003/01/25 22:21:31 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# See the file 'Changes' for information.
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -57,18 +33,22 @@
 
 Getopt::Long::config(qw/permute/);
 
-my $Self = {
-	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLPRIVLIB => '~_~INSTALLPRIVLIB~_~',
-	INSTALLARCHLIB => '/usr/local/interchange',
-#	INSTALLARCHLIB => '~_~INSTALLARCHLIB~_~',
-	INSTALLMAN1DIR => '/usr/local/interchange/doc',
-#	INSTALLMAN1DIR => '~_~INSTALLMAN1DIR~_~',
-	INSTALLSCRIPT => '/usr/local/interchange/bin',
-#	INSTALLSCRIPT => '~_~INSTALLARCHLIB~_~/bin',
-	INSTALLBIN => '/usr/local/interchange/bin',
-#	INSTALLBIN => '~_~INSTALLBIN~_~',
-};
+use vars qw/$Self/;
+
+BEGIN {
+	$Self = {
+		INSTALLPRIVLIB => '/usr/local/interchange/lib',
+#		INSTALLPRIVLIB => '~_~INSTALLPRIVLIB~_~',
+		INSTALLARCHLIB => '/usr/local/interchange',
+#		INSTALLARCHLIB => '~_~INSTALLARCHLIB~_~',
+		INSTALLMAN1DIR => '/usr/local/interchange/doc',
+#		INSTALLMAN1DIR => '~_~INSTALLMAN1DIR~_~',
+		INSTALLSCRIPT => '/usr/local/interchange/bin',
+#		INSTALLSCRIPT => '~_~INSTALLARCHLIB~_~/bin',
+		INSTALLBIN => '/usr/local/interchange/bin',
+#		INSTALLBIN => '~_~INSTALLBIN~_~',
+	};
+}
 
 ### END CONFIGURATION VARIABLES
 
@@ -126,13 +106,10 @@
 sub doit {
 	my ($self, $orig, $template, $preamble, $key, $postamble) = @_;
 	my $replace =  $Self->{$key} || $Config{$key};
-#warn <<EOF;
-#orig=$orig
-#template=$template
-#key=$key
-#replace=$replace
-#EOF
+
 	return "$orig$template" unless defined $replace;
+	$preamble =~ s/~_~(\w+)~_~/$Self->{$1} || $Config{$1}/eg;
+	$postamble =~ s/~_~(\w+)~_~/$Self->{$1} || $Config{$1}/eg;
 	return "$preamble$replace$postamble$template";
 }
 
@@ -156,7 +133,7 @@
 
 =head1 VERSION
 
-$Id: config_prog.PL,v 1.6 2000/10/04 23:36:31 heins Exp $
+# $Id: config_prog.PL,v 1.6.4.1 2003/01/25 22:21:31 racke Exp $
 
 =head1 DESCRIPTION
 
@@ -164,16 +141,8 @@
 
 =head1 SEE ALSO
 
-mvdocs(8), compile_link(1), config_prog(1), configdump(1), dump(1), expire(1),
+compile_link(1), config_prog(1), configdump(1), dump(1), expire(1),
 expireall(1), localize(1), makecat(1), interchange(1), offline(1),
 restart(1), update(1)
 
 =cut
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.8.4.1   +4 -36     interchange/scripts/configdump.PL


rev 1.8.4.1, prev_rev 1.8
Index: configdump.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/configdump.PL,v
retrieving revision 1.8
retrieving revision 1.8.4.1
diff -u -r1.8 -r1.8.4.1
--- configdump.PL	25 Sep 2000 16:35:28 -0000	1.8
+++ configdump.PL	25 Jan 2003 22:21:32 -0000	1.8.4.1
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange configuration dumper
 #
-# $Id: configdump.PL,v 1.8 2000/09/25 16:35:28 zarko Exp $
+# $Id: configdump.PL,v 1.8.4.1 2003/01/25 22:21:32 racke Exp $
 #
-# Copyright 1999, 2000 by Stefan Hornburg <racke@linuxia.de>
-#
-# See the file 'Changes' for information.
+# Copyright 1999-2002 by Stefan Hornburg <racke@linuxia.de>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -94,7 +70,7 @@
     exit 1;
 }
     
-my ($catalog, $name);
+my $catalog;
 
 $Vend::Cfg = {};
 
@@ -183,7 +159,7 @@
 
 =head1 SEE ALSO
 
-mvdocs(8), dump(1), makecat(1), interchange(1)
+dump(1), makecat(1), interchange(1)
 
 =head1 LICENSE
 
@@ -202,11 +178,3 @@
 
 =cut
 
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.8.4.1   +6 -42     interchange/scripts/dump.PL


rev 1.8.4.1, prev_rev 1.8
Index: dump.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/dump.PL,v
retrieving revision 1.8
retrieving revision 1.8.4.1
diff -u -r1.8 -r1.8.4.1
--- dump.PL	25 Sep 2000 16:51:27 -0000	1.8
+++ dump.PL	25 Jan 2003 22:21:32 -0000	1.8.4.1
@@ -1,41 +1,14 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange session dumper
 #
-# $Id: dump.PL,v 1.8 2000/09/25 16:51:27 zarko Exp $
-#
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# $Id: dump.PL,v 1.8.4.1 2003/01/25 22:21:32 racke Exp $
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# See the file 'Changes' for information.
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995-96 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -248,23 +221,14 @@
 
 =head1 VERSION
 
-$Id: dump.PL,v 1.8 2000/09/25 16:51:27 zarko Exp $
+# $Id: dump.PL,v 1.8.4.1 2003/01/25 22:21:32 racke Exp $
 
 =head1 SEE ALSO
 
-mvdocs(8), configdump(1), makecat(1), interchange(1)
-
+configdump(1), makecat(1), interchange(1)
 
 =head1 DESCRIPTION
 
 Skeleton POD to avoid make errors.
 
 =cut
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.8.4.2   +97 -78    interchange/scripts/expire.PL


rev 1.8.4.2, prev_rev 1.8.4.1
Index: expire.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/expire.PL,v
retrieving revision 1.8.4.1
retrieving revision 1.8.4.2
diff -u -r1.8.4.1 -r1.8.4.2
--- expire.PL	26 Oct 2000 07:03:28 -0000	1.8.4.1
+++ expire.PL	25 Jan 2003 22:21:32 -0000	1.8.4.2
@@ -1,41 +1,14 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange session expiration
 #
-# $Id: expire.PL,v 1.8.4.1 2000/10/26 07:03:28 racke Exp $
-#
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# $Id: expire.PL,v 1.8.4.2 2003/01/25 22:21:32 racke Exp $
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# See the file 'Changes' for information.
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995-96 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -59,11 +32,6 @@
 
 use strict;
 use Fcntl;
-use Vend::Session;
-use Vend::Config qw(get_catalog_default parse_time);
-use Vend::Util qw/errmsg/;
-use Getopt::Std;
-use vars qw/$opt_c $opt_r $opt_e $opt_f $opt_u $opt_v $opt_x/;
 
 BEGIN {
 	($Global::VendRoot = $ENV{MINIVEND_ROOT})
@@ -101,34 +69,85 @@
 #select a DBM
 
 BEGIN {
-	$Global::GDBM = $Global::DB_File = 0;
-    AUTO: {
-        last AUTO if
-            (defined $ENV{MINIVEND_DBFILE} and $Global::DB_File = 1);
-        last AUTO if
-            (defined $ENV{MINIVEND_NODBM});
-        eval {require GDBM_File and $Global::GDBM = 1} ||
-        eval {require DB_File and $Global::DB_File = 1};
-    }
+	$Global::GDBM = $Global::DB_File = $Global::SDBM =
+# LDAP
+	$Global::LDAP =
+# END LDAP
+# SQL
+	$Global::DBI =
+# END SQL
+	0;
+
+# SQL
+	# This is for standard DBI
+	eval {
+			die if $ENV{MINIVEND_NODBI};
+			require DBI and $Global::DBI = 1
+	};
+# END SQL
+# LDAP
+	eval {
+		die if $ENV{MINIVEND_NOLDAP};
+		require Net::LDAP and $Global::LDAP = 1
+	};
+# END LDAP
+
+	# Now can use any type of database
+	AUTO: {
+		last AUTO if 
+			(defined $ENV{MINIVEND_DBFILE} and $Global::DB_File = 1);
+		last AUTO if 
+			(defined $ENV{MINIVEND_SDBM} and $Global::SDBM = 1);
+		last AUTO if 
+			(defined $ENV{MINIVEND_NODBM});
+		eval {require GDBM_File and $Global::GDBM = 1};
+		last AUTO if 
+			(defined $ENV{MINIVEND_GDBM} and $Global::GDBM = 1);
+		last AUTO if
+				!   $ENV{MINIVEND_ALLDBM}
+				and $Global::GDBM;
+		eval {require DB_File and $Global::DB_File = 1};
+		last AUTO if
+				!   $ENV{MINIVEND_ALLDBM}
+				and $Global::GDBM || $Global::DB_File;
+		eval {require SDBM_File and $Global::SDBM = 1};
+	}
+
 	if($Global::GDBM) {
 		require Vend::Table::GDBM;
 		import GDBM_File;
 		$Global::GDBM = 1;
+		$Global::Default_database = 'GDBM'
+			unless defined $Global::Default_database;
 	}
-	elsif($Global::DB_File) {
+	if($Global::DB_File) {
 		require Vend::Table::DB_File;
 		import DB_File;
 		$Global::DB_File = 1;
+		$Global::Default_database = 'DB_FILE'
+			unless defined $Global::Default_database;
 	}
-	else {
-		die "Can't use expire without DBM sessions.\n";
-	}
+	if($Global::SDBM) {
+		require Vend::Table::SDBM;
+		import SDBM_File;
+		$Global::SDBM = 1;
+		$Global::Default_database = 'SDBM'
+			unless defined $Global::Default_database;
+	}
+	$Global::Default_database = 'MEMORY'
+			unless defined $Global::Default_database;
+	require Vend::Table::InMemory;
 }
 
-sub logGlobal {
-	ref $_[0] and shift(@_);
-	warn(errmsg(@_)) unless $Vend::Quiet;
-}
+use Vend::Session;
+use Vend::Config qw(get_catalog_default global_config parse_time);
+use Vend::Util qw/errmsg/;
+use Getopt::Std;
+use vars qw/$opt_c $opt_r $opt_e $opt_f $opt_u $opt_v $opt_x/;
+
+sub logGlobal {  }
+sub logError  {  }
+sub logDebug  {  }
 
 sub is_retired {}
 
@@ -167,6 +186,13 @@
 $expiretime = $opt_e || undef;
 $reorg      = $opt_r;
 
+if($opt_f) {
+	$Global::ConfigFile = $opt_f;
+}
+else {
+	$Global::ConfigFile = "$Global::VendRoot/$Global::ConfigFile";
+}
+
 GETOPT: {
 
 	last GETOPT if $catalog;
@@ -201,24 +227,25 @@
 
 if(defined $catalog) {
 	my($name,$dir,$param);
-	chdir $Global::VendRoot;
-	open(GLOBAL, "< $Global::ConfigFile") or
-		die "No global configuration file? Aborting.\n";
-	while(<GLOBAL>) {
-		next unless /^\s*((?:sub)?catalog)\s+($catalog\s+.*)/i;
-		Vend::Config::parse_catalog($1, $2);
-	}
-	close GLOBAL;
-	die "Catalog $catalog not found in $Global::ConfigFile.\n"
-		unless $Global::Catalog{$catalog};
+
+	# Parse the interchange.cfg file to look for script/catalog info
+	# but don't read in the core tags
+	$Vend::ControllingInterchange = 1;
+	chdir $Global::VendRoot
+		or die "Couldn't change to $Global::VendRoot: $!\n";
+	global_config();
+
 	$g = $Global::Catalog{$catalog};
 	chdir $g->{dir} or die "chdir to $g->{dir}: $!\n";
-	$Vend::Cfg = Vend::Config::config(
+	eval {$Vend::Cfg = Vend::Config::config(
 					$g->{name},
 					$g->{dir},
 					"$g->{dir}/etc",
 					$g->{base} || undef,
-					);
+					)};
+    if ($@) {
+        die "$0: Configuration for catalog $catalog failed: $@\n";
+    }
 }
 else {
 	$Vend::Cfg->{ScratchDir} = '/tmp';
@@ -236,7 +263,8 @@
   if $opt_v;
 
 
-if ($Vend::Cfg->{SessionType} eq 'File' ) {
+if ($Vend::Cfg->{SessionType} eq 'File'
+	or $Vend::Cfg->{SessionType} eq 'NFS') {
 	require File::Find;
 	my $expire = $Vend::Cfg->{SessionExpire} + 60;
 	$expire /= 86400;
@@ -279,7 +307,7 @@
 
 =head1 VERSION
 
-1.0
+1.1
 
 =head1 SYNOPSIS
 
@@ -322,18 +350,9 @@
 
 =head1 SEE ALSO
 
-mvdocs(8), expireall(1), http://www.akopia.com/
+expireall(1), http://interchange.redhat.com/
 
 =head1 AUTHOR
 
-Mike Heins, <heins@akopia.com>
+Mike Heins, <mheins@redhat.com>
 
-
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.8.4.2   +34 -58    interchange/scripts/expireall.PL


rev 1.8.4.2, prev_rev 1.8.4.1
Index: expireall.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/expireall.PL,v
retrieving revision 1.8.4.1
retrieving revision 1.8.4.2
diff -u -r1.8.4.1 -r1.8.4.2
--- expireall.PL	26 Oct 2000 07:03:28 -0000	1.8.4.1
+++ expireall.PL	25 Jan 2003 22:21:32 -0000	1.8.4.2
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange session expiration for all catalogs
 #
-# $Id: expireall.PL,v 1.8.4.1 2000/10/26 07:03:28 racke Exp $
+# $Id: expireall.PL,v 1.8.4.2 2003/01/25 22:21:32 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# See the file 'Changes' for information.
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -85,26 +61,42 @@
 my $USAGE = <<EOF;
 usage: $prog [-r] [-f file]
 
-	-f    Alternate interchange.cfg file
-	-r    Use reorganize parameter in command
+    -f    Alternate interchange.cfg file
+    -n    Do not unlink files
+    -r    Use reorganize parameter in command
 
 Expire all listed Interchange catalogs. Will read information from
 either the file passed with -f or:
 
-	$Global::VendRoot/interchange.cfg
+    $Global::VendRoot/interchange.cfg
 
 EOF
 
+use Vend::Config;
+
+$Vend::ExternalProgram = 1;
+$Vend::Quiet = 1;
+
 getopts('e:f:rn') or die "$@\n$USAGE\n";
 
-($Global::ConfigFile = $opt_f)
-	if defined $opt_f;
+sub logGlobal { shift(@_) if ref $_[0]; printf @_; print "\n" }
+sub logError { }
+sub logDebug { }
 
 my $flag = '';
+
+if($opt_f) {
+	$Global::ConfigFile = $opt_f;
+	$flag .= qq{ -f "$opt_f"};
+}
+else {
+	$Global::ConfigFile = "$Global::VendRoot/$Global::ConfigFile";
+}
+
 my @cats;
 
 if ($opt_r) {
-	$flag .= '-r';
+	$flag .= ' -r';
 }
 
 if($opt_e) {
@@ -120,22 +112,14 @@
 }
 
 # Parse the interchange.cfg file to look for script/catalog info
-PARSECFG: {
-	my(@cfglines,%seen);
-
-	open(GLOBAL, "< $Global::ConfigFile") or die "Couldn't read $Global::ConfigFile: $!\n";
-	while(<GLOBAL>) {
-		push(@cfglines, $_) if /^\s*catalog\s+/i;
-	}
-	close GLOBAL;
-
-	@cfglines = grep !$seen{$_}++, @cfglines;
-
-	for(@cfglines) {
-		next unless /^\s*(?:sub)?catalog\s+([-\w_]+)/i;
-		push(@cats, $1);
-	}
-
+# but don't read in the core tags
+$Vend::ControllingInterchange = 1;
+chdir $Global::VendRoot or die "Couldn't change to $Global::VendRoot: $!\n";
+global_config();
+
+while( my($name, $cat) = each %Global::Catalog ) {
+	next if $cat->{base};
+	push @cats, $name;
 }
 
 for(@cats) {
@@ -148,7 +132,7 @@
 
 =head1 VERSION
 
-$Id: expireall.PL,v 1.8.4.1 2000/10/26 07:03:28 racke Exp $
+# $Id: expireall.PL,v 1.8.4.2 2003/01/25 22:21:32 racke Exp $
 
 =head1 DESCRIPTION
 
@@ -156,15 +140,7 @@
 
 =head1 SEE ALSO
 
-mvdocs(8), expire(1), http://www.akopia.com/
+expire(1), http://interchange.redhat.com/
 
 
 =cut
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.8.4.24  +271 -1827 interchange/scripts/interchange.PL


rev 1.8.4.24, prev_rev 1.8.4.23
Index: interchange.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/interchange.PL,v
retrieving revision 1.8.4.23
retrieving revision 1.8.4.24
diff -u -r1.8.4.23 -r1.8.4.24
--- interchange.PL	15 Apr 2001 13:15:41 -0000	1.8.4.23
+++ interchange.PL	25 Jan 2003 22:21:32 -0000	1.8.4.24
@@ -1,41 +1,17 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
-# Interchange version 4.6
-#
-# $Id: interchange.PL,v 1.8.4.23 2001/04/15 13:15:41 racke Exp $
+# Interchange version 4.9.7
 #
-# Copyright (C) 1996-2001 Akopia, Inc. <info@akopia.com>
+# $Id: interchange.PL,v 1.8.4.24 2003/01/25 22:21:32 racke Exp $
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. and others.
+# http://www.icdevgroup.org/
 #
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
-# See the file 'Changes' for information.
+# See the files 'README' and 'WHATSNEW' for information.
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -60,10 +36,16 @@
 use strict;
 
 BEGIN {
-	$Vend::Foreground = 1;
+	$Global::Foreground = 1;
 	
 	($Global::VendRoot = $ENV{MINIVEND_ROOT})
 		if defined $ENV{MINIVEND_ROOT};
+
+	## This should only happen in "make test"
+	if($Global::VendRoot =~ m{/blib$}) {
+		shift @INC;
+		shift @INC;
+	}
 	
 	$Global::VendRoot = $Global::VendRoot || '/usr/local/interchange';
 #	$Global::VendRoot = $Global::VendRoot || '~_~INSTALLARCHLIB~_~';
@@ -76,7 +58,7 @@
 		$Global::ExeName = 'minivend';
 		$Global::ConfigFile = 'minivend.cfg';
 	}
-	elsif(-f "$Global::VendRoot/interchange.cfg.dist") {
+	else {
 		$Global::ExeName = 'interchange';
 		$Global::ConfigFile = 'interchange.cfg';
 	}
@@ -87,13 +69,17 @@
 
 	$Global::InitialErrorFile = $Global::ErrorFile = "$Global::VendRoot/error.log";
 
-	if($^O =~ /win32/i) {
+	if($^O =~ /cygwin|win32/i) {
 		$Global::Windows = 1;
 	}
 
 # Uncomment next line if you want to guarantee use of DB_File
 #$ENV{MINIVEND_DBFILE} = 1;
 
+# Uncomment next line in the unlikely event you want to ignore
+# GDBM and DB_File and force use of SDBM.
+#$ENV{MINIVEND_SDBM} = 1;
+
 # Uncomment next line if you want to guarantee use of GDBM and not DB_File
 #$ENV{MINIVEND_GDBM} = 1;
 
@@ -101,6 +87,10 @@
 # stored in files and databases in memory (or SQL)
 #$ENV{MINIVEND_NODBM} = 1;
 
+# Uncomment next line if you want the ability to use ALL DBM.
+# Otherwise we use only the first choice to save memory.
+#$ENV{MINIVEND_ALLDBM} = 1;
+
 # Uncomment next line if you DON'T want to use DBI, can
 # save a bit on code size
 #$ENV{MINIVEND_NO_DBI} = 1;
@@ -140,7 +130,11 @@
 require Exporter;
 
 BEGIN {
-	$VERSION = '4.6.5';
+	$VERSION = '4.9.7';
+
+	unless ($] >= 5.006) {
+		die "Interchange $VERSION requires Perl 5.6.0 or later,\nbut you're trying to run it under Perl $]. Exiting.\n";
+	}
 }
 
 use Fcntl;
@@ -148,8 +142,9 @@
 # BSD, among others, defines sendmail to be in /usr/sbin, and
 # we want to make sure the program is there. Insert the location
 # of you sendmail binary (the configure script should do this)
+$Global::SendMailLocation = '' if ! $Global::SendMailLocation;
 $Global::SendMailLocation = ($Global::Windows and $Global::SendMailLocation) ||
-	(-x $Global::SendMailLocation and $Global::SendMailLocation) ||
+	($Global::SendMailLocation and -x $Global::SendMailLocation and $Global::SendMailLocation) ||
 	(-x '/usr/lib/sendmail' and '/usr/lib/sendmail') ||
 	(-x '/usr/sbin/sendmail' and '/usr/sbin/sendmail') ||
 	'';
@@ -158,13 +153,14 @@
 #select a DBM
 
 BEGIN {
-	$Global::GDBM = $Global::DB_File =
+	$Global::GDBM = $Global::DB_File = $Global::SDBM =
 # LDAP
 	$Global::LDAP =
 # END LDAP
 # SQL
 	$Global::DBI =
 # END SQL
+    $Global::Shadow = 
 	0;
 
 # SQL
@@ -186,11 +182,20 @@
 		last AUTO if 
 			(defined $ENV{MINIVEND_DBFILE} and $Global::DB_File = 1);
 		last AUTO if 
+			(defined $ENV{MINIVEND_SDBM} and $Global::SDBM = 1);
+		last AUTO if 
 			(defined $ENV{MINIVEND_NODBM});
 		eval {require GDBM_File and $Global::GDBM = 1};
 		last AUTO if 
 			(defined $ENV{MINIVEND_GDBM} and $Global::GDBM = 1);
+		last AUTO if
+				!   $ENV{MINIVEND_ALLDBM}
+				and $Global::GDBM;
 		eval {require DB_File and $Global::DB_File = 1};
+		last AUTO if
+				!   $ENV{MINIVEND_ALLDBM}
+				and $Global::GDBM || $Global::DB_File;
+		eval {require SDBM_File and $Global::SDBM = 1};
 	}
 
 	if($Global::GDBM) {
@@ -207,9 +212,17 @@
 		$Global::Default_database = 'DB_FILE'
 			unless defined $Global::Default_database;
 	}
+	if($Global::SDBM) {
+		require Vend::Table::SDBM;
+		import SDBM_File;
+		$Global::SDBM = 1;
+		$Global::Default_database = 'SDBM'
+			unless defined $Global::Default_database;
+	}
 	$Global::Default_database = 'MEMORY'
 			unless defined $Global::Default_database;
 	require Vend::Table::InMemory;
+	require Vend::Table::Shadow;
 }
 
 
@@ -217,11 +230,12 @@
 use Vend::Server;
 use Vend::Session;
 use Vend::Config;
+use Vend::Payment;
 
 # You might try commenting out these lines and uncommenting the ones
 # below to compact memory size
 # NOAUTOUSE
-#use Vend::Order;
+use Vend::Order;
 #use Vend::Imagemap;
 #use Vend::Error;
 #use Vend::Control;
@@ -236,1644 +250,71 @@
 use autouse 'Vend::Control' => qw/
 											signal_reconfig
 											signal_add
+											signal_cron
 											signal_remove
 											control_interchange
-											change_catalog_directive
-											change_global_directive
 											remove_catalog
 											add_catalog
 											change_catalog_directive
 											change_global_directive
 									/;
-use autouse 'Vend::Order' => qw/
-											add_items
-											check_order
-											check_required
-											cyber_charge
-   										encrypt_standard_cc
-   										mail_order
-   										onfly
-   										route_order
-   										validate_whole_cc
-   								/;
+#use autouse 'Vend::Order' => qw/
+#											add_items
+#											check_order
+#											check_required
+#   										encrypt_standard_cc
+#   										mail_order
+#   										onfly
+#   										route_order
+#   										validate_whole_cc
+#   								/;
 
 # END AUTOUSE
 
-# GLIMPSE
-use Vend::Glimpse;
-# END GLIMPSE
-
 # TRACK
 use Vend::Track;
 # END TRACK
 
 use Vend::Scan;
-use Vend::TextSearch;
-use Vend::DbSearch;
 use Vend::Data;
 use Vend::UserDB;
 use Vend::Interpolate;
 use Vend::Page;
-use File::CounterFile;
-
-if( ! $Global::Windows and $> == -1 || scalar(getpwuid($>)) eq 'nobody' ) {
-	warn errmsg("\aYou probably don't want to run as nobody!\n");
-	sleep 1;
-	warn errmsg("The security problems are on your head, though. Continuing...\n");
-}
-
-my $H;
-sub http {
-	return $H;
-}
-
-sub response {
-	my ($output) = @_;
-	return 1 if $Vend::BuildingPages;
-	my $out = ref $output ? $output : \$output;
-	if (defined $Vend::CheckHTML) {
-		require Vend::External;
-		Vend::External::check_html($out);
-	}
-	$H->respond($out);
-}
-
-## DO ORDER
-
-# Order an item with product code CODE.
-
-sub do_order {
-    my($path) = @_;
-	my $code        = $CGI::values{mv_arg};
-#::logDebug("do_order: path=$path");
-	my $cart;
-	my $page;
-# LEGACY
-	if($path =~ s:/(.*)::) {
-		$cart = $1;
-		if($cart =~ s:/(.*)::) {
-			$page = $1;
-		}
-	}
-# END LEGACY
-	if(defined $CGI::values{mv_pc} and $CGI::values{mv_pc} =~ /_(\d+)/) {
-		$CGI::values{mv_order_quantity} = $1;
-	}
-	$CGI::values{mv_cartname} = $cart if $cart;
-	$CGI::values{mv_nextpage} = $page if $page;
-# LEGACY
-	$CGI::values{mv_nextpage} = $CGI::values{mv_orderpage}
-								|| find_special_page('order')
-		if ! $CGI::values{mv_nextpage};
-# END LEGACY
-	add_items($code);
-    return 1;
-}
-
-# Returns undef if interaction error
-sub update_quantity {
-    return 1 unless defined  $CGI::values{"quantity0"};
-	my($h, $i, $quantity, $modifier, $cart);
-
-	$cart = Vend::Cart::get_cart($CGI::values{mv_cartname});
-
-	if(ref $Vend::Cfg->{UseModifier}) {
-		foreach $h (@{$Vend::Cfg->{UseModifier}}) {
-			delete @{$::Values}{grep /^$h\d+$/, keys %$::Values};
-			foreach $i (0 .. $#$cart) {
-#::logDebug("updating line $i modifiers: " . ::uneval($cart->[$i]));
-				$modifier = $CGI::values{"$h$i"} || undef;
-				if (defined($modifier)) {
-					$modifier =~ s/\0+/\0/g;
-					$modifier =~ s/\0$//;
-					$modifier =~ s/^\0//;
-					$modifier =~ s/\0/, /g;
-					$cart->[$i]->{$h} = $modifier;
-					$::Values->{"$h$i"} = $modifier;
-					delete $CGI::values{"$h$i"};
-				}
-			}
-		}
-	}
-
-	foreach $i (0 .. $#$cart) {
-#::logDebug("updating line $i quantity: " . ::uneval($cart->[$i]));
-    	$quantity = $CGI::values{"quantity$i"};
-    	if (! defined $quantity) {
-        	interaction_error("Variable '$quantity' not passed from form\n");
-        	return undef;
-		}
-    	elsif ($quantity =~ m/^\d*$/) {
-        	$cart->[$i]->{'quantity'} = $quantity || 0;
-    	}
-    	elsif ($quantity =~ m/^[\d.]+$/
-				and $Vend::Cfg->{FractionalItems} ) {
-        	$cart->[$i]->{'quantity'} = $quantity;
-    	}
-		# This allows a multiple input of item quantity to
-		# pass -- FIRST ONE CONTROLS
-		elsif ($quantity =~ s/\0.*//) {
-			$CGI::values{"quantity$i"} = $quantity;
-			redo;
-		}
-		else {
-			my $item = $cart->[$i]->{'code'};
-        	interaction_error("'$quantity' for item $item is not numeric\n");
-        	return undef;
-    	}
-    	$::Values->{"quantity$i"} = delete $CGI::values{"quantity$i"};
-    }
-#::logDebug("after update, cart is: " . ::uneval($cart));
-
-	# If the user has put in "0" for any quantity, delete that item
-    # from the order list.
-    Vend::Cart::toss_cart($cart);
-
-#::logDebug("after toss, cart is: " . ::uneval($cart));
-
-	1;
-
-}
-
-sub set_db {
-	my ($base, $thing) = @_;
-	return ($base, $thing) unless $thing =~ /^(\w+):+(.*)/;
-	my $t = $1;
-	my $c = $2;
-	$Vend::WriteDatabase = 1 if $::Scratch->{mv_data_enable} =~ /\b$t\b/;
-	my $db = ::database_exists_ref($t);
-	return undef unless $db;
-	return ($db->ref(), $c);
-}
-
-## Update the user-entered fields.
-sub update_data {
-	my($key,$value);
-    # Update a database record
-
-	# Check to see if this is allowed
-	if(! $::Scratch->{mv_data_enable}) {
-		logError(
-			 "Attempted database update without permission, table=%s key=%s.",
-			 $CGI::values{mv_data_table},
-			 $CGI::values{$CGI::values{mv_data_key}},
-		);
-		return undef;
-	}
-	unless (defined $CGI::values{mv_data_table} and 
-		    defined $CGI::values{mv_data_key}      ) {
-		logError("Attempted database operation without table, fields, or key.\n" .
-					 "Table: '%s'\n" .
-					 "Fields:'%s'\n" .
-					 "Key:   '%s'\n",
-					 $CGI::values{mv_data_table},
-					 $CGI::values{mv_data_fields},
-					 $CGI::values{mv_data_key},
-				 );
-
-		return undef;
-	}
-
-	my $function	= lc (delete $CGI::values{mv_data_function});
-	if($function eq 'delete' and ! delete $CGI::values{mv_data_verify}) {
-		logError("update_data: DELETE without VERIFY, abort");
-		return undef;
-	}
-	my $table		= $CGI::values{mv_data_table};
-	my $prikey		= $CGI::values{mv_data_key};
-	my $decode		= is_yes($CGI::values{mv_data_decode});
-	my ($ref, $db, $database);
-
-	$ref = $Vend::Cfg->{Database}->{$table} || '';
-
-	if (! $ref) {
-		logError("set: non-existent table %s", $table);
-		return undef;
-	}
-	$Vend::WriteDatabase{$table} = 1;
-
-    my $base_db = database_exists_ref($table)
-        or die "Not a defined database '$table': $!\n";
-    $base_db = $base_db->ref();
-
-	my @fields		= grep $_ && $_ ne $prikey,
-						split /[\s\0,]+/, $CGI::values{mv_data_fields};
-	unshift(@fields, $prikey);
-	$function = 'update' unless $function;
-
-    my @file_fields = split /[\s\0,]+/, $CGI::values{mv_data_file_field};
-    my @file_paths = split /[\s\0,]+/, $CGI::values{mv_data_file_path};
-    my @file_oldfiles = split /[\s\0,]+/, $CGI::values{mv_data_file_oldfile};
-
-	my (%data);
-	for(@fields) {
-		$data{$_} = [];
-	}
-
-    while (($key, $value) = each %CGI::values) {
-        next unless defined $data{$key};
-		@{$data{$key}} = split /\0/, $value;
-	}
-
-    if(@file_fields) {
-	    my $Tag = new Vend::Tags;
-		my $acl_func;
-        my $outfile;
-
-		if($Vend::Session->{logged_in} and $Vend::admin) {
-			$acl_func = sub {
-				return $Tag->if_mm('files', shift);
-			};
-		}
-		elsif($Vend::Session->{logged_in} and ! $Vend::admin) {
-			$acl_func = sub {
-				my $file = shift;
-				return 1 if $::Scratch->{$file} == 1;
-				return $Tag->userdb(
-								function => 'check_file_acl',
-								location => $file,
-								mode => 'w'
-								);
-			};
-		}
-		else {
-			$acl_func = sub { return $::Scratch->{shift(@_)} == 1 }
-		}
- 
-	    for (my $i = 0; $i < @file_fields; $i++) {
-    	    unless (length($data{$file_fields[$i]}->[0])) {
-        	    # no need for a file update
-            	$data{$file_fields[$i]}->[0] = $file_oldfiles[$i];
-	            next;
-    	    }
-
-        	# remove path components
-	        $data{$file_fields[$i]}->[0] =~ s/.*\\//; 
-
-    	    if (length ($file_paths[$i])) {
-        	    # real file upload
-            	$outfile = join('/', $file_paths[$i], $data{$file_fields[$i]}->[0]);
-#::logDebug("file upload: field=$file_fields[$i] path=$file_paths[$i] outfile=$outfile");
-				my $ok;
-				if (-f $outfile) {
-					eval {
-						$ok = $acl_func->($outfile);
-					};
-				} else {
-					eval {
-						$ok = $acl_func->($file_paths[$i]);
-					};
-				}
-				if (! $ok) {
-					if($@) {
-						::logError ("ACL function failed on '%s': %s", $outfile, $@);
-					}
-					else {
-						::logError ("Not allowed to upload \"%s\"", $outfile);
-					}
-					next;
-				} 
-				my $err;
-				Vend::Interpolate::tag_value_extended(
-										$file_fields[$i],
-										{
-											test => 'isfile'
-										}
-										)
-					or do {
-						 ::logError("%s is not a file.", $data{$file_fields[$i]}->[0]);
-						 next;
-					};
-				Vend::Interpolate::tag_value_extended(
-										$file_fields[$i],
-										{
-											outfile => $outfile,
-											umask => '022',
-											yes => '1',
-										}
-										)
-					or do {
-						 ::logError("failed to write %s: %s", $outfile, $!);
-						 next;
-					};
-        	}
-			else {
-            	# preparing to dump file contents into database column
-	            $data{$file_fields[$i]}->[0]
-    	            = Vend::Interpolate::tag_value_extended ($file_fields[$i],
-        	            {file_contents => 1});
-	        }
-    	}
-	}
-
-    if ($function eq 'insert' && $base_db->config('AUTO_INCREMENT')) {
-        # special insertion case => key not needed
-        my (@k, @v);
-        
-		for(keys %data) {
-            next if $_ eq $prikey && length($data{$_}->[0]) == 0;
-			next unless (length($value = $data{$_}->[0]) || $CGI::values{mv_update_empty});
-			push(@k, $_);
-# LEGACY
-			HTML::Entities::decode($value) if $decode;
-# END LEGACY
-			if(defined $CGI::values{"mv_data_filter_$_"}) {
-				$value = Vend::Interpolate::filter_value(
-							 $CGI::values{"mv_data_filter_$_"},
-							 $value,
-							 0
-							 );
-			}
-			push(@v, $value);
-		}
-        my $func = $base_db->row_settor(@k);
-        return &$func(@v);
-    }
-
-	if (not defined $data{$prikey}) {
-		logError("No key '%s' in field specifier %s", $prikey, 'mv_data_fields');
-		return undef;
-	}
-	elsif ( ! @{$data{$prikey}}) {
-		logError("No key '%s' found for function='%s' table='%s'",
-					$prikey, $function, $CGI::values{mv_data_table},
-					);
-		return undef;
-	}
-
-	my ($query,$i);
-	my (@k);
-	my (@v);
-	my (@c);
-#::logDebug("update_data:db=$db key=$prikey VALUES=" . ::uneval(\%CGI::values));
-	my $select_key;
-	for($i = 0; $i < @{$data{$prikey}}; $i++) {
-		@k = (); @v = ();
-		for(keys %data) {
-			next unless (length($value = $data{$_}->[$i]) || $CGI::values{mv_update_empty} );
-			push(@k, $_);
-# LEGACY
-			HTML::Entities::decode($value) if $decode;
-# END LEGACY
-			if(defined $CGI::values{"mv_data_filter_$_"}) {
-				$value = Vend::Interpolate::filter_value(
-							 $CGI::values{"mv_data_filter_$_"},
-							 $value,
-							 $i,
-							 );
-			}
-			$select_key = $value if $_ eq $prikey;
-			push(@v, $value);
-		}
-
-		if($function eq 'delete') {
-			$base_db->delete_record($select_key);
-		}
-		else {
-			my $field;
-			$key = $data{$prikey}->[$i];
-			while($field = shift @k) {
-				$value = shift @v;
-				next if $field eq $prikey;
-				my ($d, $f) = set_db($base_db, $field);
-#::logDebug("update_data:db=$d key=$key field=$f value=$value");
-				$d->set_field($key, $f, $value);
-			}
-		}
-	}
-
-	if($CGI::values{mv_auto_export}) {
-		Vend::Data::export_database($table);
-	}
-	return;
-}
-
-# Parse the mv_click and mv_check special variables
-sub parse_click {
-	my ($ref, $click, $extra) = @_;
-    my($codere) = '[-\w_#/.]+';
-	my $params;
-
-#::logDebug("Looking for click $click");
-	if($params = $::Scratch->{$click}) {
-		# Do nothing, we found the click
-#::logDebug("Found scratch click $click = |$params|");
-	}
-	elsif(defined ($params = $Vend::Cfg->{OrderProfileName}{$click}) ) {
-		# Do nothing, we found the click
-		$params = $Vend::Cfg->{OrderProfile}[$params];
-#::logDebug("Found profile click $click = |$params|");
-	}
-	elsif(defined ($params = $Global::ProfilesName->{$click}) ) {
-		# Do nothing, we found the click
-		$params = $Global::Profiles->[$params];
-#::logDebug("Found profile click $click = |$params|");
-	}
-	elsif($params = $::Scratch->{"mv_click $click"}) {
-		$::Scratch->{mv_click_arg} = $click;
-	}
-	elsif($params = $::Scratch->{mv_click}) {
-		$::Scratch->{mv_click_arg} = $click;
-	}
-	else {
-#::logDebug("Found NO click $click");
-		return 1;
-	} # No click processor
-
-	my($var,$val,$parameter);
-	$params = interpolate_html($params);
-	my(@param) = split /\n+/, $params;
-
-	for(@param) {
-		next unless /\S/;
-		next if /^\s*#/;
-		s/^[\r\s]+//;
-		s/[\r\s]+$//;
-		$parameter = $_;
-		($var,$val) = split /[\s=]+/, $parameter, 2;
-		$val =~ s/&#(\d+);/chr($1)/ge;
-		$ref->{$var} = $val;
-		$extra->{$var} = $val
-			if defined $extra;
-	}
-}
+use Vend::CounterFile;
+use Vend::Dispatch;
 
-# This is the set of CGI-passed variables to ignore, in other words
-# never set in the user session.  If set in the mv_check pass, though,
-# they will stick.
-my %Ignore = qw(
-	mv_todo  1
-	mv_todo.submit.x  1
-	mv_todo.submit.y  1
-	mv_todo.return.x  1
-	mv_todo.return.y  1
-	mv_todo.checkout.x  1
-	mv_todo.checkout.y  1
-	mv_todo.todo.x  1
-	mv_todo.todo.y  1
-	mv_todo.map  1
-	mv_doit  1
-	mv_check  1
-	mv_click  1
-	mv_nextpage  1
-	mv_more_ip  1
-	mv_credit_card_number  1
-	);
-
-sub update_values {
-
-	if( $Vend::Cfg->{CreditCardAuto} and $CGI::values{mv_credit_card_number} ) {
-		(
-			@{$::Values}{
-				qw/
-						mv_credit_card_valid
-						mv_credit_card_info
-						mv_credit_card_exp_month
-						mv_credit_card_exp_year
-						mv_credit_card_exp_all
-						mv_credit_card_type
-						mv_credit_card_reference
-						mv_credit_card_error
-				/ }
-		) = encrypt_standard_cc(\%CGI::values);
-	}	
-
-	my ($key, $value);
-    while (($key, $value) = each %CGI::values) {
-        next if defined $Ignore{$key};
-        next if defined $Vend::Cfg->{FormIgnore}->{$key};
-        next if ($key =~ m/^quantity\d+$/);
-		# We add any checkbox ordered items, but don't update -- 
-		# we don't want to order them twice
-        $::Values->{$key} = $value;
-    }
-}
-
-sub update_user {
-	my($key,$value);
-    # Update the user-entered fields.
-
-	add_items() if defined $CGI::values{mv_order_item};
-	update_values();
-
-	if($CGI::values{mv_check}) {
-		my(@checks) = split /\s*[,\0]+\s*/, delete $CGI::values{mv_check};
-		my($check);
-		foreach $check (@checks) {
-				parse_click $::Values, $check, \%CGI::values;	
-		}
-	}
-
-	check_save if defined $CGI::values{mv_save_session};
-
-}
-
-## DO PROCESS
-
-sub do_click {
-	my($click, @clicks);
-	if(defined $CGI::values{mv_click}) {
-		@clicks = split /\s*[\0]+\s*/, $CGI::values{mv_click};
-	}
-
-	if(defined $CGI::values{mv_click_map}) {
-		my(@map) = split /\s*[\0]+\s*/, $CGI::values{mv_click_map};
-		foreach $click (@map) {
-			push (@clicks, $click)
-				if defined $CGI::values{"mv_click.$click.x"}
-				or defined $CGI::values{"$click.x"}
-				or $click = $CGI::values{"mv_click_$click"};
-		}
-	}
-
-	foreach $click (@clicks) {
-		parse_click \%CGI::values, $click;
-	}
-	return 1;
-}
-
-sub do_deliver {
-	my $file = $CGI::values{mv_data_file};
-	my $mode = $CGI::values{mv_acl_mode} || '';
-	if($::Scratch->{mv_deliver} !~ m{(^|\s)$file(\s|$)}
-		and 
-		! Vend::UserDB::userdb(
-							'check_file_acl',
-							location => $file,
-							mode => $mode,
-							)
-		)
-	{
-		$Vend::StatusLine = "Status: 403\nContent-Type: text/html";
-		my $msg = get_locale_message(403, <<EOF);
-<B>Authorization Required<B>
-<P>
-This server could not verify that you are authorized to access the document
-requested. 
-EOF
-		::response($msg);
-		return 0;
-	}
-
-	if (! -f $file) {
-		$Vend::StatusLine = "Status: 404\nContent-Type: text/html";
-		my $msg = get_locale_message(404, <<EOF, $file);
-<B>Not Found<B>
-<P>
-The requested file %s was not found on this server.
-
-EOF
-		::response($msg);
-		return 0;
-	}
-
-	$Vend::StatusLine = "Content-Type: " .
-						($CGI::values{mv_content_type} || 'application/octet-stream');
-	::response(	Vend::Util::readfile (
-					$CGI::values{mv_data_file},
-					$Global::NoAbsolute,
-				)
+if($ENV{INTERCHANGE_REQUIRE}) {
+	my @mods = split /[;\s]+/, $ENV{INTERCHANGE_REQUIRE};
+	foreach my $mod (@mods) {
+		eval {
+			eval "require $mod";
+			die $@ if $@;
+		};
+		if($@) {
+			die errmsg(
+				"FAILED to require module %s as specified in environment. Error: %s\n", 
+				$mod,
+				$@,
 			);
-	return 0;
-}
-
-my %form_action = (
-
-	search	=> \&do_search,
-	deliver	=> \&do_deliver,
-	submit	=>
-				sub {
-					update_user();
-					update_quantity()
-						or return interaction_error("quantities");
-					my $ok;
-					my($missing,$next,$status,$final);
-
-					# Set shopping cart if necessary
-					# Vend::Items is tied, remember!
-					$Vend::Items = $CGI::values{mv_cartname}
-						if $CGI::values{mv_cartname};
-
-				  CHECK_ORDER: {
-
-					# If the user sets this later, will be used
-					delete $Vend::Session->{mv_order_number};
-
-					if (defined $CGI::values{mv_order_profile}) {
-						($status,$final,$missing) =
-							check_order($CGI::values{mv_order_profile});
-					}
-					else {
-						$status = $final = 1;
-					}
-
-					my $provisional;
-					if ($status and defined $CGI::values{mv_order_route}) {
-						# This checks only route order profiles
-#::logDebug("Routing order, pre-check");
-						($status, $provisional, $missing) = route_order(
-												$CGI::values{mv_order_route},
-												$Vend::Items,
-												'check',
-											);
-					} 
-
-					$final = $provisional if ! $final;
-
-#::logDebug("Routing status status=$status final=$final errors=$missing");
-					if($status) {
-						$CGI::values{mv_nextpage} = $::Values->{mv_successpage} 
-							if $::Values->{mv_successpage};
-						$CGI::values{mv_nextpage} = $::Values->{mv_orderpage} 
-							if ! $CGI::values{mv_nextpage};
-					}
-					else {
-						$CGI::values{mv_nextpage} = $::Values->{mv_failpage}
-							if $::Values->{mv_failpage};
-						$CGI::values{mv_nextpage} = find_special_page('needfield')
-							if ! $CGI::values{mv_nextpage};
-						undef $final;
-					}
-
-					return 1 unless $final;
-
-					my $order_no;
-					if (defined $CGI::values{mv_order_route}) {
-						# $ok will not be defined unless Route "supplant" was set
-						# $order_no will come back so we don't issue two of them
-#::logDebug("Routing order");
-						($ok, $order_no) = route_order(
-											$CGI::values{mv_order_route},
-											$Vend::Items
-											);
-					}
-					my $mode = $CGI::values{mv_payment_mode};
-					if (! $ok and defined $Vend::Cfg->{ActionMap}{$mode}) {
-						($ok, $status) = $Vend::Cfg->{ActionMap}{$mode}->();
-					}
-					elsif(
-							$Vend::Cfg->{CyberCash}
-							and defined $CGI::values{mv_cyber_mode}
-						)
-					{
-#::logDebug("Cyber charge");
-						$status = cyber_charge();
-						unless($status) {
-							$CGI::values->{mv_nextpage} = find_special_page('failed')
-								if ! $CGI::values->{mv_nextpage};
-							return 1;
-						}
-					}
-
-					# This function (followed down) now does the rudimentary
-					# backend ordering with AsciiTrack and the order report.
-					# If the "supplant" option was set in order routing it will
-					# not be used ($ok would have been defined)
-
-# TRACK
-                    $Vend::Track->finish_order ();
-# END TRACK
-
-#::logDebug("Order number=$order_no\n");
-					$ok = mail_order(undef, $order_no || undef) unless defined $ok;
-#::logDebug("Order number=$order_no\n");
-
-					# Display a receipt if configured
-
-					if ($ok) {
-						eval {
-							display_special_page(
-											$::Values->{mv_order_receipt}	||
-											find_special_page('receipt')
-											);
-						};
-						if($@) {
-							my $msg = $@;
-							::logError( 
-								'Display of receipt on order number %s failed: %s',
-								$::Values->{mv_order_number},
-								$msg,
-							);
-						}
-					}
-					else {
-						display_special_page(
-								find_special_page('failed'),
-								errmsg('Error transmitting order(%s): %s', $!, $@),
-						);
-					}
-
-					# Remove the items
-					@$Vend::Items = ();
-					put_session();
-					return 0;
-				  }
-
-			},
-	refresh	=> sub {
-					update_quantity()
-						or return interaction_error("quantities");
-# LEGACY
-					$CGI::values{mv_nextpage} = $CGI::values{mv_orderpage}
-						if $CGI::values{mv_orderpage};
-# END LEGACY
-					$CGI::values{mv_nextpage} = $CGI::values{mv_orderpage}
-												|| find_special_page('order')
-						if ! $CGI::values{mv_nextpage};
-					update_user();
-					return 1;
-				},
-	set		=> sub {
-					update_user();
-					update_data();
-					return 1;
-				},
-	back    => sub { return 1 },
-	return	=> sub {
-					update_user();
-					update_quantity()
-						or return interaction_error("quantities");
-					return 1;
-				},
-	cancel	=> sub {
-					put_session();
-					get_session();
-					init_session();
-					$CGI::values{mv_nextpage} = find_special_page('canceled')
-						if ! $CGI::values{mv_nextpage};
-					return 1;
-				},
-);
-
-$form_action{go} = $form_action{return};
-
-# Process the completed order or search page.
-
-sub do_process {
-
-	do_click();
-
-    my $todo = $CGI::values{mv_todo};
-
-	# Maybe we have an imagemap input, if not, use $doit
-    if ( ! defined $todo) {
-		if (defined $CGI::values{'mv_todo.x'}) {
-				my $x = $CGI::values{'mv_todo.x'};
-				my $y = $CGI::values{'mv_todo.y'};
-				my $map = $CGI::values{'mv_todo.map'};
-				# Called with action_map and not package id
-				# since "autouse" is possibly in force...found
-				# by Jeff Carnahan
-				$todo = action_map($x,$y,$map);
-		}
-		elsif (defined $CGI::values{'mv_todo.submit.x'}) {
-			$todo = 'submit';
-		}
-		elsif (defined $CGI::values{'mv_todo.checkout.x'}) {
-			$todo = 'checkout';
-		}
-		elsif (defined $CGI::values{'mv_todo.return.x'}) {
-			$todo = 'return';
 		}
 		else {
-			$todo = $CGI::values{mv_doit} if defined $CGI::values{mv_doit};
-		}
-	}
-
-	my ($sub, $status);
-	#Now determine the action on the todo
-    if (defined $Vend::Cfg->{FormAction}{$todo}) {
-		$sub = $Vend::Cfg->{FormAction}{$todo};
-		new Vend::Parse;
-	}
-    elsif (not $sub = $form_action{$todo} ) {
-		interaction_error("No action passed for processing\n");
-		return;
-    }
-	eval {
-		$status = $sub->($todo);
-	};
-	if($@) {
-		undef $status;
-		my $err = $@;
-		my $template = <<EOF;
-Sorry, there was an error in processing this form action. Please 
-report the error or try again later.
-EOF
-		$template .= "\n\nError: %s\n"
-				if $Global::DisplayErrors && $Vend::Cfg->{DisplayErrors}
-			;
-		logError ("Error in form action: $err");
-		$template = get_locale_message(500, $template, $err);
-		$template .= "($err)";
-		::response($template);
-	}
-
-	return $status;
-}
-
-sub config_named_catalog {
-	my ($cat_name, $source, $build) = @_;
-	my ($g,$c,$conf);
-
-	$g = $Global::Catalog{$cat_name};
-	unless (defined $g) {
-		logGlobal( "Can't find catalog '%s'" , $cat_name );
-		return undef;
-	}
-
-	$Vend::Log_suppress = 1;
-    logGlobal( "Config '%s' %s", $g->{'name'}, $source )
-		unless $Vend::Quiet;
-	undef $Vend::Log_suppress;
-
-    chdir $g->{'dir'}
-            or die "Couldn't change to $g->{'dir'}: $!\n";
-    $conf = $g->{'dir'} . '/etc';
-    eval {
-        $c = config($g->{'name'},
-					$g->{'dir'},
-					$conf,
-					$g->{'base'} || undef,
-# OPTION_EXTENSION
-#					$Vend::CommandLine->{$g->{'name'}} || undef
-# END OPTION_EXTENSION
-					);
-    };
-
-    if($@) {
-		my $msg = $@;
-        logGlobal( "%s config error: %s" , $g->{'name'}, $msg );
-     	return undef;
-    }
-
-	return $c if defined $g->{'base'};
-
-	eval {
-		$Vend::Cfg = $c;	
-# STATICPAGE
-	READSTATIC: {
-			my $basedir = $c->{PageDir};
-			if ($c->{Static}) {
-				last READSTATIC if $c->{StaticDBM};
-				last READSTATIC if ! -f "$basedir/.static";
-				print "loading static page names..." unless $Vend::Quiet;
-				last READSTATIC if $c->{StaticDBM};
-				open STATICPAGE, "< $basedir/.static"
-					or warn <<EOF;
-Couldn't read static page status file $basedir/.static: $!
-EOF
-				while(<STATICPAGE>) {
-					chomp;
-					s/\t(.*)//;
-					$c->{StaticPage}->{$_} = $1 || '';
-				}
-				close STATICPAGE;
-			}
-		}
-# END STATICPAGE
-		$::Variable = $Vend::Cfg->{Variable};
-		Vend::Data::read_salestax();
-		Vend::Data::read_shipping();
-		open_database(1);
-		my $db;
-
-		LREAD: {
-			last LREAD unless $db = $Vend::Cfg->{LocaleDatabase};
-			$db = database_exists_ref($db)
-				or last LREAD;
-			$db = $db->ref();
-			my ($k, @f);	# key and fields
-			my @l;			# refs to locale repository
-			my @n;			# names of locales
-
-			@n = $db->columns();
-			my $extra;
-			for(@n) {
-				$Vend::Cfg->{Locale_repository}{$_} = {}
-					unless $Vend::Cfg->{Locale_repository}{$_};
-				push @l, $Vend::Cfg->{Locale_repository}{$_};
-			}
-			my $i;
-			while( ($k , @f ) = $db->each_record) {
-				for ($i = 0; $i < @f; $i++) {
-					next unless length($f[$i]);
-					$l[$i]->{$k} = $f[$i];
-				}
-			}
-			unless ($Vend::Cfg->{Locale}) {
-				for(@n) {
-					next unless $Vend::Cfg->{Locale_repository}{$_}{'default'};
-					$Vend::Cfg->{DefaultLocale} = $_;
-					$Vend::Cfg->{Locale} = $Vend::Cfg->{Locale_repository}{$_};
-					last;
-				}
-				unless ($Vend::Cfg->{Locale}) {
-					$Vend::Cfg->{Locale} = $Vend::Cfg->{Locale_repository}{$n[0]};
-					$Vend::Cfg->{DefaultLocale} = $n[0];
-				}
-			}
+			warn errmsg(
+				"Required module %s successfully as specified in environment.\n", 
+				$mod,
+			);
 		}
-
-		close_database();
-	};
-
-	undef $Vend::Cfg;
-	undef $Vend::BuildingPages;  # In case of eval error
-    if($@) {
-		my $msg = $@;
-		$msg =~ s/\s+$//;
-        logGlobal( "%s config error: %s" , $g->{'name'}, $msg );
-     	return undef;
-    }
-
-	if ($c->{IPC}) {
-		my $dir = '.';
-		$dir = $c->{IPCdir} if $c->{IPCdir};
-		dump_structure($c, "$dir/$g->{name}");
-		chmod($c->{IPCmode} | 0644 , "$dir/$g->{name}")
-	}
-	dump_structure($c, $g->{name}) if $Global::DumpStructure;
-
-	undef $c->{Source};
-	my $stime = scalar localtime();
-	Vend::Util::writefile(">$Global::ConfDir/status.$g->{name}", "$stime\n");
-	Vend::Util::writefile(">$c->{ConfDir}/status.$g->{name}", "$stime\n");
-
-	return $c;
-
-}
-
-sub is_retired {
-	my $id = shift;
-	mkdir "$Vend::Cfg->{ScratchDir}/retired", 0777
-		unless -d "$Vend::Cfg->{ScratchDir}/retired";
-	my $fn = Vend::Util::get_filename($id, 2, 1, "$Vend::Cfg->{ScratchDir}/retired");
-	return -f $fn ? 1 : 0;
-}
-
-sub retire_id {
-	my $id = shift;
-	return unless $id =~ /^\w+$/;
-	mkdir "$Vend::Cfg->{ScratchDir}/retired", 0777
-		unless -d "$Vend::Cfg->{ScratchDir}/retired";
-	my $fn = Vend::Util::get_filename($id, 2, 1, "$Vend::Cfg->{ScratchDir}/retired");
-	open(TMPRET, ">$fn")
-		or die "retire id open: $!\n";
-	close(TMPRET);
-	return;
-}
-
-sub tie_static_dbm {
-	my $rw = shift;
-	untie(%Vend::StaticDBM) if $rw;
-	if($Global::GDBM) {
-        my $flags = $rw ? &GDBM_WRITER : &GDBM_READER;
-        $flags = &GDBM_NEWDB
-            if $rw && (! -f "$Vend::Cfg->{StaticDBM}.gdbm" || $Vend::BuildingPages);
-        tie(%Vend::StaticDBM,
-            'GDBM_File',
-            "$Vend::Cfg->{StaticDBM}.gdbm",
-            $flags,
-            $Vend::Cfg->{'FileCreationMask'},
-        )
-        or $Vend::Cfg->{SaveStaticDBM} = delete $Vend::Cfg->{StaticDBM};
-	}
-	elsif ($Global::DB_File) {
-		tie(%Vend::StaticDBM,
-			'DB_File',
-			"$Vend::Cfg->{StaticDBM}.db",
-			($rw ? &O_RDWR | &O_CREAT : &O_RDONLY),
-			$Vend::Cfg->{'FileCreationMask'},
-			)
-		or undef $Vend::Cfg->{StaticDBM};
-	}
-	else {
-        $Vend::Cfg->{SaveStaticDBM} = delete $Vend::Cfg->{StaticDBM};
-	}
-	::logError("Failed to create StaticDBM %s", $Vend::Cfg->{StaticDBM})
-		if $rw && ! $Vend::Cfg->{StaticDBM};
-	return $Vend::Cfg->{StaticDBM} || undef;
-}
-
-
-sub adjust_cgi {
-
-    my($host);
-
-    die "REQUEST_METHOD is not defined" unless defined $CGI::request_method
-		or @Global::argv;
-
-	# The great and really final AOL fix
-	#
-    $host      = $CGI::remote_host;
-    $CGI::ip   = $CGI::remote_addr;
-
-	if($Global::DomainTail and $host) {
-		$host =~ s/.*?([-A-Za-z0-9]+\.[A-Za-z]+)$/$1/;
-	}
-	elsif($Global::IpHead) {
-		$host = $Global::IpQuad == 0 ? 'nobody' : '';
-		my @ip;
-		@ip = split /\./, $CGI::ip;
-		$CGI::ip = '';
-		$CGI::ip = join ".", @ip[0 .. ($Global::IpQuad - 1)] if $Global::IpQuad;
-	}
-	#
-	# end AOL fix
-
-	# Fix Cobalt/CGIwrap problem
-    if($Global::Variable->{CGIWRAP_WORKAROUND}) {
-        $CGI::path_info =~ s!^$CGI::script_name!!;
-    }
-
-    $CGI::host = $host || $CGI::ip;
-
-    $CGI::user = $CGI::remote_user if $CGI::remote_user;
-	undef $CGI::authorization if $CGI::remote_user;
-	$Vend::Cookie = $CGI::cookie;
-
-	unless ($Global::FullUrl) {
-		$CGI::script_name = $CGI::script_path;
-	}
-	else {
-		if($CGI::server_port eq '80') { $CGI::server_port = ''; }
-		else 		{ $CGI::server_port = ":$CGI::server_port"; }
-		$CGI::script_name = $CGI::server_name .
-							$CGI::server_port .
-							$CGI::script_path;
-	}
-}
-
-
-sub url_history {
-	$Vend::Session->{History} = []
-		unless defined $Vend::Session->{History};
-	shift @{$Vend::Session->{History}}
-		if $#{$Vend::Session->{History}} >= $Vend::Cfg->{History};
-	if(
-		($CGI::pragma =~ /\bno-cache\b/ and ! $CGI::values{mv_force_cache})
-		or $CGI::values{mv_no_cache}
-		)
-	{
-		push (@{$Vend::Session->{History}},  [ 'expired', {} ]);
-	}
-	else {
-		my $save = delete $CGI::values{mv_credit_card_number};
-		push (@{$Vend::Session->{History}},  [ $CGI::path_info, \%CGI::values ]);
-		$CGI::values{mv_credit_card_number} = $save if length($save);
 	}
-	return;
 }
 
-## DISPATCH
-
-# Parse the invoking URL and dispatch to the handling subroutine.
-
-my %action = (
-    process	=> \&do_process,
-	ui_wrap => \&UI::Primitive::ui_wrap,
-    ui=> sub { 
-					&UI::Primitive::ui_acl_global();
-					\&do_process(@_);
-				   },
-    minimate=> sub { 
-					&MiniMate::CfgMgr::mm_acl_global;
-					\&do_process(@_);
-				   },
-    scan	=> \&do_scan,
-    search	=> \&do_search,
-    order	=> \&do_order,
-    obtain	=> \&do_order,
-);
-
-sub dispatch {
-	my($http) = @_;
-	$H = $http;
-	if($Vend::Foreground) {
-		Vend::Interpolate::reset_calc();
-	}
-#::logDebug ("begin dispatch: " . (join " ", times()) . "\n");
-#::logDebug ("begin dispatch, locale LC_CTYPE: " . POSIX::setlocale(POSIX::LC_CTYPE()) . "\n");
-
-	adjust_cgi();
-
-    my($sessionid);
-	my(@path);
-	my($g, $action);
-
-	unless (defined $Global::Selector{$CGI::script_name}) {
-		my $msg = get_locale_message(
-						403,
-						"Undefined catalog: %s",
-						$CGI::script_name,
-						);
-		$Vend::StatusLine = <<EOF;
-Status: 404 Not Found
-Content-Type: text/plain
-EOF
-		::response($msg);
-		logGlobal($msg);
-		return;
-	}
-	$Vend::Cfg = $Global::Selector{$CGI::script_name};
-
-## Uncomment this to get global directive setting on a per-catalog basis
-## Probably only useful for:
-##
-##   DebugFile
-##   DisplayErrors
-##   DomainTail
-##   ErrorLog
-##   FullUrl
-##   GlobalSub
-##   HitCount
-##   IpHead
-##   IpQuad
-##   Locale
-##   LockoutCommand
-##   NoAbsolute
-##   SafeUntrap
-##   UserTag
-##   Variable
-
-	my $catref = $Global::Catalog{$Vend::Cfg->{CatalogName}};
-	if(! $Vend::Foreground and defined $catref->{directive}) {
-		no strict 'refs';
-		my ($key, $val);
-		while ( ($key, $val) = each %{$catref->{directive}}) {
-#::logDebug("directive key=$key val=" . ::uneval($val));
-			${"Global::$key"} = $val;
-		}
-	}
-
-
-	# See if it is a subcatalog
-	if (defined $Vend::Cfg->{BaseCatalog}) {
-		my $name = $Vend::Cfg->{BaseCatalog};
-		my $ref = $Global::Catalog{$name};
-		my $c = $Vend::Cfg;
-		$Vend::Cfg = $Global::Selector{$ref->{'script'}};
-		for(keys %{$c->{Replace}}) {
-			undef $Vend::Cfg->{$_};
-		}
-		copyref $c, $Vend::Cfg;
-		if($Vend::Cfg->{Variable}{MV_LANG}) {
-			my $loc = $Vend::Cfg->{Variable}{MV_LANG};
-			$Vend::Cfg->{Locale} = $Vend::Cfg->{Locale_repository}{$loc}
-					if defined $Vend::Cfg->{Locale_repository}{$loc};
-		}
-		$Vend::Cfg->{StaticPage} = {}
-			unless $Vend::Cfg->{Static};
-	}
-	$::Variable = $Vend::Cfg->{Variable};
-
-
-	if (defined $Global::SelectorAlias{$CGI::script_name}
-		and ! defined $Vend::InternalHTTP                 )
-	{
-		my $real = $Global::SelectorAlias{$CGI::script_name};
-		if(defined $Vend::NoFork) {
-			$Vend::Save = {} unless $Vend::Save;
-			$Vend::Save->{VendURL}   = $Vend::Cfg->{VendURL};
-			$Vend::Save->{SecureURL} = $Vend::Cfg->{SecureURL};
-		}
-		unless (	$CGI::secure                                        or
-					$Vend::Cfg->{SecureURL} =~ m{$CGI::script_name$}     and
-					$Vend::Cfg->{VendURL}   !~ m{/nph-[^/]+$} 		     and
-					$Vend::Cfg->{VendURL}   !~ m{$CGI::script_name$} 		)
-		{
-			$Vend::Cfg->{VendURL}   =~ s!$real!$CGI::script_name!;
-			$Vend::Cfg->{SecureURL} =~ s!$real!$CGI::script_name!;
-		}
-	}
-	elsif ($Vend::InternalHTTP) {
-		$Vend::Cfg->{VendURL} = "http://" .
-								$CGI::http_host .
-								$CGI::script_path;
-		$Vend::Cfg->{ImageDir} = $Vend::Cfg->{ImageDirInternal}
-			if  $Vend::Cfg->{ImageDirInternal};
-	}
-
-	if($Global::HitCount) {
-		my $ctr = new File::CounterFile
-					"$Global::ConfDir/hits.$Vend::Cfg->{CatalogName}";
-        $ctr->inc();
-	}
-
-	if ($Vend::Cfg->{SetGroup}) {
-		eval {
-			$) = "$Vend::Cfg->{SetGroup} $Vend::Cfg->{SetGroup}";
-		};
-		if ($@) {
-			my $msg = $@;
-			logGlobal( "Can't set group to GID %s: %s",
-						$Vend::Cfg->{SetGroup}, $msg
-					);
-			logError("Can't set group to GID %s: %s",
-						$Vend::Cfg->{SetGroup}, $msg
-					);
-		}
-	}
-
-	chdir $Vend::Cfg->{VendRoot} 
-		or die "Couldn't change to $Vend::Cfg->{VendRoot}: $!\n";
-	set_file_permissions();
-# STATICPAGE
-	tie_static_dbm() if $Vend::Cfg->{StaticDBM};
-# END STATICPAGE
-	umask $Vend::Cfg->{Umask};
-	open_database();
-
-	$CGI::user = Vend::Util::check_authorization($CGI::authorization)
-		if defined $CGI::authorization;
-
-	my $from_cookie;
-	$sessionid = $CGI::values{mv_session_id} || undef;
-
-	if (defined $CGI::cookie and
-		 $CGI::cookie =~ /\bMV_SESSION_ID=(\w{8,32})
-								[:_] (
-									(	\d{1,3}\.   # An IP ADDRESS
-										\d{1,3}\.
-										\d{1,3}\.
-										\d{1,3})
-									# A user name or domain
-									|	([A-Za-z0-9][-\@A-Za-z.0-9]+) )?
-									\b/x)
-	{
-		$sessionid = $1
-			unless defined $CGI::values{mv_pc} and $CGI::values{mv_pc} eq 'RESET';
-		$CGI::cookiehost = $3 || undef;
-		$CGI::cookieuser = $4 || undef;
-		$from_cookie = 1;
-    }
-
-	$CGI::host = 'nobody' if $Vend::Cfg->{WideOpen};
-
-	if(! $sessionid) {
-		my $id = $::Variable->{MV_SESSION_ID};
-		$sessionid = $CGI::values{$id} if $CGI::values{$id};
-		if (! $sessionid and $Vend::Cfg->{FallbackIP}) {
-			$sessionid = generate_key($CGI::remote_addr . $CGI::useragent);
-		}
-	}
-	elsif ($sessionid !~ /^\w+$/) {
-		my $msg = get_locale_message(
-						403,
-						"Unauthorized for that session %s. Logged.",
-						$sessionid,
-						);
-		$Vend::StatusLine = <<EOF;
-Status: 403 Unauthorized
-Content-Type: text/plain
-EOF
-		::response($msg);
-		logGlobal($msg);
-		return;
-	}
-
-# DEBUG
-#::logDebug ("session='$sessionid' cookie='$CGI::cookie' chost='$CGI::cookiehost'");
-# END DEBUG
-
-RESOLVEID: {
-    if ($sessionid) {
-		$Vend::SessionID = $sessionid;
-    	$Vend::SessionName = session_name();
-		# get_session will return a value if a session is read,
-		# if not it will return false and a new session has been created.
-		# The IP address will be counted for robot_resolution
-		if(! get_session()) {
-			retire_id($sessionid);
-			last RESOLVEID;
-		}
-		my $now = time;
-		if(! $from_cookie) {
-			if( is_retired($sessionid) ) {
-				new_session();
-				last RESOLVEID;
-			}
-			my $compare_host	= $CGI::secure
-								? ($Vend::Session->{shost})
-								: ($Vend::Session->{ohost});
-
-			if(! $compare_host) {
-				new_session() unless $CGI::secure;
-				$Vend::Session->{shost} = $CGI::remote_addr;
-			}
-			elsif ($compare_host ne $CGI::remote_addr) {
-				new_session();
-			}
-		}
-		if ($now - $Vend::Session->{'time'} > $Vend::Cfg->{SessionExpire}) {
-			retire_id($sessionid);
-			new_session();
-			last RESOLVEID;
-		}
-		elsif($Vend::Cfg->{RobotLimit}) {
-			if ($now - $Vend::Session->{'time'} > 30) {
-				$Vend::Session->{accesses} = 0;
-			}
-			else {
-				$Vend::Session->{accesses}++;
-				if($Vend::Session->{'accesses'} > $Vend::Cfg->{RobotLimit}) {
-					my $msg = errmsg(
-			"WARNING: POSSIBLE BAD ROBOT. %s accesses with no 30 second pause.",
-			$Vend::Session->{accesses},
-					);
-					do_lockout($msg);
-				}
-			}
-		}
-    }
-	else {
-		if($Vend::Cfg->{RobotLimit}) {
-			if (Vend::Session::count_ip() > $Vend::Cfg->{RobotLimit}) {
-				my $msg;
-				# Here they can get it back if they pass expiration time
-				my $wait = $Global::Variable->{MV_ROBOT_EXPIRE} || 86400;
-				$wait /= 3600;
-				$msg = errmsg(<<EOF, $wait); 
-Too many new ID assignments for this IP address. Please wait at least %d hours
-before trying again. Only waiting that period will allow access. Terminating.
-EOF
-				$msg = Vend::Page::get_locale_message(403, $msg);
-				do_lockout($msg);
-				$Vend::StatusLine = <<EOF;
-Status: 403 Forbidden
-Content-Type: text/plain
-EOF
-					::response($msg);
-					return;
-			}
-		}
-		new_session();
-    }
+if( ! $Global::Windows and $> == -1 || scalar(getpwuid($>)) eq 'nobody' ) {
+	warn errmsg("\aYou probably don't want to run as nobody!\n");
+	sleep 1;
+	warn errmsg("The security problems are on your head, though. Continuing...\n");
 }
 
-#::logDebug("session name='$Vend::SessionName'\n");
-
-	$Vend::Interpolate::Calc_initialized = 0;
-	$CGI::values{mv_session_id} = $Vend::Session->{id} = $Vend::SessionID;
-
-	if($Vend::Cfg->{CookieLogin}) {
-		COOKIELOGIN: {
-			last COOKIELOGIN if $Vend::Session->{logged_in};
-			last COOKIELOGIN if defined $CGI::values{mv_username};
-			last COOKIELOGIN unless
-				$CGI::values{mv_username} = Vend::Util::read_cookie('MV_USERNAME');
-			my $password;
-			last COOKIELOGIN unless
-				$password = Vend::Util::read_cookie('MV_PASSWORD');
-			$CGI::values{mv_password} = $password;
-			my $profile = Vend::Util::read_cookie('MV_USERPROFILE');
-			local(%SIG);
-			undef $SIG{__DIE__};
-			eval {
-				Vend::UserDB::userdb('login', profile => $profile );
-			};
-			if($@) {
-				$Vend::Session->{failure} .= $@;
-			}
-		}
-	}
-
-	$Vend::Session->{'arg'} = $Vend::Argument = ($CGI::values{mv_arg} || undef);
-#::logDebug("arg is $Vend::Session->{arg}");
-	if($CGI::values{mv_pc} and $CGI::values{mv_pc} =~ /[A-Za-z]/) {
-		$Vend::Session->{'source'} =	$CGI::values{mv_pc} eq 'RESET'
-										? ''
-										: $CGI::values{mv_pc};
-	}
-
-	$Vend::Session->{'user'} = $CGI::user;
-
-	undef $Vend::Cookie if 
-		$Vend::Session->{logged_in} && ! $Vend::Cfg->{StaticLogged};
-
-	$CGI::pragma = 'no-cache'
-		if delete $::Scratch->{mv_no_cache};
-
-	$Vend::FinalPath = $Vend::Session->{last_url} = $CGI::path_info;
-	if(	defined $Vend::Session->{one_time_path_alias}{$Vend::FinalPath} ) {
-		$CGI::path_info
-					= $Vend::FinalPath
-					= delete $Vend::Session->{one_time_path_alias}{$Vend::FinalPath};
-	} 
-	elsif( defined $Vend::Session->{path_alias}{$Vend::FinalPath}	) {
-		$CGI::path_info
-					= $Vend::FinalPath
-					= $Vend::Session->{path_alias}{$Vend::FinalPath};
-	}
-    url_history($Vend::FinalPath) if $Vend::Cfg->{History};
-
-# TRACK
-    $Vend::Track = new Vend::Track;
-# END TRACK
-
-	if($Vend::Cfg->{DisplayErrors} and $Global::DisplayErrors) {
-		$SIG{"__DIE__"} = sub {
-							my $msg = shift;
-							put_session() if $Vend::HaveSession;
-							my $content = get_locale_message(500, <<EOF, $msg);
-<HTML><HEAD><TITLE>Fatal Interchange Error</TITLE></HEAD><BODY>
-<H1>FATAL error</H1>
-<PRE>%s</PRE>
-</BODY></HTML>
-EOF
-							::response(\$content);
-							exit 0;
-		};
-	}
-
-# LEGACY
-	ROUTINES: {
-		last ROUTINES unless index($Vend::FinalPath, '/process/') == 0;
-		while ($Vend::FinalPath =~ s:/process/(locale|language|currency)/([^/]*)/:/process/:) {
-			$::Scratch->{"mv_$1"} = $2;
-		}
-		$Vend::FinalPath =~ s:/process/page/:/:;
-	}
-	my $locale;
-	if($locale = $::Scratch->{mv_language}) {
-		$Global::Variable->{LANG}
-			= $::Variable->{LANG} = $locale;
-	}
-
-	if ($Vend::Cfg->{Locale}								and
-		$locale = $::Scratch->{mv_locale}	and
-		defined $Vend::Cfg->{Locale_repository}->{$locale}
-		)
-	{ 
-		$Global::Variable->{LANG}
-				= $::Variable->{LANG}
-				= $::Scratch->{mv_language}
-				= $locale
-			 if ! $::Scratch->{mv_language};
-		Vend::Util::setlocale(	$locale,
-								($::Scratch->{mv_currency} || undef),
-								{ persist => 1 }
-							);
-	}
-# END LEGACY
-
-	my $macro;
-	if ($macro = $Vend::Cfg->{Autoload}) {
-		if($macro =~ /\[\w+/) {
-			interpolate_html($macro);
-		}
-		elsif ($macro =~ /^\w+$/) {
-			my $sub = $Vend::Cfg->{Sub}{$macro} || $Global::GlobalSub->{$macro};
-			$sub->();
-		}
-	}
-
-	if ($macro = $Vend::Cfg->{Filter}) {
-		for(keys %$macro) {
-			Vend::Interpolate::input_filter_do($_, { 'op' => $macro->{$_} } );
-		}
-	}
-
-	if (
-		defined $Vend::Session->{Filter} and
-		$macro = $Vend::Session->{Filter}
-		)
-	{
-		for(keys %$macro) {
-			Vend::Interpolate::input_filter_do($_, $macro->{$_});
-		}
-	}
-
-	if (
-		defined $Vend::Session->{Autoload} and
-		$macro = $Vend::Session->{Autoload}
-		)
-	{
-		if(ref $macro) {
-			for (@$macro) {
-				interpolate_html($_);
-			}
-		}
-		else {
-			interpolate_html($macro);
-		}
-	}
-
-    # If the cgi-bin program was invoked with no extra path info,
-    # just display the catalog page.
-    if (! $Vend::FinalPath || $Vend::FinalPath =~ m:^/+$:) {
-		$Vend::FinalPath = find_special_page('catalog');
-    }
-
-	$Vend::FinalPath =~ s:^/+::;
-	$Vend::FinalPath =~ s/(\.html?)$//;
-	$Vend::Session->{extension} = $1 || '';
-#::logDebug("path=$Vend::FinalPath");
-
-  DOACTION: {
-    @path = split('/', $Vend::FinalPath, 2);
-	if (defined $CGI::values{mv_action}) {
-		$CGI::values{mv_todo} = $CGI::values{mv_action}
-			if ! defined $CGI::values{mv_todo}
-			and ! defined $CGI::values{mv_doit};
-		if($path[0] eq 'ui_wrap') {
-			$Vend::Action = 'ui_wrap';
-			delete $CGI::values{mv_action};
-			shift(@path);
-			$CGI::values{mv_nextpage} = $path[0]
-				if ! defined $CGI::values{mv_nextpage};
-			$path[0] = "process/$path[0]";
-		}
-		else {
-			$Vend::Action = 'process';
-			$CGI::values{mv_nextpage} = $Vend::FinalPath
-				if ! defined $CGI::values{mv_nextpage};
-		}
-	}
-	else {
-		$Vend::Action = shift @path;
-	}
-
-#::logGlobal("action=$Vend::Action path=$Vend::FinalPath");
-	my ($sub, $status);
-	Vend::Interpolate::reset_calc();
-	if(defined $Vend::Cfg->{ActionMap}{$Vend::Action}) {
-		$sub = $Vend::Cfg->{ActionMap}{$Vend::Action};
-		Vend::Interpolate::init_calc();
-		$CGI::values{mv_nextpage} = $Vend::FinalPath
-			if ! defined $CGI::values{mv_nextpage};
-		new Vend::Parse;
-	}
-	elsif ( defined ($sub = $action{$Vend::Action}) )  {
-		Vend::Interpolate::init_calc();
-		$Vend::FinalPath = join "", @path;
-	}
-	eval {
-		if(defined $sub) {
-#::logDebug("found sub");
-				$status = $sub->($Vend::FinalPath);
-		}
-		else {
-			$status = 1;
-		}
-	};
-	(undef $Vend::RedoAction, redo DOACTION) if $Vend::RedoAction;
-
-	if($@) {
-		undef $status;
-		my $err = $@;
-		my $template = <<EOF;
-Sorry, there was an error in processing this form action. Please 
-report the error or try again later.
-EOF
-		$template .= "\n\nError: %s\n"
-				if $Global::DisplayErrors && $Vend::Cfg->{DisplayErrors}
-			;
-		logError ("Error in form action: $err");
-		$template = get_locale_message(500, $template, $err);
-		$template .= "($err)";
-		::response($template);
-	}
-
-	$CGI::values{mv_nextpage} = $Vend::FinalPath
-		if ! defined $CGI::values{mv_nextpage};
-
-	do_page() if $status;
-
-#::logDebug ("end dispatch: " . (join " ", times()) . "\n");
-
-	if(my $macro = $Vend::Cfg->{AutoEnd}) {
-		if($macro =~ /\[\w+/) {
-			interpolate_html($macro);
-		}
-		elsif ($macro =~ /^\w+$/) {
-			$sub = $Vend::Cfg->{Sub}{$macro} || $Global::GlobalSub->{$macro};
-			$sub->();
-		}
-	}
-  }
-
-# TRACK
-	$Vend::Track->filetrack();
-# END TRACK
-
-	put_session() if $Vend::HaveSession;
-	close_database();
-
-	undef $H;
-	if($Vend::Save) {
-		copyref ($Vend::Save, $Vend::Cfg);
-		undef $Vend::Save;
-	}
-	undef $Vend::Cfg;
-
-# DEBUG
-#::logDebug ("closed all: " .  join " ", times() . "\n");
-# END DEBUG
-
-	return 1;
-}
+## This was set to 1 in Vend::Config, so that external programs calling it
+## would act properly by default
+undef $Vend::ExternalProgram;
 
 ## DEBUG
 
@@ -1882,16 +323,21 @@
 # STATICPAGE
 	$File::Find::name +
 	$File::Find::prune +
+	$File::Find::prune +
 	<DATA> + 
 # END STATICPAGE
 	$Global::AdminSub +
 	$Global::DomainTail +
 	$Global::FullUrl +
     $Global::HitCount +
+    $Global::ProfilesName +
+    $Global::Profiles +
+    $Global::LockoutCommand +
     $Global::LockoutCommand +
 	$Global::IpHead +
 	$Vend::CheckHTML +
 	$Vend::Action +
+	$Vend::CC3 +
 	$CGI::server_name +
 	$CGI::content_type +
 	$CGI::http_host +
@@ -1899,18 +345,8 @@
 	1;
 }
 
-sub dump_env {
-    my($var, $value);
-
-    open(Vend::E, ">$Vend::Cfg->{'VendRoot'}/env");
-    while(($var, $value) = each %ENV) {
-	print Vend::E "export $var='$value'\n";
-    }
-    close Vend::E;
-}
-
 sub version {
-	print "Interchange version $VERSION Copyright 1996-2001 Akopia, Inc.\n";
+	print "Interchange version $VERSION copyright 1996-2002 Red Hat, Inc. and others.\n";
 }
 
 =head1 NAME
@@ -1923,7 +359,7 @@
 
 =head1 VERSION
 
-4.6.5
+4.9.7
 
 =head1 DESCRIPTION
 
@@ -1935,7 +371,7 @@
 Interchange has many, many, functions and features; they are too numerous to
 describe in this venue. Complete information can be found at its web site:
 
-		http://www.akopia.com/
+		http://www.icdevgroup.org/
 
 Interchange requires Perl 5.005 or higher; more information on Perl can
 be seen at:
@@ -1959,9 +395,29 @@
 The information is in the form of a standard Interchange catalog line,
 and must be in the single-line format.
 
-=item C<-b catalog, --build=catalog>
+=item --cron=catalog[=job]
+
+Run a cron group which is a series of files in a directory with
+the name corresponding to the C<job>. For instance, if you 
+set up a directory called "weekly" in your pages directory
+for the catalog C<foundation>, you can run those files with:
 
-Build static page tree for C<catalog>.
+	interchange --cron=foundation=weekly
+
+Files ending in .html (or whatever HTMLsuffix is for that catalog)
+are skipped. It is not tree-recursive -- directories are ignored.
+
+Results can be emailed to an address if you specify --email=address,
+and they will be put in the cron log file.
+
+Alternatively jobs can be specified with --job=jobname B<before>
+the --cron option. In other words, this will work:
+
+	interchange --job=weekly --cron=foundation
+
+This will NOT work:
+
+	interchange --cron=foundation --job=weekly
 
 =item -d dir, --dir=dir
 
@@ -1973,13 +429,13 @@
 
 Exclude catalog from this startup.
 
-=item -f file, --config=file
+=item -email=address
 
-Configuration file to use (default is interchange.cfg in VendRoot).
+Email address to email cron job results to.
 
-=item --files spec
+=item -f file, --config=file
 
-File specification to build (perl regexp OK) for static page tree
+Configuration file to use (default is interchange.cfg in VendRoot).
 
 =item -h, --help
 
@@ -1990,6 +446,15 @@
 Run with internet-domain socket only. Normally Interchange runs with
 both UNIX- and internet-domain sockets (except on Windows).
 
+=item --job=job
+
+Sets the job for --cron if that is not included in the --cron
+call. MUST precede the --cron entry on the command line.
+
+	interchange --job=weekly --cron=foundation
+
+See --cron for an explanation of what this does.
+
 =item --kill [signal]
 
 By default, kills the server ungracefully with signal KILL (9, usually).
@@ -2037,10 +502,10 @@
 
 Display program version.
 
-=item -D, --DEBUG
+=item --DEBUG=1
 
-Run foreground in debug mode. It is normal to receive warnings about
-various things.
+Set to true value to run foreground in debug mode. It is normal to
+receive warnings about various things if you run with perl -w.
 
 =cut
 
@@ -2078,18 +543,20 @@
 
 Command line options (first letter will usually work):
 
-     --add=catalog         remove a catalog from operation, parms taken
-                           from the standard input
-     -b catalog
-        --build=catalog    build static page tree for catalog
+     --add=catalog         add a catalog to operation; parms taken from the
+                           standard input as a "Catalog ..." directive
+     --cron=catalog[=job]  run cron jobs for a particular catalog
+                           (can use --job and -email)
      -d dir, --dir=dir     directory for VendRoot (interchange.cfg, error.log, etc.)
      -e name,
         --exclude=name     exclude catalog
+     --email=emailaddr     Send results of cron job to emailaddr
      -f file,
         --config=file      configuration file (default interchange.cfg)
      --files spec          filespec (perl regexp OK) for static page tree
      -h, --help            display this message
      -i, --inetmode        run with Internet-domain socket (TCP)
+     --job=jobname         cron jobs to run (hourly, daily, weekly, etc.)
      --kill [signal]       kill server ungracefully (9 or with optional signal)
      -q, --quiet           suppress informational messages on startup
      --reconfig=catalog    reconfig a particular catalog on the server
@@ -2100,31 +567,10 @@
      -t, --test            report problems with config files
      -u, --unix            run with UNIX-domain socket
      -v, --version         display program version
-     -D, --DEBUG           run foreground in debug mode
+     --DEBUG=1             run foreground in debug mode
 END
 }
 
-## FILE PERMISSIONS
-
-sub set_file_permissions {
-	my($r, $w, $p, $u);
-
-	$r = $Vend::Cfg->{'ReadPermission'};
-	if    ($r eq 'user')  { $p = 0400;   $u = 0277; }
-	elsif ($r eq 'group') { $p = 0440;   $u = 0227; }
-	elsif ($r eq 'world') { $p = 0444;   $u = 0222; }
-	else                  { die "Invalid value for ReadPermission\n"; }
-
-	$w = $Vend::Cfg->{'WritePermission'};
-	if    ($w eq 'user')  { $p += 0200;  $u &= 0577; }
-	elsif ($w eq 'group') { $p += 0220;  $u &= 0557; }
-	elsif ($w eq 'world') { $p += 0222;  $u &= 0555; }
-	else                  { die "Invalid value for WritePermission\n"; }
-
-	$Vend::Cfg->{'FileCreationMask'} = $p;
-	$Vend::Cfg->{'Umask'} = $u;
-}
-
 ## MAIN
 
 sub catch_warnings {
@@ -2168,7 +614,6 @@
 						die "Can't set two modes -$mode and -$Vend::mode.\n"
 								if $Vend::saw_mode;
 						$Vend::saw_mode = 1;
-						$Vend::CatalogToBuild{$val} = 1 if $mode eq 'build';
 						$Vend::mode = $mode;
 					};
 
@@ -2180,18 +625,18 @@
 	my %optctl = (
 
 		DEBUG 		    => \$Global::DEBUG,
-		build           => $modesub,
 		reconfig        => $rcfgsub,
 		confdir         => \$Global::ConfDir,
+		rundir          => \$Global::RunDir,
 		configfile      => \$Global::ConfigFile,
 		dir          	=> \$Global::VendRoot,
 		exclude         => \%Vend::CatalogToSkip,
-		files	        => \$Vend::BuildSpec,
 		help            => sub { usage(); exit 0 },
 		inetmode        => \$Global::Inet_Mode,
 		log             => \$Global::ErrorFile,
 		quiet			=> \$Vend::Quiet,
 		pidfile			=> \$Global::PIDfile,
+		soappidfile		=> \$Global::SOAP_PIDfile,
 		serve           => $modesub,
 
 		test			=> $modesub,
@@ -2199,6 +644,9 @@
 		version         => sub { version(); exit 0 },
 		stop			=> \&control_interchange,
 		add				=> \&signal_add,
+		email			=> \$Vend::CronEmail,
+		job				=> \$Vend::CronJob,
+		cron			=> \&signal_cron,
 		remove			=> \&signal_remove,
 		kill			=> \&control_interchange,
 		Ignore 			=> \$ignore,
@@ -2253,20 +701,22 @@
 	);
 
 	my @options = ( qw/
-		DEBUG|D:i
+		DEBUG:i
 		Ignore
 		add|a=s
-		build|b=s
-		confdir=s
-		configfile|config|c|f=s
-		dir|vendroot|d=s
-		exclude|e=s
-		files=s
-		help|h
-		inetmode|inet|i
-		kill:s
-		log|logfile|l=s
-		quiet|q
+        confdir=s
+        configfile|config|c|f=s
+        cron=s
+        dir|vendroot|d=s
+        email=s
+        exclude|e=s
+        help|h
+        inetmode|inet|i
+        job=s
+        kill:s
+        log|logfile|l=s
+        quiet|q
+        rundir=s
 		pidfile=s
 		reconfig=s
 		remove=s
@@ -2314,14 +764,16 @@
 	# These are only starting values, can be changed by command-line
 	# options or the interchange.cfg file
 	$Global::ConfDir = "$Global::VendRoot/etc";
-	$Global::PIDfile = "$Global::ConfDir/$Global::ExeName.pid";
+	$Global::RunDir = "$Global::VendRoot/etc";
+	$Global::PIDfile = "$Global::RunDir/$Global::ExeName.pid";
+	$Global::SOAP_PIDfile = "$Global::RunDir/$Global::ExeName.soap.pid";
 
 	$Vend::mode = 'serve';      # mode will be reset by options if appropriate
 
 	# Parse command line options, getting mode if not -serve
 	# May actually exit in some situations
 	parse_options()
-		or die usage() . "\n";
+		or usage(), die "\n";
 
 	# Cannot run as root unless in 'make test'
 	if($> == 0 and ! $Global::Windows) {
@@ -2329,35 +781,12 @@
 			unless $ENV{MINIVEND_ROOT} =~ m{/blib$};
 	}
 
-	## Bring in the CyberCash libraries if present
-	## Moved here to prevent unwanted messages
-	eval {
-		package Vend::Order;
-		require CCLib;
-		$Vend::CC2 = 1;
-		my $ver = $CCLib::VERSION || '2.1';
-		::logGlobal({}, "CyberCash module found (Version %s)", $ver )
-			unless $Vend::Quiet;
-	};
-
-	$Vend::CyberCash = ! $@;
-
+# LEGACY
+	# Kept here for compatibility
 	eval {
-		package Vend::Order;
-		require CCMckLib3_2 ;
-		import CCMckLib3_2 qw/InitConfig %Config $MCKversion/;
-		require CCMckDirectLib3_2;
-		import CCMckDirectLib3_2 qw/SendCC2_1Server doDirectPayment/;
-		require CCMckErrno3_2;
-		import CCMckErrno3_2 qw/MCKGetErrorMessage/;
-		$Vend::CC3 = 1;
-		$Vend::CC3server = 0;
-		my $ver = $CCMckLib3_2::VERSION || '3.x';
-		::logGlobal({}, "CyberCash module found (Version %s)", $ver )
-			unless $Vend::Quiet;
+		require Vend::Payment::CyberCash;
 	};
-
-	$Vend::CyberCash = $Vend::CyberCash || ! $@;
+# END LEGACY
 
 	# These modules no longer necessary, why take up memory?
 	delete $INC{'Getopt/Long.pm'};
@@ -2385,6 +814,10 @@
 
 	# Read interchange.cfg (or whatever its name is set to be)
 	global_config();
+	# Select locking mode
+	set_lock_type();
+
+	Vend::Dispatch::update_global_actions();
 
 #::logDebug(::uneval(\%Global::Catalog));
 
@@ -2408,9 +841,6 @@
 		foreach $name (sort keys %Global::Catalog) {
 			$g =  $Global::Catalog{$name};
 			next if defined $Vend::CatalogToSkip{$g->{'name'}};
-			next if
-				$Vend::mode eq 'build' and
-				! defined $Vend::CatalogToBuild{$g->{'name'}};
 			print "Configuring catalog " . $g->{'name'} . '...'
 				unless $Vend::Quiet or $g->{name} eq '_mv_admin';
 			if (exists $Global::Selector{$g->{'script'}}) {
@@ -2451,27 +881,14 @@
 						warn "Alias $_ used a second time, skipping.\n";
 						next;
 					}
-					elsif (m![^\w-_:~#/.]!) {
+					elsif (m![^-\w_:~#/.]!) {
 						warn "Bad alias $_, skipping.\n";
 					}
 					$Global::Selector{$_} = $c;
 					$Global::SelectorAlias{$_} = $g->{'script'};
 				}
 			}
-# STATICPAGE
-			# This is probably not useful any more.....use the
-			# regen feature of the UI.
-			if ($Vend::CatalogToBuild{$g->{name}}) {
-				require Vend::Misc::Static;
-				eval {
-					Vend::Misc::Static::build_all($g->{name});
-				};
-				if($@) {
-					die "Error building pages: $@\n";
-				}
-				undef $Vend::BuildingPages;
-			}
-# END STATICPAGE
+
 			print "done.\n"  unless $Vend::Quiet or $g->{name} =~ /^_/;
 		}
 	}
@@ -2479,16 +896,23 @@
 	#undef $Global::DumpStructure;
 
 	if ($Vend::mode eq 'serve') {
-		undef $Vend::Foreground;
+		undef $Global::Foreground;
 
 		# Here we prepare enter the daemon mode.
 
-		# Set the $0 to something not having 'perl' (won't
-		# work on Solaris and IRIX among possibly others)
-		if(defined $Global::Variable->{MV_DOLLAR_ZERO}) {
-			$0 = $Global::Variable->{MV_DOLLAR_ZERO};
-			$0 = "interchange --> $Global::VendRoot"
-					if length($0) < 2;
+		# Set $0 to something pretty for ps(1).
+		# Won't work on Solaris and IRIX among possibly others.
+		# Dumps core on FreeBSD 4 stock Perl build.
+		if (defined $Global::Variable->{MV_DOLLAR_ZERO}) {
+			if ($Global::Variable->{MV_DOLLAR_ZERO}) {
+				if (length($Global::Variable->{MV_DOLLAR_ZERO}) > 1) {
+					$0 = $Global::Variable->{MV_DOLLAR_ZERO};
+				}
+				else {
+					$0 = "interchange --> $Global::VendRoot";
+				}
+			}
+			# do nothing if MV_DOLLAR_ZERO is defined but false
 		}
 		else {
 			$0 = 'interchange';
@@ -2504,9 +928,9 @@
 		# This should never return unless killed or a catastrophic error
         Vend::Server::run_server();
 	}
-	elsif ($Vend::mode eq 'test' || $Vend::mode eq 'build') {
-				# Blank by design, this option only tests config files
-				# or builds catalogs
+	elsif($Vend::mode eq 'test') {
+		# Blank by design, this option only tests config files
+		# or builds catalogs
 	}
 	else {
 		die "No mode!\n";
@@ -2518,42 +942,69 @@
 eval { main_loop(); };
 if ($@) {
 	my($msg) = ($@);
+	$Vend::Log_suppress = 1;
 	logGlobal( $msg );
 	if ($Global::DisplayErrors) {
 		print "$msg\n";
 	}
-	die "$msg\n" if $Vend::ForeGround;
+	die "$msg\n" if $Global::Foreground;
 }
 
 =head1 SEE ALSO
 
-mvdocs(8), compile_link(1), config_prog(1), configdump(1), dump(1), expire(1),
+compile_link(1), config_prog(1), configdump(1), dump(1), expire(1),
 expireall(1), localize(1), makecat(1), offline(1), restart(1), update(1),
-http://www.akopia.com/
+http://www.icdevgroup.org/
 
 =head1 LICENSE
 
-Interchange comes with ABSOLUTELY NO WARRANTY.  This is free software, and
+Interchange comes with ABSOLUTELY NO WARRANTY. This is free software, and
 you are welcome to redistribute and modify it under the terms of the
 GNU General Public License.
 
 =head1 COPYRIGHT
 
-Copyright 1995-2001 Akopia, Inc. All rights reserved except as in the license.
+Copyright 1995-2002, Red Hat, Inc. and others.
+All rights reserved except those granted in the license.
 
 =cut
 
 =head1 AUTHOR
 
-Mike Heins, <heins@akopia.com>. Please do not contact the author for
-direct help with the system. Use the Interchange mail lists:
+Mike Heins is the primary author of Interchange.
+
+The Interchange Development Group is:
+
+Brev Patterson
+Dan Browning
+Ed LaFrance
+Jonathan Clark
+Jon Jensen
+Kevin Walsh
+Mike Heins
+Stefan Hornburg (aka Racke), captain
+Ton Verhagen
 
-	interchange-users	(English, subscribe at http://developer.akopia.com/)
+Please do not contact the authors for direct help with the system.
+Use the Interchange mail list:
 
-General information and documentation for Interchange is at:
+    interchange-users@icdevgroup.org
 
-	http://www.akopia.com/
-	http://developer.akopia.com/
+Information on subscribing to the list, as well as general information and
+documentation for Interchange is at:
+
+    http://www.icdevgroup.org/
+
+=head1 SPECIAL ACKNOWLEDGEMENTS
+
+The original author of Vend was Andrew Wilcox. Interchange could never
+have come into being without him.
+
+Stefan Hornburg has had his hand in many parts of Interchange, and is by
+far the most prolific bug-finder. He also was primarily responsible for
+bringing MiniMate, precursor to the Interchange store administration UI,
+to being as a supported facility. He continues to make valuable
+contributions.
 
 =head1 SPECIAL ACKNOWLEDGEMENTS
 
@@ -2568,62 +1019,55 @@
 =head1 ACKNOWLEDGEMENTS
 
 Original author of Vend, ancestor to Minivend and Interchange, was Andrew
-Wilcox. Interchange was based on Vend 0.2, with portions from Vend 0.3;
-both were produced in 1995.
+Wilcox <amw@wilcoxsolutions.com>. Interchange was based on Vend 0.2, with
+portions from Vend 0.3; both were produced in 1995.
+
+# columnize with "sort -u | pr -t -2 | expand -8 | sed 's/^/    /'"
 
 Contributions to Interchange have been made by:
 
-    Andreas Koenig     
-    Bill Randle
-    Birgitt Funk       
-    Bob Jordan         
-    Brian Bullen       
-    Bruce Albrecht     
-	Cameron Prince
-    Christian Mueller
-    Christopher Thompson
-    Dave Adams
-    Dan Busarow
-    Dave Wingate
-	Dennis Cronin
-    Don Grodecki       
-    Frank Bonita       
-    Gunnar Hellekson   
-    Hans-Joachim Leidinger
-    Heinz Wittenbecher
-    Jason Holt
-    Jeff Carnahan
-    Jeff Nappi
-    Jochen Wiedmann
-    Jon Jensen
-    Keiko
-    Keith Oberlin
-    Larry Leszczynski
-    Marc Austin
-    Mark Stosberg
-    Michael McCune
-    Michael Wilk
-    Mike Frager
-    Neil Evans
-    Raj Goel
-    Ray Desjardins
-    Sonny Cook
-    Tim Baverstock
-    Ton Verhagen
-    William Dan Terry
+    Andreas Koenig                      Jason Kohles
+    Bill Carr                           Javier Martin
+    Bill Dawkins                        Jeff Carnahan
+    Bill Randle                         Jeff Nappi
+    Birgitt Funk                        Jochen Wiedmann
+    Bob Jordan                          Jon Jensen
+    Brev Patterson                      Jonathan Clark
+    Brian Bullen                        José Mª Revuelto
+    Brian Kosick                        Jurgen Botz
+    Bruce Albrecht                      Keiko
+    Cameron Prince                      Keith Oberlin
+    Chen Naor                           Kevin Walsh
+    Christian Mueller                   Kim Lauritz Christensen
+    Christopher Miller                  Larry Leszczynski
+    Christopher Thompson                Marc Austin
+    Dan Browning                        Mark Johnson
+    Dan Busarow                         Mark Stosberg
+    Dan Helfman                         Massimiliano Ciancio
+    Daniel Thompson                     Matthew Schick
+    Dave Wingate                        Michael McCune
+    David Adams                         Michael Wilk
+    David Kelly                         Mike Frager
+    Dennis Cronin                       Neil Evans
+    Don Grodecki                        Nelson Ferrari
+    Ed LaFrance                         Raj Goel
+    Frank Bonita                        Ray Desjardins
+    Frederic Steinfels                  Ron Phipps
+    Greg Hanson                         Shozo Murahashi
+    Gunnar Hellekson                    Sonny Cook
+    Hamish Bradick                      Tim Baverstock
+    Hans-Joachim Leidinger              Tom Friedel
+    Heinz Wittenbecher                  Tommi Laberno
+    Hiroyuki Cozy Kojima                Ton Verhagen
+    Ignacio Lizarán                     Troy Davis
+    Jack Tsai                           Victor Nolton
+    Jason Holt                          William Dan Terry
     and many others
 
 and, of course, the entire Perl team without whom Interchange could not exist.
 
 =cut
 
-__END__
+$Global::mod_perl ? 1 : 0;
 
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}
+__END__



1.7.4.1   +62 -54    interchange/scripts/localize.PL


rev 1.7.4.1, prev_rev 1.7
Index: localize.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/localize.PL,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- localize.PL	25 Sep 2000 16:38:49 -0000	1.7
+++ localize.PL	25 Jan 2003 22:21:32 -0000	1.7.4.1
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange localizer
 #
-# $Id: localize.PL,v 1.7 2000/09/25 16:38:49 zarko Exp $
+# $Id: localize.PL,v 1.7.4.1 2003/01/25 22:21:32 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# See the file 'Changes' for information.
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -55,7 +31,7 @@
 use Vend::Util qw(readfile escape_chars);
 require Vend::Config;
 use Getopt::Std;
-use vars qw($opt_c $opt_d $opt_l $opt_M $opt_m $opt_o $opt_t);
+use vars qw($opt_c $opt_d $opt_l $opt_M $opt_m $opt_n $opt_o $opt_t $opt_u);
 
 BEGIN {
 	($Global::VendRoot = $ENV{MINIVEND_ROOT})
@@ -75,7 +51,7 @@
 my $USAGE = <<EOF;
 $0 -- produce localization file from set of pages
 
-usage:    localize -l lg_CC [-d lg_CC] [-m file|-t] file [file2 file3 ...]
+usage:    localize -l lg_CC [-d lg_CC] [-m file|-t] [-u dir] file [file2 file3 ...]
 
 OPTIONS
 
@@ -84,12 +60,15 @@
     -d lg_CC   Create default domain file with Locale lg_CC as prefix
     -l lg_CC   Create file with Locale lg_CC as prefix
     -m <file>  Read existing information to merge from <file>
+    -n         Don't write comments
     -M         When in -c mode, prefix MM_ to make minimate_compatible; 
                when in regular mode, strip MM_ from [LC] defs
     -o         Rewrite [L] sections with [L msgNNNN], adjust file and data
                -- mutually exclusive with -c
-    -t         Two page mode, mutually exclusive with -m
-
+    -t         Two page mode, mutually exclusive with -m 
+    -u <dir>   UI directory, e.g. /usr/lib/interchange/lib/UI. This can
+	           be used to include the menu titles in the output.
+	  
 lg_CC refers to the POSIX norm of specifying two-letter
 language and country codes to refer to a locale.
     
@@ -107,7 +86,7 @@
 
 EOF
 
-getopts('cd:l:Mm:ot') or die "$USAGE\n";
+getopts('cd:l:Mm:notu:') or die "$USAGE\n";
 
 die "$USAGE\n" if $@;
 die "$USAGE\n" unless $opt_l;
@@ -160,16 +139,34 @@
 else {
 	warn "Couldn't read merge file $opt_m, continuing without.\n";
 }
-
+		
 $C->{Locale_repository} = {} unless $C->{Locale_repository};
 
 my $Locale = $C->{Locale_repository};
-
 my $one_text;
 my $two_text;
 my $one;
 my $two;
 
+if($opt_u) {
+	my $icmenu = "$opt_u/icmenu.txt";
+	my ($headline, @cols);
+	
+	open (ICMENU, $icmenu)
+		|| die  "Couldn't read UI menu file $icmenu: $!\n";
+	$headline = <ICMENU>;
+	@cols = split (/\t/, $headline);
+	unless ($cols[9] eq 'name' && $cols[12] eq 'special') {
+		die "Malformed UI menu file $icmenu\n";
+	}
+	while (<ICMENU>) {
+		@cols = split (/\t/);
+		write_structure (undef, $cols[9]);
+		write_structure (undef, $cols[12]) if $cols[12];
+	}
+	close (ICMENU);
+}
+		
 if($opt_t) {
 	$one = shift;
 	$two = shift || die "$USAGE\n";
@@ -223,6 +220,7 @@
 
 sub write_structure {
 	my($key, $default) = @_;
+
 	if($key) {
 		$Locale->{$def}->{$key} = $default;
 		$Comment{$key} = $default;
@@ -290,6 +288,12 @@
 print STDERR ".";
 					substitute_lc($1);
 		}
+        while ($data =~ m:\[loc\](\s*[^\[].*?[^\]]\s*)\[/loc\]:gsi) {
+					write_structure(undef, $1);
+		}
+        while ($data =~ m:\[msg(\s+arg\.\d+=".*?")*\s*\](\s*[^\[].*?[^\]]\s*)\[/msg\]:gsi) {
+					write_structure(undef, $2);
+		}
 	}
 
 	if($opt_c || $opt_o) {
@@ -306,20 +310,21 @@
 my($text, $dat, $cmt);
 
 foreach $key (sort keys %$d) {
-
 		$dat = ($Comment{$key} || '') and
 			$dat =~ s/\n/\n# /g;
 
 		$def_text .= "# $dat\n" if $dat;
 
-		if ($dat) {
-			$cmt = $dat;
-		}
-		else {
-			$cmt = $key;
-			$cmt =~ s/\n/\n# /g;
-		}
-		$loc_text .= "# $cmt\n";
+        unless ($opt_n) {
+		    if ($dat) {
+			    $cmt = $dat;
+		    }
+		    else {
+			    $cmt = $key;
+			    $cmt =~ s/\n/\n# /g;
+		    }
+		    $loc_text .= "# $cmt\n";
+        }
 
 		$text = &$Uneval($key);
 		$loc_text .= "$text,\n";
@@ -350,7 +355,7 @@
 
 =head1 VERSION
 
-$Id: localize.PL,v 1.7 2000/09/25 16:38:49 zarko Exp $
+# $Id: localize.PL,v 1.7.4.1 2003/01/25 22:21:32 racke Exp $
 
 =head1 SYNOPSIS
 
@@ -387,6 +392,10 @@
 When in C<-c> mode, prefix MM_ to make minimate_compatible; 
 when in regular mode, strip MM_ from [LC] defs
 
+=item C<-n>
+
+Don't write comments in the output.
+
 =item C<-o>
 
 Rewrite [L] sections with [L msgNNNN], adjust file and data.
@@ -396,6 +405,11 @@
 
 Two page mode, mutually exclusive with C<-m.>
 
+=item C<-u dir>
+
+UI directory, e.g. /usr/lib/interchange/lib/UI. This can
+be used to include the menu titles in the output.
+
 =back
 
 lg_CC refers to the POSIX norm of specifying two-letter
@@ -415,19 +429,13 @@
 
 =head1 SEE ALSO
 
-mvdocs(8), http://www.akopia.com/
+http://interchange.redhat.com/
 
 =head1 AUTHOR
 
-Mike Heins, <heins@akopia.com>. Valuable contributions made by Stefan Hornburg,
-<racke@linuxia.net>.
+Mike Heins, <mheins@redhat.com>.
+
+Valuable contributions made by Stefan Hornburg, <racke@linuxia.de>.
+
 =cut
 
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.26.4.9  +349 -180  interchange/scripts/makecat.PL


rev 1.26.4.9, prev_rev 1.26.4.8
Index: makecat.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/makecat.PL,v
retrieving revision 1.26.4.8
retrieving revision 1.26.4.9
diff -u -r1.26.4.8 -r1.26.4.9
--- makecat.PL	5 Dec 2000 16:06:17 -0000	1.26.4.8
+++ makecat.PL	25 Jan 2003 22:21:32 -0000	1.26.4.9
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange catalog configurator
 #
-# $Id: makecat.PL,v 1.26.4.8 2000/12/05 16:06:17 racke Exp $
+# $Id: makecat.PL,v 1.26.4.9 2003/01/25 22:21:32 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# See the file 'Changes' for information.
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -56,6 +32,7 @@
 use File::Find;
 use File::Copy;
 use File::Path;
+use Sys::Hostname;
 use Vend::MakeCat;
 use Vend::Util;
 use Getopt::Long;
@@ -67,6 +44,7 @@
 #Getopt::Long::config(qw/debug/);
 
 BEGIN {
+
 	($Global::VendRoot = $ENV{MINIVEND_ROOT})
 		if defined $ENV{MINIVEND_ROOT};
 	$Global::VendRoot = $Global::VendRoot || '/usr/local/interchange';
@@ -83,7 +61,7 @@
 		$Global::ExeName = 'minivend';
 		$Global::ConfigFile = 'minivend.cfg';
 	}
-	elsif(-f "$Global::VendRoot/interchange.cfg.dist") {
+	else {
 		$Global::ExeName = 'interchange';
 		$Global::ConfigFile = 'interchange.cfg';
 	}
@@ -105,7 +83,7 @@
 my $Cfg;
 my $Logfile = 'makecat.log';
 my $catalog_name;
-my %Conf;
+use vars qw( %Conf );
 my $Inetmode;
 my $Windows;
 my $pid;
@@ -122,6 +100,8 @@
     -l    File to log to (default makecat.log)
     -r    Reconfigure defaults
 
+    [catalogname] must contain alphanumerics and hyphens only.
+
     Defaults:
     --basedir=directory        Base directory for catalogs
     --cgibase=url_fragment     Base URL for link programs
@@ -137,10 +117,11 @@
     --cgidir=directory         The directory the CGI link should go to
     --servername=server        Name of server (www.whatever.domain)
     --cgiurl=url_fragment      The path to the CGI link (no server name)
-    --demotype=template        The template catalog (construct is the default)
+    --demotype=template        The template catalog (foundation is the default)
     --mailorderto=email        Email address to send orders
 
     Optional:
+    --catalogconf=file         Specify separate configuration file for catalogs
     --catuser=username         The user files should be owned by (if root)
     --sharedir=directory       The directory where shared admin images go
     --shareurl=url             The URL to prefix shared admin images with
@@ -148,7 +129,7 @@
     --imageurl=url             The URL to prefix images with
     --linkmode=mode            UNIX or INET (link program vlink or tlink)
     --linkprogram=file         Use file as link program instead of vlink/tlink
-    --nocfg                    Don't add to $Global::ExeName.cfg
+    --nocfg                    Don't add to $Global::ConfigFile
     --nocopy                   Don't actually copy the files, just test
     --norunning                Don't add to running server
     --noumask                  Don't set umask
@@ -166,6 +147,7 @@
 	    'F'                 => \$Vend::MakeCat::Force,
 	    'aliases'           => \$Conf{aliases},
 	    'basedir'           => \$Conf{basedir},
+	    'catalogconf'       => \$Conf{catalogconf},
 	    'catalogname'       => \$catalog_name,
 	    'catroot'           => \$Conf{catroot},
 	    'catuser'           => \$Conf{catuser},
@@ -180,6 +162,8 @@
 	    'imageurl'          => \$Conf{imageurl},
 	    'l'                 => \$Logfile,
 	    'linkmode'          => \$Conf{linkmode},
+	    'linkhost'          => \$Conf{linkhost},
+	    'linkport'          => \$Conf{linkport},
 	    'linkprogram'       => \$Conf{linkprogram},
 	    'mailorderto'       => \$Conf{mailorderto},
 	    'interchangegroup'  => \$Conf{interchangegroup},
@@ -215,6 +199,7 @@
 	    F
 	    aliases=s
 	    basedir|base=s
+	    catalogconf=s		
 	    catalogname|name=s
 	    catroot|dir=s
 	    catuser|user=s
@@ -229,6 +214,8 @@
 	    imageurl=s
 	    l=s
 	    linkmode=s
+	    linkhost=s
+	    linkport=s
 	    linkprogram=s
 	    mailorderto=s
 	    interchangegroup|minivendgroup|group=s
@@ -245,13 +232,16 @@
 	    serverconf|conf=s
 	    servername|server=s
 	    sharedir=s
-	    shareurl=s
+	    shareurl:s
 	    vendroot|mvdir=s
 	    <>
 	/);
 
 	GetOptions(\%optctl, @options)			or die "\n$USAGE\n";
 }
+elsif ($ARGV[0] =~ /^(--help|-h(elp)?)$/i) {
+	die "\n$USAGE\n";
+}
 
 $catalog_name = shift unless $catalog_name;
 if(@ARGV) {
@@ -275,13 +265,16 @@
 program. Depending on your CGI setup, it may also have the 
 extension .cgi added.
 
-If you are doing the demo for the first time, you might use "construct".
+Only the characters [-a-zA-Z0-9_] are allowed, and it is strongly suggested
+that the catalog name be all lower case.
+
+If you are doing the demo for the first time, you might use "foundation".
 
 EOF
    $catalog_name = prompt ("Catalog name? ");
 }
 
-die "$USAGE\n" unless $catalog_name;
+die "$catalog_name -- $USAGE\n" unless $catalog_name =~ /^[-\w]+$/;
 
 if($Conf{homedir}) {
 	die "Directory set with --homedir=$Conf{homedir} is not a directory.\n"
@@ -422,14 +415,14 @@
 
 my $isroot = 0;
 if ($< == 0) {
-	$isroot = 1 unless $Windows;
+	$isroot = 1 unless $Windows or $Conf{relocate};
 }
 
 $Conf{catalogname} = $catalog_name;
 
 my %Initial;
 
-my %IfRoot = (qw( permtype 1 interchangeuser 1 interchangegroup 1 catuser 1));
+my %IfRoot = (qw( permtype 1 interchangeuser 1 interchangegroup 1 catuser 1 linkmode 1));
 
 my %Prefix = (
 	vendroot     =>  $Global::VendRoot,
@@ -444,11 +437,14 @@
 	interchangeuser =>  sub {  return 'everybody' if $Windows;
 							get_id(); },
 	interchangegroup=>  '',
-    servername	 =>  $Config{myhostname},
+    servername => sub {
+						return Sys::Hostname::hostname() || $Config{myhostname};
+					},
+    linkmode     =>  'UNIX',
     documentroot =>  $ENV{MVC_DOCUMENTROOT} || $DocrootDefault,
 	cgidir       =>  $ENV{MVC_CGIDIR} || $CgiDefault,
 	cgibase      =>  $ENV{MVC_CGIBASE} || $CgiUrlDefault,
-	demotype     =>  $ENV{MVC_DEMOTYPE} || 'construct',
+	demotype     =>  $ENV{MVC_DEMOTYPE} || 'foundation',
     catuser      =>  sub {
 							$ENV{MVC_CATUSER} ||
 							($isroot ? '' : $Conf{'interchangeuser'})
@@ -466,7 +462,6 @@
 							$dir =~ s/^\~/$userdir/;
 							return $dir;
 							},
-	aliases      =>  sub { return "/" . $catalog_name },
 	cgiurl       =>  sub {
 							return $ENV{MVC_CGIURL} if $ENV{MVC_CGIURL};
 							my $url = '';
@@ -506,7 +501,6 @@
 							return $ENV{MVC_SHAREURL} if $ENV{MVC_SHAREURL};
 							my $url = '';
 							$url = $Tilde if defined $Tilde;
-							$url .= '/';
 							return $url;
 						},
 
@@ -538,9 +532,20 @@
 	catroot			=> \&directory_process,
 	relocate		=> \&strip_trailing_slash,
 	shareurl		=> \&strip_trailing_slash,
+	sharedir		=> \&strip_trailing_slash,
 
 );
 
+sub sum_it {
+	my ($file) = @_;
+	open(IT, "<$file")
+		or return undef;
+	my $data = '';
+	$data .= $_ while (<IT>);
+	close IT;
+	return unpack("%32c*", $data);
+}
+
 sub prefix {
 	my ($parm, $nodefault) = @_;
 	$parm = lc $parm;
@@ -559,13 +564,23 @@
     demotype =>  sub {
 						my @dir; 
 						@dir = sort map { s:(.*)/.*:$1:; $_ } glob("*/catalog.cfg");
-						@dir = grep $_ ne 'construct', @dir;
-						unshift(@dir, 'construct') if -f 'construct/catalog.cfg';
-						unshift(@dir, 'barry') if -f 'barry/catalog.cfg';
-						unshift(@dir, 'simple') if $catalog_name =~ /simp/;
+						@dir = grep $_ ne 'foundation', @dir;
+						unshift(@dir, 'foundation') if -f 'foundation/catalog.cfg';
+						unshift(@dir, 'construct')
+							if  -f 'construct/catalog.cfg'
+							and $catalog_name =~ /^construct/;
+						unshift(@dir, 'barry')
+							if  -f 'barry/catalog.cfg'
+							and $catalog_name =~ /^barry/;
+						unshift(@dir, 'art')
+							if  -f 'art/catalog.cfg'
+							and $catalog_name =~ /^art/;
+						my %seen;
+						@dir = grep !$seen{$_}++, @dir;
 						return @dir;
 					},
 
+	linkmode => sub { return ('UNIX', 'INET') },
     documentroot =>  sub {
 						if(defined $Servers->{$Servername}) {
 							return $Servers->{$Servername}->{documentroot}
@@ -743,6 +758,7 @@
 	}
 	die "Can't parse config file $Configfile\n";
 }
+
 my @parms;
 
 unless($Reconfigure or $Cfg->val('base', 'vendroot')) {
@@ -760,10 +776,16 @@
 	unless(@parms) {
 		@parms = $Cfg->Parameters('legalconfig');
 		undef $Cfg;
+		my $user_time = "run by ";
+		$user_time .= scalar getpwuid($>);
+		$user_time .= " at ";
+		$user_time .= scalar localtime();
+
 		open(CFGFILE, ">>$Configfile")	or die "Can't write $Configfile: $!\n";
 		print CFGFILE <<EOF;
 
 # New catalog definition '$catalog_name' written by makecat
+# $user_time
 [catalog $catalog_name]
 EOF
 		for(@parms) {
@@ -825,7 +847,6 @@
 		$not_set = 1;
 		if(findexe('locate')) {
 			@conf = findfiles('httpd.conf');
-			$Cfg->setval('base', 'serverconf', join(" ", @conf));
 		}
 		else {
 			print <<EOF;
@@ -837,15 +858,18 @@
 EOF
 			$ask = prompt("Find httpd.conf files? ", 'y');
 			@conf = findfiles('httpd.conf') if $ask =~ /^\s*y/i;
-			$Cfg->setval('base', 'serverconf', join(" ", @conf));
 		}
 	}
-	sethistory(@conf);
-	$httpdconf = prompt("Enter path to httpd.conf file: ", $conf[0])
-		if $not_set;
 
+	sethistory(@conf);
+	if ($not_set) {
+		$httpdconf = prompt("Enter path to httpd.conf file: ", $conf[0]);
+		$Cfg->setval('base', 'serverconf', $httpdconf);
+	}
+	else {
+		$httpdconf = shift @conf;
+	}
 	last FINDCONF if $httpdconf =~ /^none$/i;
-	$Cfg->setval('base', 'serverconf', $httpdconf);
 
 	if($httpdconf) {
 		$Servers = conf_parse_http($httpdconf);
@@ -890,7 +914,7 @@
 			print <<EOF unless $Windows;
 
 This demo configuration sometimes requires root permissions,
-depending on your ISP.  It needs to copy a few files to the CGI
+depending on your ISP. It needs to copy a few files to the CGI
 and HTML directories.
 
 You must either have your own CGI directory, or be able to run
@@ -914,7 +938,7 @@
 catalogs on the same server.
 
 MULTIPLE GROUP is the best way. Put each user in their own group, and
-place the Interchange user in that group.  In this mode, only the user of
+place the Interchange user in that group. In this mode, only the user of
 each catalog and the Interchange server may read database and error files --
 files that may contain sensitive information. If the user's default UMASK
 is 2 on a UNIX system, then this the most troublefree mode of operation.
@@ -971,7 +995,7 @@
 
 There is a "history" mechanism that will allow you to use the up
 and down arrows on your terminal (assuming you have a standard terminal)
-to cycle between possible choices.  This should contain the available
+to cycle between possible choices. This should contain the available
 servers.
 
 EOF
@@ -1013,6 +1037,10 @@
 			sethistory(@history);
 		}
 		$val = prefix($p, 1) || $Cfg->val("base", $p) || $hval;
+		if (! $isroot and defined $IfRoot{$p}) {
+			$Conf{$p} = $val;
+			next;
+		}
 		print "\n";
 		print description($p);
 		print "\n\n";
@@ -1048,7 +1076,7 @@
 print <<EOF if defined $Vend::MakeCat::Prompt_sub;
 
 During many of the following operations, defaults are placed in
-a buffer for you.  You may use the up and down arrows to toggle
+a buffer for you. You may use the up and down arrows to toggle
 between the defaults.
 
 If you made a mistake on a *previous* entry and realize that
@@ -1070,10 +1098,20 @@
 
 	@ask = $Cfg->val('global', 'askconfig');
 
-
+	my $redid;
+	my $next_force;
 	for ($i = 0; $i < scalar @ask; $i++) {
 		$p = $ask[$i];
-		if (defined $History{$p}) {
+		if ($redid) {
+#print("###redo###\n");
+			# Handle the &-d option, don't want to force first time
+			if (defined $next_force and ! $next_force) {
+#print("###force next###\n");
+				$next_force = 1;
+			}
+			$val = $Conf{$p};
+		}
+		elsif (defined $History{$p}) {
 			@history = &{$History{$p}}(prefix($p));
 			sethistory(@history);
 			$val =	prefix($p,1)							||
@@ -1091,19 +1129,42 @@
 			next;
 		}
 		print "\n";
-		print description($p);
-		print "\n\n";
+
+		unless($redid) {
+			print description($p);
+			print "\n\n";
+		}
+		else {
+			undef $redid;
+		}
+
 		my $msg = pretty($p) . "? ";
 		$Conf{$p} = prompt ($msg, $val);
+#print("###force=$Vend::MakeCat::Force###\n");
 		if(defined $Postprocess{$p}) {
 			$Conf{$p} = $Postprocess{$p}->($Conf{$p});
 		}
 		if($Conf{$p} eq '@') {
 			$Conf{$p} = $val;
+			$redid = 1;
+			$next_force = 0 if $next_force;
 			$i--;
 			$i = 0 if $i < 0;
 			redo;
 		}
+		elsif ($Conf{$p} eq '&-d') {
+			print "OK, I will run with defaults after this prompt.\n";
+			$Conf{$p} = $val;
+			$redid = 1;
+			$next_force = 0;
+			redo;
+		}
+
+		if ($next_force) {
+#print("###force now###\n");
+			$Vend::MakeCat::Force = 1;
+		}
+
 		$Cfg->setval("catalog $catalog_name", $p, $Conf{$p});
 	}
 
@@ -1165,43 +1226,53 @@
 
 EOF
 
-	$tempurl  = prompt ("\nPlease re-enter or confirm: ",
+		if ($Vend::MakeCat::Force) {
+			$tempurl = $Conf{sampleurl};
+		} else {
+			$tempurl  = prompt ("\nPlease re-enter or confirm: ",
 						"http://$Conf{servername}/$guessdir");
-
+		}
 	}
 
 	$Conf{sampleurl} = $tempurl;
 
 }
 
-$mvuid = $Windows ? 'everybody' : (getpwnam($Conf{interchangeuser}))[2];
-unless (defined $mvuid) {
-	die "$Conf{interchangeuser} is not a valid user name on this machine.\n";
+if ($Windows) {
+	$mvuid = $catuid = 'everybody';
+	$mvgid = $catgid = 'nogroup';
+}
+elsif ($Conf{relocate}) {
+	$mvuid = $catuid = $mvgid = $catgid = 'nobody';
+}
+else {
+	$mvuid = (getpwnam($Conf{interchangeuser}))[2];
+	die "$Conf{interchangeuser} is not a valid user name on this machine.\n"
+		unless defined $mvuid;
+
+	if ($Conf{interchangegroup}) {
+		$mvgid = getgrnam($Conf{interchangegroup});
+		die "$Conf{interchangegroup} is not a valid group name on this machine.\n"
+			unless defined $mvgid;
+	}
+	else {
+		$mvgid = (getpwnam($Conf{interchangeuser}))[3];
+		$Conf{interchangegroup} = getgrgid($mvgid)
+	}
+
+	($catuid, $catgid) = (getpwnam($Conf{catuser}))[2,3];
+	die "$Conf{catuser} is not a valid user name on this machine.\n"
+		unless defined $catuid;
 }
 
-# Fix supplied by Paul V. Shevtsov
 if($isroot) {
 	chown ($mvuid, $mvgid, $Configfile)
 		or warn "\nCouldn't set ownership of $Configfile: $!\n";
-}
-
-if ($Conf{interchangegroup}) {
-	$mvgid = $Windows ? 'nogroup' : getgrnam($Conf{interchangegroup});
-	unless (defined $mvgid) {
-		die "$Conf{interchangegroup} is not a valid group name on this machine.\n";
+	if(! $Conf{permtype} or $Conf{permtype} =~ /^[MUmu]/) {
+		$Conf{catgroup} = getgrgid($catgid);
 	}
-}
-else {
-	$mvgid = $Windows ? 'nogroup' : (getpwnam($Conf{interchangeuser}))[3];
-}
-
-if($Windows) {
-	($catuid,$catgid) = ('everybody', 'nogroup');
-}
-else {
-	($catuid,$catgid) = (getpwnam($Conf{catuser}))[2,3];
-	unless (defined $catuid) {
-		die "$Conf{catuser} is not a valid user name on this machine.\n";
+	else {
+		$Conf{catgroup} = getgrgid($mvgid);
 	}
 }
 
@@ -1262,22 +1333,50 @@
 		$lm = "i";
 		$Inetmode = 1;
 
+		my $defport;
+		my $defhost;
+
+	  INETASK: {
+		my (@hosts);
+		my (@ports);
 		$prog = "$Conf{relocate}$Conf{vendroot}/src/tlink";
+		my $the_one = sum_it($prog);
 
-		$default = 7786;
-		my $lp;
+		my @poss = glob("$Conf{relocate}$Conf{vendroot}/src/tlink.*.*");
+		for (@poss) {
+			my $name = $_;
+			/tlink\.(.*)\.(\d+)$/
+				or next;
+			my ($h, $p) = ($1, $2);
+			push @hosts, $h;
+			push @ports, $p;
+			my $one = sum_it($_);
+			next unless $one eq $the_one;
+			$defhost = $h;
+			$defport = $p;
+		}
+
+		my %seen;
+		sethistory(grep !$seen{$_}++, @ports);
+		$default = $defport || $Conf{linkport} || 7786;
+		$lp = $lh = '';
 		while(! $lp) {
 			$lp = prompt("TCP socket to use? ", $default);
+			redo INETASK if $lp eq '@';
 			if($lp !~ /^\d+$/ or $lp < 1024) {
 				print "Looking for an integer number > 1024 here.\n";
 				undef $lp;
 			}
 		}
-		$default = 'localhost';
-		my $lh;
+
+		sethistory(grep !$seen{$_}++, @hosts);
+		$default = $defhost || $Conf{linkhost} || 'localhost';
 		while(! $lh) {
 			$lh = prompt("Link host? ", $default);
+			redo INETASK if $lh eq '@';
 		}
+		unlink $prog unless $lh eq $defhost && $lp eq $defport;
+	  } # END INETASK
 	}
 	elsif($ask =~ /^\s*n/i) {
 		$prog = "NONE";
@@ -1445,11 +1544,27 @@
 		close ADDLHELP;
 	}
 	my $said = 0;
+	my $redid;
+	my $next_force;
 	while(<ADDL>) {
 		my $noprompt = '';
+		my $grp;
 		s/\s+$//;
 		s/__MVC_([A-Z0-9]+)(__)?/substitute($1,$2)/eg;
 		my ($var, $prompt, $default) = split /\n/, $_, 3;
+		$var =~ s/\t(.*)//;
+		next unless $var;
+		$grp = $1 || $var;
+
+		if ($redid) {
+#print("###redo###\n");
+			# Handle the &-d option, don't want to force first time
+			if (defined $next_force and ! $next_force) {
+#print("###force next###\n");
+				$next_force = 1;
+			}
+			$val = $Conf{$p};
+		}
 		if($var =~ s/{\s*([A-Z0-9]+)(\s*\S.*?)?\s*}\s*//) {
 			my $param = $1;
 			my $test = $2;
@@ -1473,7 +1588,7 @@
 			sethistory(@history);
 		}
 		unless ($noprompt) {
-			if (defined $help{$ucvar}) {
+			if (defined $help{$ucvar} and ! $redid) {
 				$help{$ucvar} =~ s/__MVC_([A-Z0-9]+)(__)?/substitute($1,$2)/eg;
 				print $help{$ucvar};
 			}
@@ -1484,10 +1599,23 @@
 										|| $Conf{$var}
 										|| $default)
 									);
+			if ($Conf{$var} eq '&-d') {
+				print "OK, I will run with defaults after this prompt.\n";
+				$Conf{$var} = $default;
+				$redid = 1;
+				$next_force = 0;
+				redo;
+			}
 		}
 		else {
 			$Conf{$var} = delete $ENV{"MVC_$ucvar"} || $Conf{$var} || $default;
 		}
+
+		if ($next_force) {
+#print("###force now###\n");
+			$Vend::MakeCat::Force = 1;
+		}
+
 	}
 	close ADDL;
 }
@@ -1495,6 +1623,7 @@
 CRYPTPW: {
 	my $pw = substitute('CRYPTPW', '__');
 	last CRYPTPW unless $pw;
+	last CRYPTPW if substitute('ALREADYCRYPT', '__');
 	my @letters = ('A' .. 'Z', 'a' .. 'z');
 	my $salt = $letters[ int rand(scalar @letters) ];
 	$salt .= $letters[ int rand(scalar @letters) ];
@@ -1508,11 +1637,13 @@
 	print "\nFound system commands to run.\n\n";
 	local ($/) = "";
 	while(<ADDL>) {
+		my $unprompted;
 		s/\s+$//;
 		s/__MVC_([A-Z0-9]+)(__)?/substitute($1,$2)/eg;
 		my ($command, $prompt) = split /\n/, $_, 2;
 		$command =~ s/^\s+//;
 		$command =~ s/\s+$//;
+		$command =~ s/^!// and $unprompted = 1;
 		if($command =~ s/{\s*([A-Z0-9]+)(\s*\S.*?)?\s*}\s*//) {
 			my $param = $1;
 			my $test = $2;
@@ -1525,7 +1656,8 @@
 			next unless $true;
 		}
 		print "$prompt\n\n";
-		my $ans = prompt( qq{run "$command"? }, 'y' );
+		print "Running: $command\n" if $unprompted;
+		my $ans = $unprompted ? 'y' : prompt( qq{run "$command"? }, 'y' );
 		if($ans =~ /^\s*y/i) {
 			system $command;
 			if($?) {
@@ -1612,8 +1744,8 @@
 );
 
 sub set_owner {
+	return unless $> == 0;
 	my($file) = @_;
-	return unless $isroot;
 	my ($user, $group) = ($mvuid, $mvgid);
 	if($Conf{permtype} =~ /^m/i) { $user = $catuid; $group = $catgid; }
 	elsif($Conf{permtype} =~ /^g/i) { $group = $catgid; }
@@ -1747,6 +1879,20 @@
 		}
 
 		print "done.\n";
+
+		if($CGIwrap and $isroot) {
+			print <<EOF;
+Since you selected the SUEXEC/CGIwrap option and are root, we aren't sure
+which user and group you intended to own the link program. We have selected
+the catalog user's UID/GID ($catuid/$catgid), but this may not match your
+server definition. If you get a server error, change the ownership to its
+proper value and ensure that the SUID bit is turned off on the link
+program ($cginame).
+
+EOF
+			chown($catuid, $catgid, $cginame) or die "\nchown $cginame: $!\n";
+			prompt("Press <ENTER> to continue....");
+		}
 	}
 
 	my $chg_to_catuser = sub {
@@ -1770,15 +1916,16 @@
 			chdir "$Conf{relocate}$Conf{vendroot}"
 				or die "\nchdir $Conf{relocate}$Conf{vendroot}: $!\n";
 			# remember directories so we can chown below
-			chdir "share" or die "\nchdir 'share': $!\n";
+			chdir "share" or die "error.\nchdir 'share': $!\n";
 			map { push @sharedirs, $_ if -d $_ } glob('*');
 			chdir "..";
-			# copy everything except some HTML help file stuff
-			my $exclude_pattern = '((^|/)src(/|$)|\.pl$)';
-			copy_dir("share", "$Conf{relocate}$Conf{sharedir}", $exclude_pattern) or die;
+			copy_dir("share", "$Conf{relocate}$Conf{sharedir}") or die;
 		};
-		if ($@) {
-			print "\nError installing share/ files: $@\n" if $@;
+		if (! @sharedirs) {
+			print "none found.\n";
+		}
+		elsif ($@) {
+			print "error.\nError installing share/ files: $@\n";
 		} else {
 			File::Find::find(
 				$chg_to_catuser,
@@ -1869,11 +2016,13 @@
 	print "\nFound additional system commands to run.\n\n";
 	local ($/) = "";
 	while(<ADDL>) {
+		my $unprompted;
 		s/\s+$//;
 		s/__MVC_([A-Z0-9]+)(__)?/substitute($1,$2)/eg;
 		my ($command, $prompt) = split /\n/, $_, 2;
 		$command =~ s/^\s+//;
 		$command =~ s/\s+$//;
+		$command =~ s/^!// and $unprompted = 1;
 		if($command =~ s/{\s*([A-Z0-9]+)(\s*\S.*?)?\s*}\s*//) {
 			my $param = $1;
 			my $test = $2;
@@ -1886,7 +2035,8 @@
 			next unless $true;
 		}
 		print "$prompt\n\n";
-		my $ans = prompt( qq{run "$command"? }, 'y' );
+		print "Running: $command\n" if $unprompted;
+		my $ans = $unprompted ? 'y' : prompt( qq{run "$command"? }, 'y' );
 		if($ans =~ /^\s*y/i) {
 			system $command;
 			if($?) {
@@ -1900,14 +2050,26 @@
 	close ADDL;
 }
 	my $add;
+	my $add_tcp;
+	my $add_inet;
 
 	umask(07) unless $Conf{noumask};
 
 	$add = prefix('nocfg') ? 'n' : 'y';
-	$yes = prompt "Add catalog to $Global::ConfigFile? ", $add;
-
+	if ($Conf{catalogconf}) {
+		$yes = prompt "Add catalog to $Conf{catalogconf}? ", $add;
+	} else {
+		$yes = prompt "Add catalog to $Global::ConfigFile? ", $add;
+	}
 	$add = prefix('norunning') ? 'n' : 'y';
 
+	if($yes and $Inetmode) {
+		$add_tcp = prompt "Add port $lp to TcpMap in interchange.cfg if necessary? ", $add;
+		$add_tcp = is_yes($add_tcp);
+		$add_inet = prompt "Set Interchange to run in INET mode if necessary? ", $add;
+		$add_inet = is_yes($add_inet);
+	}
+
 	if($pid) {
 		$add_to_running = prompt "Add catalog to server running on PID $pid? ", $add;
 		$add_to_running = is_yes($add_to_running);
@@ -1915,20 +2077,31 @@
 
 	my $full = '';
 	my $newcfgline;
+	my $tcpmark;
 
 	$newcfgline = sprintf "%-10s %s %s %s %s\n", 'Catalog',
 				$catalog_name, $Conf{catroot}, $full . $Conf{cgiurl}, $Conf{aliases};
 
 	if( is_yes($yes) ) {
 		my ($newcfgline, $mark, @out);
-		my ($tmpfile) = "$Global::ConfigFile.$$";
-		if (-f $Global::ConfigFile) {
-			File::Copy::copy ($Global::ConfigFile, $tmpfile)
-				or die "\nCouldn't copy $Global::ConfigFile: $!\n";
-		}
-		else {
-			File::Copy::copy("$Global::ConfigFile.dist", $tmpfile);
+		my $tmpfile;
+
+		if ($Conf{catalogconf}) {
+			$tmpfile = "$Conf{catalogconf}.$$";
+			File::Copy::copy ($Conf{catalogconf}, $tmpfile)
+					or die "\nCouldn't copy $Conf{catalogconf}: $!\n";
+        } else {
+        	$tmpfile= "$Global::ConfigFile.$$";
+			if (-f $Global::ConfigFile) {
+				File::Copy::copy ($Global::ConfigFile, $tmpfile)
+					or die "\nCouldn't copy $Global::ConfigFile: $!\n";
+			}	
+			else {
+				File::Copy::copy("$Global::ConfigFile.dist", $tmpfile)
+					or die "\nCouldn't copy $Global::ConfigFile.dist: $!\n";
+			}	
 		}
+
 		open(CFG, "< $tmpfile")
 			or die "\nCouldn't open $tmpfile: $!\n";
 		while(<CFG>) {
@@ -1937,6 +2110,10 @@
 				if s/^(catalog\s+$catalog_name\s+)/#$1/io;
 			$full = is_yes($1)
 				if /^\s*fullurl\s+(.*)/i;
+			if ($add_tcp and /^tcpmap\s+/i and $_ !~ /\b$lh:$lp\b/) {
+				$tcpmark = /^tcpmap\s+[^<]+$/i ? $. : $. + 1;
+				$tcpmark-- if $mark;
+			}
 			push @out, $_;
 		}
 		close CFG;
@@ -1944,11 +2121,35 @@
 		if($full) {
 			$full = $Conf{servername};
 		}
-		open(NEWCFG, ">$Global::ConfigFile")
-			or die "\nCouldn't write $Global::ConfigFile: $!\n";
+
+		if ($Conf{catalogconf}) {
+			open(NEWCFG, ">$Conf{catalogconf}")
+				or die "\nCouldn't write $Conf{catalogconf}: $!\n";
+		} else {
+			open(NEWCFG, ">$Global::ConfigFile")
+				or die "\nCouldn't write $Global::ConfigFile: $!\n";
+		}
 
 		$newcfgline = sprintf "%-13s %s %s %s %s\n", 'Catalog',
 				$catalog_name, $Conf{catroot}, $full . $Conf{cgiurl}, $Conf{aliases};
+
+		if($tcpmark) {
+			$out[$tcpmark] =~ s/\s*$/ $lh:$lp -\n/;
+		}
+
+		if($add_inet) {
+			my $found_inetmode;
+			for(@out) {
+				next unless /^\s*inet_mode\s+/i;
+				$_ = "Inet_Mode Yes\n";
+				$found_inetmode = 1;
+				last;
+			}
+			if(! $found_inetmode) {
+				push @out, "Inet_Mode Yes\n";
+			}
+		}
+
 		if (defined $mark) {
 			print NEWCFG @out[0..$mark-1];
 			print NEWCFG $newcfgline;
@@ -1960,6 +2161,7 @@
 			print NEWCFG $newcfgline;
 			print NEWCFG @out;
 		}
+
 		close NEWCFG || die "close: $!\n";
 		unlink $tmpfile;
 		if($isroot) {
@@ -2079,7 +2281,7 @@
 
 =head1 VERSION
 
-$Id: makecat.PL,v 1.26.4.8 2000/12/05 16:06:17 racke Exp $
+# $Id: makecat.PL,v 1.26.4.9 2003/01/25 22:21:32 racke Exp $
 
 =head1 INTRODUCTION
 
@@ -2226,18 +2428,18 @@
 =item --cgiurl=url_fragment
 
 The path to the CGI link (no server name). For a catalog named
-C<construct>, this would normally be one of:
+C<foundation>, this would normally be one of:
 
-    --cgiurl=/cgi-bin/construct
+    --cgiurl=/cgi-bin/foundation
 
 or 
 
-    --cgiurl=/construct.cgi
+    --cgiurl=/foundation.cgi
 
 
 =item --demotype=template
 
-The template catalog. The default is <construct>.
+The template catalog. The default is <foundation>.
 
 =item --mailorderto=email
 
@@ -2267,6 +2469,14 @@
 
 The URL to prefix images with.
 
+=item --sharedir=directory
+
+The directory where shared admin images go.
+
+=item --shareurl=url
+
+The URL to prefix shared admin images with.
+
 =item --nocfg
 
 Don't add to interchange.cfg.
@@ -2300,24 +2510,29 @@
 
 Don't set umask to the value implied by mode.
 
+=item --catalogconf=file
+
+Use file as configuration file for catalog definitions. This option
+has been designed for the use with Debian installations.
+
 =back
 
 =head1 DESCRIPTION
 
-C<makecat> needs a template catalog to operate on. The I<foundation site> and
-I<construct something> demo templates are distributed with Interchange. You can
+C<makecat> needs a template catalog to operate on. The I<Foundation
+Store> demo template is distributed with Interchange. You can
 also look for additional demo catalogs (mostly for ideas) at
-http://developer.akopia.com/.
+http://interchange.redhat.com/.
 
 B<IMPORTANT NOTE:> You only make a catalog once. All further configuration
 is done by editing the files within the I<catalog directory>.
 
 A catalog template contains an image of a configured catalog. The best
-way to see what the makecat program does is to configure the 'construct'
+way to see what the makecat program does is to configure the 'foundation'
 demo and then run a recursive C<diff> on the template and configured
 catalog directories:
 
-  diff -r interchange/construct catalogs/construct
+  diff -r interchange/foundation catalogs/foundation
 
 You will see that the files are mostly the same, except that certain
 macro strings have been replaced with the answers you gave to the script.
@@ -2344,7 +2559,7 @@
     MVC_DOCUMENTROOT MVC_VENDROOT
     MVC_ENCRYPTOR
 
-(Not all of these are present in the construct template, and
+(Not all of these are present in the foundation template, and
 quite a few more may be defined.)  In fact, any environment variable that
 is set and begins with MVC_ will be substituted for by the C<makecat>
 script. So if you wanted to set up a configurable parameter to customize
@@ -2363,7 +2578,7 @@
 software directory, i.e. where C<interchange.cfg> resides. You normally do
 not edit files in the template directory.  If you want to try creating
 your own template, it is recommended that you name it something besides
-construct and copy the C<construct> demo directory to it as a starting point.
+foundation and copy the C<foundation> demo directory to it as a starting point.
 Templates are normally placed in the Interchange base directory, but can
 be located anywhere -- the script will prompt you for location if it
 cannot find a template.
@@ -2416,7 +2631,7 @@
     We need to create an SQL database for your Interchange
     database tables.
      
-    Run command "mysqladmin create test_construct"?
+    Run command "mysqladmin create test_foundation"?
 
 If the response is "y" or "yes", then the command will be run
 by passing it through the Perl system() function. As with any
@@ -2434,7 +2649,7 @@
 to describe in this venue. Complete information can be found at
 its web site:
 
-        http://www.akopia.com/
+        http://interchange.redhat.com/
 
 Interchange requires Perl 5.005 or higher; more information on Perl can
 be seen at:
@@ -2443,7 +2658,7 @@
 
 =head1 SEE ALSO
 
-mvdocs(8), interchange(1), http://www.akopia.com/
+interchange(1)
 
 =head1 LICENSE
 
@@ -2453,49 +2668,28 @@
 
 =head1 COPYRIGHT
 
-Copyright 1995-2000, Akopia, Inc.. All rights reserved except as in the
+Copyright 1995-2002, Red Hat, Inc. All rights reserved except as in the
 license.
 
 =cut
 
 =head1 AUTHOR
 
-Mike Heins, <heins@akopia.com>. Please do not contact the author for
-direct help with the system. Use the Interchange mail lists:
+Mike Heins, <mheins@redhat.com>. Please do not contact the author for
+direct help with the system. Use the Interchange mail list:
 
-    interchange-users	(English, subscribe at http://developer.akopia.com/)
+    interchange-users
 
-General information and documentation for Interchange is at:
+Information on subscribing to the list, and general information and
+documentation for Interchange is at:
 
-    http://www.akopia.com/
-    http://developer.akopia.com/
+    http://interchange.redhat.com/
 
 =cut
 
 __END__
 
-# Sample catalog definition
-[catalog construct]
-basedir         =
-catroot         =
-catuser         =
-cgibase         =
-cgibin          =
-cgidir          =
-cgiurl          =
-demotype        = construct
-documentroot    =
-imagedir        =
-imageurl        =
-mailorderto     =
-interchangegroup=
-interchangeuser =
-samplehtml      =
-sampleurl       =
-servername      =
-vendroot        =
-
-[catalog barry]
+[catalog foundation]
 basedir         =
 catroot         =
 catuser         =
@@ -2503,7 +2697,7 @@
 cgibin          =
 cgidir          =
 cgiurl          =
-demotype        = barry
+demotype        = foundation
 documentroot    =
 imagedir        =
 imageurl        =
@@ -2515,27 +2709,6 @@
 servername      =
 vendroot        =
 
-# Simple catalog definition
-[catalog simple]
-basedir         =
-catroot         =
-catuser         =
-cgibase         =
-cgibin          =
-cgidir          =
-cgiurl          =
-demotype        = simple
-documentroot    =
-imagedir        =
-imageurl        =
-mailorderto     =
-interchangegroup=
-interchangeuser =
-samplehtml      =
-sampleurl       = 
-servername      =
-vendroot        =
-
 [base]
 permtype=
 basedir=
@@ -2549,6 +2722,7 @@
 serverconf=
 servername=
 vendroot=
+linkmode=
 
 # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
 #
@@ -2574,6 +2748,7 @@
 documentroot
 imagedir
 imageurl
+linkmode
 mailorderto
 interchangegroup
 interchangeuser
@@ -2616,6 +2791,7 @@
 vendroot
 basedir
 interchangeuser
+linkmode
 EOF
 
 # 
@@ -2671,11 +2847,4 @@
 sharedir=1
 shareurl=1
 vendroot=1
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}
+linkmode=1



1.7.4.1   +6 -41     interchange/scripts/offline.PL


rev 1.7.4.1, prev_rev 1.7
Index: offline.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/offline.PL,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- offline.PL	25 Sep 2000 16:42:51 -0000	1.7
+++ offline.PL	25 Jan 2003 22:21:32 -0000	1.7.4.1
@@ -1,41 +1,14 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange database builder and indexer
 #
-# $Id: offline.PL,v 1.7 2000/09/25 16:42:51 zarko Exp $
+# $Id: offline.PL,v 1.7.4.1 2003/01/25 22:21:32 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
-# This program was originally based on Vend 0.2
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# Portions from Vend 0.3
-# Copyright 1995 by Andrew M. Wilcox <awilcox@world.std.com>
-#
-# See the file 'Changes' for information.
+# This program was originally based on Vend 0.2 and 0.3
+# Copyright 1995-96 by Andrew M. Wilcox <amw@wilcoxsolutions.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -274,7 +247,7 @@
 
 =head1 VERSION
 
-$Id: offline.PL,v 1.7 2000/09/25 16:42:51 zarko Exp $
+# $Id: offline.PL,v 1.7.4.1 2003/01/25 22:21:32 racke Exp $
 
 =head1 DESCRIPTION
 
@@ -282,14 +255,6 @@
 
 =head1 SEE ALSO
 
-mvdocs(8), interchange(1), http://www.akopia.com/
+interchange(1), http://interchange.redhat.com/
 
 =cut
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.8.4.1   +6 -38     interchange/scripts/restart.PL


rev 1.8.4.1, prev_rev 1.8
Index: restart.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/restart.PL,v
retrieving revision 1.8
retrieving revision 1.8.4.1
diff -u -r1.8 -r1.8.4.1
--- restart.PL	25 Sep 2000 16:24:05 -0000	1.8
+++ restart.PL	25 Jan 2003 22:21:32 -0000	1.8.4.1
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange restarter
 #
-# $Id: restart.PL,v 1.8 2000/09/25 16:24:05 zarko Exp $
+# $Id: restart.PL,v 1.8.4.1 2003/01/25 22:21:32 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# See the file 'Changes' for information.
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -107,8 +83,8 @@
 if ($< == 0) {
 	$name = get_id() || 'YOUR_INTERCHANGE_USER_NAME';
 	die "Interchange user ID not set in $Global::VendRoot/_uid.\n" if $name eq 'YOUR_INTERCHANGE_USER_NAME';
-	if(-t) {
-		print <<EOM unless $force;
+	if(! $force and -t) {
+		print <<EOM;
 
 The Interchange server should not be run as root. It should run
 as a the user name you configured in when you set up the catalogs.
@@ -175,18 +151,10 @@
 
 =head1 SEE ALSO
 
-interchange(1), mvdocs(8), http://www.akopia.com/
+interchange(1), http://interchange.redhat.com/
 
 =head1 AUTHOR
 
-Mike Heins, <heins@akopia.com>
+Mike Heins, <mheins@redhat.com>
 
 
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



1.7.4.1   +6 -36     interchange/scripts/update.PL


rev 1.7.4.1, prev_rev 1.7
Index: update.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/update.PL,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -u -r1.7 -r1.7.4.1
--- update.PL	25 Sep 2000 16:08:06 -0000	1.7
+++ update.PL	25 Jan 2003 22:21:32 -0000	1.7.4.1
@@ -1,35 +1,11 @@
-#$self = {
-#	INSTALLPRIVLIB => '/usr/local/interchange/lib',
-#	INSTALLARCHLIB => '/usr/local/interchange',
-#};
-
-use Config;
-require 'scripts/initp.pl';
-
-sub doit {
-	my ($key) = @_;
-	my $val;
-	if ($MV::Self->{RPMBUILDDIR} and $val = $MV::Self->{$key}) {
-		$val =~ s!^$MV::Self->{RPMBUILDDIR}/!/!; 
-		return $val;
-	}
-	return $MV::Self->{$key} unless $key =~ /[a-z]/;
-	return $Config{$key};
-}
-
-DOIT: {
-	local ($/);
-	local($_) = <<'_EoP_';
 #!/usr/bin/perl
 ##!~_~perlpath~_~
 #
 # Interchange database updater
 #
-# $Id: update.PL,v 1.7 2000/09/25 16:08:06 zarko Exp $
+# $Id: update.PL,v 1.7.4.1 2003/01/25 22:21:32 racke Exp $
 #
-# Copyright (C) 1996-2000 Akopia, Inc. <info@akopia.com>
-#
-# See the file 'Changes' for information.
+# Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -233,6 +209,8 @@
 
 chdir $dir or die "Couldn't change directory to $dir: $!\n";
 
+$Vend::ExternalProgram = $Vend::Quiet = 1;
+
 $Vend::Cfg = config($name, $dir, "$dir/etc", ($subconfig || undef));
 $::Variable = $Vend::Cfg->{Variable};
 
@@ -333,17 +311,9 @@
 
 =head1 SEE ALSO
 
-http://www.akopia.com/
+http://interchange.redhat.com/
 
 =head1 AUTHOR
 
-Mike Heins, <heins@akopia.com>
+Mike Heins, <mheins@redhat.com>
 
-_EoP_
-	s{.*\n(#(.*)~_~(\w+)~_~(.*))}{$2 . doit($3) . "$4\n$1"}eg;
-	my $file = $0;
-	$file =~ s/\.PL$//;
-	open(OUT, ">$file") 
-		or die "Create $file: $!\n";
-	print OUT $_;
-}



No                   revision



No                   revision



1.1.2.1   +1 -1      interchange/scripts/findtags.PL


rev 1.1.2.1, prev_rev 1.1
Index: findtags.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/findtags.PL,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1
--- findtags.PL	10 Aug 2002 17:34:03 -0000	1.1
+++ findtags.PL	25 Jan 2003 22:21:32 -0000	1.1.2.1
@@ -3,7 +3,7 @@
 #
 # Interchange session expiration for all catalogs
 #
-# $Id: findtags.PL,v 1.1 2002/08/10 17:34:03 mheins Exp $
+# $Id: findtags.PL,v 1.1.2.1 2003/01/25 22:21:32 racke Exp $
 #
 # Copyright (C) 1996-2001 Red Hat, Inc. <interchange@redhat.com>
 #



1.1.2.1   +0 -0      interchange/scripts/ic_mod_perl.PL


rev 1.1.2.1, prev_rev 1.1
Index: ic_mod_perl.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/ic_mod_perl.PL,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.6.2.1   +1 -1      interchange/scripts/newcat.PL


rev 2.6.2.1, prev_rev 2.6
Index: newcat.PL
===================================================================
RCS file: /var/cvs/interchange/scripts/newcat.PL,v
retrieving revision 2.6
retrieving revision 2.6.2.1
diff -u -r2.6 -r2.6.2.1
--- newcat.PL	27 Jun 2002 18:55:50 -0000	2.6
+++ newcat.PL	25 Jan 2003 22:21:32 -0000	2.6.2.1
@@ -3,7 +3,7 @@
 #
 # Interchange catalog configurator with curses
 #
-# $Id: newcat.PL,v 2.6 2002/06/27 18:55:50 jon Exp $
+# $Id: newcat.PL,v 2.6.2.1 2003/01/25 22:21:32 racke Exp $
 #
 # Copyright (C) 1996-2002 Red Hat, Inc. <interchange@redhat.com>
 #



No                   revision



No                   revision



1.2.2.1   +0 -0      interchange/share/interchange/ic.css


rev 1.2.2.1, prev_rev 1.2
Index: ic.css
===================================================================
RCS file: /var/cvs/interchange/share/interchange/ic.css,v
retrieving revision 1.2
retrieving revision 1.2.2.1
diff -u -r1.2 -r1.2.2.1



1.1.2.1   +0 -0      interchange/share/interchange/ic1.css


rev 1.1.2.1, prev_rev 1.1
Index: ic1.css
===================================================================
RCS file: /var/cvs/interchange/share/interchange/ic1.css,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/share/interchange/en_US/az.gif


<<az.gif: GIF image data, version 87a, 20 x 22,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/bg.gif


<<bg.gif: GIF image data, version 89a, 1 x 1,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/box_checked.gif


<<box_checked.gif: GIF image data, version 89a, 15 x 15,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/box_empty.gif


<<box_empty.gif: GIF image data, version 89a, 15 x 15,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/delete.gif


<<delete.gif: GIF image data, version 89a, 20 x 20,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/delsm.gif


<<delsm.gif: GIF image data, version 89a, 13 x 11,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/doc.gif


<<doc.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/down.gif


<<down.gif: GIF image data, version 89a, 20 x 22,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/folder.gif


<<folder.gif: GIF image data, version 89a, 20 x 22,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/folder.open.gif


<<folder.open.gif: GIF image data, version 89a, 27 x 22,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/forward.gif


<<forward.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/generic.gif


<<generic.gif: GIF image data, version 89a, 16 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/graylogo.gif


<<graylogo.gif: GIF image data, version 89a, 121 x 32,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/icfooter.gif


<<icfooter.gif: GIF image data, version 89a, 90 x 15,>>


1.1.4.1   +0 -0      interchange/share/interchange/en_US/iclogo.gif


<<iclogo.gif: GIF image data, version 89a, 127 x 34,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_download.gif


<<ico_download.gif: GIF image data, version 89a, 9 x 12,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_duck.gif


<<ico_duck.gif: GIF image data, version 89a, 16 x 14,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_export.gif


<<ico_export.gif: GIF image data, version 89a, 15 x 15,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_folder.gif


<<ico_folder.gif: GIF image data, version 89a, 13 x 10,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_import.gif


<<ico_import.gif: GIF image data, version 89a, 15 x 15,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_magnify.gif


<<ico_magnify.gif: GIF image data, version 89a, 16 x 15,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_pen.gif


<<ico_pen.gif: GIF image data, version 89a, 14 x 11,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/ico_upload.gif


<<ico_upload.gif: GIF image data, version 89a, 11 x 12,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_config.gif


<<icon_config.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_design.gif


<<icon_design.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_error.gif


<<icon_error.gif: GIF image data, version 89a, 16 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/icon_ic.gif


<<icon_ic.gif: GIF image data, version 89a, 25 x 25,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_item.gif


<<icon_item.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_merch.gif


<<icon_merch.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_orders.gif


<<icon_orders.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_pages.gif


<<icon_pages.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_people.gif


<<icon_people.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_regen.gif


<<icon_regen.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/icon_stats.gif


<<icon_stats.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/index.gif


<<index.gif: GIF image data, version 89a, 20 x 22,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/interchange.css


rev 1.1.2.1, prev_rev 1.1
Index: interchange.css
===================================================================
RCS file: /var/cvs/interchange/share/interchange/en_US/interchange.css,v
retrieving revision 1.1
retrieving revision 1.1.2.1
diff -u -r1.1 -r1.1.2.1



2.0.4.1   +0 -0      interchange/share/interchange/en_US/layout.gif


<<layout.gif: GIF image data, version 89a, 20 x 22,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/left.gif


<<left.gif: GIF image data, version 89a, 20 x 22,>>


1.2.2.1   +0 -0      interchange/share/interchange/en_US/logo.gif


<<logo.gif: GIF image data, version 89a, 121 x 32,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/meta.png


<<meta.png: PNG image data, 16 x 16, 8-bit gray+alpha, non-interlaced>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/minus.gif


<<minus.gif: GIF image data, version 89a, 20 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/photo.jpg


<<photo.jpg: JPEG image data, JFIF standard 1.01, resolution (DPI), 72 x 72>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/plus.gif


<<plus.gif: GIF image data, version 89a, 20 x 20,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/poweredby.gif


<<poweredby.gif: GIF image data, version 89a, 82 x 33,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/right.gif


<<right.gif: GIF image data, version 89a, 20 x 22,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/smindex.gif


<<smindex.gif: GIF image data, version 89a, 16 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/specmeta.png


<<specmeta.png: PNG image data, 20 x 16, 8-bit/color RGBA, non-interlaced>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/text.gif


<<text.gif: GIF image data, version 89a, 16 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/tminus.gif


<<tminus.gif: GIF image data, version 89a, 16 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/en_US/tplus.gif


<<tplus.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/transfer.gif


<<transfer.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/unknown.gif


<<unknown.gif: GIF image data, version 89a, 16 x 16,>>


2.0.4.1   +0 -0      interchange/share/interchange/en_US/up.gif


<<up.gif: GIF image data, version 89a, 20 x 22,>>


No                   revision



No                   revision



1.1.2.1   +0 -0      interchange/share/interchange/u/subtab_down_fill.gif


<<subtab_down_fill.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/subtab_down_left.gif


<<subtab_down_left.gif: GIF image data, version 89a, 16 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/subtab_down_right.gif


<<subtab_down_right.gif: GIF image data, version 89a, 16 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/subtab_fill.gif


<<subtab_fill.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/subtab_filllwr.gif


<<subtab_filllwr.gif: GIF image data, version 89a, 400 x 2,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/subtab_left.gif


<<subtab_left.gif: GIF image data, version 89a, 16 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/subtab_right.gif


<<subtab_right.gif: GIF image data, version 89a, 16 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_dark_left.gif


<<tab_dark_left.gif: GIF image data, version 89a, 14 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_dark_right.gif


<<tab_dark_right.gif: GIF image data, version 89a, 2 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_down_fill.gif


<<tab_down_fill.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_down_left.gif


<<tab_down_left.gif: GIF image data, version 89a, 24 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_down_right.gif


<<tab_down_right.gif: GIF image data, version 89a, 24 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_fill.gif


<<tab_fill.gif: GIF image data, version 89a, 1 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_left.gif


<<tab_left.gif: GIF image data, version 89a, 24 x 20,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_light_left.gif


<<tab_light_left.gif: GIF image data, version 89a, 17 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_light_right.gif


<<tab_light_right.gif: GIF image data, version 89a, 2 x 16,>>


1.1.2.1   +0 -0      interchange/share/interchange/u/tab_right.gif


<<tab_right.gif: GIF image data, version 89a, 24 x 20,>>