How how send file with post in StippleUI.form?

Why doesn’t this work?

using Genie, Stipple
using Genie.Requests
using StippleUI

Genie.config.cors_headers["Access-Control-Allow-Origin"]  =  "*"
Genie.config.cors_headers["Access-Control-Allow-Headers"] = "Content-Type"
Genie.config.cors_headers["Access-Control-Allow-Methods"] = "GET,POST,PUT,DELETE,OPTIONS"
Genie.config.cors_allowed_origins = ["*"]

function create_storage_dir(name)
  try
    mkdir(joinpath(@__DIR__, name))    
  catch 
    @warn "directory already exists" 
  end
  return joinpath(@__DIR__, name)
end

# Generate file path
const FILE_PATH = create_storage_dir("Banco de dados")

@reactive mutable struct FormComponent <: ReactiveModel
  client_file1 = ""
  client_file2 = "" 
  warin::R{Bool} = true
end

myform() = xelem(
  :div,
  class = "q-pa-md col-4 self-center",  
  [
    StippleUI.form(action = "/sub", method = "POST",
      [
        filefield(
          "File1", :client_file1, field__name="File1"
        ),
        filefield(
          "File2", :client_file2, field__name="File2"
        ),      
        toggle("I accept the license and terms", :accept),
        Stipple.Html.div(
          [
            btn("Enviar", type = "submit", color = "primary")
            btn("Reset", type = "reset", color = "primary", :flat, class = "q-ml-sm")
          ],
        )
      ],
      @on(:submit, "onSubmit"),
      @on(:reset, "onReset"),
      class = "q-gutter-md",
    ),
  ],
)

import Stipple.js_methods
js_methods(m::FormComponent) = raw"""
    onSubmit () {
      if (this.accept !== true) {
        this.$q.notify({
          color: 'red-5',
          textColor: 'white',
          icon: 'warning',
          message: 'You need to accept the license and terms first'
        })
      }
      else {
        this.$q.notify({
          color: 'green-4',
          textColor: 'white',
          icon: 'cloud_done',
          message: 'Submitted'
        });
        this.client_file1 = this.client_file1;
        this.client_file2 = this.client_file2;
      }
    },
    onReset () {
      console.log(this.client_name)  // Hit F12 open console and you should see name
      console.log(this.client_age)  // Hit F12 open console tab and you should see age
      this.client_file1 = null
      this.client_file2 = null   
      this.accept = false
    }
  """

import Stipple.client_data
client_data(m::FormComponent) =
  client_data(client_file2 = js"null", client_file1 = js"null", accept = false)

function ui(model)
  page(model, class = "full-width row wrap justify-center items-center", title = "Hello Stipple", myform())
end

# Using Genie Route to serve ui
route("/") do
  hs_model = FormComponent |> init |> ui
end

route("/sub", method = POST) do  
  files = Genie.Requests.filespayload()
  post = Genie.Requests.rawpayload()
  print(post)
  for f in files
      write(joinpath(FILE_PATH, f[2].name), f[2].data)
      @info "msg1"
  end
  if length(files) == 0
      @info "msg2"
  end
  return "msg3"
end


up(9001)

Finally, I can use Axios. But, how do I return a response to Axios?

using Genie, Stipple
using Genie.Requests
using StippleUI

Genie.config.cors_headers["Access-Control-Allow-Origin"]  =  "*"
Genie.config.cors_headers["Access-Control-Allow-Headers"] = "Content-Type"
Genie.config.cors_headers["Access-Control-Allow-Methods"] = "GET,POST,PUT,DELETE,OPTIONS"
Genie.config.cors_allowed_origins = ["*"]

function create_storage_dir(name)
  try
    mkdir(joinpath(@__DIR__, name))    
  catch 
    @warn "directory already exists" 
  end
  return joinpath(@__DIR__, name)
end

# Generate file path
const FILE_PATH = create_storage_dir("Banco de dados")

@reactive mutable struct FormComponent <: ReactiveModel
  file1::R{Any} = ""
  file2 = "" 
  warin::R{Bool} = false
end

myform() = xelem(
  :div,
  class = "q-pa-md col-4 self-center",  
  [
    StippleUI.form(action = "/sub", method = "POST",
      [
        filefield(
          "File1", :client_file1, field__name="File1", name="file1_id"
        ),
        filefield(
          "File2", :client_file2, field__name="File2", name="file2_id"
        ),      
        toggle("I accept the license and terms", :accept),
        Stipple.Html.div(
          [
            btn("Enviar", type = "submit", color = "primary")
            btn("Reset", type = "reset", color = "primary", :flat, class = "q-ml-sm")
          ],
        )
      ],
      @on(:submit, "onSubmit"),
      @on(:reset, "onReset"),
      class = "q-gutter-md",
    ),    
  ],
)

sctp = """<script src=\"https://unpkg.com/axios/dist/axios.min.js"></script>"""

import Stipple.js_methods
js_methods(m::FormComponent) = raw"""
    onSubmit (evt) {
      if (this.accept !== true) {
        this.$q.notify({
          color: 'red-5',
          textColor: 'white',
          icon: 'warning',
          message: 'You need to accept the license and terms first'
        })
      }
      else {
        this.$q.notify({
          color: 'green-4',
          textColor: 'white',
          icon: 'cloud_done',
          message: 'Submitted'
        });
        //alert(this.client_file1);
        
        this.warin = true;
        const formData = new FormData(evt.target);
        const data = [];

        axios.post( '/sub',
          formData,
          {
            headers: {
                'Content-Type': 'multipart/form-data'
            }
          }
        ).then(function(){
          alert('SUCCESS!!');
        })
        .catch(function(){
          alert('FAILURE!!');
        });
       
       }
    },
    onReset () {
      console.log(this.client_name)  // Hit F12 open console and you should see name
      console.log(this.client_age)  // Hit F12 open console tab and you should see age
      this.client_file1 = null
      this.client_file2 = null   
      this.accept = false
      this.warin = false
    }
  """

import Stipple.client_data
client_data(m::FormComponent) =
  client_data(client_file2 = js"null", client_file1 = js"null", accept = false)

# function handlers(model)
#   onbutton(model.warin) do 
#     println("foi")
#     test = copy(model.warin[])
#     println(test)
#     if test === true
#       println(values(model.file2))

     
#     end
   
#   end
#   model.warin[] = false
#   model
# end

model = init(FormComponent) # |> handlers

function ui(model)  
  page(model, class = "container", title = "Hello Stipple", myform()) * sctp
end

route("/") do
  global model
  ui(model)
  
end

route("/sub", method = POST) do  
  print("post")
  files = Genie.Requests.filespayload()
  post = Genie.Requests.rawpayload()
  print(post)
  for f in files
      write(joinpath(FILE_PATH, f[2].name), f[2].data)
      @info "msg1"
  end
  if length(files) == 0
      @info "msg2"
  end
  return "msg3"
end

up(8020, open_browser=true)

Complete

using Genie, Stipple
using Genie.Requests, Genie.Renderer.Json
using StippleUI

Genie.config.cors_headers["Access-Control-Allow-Origin"]  =  "*"
Genie.config.cors_headers["Access-Control-Allow-Headers"] = "Content-Type"
Genie.config.cors_headers["Access-Control-Allow-Methods"] = "GET,POST,PUT,DELETE,OPTIONS"
Genie.config.cors_allowed_origins = ["*"]

function create_storage_dir(name)
  try
    mkdir(joinpath(@__DIR__, name))    
  catch 
    @warn "directory already exists" 
  end
  return joinpath(@__DIR__, name)
end

# Generate file path
const FILE_PATH = create_storage_dir("Banco de dados")

@reactive mutable struct FormComponent <: ReactiveModel
  file1::R{Any} = ""
  file2 = "" 
  warin::R{Bool} = false
end

myform() = xelem(
  :div,
  class = "q-pa-md col-4 self-center",  
  [
    StippleUI.form(action = "/sub", method = "POST",
      [
        filefield(
          "File1", :client_file1, field__name="File1", name="file1_id"
        ),
        filefield(
          "File2", :client_file2, field__name="File2", name="file2_id"
        ),      
        toggle("I accept the license and terms", :accept),
        Stipple.Html.div(
          [
            btn("Enviar", type = "submit", color = "primary")
            btn("Reset", type = "reset", color = "primary", :flat, class = "q-ml-sm")
          ],
        )
      ],
      @on(:submit, "onSubmit"),
      @on(:reset, "onReset"),
      class = "q-gutter-md",
    ),    
  ],
)

sctp = """<script src=\"https://unpkg.com/axios/dist/axios.min.js"></script>"""

import Stipple.js_methods
js_methods(m::FormComponent) = raw"""
    onSubmit (evt) {
      if (this.accept !== true) {
        this.$q.notify({
          color: 'red-5',
          textColor: 'white',
          icon: 'warning',
          message: 'You need to accept the license and terms first'
        })
      }
      else {
        this.$q.notify({
          color: 'green-4',
          textColor: 'white',
          icon: 'cloud_done',
          message: 'Submitted'
        });
        //alert(this.client_file1);
        
        this.warin = true;
        const formData = new FormData(evt.target);
        const data = [];

        axios.post( '/sub',
          formData,
          {
            headers: {
                'Content-Type': 'multipart/form-data'
            }
          }
        ).then(function(resp){
          alert(Object.keys(resp.data));
          alert(resp.data['form'])
          alert('SUCCESS!!');
        })
        .catch(function(){
          alert('FAILURE!!');
        });
       
       }
    },
    onReset () {
      console.log(this.client_name)  // Hit F12 open console and you should see name
      console.log(this.client_age)  // Hit F12 open console tab and you should see age
      this.client_file1 = null
      this.client_file2 = null   
      this.accept = false
      this.warin = false
    }
  """

import Stipple.client_data
client_data(m::FormComponent) =
  client_data(client_file2 = js"null", client_file1 = js"null", accept = false)

# function handlers(model)
#   onbutton(model.warin) do 
#     println("foi")
#     test = copy(model.warin[])
#     println(test)
#     if test === true
#       println(values(model.file2))

     
#     end
   
#   end
#   model.warin[] = false
#   model
# end

model = init(FormComponent) # |> handlers

function ui(model)  
  page(model, class = "container", title = "Hello Stipple", myform()) * sctp
end

route("/") do
  global model
  ui(model)
  
end

route("/sub", method = POST) do  
  files = Genie.Requests.filespayload()
  post = Genie.Requests.rawpayload()
  #print(post)
  for f in files
      write(joinpath(FILE_PATH, f[2].name), f[2].data)
      @info "msg1"
  end
  if length(files) == 0
      @info "msg2"
  end
  resp = Dict("form" => true)
  return Json.json(resp)
end

up(8020, open_browser=true)