0.12_07 commit r0_12_07
authorTony Cook <tony@develop-help.com>
Fri, 16 Aug 2002 00:49:13 +0000 (00:49 +0000)
committertony <tony@45cb6cf1-00bc-42d2-bb5a-07f51df49f94>
Fri, 16 Aug 2002 00:49:13 +0000 (00:49 +0000)
29 files changed:
Makefile
schema/bse.sql
site/cgi-bin/bse.cfg
site/cgi-bin/modules/BSE/Edit/Article.pm
site/cgi-bin/modules/BSE/Edit/Catalog.pm
site/cgi-bin/modules/BSE/Edit/Product.pm
site/cgi-bin/modules/BSE/TB/AdminBase.pm
site/cgi-bin/modules/BSE/TB/AdminBases.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminGroup.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminGroups.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminMembership.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminMemberships.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminPerm.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminPerms.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminUser.pm [new file with mode: 0644]
site/cgi-bin/modules/BSE/TB/AdminUsers.pm [new file with mode: 0644]
site/cgi-bin/shop.pl
site/docs/access.pod
site/docs/bse.pod
site/docs/config.pod
site/templates/admin/article_img.tmpl
site/templates/admin/edit_1.tmpl
site/templates/admin/edit_2.tmpl
site/templates/admin/edit_catalog.tmpl
site/templates/admin/edit_product.tmpl
site/templates/cart_base.tmpl
site/templates/shopitem.tmpl
site/templates/user/userpage_base.tmpl
t/t00smoke.t

index 8ac8ed2bcb0efa9bc2432524e8e2bdd0438e6aea..007597865e1e339c1d85de83571bea45bb1edc54 100755 (executable)
--- a/Makefile
+++ b/Makefile
@@ -1,4 +1,4 @@
-VERSION=0.12_06
+VERSION=0.12_07
 DISTNAME=bse-$(VERSION)
 DISTBUILD=$(DISTNAME)
 DISTTAR=../$(DISTNAME).tar
index ced97e9e0a52f1a45a2c4e82920634708e573c9c..42f31e59be5f0489ed524f4e049ba03e2b51ee4a 100644 (file)
@@ -457,4 +457,47 @@ create table email_blacklist (
 
   primary key (id),
   unique (email)
-);
\ No newline at end of file
+);
+
+drop table if exists admin_base;
+create table admin_base (
+  id integer not null auto_increment,
+  type char not null,
+  primary key (id)
+);
+
+drop table if exists admin_users;
+create table admin_users (
+  base_id integer not null,
+  logon varchar(60) not null,
+  name varchar(255) not null,
+  password varchar(80) not null,
+  perm_map varchar(255) not null,
+  primary key (base_id),
+  unique (logon)
+);
+
+drop table if exists admin_groups;
+create table admin_groups (
+  base_id integer not null,
+  name varchar(80) not null,
+  description varchar(255) not null,
+  perm_map varchar(255) not null,
+  primary key (base_id),
+  unique (name)
+);
+
+drop table if exists admin_membership;
+create table admin_membership (
+  user_id integer not null,
+  group_id integer not null,
+  primary key (user_id, group_id)
+);
+
+drop table if exists admin_perms;
+create table admin_perms (
+  object_id integer not null,
+  admin_id integer not null,
+  perm_map varchar(255),
+  primary key (object_id, admin_id)
+);
index f1fa94b29e0192f4cdf23262cd6277436dd7074a..0f750ba907eaa0882084fbc18c2807353ca7b8d5 100644 (file)
@@ -86,3 +86,24 @@ override=1
 
 [articles]
 shop=3
+
+[level 1]
+template=common/default.tmpl
+
+[level 2]
+template=common/default.tmpl
+
+[level 3]
+template=common/default.tmpl
+
+[level 4]
+template=common/default.tmpl
+
+[level 5]
+template=common/default.tmpl
+
+[catalogs]
+template=catalog.tmpl
+
+[products]
+template=shopitem.tmpl
index b15f5ca72380b994911cfa3996f2cfdd147258d8..85917fb0cb34d31b9197864c8a2dad665df1752d 100644 (file)
@@ -291,6 +291,22 @@ sub tag_is {
   return $templater->perform($acts, $func, $funcargs) ? 'Yes' : 'No';
 }
 
+sub default_template {
+  my ($self, $article, $cfg, $templates) = @_;
+
+  if ($article->{parentid}) {
+    my $template = $cfg->entry("children of $article->{parentid}", "template");
+    return $template 
+      if $template && grep $_ eq $template, @$templates;
+  }
+  if ($article->{level}) {
+    my $template = $cfg->entry("level $article->{level}", "template");
+    return $template 
+      if $template && grep $_ eq $template, @$templates;
+  }
+  return $templates->[0];
+}
+
 sub tag_templates {
   my ($self, $article, $cfg, $cgi) = @_;
 
@@ -300,7 +316,8 @@ sub tag_templates {
     $default = $article->{template};
   }
   else {
-    $default = $templates[0];
+    my @options;
+    $default = $self->default_template($article, $cfg, \@templates);
   }
   return $cgi->popup_menu(-name=>'template',
                          -values=>\@templates,
@@ -357,6 +374,11 @@ sub template_dirs {
       push @dirs, split /,/, $dirs;
     }
   }
+  if ($article->{level}) {
+    push @dirs, $article->{level};
+    my $dirs = $self->{cfg}->entry("level $article->{level}", 'template_dirs');
+    push @dirs, split /,/, $dirs if $dirs;
+  }
 
   @dirs;
 }
@@ -1042,6 +1064,9 @@ sub save_new {
   $article->setLink($self->make_link($article));
   $article->save();
 
+  use Util 'generate_article';
+  generate_article($articles, $article) if $Constants::AUTO_GENERATE;
+
   my $urlbase = $self->{cfg}->entryVar('site', 'url');
   return BSE::Template->get_refresh($urlbase . $article->{admin}, 
                                    $self->{cfg});
@@ -1129,6 +1154,10 @@ sub save {
   }
 
   $article->save();
+
+  use Util 'generate_article';
+  generate_article($articles, $article) if $Constants::AUTO_GENERATE;
+
   my $urlbase = $self->{cfg}->entryVar('site', 'url');
   return BSE::Template->get_refresh($urlbase . $article->{admin}, 
                                    $self->{cfg});
index 3b863579ed28c44368a5dff80d3b6d63e898cfe1..4627fb0e6ce271d302eddcfc90e491a804c9df3c 100644 (file)
@@ -88,5 +88,15 @@ sub child_types {
   return qw(BSE::Edit::Product BSE::Edit::Catalog);
 }
 
+sub default_template {
+  my ($self, $article, $cfg, $templates) = @_;
+
+  my $template = $cfg->entry('catalogs', 'template');
+  return $template
+    if $template && grep $_ eq $template, @$templates;
+
+  return $self->SUPER::default_template($article, $cfg, $templates);
+}
+
 1;
 
index bed46647d157c9f6d74ef518a3c2a89b9ecf0af6..84f8102d1703ea0aa336ebd8f5f90beffd7cbaf8 100644 (file)
@@ -203,4 +203,14 @@ sub fill_old_data {
   return $self->SUPER::fill_old_data($req, $article, $src);
 }
 
+sub default_template {
+  my ($self, $article, $cfg, $templates) = @_;
+
+  my $template = $cfg->entry('catalogs', 'template');
+  return $template
+    if $template && grep $_ eq $template, @$templates;
+
+  return $self->SUPER::default_template($article, $cfg, $templates);
+}
+
 1;
index f37ba040a4a45d758be940f01d9f9c7aebb1df9d..7425ae5731b64455a36ec1d47ee01b80276e88f2 100644 (file)
@@ -1,10 +1,9 @@
 package BSE::TB::AdminBase;
 use strict;
-bse base qw(Squirrel::Table);
-use BSE::TB::AdminBase;
+use base qw(Squirrel::Row);
 
-sub rowClass {
-  return 'BSE::TB::AdminBase';
+sub columns {
+  return qw/id type/;
 }
 
 1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminBases.pm b/site/cgi-bin/modules/BSE/TB/AdminBases.pm
new file mode 100644 (file)
index 0000000..24db729
--- /dev/null
@@ -0,0 +1,10 @@
+package BSE::TB::AdminBases;
+use strict;
+use base 'Squirrel::Table';
+use BSE::TB::AdminBase;
+
+sub rowClass {
+  return 'BSE::TB::AdminBase';
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminGroup.pm b/site/cgi-bin/modules/BSE/TB/AdminGroup.pm
new file mode 100644 (file)
index 0000000..1caa231
--- /dev/null
@@ -0,0 +1,14 @@
+package BSE::TB::AdminGroup;
+use strict;
+use base qw(BSE::TB::AdminBase);
+
+sub columns {
+  return ($_[0]->SUPER::columns,
+         qw/base_id name description perm_map/;
+}
+
+sub bases {
+  return { base_id=>{ class=>'BSE::TB::AdminBase' } };
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminGroups.pm b/site/cgi-bin/modules/BSE/TB/AdminGroups.pm
new file mode 100644 (file)
index 0000000..f8cc225
--- /dev/null
@@ -0,0 +1,10 @@
+package BSE::TB::AdminGroups;
+use strict;
+use base 'Squirrel::Table';
+use BSE::TB::AdminGroup;
+
+sub rowClass {
+  return 'BSE::TB::AdminGroup';
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminMembership.pm b/site/cgi-bin/modules/BSE/TB/AdminMembership.pm
new file mode 100644 (file)
index 0000000..1829e65
--- /dev/null
@@ -0,0 +1,10 @@
+package BSE::TB::AdminMembership;
+# this probably won't be used
+use strict;
+use base qw(Squirrel::Row);
+
+sub columns {
+  return qw/user_id group_id/;
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminMemberships.pm b/site/cgi-bin/modules/BSE/TB/AdminMemberships.pm
new file mode 100644 (file)
index 0000000..a6827e5
--- /dev/null
@@ -0,0 +1,10 @@
+package BSE::TB::AdminMemberships;
+use strict;
+use base 'Squirrel::Table';
+use BSE::TB::AdminMembership;
+
+sub rowClass {
+  return 'BSE::TB::AdminMembership';
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminPerm.pm b/site/cgi-bin/modules/BSE/TB/AdminPerm.pm
new file mode 100644 (file)
index 0000000..1e927ad
--- /dev/null
@@ -0,0 +1,10 @@
+package BSE::TB::AdminPerm;
+# this probably won't be used
+use strict;
+use base qw(Squirrel::Row);
+
+sub columns {
+  return qw/object_id admin_id/;
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminPerms.pm b/site/cgi-bin/modules/BSE/TB/AdminPerms.pm
new file mode 100644 (file)
index 0000000..76186d5
--- /dev/null
@@ -0,0 +1,10 @@
+package BSE::TB::AdminPerms;
+use strict;
+use base 'Squirrel::Table';
+use BSE::TB::AdminPerm;
+
+sub rowClass {
+  return 'BSE::TB::AdminPerm';
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminUser.pm b/site/cgi-bin/modules/BSE/TB/AdminUser.pm
new file mode 100644 (file)
index 0000000..422fd2d
--- /dev/null
@@ -0,0 +1,14 @@
+package BSE::TB::AdminUser;
+use strict;
+use base qw(BSE::TB::AdminBase);
+
+sub columns {
+  return ($_[0]->SUPER::columns,
+         qw/base_id logon name password perm_map/;
+}
+
+sub bases {
+  return { base_id=>{ class=>'BSE::TB::AdminBase' } };
+}
+
+1;
diff --git a/site/cgi-bin/modules/BSE/TB/AdminUsers.pm b/site/cgi-bin/modules/BSE/TB/AdminUsers.pm
new file mode 100644 (file)
index 0000000..a62f682
--- /dev/null
@@ -0,0 +1,10 @@
+package BSE::TB::AdminUsers;
+use strict;
+use base 'Squirrel::Table';
+use BSE::TB::AdminUser;
+
+sub rowClass {
+  return 'BSE::TB::AdminUser';
+}
+
+1;
index a15c27ed5a8da5846fa1123f772e27f3987789ee..4891e2c0270f1aeef91d70983ef00710ad4dce31 100755 (executable)
@@ -88,26 +88,42 @@ show_cart();
 
 sub add_item {
   my $addid = param('id');
+  $addid ||= '';
   my $quantity = param('quantity');
+  $quantity ||= 1;
   my $product;
   $product = Products->getByPkey($addid) if $addid;
-  $product or return show_cart(); # oops
+  $product or return show_cart("Cannot find product $addid"); # oops
 
   # collect the product options
-  my @options = map scalar param($_), split /,/, $product->{options};
-  grep(!defined, @options) 
-    and return show_cart(); # invalid parameter
+  my @options;
+  my @opt_names = split /,/, $product->{options};
+  my @not_def;
+  for my $name (@opt_names) {
+    my $value = param($name);
+    push @options, $value;
+    unless (defined $value) {
+      push @not_def, $name;
+    }
+  }
+  @not_def
+    and return show_cart("Some product options (@not_def) not supplied");
   my $options = join(",", @options);
   
   # the product must be non-expired and listed
-  my $today = epoch_to_sql(time);
-  $product->{release} le $today and $today le $product->{expire}
-    or return show_cart();
-  $product->{listed} or return show_cart();
+  use BSE::Util::SQL qw(now_sqldate);
+  (my $comp_release = $product->{release}) =~ s/ .*//;
+  (my $comp_expire = $product->{expire}) =~ s/ .*//;
+  my $today = now_sqldate();
+  $comp_release le $today
+    or return show_cart("Product has not been released yet");
+  $today le $comp_expire
+    or return show_cart("Product has expired");
+  $product->{listed} or return show_cart("Product not available");
 
   # we need a natural integer quantity
   $quantity =~ /^\d+$/
-    or return show_cart();
+    or return show_cart("Invalid quantity");
 
   my @cart = @{$session{cart}};
  
@@ -123,6 +139,7 @@ sub add_item {
 }
 
 sub show_cart {
+  my ($msg) = @_;
   my @cart = @{$session{cart}};
   my @cart_prods = map { Products->getByPkey($_->{productId}) } @cart;
   my $item_index = -1;
@@ -133,6 +150,8 @@ sub show_cart {
   my %custom_state = %{$session{custom}};
 
   BSE::Custom->enter_cart(\@cart, \@cart_prods, \%custom_state); 
+  $msg = '' unless defined $msg;
+  $msg = CGI::escapeHTML($msg);
 
   my %acts;
   %acts =
@@ -140,6 +159,7 @@ sub show_cart {
      BSE::Custom->cart_actions(\%acts, \@cart, \@cart_prods, \%custom_state),
      shop_cart_tags(\%acts, \@cart, \@cart_prods, \%session, $CGI::Q),
      basic_tags(\%acts),
+     msg => $msg,
     );
   $session{custom} = \%custom_state;
 
@@ -340,9 +360,15 @@ sub prePurchase {
     if (!$product) {
       return show_cart("Product $item->{productId} not found");
     }
-    elsif ($product->{release} gt $today || $product->{expire} lt $today
-          || !$product->{listed}) {
-      return show_cart("Sorry, '$product->{title}' is no longer available");
+    else {
+      (my $comp_release = $product->{release}) =~ s/ .*//;
+      (my $comp_expire = $product->{expire}) =~ s/ .*//;
+      $comp_release le $today
+       or return show_cart("'$product->{title}' has not been released yet");
+      $today le $comp_expire
+       or return show_cart("'$product->{title}' has expired");
+      $product->{listed} 
+       or return show_cart("'$product->{title}' not available");
     }
     push(@products, $product); # used in page rendering
     @$item{qw/price wholesalePrice gst/} = 
@@ -517,16 +543,22 @@ sub purchase {
   $order{gst} = 0;
   $order{wholesale} = 0;
   my @products;
-  my $today = epoch_to_sql(time);
+  my $today = now_sqldate();
   for my $item (@cart) {
     my $product = Products->getByPkey($item->{productId});
     # double check that it's still a valid product
     if (!$product) {
       return show_cart("Product $item->{productId} not found");
     }
-    elsif ($product->{release} gt $today || $product->{expire} lt $today
-          || !$product->{listed}) {
-      return show_cart("Sorry, '$product->{title}' is no longer available");
+    else {
+      (my $comp_release = $product->{release}) =~ s/ .*//;
+      (my $comp_expire = $product->{expire}) =~ s/ .*//;
+      $comp_release le $today
+       or return show_cart("'$product->{title}' has not been released yet");
+      $today le $comp_expire
+       or return show_cart("'$product->{title}' has expired");
+      $product->{listed} 
+       or return show_cart("'$product->{title}' not available");
     }
     push(@products, $product); # used in page rendering
     @$item{qw/price wholesalePrice gst/} = 
index bb578d6b3ae3a6fa2614e1708f64b046fd91ee08..6008d438f850cb3ad54d94fdbb5929417d4321e2 100644 (file)
@@ -88,6 +88,9 @@ control specific articles, and those that are applied to an article.
 Each macro will need to be described in bse.cfg, and the name of the
 macro assigned an index so that it can be controlled.
 
+Since most normal permissions aren't going to be directly useful, the
+only permissions stored in the system will be macro based permissions.
+
 =head2 Attached macros
 
 These name one or more articles and the permissions can be different
index a6f91f1a88fd5effcaca9dea3e554e45cac7501d..b94948b47cad0638592d07c80e74b41488301f16 100644 (file)
@@ -10,6 +10,61 @@ Maybe I'll add some other bits here.
 
 =head1 CHANGES
 
+=head2 0.12_07
+
+=over
+
+=item *
+
+added handling for a default template based on parent, level and type.
+Returns to our original defaults from %LEVEL_DEFAULTS, but uses the
+config file instead.
+
+=item *
+
+now lists level specific templates in the templates drop-down for
+normal articles
+
+=item *
+
+updated templates from Adrian
+
+=item *
+
+since the default release date for new products is now the date the
+product was added, and release is a datetime, add_item()'s check to
+make sure the product had been released was broken, since it only
+compared it with a date.
+
+=item *
+
+the purchase() and prePurchase() functions in shop.pl had a similar
+problem
+
+=item *
+
+articles weren't being regenerated on save
+
+=item *
+
+report errors supplied to show_cart() in shop.pl
+
+=item *
+
+changed add_item() to report why it didn't add an item to the cart via
+show_cart() (#167)
+
+=item *
+
+t/t00smoke.t now checks add.pl for normal articles, catalogs and
+products
+
+=item *
+
+removed now unneeded onClick handler from delete in the image manager
+
+=back
+
 =head2 0.12_06
 
 This release includes some inactive files for access control.
index 310f6cfd3a07f7666f1a689571521fe0e0da766f..c1320cf2906a95969b6cd7babee460a91eaaa4af 100644 (file)
@@ -228,6 +228,42 @@ used for the given article.
 
 =back
 
+=head2 [level I<level>]
+
+=over
+
+=item template
+
+The default template for this level of article, assuming it hasn't
+been set in the [children of I<article id>] section.
+
+=item template_dirs
+
+A comma-separated list of extra directories under $TMPLDIR to search
+for templates that can be used for articles at the given I<level>.
+
+=back
+
+=head2 [catalogs]
+
+=over
+
+=item template
+
+The default template for catalogs.
+
+=back
+
+=head2 [products]
+
+=over
+
+=item template
+
+The default template for products.
+
+=back
+
 =head2 [messages]
 
 This can be used to control translation of error messages.  Each key
index db98ab22411a57a6d272e64fa184f7792e891b73..6beaa5bb2038c3eaaf466f3f1547eba4eb757c24 100644 (file)
@@ -54,7 +54,7 @@
 </form>
 
 
-<form method="POST" action="<:script:>" enctype="multipart/form-data">
+<form method="post" action="<:script:>" enctype="multipart/form-data">
 <input type="hidden" name="level" value="<: level :>">
 <input type="hidden" name="id" value="<: article id :>">
 <input type="hidden" name="parentid" value="<: article parentid :>">
@@ -97,8 +97,8 @@
               <input type="text" name="url" value="<: image url :>" size="32">
             </td>
             <td valign="bottom" nowrap> 
-              <input type="submit" name="removeimg_<: image id :>" value="Delete" onClick="return window.alert('Remember to update the article after deletion is complete')" >
-              <:imgmove:> </td>
+              <b><a href="<:script:>?level=<: level :>&parentid=<: article parentid :>&id=<:article id:>&imgtype=<: articleType :>&removeimg_<: image id :>">Delete</a></b>
+<:imgmove:> </td>
           </tr>
           <: iterator separator images :> 
           <tr bgcolor="#FFFFFF"> 
index 40ea32843358f32350c586ef0ab2e6b80a120eee..1028415a1072d24323242828a35091ec311d0ff5 100644 (file)
                       </tr>
                       <:iterator end files:> 
                     </table>
-              </td></tr></table><br>
-              <:or Files:><p>No files are attached to this article.<:eif Files:> 
-                <a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a></p>
+              </td></tr></table>
+              <p><a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a>
+              </p>
+              <:or Files:>
+              <p>No files are attached to this article. <a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a></p><:eif Files:>
             </td>
             <td nowrap bgcolor="#FFFFFF" valign="top"><:help edit files:></td>
           </tr>
index 40ea32843358f32350c586ef0ab2e6b80a120eee..1028415a1072d24323242828a35091ec311d0ff5 100644 (file)
                       </tr>
                       <:iterator end files:> 
                     </table>
-              </td></tr></table><br>
-              <:or Files:><p>No files are attached to this article.<:eif Files:> 
-                <a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a></p>
+              </td></tr></table>
+              <p><a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a>
+              </p>
+              <:or Files:>
+              <p>No files are attached to this article. <a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a></p><:eif Files:>
             </td>
             <td nowrap bgcolor="#FFFFFF" valign="top"><:help edit files:></td>
           </tr>
index e99381720f91d4948cfc2dde5659b21c7ab5855e..690cf0cf8b412ca948b602a50bde2d1eb5db8b1d 100644 (file)
                       <:iterator end files:> 
                     </table>
               </td></tr></table>
-              <:or Files:><p>No files are attached to this article.<:eif Files:> 
-                <a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a></p>
+              <p><a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a>
+              </p>
+              <:or Files:>
+              <p>No files are attached to this article. <a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a></p><:eif Files:>
             </td>
             <td nowrap bgcolor="#FFFFFF" valign="top"><:help edit files:></td>
           </tr>
index a45dbffec42819e87d3c8387cdf08d70945320c2..2c54debc77b49bdad736623d07dc34dd76ce85ed 100644 (file)
@@ -32,7 +32,8 @@
           </tr>
           <tr> 
             <th align="left" bgcolor="#FFFFFF">Catalog:</th>
-            <td bgcolor="#FFFFFF"><select name="parentid"><:list:></select></td>
+            <td bgcolor="#FFFFFF">
+<select name="parentid"><:list:></select></td>
             <td nowrap bgcolor="#FFFFFF"><:help product catalog:></td>
           </tr>
           <tr> 
           </tr>
           <tr> 
             <th nowrap align="left" bgcolor="#FFFFFF" valign="top"><a name="files"></a>Files:</th>
-            <td nowrap bgcolor="#FFFFFF" width="100%"> <:if Files:> 
+            <td nowrap bgcolor="#FFFFFF"> <:if Files:> 
               <table cellpadding="0" cellspacing="0" border="0" bgcolor="#333333">
                 <tr> 
                   <td> 
                     </table>
                   </td>
                 </tr>
-              </table><br>
-              <:or Files:><p>No files are attached to this article.<:eif Files:> 
-                <a href="<:script:>?filelist=1&id=<:product id:>"><b>Manage Files</b></a></p>
+              </table>
+              <p><a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a>
+              </p>
+              <:or Files:>
+              <p>No files are attached to this article. <a href="<:script:>?filelist=1&id=<:article id:>"><b>Manage Files</b></a></p><:eif Files:>
             </td>
-            <td nowrap bgcolor="#FFFFFF" width="100%" valign="top"><:help product 
+            <td nowrap bgcolor="#FFFFFF" valign="top"><:help product 
               files:></td>
           </tr>
           <tr> 
             <th valign="top" nowrap bgcolor="#FFFFFF" align="left"> Images: 
             </th>
-            <td align="center" bgcolor="#FFFFFF" width="100%"> <:if Images:> <:iterator begin 
+            <td align="center" bgcolor="#FFFFFF"> <:if Images:> <:iterator begin 
               images:> <img src="/images/<: image image :>" alt="<:image alt :>" width= 
               <:image width:> height=<:image height:>> <:iterator separator images:> 
               <hr noshade size="1">
              <:or Images:><p align="left">No images are attached to this article.  <a href="<:script:>?id=<:article id:>&showimages=1"><b>Manage Images</b></a></p>
              <:eif Images:>
             </td>
-            <td valign="top" bgcolor="#FFFFFF" width="100%"><:help product images:></td>
+            <td valign="top" bgcolor="#FFFFFF"><:help product images:></td>
           </tr>
         </table>
       </td>
index 48961d97400cf73548aea8a47af15571bec3bff5..e9a34efc6e60dd624879e1130de890208dd738d1 100644 (file)
@@ -21,6 +21,7 @@
     </td>
   </tr>
 </table>
+<:ifMsg:><p><font face="Verdana, Arial, Helvetica, sans-serif"><b><:msg:></b> </font></p><:or:><:eif:>
 <p><font face="Verdana, Arial, Helvetica, sans-serif" size="-2"><b>Contains</b> 
   - <:count:> items</font></p>
 <form name="form1" method="POST" action="/cgi-bin/shop.pl">
index 64f5254d22e5846f73f77f16971e5d6d0c7dad8d..a677cb9f4cd44b3f50f16a00a2c2e48e8583a1fe 100644 (file)
 <form name="ff" method="POST" action="/cgi-bin/shop.pl">
               
 <:if Options:>
-<table>
+  <table>
 <tr>
-      <td> <:iterator begin options:> <font face="Verdana, Arial, Helvetica, sans-serif" size="2"><b><:option 
-        desc:>:</b></font> <:option popup:> <:iterator end options:> </td>
+       <:iterator begin options:><td valign="middle"> <font face="Verdana, Arial, Helvetica, sans-serif" size="2"><b><:option desc:>:</b></font></td><td> <:option popup:> </td><:iterator end options:>
 </tr>
 </table>
   <:or Options:><:eif Options:>
-<:ifProduct leadTime:> 
-  <p> <b><font face="Verdana, Arial, Helvetica, sans-serif" size="-2" color="#FE7F00">Usually ships in: <:product leadTime:> <:if Eq [product leadTime] "1":>day<:or Eq:>days<:eif Eq:></font></b></p>
-<:or:><:eif:>
+  <:ifProduct leadTime:> 
+   <p><b><font face="Verdana, Arial, Helvetica, sans-serif" size="-2" color="#FE7F00">Usually ships in: <:product leadTime:> <:if Eq [product leadTime] "1":>day<:or Eq:>days<:eif Eq:></font></b>
+</p><:or:><br><:eif:>
 
 <table border="0" cellspacing="0" cellpadding="0">
     <tr valign="middle" align="center"> 
@@ -67,7 +66,7 @@
     </tr>
   </table>
 </form>
-<:or Product:>
+<:or Product:><br>
 <table border="0" cellspacing="0" cellpadding="1" bgcolor="#CCCCCC">
   <tr>
     <td>
index 3fbf0896ede9c05512d73b277831eeff7a35e116..9a9112995b8b4985595f827bf8ae963061b35f82 100644 (file)
             <td align="center"><font face="Verdana, Arial, Helvetica, sans-serif" size="2"><:item units:></font></td>
             <td align="right"><font face="Verdana, Arial, Helvetica, sans-serif" size="2">$<:money item price:></font></td>
           </tr>
-          <:if Prodfiles:> 
+<:iterator end items:>
         </table>
+
+          <:if Prodfiles:> 
         <table width="100%" cellpadding="3" cellspacing="1">
           <tr bgcolor="#CCCCCC"> 
             <th colspan="3"><font face="Verdana, Arial, Helvetica, sans-serif" size="2" color="#666666"><:if 
               "yes":>Files available when order status is &#145;Complete&#146;<:or:>Files<:eif:><:eif 
               Order:></font></th>
           </tr>
+
           <tr bgcolor="#EEEEEE"> 
             <th width="50%" align="left"><font face="Verdana, Arial, Helvetica, sans-serif" size="2">Description</font></th>
             <th nowrap width="50%" align="left"><font face="Verdana, Arial, Helvetica, sans-serif" size="2">File</font></th>
             <th><font face="Verdana, Arial, Helvetica, sans-serif" size="2">Size</font></th>
           </tr>
+<:iterator begin items:>
           <:iterator begin prodfiles:> 
           <tr bgcolor="#FFFFFF"> 
             <td width="50%"><font face="Verdana, Arial, Helvetica, sans-serif" size="2"><:prodfile 
             <td align="right"><font face="Verdana, Arial, Helvetica, sans-serif" size="2"><:kb 
               prodfile sizeInBytes:></font></td>
           </tr>
-          <:iterator end prodfiles:> <:or Prodfiles:><:eif Prodfiles:> <:iterator end items:> 
+          <:iterator end prodfiles:><:iterator end items:> 
         </table>
+<:or Prodfiles:><:eif Prodfiles:>  
 <:or Items:><:eif Items:>
         </td>
     </tr>
index 5afed57aa73867f17217924c7d7d2f5539f7bccb..4d34c2c8e13626abbd204a4adc15c43421e8c6b8 100644 (file)
@@ -3,7 +3,7 @@ use strict;
 use BSE::Test;
 
 ++$|;
-print "1..29\n";
+print "1..39\n";
 my $baseurl = base_url;
 ok($baseurl =~ /^http:/, "basic check of base url");
 my $ua = make_ua;
@@ -31,4 +31,14 @@ fetch_ok($ua, "user logon page", "$baseurl/cgi-bin/user.pl",
         qr!User\s+Logon!s);
 fetch_ok($ua, "shop admin page", "$baseurl/cgi-bin/admin/shopadmin.pl",
         qr!Shop\s+administration!s);
+fetch_ok($ua, "add article form", "$baseurl/cgi-bin/admin/add.pl",
+        qr!New\s+Subsect\sLev2!s);
+fetch_ok($ua, "add catalog form", "$baseurl/cgi-bin/admin/add.pl?type=Catalog",
+        qr!New\s+Catalog!s);
+fetch_ok($ua, "add product form", "$baseurl/cgi-bin/admin/add.pl?type=Product",
+        qr!Add\s+product!s);
+fetch_ok($ua, "edit article form", "$baseurl/cgi-bin/admin/add.pl?id=1",
+        qr!Section\sDetails!s);
+fetch_ok($ua, "edit catalog form", "$baseurl/cgi-bin/admin/add.pl?id=4",
+        qr!Catalog\sDetails!s);