2023年5月30日火曜日

emacsでFirefoxの拡張を開発する際にコード補完を設定する方法

emacsでFirefoxの拡張を開発する際にコード補完を設定する方法

概要

前回 emacs で Firefox 拡張を開発する環境を構築し lint やインデントの設定などを行いました

今回はコード補完を行う方法を紹介します

環境

  • macOS 11.7.6
  • emacs 28.2
  • nodejs 19.7.0
    • tern

tern のインストール

  • npm install -g tern

.tern.conf の作成

  • vim ~/.tern-config
{
  "libs": [
    "browser",
    "jquery",
    "ecma5",
    "underscore"
  ],
  "plugins": {
    "angular": {},
    "commonjs":{},
    "node":{},
    "requirejs":{},
    "node_resolve":{}
  }
}

tern-mode のインストール

  • M-x package-list-packages

tern-mode と tern-auto-complete をインストール

emacs の設定

前回の設定 (mode の起動や lint の設定) も記載しています
tern はどうやら company には対応しなくなったようで auto-complete 用の拡張があるのでそれを使うように変更しています

; for firefox extension (via js2-mode)
(require 'tern)
(require 'js2-mode)
(require 'flycheck)

# .js ファイルで js2-mode 起動
(add-to-list 'auto-mode-alist '("\\.js\\'" . js2-mode))
# js2-mode 起動時に auto-complete-mode 起動
(add-hook 'js2-mode-hook 'auto-complete-mode)
# インデントはスペース2つにする
(add-hook 'js2-mode-hook
  (lambda ()
     (setq my-js-mode-indent-num 2)
     (setq js2-basic-offset my-js-mode-indent-num)
     (setq js-switch-indent-offset my-js-mode-indent-num)
    ))
# js2-mode のデフォルトの linter は無効にする
(setq js2-mode-show-strict-warnings nil)
# js2-mode 起動時に flycheck-mode 起動
(add-hook 'js2-mode-hook #'flycheck-mode)
# flycheck の linter は eslint にする
(setq flycheck-javascript-eslint-executable "eslint")
(with-eval-after-load 'flycheck
  (flycheck-add-mode 'javascript-eslint 'js2-mode))

# js2-mode 起動時に tern-mode 起動
(add-hook 'js2-mode-hook
  (lambda ()
    (tern-mode t)))
# tern-auto-complete を使って連携 
(eval-after-load 'tern
  '(progn
    (require 'tern-auto-complete)
    (tern-ac-setup)))
# 補完用のキーバインドを設定
(define-key tern-mode-keymap (kbd "M-.") 'tern-find-definition)
(define-key tern-mode-keymap (kbd "M-,") 'tern-pop-find-definition)

最後に

js2-mode + flycheck (eslint) + tern-mode はおそらく JavaScript 単体の開発であれば Firefox 以外の環境でも使えると思います

emacsでFirefoxの拡張を開発する環境を構築する

emacsでFirefoxの拡張を開発する環境を構築する

概要

emacs で Firefox 拡張を開発する環境を構築してみます

環境

  • macOS 11.7.6
  • emacs 28.2
  • nodejs 19.7.0
    • eslint 8.41.0

eslint のインストール

  • npm -g install eslint

firefox 拡張のプロジェクト配下で eslint 用の設定ファイルを記載します

  • npm init @eslint/config
✔ How would you like to use ESLint? · problems
✔ What type of modules does your project use? · esm
✔ Which framework does your project use? · none
✔ Does your project use TypeScript? · No / Yes
✔ Where does your code run? · browser
✔ What format do you want your config file to be in? · JavaScript
A config file was generated, but the config file itself may not follow your linting rules.
Successfully created .eslintrc.js file in 
  • cat .eslintrc.js
module.exports = {
  "env": {
    "webextensions": true,
    "browser": true,
    "es2021": true,
    "node": true
  },
  "extends": "eslint:recommended",
  "overrides": [
  ],
  "parserOptions": {
    "ecmaVersion": "latest",
    "sourceType": "module"
  },
  "rules": {
  }
}

js2-mode, company, flycheck のインストール

  • M-x package-list-packages

で js2-mode, company, flycheck を選択しインストールします

emacs の設定

(require 'company)
(require 'js2-mode)
(require 'flycheck)

# .js ファイルで js2-mode 起動
(add-to-list 'auto-mode-alist '("\\.js\\'" . js2-mode))
# js2-mode 起動時に company-mode 起動
(add-hook 'js2-mode-hook 'company-mode)
# インデントはスペース2つにする
(add-hook 'js2-mode-hook
  (lambda ()
     (setq my-js-mode-indent-num 2)
     (setq js2-basic-offset my-js-mode-indent-num)
     (setq js-switch-indent-offset my-js-mode-indent-num)
    ))
# js2-mode のデフォルトの linter は無効にする
(setq js2-mode-show-strict-warnings nil)
# js2-mode 起動時に flycheck-mode 起動
(add-hook 'js2-mode-hook #'flycheck-mode)
# flycheck の linter は eslint にする
(setq flycheck-javascript-eslint-executable "eslint")
(with-eval-after-load 'flycheck
  (flycheck-add-mode 'javascript-eslint 'js2-mode))

課題

  • 補完をどうするか

2023年5月29日月曜日

docker secret を docker-compose で使う方法

docker secret を docker-compose で使う方法

概要

過去に docker secret を使う方法を紹介しました

今回は docker-compose から使ってみます

環境

  • Ubuntu 18.04
  • docker 19.03
  • docker swarm

シークレットファイル作成

  • echo "This is secret.txt" > secret.txt

docker-compose.yml

version: '3.8'
services:
  myapp:
    image: alpine:latest
    secrets:
      - source: my_secret
        target: secret.txt
    command: cat /run/secrets/secret.txt

secrets:
  my_secret:
    file: ./secret.txt

stack deploy

  • docker -H swarm01:2376 stack deploy test -c docker-compose.yml

動作確認

  • docker -H swarm01:2376 service logs test_myapp

シークレットファイルを更新した場合は

再度同じ docker-compose.yml で更新しようとすると以下のようなエラーになります

これはすでに前のシークレット情報で同一名称のシークレットが作成されてしまっているので名前を変更して別のシークレットとして登録する必要があります

failed to update secret test_my_secret: Error response from daemon: rpc error: code = InvalidArgument desc = only updates to Labels are allowed

docker-compose.yml の secret だけ書き換え

version: '3.8'
services:
  myapp:
    image: alpine:latest
    secrets:
      - source: my_secret_v2
        target: secret.txt
    command: cat /run/secrets/secret.txt

secrets:
  my_secret_v2:
    file: ./secret.txt

これで再度 stack deploy をすれば成功します

2023年5月28日日曜日

(解決) This App has violated Twitter Rules and policies. As a result, it can no longer be accessed. For assistance, submit a support ticket.

(解決) This App has violated Twitter Rules and policies. As a result, it can no longer be accessed. For assistance, submit a support ticket.

概要

Twitter のアプリが突然 suspend されたので対応しました
おそらく昔から存在するアプリは使用に関係なくこうなる気がします

環境

  • Twitter API (2023/05/24時点)

古いアプリを削除する

どうやらすでに異議申し立てもできなくなっているので素直に削除しましょう

ちゃんと v2 エンドポイントを使う

これが結構重要かなと思います
古いアプリは v1.1 エンドポイントでもツイートできちゃったりします
無料プランの場合は v1.1 エンドポイントは一部の機能しか使えなくツイートできません

で古いアプリを使っていると v1.1 でツイートできてしまうため規約違反となり suspend になったと推測されます

なので新しく作ったアプリではちゃんと v2 エンドポイントを使うようにしましょう

というかおそらく新しく作ったアプリでこれまで動作していたアプリを使うと

You currently have access to Twitter API v2 endpoints and limited v1.1 endpoints only. If you need access to this endpoint, you may need a different access level. You can learn more here: https://developer.twitter.com/en/docs/twitter-api/getting-started/about-twitter-api#v2-access-level

になるんじゃないかなと思います

多くのライブラリは v2 API に対応していない

例えば Ruby の twitter gem は v2 サポートしていません (執筆時点で)

なのでアプリを使ってツイートしようとすると上記のエラーで怒られます

なので頑張って自分で API リファレンスを見て自作のツール対処するか v2 サポートしているライブラリを探す感じになります

2023年5月26日金曜日

RubyでTwitterV2 API を使ってツイートする方法

RubyでTwitterV2 API を使ってツイートする方法

概要

twitter gem が v2 に対応していないので自作する必要があります

You currently have access to Twitter API v2 endpoints and limited v1.1 endpoints only. If you need access to this endpoint, you may need a different access level. You can learn more here: https://developer.twitter.com/en/docs/twitter-api/getting-started/about-twitter-api#v2-access-level

こんなエラーが出る場合にはライブラリが v1.1 にしか対応しておらず v2 のエンドポイントをサポートしていません

環境

  • macOS 11.7.6
  • ruby 3.2.1

Gemfile

gem 'oauth'
gem 'typhoeus'

サンプルコード

# frozen_string_literal: true

require 'json'
require 'typhoeus'
require 'oauth'
require 'oauth/request_proxy/typhoeus_request'

# TwitterV2を使ってツイートするクラス
class TwitterV2
  def initialize
    @consumer_key        = 'xxx'
    @consumer_secret     = 'xxx'
    @access_token        = 'xxx'
    @access_token_secret = 'xxx'
    @endpoint            = 'https://api.twitter.com/2/tweets'
  end

  def options(payload)
    {
      method: :post,
      headers: {
        'User-Agent': 'v2CreateTweetRuby',
        'content-type': 'application/json'
      },
      body: JSON.dump(payload)
    }
  end

  def consumer
    OAuth::Consumer.new(@consumer_key, @consumer_secret, { site: 'https://api.twitter.com', debug_output: false })
  end

  def access_token
    OAuth::AccessToken.new(@consumer, @access_token, @access_token_secret)
  end

  def post_tweet(url, oauth_params, payload)
    request = Typhoeus::Request.new(url, options(payload))
    oauth_helper = OAuth::Client::Helper.new(request, oauth_params.merge(request_uri: url))
    request.options[:headers].merge!({ Authorization: oauth_helper.header })
    request.run
  end

  def tweet(text)
    payload = { text: text }
    oauth_params = {
      consumer: consumer,
      token: access_token
    }
    post_tweet(@endpoint, oauth_params, payload)
  end
end

TwitterV2.new.tweet("test")

参考サイト

2023年5月25日木曜日

HuginnでWebhookを試してみる

HuginnでWebhookを試してみる

概要

Huginn は IFTTT や Zapier のようなオートメーションツールです
IFTTT や Zapier の無料プランではいろいろと制限があるので自分で構築してみました
今回は Webhook を使ってみます

環境

  • macOS 11.7.6
  • docker 23.0.5
  • Huginn 2022.08.18

起動

公式の推奨は docker なので docker を使います
とりあえず起動してアクセスできることを確認しましょう (あとで停止していろいろ設定を入れ込み再起動します)

  • docker run -it -p 3000:3000 ghcr.io/huginn/huginn
Rails 6.1.7.2 application starting in production http://0.0.0.0:3000

というログが出るまでしばらく時間がかかるので待ちます
起動後は http://localhost:3000 で管理 UI にアクセスできます
admin/password でログインできます

Twitter アプリの作成

アプリを作成して OAuth 用の権限設定と API キー/シークレットキーの取得をします

アプリの権限などを設定します
コールバック URL に localhost は設定できますがサイト URL に localhost は設定できないのでまだサイトがない場合は適当な URL を入力しましょう

  • App permissions・・・Read and write
  • Type of App・・・Web App, Automated App or Bot
  • App info (Callback URI)・・・http://your.huginn.site.com:3000/auth/twitter/callback
  • App info (Website URL)・・・http://your.huginn.site.com:3000

設定が完了するとクライアントIDとクライアントシークレットキーが払い出されます
が huginn では使用しないので無視します

権限設定ができたら Consummer Keys を再作成してメモしておきます
huginn ではこちらの API キーとシークレットキーを使います

キーを huginn に登録して起動

取得した Twitter の クライアントIDとクライアントシークレットキー情報を huginn に渡します
基本的には環境変数として渡します

docker run -it -p 3000:3000 \
-e HUGINN_TWITTER_OAUTH_KEY=xxx -e HUGINN_TWITTER_OAUTH_SECRET=xxx \
ghcr.io/huginn/huginn

huginn と Twitter を連携する (サービスの登録)

http://localhost:3000/services にアクセスすると Twitter の OAuth が使えるようになっています
huginn 経由でツイートするユーザでログインしましょう

We're sorry, but something went wrong (500) となる場合は HUGINN_TWITTER_OAUTH_KEY と HUGINN_TWITTER_OAUTH_SECRET に正しい API キー/シークレットキーが設定されているか確認してください (クライアントIDとクライアントシークレットキーではないので注意してください)

Webhook エージェントの作成

次に Webhook エージェントを作成します http://localhost:3000/agents/new から作成します

Type・・・Webhook Agent Name・・・test_webhook Schedule・・・そのまま Controllers・・・そのまま Keep events・・・そのまま Sources・・・そのまま Receivers・・・そのまま Scenarios・・・そのまま

これで OK です
作成した Webhook エージェントを確認するとコールする URL が発行されるのでメモしておきます
この URL に POST リクエストでアクセスすると Webhook を実行できます

Twitter Publish Agent の作成

あとは Webhook した際に実行されるエージェントを作成します

http://localhost:3000/agents/new から Twitter Publish Agent を作成します

Type・・・Twitter Publish Agent Name・・・test Service・・・Twitter アカウントで連携したサービスを選択 Schedule・・・そのまま Controllers・・・そのまま Keep events・・・そのまま Sources・・・test_webhook Propagate immediately・・・チェックしない Receivers・・・そのまま Scenarios・・・そのまま

Sources に先程作成した Webhook エージェントを指定します
これでツイートする用のエージェントの作成は完了です

動作確認

Webhook をリクエストしてみましょう
そして問題なくツイートされているか確認してください

内部的に順番にジョブが処理されるので少しラグがあるかもしれません

最後に

huginn で Twitter と連携する方法を紹介しました
Twitter と連携する部分がやや面倒ですがそれができれば簡単に Webhook 経由でツイートできました

これで IFTTT や zapier を使わなくて済むかもしれません

参考サイト

2023年5月24日水曜日

emacsで現在のカーソル位置の背景色を変更する方法

emacsで現在のカーソル位置の背景色を変更する方法

概要

global-hl-line-mode を使ってカーソル位置の背景色を変更する方法を紹介します

環境

  • macOS 11.7.6
  • emacs 28.2

設定方法

(global-hl-line-mode t)
(custom-set-faces
 '(hl-line ((t (:background "SteelBlue4")))))

custom-set-faces という関数が用意されているのでそれを使って設定します

2023年5月23日火曜日

ruby-modeでファイルが保存されたときに特定の関数を実行する方法

ruby-modeでファイルが保存されたときに特定の関数を実行する方法

概要

ファイルを保存する際の hook の使い方を紹介します

環境

  • macOS 11.7.6
  • emacs 28.2

サンプルコード

(defun run-anything-after-ruby-file-saved ()
  (when (eq major-mode 'ruby-mode)
    (message "Ruby file saved!")))

(add-hook 'ruby-mode-hook (lambda()
                            (add-hook 'after-save-hook 'run-anything-after-ruby-file-saved)))

ちょっと解説

after-save-hook ではなく before-save-hook もあります

when の部分でメジャーモードを判定しています
ここで指定するモードを変更すれば別のモードでも同じことができます

2023年5月22日月曜日

SolargraphのRequired path patreon could not be resolvedはbundle配下だとほぼ確実に出てしまうので無視するといい

SolargraphのRequired path patreon could not be resolvedはbundle配下だとほぼ確実に出てしまうので無視するといい

概要

Solargraph の reporters にはデフォルトで require_not_found が含まれています

require_not_found は require している gem がちゃんとプロジェクト内に存在してるかチェックしてる機能です

Solargraph で require_not_found を使っている場合に「Required path patreon could not be resolved.」というエラーが出る場合の対処方法を紹介します

原因

bundle 配下で gem を管理しているが Solargraph はグローバルにインストールしたコマンドを使っている場合にはほぼ確実に発生します

理由は bundle 配下にはちゃんと gem があるがグローバルにインストールした Solargraph だと bundle 配下の gem は管理外になるので対象の gem が見つからず require_not_found がエラーを吐いている状況です

対処方法1

solargraph を bundle 配下で動作させる方法で解決できます

設定方法はこちらで紹介しています

対処方法2

.solargraph.yml から require_not_found を削除してしまいましょう

reporters:
- rubocop

おそらくこれが一番簡単です

上記でいい理由

Ruby の場合実行しないと結局わからないので実行することで gem がないかどうかは判別できます
また require した gem があるかどうかよりも require した gem がコード内で参照されているかをチェックしたいですが ruby や rubocop ではそれはできません

結局 require の部分に関しては自分で管理するしかないので require_not_found があってもなくてもそこまで変わらないかなと思います

2023年5月19日金曜日

Python で docker のイメージ名をバリデーションする正規表現

Python で docker のイメージ名をバリデーションする正規表現

概要

結構難しいです

環境

  • macOS 11.7.6
  • Python 3.10.9

正規表現

^(?:(?=[^:\/]{4,253})(?!-)[a-zA-Z0-9-]{1,63}(?<!-)(?:\.(?!-)[a-zA-Z0-9-]{1,63}(?<!-))*(?::[0-9]{1,5})?/)?((?![._-:])(?:[a-z0-9._-]*)(?<![._-])(?:/(?![._-])[a-z0-9._-]*(?<![._-]))*)(?::(?![.-])[a-zA-Z0-9_.-]{1,128})?$

パーツごとに説明

^
(?:  # プロトコルとドメインの部分
    (?=[^:\/]{1,253})  # ドメインが253文字以下であることを確認
    (?!-)[a-zA-Z0-9-]{1,63}(?<!-)  # ドメインの最初と最後にハイフンがないことを確認
    (?:\.(?!-)[a-zA-Z0-9-]{1,63}(?<!-))*  # ドメインの各部分が最初と最後にハイフンがないことを確認
    (?::[0-9]{1,5})?  # ポート番号がある場合にマッチ
    /  # ドメインとパスの区切りを表すスラッシュ
)?
(  # パスの部分
    (?![:._-])  # パスがコロン、ハイフン、ピリオド、アンダースコアで始まらないことを確認
    (?:[a-z0-9._-]*)  # パスの部分に含まれる文字列
    (?<![._-])  # パスがハイフン、ピリオド、アンダースコアで終わらないことを確認
    (?:/(?![._-])[a-z0-9._-]*(?<![._-]))*  # イメージ名
)
(?::(?![.-])[a-zA-Z0-9_.-]{1,128})?  # オプションでタグ名
$

2023年5月18日木曜日

(emacs)robeを再起動する方法

(emacs)robeを再起動する方法

概要

robe-start すると inf-ruby 経由で pry バッファが起動します
新規でファイルを追加したり既存のファイルを変更すると pry バッファには反映されません

今回はそんなときに使える pry バッファの再起動方法を紹介します

環境

  • macOS 11.7.6
  • emacs 28.2
  • robe 20221207.225
  • pry 0.14.2

仕組み

robe を再起動するということは pry バッファを削除し再度 robe-start を実行することと同義です

なのでそれを行う関数を定義するだけです

コード

(defun restart-pry-buffer ()
  "Restart the Pry buffer by killing it and starting robe again."
  (interactive)
  (let ((pry-buffer (get-buffer "*pry*")))
    (when pry-buffer
      (kill-buffer pry-buffer)))
  (robe-start))

使い方

  • M-x restart-pry-buffer

注意点

kill-buffer と robe-start の際に確認を求められます

改良版: kill-buffer 時に確認を求められない

(defun restart-pry-buffer ()
  "Restart the Pry buffer by killing it and starting robe again."
  (interactive)
  (let ((pry-buffer (get-buffer "*pry*"))
        (kill-buffer-query-functions nil)
        (kill-buffer-hook nil))
    (when pry-buffer
      (kill-buffer pry-buffer)))
  (robe-start))

2023年5月17日水曜日

Stable Diffusion でシード値を使って全く同じ画像を生成する方法

Stable Diffusion でシード値を使って全く同じ画像を生成する方法

概要

Stable-Diffusion で全く同じ画像を生成するにはシード値を使います
今回は PromptHero にある画像をシード値を使って生成する方法を紹介します

環境

  • GoogleColab (2023/05/03 時点)
  • stable-diffusion-webui 1.1.0
  • stable-diffusion 1.5 (pruned)

再現する画像

今回はこちらを生成してみます

ポイント

シード値は当然ですがそれ以外にもモデル、モデル用設定ファイル、プロンプトやネガティブプロンプト、ステップ数なども同一の値にする必要があります

特にモデルが大変でバージョンが違うだけで全然違う画像が生成されてしまうので必ず同一モデル+同一パラメータで生成する必要があります

コード

今回は stable-diffusion-v1.5 を使います
StableDiffusionWebUI はデフォルトで stable-diffusion-v1.5 を使いますが emaonly 版なので pruned 版を使うようにします

!git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui
%cd stable-diffusion-webui

!wget https://huggingface.co/runwayml/stable-diffusion-v1-5/resolve/main/v1-5-pruned.safetensors -O /content/stable-diffusion-webui/models/Stable-diffusion/v1-5-pruned.safetensors
!wget https://huggingface.co/runwayml/stable-diffusion-v1-5/raw/main/v1-inference.yaml -O /content/stable-diffusion-webui/configs/v1-inference.yaml

!COMMANDLINE_ARGS="--share --gradio-debug --xformers --gradio-auth me:qwerty" REQS_FILE="requirements.txt" python launch.py

動作確認

今回は以下を同一の値に設定します

  • プロンプト -> (masterpiece:1.0), (best quality:1.4), (ultra highres:1.2), (photorealistic:1.4), (8k, RAW photo:1.2), (soft focus:1.4), 1 woman, posh, (sharp focus:1.4), (korean:1.2), (american:1.1), detailed beautiful face, black hair, (detailed open blazer:1.4), tie, beautiful white shiny humid skin, smiling
  • ネガティブプロンプト -> illustration, 3d, sepia, painting, cartoons, sketch, (worst quality:2), (low quality:2), (normal quality:2), lowres, bad anatomy, bad hands, normal quality, ((monochrome)), ((grayscale:1.2)),newhalf, collapsed eyeshadow, multiple eyebrows, pink hair, analog, analogphoto
  • シード値 -> 300563992
  • ステップ数 -> 35
  • サンプラー -> DPM++ 2M Karras
  • CFG -> 7.0

これで実行して同一画像が生成されることを確認しましょう

最後に

モデルのバージョンが違うと別の画像になることがあるのでモデルのバージョンとリビジョンも確認しましょう

2023年5月16日火曜日

StableDiffusionWebUI を Intel Mac 上で動かしてみる

StableDiffusionWebUI を Intel Mac 上で動かしてみる

概要

Intel Mac 搭載の MacBookAir 2014 Late で動作するか試してみました

環境

  • MacBookAir late 2014
    • Intel® Core™ i7-4650U CPU @ 1.70GHz
    • Memry8GB
    • Intel HD Graphics 5000
  • macOS 11.7.6
  • Stable Diffusion WebUI
  • Python 3.10.9

インストール

  • git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui
  • cd stable-diffusion-webui
  • sh webui.sh --no-half --use-cpu all

今回は CPU リソースのみ使用するので --no-half --use-cpu all オプションが必須です

必要なライブラリなどがない場合は適当に Homebrew でインストールしてください

v1-5-pruned-emaonly.safetensors モデルが 4GB ほどあるのでディスク容量があることも確認してください

起動までに掛かった時間

モデルのダウンロードも含めて 20 分くらいで完了します
ダウンロード後にロードもあるので低スペックマシンだと起動だけで結構な時間がかかります

なお起動すると CPU もメモリもかなり消費量が上がりマシンの動作が重くなります

動作確認

http://127.0.0.1:7860/ にアクセスしましょう

試しに適当に画像を出力してみました
プロンプトは「a cute girl」にしています

出力までにかかった時間

とりあえずデフォルトの設定で1枚出力するのに 約 10 分はかかりました

20/20 [12:01<00:00, 36.09s/it]

ステップ数は20なのでこれを増やせばもっと時間はかかるかなと思います

最後に

StableDiffusionWebUI を IntelMac 上で動かしてみました
動くには動きますが画像の生成にかなり時間がかかるので検証などに使うのもあまりおすすめはできません

もう少しいい CPU の Mac ならもっと生成は早くなるかもしれません

2023年5月15日月曜日

StableDiffusionWebUIでLoraモデルを使用する方法

StableDiffusionWebUIでLoraモデルを使用する方法

概要

タイトルの通りです
Loraモデルを使う場合でも単純にモデルを入れ替える方法を使うだけで OK です

今回はこちらのモデルを使います

環境

  • GoogleColab (2023/05/03 時点)
  • stable-diffusion-webui 1.1.0
  • stable diffustion 2.0MeinaMix v9

注意点

今回の Lora モデルは「CHECKPOINT MERGE」という種類になります
これはすでにベースとなるモデルに対して追加で Lora モデルを足しているのでベースとなるモデルの指定が不要になります

対して「Lora 拡張」なモデルもありこの場合はベースとなるモデル (例えば stable-diffusion-v1.5 など) が必要になります

今回の方法は CheckPoint Merge なモデルなので普通にモデルを入れ替える方法で OK です

コード

!git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui
%cd stable-diffusion-webui

# 今回は CheckPoint Merge なモデルなので Stable-diffusion 配下に直接配置する
!wget https://civitai.com/api/download/models/46137 --content-disposition -O /content/stable-diffusion-webui/models/Stable-diffusion/meinamix_meinaV9.safetensors
# CheckPoint Merge ではなく Lora 拡張の場合は拡張用の別のディレクトリ (models/Lora) に配置する
# !mkdir -p /content/stable-diffusion-webui/models/Lora/
# !wget https://civitai.com/api/download/models/63006 --content-disposition -O /content/stable-diffusion-webui/models/Lora/LowRA.safetensors

!COMMANDLINE_ARGS="--share --gradio-debug --xformers --gradio-auth me:qwerty" REQS_FILE="requirements.txt" python launch.py

!wget ... の部分が CivitAI というサイトから Lora モデルをダウンロードしている処理になります
ポイントは CheckPoint Merge な Lora モデルは /content/stable-diffusion-webui/models/Stable-diffusion/ に直接配置する点です

あとは普通に SD-WebUI を起動するだけです

動作確認

CheckPoint が Lora モデルになっていることを確認します
CheckPoint Merge の場合は普通にプロンプトに入力すれば OK です

最後の

Lora モデルを Stable Diffusion WebUI に導入する方法を紹介しました

CheckPointMerge の場合は Lora 拡張のみの場合で導入方法が少し異なるので注意しましょう

参考サイト

2023年5月12日金曜日

StableDiffusionWebUIでStableDiffusion2.0を使う方法

StableDiffusionWebUIでStableDiffusion2.0を使う方法

概要

HuggingFaceからStable Diffusion2.0モデルを取得して StableDiffusionWebUI で使ってみます

動作は Google Colab を使います

環境

  • GoogleColab (2023/05/03 時点)
  • stable-diffusion-webui 1.1.0
  • stable diffustion 2.0

コード

!git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui
%cd stable-diffusion-webui

!wget https://huggingface.co/stabilityai/stable-diffusion-2/resolve/main/768-v-ema.ckpt -O /content/stable-diffusion-webui/models/Stable-diffusion/768-v-ema.ckpt
!wget https://raw.githubusercontent.com/Stability-AI/stablediffusion/main/configs/stable-diffusion/v2-inference-v.yaml -O /content/stable-diffusion-webui/models/Stable-diffusion/768-v-ema.yaml

!COMMANDLINE_ARGS="--share --gradio-debug --xformers --gradio-auth me:qwerty" REQS_FILE="requirements.txt" python launch.py

動作確認

参考サイト

2023年5月11日木曜日

StableDiffusionWebUIで使用するモデルを変更する方法

StableDiffusionWebUIで使用するモデルを変更する方法

概要

前回 Stable Diffusion WebUI を Google Colab 上で動作させました

今回は Stable Diffusion のモデルを変更する方法を紹介します
モデルは waifu-diffusion というモデルに変更します

環境

  • GoogleColab (2023/05/03 時点)
  • stable-diffusion-webui 1.1.0
  • waifu-diffusion 1.4.0

前回のコードにモデルをダウンロードするコードを追加

以下のコードを Stable Diffusion WebUI クローン後に追加します

!wget https://huggingface.co/hakurei/waifu-diffusion-v1-4/resolve/main/wd-1-4-anime_e2.ckpt -O /content/stable-diffusion-webui/models/Stable-diffusion/wd-1-4-anime_e2.ckpt

コード全体

コード全体は以下のようになります

!git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui
%cd stable-diffusion-webui

!wget https://huggingface.co/hakurei/waifu-diffusion-v1-4/resolve/main/wd-1-4-anime_e2.ckpt -O /content/stable-diffusion-webui/models/Stable-diffusion/wd-1-4-anime_e2.ckpt

!COMMANDLINE_ARGS="--share --gradio-debug --gradio-auth me:qwerty" REQS_FILE="requirements.txt" python launch.py

動作確認

起動後にモデルが wd-1-4-anime_e2.ckpt に変わっていることを確認します

最後に

StableDiffusion WebUI もすでに models/Stable-diffusion 配下に何かしらのモデルがあるとデフォルトの runwayml のモデルは取得しないようです

なので runwayml もほしい場合は明記する必要があります (もしくは今回追加したコードを削除する)

参考サイト

2023年5月10日水曜日

GoogleColab で StableDiffusionWebUI が起動するか試す

GoogleColab で StableDiffusionUI を起動するか試す

概要

StableDiffusionUI が無料の GoogleColaboratory 上で動作するか試してみました

環境

  • GoogleColab (2023/05/03 時点)
  • stable-diffusion-webui 1.1.0

リポジトリの clone

!git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui
%cd stable-diffusion-webui

実行

!COMMANDLINE_ARGS="--share --gradio-debug --gradio-auth me:qwerty" REQS_FILE="requirements.txt" python launch.py

実行ログ

Python 3.10.11 (main, Apr  5 2023, 14:15:10) [GCC 9.4.0]
Commit hash: 5ab7f213bec2f816f9c5644becb32eb72c8ffb89
Installing gfpgan
Installing clip
Installing open_clip
Cloning Stable Diffusion into /content/stable-diffusion-webui/repositories/stable-diffusion-stability-ai...
Cloning Taming Transformers into /content/stable-diffusion-webui/repositories/taming-transformers...
Cloning K-diffusion into /content/stable-diffusion-webui/repositories/k-diffusion...
Cloning CodeFormer into /content/stable-diffusion-webui/repositories/CodeFormer...
Cloning BLIP into /content/stable-diffusion-webui/repositories/BLIP...
Installing requirements for CodeFormer
Installing requirements
Launching Web UI with arguments: --share --gradio-debug --gradio-auth me:qwerty
2023-05-03 07:06:08.915792: I tensorflow/core/platform/cpu_feature_guard.cc:182] This TensorFlow binary is optimized to use available CPU instructions in performance-critical operations.
To enable the following instructions: AVX2 AVX512F FMA, in other operations, rebuild TensorFlow with the appropriate compiler flags.
2023-05-03 07:06:09.904251: W tensorflow/compiler/tf2tensorrt/utils/py_utils.cc:38] TF-TRT Warning: Could not find TensorRT
No module 'xformers'. Proceeding without it.
Downloading: "https://huggingface.co/runwayml/stable-diffusion-v1-5/resolve/main/v1-5-pruned-emaonly.safetensors" to /content/stable-diffusion-webui/models/Stable-diffusion/v1-5-pruned-emaonly.safetensors

100% 3.97G/3.97G [00:23<00:00, 180MB/s]
Calculating sha256 for /content/stable-diffusion-webui/models/Stable-diffusion/v1-5-pruned-emaonly.safetensors: 6ce0161689b3853acaa03779ec93eafe75a02f4ced659bee03f50797806fa2fa
Loading weights [6ce0161689] from /content/stable-diffusion-webui/models/Stable-diffusion/v1-5-pruned-emaonly.safetensors
Creating model from config: /content/stable-diffusion-webui/configs/v1-inference.yaml
LatentDiffusion: Running in eps-prediction mode
DiffusionWrapper has 859.52 M params.
Downloading (…)olve/main/vocab.json: 100% 961k/961k [00:00<00:00, 11.8MB/s]
Downloading (…)olve/main/merges.txt: 100% 525k/525k [00:00<00:00, 3.19MB/s]
Downloading (…)cial_tokens_map.json: 100% 389/389 [00:00<00:00, 2.52MB/s]
Downloading (…)okenizer_config.json: 100% 905/905 [00:00<00:00, 5.12MB/s]
Downloading (…)lve/main/config.json: 100% 4.52k/4.52k [00:00<00:00, 21.7MB/s]
Applying cross attention optimization (Doggettx).
Textual inversion embeddings loaded(0): 
Model loaded in 30.9s (calculate hash: 14.0s, load weights from disk: 0.3s, create model: 2.3s, apply weights to model: 4.4s, apply half(): 1.4s, load VAE: 7.9s, move model to device: 0.6s).
Running on local URL:  http://127.0.0.1:7860
Running on public URL: https://xxx.gradio.live

This share link expires in 72 hours. For free permanent hosting and GPU upgrades (NEW!), check out Spaces: https://huggingface.co/spaces

結果

普通に起動しました

メモリ不足で起動しない場合は StableDiffusionUI-Voldemort V1.3.ipynb ではなく素の stable-diffusion-webui から起動するといいかもしれません

参考サイト

2023年5月9日火曜日

GoogleColab超入門

GoogleColab超入門

概要

Google Colaboratory は Python の実行環境を提供してくれるサービスです
無料で GPU リソースも使えます
今回は超入門として簡単なスクリプトを実行してみます

環境

  • GoogleColab (2023/05/03 時点)
    • ハードウェアアクセラレータ None

アクセス

ノートブックを新規作成

モーダルが表示されるので「ノートブックを新規作成」をクリックします

コードの追加

import sys
print(sys.version)

コードの実行

  • 三角ボタンをクリック

GPU を使う

  • ランタイム -> ランタイムのタイプを変更 -> ハードウェアアクセラレータ -> GPU

GPU の状態を確認

  • !nvidia-smi

シェルコマンドの実行

  • !hostname

先頭にビックリマークを付けるとシェルコマンドが実行できます

最後に

こんな感じで簡単に Python を実行できます
無料で GPU リソースも使えます

2023年5月8日月曜日

wxPythonでメニューバーやステータスバーを設置する(超入門2)

wxPythonでメニューバーやステータスバーを設置する(超入門2)

概要

前回 wxPython を動かすところまでやってみました
今回は実践としてメニューバーとステータスバーを追加するところまでやってみました

こちらのサンプルコードを使っています

環境

  • macOS 11.7.6
  • Python 3.10.2
  • wxPython 4.2.0

サンプルコード

import wx

class HelloFrame(wx.Frame):
    """フレームを管理するクラス、このクラス配下にパネルやメニューバーを追加します"""

    def __init__(self, *args, **kw):
        super(HelloFrame, self).__init__(*args, **kw)

        # メインパネルの作成
        pnl = wx.Panel(self)

        st = wx.StaticText(pnl, label="Hello World!")
        font = st.GetFont()
        font.PointSize += 10
        font = font.Bold()
        st.SetFont(font)

        sizer = wx.BoxSizer(wx.VERTICAL)
        sizer.Add(st, wx.SizerFlags().Border(wx.TOP|wx.LEFT, 25))
        pnl.SetSizer(sizer)

        # メニューバー作成
        self.makeMenuBar()

        # ステータスバー作成
        self.CreateStatusBar()
        self.SetStatusText("Welcome to wxPython!")

    def makeMenuBar(self):
        # メニューの作成
        fileMenu = wx.Menu()
        helpMenu = wx.Menu()
        # メニューバーに表示するアイテムの作成
        helloItem = fileMenu.Append(-1, "&Hello...\tCtrl-H", "Help string shown in status bar for this menu item")
        exitItem = fileMenu.Append(wx.ID_EXIT)
        aboutItem = helpMenu.Append(wx.ID_ABOUT)

        # メニューバーの作成、各種アイテムの追加
        menuBar = wx.MenuBar()
        menuBar.Append(fileMenu, "&File")
        menuBar.Append(helpMenu, "&Help")
        self.SetMenuBar(menuBar)
        # アイテムが押されたときのイベント処理を定義
        self.Bind(wx.EVT_MENU, self.OnHello, helloItem)
        self.Bind(wx.EVT_MENU, self.OnExit,  exitItem)
        self.Bind(wx.EVT_MENU, self.OnAbout, aboutItem)

    def OnExit(self, event):
        self.Close(True)

    def OnHello(self, event):
        wx.MessageBox("Hello again from wxPython")

    def OnAbout(self, event):
        wx.MessageBox("This is a wxPython Hello World sample", "About Hello World 2", wx.OK|wx.ICON_INFORMATION)


if __name__ == '__main__':
    app = wx.App()
    frm = HelloFrame(None, title='Hello World 2')
    frm.Show()
    app.MainLoop()

ちょっと解説

基本はフレーム上にパネルやメニューを追加していきます
前回の HelloWorld とは違いクラス化していますが実際にアプリケーションを作る場合はこんな感じで各種パーツをクラス化して配置していくほうが開発効率が良いと思います

メニューはメニューバーとアイテムから構成されています
各種アイテムにはイベントを設定することができボタンが押されたときのアクションやホバーしたときのアクションを定義することができます

最後に

次はこのあたりを参考にして必要なパーツの追加やアクションを定義します