Как ввести сценарий контента в IFRAME с расширением веб -интерфейса iOS?IOS

Программируем под IOS
Ответить Пред. темаСлед. тема
Anonymous
 Как ввести сценарий контента в IFRAME с расширением веб -интерфейса iOS?

Сообщение Anonymous »

Я строю расширение браузера, которое добавляет аннотации к тексту, который читает пользователь. Важным вариантом использования являются электронные книги, и многие популярные читатели электронных книг используют iframes для отображения контента книги. Вот автономный индекс.html с iframe и кнопкой, которая вводит скрипт в iframe. Сценарий регистрирует периодические сообщения в консоли: < /p>

Код: Выделить всё






Iframe Script Test

iframe {
width: 100%;
height: 600px;
border: 2px solid #ccc;
border-radius: 8px;
}






Iframe Script Injection Test

Inject Test Script







function injectScript() {
const iframe = document.getElementById('test-iframe');
try {
const doc = iframe.contentDocument || iframe.contentWindow.document;

if (!doc) {
console.log('ERROR: Cannot access iframe document');
return;
}

// Check if script already exists
if (doc.querySelector('script[data-test-injected]')) {
console.log('Script already exists, removing old one...');
doc.querySelector('script[data-test-injected]').remove();
}

const script = doc.createElement('script');
script.setAttribute('data-test-injected', 'true');
script.textContent = `
let heartbeat = 0;
console.log('IFRAME: Test script injected successfully!');

setInterval(() => {
heartbeat++;
console.log('IFRAME: Heartbeat ' + heartbeat + ' - Script still alive!');
}, 1000);

console.log('IFRAME: Script setup complete, heartbeat started');
`;

doc.head.appendChild(script);
console.log('SUCCESS: Test script injected into iframe');

} catch (error) {
console.log('ERROR: Failed to inject script - ' + error.message);
}
}




< /code>
Я размещаю это в домене HTTPS (извините, не могу поделиться этим здесь, это туннель Ngrok, который я использую для разных вещей в разное время). Я могу получить доступ к этому через Firefox Desktop и Safari Mobile на симуляторе iPhone.
Для обоих браузеров все работает, как и ожидалось < /strong>. Нажав кнопку, внедряя скрипт, я вижу приветственное сообщение, а затем периодическое сердцебиение. Затем я добавил небольшой сценарий контента в расширение моего браузера. Это автономный сценарий контента, который сканирует для iFrames и добавляет тег сценария. В основном точно та же логика, что и для index.html 
. Я добавил некоторое защитное программирование вокруг сценария, чтобы убедиться, что веб -сайт полностью загружен и т. Д. Вот сценарий: < /p>

function injectScriptIntoIframe(iframe: HTMLIFrameElement) {
try {
const doc = iframe.contentDocument || iframe.contentWindow?.document;
if (!doc) {
console.warn('[INJECT] Could not access iframe document:', iframe);
return;
}
console.log('[INJECT] Injecting test script into iframe');

const testScript = doc.createElement('script');
testScript.setAttribute('data-timely-test-injected', 'true');
testScript.textContent = `
let count = 0;
console.log('Injected via contentscript: Test script injected successfully!');

setInterval(() => {
count++;
console.log('Injected via contentscript: count ' + count + ' - Script still alive!');
}, 1000);

console.log('Injected via contentscript: Script setup complete, count started');
`;

doc.head.appendChild(testScript);
console.log('[INJECT] Successfully injected script into iframe');

} catch (e) {
console.warn('[INJECT] Could not inject into iframe (likely cross-origin):', e);
}
}

function scanAndInjectIframes() {
const iframes = Array.from(document.getElementsByTagName('iframe'));
console.log(`[INJECT] Scanning ${iframes.length} iframes`);

for (const iframe of iframes) {
const inject = () => {
if (iframe.contentDocument && iframe.contentDocument.readyState === 'complete') {
injectScriptIntoIframe(iframe);
} else {
iframe.addEventListener('load', () => injectScriptIntoIframe(iframe), { once: true });
}
};

inject();
}
}

function initializeIframeInjector() {
console.log('[INJECT] Initializing iframe injector...');

// Initial scan
scanAndInjectIframes();

// Set up mutation observer for dynamically added iframes
const observer = new MutationObserver((mutations) => {
for (const mutation of mutations) {
if (mutation.type === 'childList') {
const hasNewIframe = Array.from(mutation.addedNodes).some(
(node) => node.nodeType === Node.ELEMENT_NODE && (node as Element).tagName === 'IFRAME'
);
if (hasNewIframe) {
console.log('[INJECT] Detected new iframe in DOM');
scanAndInjectIframes();
}
}
}
});

observer.observe(document.body, { childList: true, subtree: true });
console.log('[INJECT] Mutation observer set up for iframe detection');
}

// Initialize when DOM is ready
if (document.readyState === 'loading') {
console.log('[INJECT] Document still loading, waiting for DOMContentLoaded');
document.addEventListener('DOMContentLoaded', initializeIframeInjector, { once: true });
} else {
console.log('[INJECT] Document already loaded, starting immediately');
initializeIframeInjector();
}
< /code>
Теперь, на рабочем столе Firefox, это работает. Я вижу журналы: < /p>
[INJECT] Content script loaded injectIntoIframe.js:22:9
[INJECT] Document already loaded, starting immediately injectIntoIframe.js:107:13
[INJECT] Initializing iframe injector... injectIntoIframe.js:72:13
[INJECT] Scanning 1 iframes injectIntoIframe.js:45:13
[INJECT] Mutation observer set up for iframe detection injectIntoIframe.js:99:13

[INJECT] Injecting test script into iframe injectIntoIframe.js:31:17
Injected via contentscript: Test script injected successfully! srcdoc:3:21
Injected via contentscript: Script setup complete, count started srcdoc:10:21
[INJECT] Successfully injected script into iframe injectIntoIframe.js:36:17
Injected via contentscript: count 1 - Script still alive!
Injected via contentscript: count 2 - Script still alive!
...
< /code>
Приведенные выше журналы взяты из Firefox Desktop. Они хорошо выглядят. Теперь я показываю журналы из iOS Safari в эмуляторе: < /p>
[Log] [INJECT] Initializing iframe injector... (injectIntoIframe.js, line 70)
[Log] [INJECT] Scanning 1 iframes (injectIntoIframe.js, line 43)
[Log] [INJECT] Injecting test script into iframe (injectIntoIframe.js, line 29)
[Log] Injected via contentscript: Test script injected successfully! (about:srcdoc, line 3)
[Log] Injected via contentscript: Script setup complete, count started (about:srcdoc, line 10)
[Log] [INJECT] Successfully injected script into iframe (injectIntoIframe.js, line 34)
[Log] [INJECT] Mutation observer set up for iframe detection (injectIntoIframe.js, line 97)
< /code>
Журналы останавливаются здесь, не периодическое сообщение «все еще живое» из инъекционного сценария.
Это довольно удивительно для меня. Самый первый «вводится через содержимое: тестовый скрипт успешно вводится!» и «вводится через содержимое: настройка скрипта заполнена, count запускается» сообщения поступают из инъекционного сценария. Но после этого это просто исчезает.
Нет сообщения об ошибке. Глядя на вкладку Iframe на вкладке «Элементы» инструментов разработчика Safari также показывает, что в iframe нет введенного сценария. Он остается там и продолжает регистрировать свое сообщение «Я жив». Это так: < /p>

Откройте веб -сайт на сафари iOS в симуляторе < /li>
Переключить на XCode, нажмите «Стройте и запустите» < /li>
На симуляторе, которое мое приложение доведено на передний план. Расширения Safari iOS всегда находятся в пакете приложений вместе с каким -то компаньоном. Это нормальное приложение, оно имеет значок, его можно открыть и т. Д. Если пользователь удаляет это приложение, расширение тоже исчезает. Поэтому при запуске проекта Xcode это приложение открывается и доставляется на переднюю часть. Сообщения журнала теперь выглядят так: < /li>
< /ul>
[Log] [INJECT] Document already loaded, starting immediately (injectIntoIframe.js, line 105)
[Log] [INJECT] Initializing iframe injector... (injectIntoIframe.js, line 70)
[Log] [INJECT] Scanning 1 iframes (injectIntoIframe.js, line 43)
[Log] [INJECT] Injecting test script into iframe (injectIntoIframe.js, line 29)
[Log] Injected via contentscript: Test script injected successfully! (about:blank, line 3)
[Log] Injected via contentscript: Script setup complete, count started (about:blank, line 10)
[Log] [INJECT] Successfully injected script into iframe (injectIntoIframe.js, line 34)
[Log] [INJECT] Mutation observer set up for iframe detection (injectIntoIframe.js, line 97)
[Log] [INJECT] Document already loaded, starting immediately (injectIntoIframe.js, line 105)
[Log] [INJECT] Initializing iframe injector... (injectIntoIframe.js, line 70)
[Log] [INJECT] Scanning 1 iframes (injectIntoIframe.js, line 43)
[Log] [INJECT] Injecting test script into iframe (injectIntoIframe.js, line 29)
[Log] Injected via contentscript: Test script injected successfully! (about:srcdoc, line 3)
[Log] Injected via contentscript: Script setup complete, count started (about:srcdoc, line 10)
[Log] [INJECT] Successfully injected script into iframe (injectIntoIframe.js, line 34)
[Log] [INJECT] Mutation observer set up for iframe detection (injectIntoIframe.js, line 97)
[Log] Injected via contentscript: count 1 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 2 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 3 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 4 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 5 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 6 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 7 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 8 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 9 - Script still alive! (about:srcdoc, line 7)
[Log] Injected via contentscript: count 10 - Script still alive! (about:srcdoc, line 7)
< /code>
Также обратите внимание, сценарий контента, кажется, работает дважды. По -прежнему существуют прерванные журналы, когда я впервые открыл страницу (впрыскиваемый скрипт дает один журнал, но не продолжает журнал), а затем те же журналы появляются снова, но теперь с периоическими обновлениями, которые говорят, что скрипт все еще жив. Журналы показывают, что скрипт вводится, но он не продолжает регистрироваться.
Что здесь происходит?

Подробнее здесь: https://stackoverflow.com/questions/797 ... -extension
Реклама
Ответить Пред. темаСлед. тема

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

  • Похожие темы
    Ответы
    Просмотры
    Последнее сообщение