OmniAICreator/Qiita-1.07M huggingface dataset:
ASUS Chromebook Flip C101PA にインストールしたVisual Studio Codeをターミナルから起動

ChromebookでLinuxが起動できるようになったとのことで、
ASUS Chromebook Flip C101PAに、VS Codeをインストールしてみました。

Linuxのターミナルから起動しようと思ったら躓いたのでメモ。
通常は、`code`コマンドで起動しますが、C101PAのCPUアーキテクチャの関係で、ARM64版のVS-Codeをインストールしているので起動コマンドは

```
$ code-oss [ファイル名]
```

になります。

インストールは、詳しいサイトがたくさんあるので参考に。


## 参考サイト

- http://www.webcyou.com/?p=8765
- https://code.headmelted.com/
- https://goodegg.jp/archives/10403

日本語入力の設定はここのが新しくてよかった

- https://matoken.org/blog/2018/10/23/debian-ubuntu-borrows-the-upstream-package/
visudoをvimで編集する

vi苦手なので、下記で編集しています。

```
$ sudo vim /etc/sudoers
```
こんなことがやりたい時に使います。

[linuxに、root userでも使えるpyenv環境の構築](https://qiita.com/u_kan/items/d7e602bf1cf52f6b0935)
テスト・ケース制作ツールの制作記（はじめに）



ご存知ですか知らないですが、私はテスト・ケースの設計ツール・サイトを作ってこれをanalyzingcontext.comというサイトに組み込んで運営しています。まだユーザはゼロに近いです。



でも私なりにおよそ十年経たSW品質の経験を上のツールでまとめたものですが、あんまり関連者たちに影響をくれなかったと思ってちょっともったいない感じが心のすみにありましたが…

 

この間にRubyの創始者である「まつもとゆきひろ」の「言語のしくみ」という本をよみました。この本は、Rubyとは別のストリームの形態の言語「Streem（streamとはスペルが違う）」を提示し、その制作過程を日経Linuxのに連載したものを単行本化したものです。



現在Streemがある程度まで完成されているかどうか分かりませんが、Rubyを育てておいて、また新しい言語を設計して提示する著者の情熱も驚いくらいです。ステップバイステップの製作過程を記述して、著者がどの悩みをしたのか、その悩みをどのように解決したのかを読んでみるのもシステムプログラミングをよく知らない私としてもかなり面白いでした。

analyzingcontext.comというサイトを作成まで私なりに多くの旅があった。当時私は思っていたプロセスをある程度整理することも、業界や他の人に役立つような気が、上記の本を読んでからに考えたものです。



#### すると実践しなきゃ!!!



今考えている目次は以下のようです。

1. 開発ドキュメントを読み込んでテスト・ケースを直接つくる？
2. 愛憎のallpairs.py
3. MC/DCのフェイクバージョン
4. pyinstaller...
5. ユーザシナリオの未練
6. MC/DCの完成
6. ウェーブで行こう。
7. ウェーブで実装するマインド・マップ
8. ウェーブのユーザー権限制限
9. テストケース？ユーズ・ケース？

では、よろしくお願いします。
SCSSで連番のClassを作成して、限られた色を回す

## Before

```scss
// 色は4色
$colors:
        var(--blue-dark),
        var(--pale),
        var(--blue),
        var(--purple);

// 10が回す件数
$typeCount: 10 - 1;
.color {
  @for $i from 0 through $typeCount {
    $num: "";
    // ０埋め処理
    @if $i < 9 {
      $num: "0#{$i + 1}";
    } @else {
      $num: $i + 1;
    }
    &--type#{$num} {
      $n: nth($colors, $i % length($colors) + 1);
      border: 2px solid #{$n};
    }
  }
}
```

## After

```css
.color--type01 {
  border: 2px solid var(--blue-dark);
}
.color--type02 {
  border: 2px solid var(--pale);
}
.color--type03 {
  border: 2px solid var(--blue);
}
.color--type04 {
  border: 2px solid var(--purple);
}
.color--type05 {
  border: 2px solid var(--blue-dark);
}
.color--type06 {
  border: 2px solid var(--pale);
}
.color--type07 {
  border: 2px solid var(--blue);
}
.color--type08 {
  border: 2px solid var(--purple);
}
.color--type09 {
  border: 2px solid var(--blue-dark);
}
.color--type10 {
  border: 2px solid var(--pale);
}

```
Windows10にJenkinsインストール~起動 ポート番号変更

## 全体的に
* [このサイト](https://ics.media/entry/2410)を参考にインストール、初期設定した

## Jenkinsのインストール
ざっくり手順を書くと・・・ 

* [Jenkins公式サイト](https://jenkins.io/download/)よりWindows用のLTS版をダウンロード
* インストールフォルダをC:\Jenkins\に変更
* それ以外はデフォルトのまま

## Jenkins起動しようとしたけど、、、
* デフォルトでは  
http://localhost:8080/  
でアクセスするが、
ポート8080は他で使用中なので、ポートを変更しなきゃ

## Jenkins ポート番号変更
* インストールフォルダ直下にある  
C:\Jenkins\jenkins.xml  
を下記のように、任意のポート番号xxxxに修正

``` 修正前
<arguments>-Xrs 省略 --httpPort=xxxx 省略</arguments>
```
## ポート番号変更後は、Jenkinsサービスを再起動
* ctrl + alt + delete でタスクマネージャ起動して
* サービスタブを選択して
* Jenkisサービスを再起動
![jks.png](https://qiita-image-store.s3.amazonaws.com/0/281492/00bc3c47-b6fa-462a-aa6b-c83f0d442b08.png)

## 上記以外は、参考サイトの通り！ おしまい！
Netlify Forms の完了画面をデフォルトから変更する

GitHub へ push するだけで deploy できてしまう便利な Netlify ですが、`<form>` タグに `data-netlify="true"` を入れるだけで、フォームを置くことができます。

ただそれだけだと、フォーム送信後に Netlify のデフォルトのものが表示されてしまいます。これって、カスタマイズできないものかと、[ドキュメント](https://www.netlify.com/docs/form-handling/)を漁ってみると…

>By default, when visitors complete a form, they will see a generically styled success message with a link back to the form page. You can replace the default success message with a custom page you create by adding an action attribute to the <form> tag, entering the path of your custom page (like "/pages/success") as the value. The path must be relative to the site root, starting with a /.

つまり、

```html
<form name="contact" method="POST" data-netlify="true" action="/送信完了後に表示させたいページパス">
```

で、とりあえずいけるということでした。

ヴァリデーションなど、細かな実装は必要ですが、簡易的なものから、 reCAPTCHA 2 を絡めたものまで Netlify でできてしまうのはなかなか興味深いです。

フォームに投稿された通知は [Zapier](https://zapier.com/) の連携をオススメしてますが、~~そこをどうするかは悩み中。~~ Netlify の中で設定できるので、それを試してみようと思っています。
ReactでGoogleログイン認証を実装してみた

#概要
今回はGoogleのログインを実装していきます。
目標としてはstateにログイン情報を置いて、それがtrueならば"login with google!!", falseならば"I can not see your google account!!"　と文字を出したいと思います。
#実装
まずはGoogle APIのライブラリを使うためにscriptで読み込んであげないといけません。

```javascript:public/index.html
<script src="https://apis.google.com/js/api.js"></script>
```
こうすることでgapiと呼ばれるメソッドを使うことができます。
メソッドの説明に関しては以下を参考にしてください。

参考　https://developers.google.com/api-client-library/javascript/reference/referencedocs#gapiauth2getauthinstance

ページを読み込んだ際に、ログインしているか否かを判断したいので、componentDidMount()の中に実装していきます。
以下のコードを見てください。

```javascript:src/components/App.js
componentDidMount() {
    window.gapi.load('client:auth2', () => {
      window.gapi.client.init({
        clientId: "clientID", //"clientID"は個人で取得する
        scope: "email"
      }).then(() => {
        const auth = window.gapi.auth2.getAuthInstance();

        this.setState({ isSignedIn: auth.isSignedIn.get() });
      });
    });
  }
```
"clientID"は以下のサイトからプロジェクトを登録して取得する必要があります。

https://console.developers.google.com

プロジェクトを作成したら認証情報をクリックし、そこのOAuth同意画面でアプリケーション名を決めた後、認証情報を作成からOAuth クライアントIDをクリックしたら取得できると思います。

上のコードではログイン状態をstateに保存しています。
src/components/App.jsの全体を見ましょう。

```javascript:src/components/App.js
import React, { Component } from 'react';

class App extends Component {
  state = { isSignedIn: null };

  componentDidMount() {
    window.gapi.load('client:auth2', () => {
      window.gapi.client.init({
        clientId: "clientID", 
        scope: "email"
      }).then(() => {
        const auth = window.gapi.auth2.getAuthInstance();

        this.setState({ isSignedIn: auth.isSignedIn.get() });
      });
    });
  }

  renderAuth() {
    if (this.state.isSignedIn === null) {
      return <div>i dont know your google account</div>
    } else if (this.state.isSignedIn) {
      return <div>login with google!!</div>
    } else {
      return <div>I can not see your google account!!</div>
    }
  }

  loginWithGoogle = () => {
    window.gapi.auth2.getAuthInstance().signIn();
  }

  logoutFromGoogle = () => {
    window.gapi.auth2.getAuthInstance().signOut();
  }

  render() {
    return (
      <div>
        {this.renderAuth()}
        <button onClick={this.loginWithGoogle}>
          login with google
        </button>
        <button onClick={this.logoutFromGoogle}>
          logout from google
        </button>
      </div>
    );
  }
}

export default App;
```
renderAuth()で条件分岐してstateの状態によって表示する文字を変えます。
ボタンを２つ配置し、それぞれログインとログアウトのボタンです。
これらをクリックし、ページをリロードするとそれにあった文字が表示されるはずです。
#まとめ
Google認証を作ってみました。
何かサービスを作るときに利用できればと思ってます。
参考になれば幸いです。
chart.jsでCanvasタグが画面全体に広がってしまうことに関して

chart.jsでグラフを描写しようとしたときに、グラフがブラウザ全体に広がってしまいました。
optionsで`responsive: false`と明示することでレスポンシブルが解除されました。
デフォルトでレスポンシブルになっているようなので、記入しなかったり、コメントアウトしてもレスポンシブルになってしまいます。

```
var options = {

    responsive: false,
    title:{ display:true,
        text:'Chart sample'
    },
    chartArea: {
        backgroundColor: "#ecf0f1"
    }
};

```
Vue CLI 3 インストールからプロジェクト作成まで

# Vue CLI 3 インストールからプロジェクト作成まで

Windows コマンドプロンプトを起動します。

node & npm のバージョンは以下の通りです。

```
$ node --version
v10.14.2
$ npm --version
6.4.1
```

## @vue/cli をグローバルにインストール

```
$ npm install -g @vue/cli
...
+ @vue/cli@3.4.0
added 668 packages from 500 contributors in 161.611s
```

## プロジェクト作成（マニュアル）

以前は`init`サブコマンドを使っていましたが ver3 から create です。

```
$ vue create vue-example
```

インストール方法を「デフォルト」か「手動」か選択するよう確認されます。

```
Vue CLI v3.4.0
? Please pick a preset:
  default (babel, eslint)
> Manually select features
```

ここでは「マニュアル」を選択します。
`Manually select features`を選んで Enter を押します。

次にプロジェクトに必要な機能を選択します。
下記の`*`がついた機能をインストールします。スペースキーでトグルしてください。

```
? Check the features needed for your project:
>(*) Babel
 ( ) TypeScript
 ( ) Progressive Web App (PWA) Support
 (*) Router
 (*) Vuex
 (*) CSS Pre-processors
 (*) Linter / Formatter
 (*) Unit Testing
 ( ) E2E Testing
```

選択したら Enter キーを押します。

### router のヒストリーモード

```
? Use history mode for router? (Requires proper server setup for index fallback in production) (Y/n)
```

ヒストリーモードを使用するので Y キーを入力して Enter を押します。

### CSS プリプロセッサ

```
? Pick a CSS pre-processor (PostCSS, Autoprefixer and CSS Modules are supported by default): (Use arrow keys)
  Sass/SCSS (with dart-sass)
  Sass/SCSS (with node-sass)
  Less
> Stylus
```

`Stylus`を選択した状態で Enter を押します。

### ESLint

```
? Pick a linter / formatter config: (Use arrow keys)
> ESLint with error prevention only
  ESLint + Airbnb config
  ESLint + Standard config
  ESLint + Prettier
```

エラー防止のみの`ESLint with error prevention only`を選択して Enter を押します。

### Lint 実行タイミング

```
? Pick additional lint features: (Press <space> to select, <a> to toggle all, <i> to invert selection)
>(*) Lint on save
 ( ) Lint and fix on commit
```

保存時に Lint を実行するため`Lint on save`のみチェックを入れて Enter を押します。

### 単体テスト

```
? Pick a unit testing solution: (Use arrow keys)
> Mocha + Chai
  Jest
```

ユニットテストは`Mocha + Chai`を選択して Enter を押します。

### 設定ファイル

```
? Where do you prefer placing config for Babel, PostCSS, ESLint, etc.? (Use arrow keys)
> In dedicated config files
  In package.json
```

設定ファイルは個別に管理するので`In dedicated config files`を選択して Enter を押します。

### プリセットの保存

```
? Save this as a preset for future projects? (y/N)
```

次回のインストールのためにこの設定を保存しておきます。y キーを入力して Enter キーを押します。

```
? Save preset as: example
```

ここではプリセット名を`example`と入力します。
Enter でインストールを開始します。

### 起動

```
> cd vue-example
> npm run serve
```
Stanford NLP で英語キーワードの原型などを取得する



#ソースコード

```java

import java.util.List;
import java.util.Properties;

import edu.stanford.nlp.ling.CoreAnnotations.LemmaAnnotation;
import edu.stanford.nlp.ling.CoreAnnotations.NamedEntityTagAnnotation;
import edu.stanford.nlp.ling.CoreAnnotations.PartOfSpeechAnnotation;
import edu.stanford.nlp.ling.CoreAnnotations.TextAnnotation;
import edu.stanford.nlp.ling.CoreAnnotations.TokensAnnotation;
import edu.stanford.nlp.ling.CoreLabel;
import edu.stanford.nlp.pipeline.Annotation;
import edu.stanford.nlp.pipeline.StanfordCoreNLP;

public class App {
	public static void main(String[] args) {
		String text = "Nissan Motor Co., Ltd is a Japanese multinational automobile manufacture headquartered in Yokohama.";
		Properties properties = new Properties();
		properties.setProperty("annotators", "tokenize,ssplit,pos,lemma,ner");

		StanfordCoreNLP coreNLP = new StanfordCoreNLP(properties);

		Annotation annotation = new Annotation(text);
		coreNLP.annotate(annotation);

		List<CoreLabel> labels = annotation.get(TokensAnnotation.class);

		System.err.println("Text,POS,Lemma,NE");

		for (CoreLabel label : labels) {
			System.err.println(label.get(TextAnnotation.class) + ":" //
					+ label.get(PartOfSpeechAnnotation.class) + ":" //
					+ label.get(LemmaAnnotation.class) + ":" //
					+ label.get(NamedEntityTagAnnotation.class) + ":" //
			);
		}

	}
}

```

#出力結果

```

Text,POS,Lemma,NE
Nissan:NNP:Nissan:ORGANIZATION:
Motor:NNP:Motor:ORGANIZATION:
Co.:NNP:Co.:ORGANIZATION:
,:,:,:O:
Ltd:NNP:Ltd:ORGANIZATION:
is:VBZ:be:O:
a:DT:a:O:
Japanese:JJ:japanese:MISC:
multinational:JJ:multinational:O:
automobile:NN:automobile:O:
manufacture:NN:manufacture:O:
headquartered:VBN:headquarter:O:
in:IN:in:O:
Yokohama:NNP:Yokohama:LOCATION:
.:.:.:O:


```

#結果表

結果を表にすると以下の通り。


|Text        |POS         |Lemma       |NE          |
|:-----------|:-----------|:-----------|:-----------|
|Nissan|NNP|Nissan|ORGANIZATION|
|Motor|NNP|Motor|ORGANIZATION|
|Co.|NNP|Co.|ORGANIZATION|
|,|,|,|O|
|Ltd|NNP|Ltd|ORGANIZATION|
|is|VBZ|be|O|
|a|DT|a|O|
|Japanese|JJ|japanese|MISC|
|multinational|JJ|multinational|O|
|automobile|NN|automobile|O|
|manufacture|NN|manufacture|O|
|headquartered|VBN|headquarter|O|
|in|IN|in|O|
|Yokohama|NNP|Yokohama|LOCATION|
|.|.|.|O|
JavaのStringで全角→半角変換 (全角かな→半角カナ)

```
public class Zen2HanUtil {
    private static final Map<Character, String> zen2HanMap = new HashMap<>();

    // https://so-zou.jp/web-app/text/fullwidth-halfwidth/
    private static final String ZEN_CHARS = "０ １ ２ ３ ４ ５ ６ ７ ８ ９ "
            + "Ａ Ｂ Ｃ Ｄ Ｅ Ｆ Ｇ Ｈ Ｉ Ｊ Ｋ Ｌ Ｍ Ｎ Ｏ Ｐ Ｑ Ｒ Ｓ Ｔ Ｕ Ｖ Ｗ Ｘ Ｙ Ｚ "
            + "ａ ｂ ｃ ｄ ｅ ｆ ｇ ｈ ｉ ｊ ｋ ｌ ｍ ｎ ｏ ｐ ｑ ｒ ｓ ｔ ｕ ｖ ｗ ｘ ｙ ｚ "
            + "あ い う え お か き く け こ さ し す せ そ た ち つ て と な に ぬ ね の は ひ ふ へ ほ ま み む め も や ゆ よ ら り る れ ろ わ を ん "
            + "ア イ ウ エ オ カ キ ク ケ コ サ シ ス セ ソ タ チ ツ テ ト ナ ニ ヌ ネ ノ ハ ヒ フ ヘ ホ マ ミ ム メ モ ヤ ユ ヨ ラ リ ル レ ロ ワ ヲ ン "
            + "ゔ が ぎ ぐ げ ご ざ じ ず ぜ ぞ だ ぢ づ で ど ば び ぶ べ ぼ ぱ ぴ ぷ ぺ ぽ ぁ ぃ ぅ ぇ ぉ ゃ ゅ ょ っ "
            + "ヴ ガ ギ グ ゲ ゴ ザ ジ ズ ゼ ゾ ダ ヂ ヅ デ ド バ ビ ブ ベ ボ パ ピ プ ペ ポ ァ ィ ゥ ェ ォ ャ ュ ョ ッ "
            + "ー ゛ ゜ 、 。 ・ 「 」 "
            + "！ ” ＃ ＄ ％ ＆ ’ （ ） ＊ ＋ ， － ． ／ ： ； ＜ ＝ ＞ ？ ＠ ［ ＼ ］ ＾ ＿ ｀ ｛ ｜ ｝ ～ "
            + "｟ ｠ ￠ ￡ ￢ ￣ ￤ ￥ ￦ │ ← ↑ → ↓ ■ ○";
    private static final String HAN_CHARS = "0 1 2 3 4 5 6 7 8 9 "
            + "A B C D E F G H I J K L M N O P Q R S T U V W X Y Z "
            + "a b c d e f g h i j k l m n o p q r s t u v w x y z "
            + "ｱ ｲ ｳ ｴ ｵ ｶ ｷ ｸ ｹ ｺ ｻ ｼ ｽ ｾ ｿ ﾀ ﾁ ﾂ ﾃ ﾄ ﾅ ﾆ ﾇ ﾈ ﾉ ﾊ ﾋ ﾌ ﾍ ﾎ ﾏ ﾐ ﾑ ﾒ ﾓ ﾔ ﾕ ﾖ ﾗ ﾘ ﾙ ﾚ ﾛ ﾜ ｦ ﾝ "
            + "ｱ ｲ ｳ ｴ ｵ ｶ ｷ ｸ ｹ ｺ ｻ ｼ ｽ ｾ ｿ ﾀ ﾁ ﾂ ﾃ ﾄ ﾅ ﾆ ﾇ ﾈ ﾉ ﾊ ﾋ ﾌ ﾍ ﾎ ﾏ ﾐ ﾑ ﾒ ﾓ ﾔ ﾕ ﾖ ﾗ ﾘ ﾙ ﾚ ﾛ ﾜ ｦ ﾝ "
            + "ｳﾞ ｶﾞ ｷﾞ ｸﾞ ｹﾞ ｺﾞ ｻﾞ ｼﾞ ｽﾞ ｾﾞ ｿﾞ ﾀﾞ ﾁﾞ ﾂﾞ ﾃﾞ ﾄﾞ ﾊﾞ ﾋﾞ ﾌﾞ ﾍﾞ ﾎﾞ ﾊﾟ ﾋﾟ ﾌﾟ ﾍﾟ ﾎﾟ ｧ ｨ ｩ ｪ ｫ ｬ ｭ ｮ ｯ "
            + "ｳﾞ ｶﾞ ｷﾞ ｸﾞ ｹﾞ ｺﾞ ｻﾞ ｼﾞ ｽﾞ ｾﾞ ｿﾞ ﾀﾞ ﾁﾞ ﾂﾞ ﾃﾞ ﾄﾞ ﾊﾞ ﾋﾞ ﾌﾞ ﾍﾞ ﾎﾞ ﾊﾟ ﾋﾟ ﾌﾟ ﾍﾟ ﾎﾟ ｧ ｨ ｩ ｪ ｫ ｬ ｭ ｮ ｯ "
            + "ｰ ﾞ ﾟ ､ ｡ ･ ｢ ｣ "
            + "! \" # $ % & ' ( ) * + , - . / : ; < = > ? @ [ \\ ] ^ _ ` { | } ~ "
            + "⦅ ⦆ ¢ £ ¬ ¯ ¦ ¥ ₩ ￨ ￩ ￪ ￫ ￬ ￭ ￮";
    static {
        String[] zenSplit = ZEN_CHARS.split(" ");
        String[] hanSplit = HAN_CHARS.split(" ");
        if (zenSplit.length != hanSplit.length) {
            throw new RuntimeException("char count not match. zen=" + zenSplit.length + ", han=" + hanSplit.length);
        }
        for (int i = 0; i < zenSplit.length; i++) {
            zen2HanMap.put(zenSplit[i].charAt(0), hanSplit[i]);
        }
    }

    public static String conv(String s) {
        StringBuilder sb = new StringBuilder();
        s.chars().mapToObj(c -> (char) c).forEach(c -> {
            if (c == '　') {
                sb.append(' ');
            } else {
                String han = zen2HanMap.get(c);
                if (han == null) {
                    sb.append(c);
                } else {
                    sb.append(han);
                }
            }
        });
        return sb.toString();
    }
}
```
DockerでGolangの環境を構築する

Docker初心者ですが頑張りたいと思います。
よろしくお願いします。
#目的
Dockerの勉強がてらGoの勉強をする
Hello Worldを出力するまでやろうと思います。

#動作環境
Windows10 Pro
Docker for windows

#Goの環境を構築する
ファイル構成は以下のようになってます

```
-go_lang
　│-docker-compose.yml
　|
　|-app_go
    │-Dockerfile
    |-app
```
今後DBコンテナ等を増やすかもしれないのでdocker-composeを用いています

```yml:docker-compose.yml
version: '3'
services:
  app:
    #app_goの中にあるDockerfileの読み込み
    build: ./app_go
    container_name: "app_go"
    tty: true
    #ホストのディレクトリをコンテナにマウント
    volumes:
      - ./app_go/app:/go/src/app
```
ローカル側でファイルをいじりたいのでappディレクトリをマウントしています
```tty: true```がないとコンテナが終了してしまいます。

```dockerfile:Dockerfile
FROM golang:1.8

WORKDIR /go/src/app
```
Dockerfileについては特に言うことはないでしょう

コンテナ作成に必要なファイルは揃ったのでbuildしていきましょう
ターミナルを開きdocker-compose.ymlがあるディレクトリまで移動して以下のコマンドを実行

```
PS C:\go_lang> docker-compose build
Building app
Step 1/2 : FROM golang:1.8
 ---> 0d283eb41a92
Step 2/2 : WORKDIR /go/src/app
 ---> Running in b2e6eb0d0fc5
Removing intermediate container b2e6eb0d0fc5
 ---> e142e671f39f
Successfully built e142e671f39f
Successfully tagged go_lang_app:latest
```
golangイメージがローカルにない場合はdockerhubからgolangイメージを取ってくるので2～3分程かかります

ビルドが終わったら実際にイメージが作られているか確認してみましょう。

```
PS C:\go_lang> docker images
REPOSITORY                 TAG                 IMAGE ID            CREATED             SIZE
go_lang_app                latest              febbabb91a83        About an hour ago   713MB
golang                     1.8                 0d283eb41a92        11 months ago       713MB
```
go_lang_appとgolangがビルドして作られたイメージです
確認ができたらコンテナを起動していきましょう

```
PS C:\go_lang> docker-compose up -d
Creating network "go_lang_default" with the default driver
Creating app_go ... done
PS C:\go_lang>
```
環境構築はできたのでGoのコードを書いていきます。

#Hello World
go_lang/app/go_appの中にsample.goを作成します。

```go:sample.go
package main

import "fmt"

func main() {
	fmt.Println("Hello, World")
}
```
作成したらコンテナの中に入りプログラムを実行します
コンテナに入るにはexecコマンドを使います

```
PS C:\go_lang> docker exec -it app_go bash
root@803babe23e01:/go/src/app# ls
sample.go
root@803babe23e01:/go/src/app#
```
go/src/appには先ほどローカルで作成されたsample.goがあります。
go runでプログラムを実行します

```
root@803babe23e01:/go/src/app# go run sample.go
Hello, world
```
できた！！ヽ(・∀・)ﾉ


コンテナから抜けて終了します

```
root@803babe23e01:/go/src/app# exit
exit
PS C:\go_lang> docker-compose down
Stopping app_go ... done
Removing app_go ... done
Removing network go_lang_default
PS C:\go_lang>
```

以上です
今回はこれで終わります
【Unity】複数のUIの活性／非活性を一度に切り替える

# 複数のUIの活性／非活性を一度に切り替えたい

そんな時ってありますよね。今の私が、まさにそれです。
.NETだったらPanelコントロール等で実現できますが
Unityでも同じようなことができるんじゃないかと思いまして。

![その１.png](https://qiita-image-store.s3.amazonaws.com/0/354674/dea214cd-cd2d-94ec-4b58-fce959aba9b2.png)


とりあえず、何も考えずに
**親Canvasをそのまま非活性にしてみました。**

```cs:Canvas.cs
public Canvas UICanvas;
void Start(){
        this.UICanvas.enabled = false;
}
```

その結果は、こちら。

![その１.png](https://qiita-image-store.s3.amazonaws.com/0/354674/1d07122f-b596-081f-28e0-4d386a772558.png)

あらら、消えてしまいました・・・。
Canvasのenabledについて、リファレンスを見てみると

>有効であれば更新され、無効であれば更新されません。

となっていました。
どうやら表示／非表示の切り替えということみたいです。

それはそうと、CanvasはUnityEngine.UI名前空間ではないのですね。
Hierarchyで作成する際、UIメニューから選べるので
てっきりUnityEngine.UI名前空間なんだと思っていたら
Behaviourを継承していたんですね。勉強になるなぁ。

# CanvasGroupを使う

ではどうするかというと、
CanvasGroupというコンポーネントを使うと良いみたいです。
さっそくCanvasに追加してみます。

![その１.png](https://qiita-image-store.s3.amazonaws.com/0/354674/54a992e0-713f-bd4a-8302-9ef6a0eef5c9.png)

| alpha | グループのアルファを設定します |
|:--:|:--:|
| blocksRaycasts | このグループのレイキャストをブロックする（衝突が許可されている）|
| ignoreParentGroups | グループが親グループを無視するべきか？ |
| interactable | グループに互換性がある（許可グループの下の要素である）。|
※リファレンスより引用

InteractableをOffにしてみます。

![その１.png](https://qiita-image-store.s3.amazonaws.com/0/354674/f8e21958-c99e-f38f-607e-8ba57235c795.png)


おー！
Canvas内のUIが、すべて非活性となりました！
これは便利:laughing:
600円で出来た！macOS環境で動画キャプチャの環境構築

# なぜMacで動画キャプチャができる環境が必要になったのか
自社で使用しているAdobeのIllustratorで動作するスクリプトの事例を動画配信しよう。
私はある日突然思いついた。（現段階で収益化の出口は見えていないが…汗）
そこでまずは手元にあるMacBooc Proさんに環境を作ろうとしたのだが、結構ハマったので備忘録として残しておく。

## 動作環境はこんな感じ
[PC] MacBook Pro 2017(15-inch)
[OS] macOS Mojave ver.10.14.2
[CPU] Intel Core i7 2.9GHz 
[メモリ] 16GB

## やりたいこと
1) 音声入力は**外部マイク**+**動画などPCからの操作音**
2) クリックしたと分かるように（音声として）クリック音がカチカチ鳴るようにしたい
3) マウスポインタの現在位置が分かりやすいようにしたい
<font color="Red">4) なるべく低い予算で環境を構築したい（これ重要）</font>

## 結果やったこと
いろいろハマってアプリや環境についてかなり比較検討したが、上記要件を満たす満足な環境ができた。
最終的に落ち着いた環境は以下。

### 1) 音声入力は**外部マイク**+**動画などPCからの操作音**
<font color="Blue">**SoundFlower**</font> + <font color="Blue">**LadioCast**</font> で出来た。

**・SoundFlowerとは**
SoundFlowerは仮想のオーディオデバイスだ。
（動画や音楽、操作音など）PC内部の音を仮想的に出力したり、入力したりすることができる。

**・LadioCastとは**
LadioCastはPC内部の音の行き先を設定（ルーティング）できるアプリだ。

**[参考サイト]**
今回は外部マイクからの入力+PC内部の音を録画の音声としたかったので、以下サイトを参考に設定した。
***https://sleepfreaks-dtm.com/dtm-materials/mac-sound/***

**[ダウンロード先]**
[SoundFlower(githubからダウンロード)](https://github.com/mattingalls/Soundflower/releases)
LadioCast（App Storeから）

### 2) クリックしたと分かるように（音声として）クリック音がカチカチ鳴るようにしたい
**<font color="Blue">Mousepose</font>**というアプリで簡単に実現できた。
Mouseposeは多機能なマウス操作を装飾するアプリだが、今回はクリック音を鳴らすためだけにインストールする。

**[preferences]→[Mouse Clicks]→[Click Sound]にチェック**
<img width="350" alt="screen_shot 2019-02-06 13.59.12.png" src="https://qiita-image-store.s3.amazonaws.com/0/234671/f91aa31d-5dae-10fa-8cd0-367a90c6f4fd.png">

**[ダウンロード先]**
[Mousepose](https://boinx.com/survey/mouseposebeta/)

### 3) マウスポインタの現在位置が分かりやすいようにしたい
Windows用だとこの手のアプリはたくさん見つかるのだが、Mac用が思う様に見つからずかなり探した。
最終的に選んだのは**<font color="Blue">PintPoint</font>**というアプリ。（有償：600円　※2019/02/05時点）
下記画像のようにマウスポインタがある箇所に装飾することが出来た。
<img width="350" alt="screen_shot 2019-02-06 14.05.01.png" src="https://qiita-image-store.s3.amazonaws.com/0/234671/1b27528e-bb1e-2ae8-e486-04a99f141c51.png">

**[ダウンロード先]**
PinPoint（App storeから)


### 4) なるべく低い予算で環境を構築したい
今回はPinPointの費用600円で環境を構築することができた！
環境も満足がいくものなので大満足である。

## これから
ようやく動画キャプチャの環境も整ったので、ガンガンIllustratorのスクリプトの事例動画をアップしていくぞー！
Android端末でlocalhost:3000なRailsアプリにアクセスする方法

# やりたいこと
`rails s` で起動した開発環境に、Androidスマホ実機でアクセスしたい
**※PCもAndroidもChromeのみ実施可能**

## PC側の準備
+ Chromeブラウザで `chrome://inspect/devices` にアクセス
+ `Port forwarding...` をクリック<br>

|<img width="440" alt="Chrome Inspect" src="https://qiita-image-store.s3.amazonaws.com/0/25900/943068b6-4732-6717-5c63-b157b206dfe1.png">|
|:-:|

+ `Port forward settings` で、3000番ポートを `localhost:3000` へポートフォワードするよう追記
+ `Enable port forwarding` にチェック

|<img width="329" alt="スクリーンショット 2019-02-06 14.16.26.png" src="https://qiita-image-store.s3.amazonaws.com/0/25900/549e4d54-3163-9e8e-dad5-cd5397a168ee.png">|
|:-:|

## Android端末側の準備
+ `設定 > 開発者向けオプション > ON` に設定
+ PCに接続し、 `USBデバッグを許可しますか?` というメニューが出てきたら `OK` を選択

## 実機確認
+ PC側で `rails s` でアプリケーションを起動
+ 端末のChromeブラウザを開く
+ `localhost:3000` にアクセス
+ なんと実機で確認できる！

## よいこと
PC用Chromeデバッグメニューが、実機の環境下(スワイプとか、PCブラウザでできないことも含めて)で確認できる！すごいね！
osmdroid を使ってAndroid の OpenStreetMap 地図にカスタムタイルを重ねる

[osmdroid を使って OpenStreetMap を Android に表示する](https://qiita.com/ohwada/items/c3741fb14a5142035314)
の続きです

OpenStreetMap は、共通の地図情報から任意のタイルを生成することができる。
その種のタイルをカスタムタイルと呼ぶ。

[カスタムタイルの一覧](https://qiita.com/nyampire/items/fbe359a2c9ccf0116787)

### MainActivity.java

カスタムタイルは OSM日本 を使用する。

```
	    mMapView.setTilesScaledToDpi(true);
		mMapView.getZoomController().setVisibility(CustomZoomButtonsController.Visibility.SHOW_AND_FADEOUT);


		// Add tiles layer with Custom Tile Source
		final MapTileProviderBasic tileProvider = new MapTileProviderBasic(getApplicationContext());

       // OSM日本
		final ITileSource tileSource = new XYTileSource("OSM Japan",  3, 18, 256, ".png",
				new String[] { "http://tile.openstreetmap.jp/" });

		tileProvider.setTileSource(tileSource);

		final TilesOverlay tilesOverlay = new TilesOverlay(tileProvider, this.getBaseContext());
		tilesOverlay.setLoadingBackgroundColor(Color.TRANSPARENT);
		mMapView.getOverlays().add(tilesOverlay);

```

### スクリーンショット

右は、タイルを重ねる前の背景地図
左は、タイルを重ねた後の地図
![4_base.png](https://qiita-image-store.s3.amazonaws.com/0/64075/5a4d8372-8b44-e3b3-27ba-5098c232a390.png)　![4_jp.png](https://qiita-image-store.s3.amazonaws.com/0/64075/bd37b7e6-0c30-f5ab-2a66-def8239f7c06.png)


github にソースを公開した

https://github.com/ohwada/Android_Samples/tree/master/Osmdroid4
初心者がRails+bootstrap+ajaxでメモアプリをつくってみた

# つくったもの
・Devenon
https://devenon.herokuapp.com/

![WS000000.JPG](https://qiita-image-store.s3.amazonaws.com/0/159483/3ba8d358-6743-eee9-ec4f-0cd29053878d.jpeg)


## これはなに？

**タグ付きメモアプリ**です。会員登録をしないと利用できません。ログイン機能は、セキュリティ上好ましくない状態かと思います。（パスワードはハッシュ化されています）それで、捨てアドなどでご登録ください。

つくったメモは、会員トップページで検索して探すことで参照できます。また、つくったメモにお気に入り登録する機能があります。お気に入り登録をすると、会員トップページにて一番上に表示されるようになります。

# できあがるまでの主な過程

- ProgateのRuby on Railsなどを受講
- Wikipediaみたいなアプリを製作開始
- かっこ悪いがまぁまぁの出来で完成
- Devenonの製作を開始
- railsのdbをmysqlに変更
- bootstrapというオサレサイトを作るツールを知る
- bootstrapで雛形をつくる
- ログイン機能をbcryptを利用しながら実装
- ajax通信で検索機能を実装
- ajax通信でお気に入り登録機能を実装
- turbolinkに悩まされる
- herokuにデプロイ
- 完成

# つくった人について
Ruby on Railsの学習をはじめて2週間ほど。少しずつプログラム関係の仕事ができたらいいなと思案中。

# 参考になったサイトなど

### mysql

RailsのDBを(初めから| |後から)MySQLに変更する
https://qiita.com/reeenapi/items/9fc38c4f2f8186c78288

### bcrypt

BCryptのすすめ
https://qiita.com/ponkotuy/items/1a703b866ddf5c9fe80c

### CoffeeScript

JavaScriptを卒業してCoffeeScriptで飛躍しよう - 基本などまとめ
https://qiita.com/Yama-to/items/a947cfa2565b03ddc9de

### ajax

Rails 非同期でいいね機能(Ajax)
https://qiita.com/shotadesu/items/d2e3eee6f17dc3de59c4

### turbolink

Turbolinksをオフしないためにやった事
https://qiita.com/saboyutaka/items/bcc0966313c6f7399a6e

### heroku

【初心者向け】railsアプリをherokuを使って確実にデプロイする方法【決定版】
https://qiita.com/kazukimatsumoto/items/a0daa7281a3948701c39



# 今後したいことなど

- ログイン再発行機能の実装
- セキュリティの向上
- 公式のRailsチュートリアルをする
- カレンダーアプリを製作する


もしDevenonを使ってみて感想などあればコメントしていただけると嬉しいです！！
Windows10環境でPythonとOpenCVで画像加工する

# Windows10環境でPythonとOpenCVで画像加工する

前提：
python-3.7.2 インストール済み。
Anaconda3-2018.12-Windows-x86 インストール済み。

#　OpneCVをインストールする。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/f4d009c4-3bee-e254-317d-94c0258ec664.png)


![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/20d51bc6-41e5-24c6-9570-dd1b60363f6e.png)


![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/d6c9e565-0b2d-f043-0279-0b8f47c4e238.png)

Anaconda Prompt で、コマンドラインでインストールします。

『pip install opencv-python』

数秒で終わると思います。サクセスすれば完了。

余談、必要なモジュールがあれば入れてもよいでしょう。
pip install numpy
pip install matplotlib
pip install scikit-learn
pip install ipython
pip install jupyter

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/b9da635c-dcbe-25ac-905c-dfe474a72118.png)

はい、

OpenCVが入ったかコマンドラインで確認します。
『import cv2』

何事起きないので問題ないです。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/aeec4b6b-0289-9fc3-7985-90dbac57fa5f.png)

私の様に心配性な方はhelpコマンドしてみましょう。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/7561eb9b-c338-26e5-504c-f36e587ecbce.png)

はい、大丈夫そうです。

## OpenCV に画像を食わせて色々やってみます。

### 画像を用意しましょう。

セオリー通り、『レナ』さんの画像で行きましょう。
http://www.lenna.org/

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/622d63dd-94a6-7855-da69-7c1d3f263183.png)

余談ですが、こちらの『レナ』さん画像の肩から下はヌー〇なんですよ。

はい、とりあえず画像をダウンロードしましょう。
こちらのサイトから画像をダウンロードすると『TIF ファイル (.tif)』形式
だと思いますが、問題ありません。

pythonを使ってコマンドラインで保存する場合は、下記です。

````

import urllib.request as rq
u = "http://www.lenna.org/len_std.jpg"
local = "C:\TMP\Lena\len_std.jpg"
rq.urlretrieve(u, local)


````


![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/baefc6c6-3da4-44c9-e401-8fb6cd271929.png)

次に、コマンドプロンプトを開いてpythonを実行していきます。
Anacondaからpromptを開き、『　import cv　』します。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/2ebac3a3-2009-e3f8-3b7c-e5f858b05ccf.png)

ここから、コマンドラインでOpenCVの機能を使って画像を加工して保存してみます。


````

# カラー画像をグレースケール画像に変換して保存するサンプル
import cv2

im = cv2.imread("C:\TMP\Lena\len_std.jpg")

# グレイスケールに変換
gry = cv2.cvtColor(im, cv2.COLOR_BGR2GRAY)

# ファイルに保存
cv2.imwrite("C:\TMP\Lena\len_std_gray.jpg", gry)

````

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/d563788f-f4d8-e9a8-765a-1f29a657dec2.png)

指定したフォルダーに画像が作成されました。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/3785a7fa-00be-cd44-a0b0-d31edec06566.png)


Python＋OpenCVを使えばとても簡単に画像の変換ができます。
OpenCVには様々な画像処理機能があります。AIの技術分野でも
画像をAIに食わす前に、適切な前処理をする場合が多いので、
このようにシンプルに実装できるというのはメリットだと
思います。


````

# 例えば画像のエッジ検出ならCanny関数で簡単に実装できます。

import cv2

im = cv2.imread("C:\TMP\Lena\len_std.jpg")

# Cannyフィルタを適用
im_canny = cv2.Canny(im, 30, 200)

# ネガポジ反転（エッジ黒、背景白にしたいので。）
im_canny = 256 - im_canny

# ファイルに保存
cv2.imwrite("C:\TMP\Lena\len_std_canny.jpg", im_canny)

````

![image.png](https://qiita-image-store.s3.amazonaws.com/0/303278/dc47ad40-29d0-7179-93c9-871832dec4d8.png)


OpenCVの関数などは本家で。
https://opencv.org/

ホント、ITエンジニアには良い時代になりました。

以上です。
osmdroid を使ってAndroid の OpenStreetMap 地図にタイルを重ねる

[osmdroid を使って OpenStreetMap を Android に表示する](https://qiita.com/ohwada/items/c3741fb14a5142035314)
の続きです

## タイル

地図は１つの画像ではなく、タイルと称される複数の小さな画像の集合体です。

[OSMのタイルの説明](https://wiki.openstreetmap.org/wiki/JA:%E3%82%BF%E3%82%A4%E3%83%AB)

## osmdroid で定義されている タイルの一覧

日本を中心にすると、表示できないものもある。

| タイル名 | タイルサーバー |
| :----------- | :----------- |
| MAPNIK  | https://a.tile.openstreetmap.org/| 
| PUBLIC_TRANSPORT| http://openptmap.org/tiles/| 
| FIETS_OVERLAY_NL| http://overlay.openstreetmap.nl/openfietskaart-overlay/| 
| BASE_OVERLAY_NL| http://overlay.openstreetmap.nl/basemap/| 
| ROADS_OVERLAY_NL| http://overlay.openstreetmap.nl/roads/
| HIKEBIKEMAP| http://a.tiles.wmflabs.org/hikebike/| 
| OPEN_SEAMAP | http://tiles.openseamap.org/seamark/| 
| USGS_TOPO | https://basemap.nationalmap.gov/arcgis/rest/services/USGSTopo/MapServer/tile/| 
| USGS_SAT | https://basemap.nationalmap.gov/arcgis/rest/services/USGSImageryTopo/MapServer/tile/| 

### MainActivity.java

タイルは PUBLIC_TRANSPORT を指定する

```
		// Add tiles layer
		mProvider = new MapTileProviderBasic(getApplicationContext());

 // Tiles
mProvider.setTileSource(TileSourceFactory.PUBLIC_TRANSPORT);

		this.mTilesOverlay = new TilesOverlay(mProvider, this.getBaseContext());
		this.mMapView.getOverlays().add(this.mTilesOverlay);
```

### スクリーンショット

右は、タイルを重ねる前の背景地図
左は、タイルを重ねた後の地図
![base.png](https://qiita-image-store.s3.amazonaws.com/0/64075/61cdb142-11c8-ae30-6531-35f5b5b2558f.png)![transport.png](https://qiita-image-store.s3.amazonaws.com/0/64075/8ec81b07-8320-7b43-9ea1-c6ed5cb1a66b.png)






github にソースを公開した

https://github.com/ohwada/Android_Samples/tree/master/Osmdroid3
pacmanのラッパー兼aurパッケージマネージャーのauraをインストールする

# auraとは
pacmanのラッパーであると同時に、AUR用のパッケージマネージャー
[aura/README.md at master · aurapm/aura](https://github.com/aurapm/aura/blob/master/aura/README.md)
[aura: A secure package manager for Arch Linux and the AUR, written in Haskell.](http://hackage.haskell.org/package/aura)

その他のパッケージマネージャーは下記を参照
[AUR ヘルパー - ArchWiki](https://wiki.archlinux.jp/index.php/AUR_%E3%83%98%E3%83%AB%E3%83%91%E3%83%BC)

# インストール方法
READMEに従えばインストールできます。

## githubから

```terminal
$ git clone https://aur.archlinux.org/aura-bin.git
$ cd aura-bin
$ makepkg
$ sudo pacman -U <pkg.tarファイル>
```
例えば
`sudo pacman -U aura-bin-1.4.0-1-x86_64.pkg.tar`
これで利用できるようになりますが、バージョン1系では文字化けのバクが確認されていて、私も再現しました。
[pacman's output is garbled · Issue #519 · aurapm/aura](https://github.com/aurapm/aura/issues/519)
利用自体に問題があるかは未確認です。

2系では直っていますが、現在は次に説明するhackageからしかインストールできません。

## hackageから
(ちなみに私は、haskellは一応インストールしていますが、まったくわかりません。)
[Hackage](http://hackage.haskell.org/)というhaskellのライブラリアーカイブから取得しインストールする方法です。
こちらもREADMEに従えば問題なくインストールできましたが、必要なものがあります。

### 準備
stackが必要です、
stackは、コンパイラのインストールをしてくれたりパッケージマネージャーの機能をもつhaskell開発の便利ツールみたいです。
[Home - The Haskell Tool Stack](https://docs.haskellstack.org/en/stable/README/)
事前に`stack`を使用できる状態にしてください。

### auraのインストール

```terminal
$ git clone https://github.com/aurapm/aura.git
$ cd aura
$ stack install -- aura
```
これはクローンしてきた`package.yaml`をもとにパッケージをビルドしてくれているのでしょうか。くわしくはわかりません。

# 使い方
## pacmanで使用できるリポジトリのアップデート
`$ sudo aura -Syu`
pacmanコマンドは同じなんだとおもいます。

## AURのアップデート
`$ sudo aura -Au`
AURを触る場合は`-A`を使い、複数のオプションがあります。

くわしくは[README](https://github.com/aurapm/aura/blob/master/aura/README.md#sample-usage)を参照
LaravelにRansack的なのがなかったので、Model側にそれっぽいのを定義してみた。

# Laravelでもransack的なことをできるように
Controllerでやることは $request を検索メソッドに渡すだけにするため
Model側にクラスメソッドを定義

## Controller
```php:HogeController
public function index(Request $request) {
    $clients = Hoge::search($request);
}
```

# Modelの検索ロジック

`array_keys($request->all()`でフォームから渡された項目全てのkeyを取得し、それをeachで回す。
ページネーションは好みですが、今回はつけておいて欲しいので入れておきました、デフォルト50です。


```php:HogeModel
public static function search($request, $number = 50 ){
    $query = Self::query();
    foreach ($request->all() as $key => $value) {
        $query->where($key, 'like', '%'.$value.'%');
    }
    return $query->paginate($number);
}
```

# 共通関数化する

こちらにあるようにこれを共通関数化してしまっても良いと思ったのですが、今回はやらず。
しておくといいことがあるかもしれないです

https://saba.omnioo.com/note/2446/laravel5-%E5%85%B1%E9%80%9A%E3%82%AF%E3%83%A9%E3%82%B9%EF%BC%88%E6%B1%8E%E7%94%A8%E9%96%A2%E6%95%B0%EF%BC%89%E3%82%92%E3%81%A4%E3%81%8F%E3%82%8B/
Jupyter-notebook初心者がよく使うpandas関数まとめてみた

jupyter notebookを最近使い始めたので、よく使う関数まとめてみた
ちなみにpython自体、趣味で少し使う程度

#### pandasのインポート : import
```python
import pandas as pd
```


#### csvインポート : read_csv()
```python
df = pd.read_csv("hoge.csv", encoding="utf-8")
```

#### csvエクスポート : to_csv()
```python
df.to_csv('result.csv')
```

#### 統計値の一括表示 : describe()
```python
df.describe()
```

#### 行と列の入れ替え(転置) : T
```python
df.T
```

#### 特定の要素の取得 : loc(),iloc()
※ソート順ではなくindexに準拠するので注意

```python
## 行番号と列番号の指定
# 特定の要素を取得(1行目の2列目)
df.iloc[1, 2]

# スライスも可能(1~10行目の1~10列目)
df.iloc[1:10,1:10]

## ラベルの指定
# 'index_1'の'column_a'の値を取得
df.loc['index_1', 'column_a']

# スライスも可能
df.loc['index_1':'index_3', 'column_a':'column_d']
```

#### 列数,行数などのサイズ取得 : len(),shape(),size()
```python
# 行数
len(df)

# 列数
len(df.columns)

# 両方(行と列)
df.shape

# 要素数
df.size
```

#### 列の削除 : drop()
```python
df.drop(['column_a','column_b'], axis='columns')
```

#### 列(column),行(index)の名前変更 : rename()
```python
df.rename(columns={'column_a': 'a'}, index={'index_1': 'index_0001'}, inplace=True)
```

#### 欠損値のチェック(便利) : to_datetime()
```python
df.isnull().any(axis=0)

# 欠損がある場合Trueに
# column_a    False
# column_b    True
# column_c    True
# column_d    False
```

#### 欠損値の置換 : fillna()
```python
# 全て0で埋める場合
df.fillna(0)

# 列指定で埋める場合
df.fillna({'column_b': 0})
```

#### 四捨五入: fillna()
```python
# 整数
df.round()

# 少数第３位で四捨五入
df.round(2)
```

#### 時間型の変換 : to_datetime()
変換しておくと何かと便利　　　　

```python
pd.to_datetime(df['datetime'])
```


#### DataFrameのソート : sort_values()
```python
df.sort_values(['date', 'id'], ascending=[False, True], inplace=True)
```


#### DataFrameのindex振り直し : reset_index()
```python
# dropを指定しない場合、新たな列にindexが追加される
df.sort_values(['date', 'id'], ascending=[False, True]).reset_index(inplace=True, drop=True)
```

#### 合計値・平均・標準計算 : sum(), mean(), std()
```python
# 列ごと
df.sum()

# 行ごと
df.sum(axis=1)

# 合計:sum()
# 平均:mean()
# 標準偏差:std()
```

#### 条件抽出 : where()
```python
# 抽出
df.where(df['date'] >= '2018-07-18')

# 抽出すると条件外の行は全てNaNになるので、削除する場合
df.where(df['date'] >= '2018-07-18').dropna(how='all')
```

#### DataFrameの結合 : merge()
```python
pd.merge(df_a, df_b, on='id', how='inner')

# 内部結合（inner_join）: how='inner'
# 左結合（left_join）: how='left'
# 右結合（right_join）: how='right'
# 外部結合（outer_join）: how='outer'
```

#### ランキング : rank()
```python
df.rank(method='dense', ascending=False)['column_a']
```

ざっとまとめてみました。
その他、ループやgroup,カウントなど便利なものがまだまだあるので後日。
Windows 10 Pro x64 + Excel2016 x86 VBA + ADODB.Command を使って SQL Server 2016 Express でストアドを試してみる

#目的
簡単なストアドを書いて、ADODB.Command から使ってみる
※Windows版、Linux版ともに同じコードの動作確認(ODBCの指定以外は同じ)
※クラスへの実装の追加はどうするか、検討中
　adoCmd.ActiveConnection = adoCon 実行後
　adoCmd(1) = "00000001" が正常に動くため
対象テーブルは[こちら]()で作成したものを対象とする
##ストアドの作成
以下をSSMSから実行する

```t-sql
USE DEMO; 
GO 
CREATE PROCEDURE GETZIPCODE @SEQ nchar(8) AS  
SELECT PREFCODE, POSTAL, CITIESKANJI, POADDRKANJI 
FROM ZIPCODE 
WHERE SEQ = @SEQ;
GO 
```
##ストアドのテスト
```t-sql
EXECUTE GETZIPCODE N'00000001'
```
##サンプルコード
```vb

'=================================================================
'
'   DBCtrlクラスを使用した
'   Excel2016 VBA -> SQLServer からストアドを使った読込サンプル
'
'=================================================================
Private Sub ReadSQLSVDBCtrl()
On Error GoTo ERR_PROC
'
    Dim adoCon      As ADODB.Connection
    Dim adoRst      As New ADODB.Recordset
    Dim adoCmd      As New ADODB.Command
    Dim host        As String
    Dim user        As String
    Dim pass        As String
    Dim conn        As String
'
    host = "SQLSVODBC32"
'    host = "SQLSV2UBUNTU" ' Linux版
'
    user = "demo"
    pass = "demo"
'
    conn = "DSN=" & host & ";UID=" & user & ";PWD=" & pass
'
    adoCmd.CommandText = "GETZIPCODE"
    adoCmd.CommandType = adCmdStoredProc
'
    Set adoCon = New ADODB.Connection
'
    adoCon.ConnectionString = conn
    adoCon.CursorLocation = adUseClient
    Call adoCon.Open
'
    adoCmd.ActiveConnection = adoCon
'
    adoCmd.Parameters.Refresh
    '
    '   adoCmd.ActiveConnection = adoCon
    '   を実行しないとエラーになる
    '   adoCmd のクラスの実装は要検討
    '
    adoCmd(1) = "00000001"
'
    Set adoRst = adoCmd.Execute
'
    While Not adoRst.EOF
        Debug.Print Trim(adoRst.Fields("PREFCODE")) & vbTab & _
                    Trim(adoRst.Fields("POSTAL")) & vbTab & _
                    Trim(adoRst.Fields("CITIESKANJI")) & vbTab & _
                    Trim(adoRst.Fields("POADDRKANJI"))
'
        adoRst.MoveNext
    Wend
'
    adoCon.Close
    Set adoCon = Nothing
    Set adoCmd = Nothing
'
    Exit Sub

ERR_PROC:
    adoCon.Close
    Set adoCon = Nothing
'
End Sub
```
##参考にしたのは以下のサイト
[Create a Stored Procedure](https://docs.microsoft.com/ja-jp/sql/relational-databases/stored-procedures/create-a-stored-procedure?view=sql-server-2017)
[コマンドでストアド プロシージャを呼び出す](https://docs.microsoft.com/ja-jp/sql/ado/guide/data/calling-a-stored-procedure-with-a-command?view=sql-server-2017)
Poetryのここが判らない

以前[Pythonのパッケージ周りのベストプラクティスを理解する（2019年現在）]
(https://www.m3tech.blog/entry/python-packaging)を書きました。

この記事では「基本的には pipenvを使えばOK」と書きましたが、意図的に無視していた部分があります。

**Poetry**です。

Poetryは調べてみたのですが、各種日本語の記事（は一部の英語記事）はざっと読んだ限りでは、**Poetryはどうにも了解できないことが多かった**からです。そして、現時点ではPoetryよりPipenvの方が知名度が高そうだし、Pipenv自体は十分実用的なので「pipenvを使えばOK」としました。

とは言え、来年にはPoetryが天下をとっているかもしれません。そこで、そのうち書く記事の足がかりとして、あわよくば誰かが教えてくれたらいいなという虫のいい期待を込め、疑問点を列挙したいと思います。


<!-- more -->


# Pipfile の使用はPEPで決まったものではない？

それはどこまで問題でしょうか？

まあPEPで定義されていた方が良いに決まっています。特にパッケージングツールの開発者にとっては。

一方、一般のPythonユーザーにとってPEPで定義されているかは、あまり関係ありません。それより、ツールが使い物になるかどうかが問題です。

（もし）Pipenvが使いづらいというなら、PipfileがPEPであろうがなかろうが関係なく、Pipenvは使いづらいのです。

# `pyproject.toml`１個でOK ？

Pipenvの setup.py, setup.cfg, Pipfile, Pipfile.lock が、Poetryではpyproject.toml に置き換わるらしいです。

でも、私の理解では 「setup.py, setup.cfg」と「Pipfile, Pipfile.lock」は役割が違うファイルです。前者は公開パッケージとしての情報を定義するファイル（開発者以外の人が使うファイル）、後者は開発者が使うファイルです。異なる役割を１ファイルに書くのが適切なのでしょうか？

（※補足: のちに分かったことですが、Poetry では Pipfile.lock に相当する poetry.lock というファイルを作るらしいです。でも、当時の Poetry の紹介記事で poetry.lock に言及しているものは見当たりませんでした。）

# アプリケーションとライブラリの両方に対応する？

また、Poetryはアプリケーションとライブラリの両方に`pyproject.toml`で対応できるとしています。

しかし、[Pythonのパッケージ周りのベストプラクティスを理解する（2019年現在）]
(https://www.m3tech.blog/entry/python-packaging)でも書きましたが、アプリケーションとライブラリでは、依存パッケージの管理方法が異なります。

`pyproject.toml`１つで上手く行くのでしょうか？

# Pipenvはrequirements.txtを置き換えるに過ぎない？

私の理解では、requirements.txtを置き換えたこと自体が一大革命で、かなり本質的な変化です。

Rubyコミュニティでは、速い段階から単なるパッケージ名のリストでは上手くいかないことが理解され、Bundlerが作られていました。

# 依存関係の解決？

Poetryは依存関係の解決が上手く、Pipenvが失敗するようなケースでも、Poetryは解決できるとうたっています。

https://github.com/sdispater/poetry#dependency-resolution

でも、それは決定的な優劣なのでしょうか？

多分、依存関係解決の速度と、新しいファイルフォーマット（`pyproject.toml`）を採用することは無関係です。なら、Pipenvに、Poetryの依存関係解決のアルゴリズムを移植すれば、Pipenvも同じくらい早くなるはずです。

# インストール速度？

PoetryはPipenvよりインストール速度が速いらしいです。公式ページでは速度の記載はなく、あくまで第三者の感想ですが。

http://kk6.hateblo.jp/entry/2018/12/20/124151#Pipenvは確かに便利だけど

これも、依存関係解決と同じで、Pipenvにアルゴリズムを導入すれば良いのではないかと思います。

また、インストールの速さはそんなに重要でしょうか？実環境ではデプロイ時の１回しかインストールをしないし、開発中もせいぜい１時間に１回とか程度しかしないはずです。

# （Poetry関係ないけど） 初心者は Pipenv 不要？

> Python には依存関係を管理するツールがたくさんあります。 Python も歴史あるプログラミング言語なので仕方ないですが、情報が多すぎて特に初心者は混乱してしまいます。 結局の所、pip、virtualenv (venv) を使えば十分な場合が多いので、まずはこれらの使い方を学習しましょう。
>
> https://org-technology.com/posts/python-poetry.html

なんか、こういう「初心者はpipで十分」的な意見をよく見ますけど、私は反対です。100％絶対反対ではないが、90％ぐらい反対です。

だってRubyとかJavaなどの他言語では、割と早い段階でBundlerやGradleを紹介してるじゃないですか。ならPythonでも初めから Pipenv / Poetry を使えばいいんじゃないでしょうか？

まあ、なんの説明も教育もなしに Pipenv / Poetry を使わせると

> 新入社員「Pipfile.lockはGitにコミットしちゃいけないんですよね！？課長がそう言っていました！！僕はあなたより、課長の言うことに従います！！」
> 
> （※課長はJava歴は長いがPythonは未経験）

みたいな混乱は発生したりしますが、それはまた別のレイヤーの話だと思います。

# まとめ

ありません。
Windows Subsystem for Linuxの設定

# はじめに
脱デュアルブート！
bash on windows から名称が変わったらしいですね．
設定のメモ書き  
インストールは適当してubuntu18.04を入れた．  
初期設定の個人的メモ．

## 参考にしたサイト
> http://www.aise.ics.saitama-u.ac.jp/~gotoh/UbuntuOnWSL.html

# 基本的な初期設定
## リボジトリを日本にする
    sudo sed -i -e 's%http://.*.ubuntu.com%http://ftp.jaist.ac.jp/pub/Linux%g' /etc/apt/sources.list # リポジトリを日本のに変更
    sudo apt update
    sudo apt upgrade
## 個人的にインストールしたパッケージ
emacs

    sudo apt install emacs
    sudo apt install python3

ssh

    chmod 600 ~/.ssh/
    
## pathの変更
ファイルをいじりたいが，どこにあるかわかりにくい．
多くのサイトではHomeディレクトリ場所を変更しているが，これだと，Ubuntuで所有権を変更することができない．  
なので，以下の方針にした．

- Windowsから見るときはWindowsでショートカットを作成．
- UbuntuでWindowsファイルを使うときはシンボリックリンク

### windows上でubuntuのファイルはどこにあるか
まず，Ubuntuのファイルの居場所を探した．  
`C:\Users\%USERNAME%\AppData\Local\Packages\CanonicalGroupLimited.Ubuntu18.04onWindows_79rhkp1fndgsc\LocalState\rootfs`
深い．サイトによって書いてることが違うので，インストールした時期とかによって違うみたい？  
設定後にこのPathを変えるような暴挙をされないことを願う．
### ubuntu上でwindowsのファイルはどこにあるか．
    ls /mnt/c
はい，わかりやすい．Ubuntu最高．
### ubuntuでよく使うもののシンボリックリンク作成．
その都度，使いたいファイルのシンボリックリンクを貼ることにした．  
例えばDropbox．
 
    ln -s /mnt/c/Users/%USERNAME%/Dropbox ./
### 所有権を変更する必要があるファイル．
Windows側のディレクトリにある


## 文字サイズの変更
ツールバー？右クリックでプロパティ開いたら変更できた．
Nuxt 2.xでexpressを使ってhello worldするまでの道のり【備忘録】

expressについては今まで扱ったことがなく、Nuxtとどのように連動するのか、実際のところまだしっかり理解できていません。とりあえずここでは、nuxtプロジェクトでexpressを使うまでの初期設定までをリサーチしたので、備忘録として記録。

現在のnuxtのバージョンは以下のコマンドから分かるのかな？

```
./node_modules/nuxt/bin/nuxt.js -v

@nuxt/cli v2.4.2
```
バージョンはv2.4.2のようです。


## hello worldまでの道のり
* nuxtでプロジェクトを作成

```bash
npx create-nuxt-app <project-name>
```
* プロジェクトルートに`api`フォルダーを用意
* apiフォルダにindex.jsを追加して以下の内容を記入

```js:/api/index.js
const app = require('express')()
module.exports = { path: '/api', handler: app }

app.get('/hello', (req, res) => {
    console.log('hello nuxt in text')
    res.send('world')
})
```
注意点
>Notice, there is no `/api` prefix in the `app.get()`, above. This is because in `module.exports` we already specified the "global" prefix as `/api` for this whole express router instance.

つまり、`app.get`のパスはグローバルで登録している**`/api`**以降のパスを登録する。

* nuxt.config.jsに**`serverMiddleware`**を追加
  - `middleware`ではないことに注意！

```js:nuxt.config.js
serverMiddleware: ['~/api/index.js'],
```
nuxt.config.jsはdeaultではwatchされていないので、ホッとリロードされない。起動していたら、再起動する必要がある。

* localhost:3000/api/helloにアクセスして、画面に`world`と表示されれば成功
  - 当たり前かもしれないが、`console.log('hello nuxt in text')`の出力はwebのコンソールではなく、端末のコンソール上に表示される。

これで、vue側からjsonをなどを取得する際に`localhost:3000/api/hello`などでアクセスすると、express経由で処理を行えると思う。
【Egret無料ご相談室】ブラウザを閉じてもデータをセーブしたい


# 今日のご質問

> ![image.png](https://qiita-image-store.s3.amazonaws.com/0/302078/466a032e-b2b1-f082-a429-f9924dc74bd3.png)
> 変数のセーブってどうすればいいんだろ。
> ブラウザ閉じたたらデータ消えますよね？

# 回答

`egret.localStorage` のグローバル関数を使うといいですよ

APIリファレンス：
http://developer.egret.com/cn/apidoc/index/name/egret.localStorage.globalFunction#methodSummary

使いかた

```ts
/// 簡単なデータの読み込みと保存
const userName = egret.localStorage.getItem("userName");
userName = "New Name";
egret.localStorage.setItem("userName", userName);

/// ちょっと複雑なデータの読み込み・保存
const savedJson = egret.localStorage.getItem("savedData");
const data = JSON.parse(savedJson);
const newData = { ... data, newProp: "New Value" } ;
const toSaveJson = JSON.stringfy(newData);
egret.localStorage.setItem("savedData",toSaveJson );
```

## 解説

インターフェースの定義
https://github.com/egret-labs/egret-core/blob/de70bf2cc9e04b674a2897f907e97f887f897c7a/src/egret/localStorage/localStorage.ts

ブラウザ向けの実装
https://github.com/egret-labs/egret-core/blob/de70bf2cc9e04b674a2897f907e97f887f897c7a/src/egret/localStorage/web/WebLocalStorage.ts


EgretEngineのLocalStorageha,ブラウザが実装しているLocalStorageへのラッパーです。


```ts:/src/egret/localStorage/web/WebLocalStorage.ts
    function getItem(key:string):string {
        return window.localStorage.getItem(key);
    }

    function setItem(key:string, value:string):boolean {
        try{
            window.localStorage.setItem(key, value);
            return true;
        }
        catch(e){
            egret.$warn(1047, key, value);
            return false;
        }
    }

    function removeItem(key:string):void {
        window.localStorage.removeItem(key);
    }


    function clear():void {
        window.localStorage.clear();
    }
```

> LocalStorageとはWebStorageと呼ばれるものの一つで、javascriptを用いてクライアント側にデータを保存する仕組みです。ユーザのローカル(ブラウザ)にデータを保存することができるので、半永久的にデータを保持することができます。データの読み込み・更新も比較的簡単に行うことができます。
> 引用：http://wp.tech-style.info/archives/742

## 各ブラウザーの実装状況は？

おおむね実装されているようです

いつものごとく、iOSにはいろいろ制限があるようです

> 注記: iOS 5.1 より Safari Mobile は localStorage データを cache フォルダに保存しており、概して空き容量が少ない場合に OS の要求により、時々クリーンアップを受けます。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/302078/b106b677-d88a-b28e-2281-dbdd0cc458d8.png)


参考：
https://developer.mozilla.org/ja/docs/Web/API/Web_Storage_API
https://bbs.egret.com/forum.php?mod=viewthread&tid=11824&highlight=localstorage


iOS11未満のSafariはシークレットモードではLocalStorageにアクセスできなかったようです

http://kimizuka.hatenablog.com/entry/2018/09/25/175335
英語圏のフォーマットで日付文字列を出力する

# はじめに

以下のような英語圏のフォーマットで日付を出力する方法を考えてみました。

```
Thu,31 Jan 2019 17:10:46
```

# 環境

+ OS: Windows10
+ Java:1.8.0.191
+ ASTERIA Warp : 1812

# フロー

動作に確認したフローです。(マッピング画面込み)

![Now01.png](https://qiita-image-store.s3.amazonaws.com/0/180292/f678ae78-4261-6a7c-2e91-dfccf1b73066.png)

## Now関数

<img width="434" alt="Now04.png" src="https://qiita-image-store.s3.amazonaws.com/0/180292/55959d75-efcb-0362-7341-5e87b8310f52.png">

現在日時を取得するNow関数1つでできました。

Now関数のプロパティを以下のように設定します。

|プロパティ名  |値  |
|---|---|
|日付フォーマット  | `EEE,dd MMM yyyy HH:mm:ss`  |
|ロケール  |ENGLISH  |

![Now02.png](https://qiita-image-store.s3.amazonaws.com/0/180292/75dac50a-cd28-7fff-8463-8de3886f2611.png)


「日付フォーマット」はプルダウンから選択せず、直接入力で`EEE,dd MMM yyyy HH:mm:ss `と定義しました。
「ロケール」は`システムのロケール`をプルダウンから`ENGLISH`に変更しました。

# フローの実行
![Now03.png](https://qiita-image-store.s3.amazonaws.com/0/180292/6a89ed05-0424-951a-ad59-7a0518551ac7.png)


# おわりに
日付フォーマットの構文や記法を調べる必要がありますが、Now関数の「ロケール」プロパティを変更するだけで英語圏の日付フォーマットで日付文字列を出力できるのは便利ですね。

以上です。
SendGridのメール履歴で特定のタイトルに一致するメールを受信しているユーザーのメールアドレスを取得する

# 背景
システム的に一部ユーザーに誤送信をしてしまいました。そして誰に送ったかはシステム上では記録しておらず誰に送ったかを知る必要がありました。
メールサーバーにはSendGridを使用しており、APIには送ったメールをタイトルで検索などができなさそうでした。

（SendGridのActivityFeedに subject がありましたが検索できず・・）

そこでjsを使ってconsole.logに上げたのでそのコードをメモ。

# コード

```js
function logEmails() {
  var subject = 'このタイトルを検索したい'
  document.querySelectorAll('td.col-5').forEach(function(tag, index) {
    if(tag.querySelectorAll('span.subject')[0].textContent == subject) {
      console.log(tag.querySelectorAll('span.email')[0].textContent);
    }
  })
};

setInterval(function() {
  document.querySelectorAll('a.pagination-next')[0].click()
  logEmails();
}, 3000)
```

# あとがき
多分、発火タイミングはもっと厳密にやるべき。
renderingが遅れたら多分検知できなくなる
2019-02-06 Raspberry Pi 3 Model B > セットアップ (raspbian Stretch) > 固定IP設定 + SSH接続設定 + lxsessionでの開通確認

```
Raspberry Pi 3 Model B (以下RPi3)
Raspbian Stretch 
```

### 概要

- Raspbianのセットアップ
    - raspbian Stretch
- 固定IP設定
- SSH接続設定
- lxsessionでの開通確認

### NOOBSからのインストール

microSDにNOOBSのファイルを書込み、NOOBSからセットアップしました。

- 参考
    - [Raspberry Pi 3 Model B のセットアップ](https://qiita.com/yuyash/items/a779f750791c8cde90c6)
        - @yuyash さん
    - [Raspbianのインストールと初期設定](https://qiita.com/pira/items/d2f3d18f98d7bde04a87)
        - @pira さん

情報感謝です。

https://www.raspberrypi.org/downloads/noobs/
NOOBS 
Offline and network install
Version 3.0.0
Release date: 2018-11-16
を使用しました。


### 固定IPアドレス設定

過去にRPi2の時に`/etc/network/interfaces`を設定していたが、そのファイルを見た時のメッセージから、そのファイルを編集するのは正しくない、と気づいた。

- [Raspbian(jessie)の固定IPアドレス設定方法](http://xn--u9j0md1592aqmt715c.net/raspbian-ipaddress-config/
) @ 俺の技術メモ
    - by 兄さん(管理人)

を参考に`/etc/dhcpcd.conf`を設定しました。

情報感謝です。

### SSH接続の有効化

SSH接続は初期状態では接続できません。

- [raspberry pi 3のsshが繋がらない対策（Connection refused）](http://web09.hatenablog.com/entry/how-to-raspberry-ssh) @ Aopika技術日記
    - hika09さん

情報感謝です。

上記の「GUIで設定する方法」を参考に設定しました。
(スタートメニュー > 設定 > Raspberry Piの設定 > インターフェイス > sshを有効に）

### lxsessionでの開通確認

自分の記事を参考にSSH接続とLXsessionの起動を確認した。

- [CentOS on vmware > RPiのデスクトップを表示する > on MacOSX | on Windows 7pro](https://qiita.com/7of9/items/71f6d3a3b37da0ee40b2)
[Rails5]jquery-railsってなんぞ？

# はじめに

Railsの勉強としてgem周りを触ってみる企画です。
今回は、

[jquery-rails](https://github.com/rails/jquery-rails)

です。

## どういうgemなの？

RailsでjQueryを使えるようにするためのgem。

## 検証環境

以下の環境で実施しました。

```
[client]
・MacOS Mojave(10.14.2)
・Vagrant 2.2.2
・VBoxManage 6.0.0

[virtual]
・CentOS 7.6
・Rails 5.2.2
・ruby 2.3.1
```

ご参考までに。

# jquery-rails導入

**1.gemのインストール**

事前にRails勉強用に作成したプロジェクトで進めます。
各MVCは適当に掲示板アプリを想定してPostsコントローラーなどを生成済みです。
(index,show,editの空ページが見れる程度)

```余談
$ rails g model post
$ rails g controller posts index show edit
```

その前提のもと、Gemfileに以下を追記。

```ruby:Gemfile
# jquery-rails
gem 'jquery-rails'
```

追記したらインストール。

```
$ bundle install

-----------
Fetching jquery-rails 4.3.3
Installing jquery-rails 4.3.3
-----------
→無事に完了。
```

**2.jquery-railsの設定調整**

gemインストール後の設定を進めていきます。

```javascript:application.js
//= require jquery3
```

```ruby:application.html.erb
<%= javascript_include_tag 'application', 'data-turbolinks-track': 'reload' %>
```

を追加。

**3.jQueryを使ってみる**

これで準備が整ったので、
実際にjQueryを使った処理を書いてみます。

```ruby:index.html.erb
<h1>Dashboards#index</h1>
<p>Find me in app/views/dashboards/index.html.erb</p>

<p>jQueryが動けば中身が出てくるよ</p>
<p id="test"></p>

<script>
  $("#test").html("ミッションコンプリート！");
  $("#test").css("color","red");
</script>
```

![cap1.png](https://qiita-image-store.s3.amazonaws.com/0/335844/7a2e9f5b-bf15-ec72-2f02-9673eb0d2431.png)

動いた！

# 所感

jQueryを簡単に導入出来る素敵なgemでした。

# おわりに

何かお気づきの点がありましたら、
ご指摘やアドバイス等頂けると大変助かります！