OmniAICreator/Qiita-1.07M huggingface dataset:
python3をatomで実行する方法を教えてください

python３をatomで実行しようとしたところ、このようなエラー（下記記載）が出てきました。超初心者なため、英語を読んでも意味がわからず混乱しております。どうか対処法をおしえてください。

エラー文
Unable to find command: /Library/Frameworks/Python.framework/Versions/3.8.2/bin/Python3
Are you sure PATH is configured correctly?

ENV PATH: /Library/Frameworks/Python.framework/Versions/3.8/bin:/Users/私のuser name/.pyenv/shims:/Users/私のuser name/.pyenv/bin:/Library/Frameworks/Python.framework/Versions/3.8/bin:/Library/Frameworks/Python.framework/Versions/2.7/bin:/Library/Frameworks/Python.framework/Versions/3.6/bin:/Library/Frameworks/Python.framework/Versions/3.6/bin:/Library/Frameworks/Python.framework/Versions/3.6/bin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin:/Library/Frameworks/Python.framework/Versions/3.8/bin:/Users/私のuser name/.pyenv/shims:/Users/私のuser name/.pyenv/bin:/Library/Frameworks/Python.framework/Versions/2.7/bin:/Library/Frameworks/Python.framework/Versions/3.6/bin

Error: spawn /Library/Frameworks/Python.framework/Versions/3.8.2/bin/Python3 ENOENT
    at Process.ChildProcess._handle.onexit (internal/child_process.js:232:19)
    at onErrorNT (internal/child_process.js:407:16)
    at process._tickCallback (internal/process/next_tick.js:63:19)
Hyper-VとVirtualBoxの共存について

Docker desktop for windowsとGenymotion同時に使いたいんだよぉ！

## きっかけ

Native技術に全く無知な私ですが突然React Nativeに興味が湧いたので @naoshihoshi さんが著した『サンプルコードで作りながら学ぶReactNative実践入門』[^1]を読みました。

環境構築の章を読み、[Genymotion](https://www.genymotion.com/)というAndroidエミュレータを入れる段階に至ったタイミングでこのGenymotionはVirtualBoxを必要としていることに気が付きました。

しかし私のWindows開発機はdocker desktop for windows用(あと色々遊び用)にHyper-Vが有効化されています。

私の知識ではHyper-VとVirtualBoxの共存は御法度なのでここで躊躇してしました[^2]・・・が、そういえば今のHyper-Vはnestできるのでもしかしたら可能なのでは？と考え調査開始。

この記事はその調査結果をまとめたものになります。

環境は以下の通りです。

- Windows 10 Professional build 18363 + Microsoft-Hyper-V 有効化
- VirtualBox 6.1.4
- Genymotion 3.0.4

## Hyper-VとVirtualBox

以前のWindowsではHyper-VとVirtualBoxの共存が不可能でしたがVirtualBox v6からは共存が可能になったことが[公式のCHANGELOG](https://www.virtualbox.org/wiki/Changelog-6.0)に記載されています。

> Added support for using Hyper-V as the fallback execution core on Windows host, to avoid inability to run VMs at the price of reduced performance

ところが『Hyper-V VirtualBox 共存』で検索してみるとできなさそうなオーラが漂ってきます。

実際に試してみるとVM自体は立ち上がることがわかりました(Ubuntuをinstallしようとすると成功したりしなかったりで確かに微妙な挙動ですがArch Linuxのinstallでは問題なさそうでした)。

私の環境ではVirtualBox Forumの[このスレッド](https://forums.virtualbox.org/viewtopic.php?f=6&t=90853)に記載されている通り、fallbackが正常に働いているようです(CPUインジゲーター部分に亀マークが出ています)。

## Genymotionは問題なさそう？

Pixel 3を選びStart...するとVMは起動するものの起動時の `Android` の文字でフリーズする現象に。VirtualBoxからターミナル画面を見ると一部のデバイスを正常に読み込めていない様子だったので再起動すると無事Androidのホーム画面が表示され、経由でのました。

その後もいろいろ試しましたがadb経由のアプリの配信もできたので問題はなさそうです。初期化が不安定な問題は解決しませんでしたが・・・。

## まとめ

一部挙動に問題が起きるかもしれないが、Hyper-VとVirtual Boxの併用はできる。

[^1]: 本題とずれるため、こちらに記載させていただきますがこちらの本はとても勉強になりました。特に第二章は具体的な事例を元になぜReactNativeを採用するに至ったのかを丁寧に解説されているので技術選定に困ったときに参考にできそうです。自分のようなNativeアプリ全く知らないマンにはぜひお勧めしたい1冊です(環境構築の際 `adb` にpathを通さないとexpo projectで `yarn start` しても正常に動かないことは少しハマってしまいましたので一応メモ)。

[^2]: 一応Kernel起動時のパラメータでHyper-Vを切る or 余っているライセンスでもう一つWindows 10をインストールする等々方法はないことはないのですが、前者はその状況で`Enable-WindowsOptionalFeature  -Online -FeatureName Hyper-V` すると大変なことになり(実体験)、後者はBoot Loaderのentry数が増えて管理が大変(既に開発用・ゲーム用・Linuxとtriple bootしている)なのでできれば採用したくない選択肢でした。
Firebase  Realtime Database を Cocos Creatorで使う。

##はじめに
初投稿です。こんにちは。
昨今ではクロスプラットフォームのゲームエンジンといえば Unity 一択で、
次点でどうにかUEが出てくる程度じゃないかと思います。
そんな中 cocos creator に手を出したのはいいものの、情報が少なく割と困ったので、備忘録がてら投稿します。

##したいこと
cocos creator で開発中のアプリで Firebase の Realtime Databaseにアクセスする。

##方法
cocos creator は Node.js を利用しているので基本的には npm を利用する。
ただし、この方法ではAndroid上では動作しなかった。(iOSやWeb上では問題ない)
仕方なくAndroid StudioでFirebase Databaseを導入し、それをJavaを通じて呼び出すという手法をとりました。

##npm install --save firebase
Cocos creator のプロジェクトフォルダでターミナル等を使って

```
npm install --save firebase
```
を実行する。
これについては以下の記事が非常に参考になりました。
[Cocos Creator を使って Firebase Authentication を実装する](https://noitalog.tokyo/cocos-creator-firebase-authentication/)

最初はうまくモジュールを読み込めていなかったのですが、Cocos Creator を再起動するとうまく読み込めたようです。
あとは Node.js でFirebase を利用するやり方で問題なく実行できます。
[Firebase を JavaScript プロジェクトに追加する](https://firebase.google.com/docs/web/setup?hl=ja)

##Android
Androidでは何故かモジュールを利用できません。Node.js の npm を利用しているという都合上、何か問題が起きているのかもしれないです。(把握できてない)
上記の記事では少なくとも Firebase Authentication については問題なく実行できていますが、自分の環境では Firebase Realtime Database は使用できなかったので仕方なく Java を直接利用することにしました。

まずはプロジェクトに Firebase を導入する必要があります。
[Android プロジェクトに Firebase を追加する](https://firebase.google.com/docs/android/setup?hl=ja)
そうして導入した Firebase Realtime Database を Java を通じて利用します。
cocos creator から javascript で Java を利用するには

```
jsb.reflection.callStaticMethod(className, methodName, methodSignature, parameters...)
```

を使用します。
[How to Call Java methods using JavaScript on Android](https://docs.cocos.com/creator/manual/en/advanced-topics/java-reflection.html)

具体的には org.cocos2dx.javascript に使いたい Java のパッケージを置き、それを javascript から呼び出すといった形です。最初は org.cocos2dx.javascript の場所がわからなかったので一応書いておくと、
/Project_Folder/build/jsb-default/frameworks/runtime-src/proj.android-studio/src/org/cocos2dx/javascript/
にあります。

そこに、

```FirebaseWrapper.java
package org.cocos2dx.javascript;

import android.util.Log;
import com.google.firebase.database.FirebaseDatabase;

public class FirebaseWrapper {
    private static FirebaseDatabase database=null;

    public static void init(){
        if(null==database){
            database=FirebaseDatabase.getInstance();
            Log.d("Firebase Wrapper","Firebase Initialized!");
        }
    }
}
```

みたいなものを適当にでっち上げました。
これを実行するには javascript 上で

```
jsb.reflection.callStaticMethod("org/cocos2dx/javascript/FirebaseWrapper","init","()V")
```

を呼びます。
なお ```result=jsb.reflection.callStaticMethod()``` は残念ながら引数、返り値ともに渡せるものが限られています。
具体的には、int, float, boolean, String しか渡せません。なので、配列などを渡すことはできません。一つずつ渡すなど何か工夫が必要です。

とはいえ一先ずこれで無事 Firebase Realtime Database にはアクセスできます。

##終わりに
今回、cocos creator を使って初めてアプリを作ったのですが、自分の技術不足もあり、正直とてもしんどかったです。
まだまだ情報不足の面が多く、基本的に英語か中国語の情報を漁るしかないので素人は手を出すべきでなかったと感じました。
ただそれゆえに情報が増えづらいといった面もあるので、未来の誰かか自分の為にもこの記事を投稿しておきます。

いろいろ勉強にはなりましたが次はたぶん素直に Unity を使うと思います。笑
AtCoder用Python3 個人メモ 高速化とか注意点

#文字列結合が遅い
pythonだと文字がイミュータブル(作成後に変更できない)ので、変更のたびにオブジェクトが再作成される。
そのため、文字列結合をループとかで繰り返し行う場合、ループごとに変更を行うと遅い。

```
s = ""
for i in range(10)
    s = s + str(i)

print(s)
```

そのため、

```
s = []
for i in range(10)
    s.append(str(i))

s= ''.join(s)
print(s)
```

例題
https://atcoder.jp/contests/abc158/tasks/abc158_d

参考
http://nobunaga.hatenablog.jp/entry/2018/03/19/081425

#リスト操作の注意点
内容的には同じだが、参照する回数を減らすために

```
for i in range(n)
    list[i] = list[i] +1

```

これで実行時間が一割くらい変わった

```
for i in range(n)
    list[i] +=1

```

```
    for i in range(1, n):
        for j in range(i+1, n+1):
                list[minCost] +=1

```

#listよりdict
dictがhashテーブルのためinとか使う際の速度が大きく違う。

https://atcoder.jp/contests/abc065/tasks/abc065_b
Andorid Studioのインストールガイド

# 目次
- インストーラのダウンロード
- インストール
- Android Studioの初期設定

## インストーラのダウンロード
以下のリンクからAndroid Studio 3.6.1のインストーラをダウンロードする。
https://developer.android.com/studio
## インストール
- ダウンロードしたインストーラをクダブルリックする。
![0002.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/75242963-db90-df07-a835-c6789571cdd5.jpeg)

- Android Studioのインストールポップアップが表示されたら、「Next」をクリックする。
![0004.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/0a129391-494a-3a16-b65a-961808fd5352.jpeg)


- 「Next」をクリックする。
![0002.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/082546f6-a419-04b0-2966-b83ca4a6d845.jpeg)

- 「Next」をクリックする。
![0003.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/a2be1df1-7393-f9f3-115e-241f34ad05a8.jpeg)

- 「Install」をクリックする。
![0004.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/1b78ac7a-120b-e3f5-5e79-e7fe30ff5a76.jpeg)

- インストールしているのを待って、完了後「Next」をクリックする。
![0005.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/f1999dec-e331-8ee7-f722-c43b12b10d7c.jpeg)
![0006.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/5ed271be-9746-52c4-ea86-d18582dd55ea.jpeg)
- 最後は「Finish」をクリックする。
![0007.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/04ca702d-2cd5-73b8-39d0-c906188fec62.jpeg)

## Android Studioの初期設定
- 上記のインストール完了後、以下のインポート設定のポップアップが表示されたら、「OK」をクリックする。

![0008.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/44d867c5-db32-5ed5-e455-f28c170e3e3e.jpeg)

- Android Studioがロードされる。
![0009.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/d9f0464a-0c48-5ca0-9c5b-9c70ffcc64d6.jpeg)

- 「Next」をクリックする。
![0010.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/84a5ca2d-c21b-d3a7-e97d-7c474a21b75a.jpeg)

- 自分の好きなテーマを選び、「Next」をクリックする。
![0012.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/6eaf9ec8-007c-206c-91d1-abba3759b432.jpeg)

- 設定が完了後、「Finish」をクリックする。
![0013.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/6ba6f819-324c-780c-8f0f-5a7a3503d3c9.jpeg)
![0014.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/c203e927-31f5-a3f6-a159-586bcdf16e22.jpeg)

- Android Studioの必要なコンポーネントがインストールされる。
![0015.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/73e1d27d-4d99-ddb3-fa2c-ccf118de63cb.jpeg)

- インストールが完了後、「Finish」をクリックする。
![0016.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/1fe8bc5f-b5ee-8350-a64b-6e4ca16a3b9e.jpeg)

- これでAndroid Studioの初期設定が完了で、アンドロイドアプリケーションが作成出来る状態になる。
![0017.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/602725/14cd4d29-29f8-7acc-9616-c185ce47decb.jpeg)
Android開発初心者の自分が躓いたところ

# その1　SDKの差異
- Conflict with dependency 'com.android.support:support-annotations'. Resolved versions for app (26.1.0) and test app (27.1.1) differ


どうやらSDKのヴァージョンの差異が原因のよう。

以下をbuild.gradle(Module:app)のdependencies内に追記。

```gradle
androidTestCompile 'com.android.support:support-annotations:27.1.1'
compile 'com.android.support.test:runner:1.+'
```

#その2　エミュレーターが動かない
- 色々解決方法があるようだが、実機で確認したほうが手っ取り早い。
動かなければ諦めろ。

#その3　実機を認識しない
- スマホ側から設定→デバイス接続→USBの設定を確認し、「充電のみ」が設定されているので
「ファイルを転送」or 「写真を転送」に切り替える。

　併せて、たまにSDKManagerから「Google USB Driver」をインストールし忘れることがあるので
　必ずインストールしておくこと。

#その4　メインのプログラム（javaとかkotlinとか）でRがエラーになる
- 結構単純で、レイアウトを編集するstring.xmlやstyle.xml上にエラーが1つでも存在すると、ソース上のRは全てエラーになってしまうので、そちらで原因を探る。設定したidがメインプログラムと紐づいていないことが結構あった。スペルミスが大半。

#最後に
- 環境構築で時間がかかり、実際のコードもいつものJavaより難しい気も。
Unityを用いて、ARアプリの開発もしてみたい。

#参考にしたサイト
- http://nuruyu.hatenablog.com/entry/2018/05/12/232000
- https://www.bioerrorlog.work/entry/android-studio-detection
- http://ayuzaki.hatenablog.jp/entry/2015/07/01/001425
DockerHub Dockerイメージのタグ一覧を取得するコマンドを作る

Dockerイメージの検索は `docker search` コマンドが用意されているがイメージのタグ情報は検索できないようです...(困惑)

タグを取得するAPIは提供されていたのでそれを使ってDockerイメージのタグ一覧を取得します。

## 環境

- Mac

## Dockerイメージの検索

```
$ docker search ubuntu
NAME                                                      DESCRIPTION                                     STARS               OFFICIAL            AUTOMATED
ubuntu                                                    Ubuntu is a Debian-based Linux operating sys…   10614               [OK]
dorowu/ubuntu-desktop-lxde-vnc                            Docker image to provide HTML5 VNC interface …   404                                     [OK]
rastasheep/ubuntu-sshd                                    Dockerized SSH service, built on top of offi…   243                                     [OK]
consol/ubuntu-xfce-vnc                                    Ubuntu container with "headless" VNC session…   211                                     [OK]
ubuntu-upstart                                            Upstart is an event-based replacement for th…   106                 [OK]

...
```

## 前提条件

- curl, jq コマンドが必要です。

```
$ brew install jq
```

## イメージのタグを取得する

ubuntu イメージのタグは下記のAPIから取得できます。

- https://registry.hub.docker.com/v1/repositories/ubuntu/tags

イメージ名のところを引数にしてコマンドを作れば良さそうです。

```shell-session:.bash_profile
function docker-tags {
  curl -s https://registry.hub.docker.com/v1/repositories/$1/tags | jq -r '.[].name'
}
```

自作した `docker-tags` コマンドを実行してみる。

```
$ docker-tags ubuntu
latest
10.04
12.04
12.04.5
12.10
13.04
13.10
14.04
14.04.1
14.04.2
14.04.3
14.04.4
14.04.5

...
```

良い感じです☺️
Vue.jsの$emitでpromiseしたいでござるの巻

先日書いた記事で、出来るだけtemplateで$emitした方が良いと書きました。

```vue
<template>
 <dl>
  <dt>名前入力</dt>
  <dd>
   <input
    type="text"
    @input="$emit('customEvent', hoge('hogehoge'))"
   />
  </dd>
 </dl>
</template>
```

>こういう感じにemitは直接templateから指定して、引数からメソッドを呼んで必要に応じて成型した戻り値を親コンポーネントへ送ります。

みたいなことを書いたわけですが、$emit時に返す値がAPIの読み込みなどの非同期な場合に上手くいかない事がありました。

なのでそういう場合は

```javascript
hoge(e){
  axios.get('fuga', e).then(res => {
    this.$emit('fuga', res.data)
  })
}
```

みたいな感じに、イベントから呼び出した関数内でemitするパターンになってしまうのですが…。

```javascript
async hoge(e){
  const param = await axios.get('fuga', e).then(res => res.data)
  // 実際にはここでparamの加工とかする
  return param
}
```

とか言う感じでpromiseで返してあげると

```vuejs
<template>
  <div id="app">
    <SampleComponent @customEvent="fuga" />
  </div>
</template>

<script>
export default {
  components: {
    SampleComponent 
  },
  methods:{
    fuga(e){
      e.then(result => alert(result))
    }
  }
}
</script>
```

親側で受け取った際に、引数にPromiseオブジェクトで帰ってくるので、引数に`then`とか付けれました。
まぁ、よく考えれば、そりゃそうだろうって感じですが…。

さらにこんな感じにすると、もっといい感じに！？

```vue

<script>
export default {
  components: {
    SampleComponent 
  },
  methods:{
    async fuga(e){
      alert(await e)
    }
  }
}
</script>
```

ちなみに、Promiseオブジェクトで送るのがなんか嫌でこう書いたら動くんですが、vue側でエラーを出してきます。


```html
<button @click="hoge().then(res => $emit('hogehoge', res))">TEST2</button>
```

><font color="red">[Vue warn]: Property or method "then" is not defined on the instance but referenced during render. Make sure that this property is reactive, either in the data option, or for class-based components, by initializing the property.</font>

こんな感じのエラーになりました。英語に疎いのでちょっと意味が…。

とまぁ、何の役にも立ちそうにない小話です。

できれば$emitがpromiseにも対応してくれればいいなぁと思った今日この頃です。
仙台CTF 2019 Lab7.マルウェア解析本番 100

#問題

http://ctf.sectanlab.jp/2019/

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/0155b081-1e6d-1ae7-060c-6fdf786ec1ef.png)

#解いてみた

bintext使います。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/34091d24-0c04-0928-bdba-a96787d8a5bc.png)

それっぽいのがありました。
入力してみるとこれが答えでした。
【VisualStudio】VisualStudioで自作コメント挿入したい

よく使用するコメントとかC#のXMLドキュメント的な感じで挿入したい場合
VSのコードスニペット機能を使います
スニペットのファイルがあればいいんですが今回はVS上で作成～反映まで行います

# 手順
### １．作成
「ctrl+N」で新しいファイル作成
XMLファイルを選択
![xmlfile.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/216261/b704fa43-c816-2336-28a7-7e4cfc4401f7.png)

### ２．コード
```c#:sample.snippet
<?xml version="1.0" encoding="utf-8"?>
<CodeSnippet Format="1.0.0">
	<Header>
		<Title>mycomment</Title>
		<Description>自作コメント</Description>
		<Shortcut>com</Shortcut>
	</Header>
	<Snippet>
		<Declarations>
			<Literal>
				<ID>comment</ID>
				<Default>コメント</Default>
			</Literal>
		</Declarations>
		<Code Language="csharp">
			<![CDATA[/// <summary>$comment$</summary>$end$]]>
		</Code>
	</Snippet>
</CodeSnippet>
```
細かい記述の説明は省きますが

`<Shortcut>com</Shortcut>`
挿入時の入力文字

`<Code Language="csharp">`
どの言語ファイルに反映させるか
上記の場合はC#のファイルで挿入可能になります
その他のファイル設定などはVSのドキュメントに書いてあります
https://docs.microsoft.com/ja-jp/visualstudio/ide/code-snippets-schema-reference?view=vs-2019

`<![CDATA[/// <summary>$comment$</summary>$end$]]>`
挿入する文字列

改行はそのまま反映されます
同じくタブなども反映されるのでインデントが気にはなるけども

```c#:sample.snippet
...
		<Code Language="csharp">
			<![CDATA[/// <summary>$comment$</summary>
/// <remarks>備考</remarks>$end$]]>
		</Code>
...
```

### ３．保存
「ctrl+S」で保存
ファイル保存ダイアログが開くので
拡張子を.snippetに変更して保存
保存場所はどこでもいいです
![snippetfile.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/216261/54f9085a-0ad6-5e6e-a1ff-5ea73f722971.png)

### ４．インポート
VS上部のメニューから
「ツール > コードスニペットマネージャ」でダイアログ開きます
「インポート」ボタンから先ほど作成した.snippetのファイルを選択
スニペットの場所の選択ダイアログがでますがデフォルトの「My Code Snippets」にチェック付いてれば問題ないです

### ５．確認
これで反映されたので適当なファイルでショートカット文字（この記事の場合は`com`）を入力して「tab」を2回（or 1回）押してみてください
`<![CDATA[...]]>`
ここに記載した文字が挿入されたかと思います

今回はコメントとして挿入しましたが、よく使う処理でもなんでも活用できるかと思います
仙台CTF 2019 Lab6.マルウェア解析練習3 100

#問題

http://ctf.sectanlab.jp/2019/

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/2fc6c3eb-9344-a468-20f6-16c17d5a3020.png)

#解いてみた

たぶんないけどbintextで見てみます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/a9dbd4e3-02fa-96ea-f4ac-b854d0e4fb66.png)

それらしきものがあったので入力してみるとこれが答えでした。
自己責任でPHP7のcount()関数を改造してエラー抑制する

# Parameter must be an array or an object that implements Countable

古いPHPのプログラムをPHP7.2以降で動かして、上記エラーの山に呆然となった人も多いことでしょう。
私もそうです。

プログラムをgrepしてみたら、数100か所でcount()関数が使われていました。
それらに全部countableな値が渡されているのかチェックするのは苦痛でしたし、書き換えの事を考えると吐きそうです。

新しい関数を作ったとしても、count()関数を使っている箇所全てを書き直さないといけません。

一括置換をかけたいのですが、困ったことに
**select count(*) from…**
とか恐ろしい記述があったりします。

php.ini等で、warning抑制という荒業もありますが、
私はその環境で関発出来る自信がありません。

try～catchで捕捉しようかとも思いましたが、
既存のファイル構造上めんどくさそうでした。

てか、なんで互換モードとかないんだろう…。

ネットで検索しても、「これだ！！」という解決策は見つかりませんでした。

というわけで・・・

## 自己責任でPHP本体を改造します！！

これは

- PHPのバージョンは、7.4.3
- 同じサーバで他のWEBサイトが動いてないこと
- PHPがソースコードからのコンパイルでインストールされていること
- トラブルが起きても他人のせいにしないこと

が、前提条件となっています。

条件を満たせない場合は、
素直に「is_countable」で検索してください。

エラーを出さないこともできるのですが、今回は
**E_WARNING** を **E_NOTICE** に変える改造をします。
別に**E_DEPRECATED**でもいいと思います。
php.ini等でエラー出力を制御できればいいです。

対象ファイルは、

- Zend/zend_vm_def.h（書き換え1か所）
- Zend/zend_vm_execute.h（書き換え3か所）
- ext/standard/array.c（書き換え3か所）

の3ファイルです。

**Zend/zend_vm_def.h**, **Zend/zend_vm_execute.h** の書き換え箇所は、

```c
zend_error(E_WARNING, "%s(): Parameter must be an array or an object that implements Countable", opline->extended_value ? "sizeof" : "count");
```

これを、

```c
zend_error(E_NOTICE, "%s(): Parameter must be an array or an object that implements Countable", opline->extended_value ? "sizeof" : "count");
```

に書き換えます。（E_WARNING → E_NOTICE）
多分コメントアウトしてしまえば、NOTICEすら発生しません。（試してない）

**ext/standard/array.c** は、

```c
php_error_docref(NULL, E_WARNING, "Parameter must be an array or an object that implements Countable");
```

これを、

```c
php_error_docref(NULL, E_NOTICE, "Parameter must be an array or an object that implements Countable");
```

に書き換えます。（E_WARNING → E_NOTICE）

あとは念のため、make clean して再インストールします。
怖いのでmake test はしません。

```bash
make clean
./configure {オプション自由}
make
make install
```
 
あとは、

```php
<?php print count(NULL); ?>
```

などして、WARNINGが発生しないことを確認してください。
（php.ini の設定などで、メッセージの出力等は異なります。）

```php
count(null); // 0
count(1); // 1
count('abc'); // 1
count(new stdclass); // 1
count([1,2]); // 2
```
WARNING無しでPHP5と同じ結果が出るようになりました。（NOTICEは発生してる）

当然ですが、**公式では非推奨**です。

多分、これやると**PHPコミュニティにすっげぇ怒られます。**

**バージョンアップをするときは、毎回同じ改造が必要です。**

くどいようですが、本当に、
**自己責任**
でやりましょう。

というわけで、patch簡単に作れるんですが、
作らないでおきます。

##他、undefinedが出るような関数##
自分で定義して互換動作させてます。
mysql関数とか、ereg()関数とか。
いろいろ問題ありそうだけど…。
Unityで子オブジェクトを全部削除する

下手に検索しても出てこないので自分用にメモ。
なおこれはEditor用

```C#
GameObject o;//削除対象の親オブジェクト
while(0 < o.transform.childCount)
{
  DestroyImmediate(o.transform.GetChild(0).gameObject) ;
        
}
```
仙台CTF 2019 Lab5.マルウェア解析練習2 100

#問題

http://ctf.sectanlab.jp/2019/

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/6f66c950-6484-5ee2-859c-564cc6911450.png)

#解いてみた

たぶんbintextでは解決しないだろうけど一応やってみます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/de7c16bb-7628-4c29-c33d-e4cd1b718587.png)

一通り見ましたが、やはりありませんでした。

ollydbg使いますか。

今の年月と今回のフラグとなる年月を比較する処理がどこかにあるはず。
とりあえずAPIでローカルタイムを取得する処理があるはずです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/1e45157d-3efd-811c-12ad-75bb44c03b56.png)

ラベルネームを見てみるとGetLocalTimeがあるのでここが怪しそうです。
呼ばれているところを確認してみます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/93253810-b219-6e31-a73d-9cabfc0b1ef8.png)

1つしかありません。
なのでここにジャンプしてブレークポイントを張って、プログラムを実行します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/ee76f8dc-dc8d-88e9-85b2-d2c4315d43de.png)

すぐあとに比較しているところが2つあるので年と月っぽいです。
詳しく見てみます。

```
00401021   . 81F9 E3070000  CMP ECX,7E3
```
で値を比較しています。
7E3が何か確認してみます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/7b5ba7b6-1672-a02c-2f49-2b58196e20c8.png)

2019ですね。
2019年ということでしょう。

```
0040102D   . 83FA 0A        CMP EDX,0A
```

これも同様に変換すると月が出てきて、これが答えになります。
【Scrapy】抜き出したURLを修正・加工する

#想定例
[Scrapy](https://scrapy.org)のCrawlSpiderを使用して、
アイテム一覧ページ->個々のアイテムの概要ページ->個々のアイテムの詳細ページ、とリンクを辿っていけるサイトをクローリングし、
詳細ページの情報をスクレイピングして保存する場合を想定。

ページとURLの対応関係は下のような感じで。

| ページ       |       URL |
|:-----------------|:------------------|
| アイテム一覧|              example.com/list|
| アイテムの概要|            example.com/item/(ID)/|
| アイテムの詳細|       example.com/item/(ID)/details|

こういった構造のサイトの場合、一覧ページから抜き出した、概要ページへのリンクの末尾に、/detailsをつけ加えて、それを使って直接詳細ページにリクエストすることができれば、相手先のサイトへのリクエスト数が半減し、こちらのプログラムの実行にかかる時間も減らせて一石二鳥！
というわけで下記が実装例。

#実装
LinkExtractorの引数*process_value*に、URLを加工する処理をラムダ式で記述する。

``` example.py
class ExampleSpider(CrawlSpider):
    name = 'example'
    allowed_domains = ['example.com']
    start_urls = ['http://example.com/list'] #アイテムの一覧ページ

    rules = [
            Rule(LinkExtractor(
                #/item/を含むURLを抜き出す
                allow=r'.*/item/.*',
                #抜き出したURLに'details/'を付け加える
                process_value= lambda x:x + 'details/' 
                ),callback='parse_details'),
    ]
#

    def parse_details(self, response):
        #(省略)

```

以上！
AWS認定資格_ソリューションアーキテクト-アソシエイト取得

# はじめに
AWS認定資格_ソリューションアーキテクト-アソシエイト取得を目指すためにQiitaを使って勉強内容を記載していこうと思います。

# きっかけ
PLとしてあるシステムの開発に携わる際に、AWSのサービスである下記を用いました。
- EC2
- RDS
- S3
- elasticache
- amazon elasticsearch service
- DMS

当初、AWSに触ったことがなかった私としては？？が飛び交っており、正直よくわからないまま「よくわからないな～。。」と思いながら使っていました。
しかし、AWSのサービスを利用していくうちに慣れていき、次第にもっと知りたい、様々なサービスを知り顧客に提案できるエンジニアになりたい。という意識を持つようになりました。
上司と面談した際に、「AWSの資格の勉強してみたら？インセンティブももらえるし」という言葉で資格勉強をすることを決意しました（取得できればお金ももらえるし！）

# 資格本
さっそく本屋にいき「ソリューションアーキテクト[アソシエイト]」の本を買いにいきました。
そこで私は「AWS認定資格試験テキスト　AWS認定 ソリューションアーキテクト-アソシエイト」という書籍を買いました。
詳しくは下記URLを参照
https://bookwalker.jp/de68074883-4cc9-4d5a-bd8e-45f67af85fb9/?adpcnt=7qM_Vsc7&utm_source=google&utm_medium=cpc&utm_term=_&utm_campaign=&utm_content=__cp_1471997507_gr_65566109508_kw_pla-428567606763_cr_281840075652&gclid=CjwKCAjwgbLzBRBsEiwAXVIygPlCk_Stubn-vfVM2S6mRfjiHUM_WtdJrCSwxa1MN-Es8K2icC7toBoCH-AQAvD_BwE
この書籍を1週間で一周しましたが、かなり勉強になりました。
様々なAWSのサービスの概要、資格試験の対策や傾向について細かく記載されているためおすすめです（まだこれしか読んでいないのでなんともいえないですが）

# サイト（記事）
資格本だけだと具体的な内容について知りたくなります。
Qiitaにはいろんな方がAWSの内容について書かれているのでとても勉強になっています。
私がいままでみて勉強になったリンクを記載していきます。

・AWSのルートテーブルについて
https://qiita.com/chro96/items/21863e0960ba4ac72470

・【AWS】AWSの勉強
https://qiita.com/s_Pure/items/582673e01ed5218cc62b

・AWSで不正利用され80000ドルの請求が来た話
https://qiita.com/koyama9876/items/add70cba3cccdb7fa995


あと、実際に手を動かしてみようと思い、下記Qiita記事の手順が非常に参考となったためこの記事通りに「VPC構築→EC2構築→ELB構築」まで構築完了しました。
※RDSは後程構築していこうかと思います。

・から始めるAWS入門：概要
https://qiita.com/hiroshik1985/items/6433d5de97ac55fedfde


また、IAMユーザー作成時に参考にしたURLを下記に記載
https://qiita.com/moiwa/items/ac65481c0b7433aac468

# 最後に
今後AWS関連の記事を記載していこうかと思います。
参考になる資料やURLなどあれば共有いただけるとありがたいと思います。
OSSで開発する時は真っ先にブランチを切ろう


# まとめ
初めてのOSS参加だったんですが、ブランチを切り忘れた結果別イシューの開発ができなくなってしまいました。そこでforkしてきた自分のリポジトリだからいいだろうとgit push -f をしたら承認済みのPRまで消えてしまって焦ったという話です。push -fは使わないようにしよう。

# 背景

今東京都とCode for Japanが一体となって作っている新型コロナウィルス感染症対策サイトに自分も参加していました。

https://github.com/tokyo-metropolitan-gov/covid19

Code for Japanの活動に去年からちょくちょく参加していましたが、サービス設計やデータ整備の部分を多くやっていたのでgitを使った集団開発はかじったことがある程度、、でした。なのですがQiitaに素晴らしい記事が公開されていたので初OSS参加やってみようと思い立ちました。

OSS参加のための素晴らしい記事
https://qiita.com/FPC_COMMUNITY/items/b9cc072813dc2231b2b2#%E3%81%AF%E3%81%98%E3%82%81%E3%81%AB

無事に初PRも承認されて、意気揚々と別のイシューに取り掛かったんですがそこでちょっとした問題が発生しました。

# 起こったこと

ブランチを切らずにdevelopmentで開発をしてPRを投げた自分、2つ目のissueにどう取り組むんだ？という疑問に突き当たりました。
  
<img width="725" alt="スクリーンショット 2020-03-14 17.34.43.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/223757/febee1ed-4b38-ec12-e2f4-fa3b8b0695e5.png">


このままdevelopmentにcommitしたら、そのコミットまでが1つ目のPRに乗ってしまいます。そこでようやく「集団作業の時は作業ごとにブランチを切れ！」という大原則を思い出しました。
本来はイシューを始める段階でブランチを切って開発して、そのブランチからPRを出すのが正解だったんですね。Developmentブランチは常にfork先の状態と一致させておく運用の方が直感的でわかりやすいです。

今からでも遅くはない、修正しようと思って行ったのが次の手順になります(結果面倒なことになったので真似しないでください)。

1. ローカルブランチでIssue 1に取り組む前のコミットまで戻る
2. ブランチを切ってnew-issue-1ブランチにIssue 1に関するコミットをcherry-pickを使って移動する
3. 自分のリモートリポジトリのnew-issue-1ブランチにpushする
4. developmentブランチに戻り、git reset --hard (コミット番号)でIssue 1に関するコミットログを消す
5. <b>(大戦犯)git push -f でリモートのdevelopmentブランチを元に戻す</b>

<img width="797" alt="スクリーンショット 2020-03-14 17.52.47.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/223757/249ab3a6-b815-7f13-516f-e67d75f1c093.png">


自分のリポジトリには自分しかコミットしないしforce-pushしていいだろ〜とか軽く考えていたんですが、、、

結果承認済みだったIssue 1のPRが自動で閉じてしまいました・・・

プルリクエストは個人のリモートのdevelopmentブランチからfork先のリモートのdevelopmentブランチに送られているので、個人のリモートのdevelopmentからログが消えたら自動でプルリクエストは閉じる仕様になっていたようです。「せっかく通ったはずのPRを勝手にcloseさせてしまったショック」に数分打ちひしがれていたのですが、事情を説明してすぐにnew-issue-1ブランチからPRを送り直しました。

集団開発の時は必ずローカルのブランチを切ってから作業しましょう！
後OSS参加楽しいので是非みなさんもやりましょう！
オレオレSSL証明書作成スクリプト

自分用メモ。

有効期限398日間のオレオレ証明書を作成するスクリプト。

create_ssl_cert.sh

```sh
#!/bin/sh

domain=$1

crt_file="$domain.crt"
key_file="$domain.key"
subject="/C=JP/ST=Tokyo/L=Tokyo City/CN=*.$domain"

openssl req -new -newkey rsa:2048 -x509 -nodes \
  -set_serial 1 \
  -days 398 \
  -subj "$subject" \
  -out "$crt_file" -sha256\
  -keyout "$key_file" -sha256
```

使い方

```sh
$ ./create_ssl_cert.sh example.com
```

実行したディレクトリに
example.com.crt
example.com.key
が作成される。
Github ActionsのAndroid CIでNDKを切り替える

## 概要
Github ActionsのAndroid CIを実行させた場合、Github Actionsで用意されているHost Runnerをそのままを使うと、[virtual-environments/Ubuntu1804-README.md](https://github.com/actions/virtual-environments/blob/master/images/linux/Ubuntu1804-README.md) に記載されたバージョンのNDKが適用される。
例えば、2020年3月14日時点では`Android NDK 21.0.6113669`となる。

ただ、場合によっては別のバージョンのNDKを利用したいケースもある。

## NDKの切り替えに対応したandroid.yml
[CircleCI Orb Registry - circleci/android](https://circleci.com/orbs/registry/orb/circleci/android) を参考に、NDKを指定できるようにandroid.ymlを記述する。

なお、`NDK_SHA`と`NDK_VERSION`は、[こちら](https://developer.android.com/ndk/downloads/older_releases?hl=ja)を参考に設定すればよい。

```yaml
name: Android CI

on:
  pull_request:
    types: [opened]
  push:
    branches: [ master ]

jobs:
  build:

    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v2
    - name: set up JDK 1.8
      uses: actions/setup-java@v1
      with:
        java-version: 1.8
    - name : install ndk
      run: | 
        sudo curl --silent --show-error --location --fail --retry 3 \
          --output /tmp/$NDK_VERSION.zip \
          https://dl.google.com/android/repository/$NDK_VERSION-linux-x86_64.zip

        sudo echo "$NDK_SHA /tmp/$NDK_VERSION.zip" > /tmp/$NDK_VERSION.zip.sha1

        sha1sum -c /tmp/$NDK_VERSION.zip.sha1
        
        sudo rm -rf $ANDROID_SDK_ROOT/ndk-bundle
        sudo unzip -q /tmp/$NDK_VERSION.zip -d $ANDROID_SDK_ROOT
        sudo mv $ANDROID_SDK_ROOT/$NDK_VERSION $ANDROID_SDK_ROOT/ndk-bundle
        sudo chown -R root:root $ANDROID_SDK_ROOT/ndk-bundle
        sudo rm -f /tmp/$NDK_VERSION*
        
        if [[ -d $ANDROID_SDK_ROOT/ndk-bundle && \
          -n "$(ls -A $ANDROID_SDK_ROOT/ndk-bundle)" ]]; then
          echo "Android NDK installed"
        else
          echo "Android NDK did not install successfully"
          exit 1
        fi
      env:
        NDK_SHA: fd94d0be6017c6acbd193eb95e09cf4b6f61b834
        NDK_VERSION: android-ndk-r19c
    - name: Build with Gradle
      run: ./gradlew build
```

## Gist
- [Switch NDK on Android CI](https://gist.github.com/okhiroyuki/bb28374f2fcf274e80cc06688f119a98)
Mailer viewでヘルパーメソッドを使用する

#Mailer viewでヘルパーを使いたい

###郵便番号にハイフンをいれてくれるメソッド

```application_helper.rb
def format_zipcode_include_hyphen(zipcode)
    zipcode.include?('-') ? zipcode : zipcode.insert(3,'-')
end
```

mailer viewでいきなり使用するとエラーになった。

###application_mailer.rb
```application_mailer.rb
class ApplicationMailer < ActionMailer::Base
  add_template_helper(ApplicationHelper)
end
```

と記述する

###view
```mailer.ftml.slim
p 〒#{format_zipcode_include_hyphen(zipcode)}
```

でうまくいきました。
ALBはなぜ3AZにするべきなのか

# はじめに
2019年8月に発生したAWSの東京リージョンでの障害は記憶に新しいことかと思います。
[東京リージョン (AP-NORTHEAST-1) で発生した Amazon EC2 と Amazon EBS の事象概要]
(https://aws.amazon.com/jp/message/56489/)
マルチAZで構築していても影響があった方も多かったと思います。
その中でALBにおいて、継続してサービスを提供するには`2AZより3AZにすべき`という意見が見られたので、なぜ3AZにしなければならないのかを調べてみました。

なおAWSについて勉強し始めたばかりなので、間違い等あればご指摘ください。

# ALBは2AZを指定する必要がある
![スクリーンショット 2020-03-14 17.03.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/402550/94ff3790-1af1-c22d-d54f-5232cd51892e.png)
ALBでは2つ以上のAZのサブネットを設定する必要があります。1AZにすることは出来ません。
そのため、3AZならば2AZに減らすことは出来ます。

2AZでもALBがロードバランスしてくれるから、問題ないのではと最初思っていました。
しかし、ALBの仕組みを見ていくと2AZでも障害が起こってしまう可能性があることがわかりました。

# ALBはどう動いているのか
2AZでALBを試しに作り、`yuki-furukawa-alb-hogehoge.us-east-1.elb.amazonaws.com`というDNS名が払い出されたとします。
これをdigコマンドを使って見てみます。
（DNS名やIPアドレスは適当に書き換えています）

```bash
$ dig yuki-furukawa-alb-hogehoge.us-east-1.elb.amazonaws.com                                                                                                                      土  3/14 16:59:20 2020

; <<>> DiG 9.10.6 <<>> yuki-furukawa-alb-hogehoge.us-east-1.elb.amazonaws.com
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 26213
;; flags: qr rd ra; QUERY: 1, ANSWER: 2, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 512
;; QUESTION SECTION:
;yuki-furukawa-alb-hogehoge.us-east-1.elb.amazonaws.com. IN A

;; ANSWER SECTION:
yuki-furukawa-alb-hogehoge.us-east-1.elb.amazonaws.com. 59 IN A XXX.XXX.XXX.1
yuki-furukawa-alb-hogehoge.us-east-1.elb.amazonaws.com. 59 IN A XXX.XXX.XXX.2

;; Query time: 41 msec
;; SERVER: 8.8.8.8#53(8.8.8.8)
;; WHEN: Sat Mar 14 17:01:18 JST 2020
;; MSG SIZE  rcvd: 116
```

DNSのAレコードに2つのIPアドレスが割り当てられているため、DNSラウンドロビンによって`XXX.XXX.XXX.1`または`XXX.XXX.XXX.2`にアクセスすることになります。

ここで今回の構成を図にしてみました。
![Untitled Diagram (2).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/402550/2b0c9a17-c952-5903-2110-a87e43483cdc.png)

`XXX.XXX.XXX.1`と`XXX.XXX.XXX.2`がALBのIPアドレスになります。
ALBはEC2のインスタンスのようなものが立ち上がって、アクセスを振り分けているということです。

## EC2のインスタンスが停止した場合
まずはEC2のインスタンスが停止した場合を考えてみます。
![Untitled Diagram (3).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/402550/01a2c3c1-4cdb-ff2c-da9f-c660bf300970.png)

ALBはヘルスチェックを行っているので、停止したEC2インスタンスへアクセスは行かず、他のインスタンスにアクセスします。
この場合は2AZでも障害が起きても問題はないです。

## ALBのインスタンスが停止した場合
ALBのインスタンスが停止した場合を考えてみます。
ALBはEC2の基盤を使っていると考えれれるので、EC2のサービスが提供できなくなった場合、ALBにも影響が出ると思われます。
![Untitled Diagram (4).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/402550/5f9df883-0af8-bc7a-02dd-8b2fb76523a0.png)

DNSラウンドロビンによってALBへのアクセスを振り分けているため、ALBのインスタンスが1つでも停止していると影響を受けることになります。
この例では名前解決の結果`XXX.XXX.XXX.2`にアクセスした場合、エラーが表示されてしまいます。

これが3AZだったらどうでしょうか。
3AZなら2AZに変更することができるので、障害が起きたALBを切り離す事ができます。
つまり、ALBの障害を考慮すると、3AZで構築する必要があるということになります。

# おわりに
SLAにもよるかと思いますが、ALBでの障害を考慮した場合3AZにしたほうが安心です。
ALBは3AZにした方がいいよって言われたときに、なんでだろうと思った人に参考になれば幸いです。
[WSL Debian] Gitのコマンドの入力補完を有効にする

# 概要

WSL版のDebian（以下，WSL-Debian）にて，Gitのコマンドの入力補完を有効にする．**ただし，ここでの`Git`とは，WSL-Debianの`apt`を通してインストールしたものを示す．**

## 「WSL-Debianのaptを通してインストールしたGit」とは

下のようなコマンドでインストールした`Git`のことを示す．つまり，`Git for Windows`は対象としない．

```bash:Install_git
sudo apt install git
```

# 動作確認した環境

動作を確認した環境は以下の通りである．

```bash:Environment
$ cat /etc/debian_version
9.12
$ uname -a
Linux DESKTOP-7IQQAG7 4.4.0-18362-Microsoft #476-Microsoft Fri Nov 01 16:53:00 PST 2019 x86_64 GNU/Linux
$ git --version
git version 2.11.0
```

# 結論

下に示すように，`apt`を通して，`bash-completion`をインストールする．

```bash:Install_bash-completion
sudo apt install bash-completion
```

なお，これを実行すると，`apt`をはじめとする他のコマンドの入力補完も有効となる．

# 結論に至った経緯

`/usr/share/bash-completion/completions/`の下に，`Git`をはじめとするコマンドの入力補完のためのスクリプトがあるにもかかわらず，これがシェルに反映されないことを疑問に思い，試行錯誤してみた．

WSL-Debianは，初期設定において，`bash-completion`がインストールされていないため，補完スクリプトがあるにもかかわらず，これらが反映されないようである．

# 参考文献

[bash-completionでserviceコマンドなどの補完を強化しよう](https://heartbeats.jp/hbblog/2013/06/bash-completion.html)
Android+RS-232C通信

# はじめに
まだまだ計測機器と通信はRS-232Cが現役です。
ある計測機器(USB-miniB/RS-232C)とAndroidでRS-232C通信できないかと相談がありました。
そこでUSB-miniB/RS-232C(変換ケーブル)で通信できるか調査しました。

先に結論を書くと、

- USB-TypeC→USB-TypeA変換→USB-miniBでは計測機器が認識できない端末あり。
- USB-TypeC→RS-232C変換ケーブル(ラトックシステム製)→RS-232CではUSB-TypeCの端末で認識できました。

# 調査環境
- Android(バージョンは後述)
- ある計測機器(USB-miniB/RS-232C)
- USB-TypeC→RS-232C変換ケーブル(ラトックシステム製)  
[USBシリアルコンバーター RS-USB60FC](https://www.ratocsystems.com/products/subpage/convert/usb60fc_siyou.html)
- usb-serial-for-android(計測機器を認識できたときに通信テスト)  
[usb-serial-for-android GitHub](https://github.com/mik3y/usb-serial-for-android)

# 計測機器の認識調査
- UsbManager. getDeviceList()でUSB機器を検索します。
- 見つかったUSB機器情報をテキストに表示します。
- USB機器(計測機器/変換ケーブル)が見つからない場合、認識しないと判断します。

```kotlin
import android.os.Bundle
import kotlinx.android.synthetic.main.activity_main.*
import android.hardware.usb.UsbDevice
import android.hardware.usb.UsbManager

class MainActivity : AppCompatActivity() {
    private lateinit var usbManager:UsbManager

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        usbManager = getSystemService(Context.USB_SERVICE) as UsbManager

        btnTest.setOnClickListener {
            // USB機器を検索してテキストに表示
            val devices = usbManager.deviceList
            var str = ""
            for (device in devices.values) {
                val name = device.deviceName
                str += "Name:${name}\n"
                str += "Vendor:{$device.vendorId}\n"
                str += "Product:{$device.productName}\n"
                str += "\n"
            }
            txtMsg.text = str
        }
    }
}
```

## USB-miniBで調査
- USB-microB/Type-C→USB TypeA変換ケーブル→計測機器(USB-miniB)とAndroid端末の組み合わせで、計測機器を認識できる端末/できない端末があった。
- USB-Type-Cでは認識できる端末/できない端末があり、変換ケーブルと端末の選定が難しくなった。

### 計測機器を認識できる組み合わせ
* USB-microB→USB-TypeA→USB-miniB

|端末|OS|認識|
|---|---|---|
|Nexus7|6.0.1|O|
|Moto5G|7.0|O|


* USB-TypeC→USB-TypeA→USB-miniB
 
|端末|OS|認識|
|---|---|---|
|Pixel3a|10.0|O|

### 計測機器を認識できない
* USB-TypeC→USB-TypeA→USB-miniB

|端末|OS|認識|
|---|---|---|
|ZenfoneAR|7.0|X|
|Zenfone5|8.0.0|X|

## USB-TypeC→RS-232C変換ケーブル(RS-USB60FC)で調査
- 下記の全ての端末で認識できました。
- USB-TypeC→RS-USB60FC

|端末|OS|認識|
|---|---|---|
|ZenfoneAR|7.0|O|
|Zenfone3 Deluxe|8.0.0|O|
|Zenfone5|8.0.0|O|
|Nexus5X|8.1.0|O|
|Essential Phone PH-1|10.0|O|
|Zenfone5Z|10.0|O|
|Pixel3a|10.0|O|

# おわりに
- USB-TypeC→USB-TypeA変換→USB-miniBでは計測機器が認識できない端末あり。
- USB-TypeC→RS-232C変換ケーブル(ラトックシステム製)→RS-232CではUSB-TypeCの端末で認識できました。
- ラトックシステム製のRS-232C変換ケーブルは、USB-TypeA/miniB/microB/Type-Cのタイプが用意されているので、ターゲット端末に応じて使おうと思います。
仮想環境のCentos7のファイルをVS codeでリモート編集する

#概略
VMwareを使って仮想マシン上にCentos 7をインストールした。centOS7上のファイルをもともとローカル環境（windows 10）にあったVS codeで編集したいと思い、VS codeのRemote Developmentを使って実行した。

##環境
サーバー：centOS 7.7.1988
クライアント：windows 10 1903
VS code 1.42.1

##VS codeのRemote Developmentの設定
VS codeの拡張機能であるRemote Developmentを使うことによって、リモートサーバーにssh接続をすることができます。VS codeの拡張機能追加（画像左端のメニューバーの四角形4つのアイコン）を選択して、検索ボックスに"Remote Development"と入力します。そうすると、`Remote Development`が検索結果として表示されるので、それをインストールします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/aaf72e77-c0f8-15d1-f8fd-aacd37291ab1.png)

そしたら画面左下に表示される以下のアイコンをクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/80598278-5dc5-d614-6d6a-6457b9f28921.png)

以下のような検索ボックスが起動するので、`Remote-SSH:Connect to Host...`を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/8f52bdf5-76b2-62c1-ee47-44d1f5548e17.png)

続けて`Configure SSH Hosts...`を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/017572b8-934b-04a8-d654-d683f25616b7.png)

続けて`C:\Users\ユーザ名\.ssh\config`を選択します。下の画像ではユーザ名＝keikeとなっています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/9605fc29-d674-a351-6773-281cfde2d3c0.png)

configファイルが起動するので、`HostName`の後ろににsshサーバーのIPアドレス、`User`の後ろにユーザ名を入力して保存します。なお、この設定はaliasというホスト名で保存されます。ホスト名を変えたい場合は画像中の`alias`のところを変更してください。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/6ff28fe7-7c8d-4f1f-5bd3-e3add2e6ba5f.png)

事前の設定は以上です。

##リモートサーバー（Centos 7）にsshで接続

ここからリモートサーバーへssh接続していきます。先ほど`alias`という名前のホスト名で設定をしたので、`Remote-SSH:Connect to Host...` ⇒ `alias`と選択します。そうすると、VS codeの新しいウィンドウが起動し、接続先ホストのパスワードを求められるので、入力します。接続に成功すると、画面左下に以下のように表示されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/c5c5d3c0-4110-e351-71cb-89c4d0f45b7e.png)

試しにここで`test.php`というphpファイルを作ってリモートサーバー上に保存してみます。今のところ、以下の画像のようにリモートサーバ上のhomeにはファイルはありません。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/0080fda4-3632-2de6-5516-874c28878e4a.png)

`test.php`はHello worldと表示するだけの簡単なファイルです。

```test.php
<?php
    echo "Hello world\n";
?>
```
以下のように普通にVS codeでphpファイルを作成し、保存します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/3d837bf2-7b08-702e-4eb4-8eac26b2ad49.png)

これでcentos 7上に`test.php`が保存され、実行することもできます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587343/3624d57e-9c3c-d0eb-774e-1a8544238584.png)
Railsにおけるセッション管理とCookieについて

セッション管理とCookieの働きについてあやふやだったのでまとめてみました

### HTTP通信
- クライアントとサーバ間は**HTTP**というルールでやり取りをする
- クライアントからサーバに対して「リクエスト」が送られる
  - リクエスト = 「要求」（このURLの情報ちょうだい、とか）
  - レスポンス = 「返答」（情報はこれだよ、とか）
![スクリーンショット 2020-03-14 14.52.48.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159704/b1932d11-8aa3-50ae-293d-2bf07bf0eb72.png)

### HTTPはステートレス
  - ステートレス＝記憶力がない
  - たとえばyahooにアクセスするときには、クライアントからサーバへ「yahooの情報ちょうだい」とリクエストを送るが、その直後には送ったことすら覚えていない
  - yahooの情報がレスポンスで送られてきて画面表示をしたとしても、送られてきたこと自体を覚えていない
  - 要求しっぱなし。もらいっぱなし。
![スクリーンショット 2020-03-14 17.19.39.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159704/58f13891-8dc2-0afc-68db-f1c82d9cd7cb.png)


### ステートレスだと、Webアプリでログインする時にどんな問題が発生するか
  - ログインできても、ログインしたことすら覚えていない
  - そのため、次にアクセスした時には、またログインしなければならない
  - ショッピングサイトの場合、カートに入れた商品情報が保持されない

### そこでCookieの登場
  - [CookieStore](https://railsguides.jp/action_controller_overview.html#%E3%82%BB%E3%83%83%E3%82%B7%E3%83%A7%E3%83%B3)を前提に書きます
  - ログインできた時点で、サーバでユーザーのidをCookieに入れてクライアントへ送り返す

コード例:

```ruby
session[:user_id] = user.id
```
こうすることで、暗号化されたuser_idがHTTPレスポンスヘッダのSet-Cookieフィールドに格納され、レスポンスとしてクライアントへ送り返される

![スクリーンショット 2020-03-18 15.31.22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159704/15d33d2a-773a-7074-a078-093ac815ecea.png)


  - クライアントはCookieを受け取り、ブラウザに保存する
![スクリーンショット 2020-03-18 15.31.58.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159704/5b603859-66f3-b90f-8e26-57311bc8dcb8.png)



  - 次にリクエストを送る時には、保存しているCookieをリクエストに含めて送る
![スクリーンショット 2020-03-18 15.33.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159704/573a4190-1853-315c-38e3-e15d1f63e44f.png)


  - リクエストで送られてきたCookieをサーバが受け取る
![スクリーンショット 2020-03-18 15.34.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159704/9c78ae7c-2c83-dfb9-dcd2-87403598b051.png)



  - そのCookieから暗号化されたuser_idを復元・抽出し、そのidと合致するユーザをログイン状態として処理をする
コード例:

```ruby
@current_user ||= User.find_by(id: session[:user_id])
```
  - ログイン中は、user_idをCookieの中に含めたままクライアント〜サーバ間をグルグルと回っている状況
  - ログアウト時には、サーバにてCookieからuser_idを消去する

コード例:

```ruby
session.delete(:user_id)
```
とか

```ruby
session[:user_id] = nil
```
など。

  - user_idが除かれたCookieが、サーバからクライアントに渡る（user_idが存在しない＝ログアウト状態）
  - ログアウト中は、user_idが除かれたCookieがクライアント〜サーバ間をグルグルと回ることになる
Fioneではじめる機械学習〜Titanic編

## はじめに

[前回(Fioneではじめる機械学習〜導入)](https://qiita.com/shinsuke_sugaya/items/338d97161d9a27bb14b8)はFioneの基本的な利用方法を紹介しました。今回は、Kaggleで公開されているデータを利用して、予測データを作成してみます。Kaggleのデータを利用するので、Kaggleにサブミットするところまでおこなっていきます。

## Kaggleとは

Kaggleは世界的なデータサイエンスのコミュニティで、分析用のデータセットを公開したり、予測モデルを探求したり、精度を競い合ったりするような場を提供するプラットフォームであり、会社でもあります。Kaggleに関する情報は検索すれば見つかるので、そちらを参照してください。

今回は、その中で入門データであるタイタニック(Titanic)を用いて、生存予測を行います。Kaggleからのデータ取得をするためには、Kaggleにログインする必要があるので、ユーザー登録してあるものとして話を進めます。

### Titanicデータ

https://www.kaggle.com/c/titanic/data にアクセスして、train.csvとtest.csvをダウンロードしてください。

![Titanicデータの取得](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/19758/c6ec796b-ba8c-1c7c-5327-c3b3df37f694.png)

train.csvが学習用データで、test.csvはテスト用データです。テスト用データの方には生存かどうかの(Survived列)が含まれていません。

## Fioneで予測データ作成

### 起動

Fioneの起動に必要な設定等は[前回の記事](https://qiita.com/shinsuke_sugaya/items/338d97161d9a27bb14b8)を参照してください。今回は、Fione 13.6.1を利用します。

```
$ git clone https://github.com/codelibs/docker-fione.git -b v13.6.1
$ cd docker-fione/compose
$ docker-compose up
```

### プロジェクトの作成

ブラウザで `http://localhost:8080/admin/easyml/` にアクセスして、fioneユーザーでログインします。 デフォルトのパスワードはfioneです。

fioneユーザーでログインすると、EasyMLのプロジェクトダッシュボードが表示されます。プロジェクト名にTitanic、学習データにtrain.csvを指定して、作成ボタンを押下してください。

![プロジェクトダッシュボード](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/19758/79264ff4-98bb-5c20-360c-99c30e7a5657.png)

### 学習

train.csvの読み込みが終わると、データ分析が表示されます。今回の予測対象はSurvived列なので、左側の予測領域で予測する列にSurvivedを選択します。Survivedは0または1の二値の予測なので、予測の種類には二値分類を選択します。最大実行時間はどれだけ時間で計算するか？なので、今回は1時間を選択して、1時間の計算を行います。実行ボタンを押下して、計算を開始します。

![データ分析](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/19758/2698cf7a-d095-76fa-43b7-0f504c0ad092.png)

計算が終わるまたは1時間後、予測結果サマリーが表示されます。今回は275モデルを作成して、GBM gridの結果が良いようです。作成するモデル数などは実行環境に依存します。

![予測結果サマリー](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/19758/b45e9938-ed3a-76d1-0294-310c862fcced.png)

### 予測データの作成

テスト用データtest.csvから予測データを作成しましょう。予測結果サマリーのFioneくんが「予測ページからデータファイルをアップロードしてください。」と言ってますので、その予測ページのリンクを押下します。

新規予測ページが表示されます。予測するデータにtest.csvを指定します。KaggleにサブミットするデータはIDと予測値だけのデータが必要なので、今回は出力する列の中でPassengerIdだけを選択します。入力後、アップロードボタンを押下します。

![新規予測](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/19758/68cc9ffb-90c8-cb25-17a5-9c6a16444349.png)

予測データ作成が完了すると、予測結果サマリーに戻ります。データセット領域が表示されるので、predict_〜.csvファイルをダウンロードします。

![予測結果サマリー](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/19758/750dc4e8-fc8f-b6b0-669c-f021bea05d58.png)

## 予測結果の提出

Kaggleに戻り、https://www.kaggle.com/c/titanic/submit を表示します。Step 1のところにpredict_〜.csvを指定して、コメントがあればStep 2のテキスト欄に入力して、Make Submissionボタンを押下します。

![Submit predictions](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/19758/1fd0ac4c-ea17-03e0-58a4-4e7e22608f01.png)

問題がなければ、My Submissionsでアップロードした結果を確認することができます。

## まとめ

今回は2クラス分類問題の予測モデルを作成して、Kaggleに結果をアップロードする方法を紹介しました。(ほぼ何も考えずに)データをFioneに渡すだけで、必要な予測結果が取得できることを紹介できたと思います。予測結果サマリーから予測API化も簡単にできるので、予測したいデータがあれば同様に、予測結果またはAPIなどで利用できると思います。
盲点rubyのメソッドdeleteのそれぞれ

ルビーのシルバー勉強中に盲点だったところが見つかりました。

それは**deleteメソッド**

deleteメソッドの挙動について今回は記事をあげたいと思います。

まずdeleteメソッドはarray、string、hashそれぞれのクラスで使えるメソッドです。

# Array

まずはarrayクラスのdeleteメソッドの動き

deleteメソッドは引数で与えた値が一致したものも全て削除します。

```ruby
array = [1,2,3,4,5,1,2,3,4,5]
p array.delete(3)
3
p array
[1,2,4,5,1,2,4,5]
```
上記のようにdeleteメソッドを使ったタイミングで返ってくる値は削除する対象の値が返ってきます。

そして破壊メソッドなので3が削除されています。

私は、deleteメソッドは他stringやhashも動きそんなに変わらないだろうと思っていました。

そして、模擬問題をとているときに間違えてしまい、
あれ？となったのです。

それはstringのdeleteメソッドの問題でした。

#String

```ruby
string = '1234512345'
p string.delete('3')
```
さてこのとき何が返ってくるか?

正解は

```ruby
string = '1234512345'
p string.delete('3')
"12451245"
```
またもう一度stringを呼び出すとどうなるか?

```ruby
string = '1234512345'
p string.delete('3')
"12451245"
p string
"1234512345"
```
というわけで破壊メソッドではないんですね！
もちろんdelete!で破壊メソッドとなります。

```ruby
string = '1234512345'
p string.delete!('3')
"12451245"
p string
"12451245"
```

#Hash

それではhashクラスはどうなるか?

```ruby
hash = {a: 1, b: 2, c: 3, d: 4, e: 5}
p hash.delete(:c)
3
p hash
{:a=>1, :b=>2, :d=>4, :e=>5}
```
という動きをします。

返ってくるのは削除したkeyに対応するvalueです。

また破壊メソッドなので指定した引数が削除されています。

というわけでdeleteメソッドでした。
多言語サイトで使うlang属性、lang属性を使ったCSS指定

多言語サイト制作ではlang属性を使います。

`<html lang="en">` 言語指定は今までこのように書いていましたが
[Google推奨の書き方](https://support.google.com/webmasters/answer/189077?hl=ja&ref_topic=2370587)があったのでメモしておきます。

```HTML:HTML
<link rel="alternate" hreflang="ja" lang="ja" href="https://hoge.com/"><!--日本語-->
<link rel="alternate" hreflang="en" lang="en" href="https://hoge.com/en/"><!--英語-->
<link rel="alternate" hreflang="zh-cmn-Hans" lang="zh-cmn-Hans" href="https://hoge.com/zh-cn/"><!--中国語（簡体）-->
<link rel="alternate" hreflang="zh-cmn-Hant" lang="zh-cmn-Hant" href="https://hoge.com/zh-tw/"><!--中国語（繁体）-->
<link rel="alternate" hreflang="ko" lang="ko" href="https://hoge.com/ko/"><!--韓国語-->
<link rel="alternate" hreflang="fr" lang="fr" href="https://hoge.com/fr/"><!--フランス語-->
```

hreflang属性＝国コードを指定
herf属性＝国別URLを指定

#主要な国のlang属性

サイト制作でよく使う国のlang属性は以下となります。

| 国名| lang属性 |
|:---|:---|
|日本語|ja |
|英語| en |
|中国語（簡体）| zh-cmn-Hans |
|中国語（繁体）| zh-cmn-Hant |
|韓国語| ko |
|フランス語| fr |

その他の国はこちらを参照ください。

HTML5/HTML5の基本/言語コード - TAG index
https://www.tagindex.com/html5/basic/langcode.html

#lang属性で言語別のCSS指定

lang属性で文字色を変更するmixnです。
font-familyやline-height言語ごとのCSSを指定します。

##Sass

```scss:scss

//言語ごとにfont-familyを指定するmixin
@mixin font_style {
  [lang=ja] & {
    color: darkred;
  }
  [lang=en] & {
    color: darkcyan;
  }
  [lang=zh-cmn-Hans] & {
    color: darkgreen;
  }
  [lang=zh-cmn-Hant] & {
    color: darkorange;
  }
  [lang=ko] & {
    color: darkviolet;
  }
  [lang=fr] & {
    color: darkslategray;
  }
}
```

#まとめ

classを使わないCSS指定は便利ですね〜。
lang属性に新しい属性が増えていて知識のブラッシュアップの必要を感じました。

海外市場に進出するため多言語サイトを制作する日本企業が増えています。
正しい多言語サイトを制作できるよう細かい部分を覚えておきたいです:v_tone1:


#参考URL

ページのローカライズ版について Google に知らせる - Search Console ヘルプ
https://support.google.com/webmasters/answer/189077?hl=ja&ref_topic=2370587

他言語サイトを制作するときのメモ
https://gist.github.com/manabuyasuda/dd976907005a588e3203da433289e6af

:lang擬似クラスは便利 - Qiita
https://qiita.com/butchi_y/items/334f2dd35a54fbbd116d
【瞬時に解決】vue.jsのエラー：Elements in iteration expect to have 'v-bind:key' directives  vue/require-v-for-key

vue cliを使用してプロジェクトを作成していると、このようなエラーに遭遇するかもしれません。

`Elements in iteration expect to have 'v-bind:key' directives  vue/require-v-for-key`

対処法は意外にも簡単でした。
vue.jsの[公式](https://jp.vuejs.org/v2/guide/list.html)ドキュメントにも解決策が載っています。

たとえば`v-for`を使って、monkeyの名前を`li`タグの中に出したいとしましょう。

### 例
```
<template>
    <ul>
        <li v-for="monkey in monkeys">{{ monkey }}</li>
    </ul>
</template>

<script>

export default {
  data() {
    return {
      monkeys: ['Taro', 'Hanako', 'Jiro']
    }
  }
}
</script>
```
こう書くとエラーが発生してしまいアウトプットされません。

ところが以下のように`v-bind:key="monkey"`を`li`タグのなかに追加するとエラーが消えます:point_down:

### 解決!
```
<template>
    <ul>
        <li v-for="(monkey, dog) in monkeys" v-bind:key="dog">{{ monkey }}</li>
    </ul>
</template>
```

どうやらv-forを使うときは、`v-bind:key=""`を付け加えてあげる必要があるそうです。これはvue.jsの公式ドキュメントでも推奨されています。
`v-bind:key=""`の中身は、`in`の手前にくるもの（この場合は`(monkey, dog)`）とそろえる必要があります。ただし、最初のオブジェクトとかぶるのはNGのようで、他とかぶらない名前を`(monkey, dog` このようにしてオブジェクトのあとにカンマで区切って付け加えるといいようです。ここでは`dog`という名前をつけました。括弧にくくらないと、またエラーが出てしまいます。たとえば以下のようでは効きません。

### 誤り:heavy_multiplication_x:

```
<template>
    <ul>
        <li v-for="monkey,dog in monkeys" v-bind:key="dog">{{ monkey }}</li>
    </ul>
</template>

//以下も効きません。 

<template>
    <ul>
        <li v-for="monkey in monkeys" v-bind:key="dog">{{ monkey }}</li>
    </ul>
</template>
```

👆ご注意ください。

このようにして解決することができました！

とはいえ初心者なので、もし何かあればご指摘ください:speaking_head:
Laravelのサービスプロバイダのキャッシュについてのエラー

作成したサービスプロバイダを削除した際にエラーが出る。

###状況
FormComponentServiceProviderというサービスプロバイダを作成し、config/app.phpへ追加した後、不要になったため削除。

下記エラーが出る。

```shell

In ProviderRepository.php line 208:

  Class 'App\Providers\FormComponentServiceProvider' not found
```

config/app.phpでの定義を削除し、キャッシュクリアしてみるが同様のエラーが出る。

```shell
$ php artisan config:cache

In Application.php line 670:

  Class 'App\Providers\FormComponentServiceProvider' not found
```

###原因・対処
bootstrap/cache/にキャッシュが残っていたため。

それらを削除し、composer dump-autoloadを行うことで解決。
ユーザーの書き込みとプロバイダ責任法、民事裁判

掲示板、5ch のようなサービスを作っていると
いたずら投稿される場合がある。

このいたずら投稿に対する処置はどのようにしたらいいのか？
まぁ、普通は

「削除して」

と言われりゃ削除するだろう。

しかし中にはいきなり訴訟を起こしてくる変わった人もいる。

そこで勉強しておきたいプロバイダ責任制限法。

参考
https://www.sbbit.jp/article/cont1/25539#continue_reading
https://legalus.jp/internet/defamation/qa-1081


# プロバイダ責任制限法って？

プロバイダには、webサービス管理者も含まれる。
被害者が損害賠償を求めるのは、あくまで書き込みを行ったユーザー。

しかし、以下の場合は損害賠償を請求される場合がある。

・被害者もしくは第三者からの削除依頼によって書き込みを知り、
書き込みを削除しなかったWebサービス運営者



![alt](https://www.sbbit.jp/article/image/25539/l_bit121012_kawase4-3.jpg)


書き込みを知っているのに削除していない場合、責任取らされる可能性がある。
よってwebサービス管理者は
「私、知りませんでした！」とちゃんと伝えることが大切。

Webサービス運営者等は、問題となっている書き込みの存在自体を知らない限り、必ず免責される。書き込みの存在自体を知らないならば、Webサービス運営者等が責任を負うことはあり得ないのだ。従ってWebサービス運営者等は、問題のある書き込みを削除要請前に削除するために、監視を行う必要はない。プロバイダ責任制限法は、Webサービス運営者等に監視義務がないことを明確にしている。

# 誰が書いたか、IPアドレスやログを開示してくれと言われたら？

ログの保存義務は無いので、
ログが無い場合は無いでも済む。

一般的には、

携帯電話事業者は3か月程度
ISP事業者などは3～6か月程度
ネットカフェ運営事業者の店舗利用者のログは1か月程度

# 少なくとも第三者が書けたという立証は必要

いや、第三者が書けたから知らんがな。
という主張では「立証不足」でwebサービス運営者が責任を取らされる可能性がある。

・どのような手段で第三者が書き込めたか
・誰が、上記の書き込みを行う理由があったのか
（5chでもXさんの事書いている人見つけたから、その人じゃないか？等）

の2点は必ず立証し、証拠として提出しよう。

本人訴訟の場合、仮に同じ主張をしたとしても弁護士に比べ大幅に不利なので
証拠を無視されるなどされた場合は、控訴しよう。

また、裁判官忌避や裁判官訴追請求で裁判官に対抗する方策がある。

# まとめ

消せと言われたら、消せば責任を取ることは無いので安心。