Weweb variable not updating from JS

The following code is not updating the Weweb variable.

if (!window["scp-loading-0429c712-7af3-4686-b036-43d8a2e6d63f"]) {
    window["scp-loading-0429c712-7af3-4686-b036-43d8a2e6d63f"] = true;
    let scriptContent = `
import { initializeApp } from 'https://www.gstatic.com/firebasejs/10.12.0/firebase-app.js';
import { getStorage, ref, uploadBytesResumable, getDownloadURL } from 'https://www.gstatic.com/firebasejs/10.12.0/firebase-storage.js';
const firebaseConfig = {
  apiKey: "XXXXX",
  authDomain: "XXXXX",
  projectId: "XXXXX",
  storageBucket: "XXXXX",
};
// Initialize Firebase
const app = initializeApp(firebaseConfig);
const storage = getStorage(app);
// Handle upload button click event
document.getElementById('uploadFileButton').addEventListener('click', async () => {
  const fileInput = document.getElementById('fileInput');
  const file = fileInput.files[0];
  if (file) {
    try {
      const downloadURL = await uploadFile(file);
      console.log('File available at', downloadURL);
      document.getElementById('fileURL').innerHTML = \`<a href="\${downloadURL}" target="_blank">\${downloadURL}</a>\`;
     
      variables[/* downloadurl */'e2678680-80a5-4b53-8aff-69c1a6b3576c']=downloadURL;
    } catch (error) {
      console.error('Upload failed:', error);
      alert('Failed to upload file and get URL');
    }
  } else {
    alert('Please select a file first.');
  }
});
// Function to upload the file to Firebase Storage
async function uploadFile(file) {
  return new Promise((resolve, reject) => {
    // Create the file metadata
    const metadata = {
      contentType: file.type
    };
    // Create a storage reference
    const storageRef = ref(storage, 'images/' + file.name);
    // Upload the file and metadata
    const uploadTask = uploadBytesResumable(storageRef, file, metadata);
    // Listen for state changes, errors, and completion of the upload
    uploadTask.on('state_changed',
      (snapshot) => {
        // Get task progress, including the number of bytes uploaded and the total number of bytes to be uploaded
        const progress = (snapshot.bytesTransferred / snapshot.totalBytes) * 100;
        console.log('Upload is ' + progress + '% done');
        switch (snapshot.state) {
          case 'paused':
            console.log('Upload is paused');
            break;
          case 'running':
            console.log('Upload is running');
            break;
        }
      },
      (error) => {
        // Handle upload errors
        console.error('Upload failed:', error);
        reject(error);
      },
      () => {
        // Upload completed successfully, now we can get the download URL
        getDownloadURL(uploadTask.snapshot.ref).then((downloadURL) => {
          resolve(downloadURL);
        }).catch((error) => {
          console.error('Failed to get download URL:', error);
          reject(error);
        });
      }
    );
  });
}
    `;
    let script = document.createElement('script');
    script.type = 'module';
    script.innerHTML = scriptContent;
    document.body.appendChild(script);
  }```

I’m not certain you can update a variable by making it equal to a new value, directly in Javascript.

If you’d like to try another method, I might have a quick trick that could help you out. You can call a workflow in WeWeb using the following function: wwLib.executeWorkflow(id, parameters).

As an example, in wwLib.executeWorkflow("7cd1bbb8-e7c2-4578-b37d-de1525879161", {"keyname": "value"}), "7cd1bbb8-e7c2-4578-b37d-de1525879161" represents the ID of the workflow, which you can access in WeWeb’s dev mode, and the object {"keyname": "value"} contains the parameters you want to pass to this workflow.

You will need to set the parameter in your workflow with the same name as the key you pass in the parameters. You can then use this workflow to update the value of your variable using the “Change variable value” node and change it to the value you passed in the parameters.

You can also use wwVariable.updateValue. I made a video about how to do this:

1 Like

@raydeck
Hi Ray. Thanks for your help, and it worked.
The upload works great when I directly place the button and file uploader HTML on the page. However, it doesn’t work in a modal. The button became unresponsive in modal. Any suggestions what I need to change to the code?

Here’s the updated code for your reference.

if (!window[“scp-loading-0429c712-7af3-4686-b036-43d8a2e6d63f”]) {
window[“scp-loading-0429c712-7af3-4686-b036-43d8a2e6d63f”] = true;
let scriptContent = `
import { initializeApp } from ‘https://www.gstatic.com/firebasejs/10.12.0/firebase-app.js’;
import { getStorage, ref, uploadBytesResumable, getDownloadURL } from ‘https://www.gstatic.com/firebasejs/10.12.0/firebase-storage.js’;
const firebaseConfig = {
apiKey: “",
authDomain: "
”,
projectId: “",
storageBucket: "
”,
};
// Initialize Firebase
let wwLibLocal=wwLib.wwVariable.updateValue;
const app = initializeApp(firebaseConfig);
const storage = getStorage(app);
// Global variable to store the download URL
window.uploadedFileURL = null;
// Handle upload button click event
document.getElementById(‘uploadFileButton’).addEventListener(‘click’, async () => {
const fileInput = document.getElementById(‘fileInput’);
const file = fileInput.files[0];
if (file) {
try {

  const downloadURL = await uploadFile(file);
         

  console.log('File available at', downloadURL);
    console.log(wwLibLocal,"wwLibLocal")
  // Store the download URL in the global variable
  window.uploadedFileURL = downloadURL;

    wwLibLocal("a16e5747-6486-433b-a8e5-96a47a24a107", downloadURL);
    

 
} catch (error) {
  console.error('Upload failed:', error);
  alert('Failed to upload file and get URL');
}

} else {
alert(‘Please select a file first.’);
}
});
// Function to upload the file to Firebase Storage
async function uploadFile(file) {
return new Promise((resolve, reject) => {
// Create the file metadata
const metadata = {
contentType: file.type
};
// Create a storage reference
const storageRef = ref(storage, ‘pdfs/’ + file.name);
// Upload the file and metadata
const uploadTask = uploadBytesResumable(storageRef, file, metadata);
// Listen for state changes, errors, and completion of the upload
uploadTask.on(‘state_changed’,
(snapshot) => {
// Get task progress, including the number of bytes uploaded and the total number of bytes to be uploaded
const progress = (snapshot.bytesTransferred / snapshot.totalBytes) * 100;
console.log('Upload is ’ + progress + ‘% done’);
switch (snapshot.state) {
case ‘paused’:
console.log(‘Upload is paused’);
break;
case ‘running’:
console.log(‘Upload is running’);
break;
}
},
(error) => {
// Handle upload errors
console.error(‘Upload failed:’, error);
reject(error);
},
() => {
// Upload completed successfully, now we can get the download URL
getDownloadURL(uploadTask.snapshot.ref).then((downloadURL) => {
resolve(downloadURL);
}).catch((error) => {
console.error(‘Failed to get download URL:’, error);
reject(error);
});
}
);
});
}
`;
let script = document.createElement(‘script’);
script.type = ‘module’;
script.innerHTML = scriptContent;
document.body.appendChild(script);
}

I wonder if your code is running at the right time. On a modal the div might not be mounted when you run the JavaScript. I would try running the code in an “on mounted” workflow for your custom html element to synchronize the lifecycles.