Статьи

Создание расширения Chrome для Diigo, часть 1

В наши дни сервисы закладок стоят десять центов. Когда ваша карьера и увлечения требуют от вас сохранения сотен ссылок, все становится беспорядочным. В конце концов я остановился на Diigo из-за его поддержки списков и тегов — вы можете добавить несколько тегов к каждой закладке и добавить каждую закладку в список. Но посещение этих закладок утомительно — сначала я должен открыть свою библиотеку Diigo на новой вкладке, а затем нажать на закладку в списке передо мной. Если моя библиотека сложна и глубоко вложена, тем больше проблем — мне нужно дополнительно отфильтровать результаты поиска, щелкнув фильтры слева, и я уже трачу гораздо больше времени, пытаясь добраться до своего сайта, отмеченного закладкой, чем должен ,

планирование

В этой серии мы создадим расширение Google Chrome, которое подключается к API-интерфейсу Diigo, извлекает сохраненные там закладки и синхронизирует их в папку на панели закладок Chrome. Эта папка будет иметь несколько уровней:

  1. Корневой уровень. Здесь будет подпапка «Теги», а также все закладки пользователя, помеченные как bbs-root.
  2. Уровень тегов. Подпапка «tags» будет содержать одну папку для каждого тега, который пользователь имеет в своей библиотеке Diigo. При входе в указанную папку перечисляются все сообщения с данным тегом.

К сожалению, поскольку API Diigo недостаточно развит, нет возможности удалить теги, если они оставлены пустыми, а также нет способа удалить закладку из Diigo, если она удаляется в Chrome, — пока. Если этот API появится, я оставлю это кому-то другому, чтобы написать последующую статью. Аналогично, API Diigo не поддерживает списки на данный момент. Как только они добавят эту функцию, это будет достаточно просто, чтобы обновить это расширение с подпапкой «Списки».

Важно отметить, что Google очень монополистичен со своим сервисом закладок. В Chrome встроен максимальный предел записи , что означает, что вы не можете делать более 100 записей (создавать, обновлять и удалять) с помощью API chrome.bookmarks Это означает, что если кто-то имеет более 100 тегов / списков / закладок в Diigo, их браузеру потребуется несколько часов, чтобы извлечь их все и в конечном итоге согласиться на меньшее количество записей (только обновления, создания и удаления с этого момента должны быть намного меньше общий). Мы также будем использовать конструкции JavaScript 1.7, такие как ключевое слово let , поэтому вам нужно перейти в chrome://flags Может ли это быть сделано без let Абсолютно. Но я твердо верю, что держаться подальше от новых технологий только потому, что они еще не везде, вредно как для разработчиков, так и для сети в целом. JS 1.7 вышел 7 лет назад, что примерно триста лет в интернете. Помимо let«строгий режим» , потому что let

Обратите внимание, что это означает, что люди без экспериментального JS не смогут установить и использовать это расширение, по крайней мере до тех пор, пока поддержка JS 1.7 не будет включена по умолчанию в Chrome.

Бутстрапирование

Сначала давайте создадим папку, в которой мы будем хранить исходный код нашего расширения. Создайте структуру папок, такую ​​как эта, и оставьте файлы JS и JSON пустыми.

 /
    icons/
    background.js
    manifest.json

Далее нам нужно заполнить файл manifest.json

 {
    "name": "Diigo Bookmark Bar Sync",
    "description": "Sync Diigo Bookmarks to Chrome",
    "version": "1.0.0.0",
    "background": {
        "scripts": ["background.js"]
    },
    "permissions": [
        "bookmarks", "https://secure.diigo.com/api/v2/"
    ],
    "browser_action": {
        "default_icon": {
            "19": "icons/19.png",
            "38": "icons/38.png"
        },
        "default_title": "Diigo BBS"
    },
    "icons": {
        "16": "icons/16.png",
        "48": "icons/48.png",
        "128": "icons/128.png"
    },
    "manifest_version": 2
}

Если вы следовали моему предыдущему руководству по расширению Chrome для Sitepoint , вы должны быть знакомы со всеми ключами и их значениями.

Есть три новинки, с которыми вы, возможно, не знакомы: тот факт, что мы используем фоновую страницу JS вместо HTML (в любом случае не имеет значения — JS незаметно быстрее), мы запрашиваем разрешение «закладки», чтобы попросить Chrome разрешить мы редактируем их, и мы запрашиваем разрешение на доступ к https://secure.diigo.com/api/v2/перекрестным происхождением ajax или, другими словами, позволяет нам выполнять вызовы Ajax на Diigo без поднятия флагов безопасности ,

Мы также используем browser_action , что означает, что у нас всегда будет постоянная иконка NEXT на омнибар — а не внутри нее, пока мы находимся на конкретной странице, как в случае с действиями на странице.

Сделайте несколько иконок для вашего расширения в размерах, указанных в файле manifest.json, и добавьте их в папку с иконками, или просто загрузите мою и поместите их туда.

На этом этапе мы можем протестировать наше расширение, загрузив его на вкладку расширений (chrome: // extensions). Убедитесь, что «Режим разработчика» установлен, и нажмите «Загрузить распакованное расширение», затем укажите Chrome на папку, в которую вы положили файлы. Если все идет хорошо, значок расширения должен появиться в верхней панели справа от омнибара, и если вы наведете на него курсор мыши, вы увидите всплывающее окно «Diigo BBS».

Diigo API

Чтобы получить доступ к API Diigo, вам необходимо зарегистрироваться для получения ключа API . Это предоставит вам строку случайных символов, которую вам нужно отправлять вместе с каждым запросом API Diigo, чтобы идентифицировать себя (на самом деле, чтобы идентифицировать ваше приложение — у каждого приложения будет свой ключ API).

API Diigo сильно недоразвит, но RESTful, что означает, что мы каждый раз вызываем один и тот же URL-адрес для воздействия на один и тот же объект (т.е. закладки), но меняем тип запроса (GET-выборки, POST-обновления и вставки, DELETE удаляет закладку — еще не реализовано ). Мы скоро объясним это немного глубже.

По сути, общение с API так же просто, как отправка запроса на URL, заполненный необходимыми параметрами. Если мы предполагаем, что есть пользователь с именем «Джоэл», для получения 10 закладок Джоэла мы используем https://secure.diigo.com/api/v2/bookmarks?key=your_api_key&user=joel&count=100&filter=all

Ответом на этот запрос будет либо код ошибки, если что-то пошло не так, либо JSON-объект. Этот объект JSON либо не будет содержать ничего, если у Джоэла нет закладок, либо будет содержать блоки данных, соответствующие информации об этих закладках, во многом аналогично тому, как показано в документации по API:

 [
  {
    "title":"Diigo API Help",
    "url":"http://www.diigo.com/help/api.html",
    "user":"foo",
    "desc":"",
    "tags":"test,diigo,help",
    "shared":"yes",
    "created_at":"2008/04/30 06:28:54 +0800",
    "updated_at":"2008/04/30 06:28:54 +0800",
    "comments":[],
    "annotations":[]
  },
  {
    "title":"Google Search",
    "url":"http://www.google.com",
    "user":"bar",
    "desc":"",
    "tags":"test,search",
    "shared":"yes",
    "created_at":"2008/04/30 06:28:54 +0800",
    "updated_at":"2008/04/30 06:28:54 +0800",
    "comments":[],
    "annotations":[]
  }
]

Легко извлечь все необходимое из этих данных JSON, как только мы их получим, но мы вернемся к этому через минуту.

Документы API говорят

Аутентификация использует базовую аутентификацию HTTP — стандартный метод аутентификации, который включает в себя имя пользователя и пароль в кодировке base64 в заголовке запроса авторизации.

..но нет ни объяснения, ни демонстрации этого.

Это означает следующее: когда вы открываете фактический URL-адрес для API в браузере, попробуйте щелкнуть здесь , вам будет предложено ввести имя пользователя и пароль.

Если вы не ввели правильные учетные данные, вы получите ответ 403, что означает, что у вас недостаточно доступа.

Если у вас есть надлежащие учетные данные, вы можете получить доступ к URL-адресу двумя способами: либо ввести их и отправить форму, либо включить их в URL-адрес, например: https://myusername:[email protected]/api/v2/bookmarks?key=your_api_key&user=joel&count=100&filter=allmyusernamemypassword Вы даже можете проверить это прямо сейчас в своем браузере, если вы зарегистрировали ключ API и у вас есть действующая учетная запись Diigo. Вы должны получить либо пустой массив ([]), либо список ваших закладок (или публичные закладки пользователя, которого вы определили в параметре user URL-адреса).

Так что же означает кодирование base64? Это означает, что нам нужно запустить имя пользователя и пароль через дополнительный фильтр, чтобы учесть любые странные символы в пароле. Таким образом, строка myuser:mypassbXl1c2VyOm15cGFzcw==здесь ).

Итак, как мы можем собрать все это вместе?

Кодирование и отправка

Для начала нам понадобится способ кодирования строки в base64. Поскольку JS не имеет этой встроенной функциональности, мы можем использовать код из Webtoolkit . Вставьте этот код в файл background.js Если вы хотите, вы можете даже уменьшить его, чтобы сделать его более компактным.

Далее нам нужно указать URL-адрес API, который мы хотим авторизовать. Это делается с помощью заголовка Authorize, и при использовании собственных объектов XHR для Ajax мы можем сделать это с помощью xml.setRequestHeader('Authorization', auth); метод, где auth

Давайте создадим общую функцию, которая генерирует эту строку авторизации.

 function make_basic_auth(user, password) {
  var tok = user + ':' + password;
  var hash = Base64.encode(tok);
  return "Basic " + hash;
}

Как видите, возвращаемая строка будет «Basic» + все, что было вычислено из user + pass string в качестве значения Base64. Эта строка — то, что нужно заголовку авторизации, чтобы получить доступ к URL-адресу, на который мы ее отправим. По сути, он идентичен вводу имени пользователя и пароля вручную при доступе к URL-адресу через браузер.

Вы можете быть удивлены — не могли бы мы просто добавить пользователя: перейти к началу URL-адреса так же, как и в браузере, и просто игнорировать бизнес Base64? Да, но тогда вы не учитываете разные символы и можете столкнуться с серьезными проблемами с недопустимыми запросами — например, символ «@» обозначает начало адреса сервера, а наличие его в пароле может привести к тому, что мы усилия.

Наконец, давайте сделаем XHR-запрос к API.

 var auth = make_basic_auth('user','pass');
var url = 'https://secure.diigo.com/api/v2/bookmarks?key=your_api_key&user=desireduser&count=100&filter=all';

xml = new XMLHttpRequest();
xml.open('GET', url);
xml.setRequestHeader('Authorization', auth);
xml.send();

xml.onreadystatechange = function() {
    if (xml.readyState === 4) {
        if (xml.status === 200) {
            console.log(xml.responseText);
        } else {
            console.error("Something went wrong!");
        }
    }
};

Конечно, замените «user», «pass», «your_api_key» и «desireduser» на ваши значения.

Если мы теперь перезагрузим наше расширение с открытой фоновой страницей (нажмите _generated_background_page.html

Заключение части 1

В этой части мы загрузили наше расширение, объяснили, реализовали и продемонстрировали вызов API Diigo. Во второй части мы напишем основную часть нашего расширения.