<%@ Page Title="How Saving Works" Language="C#" MasterPageFile="~/Site.master" AutoEventWireup="true" %>
<%@ Register Assembly="AjaxUploader" Namespace="AjaxUploader.Controls" TagPrefix="au" %>
<script runat="server">
    // The whole upload lifecycle, made visible: this page lists the temp store and the
    // saved folder after every stage, so you can SEE what each step does on disk.
    private string TempDir { get { return AjaxUploader.AjaxUploaderConfig.ResolvedTempDirectory; } }
    private string SavedDir { get { return Server.MapPath("~/App_Data/DemoSaves"); } }

    protected void Uploader1_FileUploaded(object sender, AjaxUploader.Events.FileUploadedEventArgs e)
    {
        System.IO.Directory.CreateDirectory(SavedDir);
        var savedName = Guid.NewGuid().ToString("N") + System.IO.Path.GetExtension(e.FileName ?? "");
        var dest = System.IO.Path.Combine(SavedDir, savedName);
        var svc = new AjaxUploader.Services.UploadService();

        if (rbMode.SelectedValue == "move")
        {
            svc.MoveFile(e.FileGuid, dest);      // removes the temp pair immediately
            lblEvent.Text = "FileUploaded fired &rarr; <strong>MoveFile</strong> saved <code>"
                + Server.HtmlEncode(e.FileName) + "</code> and REMOVED the temp pair.";
        }
        else
        {
            svc.CopyFile(e.FileGuid, dest);      // temp pair stays until the sweep
            lblEvent.Text = "FileUploaded fired &rarr; <strong>CopyFile</strong> saved <code>"
                + Server.HtmlEncode(e.FileName) + "</code>; the temp pair stays until the 60-minute sweep.";
        }
    }

    protected void Page_PreRender(object sender, EventArgs e)
    {
        litTemp.Text = ListFolder(TempDir, "*.upload;*.meta");
        litSaved.Text = ListFolder(SavedDir, "*");
    }

    private string ListFolder(string dir, string patterns)
    {
        if (!System.IO.Directory.Exists(dir)) return "<em>(folder does not exist yet)</em>";
        var sb = new System.Text.StringBuilder();
        foreach (var pat in patterns.Split(';'))
            foreach (var f in System.IO.Directory.GetFiles(dir, pat))
            {
                var fi = new System.IO.FileInfo(f);
                sb.Append("<div><code>").Append(Server.HtmlEncode(fi.Name)).Append("</code> &mdash; ")
                  .Append(fi.Length).Append(" bytes</div>");
            }
        return sb.Length == 0 ? "<em>(empty)</em>" : sb.ToString();
    }
</script>
<asp:Content ID="TitleContent" ContentPlaceHolderID="TitleContent" runat="server">How Saving Works - AjaxUploader v5.3 Demos</asp:Content>
<asp:Content ID="HeaderContent" ContentPlaceHolderID="HeaderTitle" runat="server">How Saving Works</asp:Content>
<asp:Content ID="BodyContent" ContentPlaceHolderID="MainContent" runat="server">
<div class="demo-card"> <div class="demo-card-header">The upload lifecycle, visible on disk</div> <div class="demo-card-body">
 <p class="demo-description"> The one concept every integration depends on: an upload is <strong>staged</strong> first
 and only becomes permanent when <em>your</em> <code>FileUploaded</code> handler saves it. This page lists both folders
 live, so you can watch each stage happen. </p>
 <div class="demo-expect"><strong>What you should see:</strong> after selecting a file, a <code>.upload</code> + <code>.meta</code> pair appears in the temp store; the page then posts back automatically (<code>AutoPostBack</code>), your handler runs, and the saved file appears below &mdash; with the temp pair gone if you chose MoveFile, or still present (until the sweep) if you chose CopyFile.</div>

 <div class="mb-3"> <span class="fw-bold me-3">When the event fires, save with:</span>
 <asp:RadioButtonList ID="rbMode" runat="server" RepeatDirection="Horizontal" CssClass="d-inline-block align-middle">
   <asp:ListItem Text="&nbsp;CopyFile (temp pair stays)&nbsp;&nbsp;" Value="copy" Selected="True" />
   <asp:ListItem Text="&nbsp;MoveFile (temp pair removed)" Value="move" />
 </asp:RadioButtonList> </div>

 <au:AjaxFileUpload ID="Uploader1" runat="server"
     AutoPostBack="true"
     OnFileUploaded="Uploader1_FileUploaded"
     ShowProgress="true" />

 <div class="alert alert-success py-2 px-3 small mt-3" role="status"><asp:Label ID="lblEvent" runat="server" Text="Nothing has happened yet. Pick a save mode, then select a file - no other clicks needed." /></div>

 <div class="row mt-3"> <div class="col-md-6">
   <div class="fw-bold mb-1">1. Temp store <span class="text-muted fw-normal small">(staged uploads, swept after 60 min)</span></div>
   <div class="p-2 bg-light border rounded small" style="min-height:70px"><asp:Literal ID="litTemp" runat="server" /></div>
 </div> <div class="col-md-6">
   <div class="fw-bold mb-1">2. Saved folder <span class="text-muted fw-normal small">(what your handler wrote - permanent)</span></div>
   <div class="p-2 bg-light border rounded small" style="min-height:70px"><asp:Literal ID="litSaved" runat="server" /></div>
 </div> </div>

 <div class="alert alert-info small py-2 px-3 mt-3"><strong>Why your handler might "never fire":</strong> <code>FileUploaded</code> runs on the <em>postback</em>, not during the transfer. This page uses <code>AutoPostBack="true"</code> so the postback happens by itself; without it, the temp pair appears and then nothing happens until the page posts back some other way. If the attribute is rejected, your <code>AjaxUploader.dll</code> is old &mdash; right-click it &rarr; Details: File version must be <strong>5.3.0.808</strong> or later.</div>

 <div class="code-panel"> <pre><code>&lt;au:AjaxFileUpload ID="Uploader1" runat="server"
    AutoPostBack="true"
    OnFileUploaded="Uploader1_FileUploaded" /&gt;

protected void Uploader1_FileUploaded(object sender,
    AjaxUploader.Events.FileUploadedEventArgs e)
{
    var savedName = Guid.NewGuid().ToString("N")
        + System.IO.Path.GetExtension(e.FileName ?? "");

    // CopyFile keeps the staged copy until the sweep; MoveFile removes it now.
    new AjaxUploader.Services.UploadService()
        .CopyFile(e.FileGuid, "~/uploads/" + savedName);
}</code></pre> </div>
</div> </div>
</asp:Content>
