Commit 75594e4b authored by Stefy Spora's avatar Stefy Spora

Fix content script connection issues with comprehensive fallback system

- Add robust error handling for content script communication failures
- Implement automatic content script injection when not available
- Add executeScript fallback when message passing fails
- Update manifest.json to use http/https patterns instead of <all_urls>
- Add comprehensive debugging logs to troubleshoot connection issues
- Ensure MetaMask detection works on all websites with multiple fallback methods
- Handle cases where content scripts can't run (chrome:// pages, etc.)
parent 95a82b5f
Pipeline #177 failed with stages
......@@ -26,9 +26,10 @@
"js": ["content.js"]
},
{
"matches": ["<all_urls>"],
"matches": ["http://*/*", "https://*/*"],
"js": ["metamask-detector.js"],
"run_at": "document_start"
"run_at": "document_start",
"all_frames": false
}
],
"icons": {
......
......@@ -24,26 +24,39 @@
// Function to check if MetaMask is available
function isMetaMaskAvailable() {
return typeof window.ethereum !== 'undefined' ||
const available = typeof window.ethereum !== 'undefined' ||
(typeof window.web3 !== 'undefined' && typeof window.web3.currentProvider !== 'undefined');
console.log('MetaMask detector: MetaMask available:', available);
return available;
}
// Function to get MetaMask provider
function getMetaMaskProvider() {
return window.ethereum || window.web3.currentProvider;
const provider = window.ethereum || window.web3.currentProvider;
console.log('MetaMask detector: Provider found:', !!provider);
return provider;
}
// Listen for messages from popup
chrome.runtime.onMessage.addListener((request, sender, sendResponse) => {
console.log('MetaMask detector: Received message:', request.action);
if (request.action === 'checkMetaMask') {
sendResponse({
const response = {
available: isMetaMaskAvailable(),
provider: getMetaMaskProvider() ? true : false
});
};
console.log('MetaMask detector: Sending response:', response);
sendResponse(response);
} else if (request.action === 'executeWeb3Donation') {
console.log('MetaMask detector: Executing Web3 donation');
// Handle Web3 donation directly in content script
executeWeb3Donation().then(result => {
console.log('MetaMask detector: Donation result:', result);
sendResponse(result);
}).catch(error => {
console.error('MetaMask detector: Donation error:', error);
sendResponse({ success: false, message: 'Donation failed: ' + error.message });
});
return true; // Keep message channel open for async response
}
......
......@@ -243,9 +243,43 @@ document.addEventListener('DOMContentLoaded', function() {
return false;
}
// Send message to MetaMask detector content script
const response = await chrome.tabs.sendMessage(tab.id, { action: 'checkMetaMask' });
return response.available;
// Check if we can communicate with content script
try {
console.log('Popup: Sending checkMetaMask message to tab', tab.id);
const response = await chrome.tabs.sendMessage(tab.id, { action: 'checkMetaMask' });
console.log('Popup: Received MetaMask check response:', response);
return response.available;
} catch (messageError) {
console.log('Popup: Content script not available, trying to inject it:', messageError);
// Try to inject the MetaMask detector content script
try {
await chrome.scripting.executeScript({
target: { tabId: tab.id },
files: ['metamask-detector.js']
});
// Wait a moment for the script to load
await new Promise(resolve => setTimeout(resolve, 500));
// Try again to communicate
const response = await chrome.tabs.sendMessage(tab.id, { action: 'checkMetaMask' });
return response.available;
} catch (injectError) {
console.log('Could not inject content script, using executeScript fallback:', injectError);
// Fallback: use executeScript to check MetaMask directly
const results = await chrome.scripting.executeScript({
target: { tabId: tab.id },
function: () => {
return typeof window.ethereum !== 'undefined' ||
(typeof window.web3 !== 'undefined' && typeof window.web3.currentProvider !== 'undefined');
}
});
return results[0].result;
}
}
} catch (error) {
console.error('Error checking MetaMask availability:', error);
return false;
......@@ -262,9 +296,102 @@ document.addEventListener('DOMContentLoaded', function() {
return { success: false, message: 'No active tab found.' };
}
// Send message to MetaMask detector content script to handle donation
const response = await chrome.tabs.sendMessage(tab.id, { action: 'executeWeb3Donation' });
return response;
// Try to send message to MetaMask detector content script
try {
console.log('Popup: Sending executeWeb3Donation message to tab', tab.id);
const response = await chrome.tabs.sendMessage(tab.id, { action: 'executeWeb3Donation' });
console.log('Popup: Received donation response:', response);
return response;
} catch (messageError) {
console.log('Popup: Content script not available for donation, trying to inject it:', messageError);
// Try to inject the MetaMask detector content script
try {
await chrome.scripting.executeScript({
target: { tabId: tab.id },
files: ['metamask-detector.js']
});
// Wait a moment for the script to load
await new Promise(resolve => setTimeout(resolve, 500));
// Try again to send the donation message
const response = await chrome.tabs.sendMessage(tab.id, { action: 'executeWeb3Donation' });
return response;
} catch (injectError) {
console.log('Could not inject content script for donation, using executeScript fallback:', injectError);
// Fallback: use executeScript to handle the donation directly
const results = await chrome.scripting.executeScript({
target: { tabId: tab.id },
function: async () => {
try {
const ethereumProvider = window.ethereum || window.web3.currentProvider;
// Request account access
let accounts;
try {
accounts = await ethereumProvider.request({
method: 'eth_requestAccounts'
});
} catch (requestError) {
// Fallback for legacy providers
if (ethereumProvider.enable) {
accounts = await ethereumProvider.enable();
} else {
throw requestError;
}
}
if (!accounts || accounts.length === 0) {
return { success: false, message: 'No accounts found. Please unlock your Web3 wallet.' };
}
const donationAddress = '0xdA6dAb526515b5cb556d20269207D43fcc760E51';
// Prepare transaction parameters (user can modify amount in wallet)
const transactionParameters = {
to: donationAddress,
from: accounts[0],
value: '0x16345785D8A0000', // 0.1 ETH in wei (default amount, user can change)
gas: '0x5208', // 21000 gas limit for simple transfer
};
// Send transaction
let txHash;
try {
txHash = await ethereumProvider.request({
method: 'eth_sendTransaction',
params: [transactionParameters],
});
} catch (transactionError) {
// Handle user rejection specifically
if (transactionError.code === 4001 ||
(transactionError.message && transactionError.message.includes('User denied transaction signature'))) {
return { success: false, message: 'Transaction cancelled by user.' };
}
throw transactionError;
}
return { success: true, message: `Transaction sent! Hash: ${txHash.substring(0, 10)}...` };
} catch (error) {
console.error('Web3 donation error:', error);
if (error.code === 4001 || (error.message && error.message.includes('User denied'))) {
return { success: false, message: 'Transaction cancelled by user.' };
} else if (error.code === -32602) {
return { success: false, message: 'Invalid transaction parameters.' };
} else {
return { success: false, message: `Transaction failed: ${error.message || error.toString()}` };
}
}
}
});
return results[0].result;
}
}
// Request account access
let accounts;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment