--- /dev/null
+<%
+# Nick's web site: Generate directory listing.
+#
+# Copyright © 2021 Nick Bowler
+#
+# 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 3 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, see <https://www.gnu.org/licenses/>
+
+mydir = rep_uri
+
+files = {}
+@items.find_all(@item[:pattern]).each do |item|
+ t = item[:updated_at]
+
+ item.reps.each do |rep|
+ next if rep == @rep
+
+ p = rep_uri(rep)
+ d, f = File.split(p)
+ next unless "#{d}/" == mydir
+
+ if p =~ %r{/$}
+ sz = Dir.children(File.dirname(rep.raw_path)).length - 1
+ type = "DIR"
+ else
+ sz = human_filesize(File.size(rep.raw_path))
+ type = nil
+ end
+
+ files[f] = {
+ mtime: if t then t.getutc.strftime "%Y-%m-%d %H:%M UTC" end,
+ size: sz,
+ type: type,
+ }
+ end
+end
+
+if @items["#{File.dirname(mydir)}/index.lst"]
+ files[".."] = { type: "UP" }
+end
+%>
+<table class='filelist'>
+ <thead>
+ <tr><th /><th>Name</th><th>Last Modified</th><th>Size</th></tr>
+ </thead>
+ <tbody>
+<% files.keys.sort.each do |key| %>
+ <tr>
+ <td>
+<% if files[key][:type] %>
+ <div>
+ <img src='<%=
+ case files[key][:type]
+ when "DIR"; "/images/folder.svg"
+ when "UP"; "/images/return.svg"
+ else raise "no icon for filetype #{files[key][:type]}"
+ end %>' alt='<%= files[key][:type] %>' width='16' height='16' />
+ </div>
+<% end %>
+ </td>
+ <td><a href='<%= key %>'><%=
+ if key == ".." then "[Parent Directory]" else key end
+ %></a></td>
+ <td><%= files[key][:mtime] %></td>
+ <td><%= files[key][:size] %></td>
+ </tr>
+<% end %>
+ </tbody>
+</table>