OmniAICreator/Qiita-1.07M huggingface dataset:
addEventListenerでnullチェックが面倒くさいとき

例えば、ある要素をクリックした時の動作を定義する際、大雑把にこんな感じになる。

```js
const el = document.getElementById('checkbox');
el.addEventListener('click', e => {
  // 省略
  e.preventDefault();
});
```

だが`[id=checkbox]`が存在しない場合、`getElementById`は`null`を返す。
なのでDOM要素が存在しているかを判別する必要が出てくる。

```js
const el = document.getElementById('checkbox');
if(el != null) {
  el.addEventListener('click', e => {
    // 省略
    e.preventDefault();
  });
}
```

これはダサい。
ので、該当のDOM要素が存在しなかったらDOMを変数に入れてしまえばいい。

```js
const el = document.getElementById('checkbox') || document.createElement('input');
el.addEventListener('click', e => {
  // 省略
  e.preventDefault();
});
```

`createElement`したDOMはHTML上には存在しないので、遠慮なしに`addEventLister`でリスナー待ちになる。
ただし問題はあまりにやりすぎるとメモリを喰らっていくので、本来はちゃんとnullチェックした方がいい。
Heroku Postgresにread onlyユーザ追加

以下、Heroku CLIでの実行例について記述してあるが、Herokuの画面から作るほうがラク


作成
----
```
heroku pg:credentials:create DATABASE_URL --name ＜ユーザ名＞ --app ＜アプリ名＞
```

権限付与
--------
```
heroku pg:psql --app ＜アプリ名＞
  GRANT USAGE ON SCHEMA ＜スキーマ名＞ TO ＜ユーザ名＞;
  GRANT SELECT ON ALL TABLES IN SCHEMA ＜スキーマ名＞ TO ＜ユーザ名＞;
  ALTER DEFAULT PRIVILEGES IN SCHEMA ＜スキーマ名＞ GRANT SELECT ON TABLES TO ＜ユーザ名＞;
  \q
```
↑data.heroku.comでPermissionを指定するのでも良い

接続情報表示
------------
```
heroku pg:credentials:url --name ＜ユーザ名＞ --app ＜アプリ名＞
```
表示された情報でDBeaverのコネクション作成

アタッチ/デタッチ
-----------------
割愛

削除
----
```
heroku pg:credentials:destroy --name ＜ユーザ名＞ --app stg-＜アプリ名＞ --confirm ＜アプリ名＞
```
LambdaでS3からファイルを取得しようとしたらbotocore.exceptions.ClientError: An error occurred (AccessDenied) when calling the GetObject operation: Access Deniedとなった時の対応方法

AWSもPythonもぜーーんぶ初心者でわけわからん。

- 環境
    - OS : Ubuntu Server 18.04 LTS
    - Python 3.6

# 事象 : Lambda関数でBoto3を使ってS3にあるファイルを取得しようとしたら怒られた

```python:lambda_function.py
def get_file_from_s3(file_name: str):
    """S3よりファイルを取得する."""
    s3 = boto3.client('s3')
    try:
        file = s3.get_object(Bucket = BUCKET_NAME, Key = 'irai.txt')
    except botocore.exceptions.ClientError as e:
        if e.response['Error']['Code'] == "404":
            logger.error("The object does not exist.")
        else:
            raise e
```
```text:CloudWatchのログ
get_file_from_s3('irai.txt')
File "/var/task/lambda_function.py", line 91, in get_file_from_s3
file = s3.get_object(Bucket = BUCKET_NAME, Key = 'irai.txt')
File "/var/runtime/botocore/client.py", line 314, in _api_call
return self._make_api_call(operation_name, kwargs)
File "/var/runtime/botocore/client.py", line 612, in _make_api_call
raise error_class(parsed_response, operation_name)
botocore.exceptions.ClientError: An error occurred (AccessDenied) when calling the GetObject operation: Access Denied
```

# 原因 : Lambdaに設定されたIAMロールにS3へのアクセス権限がないから
[Lambdaはファンクション登録時にそのファンクションで利用するIAMロールを選択できると思うので、そこでS3アクセス権限のあるロールを選択してください。 - スタック・オーバーフロー](https://ja.stackoverflow.com/questions/38139/aws-lambda%E3%81%A7s3%E3%81%8B%E3%82%89getobject%E3%82%92%E5%AE%9F%E8%A1%8C%E3%81%99%E3%82%8B%E3%81%A8%E3%82%A8%E3%83%A9%E3%83%BC%E3%81%8C%E7%99%BA%E7%94%9F%E3%81%97%E5%AF%BE%E5%87%A6%E6%B3%95%E3%81%8C%E5%88%86%E3%81%8B%E3%82%8A%E3%81%BE%E3%81%9B%E3%82%93)

## 対応 : IAMロールにS3へのアクセス権限を設定する
参考 : [IAM RoleとBucket PolicyでAmazon S3へのアクセス制御を行う - yoshidashingo](https://yoshidashingo.hatenablog.com/entry/2014/08/03/190225)

1. コンソールから[IAM]を選択する
    - ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159761/9461f849-edd1-c58c-62f2-78ec25c731d6.png)
2. ロールの一覧からLambdaで使用しているIAMロールを選択する
    - ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159761/f299eab2-e212-d87c-758d-6acf0f5cc388.png)
3. [Attach policies]ボタンを押下する。
4. [AmazomS3FullAccess]を選択して[Attach policy]ボタンで追加する。
    - ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159761/9ec0cc29-1a33-7476-2fad-bf339a2524d0.png)
プログラム初心者のためのC#入門 #10 継承

# #10 継承
今回はオブジェクト指向型プログラミングで重要な継承について説明します．まずは継承を使ったコードを見てみましょう．

```InheritanceSample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace InheritanceSample
{
    class Base
    {
        public void M()
        {
            Console.WriteLine("M Method called.");
        }
    }

    class Derived : Base { }

    class Program
    {
        static void Main(string[] args)
        {
            new Base().M();
            new Derived().M();
        }
    }
}
```
```:出力結果
M Method called.
M Method called.
```
クラス名の次に`:継承したいクラス名`を書くことで継承できる．
継承というのは属性(変数)や操作(関数)の受け継ぎができる機能で，上の例では`Derived`クラスでは定義されていないはずの`M`メソッドを使用することができています．これは`Derived`クラスが`Base`クラスを継承しているので`Base`クラスのメソッドを使うことができるということです．
ちなみに，継承されるクラス(この例では`Base`)のことを，基底クラスや，スーパークラスなどと呼び，継承するクラス(この例では`Derived`)のことを，派生クラスや，サブクラスなどと呼びます．
##抽象クラス
```AbstractClassSample.cs
abstract class Base
{
    public void Method() { }
    public abstract void OverriddenMethod();
}

class Derived : Base
{
    public override void OverriddenMethod() { }
}
```
抽象クラスは自身のインスタンスを作れず，継承されることを前提とするクラスです．メソッドに`abstract`修飾子を付けることで，定義だけしてその実装を派生クラスに委譲することができます．
##インターフェース
```InterfaceSample.cs
interface IBase
{
    void Method();
}
interface IBase2
{
    void Method2();
}

class Derived : IBase, IBase2
{
    public void Method() { }
    public void Method2() { }
}
```
インターフェースは，定義したプロパティ(メンバ変数とメソッドが融合したようなもの)やメソッドを，継承したクラスへ強制的に実装させるというものです．インターフェースは上の例の様に多重継承できます．
##使用例
実際に継承を使ってみましょう．

```InheritanceSample.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace InheritanceSample
{
    abstract class Animal
    {
        public string sound;

        public Animal(string sound)
        {
            this.sound = sound;
        }

        public void MakeSounds()
        {
            Console.WriteLine(sound);
        }
    }
    class Dog : Animal
    {
        public Dog() : base("Bow wow") { }
    }
    class Cat : Animal
    {
        public Cat() : base("Meow") { }
    }
    class Bird : Animal
    {
        public Bird() : base("Chirp") { }
    }

    class Program
    {
        static void Main(string[] args)
        {
            Animal[] animals = new Animal[] { new Dog(), new Cat(), new Bird() };

            foreach (Animal animal in animals)
            {
                animal.MakeSounds();
            }
        }
    }
}
```
```:出力結果
Bow wow
Meow
Chirp
```
`Dog`クラス，`Cat`クラス，`Bird`クラスを全て`Animal`型として扱っています．`Animal`クラスは`MakeSounds`メソッドを持っているので，`animals`内の全ての動物を鳴かせることができています．
派生クラスのコンストラクタが呼び出されると，自動的に基底クラスのコンストラクタも呼び出されますが，`:Base()`と書くと，基底クラスのコンストラクタを明示的に呼び出すことができます．

次回は[ポリモーフィズム](https://qiita.com/17t7037t/items/3ee662978f6b03a7d58e)について説明します．
Core DataにおけるAttributeに@objcが永遠に求められるバグ


## 再現方法
1. CoreDataのxcdatamodeledファイルで以下のように設定．
<img width="258" alt="スクリーンショット 2019-05-10 12.03.18.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/314588/d302ea4f-5fbe-911c-5f5c-497d4c19d23c.png">

2. 適当なところでScenaryAttributeKeyを以下のように定義．
<img width="637" alt="スクリーンショット 2019-05-10 12.04.21.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/314588/191a2ac3-679f-1eef-5d94-dce489f3c936.png">

3. ランする．

## 症状
以下のような静的エラーが起こり，Fixを選ぶと永遠に@objcが並び，かつ解決されない
<img width="851" alt="スクリーンショット 2019-05-10 12.02.33.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/314588/0570ff52-9fed-ffc0-2e19-0f6a375427c1.png">
※publicにしろというお達しも出ているが，ScenaryAttributeKeyに付けても同様なバグが出る

## 解決策
UserInfoでよくやるようにDictionaryの型は[String: Any]でやること．

## 追記
ちょっと調べたら[あんな記事](https://qiita.com/Kennie/items/3788936e25cc018ca1ac)や[こんな記事](https://stackoverflow.com/questions/26900302/swift-storing-states-in-coredata-with-enums)があった．ありがたい．これでできるかも．
VagrantとVirtualBOXで構築したCentOS7環境のMySQL5.7のデータベースに、ローカル環境からアクセスする

###開発環境
・MacOS mojave 10.14.4
・MySQL5.7
・CentOS7

###はじめに
・ローカル環境のデータベースと仮想環境のMySQLのデータベースの値を同じにします。
・ローカルにはMySQLをインストールしてません。仮想環境のみにMySQLをインストールしてます。

###ローカル環境のデータベース

ローカル環境のデータベースとは、Rails 5.2.3のデータベースです。

```database.yml
default: &default
  adapter: mysql2
  encoding: utf8
  pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
  username: root
  password: password
  host: hostnumber
  #socket: /var/lib/mysql/mysql.sock


development:
  <<: *default
  database: databasename
```


###①vagrantとVirtualBOXでCentOS7環境を構築

参照記事：https://wemo.tech/1564

###②vagrantでMySQL5.7のデータベースを作成
参照記事：https://enomotodev.hatenablog.com/entry/2016/09/01/225200

###③root権限付与

```
GRANT ALL ON *.* TO root@'%' IDENTIFIED BY 'password' WITH GRANT OPTION;
```

参照記事：https://qiita.com/PallCreaker/items/0b02c5f42be5d1a14adb

###④ローカル環境からCentOS7のMySQLにログイン

ローカル環境でデータベースを作成した時と同じhostnumber,passwordを使う。
databasenameも、ローカル環境でデータベースを作成したdatabasename=CentOS7上で作成したMySQLのdatabasenameの関係になるようにする

参照記事：http://mysql.javarou.com/dat/000389.html

```
$ mysql -hhostnumber -u root  -ppassword
mysql: [Warning] Using a password on the command line interface can be insecure.
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 8
Server version: 5.7.26 MySQL Community Server (GPL)

Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
```

###
```
$ ls init* inittable.sql`
```
```
$ mysql -hhostnumber -u root  -ppassword databasename < inittable.sql 
mysql: [Warning] Using a password on the command line interface can be insecure.
```



これでローカル環境からCentOS7環境のデータベースにアクセスできた。
#git push でリモートブランチ名を指定なしで実行できるようにする   ( $ git config --global push.default current )

# グローバル設定を変更する例

```
$ git config --global push.default current
```

# ~/.gitconfig

configファイルにこんなのが記述されます

```
[push]
	default = current
```

# こういうエラーをなくしたい

```
fatal: The current branch chore/logdir has no upstream branch.
To push the current branch and set the remote as upstream, use

    git push --set-upstream origin some
```

```
git config --global push.default current
```

# ためになる記事


[gitのpush.defaultに関するノウハウ - Qiita](https://qiita.com/awakia/items/6aaea1ffecba725be601)


>simple
>これからのデフォルト。upstreamが設定されていて、それが同名のブランチ名であるときのみpushする。初心者でも安心して使える。初心を忘れないあなたと、デフォルトを愛するあなた向き。

>current
>現在のブランチをリモートに同名でpushする。例えupstreamを設定していなくてもpushされるので、めんどくさがりで効率重視なあなた向き。

>まとめ
>結局どれ使えばいいかわからないという人は、次世代のデフォルトのsimpleか、currentを使うといいと思います。currentはかなり楽なので、僕はこれを使っています。



# Original by Github issue

https://github.com/YumaInaura/YumaInaura/issues/1754








<!-- Update From Qiita API -->

# チャットメンバー募集


何か質問、悩み事、相談などあればLINEオープンチャットもご利用ください。

https://line.me/ti/g2/eEPltQ6Tzh3pYAZV8JXKZqc7PJ6L0rpm573dcQ





# Twitter


https://twitter.com/YumaInaura


<!-- Update From Qiita API -->
HTMLのflexboxについて

<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>flexbox</title>
<link rel="stylesheet" href="style.css" media="all">
</head>

<body>

<div class="main-nav2">
<p>あ</p>
<p>い</p>
<p>う</p>
<p>え</p>
<p>お</p>
</div>


</body>
</html>

このような問題を授業で出されたのですが、「あ」や「い」を囲んでいる線の出し方がわかりません....
分かる方いたら、教えてください。
![sample1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/348043/fabb9ca6-4923-ba3f-ccfa-70145c38a6ac.png)
Swift5 UIPageViewControllerの使い方

[こちら](https://qiita.com/Takeshi_Akutsu/items/dbf54df8e8a50e8ed5be)の記事が古かったのでコピペで動くものを共有します。


``` .swift
final class ViewController: UIPageViewController {
    
    private var controllers: [UIViewController] = []
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        let colors: [UIColor] = [.red, .orange, .green, .cyan]
        controllers = colors.map { color in
            let c = UIViewController()
            c.view.backgroundColor = color
            return c
        }
        
        setViewControllers([controllers[0]],
                           direction: .forward,
                           animated: false,
                           completion: nil)
        
        dataSource = self
    }
}

extension ViewController: UIPageViewControllerDataSource {
    
    /// 右にスワイプ（戻る）した場合のメソッド
    func pageViewController(_ pageViewController: UIPageViewController, viewControllerBefore viewController: UIViewController) -> UIViewController? {
        if let index = controllers.firstIndex(of: viewController),
            index > 0 {
            return controllers[index-1]
        } else {
            return nil
        }
    }
    
    /// 左にスワイプ（進む）した場合のメソッド
    func pageViewController(_ pageViewController: UIPageViewController, viewControllerAfter viewController: UIViewController) -> UIViewController? {
        if let index = controllers.firstIndex(of: viewController),
            index < controllers.count-1 {
            return controllers[index+1]
        } else {
            return nil
        }
    }
    
    func presentationCount(for pageViewController: UIPageViewController) -> Int {
        return controllers.count
    }
}

```



transitionStyleがgetterなので変更したい場合はinitで指定しないと(多分)

``` .swift
    override init(transitionStyle style: UIPageViewController.TransitionStyle, navigationOrientation: UIPageViewController.NavigationOrientation, options: [UIPageViewController.OptionsKey : Any]? = nil) {
        super.init(
            transitionStyle: .scroll,
            navigationOrientation: .horizontal,
            options: options
        )
    }
```


サクッと動かしたかったけど、Storyboard使ったパクリ記事ばっかで😹
【はじめてのUipath】メモ帳を閉じたいのにセレクターが見つからない！を解決したよ

UiPathアカデミーでUiPathを学習しています。

演習みたいなところで、メモ帳を操作する場面があったのですが、
実装したものを実行すると、メモ帳にいろいろ書き出して、保存したのはいいものの、全然メモ帳が閉じない！！

セレクターがみつからないっていうんですね～～

レコーディングを使うとたまにあるみたいです。

これを解決しました！！

# どういうものを実装していたか

1. 入力ダイアログでメモ帳に何を書きたいかをきく
2. 入力ダイアログでメモ帳のファイル名をきく
3. メモ帳を起動する（レコーディング）
4. メモ帳に1で指定された内容を入力する（レコーディング）
5. メモ帳を、2で指定されたファイル名で保存する（レコーディング）
6. メモ帳を×で閉じる（レコーディング）

んで、5まではすいすい行くんですけど、6番でメモ帳が閉じない！！ってなってたんですね～～

![UiPath Studio - resson4 2019_05_10 11_15_27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/238739/36fc44bc-4800-ecc6-b543-5a29588d086c.png)

# 解決策はセレクターをいじる！

`クリック 'push button  閉じる'`をクリックしてプロパティパネルを覗きます。

![UiPath Studio - resson4 2019_05_10 11_21_43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/238739/31e7ee9b-eb37-fc34-ce8a-452f4c749bc8.png)

プロパティパネルの`入力`の`セレクター`を探してください。
その右側にある「...」のボタンをクリックします。

するとこんなのが出てきました。


![UiPath Studio - resson4 2019_05_10 11_23_15.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/238739/78d0fcd7-d617-6347-7227-b891f85d0a9d.png)


なるほど！！！`title`のところに`arigatou.txt`って書いてある！！

これは、レコーディングをしたときのメモ帳の名前ですわ！なので、汎用的に使うことはできませんよね。

ファイル名を変えても、こいつは`arigatou.txt`のメモ帳の閉じるボタンを探しているということですね。

というわけでこいつをオフにしてあげましょう。

![UiPath Studio - resson4 2019_05_10 11_22_45.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/238739/4984e03f-f53c-a405-06b3-4e89c12d6226.png)

これで実行したらちゃんと閉じるボタンをみつけて、閉じてくれました！

同じような症状が出たら、試してみてくださいね！
Chatロボット#01Dialogflowを登録しよう

この記事たちはChatロボットのチャレンジを頑張ろうと思って書いてます。

#Dialogflowとは？
ブラウザの簡単操作で Google Home、携帯などで音声会話アプリを作成できる。
そしてプログラムあまり書かなくても行ける。

#Dialogflowを登録してみよう

下記のLINKをアクセスします。Sign Up For Freeをクルックします。
https://dialogflow.com/

![digflow1.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/1a20443e-c7b8-324f-706a-f980922c4f0b.jpeg)

次はSign in with Googleをクリックします。
![digflow2.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/a822e0a5-9be4-243b-093f-3d0e261e44ae.jpeg)

次は国などを設定し、CheckboxをいれACCEPTをクリックします。
![digflow3.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/938c3e34-7a2d-2fe4-0f31-8e8ab8989c90.jpeg)
登録終わったら下記の画面出てきます。
![digflow4.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/c2302fd9-706c-366d-0516-106ab0774eb8.jpeg)

Create Agentをクリックします。
![digflow5.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/5d91bd49-61b8-f8a1-7155-8fc683dfb021.jpeg)

Agentの名前と入力し、Default Languageを選択します。
![digflow6.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/77a11132-d48e-4dcc-8301-a4fb0f2a60e0.jpeg)

次はIntentsを追加します。
![digflow8.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/6ded55d9-6a7a-1906-7e82-235c63bc5890.jpeg)

まず隣のTry it nowでなにかを試してみよう。
うん、まだなにも設定してないからよくわかりませんって答えられましたね。
![digflow9.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/d83639ce-4e67-3a0b-5195-5a60c348950c.jpeg)

じゃTraining phrasesのところでなにか追加してみよう。
![digflow10.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/cc835c53-d6c5-8cfb-6e18-19116af825cc.jpeg)

次はResponsesで返事を追加します。
![digflow11.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/44e081ad-5a86-d4b8-c13e-2f4136cf37d3.jpeg)

SAVEボタンをクリックします。
![digflow13.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/aa5e38f1-b07f-0a68-e4ca-b1d4a79aeaa7.jpeg)

最後は試してみよう。うん、大丈夫そうだね！
![digflow14.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154661/e200562b-8da7-a4f7-63a8-dd347326137a.jpeg)

それでまずプログラム一句書かずに簡単なCHATをできました。
次はLINEとつながってみよう～
【MySQL】文字列内のスペースを無視して検索する

- テストユーザ　　　<- スペースなし
- テスト　ユーザ　　<- 全角スペース
- テスト　　ユーザ　<- 全角スペース2個
- テスト ユーザ　　　<- 半角スペース

これをまとめて検索したい。

## 解決方法
正規表現を使う。

MySQL 5.6 リファレンスマニュアル 12.5.2 正規表現
https://dev.mysql.com/doc/refman/5.6/ja/regexp.html 

```
mysql> select * from user where name regexp 'テスト( |　)*ユーザ';
+----+------------------+
| id | name             |
+----+------------------+
|  1 | テストユーザ     |
|  2 | テスト　ユーザ   |
|  3 | テスト　　ユーザ |
|  4 | テスト ユーザ    |
+----+------------------+
```

スペースが入っているものに限定するならこう。

```
mysql> select * from user where name regexp 'テスト( |　)+ユーザ';
+----+------------------+
| id | name             |
+----+------------------+
|  2 | テスト　ユーザ   |
|  3 | テスト　　ユーザ |
|  4 | テスト ユーザ    |
+----+------------------+
```
MySQL INSERT重複あるならUPDATEかIGNORE

# 基本INSERT重複あるならUPDATEかIGNORE

Pythonでデータ処理してたらMySQLで`duplicate entry`のようなエラー発生。重複ある場合にINSERTしたので発生したようです。
重複あったら上書きしてしまうか無視する方法を書きます。
※勉強中の身なので細かいところは注意してください

## ON DUPLICATE KEY UPDATE

`REPLACE INTO`でもできるみたいだが、構造上DELETEされるので削除権限与える必要あり、TIMESTAMPの問題あるので`ON DUPLICATE KEY UPDATE`使う方がいいらしい。

1行ずつINSERTでなく一括にて

```.sql
INSERT INTO
    sampletable (Id, Name, LogDate, LogTime, LogMilliSecond, LogValue)
    VALUES(%s, %s, %s, %s, %s, %s)
ON DUPLICATE KEY UPDATE
    Id = VALUES(Id),
    Name = VALUES(Name),
    LogDate = VALUES(LogDate),
    LogTime = VALUES(LogTime),
    LogMilliSecond = VALUES(LogMilliSecond),
    LogValue = VALUES(LogValue)
```

この例は単純にデータがあったらUPDATEするだけですが、重複していたら数値+1したいとか、挿入する文字を変更したいなどもに使うのが普通かと思います。
[INSERT ... ON DUPLICATE KEY UPDATE Syntax](https://dev.mysql.com/doc/refman/8.0/en/insert-on-duplicate.html)

今回の例では別にエラー出ないで重複は無視されればいいので`INSERT IGNORE INTO`も使えます


## INSERT IGNORE INTO

```.sql
INSERT IGNORE INTO
    sampletable (Id, Name, LogDate, LogTime, LogMilliSecond, LogValue)
    VALUES(%s, %s, %s, %s, %s, %s)
```
重複データが入ってくるのが基本的にない場合にはこれでもいいかも。
参考：[INSERT Syntax](https://dev.mysql.com/doc/refman/8.0/en/insert.html)


ただ、なんか怪しい雰囲気あったので調べたらやはり怪しい場合あるみたい
[kamipo TRADITIONALでは防げないINSERT IGNOREという名の化け物](http://www.songmu.jp/riji/entry/2015-07-20-insert-ignore.html)

# 最後にPYTHONコードこんな感じで登録
```insert.py
import MySQLdb
conn = MySQLdb.connect(
user='username',
passwd='pass',
host='localhost',
db='sample_db')

cur = conn.cursor()
sql = '''
INSERT IGNORE INTO
    sampletable (Id, TagName, LogDate, LogTime, LogMilliSecond, LogValue)
    VALUES(%s, %s, %s, %s, %s, %s)
'''
# ↓サンプルデータ。ここをデータ読み込み処理入れ替え
datas = [
[1, 'Status1','19/05/09','02:40:00',0,1],
[2, 'Status1','19/05/09','07:40:00',0,2],
[3, 'Status1','19/05/09','12:30:00',0,1],
[4, 'Status1','19/05/09','17:30:00',0,2],
[5, 'Status1','19/05/09','21:30:00',0,1],
[6, 'Status1','19/05/09','23:30:00',0,2],
]

try:
    cur.executemany(sql, datas)    # バルクインサート
    print(str(cur.rowcount) + "件登録")
    conn.commit()
    
except Exception as e:
        print(e)
        
finally:
    # 接続を閉じる
    cur.close
    conn.close
```
[Ruby]同名のメソッドを持つ複数の Module を include してメソッドを呼ぶと？

## 概要
同名のメソッドを持つ複数の Module を include した場合、メソッドを呼び出したときにどういう動きをするんだろう？という疑問が唐突に頭を過ぎりました。本当に唐突ですみません。

最初は事例やドキュメントを探してみようかと思ったのですが、これなら実際やってみたほうが早いと思いましたので簡単なサンプルコード書いて確認してみました。結果を以下に記載していきたいと思います。

## 予想
1. include でコケる
2. メソッドの呼び出しでコケる
3. 最後に include された Module に実装されたメソッドの動きになる

３っぽい気はします。

## 環境
ruby 2.5.1

## 結論
**選択肢3** が正解でした。<font color="red">**後勝ち**</font> みたいですね。 include の順番を入れ替えたら出力結果が変わることも確認できました。

## 検証用サンプルコード
適当な Module を3つ用意し、全てのモジュールに `run` メソッドを実装しました。これを全て include して `run` を実行したときにどのような動きをするかを確認する、というかんじで使いました。
そもそも Module の設計とかメソッドの名前とかに問題があるんじゃね？と言われたらぐうの音も出ないのでひとまずここではスルーしてくださいｗ

```ruby:test.rb
# module
module ModA
  def run
    p :ModA
  end
end

module ModB
  def run
    p :ModB
  end
end

module ModC
  def run
    p :ModC
  end
end

# class
class Sample
  include ModA
  include ModB
  include ModC
end

# main
Sample.new.run # => "ModC"
```

## 追記
@Nabetani さんから、さらに充実した検証コードを下記コメントでご教示いただきました。感謝。
https://qiita.com/tommy_aka_jps/items/f02732d993a726574f83#comment-761cc0f00cb95cc869b1

※環境によってはアンカーリンクがうまく機能していないようなので、前述のコメントからコードを転載します。

```ruby
module ModA
  def run; p :ModA ;end
end

module ModB
  def run; p :ModB ;end
end

module ModC
  def run; p :ModC ;end
end

module ModD
  def run; p :ModD ;end
end

class UseInclude
  include ModA
  def run; p :UseInclude; end
end

UseInclude.new.run #=> :UseInclude

class UsePrepend
  prepend ModA
  def run; p :UsePrepend; end
end

UsePrepend.new.run #=> :ModA

o = UsePrepend.new

def o.run; p :"o.run"; end
o.run #=> :"o.run"

o.class.prepend ModB

o.run #=> :"o.run"

o.singleton_class.include ModC

o.run #=> :"o.run"

o.singleton_class.prepend ModD

o.run #=> :ModD
```


## おわりに
よく考えてみればそんなに意外な結果ではないですかね。仮に `Sample` クラスで `run` メソッドをオーバーライドしたら当然そっちで動きますしね。 Module って C# で言うところの interface みたいなイメージを持っていたので、メソッド呼び出しの際に型指定がないとエラーになるかと勘違いしていました。クラスの多重継承を扱える言語はまだ触ったことがないので他の言語だとどうなんでしょうね。C++ とか詳しい方、よろしければご教示ください。(他力本願)
Vue CLI 3で開発サーバをngrokで公開する

# 概要
モックの共有のため、一時的に開発サーバを外部に公開したい場面があり、
方法を検討したところ、ngrokが使いやすかっため手順を備忘として残しておく。


Vue CLI 3では設定済みのwebpackの開発サーバが提供されている。
ngrokを使用すれば、一時的にその開発サーバを外部に公開することができる。


## 環境
OS:Windows 10

ローカル環境に
REST API と webpackの開発サーバをそれぞれ立てている。

APIサーバ

```
localhost:8080
```
webpack

```
localhost:8081
```

## 手順

### webpackの開発サーバを起動
予めserveコマンドを実行して開発サーバを起動しておく。

### ngrokのインストール
以下のリンクからWindows用のzipファイルを取得する。
https://ngrok.com/

### ngrokを起動
取得したzipファイルを任意のディレクトリに解凍し、コマンドプロンプトでngrokを起動する
ngrokはhttpコマンドの後にポート番号を入力することでポートフォワーディングが行われ、ngrokを介して公開される。

webpackのホストはlocalhost:8081のため、8081をポートフォワーディングする。
以下のコマンドを実行

```
ngrok http 8081
```
成功すると公開されたURLが表示される。
URLは下記のngrok.ioのURLの部分となる。

```
Forwarding                    http://XXXXXXX.ngrok.io -> localhost:8081
```

### ngrokの公開URLにブラウザでアクセス

```
Invalid Host
```
と表示されてしまう場合、vue.config.jsに下記の設定を追加する。

```vue.config.js
module.exports = {
  devServer: {
    public: "http://XXXXXXX.ngrok.io",
    disableHostCheck: true,
  }
};

```
ansible 小技

# file test

Makefile みたいに「ファイルが存在するかどうか」で実行するかどうかを判断したい場合もある。典型的には shell module の creates がまさにそのような挙動をするが、より一般的に次のような `when` を書けば大丈夫。

```yaml
- name: some action
  when: not lookup("file", "path/to/file", errors="ignore")
```

# blockinfile で placeholder
plugin 的なものは設定ファイルで [blockinfile](https://docs.ansible.com/ansible/latest/modules/blockinfile_module.html) を使うと便利。

一つのファイルで複数個所書き換える場合は、`marker` を書き換えておかないと、書き換え合戦が起こることに注意（マーカー（目印）を起点にコメントで囲まれたブロックを放り込むため）。

書き換え先のファイルも自分で用意する場合は、いっそのことあらかじめマーカーを用意しておくと分かりやすくなる。いわゆる「プレースホルダ」。

さらに推し進めると、`blockinfile` の `marker` を最初から書いておくという手もありです。

## プレースホルダの例
書き換えられる側の設定ファイルにマーカーを用意しておく。

```ini:/path/to/conf.ini
[sectionA]

;;sectionA_content

[sectionB]

;;sectionA_content
```

`blockinfile` 側の設定では、このマーカーに向かって `insertbefore` あるいは `insertafter` で放り込みます。

```yaml:roles/example/tasks/main.yml
---
- name: Put example in section A
  blockinfile:
    path: /path/to/conf.ini
    insertbefore: ";;sectionA_content"
    marker: "# {mark} ANSIBLE MANAGED BLOCK example"
    content: |
      example1=test1
      example2=test2
```

## 直接マーカーを置く

もっとあからさまにコメントブロックを置いておくのでもよい。

```ini:/path/to/conf.ini
[sectionA]

# BEGIN ANSIBLE MANAGED BLOCK example
# ansible will fill this block
# END ANSIBLE MANAGED BLOCK example

[sectionB]

# BEGIN ANSIBLE MANAGED BLOCK another
# ansible will fill this block
# END ANSIBLE MANAGED BLOCK another
```

# apt module の update_cache

見当違いのところを調べたりしていたけれども、外部との疎通に問題があっただけだった。

```
 [WARNING]: Could not find aptitude. Using apt-get instead

fatal: [hostname]: FAILED! => {"changed": false, "msg": "Failed to update apt cache: "}
```
OpenJ9 で GO

現状利用している OpenJ9 向け設定を紹介するだけの記事です。

# Apache Maven の場合

環境変数 `MAVEN_OPTS` を `-Xgcpolicy:optthruput -Xshareclasses:name=maven` に設定しました。

現在までのところ、共有クラス キャッシュのサイズはデフォルトの 64 MiB で問題なさそうです。

# NetBeasn IDE (Windows) の場合

ショートカットのリンク先に `-J-Xshareclasses:name=netbeans -J-Xscmx96m -J-Xquickstart` を追加しました。

IDE では共有クラス キャッシュの空きが厳しくなる模様なので、 96 MiB に増やしました。また IDE の起動が遅いとストレスの種になるので、 `-Xquickstart` も指定しました。

# Docker コンテナーの場合

コンテナー内環境変数 `OPENJ9_JAVA_OPTIONS` を `-Xtune:virtualized -Xshareclasses` に設定しました。

共有クラス キャッシュのサイズは、アプリケーションにより調整が必要でしょうね。
linux slab

## 背景

linuxのslabキャッシュについての記事

## キャッシュメモリとは

そもそものキャッシュとはなんなのかの説明。

```
キャッシュメモリとは、CPUの処理速度を低下させないために、メインメモリ（主記憶装置）にあるデータをあらかじめ移しておき、
高速でのデータ入出力を可能にするメモリのことである。
```

引用元：[キャッシュメモリ](https://www.sophia-it.com/content/%E3%82%AD%E3%83%A3%E3%83%83%E3%82%B7%E3%83%A5%E3%83%A1%E3%83%A2%E3%83%AA)

## Linuxキャッシュの仕組み

* キャッシュにはページキャッシュとSlabキャッシュがある
* ページキャッシュは上記のようなディスクの内容を読んだらメモリにキャッシュするというもの
* その中でもSlabキャッシュはディレクトリのメタデータ情報を格納するdentryやファイルのメタデータ情報を格納するinode構造体をキャッシュ
* カーネル領域に存在する

Linuxはキャッシュの仕組みによって効率的にメモリ管理を行うことで、ディスクへのアクセスを減らし、データアクセスを高速化している。これは「ページキャッシュ」と呼ばれる仕組みで実現している。

このページの単位の多くは4KBとなっている。(過去に1度だけ64kbをみたことあるけどそれ以外は4kb以外みたことない)

#### slabtop

slabキャッシュ自体はslabtopコマンドで確認が可能です。

slabtop - リアルタイムにカーネル slab キャッシュ情報を表示する

```
書式
slabtop [ options ]
説明
  slabtop (1) はリアルタイムに詳細なカーネル slab キャッシュ情報を表示する。 キャッシュ情報の上位を、ソート基準に挙げられている 基準のいずれかでソートして、リストで表示する。 また slab レイヤ情報が書かれた統計情報ヘッダも表示する。
オプション
通常は   slabtop (1) の起動にオプションは必要ない。 しかし以下のオプションを 1 つ以上指定することで、動作を微調整できる。

--delay=n, -d n
n 秒毎に表示を更新する。 デフォルトでは   slabtop (1) は 3 秒毎に表示を更新する。 プログラムを終了するには q を入力すること。
--sort=S, -s S
S でソートする。ここで S はいずれかのソート基準である。
--once, -o
出力を 1 回表示して終了する。
--version, -V
バージョン情報を表示して終了する。
--help
使用法の情報を表示して終了する。
ソート基準
以下は各 slab キャッシュのソートに使用できる有効なソート基準であり、 表示する「上位 (top)」の slab キャッシュがどれであるかを決定する。 デフォルトのソート基準はオブジェクト数によるソート ("o") である。
slabtop の実行中に対応する文字を押すことにより、 ソート基準を変更することができる。

a:
アクティブなオブジェクト数でソートする。
b:
slab 毎のオブジェクト数でソートする。
c:
キャッシュサイズでソートする。
l:
slab 数でソートする。
v
アクティブな slab 数でソートする。
n:
名前でソートする。
o:
オブジェクト数でソートする。
p:
slab 毎のページ数でソートする。
s:
オブジェクトサイズでソートする。
u:
キャッシュ利用率でソートする。
```

項目については以下です

```
slab_cache
スラブアロケータで使用されている物理メモリの総容量

cache
ファイルデータのキャッシュなどに使用している物理メモリの総容量。共有メモリは Cached に加算される。 SwapCached は含まない
cache－(SwapCache+buffers)

buffers
ファイルなどのメタデータとして使用している物理メモリの総容量

committed
全プロセスによって確保された仮想メモリの総容量。

active
最近アクセスした物理メモリの容量

inactive
最近アクセスしていない解放してよい物理メモリの容量
```

## ソース

[linux/mm/slub.c](https://github.com/torvalds/linux/blob/master/mm/slub.c)
MYSQL ターミナル 操作 DB データベース GUI

#はじめに
Railsを使っているとActive Recordで簡単にできてしまいますので、ターミナルでmysqlを操作してみました。
#目次

+ ターミナルでmysqlに接続する
+ データベースを一覧で確認する
+ データベースの作成
+ データベースの選択
+ テーブルを確認する
+ テーブルを作成する
+ テーブル構造を確認する
+ カラムの追加
+ カラムを一つ追加する
+ カラムを複数追加する
+ カラムを修正する
+ カラムを削除する
+ データを登録する
+ mysqlから抜ける
+ GUIでの操作

###ターミナルでmysqlに接続する
ここからは全てターミナルでの操作になります。

```
mysql -u root
```
コマンドの意味「mysqlにユーザー名がrootで接続する」
###データベースを一覧で確認する

```
mysql> SHOW DATABASES;
```
実行結果

```
+------------------------------------+
| Database                           |
+------------------------------------+
| blog_development                   |
| blog_test                          |
+------------------------------------+
```
###データベースの作成

```
CREATE DATABASE データベース名;
```
###データベースの選択

```
USE データベース名;
```
###テーブルを確認する

```
SHOW TABLES;
```
###テーブルを作成する

```
CREATE TABLE テーブル名(複数系) (カラム名 型,カラム名 型);
```
例)postsテーブルに整数型のidカラムと長文字列のtitleカラムを追加する

```
CREATE TABLE posts (id INT, title VARCHAR(255));
```
###テーブル構造を確認する

```
SHOW columns FROM テーブル名;
```
実行結果

```
+-------+--------------+------+-----+---------+-------+
| Field | Type         | Null | Key | Default | Extra |
+-------+--------------+------+-----+---------+-------+
| id    | int(11)      | YES  |     | NULL    |       |
| name  | varchar(255) | YES  |     | NULL    |       |
+-------+--------------+------+-----+---------+-------+
2 rows in set (0.01 sec)
```
###カラムの追加
カラムの操作は以下のコマンドが基本になります

```
ALTER TABLE テーブル名 操作
```

####カラムを一つ追加する

```
ALTER TABLE テーブル名 ADD カラム名 カラムの型;
```
####カラムを複数追加する

```
ALTER TABLE テーブル名 ADD (カラム名 カラムの型, ……);
```
####カラムを修正する

```
ALTER TABLE テーブル名 CHANGE 古いカラム名 新しいカラム名 新しいカラムの型;
```
####カラムを削除する

```
ALTER TABLE テーブル名 DROP カラム名;
```
###データを登録する
####全てのカラムに値を入れる場合

```
INSERT INTO テーブル名 VALUES(値1, 値2, 値3);
```
####特定のカラムに値を入れる場合

```
INSERT INTO テーブル名(カラム名1, カラム名2) VALUES(値1, 値2);
```

テーブルにある全てのレコードを取得する

```
SELECT * FROM goods;
```
####NULL
空のカラムにはデフォルト値としてNULLが入っている。
例)

```
+------+--------------+------+-------+
| id   | name         | text | price |
+------+--------------+------+-------+
|    2 | 消しゴム       | NULL |  NULL |
+------+--------------+------+-------+
```
####データを更新する

```
UPDATE テーブル名 SET 変更内容 WHERE 条件;
```
####データを削除する

```
DELETE FROM テーブル名 WHERE 条件;
```
usersテーブルのid2のレコードを削除する場合

```
DELETE FROM users WHERE id = 2;
```
###mysqlから抜ける

```
mysql> exit
```
###GUIでの操作
GUIでSQLクエリを直接入力します。
Sequel Pro
TablePlus
####取得するテーブルを指定する

```
FROM テーブル名
```
####取得するカラムを指定する

```
SELECT カラム名
```
####取得するレコードを制限する(条件)
AND演算子

```
WHERE a AND b
```
OR演算子

```
WHERE a OR b
```
NOT演算子

```
WHERE NOT a
```
BETWEEN演算子
1つのカラムに対し上限と下限を指定して式を作り

```
WHERE カラム名 BETWEEN 下限 AND 上限
```
####コメント

```
-- ここにコメントを書く
```
 IN演算子

```
WHERE カラム名 IN (値1, 値2, ……)
```
SQLServer日本語コードの確認方法

SQLServerに作成したデータベースの文字コード（コードページ）が何なのか実機から調べた際の方法を紹介します。

#環境
SQL Server 2014

#対象のデータ型
今回調査対象としたのは、文字列型のデータ型であるchar（varchar）、nchar（nvarchar）で定義された列とします。

#文字コードの設定箇所
SQLServerには文字列の区別、ソート順を決定する照合順序という定義がありますが、文字コードはそれと同一箇所で設定します。
設定する箇所は以下となります。

　１．サーバに設定（SQLServerインストール時に指定）
　２．データベースに設定（CREATE DATABASE句で指定）
　３．テーブルに設定（CREATE TABLE句で指定）
　４．列に設定（CREATE TABLE句で指定）

#優先順位

``` 列に定義　＞　テーブルに定義　＞　データベースに定義　＞　サーバに定義 ```

となります。

列に定義がなければテーブル定義を、テーブルに定義がなければデータベースの定義を、データベースに定義がなければサーバの定義が使用されることになります。

#確認方法
確認方法は以下となります。

###確認したい列はUNICODE型か非UNICODE型か
　　　``` 頭にnが付かないchar型（char、varchar、text）＝　非UNICODE型 ```
　　　であり、
　　　``` 頭にnが付くchar型（nchar、nvarchar、ntext）＝　UNICODE型 ``` 
　　　となります。

　　　■非UNICODE型の場合
　　　　→　照合順序の確認へ

　　　■UNICODE型の場合
　　　　→　文字コード（コードページ）は**UTF-16**確定。


###照合順序の確認
非UNICODE型の列の照合順序を確認します。

```
SELECT name, collation_name FROM sys.columns WHERE name = N'確認したい列名';  

name　　　　　　collation_name
----------------------------------------
確認したい列名　Japanese_CI_AS

```

この列の照合順序は
**Japanese_CI_AS**
と出ました。

今回確認したいのは文字コード（＝コードページ）ですので、この照合順序がShift-JIS形式なのかUTF-8形式なのか以下のクエリで調べます。

```
SELECT COLLATIONPROPERTY('Japanese_CI_AS', 'CodePage')

----------------------------------------
932

```
**932**
と出ました。

コードページ**932**とはいわゆる**Shift-JIS**です。
[Code Page Identifiers](https://docs.microsoft.com/ja-jp/windows/desktop/intl/code-page-identifiers)

| Identifier &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;| .NET Name &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;| Additional information &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;|
|:-----------|:----------|:------------|
| **932** | **shift_jis** | ANSI/OEM Japanese; Japanese (Shift-JIS)|
| 1200 | utf-16 | Unicode UTF-16, little endian byte order (BMP of ISO 10646); available only to managed applications |
| 65001 |utf-8 | Unicode (UTF-8)|
| 20932 | EUC-JP | Japanese (JIS 0208-1990 and 0212-1990) |

#結論

今回確認した環境の文字コードは

　　　■非UNICODE型の列
　　　　→　**Shift-JIS**

　　　■UNICODE型の列
　　　　→　**UTF-16**

であることが確認できました。

#補足

Shift-JISで定義された列にUTF-8のコードの文字を挿入すると、Shift-JISに存在する文字コードの場合は指定した文字とは異なる文字として認識／格納され、Shift-JISに存在しない文字コードの文字を挿入すると、???となって格納されてしまいます。

これは接続ドライバによっては変換を行ってくれるものもありますが、負荷を軽減する意味でもアプリケーションが指定する文字コード（セット）とDB側の文字コード（セット）は統一した方がよいかと思います。
「Model-View-ViewModel デザイン パターンによる WPF アプリケーション」のコードのダウンロード先

MVVMメモ

[Patterns - WPF Apps With The Model-View-ViewModel Design Pattern](https://msdn.microsoft.com/en-us/magazine/dd419663.aspx?f=255&MSPPError=-2147217396)

日本語訳は、
[Model-View-ViewModel デザイン パターンによる WPF アプリケーション](https://msdn.microsoft.com/ja-jp/magazine/dd419663.aspx?f=255&MSPPError=-2147217396#id0090025)

このページからコードはダウンロード出来ないが、
[February 2009 Code Downloads](https://msdn.microsoft.com/en-us/magazine/msdnmag0209.aspx)にある、
http://download.microsoft.com/download/D/1/A/D1A38A8A-B635-4A74-9B7B-1177F4297867/MvvmDemoApp.zip
からダウンロード可。
[ナビ]スクロールに合わせてヘッダーを変化（PC時のみ）

自分用メモです

ファーストビューではヘッダーを大きく、
スクロールしたら小さく表示など、スクロールに合わせてヘッダーナビのスタイルを変える時の記述。

過去の案件なので確かな記憶ではないのですが、下記サイトを参考にしたと思います
[スクロールに合わせてヘッダーを変化させる](https://rfs.jp/sb/javascript/js-lab/resize-header-scroll.html)

スクロールに合わせてヘッダーを変化させるのはPC時のみ。
`class="smaller"`の付与でスタイルが変化します。
あと、別の要件ですが、スマホ時にドロワーナビが表示された時の
背景色を変えたかったので一緒に記述しています。

```javascript:jQuery

  $(function init() {
    var px_change   = 100;
    var w = $(window).width();
    var x = 768;

    if (w >= x) {
      window.addEventListener('scroll', function(e){
        if ( $(window).scrollTop() > px_change ) {
            $("nav").addClass("smaller");
        } else if ( $("nav").hasClass("smaller") ) {
            $("nav").removeClass("smaller");
        }
      });
    } else {
        $('.navbar-toggler').on('click', function(){
        var nav = $('nav');
        var navbg = nav.css('background-color');
          if ( navbg == 'rgba(0, 0, 0, 0)') {
              nav.css({'background-color': 'rgba(0, 0, 0, 0.9)',
                      'transition-duration':0});
          } else {
              nav.css({'background-color': 'rgba(0, 0, 0, 0)',
                      'transition-duration':'.4s'});
          }
        });
      }
    });
window.onload = init();
```
通常のナビゲーションのCSSを記述し、
`class="smaller"`を付与した場合のCSSも別に記述します。

一応HTML。Bootstrapで構築してます

```html:HTML
  <nav class="navbar navbar-expand-lg navbar-dark fixed-top">
  <a class="navbar-brand" href="#"></a>
   <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
   <span class="navbar-toggler-icon"></span>
   </button>

   <div class="collapse navbar-collapse" id="navbarSupportedContent">
    <ul class="navbar-nav mr-auto container">
     <li class="nav-item active"> 
      <a class="nav-link" href="index.html"><img src="img/logo.svg" width="30" height="33" alt="ロゴ"></a>
     </li>
     <li class="nav-item active">
        <a class="nav-link" href="html/page_A.html">PAGE A</a>
     </li>
     <li id="navbutton"><a href="html/contact.html" class="button">CONTACT</a></li>
    </ul>
   </div>
  </nav>
```
非同期な処理をしている create Vue コンポーネントのテスト

### 前提条件
- バージョン情報
    - Vue 2.6.10
    - Jest 24.5.0

### TL;DR

DOMが絡むなら `$nextTick` , 絡まないなら `setTimeout` を使う。

### 実例

```test.vue
<template>
  <div id="piyo">
    {{ hoge }}
  </div>
</template>

<script>
export default {
  data() {
    return {
      hoge: '',
    };
  },
  async created() {
    this.hoge = await this.huga();
  },
  methods: {
    huga() {
      return new Promise((resolve) => {
        setTimeout(() => {
          resolve('it works');
        }, 100);
      });
    },
  },
};
</script>
```

```test.spec.js
import { shallowMount } from '@vue/test-utils';
import Target from 'test.vue';

test('DOMをチェックする時', async () => {
  const wrapper = await shallowMount(Target);
  wrapper.vm.$nextTick(() => {
    const val = wrapper.find('#piyo');
    expect(val.text()).toEqual('it works');
  });
});

test('dataをチェックする時', (done) => {
  const wrapper = shallowMount(Target);
  setTimeout(() => {
    expect(wrapper.vm.hoge).toEqual('it works');
    done();
  }, 200);
});
```

### 問題点
#### 1. `$nextTick` を使っている場合
mounted, Promise が resolve された時の2回チェックされることになり、テストには通るのですが `Error in nextTick: "Error: expect(received).toEqual(expected)` というエラー出てしまいます。。 参考文献にあるとおり、 `FlushPromises` を使えば解消するかもしれません（試してないです）。

#### 2. `setTimeout` を使っている場合
待つ時間は長めに確保しないとうまく動かないことがあります。例えば、私の環境では待つ時間を 96ms にすると、１回目はうまく動き、２回目はコケます（キャッシュが効いて２回目のテストがちょっと早く動作し始めるためと思ってます）。こちらは、 `huga()` をモックしてしまえば解消できます。

```test.spec.js
test('dataをチェックする時2', (done) => {
  const wrapper = shallowMount(Target, {
    methods: {
      huga: jest.fn().mockResolvedValue('it works'),
    },
  });
  setTimeout(() => {
    expect(wrapper.vm.hoge).toEqual('it works');
    done();
  }, 1); // 限りなく小さい値で良い
});
```

この場合、 `huga()` は Promise を返す関数なので、 `huga()` のテストも行ってあげるべきですが、Axios で API を叩いているだけな関数であればテストしなくてもよいかと（システム境界の外側なので）。Promise を返す関数であれば [Jest でちゃんとテストできます](https://jestjs.io/docs/ja/asynchronous)。

### 参考文献
https://vue-test-utils.vuejs.org/ja/guides/testing-async-components.html
Azure DevOps (旧VSTS) でGitが使えなくなったときの対処 (Mac × Sourcetree × Azure DevOps)

「Mac × Sourcetree × Azure DevOps (旧VSTS)」でGitを使っているデザイナーです。
Gitのpullもpushもできなくなったのですが、無事解決しました。

# 結論
Sourcetree側で、以下のようにGitのURLを書き換えると、再びGitが使えるようになりました。

```
変更前：  
<組織名>@vs-ssh.visualstudio.com:v3/<プロジェクト名>

変更後：
git@ssh.dev.azure.com:v3/<組織名>/<プロジェクト名>
```

# 原因 (推測です)
VSTS (Visual Studio Team Services) → Azure DevOps
というように、「MicrosoftのGitのサービス」の名称が変わり、合わせてURLも変更される移行期間のゴタゴタに巻き込まれたのでは、と推測します。 
2019年5月9日時点で、Azure DevOps (旧VSTS) のURLは以下の2つが存在する状態のようです。

```
旧：https://<組織名>.visualstudio.com
新：https://dev.azure.com/<組織名>
```

# まとめ

当記事は、Azure DevOps (旧VSTS) × Sourcetree を使用しているときに生じる問題だと認識しています。Macでしか確認していないので、Windowsで発生するかは確認していません。

GitLab、GitHub、BacklogのGitを使ってきましたが、GitのURLが変わるというのは初めて経験しました。GitのURLが変わるということは、よくあることなのでしょうか?

エンジニアは問題なくGitを使えていて、デザイナー側だけで「なぜかGitが使えない」問題が生じたときは、使っているSourcetreeなどのツールを調べてみるとよさそうですね。
メモ　Dockerfileでイメージを作り、プライベートリポジトリにpushするまで

あらかじめ、Dockerfileを作ったディレクトリに移動しておく。

<pre>
$ sudo docker build -t sample:0.0.1 .
</pre>
実行完了後は、以下のコマンドでイメージを確認できる
<pre>
$ sudo docker images
</pre>

プライベートリポジトリにpushする名前にする。
<pre>
$ sudo docker tag sample:0.0.1 (プライベートリポジトリのIP：ポート)/sample:0.0.1
</pre>

プライベートリポジトリにpush
<pre>
$ sudo docker push (プライベートリポジトリのIP：ポート)/sample:0.0.1
</pre>

以下のコマンドで、レジストリの中にあるアプリ一覧が見れる
<pre>
$ curl https://localhost:5000/v2/_catalog --insecur
</pre>

以下のコマンドで、リポジトリの中のsampleアプリケーションのタグ情報が得られる。
自己証明を使っているため、insecurオプションを付与する。
<pre>
$ curl https://localhost:5000/v2/sample/tags/list --insecur 
</pre>
UnityPackage を展開・解凍（中身を確認する）

# はじめに

*こんにちは、のんびりエンジニアのたっつーです。*
*[ブログ](https://www.fast-system.jp/)を運営しているのでよろしければ見てください。*

Unityのパッケージ（～.unitypackage）って***１つのファイルに様々なファイルを含まれていて扱いが楽なので便利***だな～って思いますよね。
だいたいこういうファイルって***.zipで圧縮***されている事が多いのですが。

～.unitypackage を ～.zip にリネームしても読み込めません。
解凍しようとしても ZIP じゃない！！って怒られます、このファイルの正体ってなんでしょうか。

# extractunitypackage

実は便利なツール「[extractunitypackage](https://github.com/gered/extractunitypackage)」を紹介したかったんです。

ダウンロードしてきて、以下のコマンドを実行すると～.unitypackage が解凍できちゃうんです。すごいですね。

```shell
extractunitypackage.py input_file ＜output_path＞
```

# ちょっと使ってみた

使ってみましたが、すばらしいですね。
ちゃんと、ファイルの中身が展開されました！

```shell
f6b1eb436e400704ab6e2ad6eff29f4b => Assets/VRM/DepthFirstScheduler/LockQueue.cs
f8ed5cb82dd13bf43a1556b24a6d13a0 => Assets/VRM/UniVRM/Scripts/Format/VRMExportObject.cs
fb1d83ccd68b93c47821000b53471eae => Assets/VRM/UniJSON/Scripts/JsonSchemaValidator/JsonNumberValidator.cs
fcb56a7eb1db73c4cb9ea1689635b246 => Assets/VRM/UniVRM/Editor/BlendShape/BlendShapeClipEditorHelper.cs
fe59508ed49a5db4287c74e0061799b3 => Assets/VRM/UniVRM/Scripts/Format/glTF_VRM_FirstPerson.cs
ff15446e31b14ac409251c931b7c2038 => Assets/VRM/UniJSON/Scripts/ActionDisposer.cs
```

![image-214.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/227880/fbf9dfaa-bed8-4f9f-9b87-d720def94773.png)

![image-215-768x373.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/227880/fbcf78c8-ced3-7c3f-00c2-66677e475c70.png)

# フォルダの圧縮形式は？

このソースコードの中身を簡単に確認してみましたが、どうやら ～.tar.gz で圧縮されているようです。

解凍ソフトを使って中身を確認してみますと、、、あかん GUID みたいな英数字の羅列でまともに読めないですね。
おとなしく「extractunitypackage」を使うのが無難かと思われます。

![image-216.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/227880/7bfeb43a-3a64-fad3-1966-4560ef473bfb.png)

# 終わりに

また、１つUnityに詳しくなりまいた。
***新しい情報をインプットするのって楽しい***ですよね！！

*よければ ブログ「[初心者向けUnity情報サイト](https://www.fast-system.jp/)」の方にも色々記載しているのでぜひご参照いただければと思います。*
Nordic UART 通信する Andorid BLE アプリをつくる (blecommunicator編) 


# BLEアプリ(1)

hiramine.com の素晴らしい step-to-step 解説ページ 「BLE通信ソフトを作る ( Android Studio 2.3.3 + RN4020 )」があります。
https://www.hiramine.com/programming/blecommunicator/index.html
こちらで作成されたプログラム「blecommunicator」を基にして、Nordic UART通信に対応させます。


アプリのソースは
https://github.com/nobukihiramine/BLECommunicator
で公開されています。
ライセンスは Apache License 2.0 なので、これを書き換えて自分のアプリを作ることが可能です。

# 改造

オリジナルのプログラムはマイクロチップ社のRN4020と接続しますが、Nordic UART 対応にするにはソース中のUUIDを書き換えます。


app/src/main/java/com/hiramine/blecommunicator/MainActivity.java
から、以下の箇所を変更します。

```

< 	private static final UUID UUID_SERVICE_PRIVATE         = UUID.fromString( "FF6B1160-8FE6-11E7-ABC4-CEC278B6B50A" );
< 	private static final UUID UUID_CHARACTERISTIC_PRIVATE1 = UUID.fromString( "FF6B1426-8FE6-11E7-ABC4-CEC278B6B50A" );
< 	private static final UUID UUID_CHARACTERISTIC_PRIVATE2 = UUID.fromString( "FF6B1548-8FE6-11E7-ABC4-CEC278B6B50A" );
---
> 	private static final UUID UUID_SERVICE_PRIVATE         = UUID.fromString( "6e400001-b5a3-f393-e0a9-e50e24dcca9e" );
> 	private static final UUID UUID_CHARACTERISTIC_PRIVATE1 = UUID.fromString( "6e400003-b5a3-f393-e0a9-e50e24dcca9e" ); // CHARACTERISTIC_TX_UUID for Read
> 	private static final UUID UUID_CHARACTERISTIC_PRIVATE2 = UUID.fromString( "6e400002-b5a3-f393-e0a9-e50e24dcca9e" ); // CHARACTERISTIC_RX_UUID for Write
```
docker-compose down しないと落ちたコンテナが残っているの嫌じゃない？




# 前フリ

たまに ``docker system prune`` そして ``docker volume prune``するのが日課になっている``docker``使いの人は多いんじゃないでしょうか。
私はそうです。
この一回一回はたいしたことないけど、めんどくさい作業をなくしましょう。


# シグナルを捕まえて後処理する

ぶっちゃけそんだけです。

Ctrl+C した時の``SIGINT``、killした時の``SIGTERM``、プロセス再起動時の``SIGHUP``あたりを捕まえとけばいいんじゃないでしょうか。

```start_docker.sh

#!/bin/sh

down() {
    echo "clean up containers..."

    docker-compose down
    docker volume prune #この辺はお好みで

    echo "done."
}

trap down HUP TERM INT;

echo "Start up containers (press Ctrl+C for stop) ..."

docker-compose up

```

trapで、``SIGINT``,``SIGTERM``,``SIGHUP``を捕まえてdown()で定義した後処理を実行します。

これ結構応用が効いて、``docker-entrypoint.sh``の中で``trap``してやればコンテナが落ちた時の後処理もかけます。

ではよい ~~trap~~ **docker** ライフを。
Nordic UART 通信する Andorid BLE アプリをつくる (準備編)

BLEボード「アオノドン」に接続する、Androidアプリを作ります。

※「アオノドン」は Nordic nRF52840を使ったBLEトレーニングボード。

「アオノドン」では Nordic UART Service を動かし、データの送受信を行います。


# 環境

- Android Studio3.2.1
- 開発PC：Ubuntu16.04
- 実機：HUAWEI P20 lite
 - Android Studio上のエミュレータではBLEは使えないので、実機を接続して実行／デバッグする必要があります。



# 練習
「初めてのアプリの作成」
https://developer.android.com/training/basics/firstapp/?hl=ja
を基にして、動作確認を兼ねて練習を行います。

File-New-New Projectで新規プロジェクトを作ります



![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139524/24ec1a58-d43f-5e97-1f63-5e12eb24cbbd.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139524/fc822314-992c-af1f-5bfa-2aa565df00af.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139524/1cb56832-593d-7b3d-a3e7-84676bbbf233.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139524/b46d7702-8c32-9ef8-012f-46d65aacc855.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139524/d59a1f1a-1c0e-8bfe-e5de-e19bf42f6475.png)


画面上の緑の三角ボタンを押すと実行します。
開発PC の USBポートに Android 端末を繋げて実行環境とします。
このテストではエミュレーターで実行するのでもいいのですが、次の段階のBLEを使ったプログラム実行はエミュレーターではできないためです。


これで、コンパイルすると Hello,worldが出てきます。


Nordic UART 通信する Andorid BLE アプリをつくる (1)に続きます
【ServiceNow】デフォルトでリスト表示をGroup By する方法

# 1.はじめに
今回はServiceNowの各アプリケーションのリスト表示をGroup By形式で表示させる小技をご紹介します。(ServiceNow的には「グループ xxx表示」しているのと同じ状態)
今回はインシデント管理の「すべて」モジュールを例にいじってみます。

# 2.設定方法
①左ペインにあるインシデント管理の「すべて」モジュールの鉛筆マーク(モジュールの編集)をクリックします。
![001.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/340027/c3ed8f1a-69a1-8df1-2eec-750c4618afb2.png)

②「リンクタイプ」タブの「引数」に「^GROUPBY(列名)」を追加します。
　今回の例では「ステータス」列でGroup byしてみますので「^GROUPBYstate」となります。
![004.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/340027/1c593ff5-f371-cfec-6c34-c64fdee67204.png)

③設定が反映されると、以下のようにリスト表示が指定した列(今回はステータス)で「Group by」された状態になります。
![005.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/340027/71d83cb5-8594-1b5a-97e3-babbd95fcaf5.png)

#3.２種類の展開方法
グループ集約されたデータを展開する方法に以下の2種類があり、表示が微妙に異なります。
用途に応じて使い分けてください。

## 3.1 「グループを展開」で展開する
レコードの左側にある三角を展開すると、そのグループだけ展開されます。
![007-1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/340027/06a7fc22-eac0-e19f-8067-e80d90b85396.png)
　　↓
![007-2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/340027/32aba97e-fab6-0cac-107f-90475a3c4312.png)

## 3.2 「このグループのみを表示」で展開する
各グループのリンクをクリックすると、その条件でフィルタがかかったリストページが表示されます。
![008-1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/340027/0eed993f-79af-5179-6b15-844194bbb111.png)
　　↓
![008-2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/340027/c9b9bac0-d5d3-4558-2ec7-b0cbd352451b.png)

# 4.補足
今回紹介の設定を、「既にリンクタイプの引数に設定が入っているモジュール」(例えば、インシデント管理の「オープン」とか)でやってみてもグループ集約された表示にはなりませんでした…。
実際に使える場所は限られるかもしれませんね。

# 5.参考URL
[Saving a "Group By" View and set it as default for all user.](https://community.servicenow.com/community?id=community_question&sys_id=8efb8325db9cdbc01dcaf3231f96194a)
Azure Active Directory のユーザーを LINE WORKS に連携する

#Azure AD のユーザー情報を PowerShell 操作で LINE WORKS に一括で連携

LINE WORKS は SAML でシングル サインオンでき、Azure Active Directory を IdP とすることが可能です。

こちらの記事で Azure Active Directory と LINE WORKS の SSO 時に Authenticator によるパスワードレス認証を利用する手順を紹介しました。

TITLE: LINE WORKS + Azure AD + Authenticator でパスワードレス認証
URL: https://qiita.com/iwaohig/items/f678a4006fc1a894d855

また、Azure AD と LINE WORKS の SSO の設定手順は、@tokotan のこちらの記事に、とても分かりやすくまとまっています。
TITLE: AzureADでLINE WORKSにSSO(SAML)する方法
URL: https://qiita.com/tokotan/items/4a8c0c71ed113884e23d

なお、SSO を設定した際の LINE WORKS 側のユーザーは、別途に登録が必要です。通常は管理画面から GUI 操作で個別に登録するか、CSV または XLS ファイルをインポートします。

ここでは、Azure AD のユーザー情報を PowerShell 操作で LINE WORKS に一括で連携する手順の一例を説明します。

#Get-AzureADUser コマンドレット

Get-AzureADUser コマンドレットで、Azure AD 上のユーザーを取得できます。

TITLE: Get-AzureADUser
URL: https://docs.microsoft.com/en-us/powershell/module/azuread/get-azureaduser?view=azureadps-2.0

こちらに記載のあるようにパラメータで、取得するユーザーの条件を設定できます。

本記事では一例として "Sales" ではじまる部署に所属のユーザーを取得します。

```
Get-AzureADUser -Filter "startswith(Department,'Sales')" 

```

#LINE WORKS メンバー追加 API

LINE WORKS の組織連携 API でメンバー追加できます。

TITLE: メンバー追加
URL: https://developers.worksmobile.com/jp/document/100300501?lang=ja

Inveke-RestMethod コマンドレットで PowerShell から LINE WORKS の組織連携 API を実行します。

ここでは、必須パラメータのみ利用しています。

UserPrincipalName -> email
Surname -> name.lastName
GivenName -> name.firstName

Get-AzureADUser コマンドレットで取得したユーザーの UPN、姓、名の情報を LINE WORKS の属性値に連携しています。

Azure AD の SSO を想定したスクリプト例を記載していますが、SSO でない場合には上記に加えて privateEmail パラメータの指定が必要です。

スクリプト例は以下のとおりです。

```
Get-AzureADUser -Filter "startswith(Department,'Sales')" | 
%{
$header = New-Object "System.Collections.Generic.Dictionary[[String],[String]]"
$header.Add("Content-Type","application/json; charset=UTF-8")
$header.Add("consumerKey","<Server API Consumer Key>")
$header.Add("Authorization","Bearer <Server Token>")
$json = @"
{
"email": "$($_.UserPrincipalName)",
 "name": {
 "lastName": "$($_.Surname)",
 "firstName": "$($_.GivenName)"
 }
}
"@
$Uri = "https://apis.worksmobile.com/r/<API ID>/organization/v2/domains/<domainID>/users/$($_.UserPrincipalName)"
Invoke-RestMethod -Uri $Uri -ContentType 'application/json' -Method Post -Header $header -Body $json
}

```

#動作確認

スクリプト実行後に管理画面でユーザーが作成されていることを確認します。
また、それぞれのユーザーがログイン可能であることを確認します。
Apache .htaccess検証ページ

# 本記事のターゲット
・Apacheの.htaccessを設定する方
・設定、検証をすぐにしたい方

# 検証サイト
[htaccess](https://htaccess.madewithlove.be/)

# 使用方法
①真ん中のテキストボックスにhtaccessの設定を入力。
②一番上のテキストボックスにURL入力
③必要に応じてOption入力
④Testボタン押下
⑤Output urlに設定反映後のURLが表示される。

![1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/254711/f4a2ca4c-783d-acb8-84ef-3ba05de05c57.png)