Сценарий запускается, но безрезультатно - PullRequest
0 голосов
/ 26 октября 2011

Я написал скрипт GreaseMonkey, чтобы добавить кнопку в HTML-представление blogger.com.У меня повсюду предупреждения, поэтому я знаю, что все работает.

Странно то, что он срабатывает дважды, каждый раз немного по-разному.Когда я перехожу к редактированию поста на blogger.com, сценарий сначала запускается на черной странице и просматривает все оповещения в правильном порядке, включая внутренний.

При втором запуске после страницызагружается, каждое предупреждение, кроме «внутреннего», запускается, и никаких ошибок не выдается.

 // ==UserScript==
 // @name  Blogger: Remove HTML Space
 // @include  http://www.blogger.com/blogger.g?blogID*editor/target*\
 // ==/UserScript=

 function contentEval(source) {
   // Check for function input.
   alert("asdas");
   if ('function' == typeof source) {
     // Execute this function with no arguments, by adding parentheses.
     // One set around the function, required for valid syntax, and a
     // second empty set calls the surrounded function.
     source = '(' + source + ')();'
   }

   alert("asdas2");
   // Create a script node holding this  source code.
   var script = document.createElement('script');
   alert("asdas3");
   script.setAttribute("type", "application/javascript");
   alert("asdas4");
   script.textContent = source;
   alert("asdas5");

   // Insert the script node into the page, so it will run, and immediately
   // remove it to clean up.
   alert("asdas6");
   document.body.appendChild(script);
   alert("asdas7");
 }

  alert("test")
  contentEval(function(){ alert("inside"); document.getElementById("postingHtmlToolbar").firstChild.innerHTML += '<div id="SP" class="goog-inline-block goog-toolbar-button" title="SP" role="button" style="-moz-user-select: none;"><div class="goog-inline-block goog-toolbar-button-outer-box"><div class="goog-inline-block goog-toolbar-button-inner-box"><button type="button" onclick="document.getElementById(\'postingHtmlBox\').value = document.getElementById(\'postingHtmlBox\').value.replace(/&amp;nbsp;/g, \' \');"><b>SP</b></button></div></div></div>'});

 alert("testw");

Есть ли у blogger.com антивирусная инъекция?

Ответы [ 2 ]

1 голос
/ 26 октября 2011

О стрельбе дважды:

Если страница содержит <iframe> с, пользовательский скрипт будет запускаться в каждом из них.

Вам нужно определить, находитесь ли вы внутри <iframe> или нет. Самый простой способ запустить только на главной странице, а не в фреймах, это заключить весь код в код:

if(top==self)
{
  ...
}

Чтобы увидеть, есть ли на странице <iframe>s (жестко закодированные в HTML или динамически генерируемые), я всегда использую AdBlock Plus (диалог «Открыть блокируемые элементы»).

Однако я не уверен, почему второе «внутреннее» предупреждение не запускается. Я создал простую HTML-страницу, содержащую <iframe>, и я получил два оповещения.

О скрипте вообще:

Вы делаете двойную работу здесь. Вам не нужно все оборачивать, чтобы выполнить скрипт. Greasemonkey выполняет строки кода после загрузки страницы (DOMContentLoaded). Таким образом, вам не нужно создавать тег <script>, устанавливать его тело и добавлять к документу. Вы можете просто написать

document.getElementById("postingHtmlToolbar").firstChild.innerHTML += ...

и он должен делать то, что вы хотите (вам вообще не нужна функция contentEval).

У меня нет блога на блоггере, поэтому я не могу войти в систему и увидеть URL-адрес и проблемное поведение, но для отладки достаточно пошаговой игры с кодом.

Редактировать 2:

Похоже, вы должны изменить firstChild на firstElementChild.

Существует свойство innerHTML в Element (начиная с Firefox 3.5), но не в Node. Да, это действительно противоречиво и раздражает время от времени. Недавно я столкнулся с подобной проблемой.

Редактировать 3:

Там есть пара вещей. Пожалуйста, не говорите мне, что это не работает до сих пор:)

var func = function() {
    var obj = document.getElementById("postingHtmlToolbar");
    if(obj !== null){ // only if object exists, so we don't have errors
       //alert(obj);
       obj.style.display = 'block'; // it's hidden by default
       obj.firstElementChild.innerHTML += "FOO";
    }
 }

 window.setTimeout(func, 3000); // execute with delay -- let's give Google's JS time to be loaded first
0 голосов
/ 27 октября 2011

GM может напрямую изменить веб-страницу, которая полезна для GM

Этот тег <button> ... Вы не имели в виду INPUT?

Я считаю, что выполняется дважды, потому что этот методЯ полагаю, это ваш обходной путь для невозможности непосредственного изменения страницы.

То, что вы делаете, это то, что вы создаете функцию Named Anonymous, которая, если вы не очень опытны в JS, тогдаВау, что придумал это.Это может быть проблемой:

if ('function' == typeof source) {
   // Execute this function with no arguments, by adding parentheses.
   // One set around the function, required for valid syntax, and a
   // second empty set calls the surrounded function.
   source = '(' + source + ')();'
}

Когда вы устанавливаете SOURCE между + +, вы вызываете функцию, потому что, поскольку вы конкатенируете, а функция не является строкой, concat пытается принудить ее, для этого он выполняет функцию, но затем в конце запускается empty (), а не в concat.Я не проверял это, но я верю, что это происходит.

Так что jakub прав, указывая на то, что сложность вашего кода не нужна, и в итоге выдает ошибки.

...