OmniAICreator/Qiita-1.07M huggingface dataset:
pythonでQuandlAPIを使ってデータ取得した際の備忘録

# 目的
pythonでQuandlAPIを使ってデータ取得した際の備忘録です。

# 準備

下記でQuandlをインストールします。

```
pip install quandl
```

下記からQuandlサイトへ登録してAPI keyを取得します。

> [Quandl API Documentation](https://docs.quandl.com/#authenticating-your-requests)


# コード

下記を参考にさせて頂きます。
> [pythonで東証から株価をAPI取得して、データをChartに表示させる](https://qiita.com/yasutaka_ono/items/2e52b6a4ef0666282896)
> [PythonでQuandlから金融データを取得する](https://www.codelab.jp/blog/?p=1105)

また、TSEコード（東京証券取引所の証券コード）は下記を参照しています。

> [yahoo finance](https://stocks.finance.yahoo.co.jp/stocks/qi/?ids=3650)


実行コード

```python:sample.py
import quandl
import pandas as pd
import  matplotlib.pyplot as plt

quandl.ApiConfig.api_key = 'xxxxxxx' # your API key

quandl_data = quandl.get("TSE/6902") # DENSO
quandl_data.to_csv('TSE_6902.csv')

stock = pd.read_csv('TSE_6902.csv')

stock['100MA'] = stock['Close'].rolling(window = 100, min_periods=0).mean()
stock['200MA'] = stock['Close'].rolling(window = 200, min_periods=0).mean()

fig = plt.figure()

axes = fig.add_axes([0.1, 0.1, 0.8, 0.8])

axes.plot(stock['Close'][-365:], 'black', lw = 1)
axes.plot(stock['100MA'][-365:])
axes.plot(stock['200MA'][-365:])
axes.set_xlabel('Time')
axes.set_ylabel('Price')
axes.set_title('TSE_6902_1_Year')
axes.legend()

plt.show()
```

実行結果

```
python sample.py
```

![Figure_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/344880/8f46781f-42da-f94f-ef9a-f023c788cacf.png)

どのデータを使って何をするか考えることが一番難しい気がする。
日経平均株価も取れるみたいで、工夫すれば色々できそうに思います。
> [pythonで日経平均株価を取得してみた](https://qiita.com/nakagawa333/items/642c422367c3dd015110)

# 参考
[Quandl API Documentation](https://docs.quandl.com/#authenticating-your-requests)
[pythonで東証から株価をAPI取得して、データをChartに表示させる](https://qiita.com/yasutaka_ono/items/2e52b6a4ef0666282896)
[PythonでQuandlから金融データを取得する](https://www.codelab.jp/blog/?p=1105)
[yahoo finance](https://stocks.finance.yahoo.co.jp/stocks/qi/?ids=3650)
[日本株式のデータをスクレイピングなしで取得・リストにしたい](https://qiita.com/Kuma_T/items/911b5201c9313717ab50)
[PythonでWebスクレイピングをしよう（株価）](https://qiita.com/neet-AI/items/da55e4fbcb1c91dfd094)
[pythonで日経平均株価を取得してみた](https://qiita.com/nakagawa333/items/642c422367c3dd015110)
EC2インスタンスの起動

# はじめに
UdemyでAWSの勉強をしたので、備忘録として、残す

# EC2インスタンスの概要
* 仮想のコンピューティング環境
    * 従量課金制

* EC2を起動までの手順
    * OS/Imageの選択
    * インスタンスタイプの選択
    * ストレージの選択
    * セキュリティグループの設定
    * SSHキーペアの作成

# EC2インスタンスの作成

1. サービス検索で"EC2"を検索。「インスタンスの作成」ボタンを押す。

2. AMI（Amazonマシンイメージ）の選択。今回は上から2番目の普通の Amazon Linux にしました。

    |![スクリーンショット 2019-08-23 8.52.54.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/58c555d1-2d11-83f0-74a7-37efedeec168.png)
|:-:|

3. インスタンスタイプの選択。無料枠のt2.microにしました。

    |![スクリーンショット 2019-08-23 8.53.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/278b7056-c59c-0a25-be54-3a8ebb3dcbd8.png)
|:-:|

4. 基本デフォルトで作成。ネットワークはデフォルトで作成することは推奨されていませんが、テストなので、今回はそのままで作成。「ストレージの追加」を押す。

    |![Componentdetail.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/36f2ce82-0467-00bc-eb4c-cee7dbf19b7d.png)
|:-:|

5. ストレージもデフォルトのまま。「タグの追加」ボタンを押す。

    |![スクリーンショット 2019-08-23 8.57.00.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/0dfd1e73-f20e-d598-0d79-c74c4f098df8.png)
|:-:|

6. タグはなんでもつけられるのですが、名前として、"Sample EC2"で設定。「セキュリティグループの設定」を押す。

    |![スクリーンショット 2019-08-23 8.56.52.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/2aeb9f30-4c78-2e8e-f8ab-66fb5a61d420.png)
|:-:|


7. 今回はapacheをサーバにインストールして、webからアクセスできるようにするので、「ルールの追加」ボタンで HTTP も追加する。これもあまりよくないのですが、ソースはフルオープンで。実際にサービスを運用するときはSSHに関しては、ポートもソースも変更してください。「確認と作成」ボタンを押す。

    |![Componentsettings.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/c05adff7-6170-d9f7-bbf8-f81e42ca0104.png)
|:-:|

8. 確認画面です。「起動」ボタンを押します。

    |![Componentconfirm.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/a85367ea-4bdd-8908-65b1-464b5c5bad30.png)
|:-:|

9. 最後にキーペアのダウンロードです。初めての場合はキーペアが無いと思うので、新しいキーペアの作成をします。任意のキーペア名をつけて、「キーペアのダウンロード」ボタンを押してください。その後、「インスタンスの作成」ボタンを押します。

    |![Componentkeypair.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/0436f22e-11aa-e4c7-13d3-12bb3f700d0f.png)
|:-:|


10. 無事、インスタンスが起動していることを確認しましょう。インスタンスの状態がrunningであることと、ステータスチェックがOKなことを確認すればよいです。

    |![Componentkido.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/462106/1e48edfd-5753-754d-a666-9c3f0510eb7d.png)
|:-:|

# おわりに
ただインスタンスを立てただけですが、誰かの役に立てば、、
ssh でインスタンスに入って、apacheをインストールして、webからアクセスできるようにします！
ヤマハルータのDHCP機能でIoT機器に固定IPアドレスを発行する場合の注意

# DHCPのClient-Identifierオプションが使われる場合、使われない場合

多くのPCやスマートフォンのDHCPクライアント機能が送出するDHCPメッセージは、Client-Identifierオプションを使う形で発行される。私が確認した例では、以下の機器がこのパターンに該当した。

* Windows10 PC
  * イーサネットインタフェースのドライバは「Realtek PCIe GBE Family Controller」とあった
* Androidスマートフォン:HTC E11 Life
  * Androidのバージョンは8.0.0

これに対し、IoT機器のDHCPクライアント機能が送出するDHCPメッセージは、Client-Identifierオプションを使わない形で発行されることがある。私が確認した例では、以下のIoT機器がこのパターンに該当した。

* Google Home Mini
* Philips hue

# 接続されている機器のDHCPクライアント機能がClient-Identifierオプションを発行しているかどうかを確認する

ヤマハルータにおいて、接続されている機器のDHCPクライアント機能がClient-Identifierオプションを発行しているかどうかは、`show status dhcp`コマンドで確認することができる。

接続されている機器のDHCPクライアント機能がClient-Identifierオプションを発行している場合、`show status dhcp`の当該機器に対する結果は以下のようになる。

```
割り当て中アドレス: xxx.xxx.xxx.xxx
 (タイプ) クライアントID: (01) 23 45 67 89 ab cd
リース残時間: ...略
```

IPアドレスに対応するMACアドレスが出力される部分において、タイトルが「(タイプ) クライアントID」となっているのがポイントである。

一方、接続されている機器のDHCPクライアント機能がClient-Identifierオプションを発行していない場合、`show status dhcp`の当該機器に対する結果は以下のようになる。

```
割り当て中アドレス: xxx.xxx.xxx.xxx
クライアントイーサネットアドレス: 01:23:45:67:89:ab
リース残時間: ...略
```

IPアドレスに対応するMACアドレスが出力される部分において、タイトルが「クライアントイーサネットアドレス」となっているのがポイントである。

# 本題…注意点は何か

ヤマハルータのDHCPサーバ機能において、特定のMACアドレスに対して発行されるIPアドレスを固定するために使われるコマンドは`dhcp scope bind`である。ところが、このコマンドの書式は、DHCPクライアントがClient-Identifierオプションを発行する場合と発行しない場合で異なるのである。以下にその違いを記す。ここで、`xx:xx:xx:xx:xx:xx`というのは、対象機器のMACアドレスを指すものとする。

* 対象機器のDHCPクライアントがClient-Identifierオプションを発行する場合…`dhcp scope bind {スコープ番号} ethernet xx:xx:xx:xx:xx:xx`
* 対象機器のDHCPクライアントがClient-Identifierオプションを発行しない場合…`dhcp scope bind {スコープ番号} xx:xx:xx:xx:xx:xx`

間違った書式の`dhcp scope bind`を使った場合、**指定したMACアドレスに対して指定したIPアドレスが発行されない。**
iniファイルをpython3で参照する方法

#概要

pythonで事前設定値を投入する際に設定ファイルから設定値を読み取ることができるようにする必要があったので、調べた際の情報をここにまとめる。

##条件
- Windows10

- Python 3.7.1

#初期化ファイル(iniファイル)

##初期化ファイルとは

主にWindowsで使用される設定
以下に初期化ファイルの例を示す。

```:.iniファイル
; コメント
;[セクション名]
[ini1]
;オプション名 = 値
Timestamp = enable
Server_access = FTP
Server_ip = ip_addr1
[ini2] 
Timestamp = disable
Server_access = FTP
Server_ip = ip_addr2 
```

##pythonで.iniを参照する方法

python標準であるConfigParserモジュールを使用する。

```python:iniファイルの読み込み
import configparser
inifile = configparser.ConfigParser()
inifile.read("test.ini","utf-8")
#設定ファイル内のセクション名とオプション名で値にアクセスできる。
print(inifile['ini1'])
print(inifile['ini1']['Timestamp'])
```

```:実行結果
<Section: ini1>
enable
```
inifile.readを変数に代入するとlist型になってしまうのでうまくいかない。

```python:失敗例
import configparser
inifile = configparser.ConfigParser()
file = inifile.read("test.ini","utf-8")

print(type(file))
print(file['ini1']['Timestamp'])
```
```:実行結果
<class 'list'>
TypeError: list indices must be integers or slices, not str
```


#参考サイト

[初期化ファイルについて](http://home.a00.itscom.net/hatada/windows/file/profile01.html)

[pythonで初期化ファイルを参照する方法](https://qiita.com/satio_koibuti/items/767ec763f4711c66c89e)
ディープラーニングでドラゴンクエストライバルズのAIを作る【0日目】

ドラゴンクエストライバルズをプレイするAIを作っていきます。
ディープラーニングを使ってそれなりに強いAIを作ることが目的です。
(8/27更新)
※本ページは各ページの「もくじ」的な使い方をするので，
随時更新していきます。

0日目はマイルストーンの提示と前提条件、ゴール設定など。

# ドラゴンクエストライバルズとは
ドラゴンクエストシリーズのモンスター同士を戦わせるカードゲームです。

【公式サイト】
https://www.dragonquest.jp/rivals/

iOS，Android，NintendoSwitchなどでプレイ可能です。
ゲームの仕組みはシャドウバースに似ており，
かなり大雑把に言うとシャドウバースのカードがドラクエになったようなものです。

# マイルストーン

・1日目
[「ディープラーニングでドラゴンクエストライバルズのAIを作る【1日目】」はこちら
](https://qiita.com/dqr-ml/items/2ace7b4de623c2691244)
まずは、人間がインタラクティブにプレイするドラゴンクエストライバルズを実装します。
GUIなどはもちろんなく，コンソールでプレイできるものを作っていきます。
フル規格のドラゴンクエストライバルズの実装は当然無理なので簡易版をまず実装します。
ルールや使えるカードはかなり限定的になるかと。
言語はディープラーニングとの相性の良い，pythonを使っていきます。

持っていないカードが多く恥ずかしいですが，下記のデッキを実装します。
![IMG_0351.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/487017/bf093b3a-d904-7cdc-75e8-539d8993d70c.png)

・2日目
[「ディープラーニングでドラゴンクエストライバルズのAIを作る【2日目】」はこちら](https://qiita.com/dqr-ml/items/594e5b6c3d637a7aa963)
1日目でひとまずゲームが実行できる状態になるので、
極力シンプルなとても弱いAIを実装します。
取り得るアクションをランダムで選ぶAI(AIと呼べるか怪しいが)を実装します。
ここではまだ機械学習によるAIの強化はできていない状態ですね。
ここでの目的はAIに多量の試合を行わせて，
多量の試合のログを取得することです。

・3日目
ここでやっと機械学習の要素が出てくるのですが，
2日目で取得した試合のログをディープラーニングで分析して，
勝ち筋のパターンを分析します。

・4日目
3日目で学習した勝ち筋を元にプレイするAIを実装します。

・5日目
強化したAI同士を戦わせてどんどん強くする仕組み(強化学習)を実装していきます。

#前提条件とゴール
おそらく個人の範疇では全てのカードの特性を実装するのは不可能と考えています。
そのため，数多あるカードの中から最強のデッキを作るAIを構築するのはかなり難しいかと思います。
ひとまずは限定されたカードの中から，構築済みのデッキを用いて戦うAIを作ります。
それなりに強いAI同士を戦わせて，あるデッキとあるデッキが戦った場合の勝率を算出することが当面のゴールになります。
人間がプレイすると1試合5分くらいかかりますが，AIではマシンパワー次第で1000試合,2000試合とできますので，デッキの勝率の定量的な分析ができるようになるかと思います。
その結果を元にどのカードを追加すると勝率が上がるか定量的に分析できるようになればなかなか有益なツールになるかと。

© 2017-2019 ARMOR PROJECT/BIRD STUDIO/SQUARE ENIX All Rights Reserved.
© SUGIYAMA KOBO
linux のユーザーとグループに関するメモ

# ユーザーとグループ

ユーザーは複数のグループに所属する。
ユーザーは primary グループを一つ持つ。
primary group は例えば所有者を特に指定せずにファイル作った時の、その所有グループになったりする。
`newgrp` で primary group を変更したりできる。

# /etc/passwd, /etc/shadow, /etc/group, /etc/group

`/etc/passwd` にユーザー情報が記述される。
パスワード、uid、primary group id、ホームディレクトリ、ログインシェルの情報を持つ。
パスワード詳細情報だけ `/etc/shadow` に切り出される場合がある。
むしろ最近は全部 `/etc/shadow` で管理される様子。

`/etc/group` にグループ情報が記述される。
(グループ)パスワード、gid、所属ユーザーの情報を持つ。
ユーザーの場合と同様に、パスワードだけ `/etc/gshadow` に切り出されうる。

`/etc/passwd` の primary group 情報と、 `/etc/group` の所属ユーザー情報が合わさって、最終的なユーザー所属するグループが決まる様子。

# /etc/sudoers

sudo で、誰が誰として、どんなことができるかを記述する。

もっぱら、以下の記述がよく見かけられる。

```
root    ALL=(ALL)       ALL
%wheel  ALL=(ALL)       ALL
```

１行目は、「root ユーザーが、全ての場所で、全てのユーザーとして、全てのコマンドを実行できる」を意味する。

# wheel グループ

sudo (as root) できるグループを慣習的に wheel と読んできた。
あと、 pam のモジュールとしてもそのような制御が用意されている模様。
iosのシミュレータ立ち上げの際に[Error: Could not find iPhone X simulator](ReactNative)

# シミュレータ起動の際、エラー発生

ReactNativeでiosのシミュレータを立ち上げる際に下記エラーが発生しました。

```
Found Xcode project ReactNativePlatform.xcodeproj

Could not find iPhone X simulator

Error: Could not find iPhone X simulator
```
シミュレータが無いという文言が書いてあります。

# 解決法
`/node_modules/react-native/local-cli/runIOS/findMatchingSimulator.js`を開いて、下記記述を変更します。

前

```
if (!version.startsWith('iOS') && !version.startsWith('tvOS')) {
  continue;
}
```

後

```
if (!version.startsWith('com.apple.CoreSimulator.SimRuntime.iOS') && !version.startsWith('com.apple.CoreSimulator.SimRuntime.tvOS')) {
  continue;
}
```

# 参考
[react-native run-ios returns Error: Could not find iPhone X simulator](https://stackoverflow.com/questions/54504076/react-native-run-ios-returns-error-could-not-find-iphone-x-simulator/55671675#55671675)
【Rails6 + RSpec】controllerテストでActionView::Template::Errorが発生する場合

# 今回検証した環境
- Rails 6.0.0
- rspec-rails 3.8.2

# 現象
例として、`users_controller`の`#new`アクションをテストするとします。

```ruby:app/controllers/users_controller.rb
class UsersController < ApplicationController
  def new
  end
end
```

```ruby:Gemfile
group :development do
  gem 'rspec-rails'
end
```

```ruby:spec/controllers/users_controller_spec.rb
require 'rails_helper'

RSpec.describe UsersController, type: :controller do

  describe "GET #new" do
    it "returns http success" do
      get :new
      expect(response).to have_http_status(:success)
    end
  end

end
```

この状態でテストを実施すると以下のようなエラーが出ます。

```
$ bundle exec rspec
1) UsersController GET #new returns http success
   Failure/Error: get :new

   ActionView::Template::Error:
     wrong number of arguments (given 2, expected 1)
```

# 原因
RSpecのバグみたいです。
詳しくは[こちら](https://github.com/rspec/rspec-rails/issues/2086)を参照

# 対策
とりあえず`v4.0.0`のベータ版をインストールすることで解決します。
正式リリースを待ちましょう。

(2020/03/25 追記)
`rspec-rails`の`v4.0.0`がリリースされました！

```ruby
group :development do
  gem 'rspec-rails', '~> 4.0.0'
end
```

# 参考
[Controller spec failed with 6.0.0.beta2](https://github.com/rails/rails/issues/35417)
processingでloadImageする場所を間違えてjava.lang.reflect.InvocationTargetExceptionが出てエラー

processingで画像を表示しようとしてエラーが出た

メッセージは
java.lang.reflect.InvocationTargetExeption


```
PImage ○○ = loadImage("○○.png") ;

void setup(){
  size(512,512);//画面サイズを初期化
}

void draw(){

  image(○○,0,0);

}

```

これでは無理だった。

loadImageをsetup(){}内で記述しないといけないらしく

```

PImage ○○;

void setup(){
  size(512,512);//画面サイズを初期化
 ○○ = loadImage("○○.png") 
}

void draw(){

  image(○○,0,0);

}

```

これでいけた。

draw(){}
の中に書いてしまうと、処理が遅くなるらしいのでやっぱりsetup内に書かないといけないようだ


公式リファレンスには

>
In most cases, load all images in setup() to preload them at the start of the program. Loading images inside draw() will reduce the speed of a program. Images cannot be loaded outside setup() unless they're inside a function that's called after setup() has already run.
Paper.js 図形の表示

##図形の表示
canvasを直接利用するより、Paper.jsやKineticJS、Fabric.js、EaselJSなどのライブラリを利用するほうが簡単。

Paper.js
・ http://paperjs.org/


```js
$(document).ready(function(){
  'use scrict';
  
  paper.install(window);
  paper.setup(document.getElementById('mainCanvas'));

  //ここで描画する
  let c = Shape.Circle(200, 200, 50);
  c.fillColor = 'green';

  paper.view.draw();


  paper.setup(document.getElementById('mainCanvas_2'));

  //ここに描画する
  let c2;
  for(let x = 25; x < 400; x += 50){
    for(let y = 25; y < 400; y += 50){
      c2 = Shape.Circle(x, y, 20);
      c2.fillColor = 'green';
    }
  }

  paper.view.draw();
});
```


##onMouseDownを記述してイベントハンドラを追加する
ユーザーがクリックしたときに円を描画する

```js
$(document).ready(function(){
  'use scrict';
  console.log('main.js を読み込み中...');

  paper.install(window); //paper の準備1
  paper.setup(document.getElementById('mainCanvas')); //mainCanvas をキャンバスに

  let tool = new Tool();

  //Hello World
  let c = Shape.Circle(200,200,80); //円の図形
  c.fillColor = '#000'; //黒く塗る

  let text = new PointText(200,200); //新しいテキストを領域中央に
  text.justification = 'center' //センタリング
  text.fillColor = '#fff'; //色
  text.fontSize = 20; //フォントサイズ
  text.content = 'hello world'; //文字列

  //イベントハンドラ
  tool.onMouseDown = function(event){
    let c = Shape.Circle(event.point.x, event.point.y, 20);
    c.fillColor = 'green';
  }

  paper.view.draw();//必要？
});
```
pyOpenGLのglBufferData

# pyOpenGLのglBufferData

の仕様がよくわからん。
undocumentedなのである。
調べていたら自分の過去記事が出てきて、２年前も同じところではまってたよ・・・

https://ousttrue.github.io/posts/glbufferdata

思い出したのでちょっとまとめておきます。

## 実験

```py
    #vbo
    def set_vertex_attribute(self, component_count: int, bytelength: int,
                             data: any) -> None:
        ''' float2, 3, 4'''
        self.component_count = component_count
        stride = 4 * self.component_count
        self.vertex_count = bytelength // stride
        self.bind()
        glBufferData(GL_ARRAY_BUFFER, bytelength, data, GL_STATIC_DRAW)

   #ibo
    def set_indices(self, stride: int, bytelength: int, data: Any) -> None:
        self.index_count = bytelength // stride
        self.bind()
        if stride == 1:
            raise Exception("not implemented")
        elif stride == 2:
            self.index_type = GL_UNSIGNED_SHORT
        elif stride == 4:
            self.index_type = GL_UNSIGNED_INT
        glBufferData(GL_ELEMENT_ARRAY_BUFFER, bytelength, data, GL_STATIC_DRAW)
```

```py
self.positions = (-1.0, -1.0, 1.0, -1.0, 0.0, 1.0) # vec2 x 3
self.indices = (0, 1, 2)
```

### ctypesで配列を作って渡す

動く

```py
float6 = (ctypes.c_float * 6) # float[6] 型
values = float6(*self.positions)
self.vbo.set_vertex_attribute(2, 4 * 2 * 3, vallues)
self.ibo.set_indices(4, 12, (ctypes.c_uint * 3)(*self.indices))
```

### bytes 作って渡す
動く
structでpackして、bytesを作る。

```py
self.vbo.set_vertex_attribute(2, 4 * 2 * 3, struct.pack("6f", *self.positions))
self.ibo.set_indices(4, 12, struct.pack("3I", *self.indices))
```

### array.array に入れて渡す
意外にも動かなかった。
対応するハンドラが無いというエラーになる。

```py
self.vbo.set_vertex_attribute(2, 4 * 2 * 3, array.array('f', self.positions))
self.ibo.set_indices(4, 12, array.array('I', self.indices))
```

### memoryview
エラーにならないが動かない。

```py
self.vbo.set_vertex_attribute(2, 4 * 2 * 3, memoryview(struct.pack("6f", *self.positions)))
self.ibo.set_indices(4, 12, memoryview(struct.pack("3I", *self.indices)))
```

## ctypes か bytes が動く
もしくは numpy

# まとめ
久しぶりに PyOpenGL やったら、過渡期のOpenGLのコードとか出てきたのでついでに整理しなければと思った。
 
DirectXの方は、11 か 12 かしか無くてバージョンの問題は無いのだけど、OpenGLの方はいろいろあるが OpenGL4が d3d11 相当くらい？。ベースラインを最低でも `WebGL2.0` あたりに揃える必要があると思った。学習用でも、それより古い OpenGL を使うのはあまりよろしくないなと。
なので、

`WebGL2.0 - OpenGLES3.0 - OpenGL3.3(Core profile)` が最低ラインになるか。

動くコード

https://gist.github.com/ousttrue/c4ae334fc1505cdf4cd7
FUZE BASICを触ってみる４（寄り道して環境整備編）

# 今日やること

前回、画面描写がきちんとされない現象にぶつかりました。
フルスクリーンモードがきちんと動かないなどから環境の問題の可能性があるため、RaspberryでもFuzeBasicの環境を入れて同じコードを試したかったのですが、手元に新しいSDカードがなくて諦めました。

描写問題に真面目に対応するために `Games Worksheet` を進めても良かったのですが、ここで一旦寄り道して環境整備をすすめます。
そもそも前回プログラムが長くなりすぎて、FuzeBasicのエディタ(FuzeEditor)だと辛くなりつつあったんですよね。

なので、ホストのMac側でソースコードを編集して、Ubuntuで実行する流れにしてみます。
fuze basicの実行がコマンドラインからできればよかったのですが、できなさそう😭
👆FuzeEditorを介さずに実行できました👍🏻

- Macでファイル編集して
- FuzeBasicでソースファイルをロードして実行

のサイクルが可能か試してみました。

-> 今回の整備の結果、こうなりました

- VSCでファイル編集
- Ubuntu側でコマンドラインから直接実行

快適になりました🎉

# アンカー

前の記事）[FUZE BASICを触ってみる３（ゲームの入り口）](https://qiita.com/suruseas/items/7d7c4e472d99d6cfda32)

# まずは、Vagrantのファイル共有について

と言ってもやることは簡単。vagrantfileを書き換えました。ホストの `toybox` を `/home/vagrant/Desktop/fuze-basic/toybox` に割当ました。

https://github.com/suruseas/fuze

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/144344/7ec0ea8f-5c4a-98d3-5373-13cdab31b2b4.png)

# VisualSourceCodeでソースを編集して、Ubuntuで実行してみる

よっしゃと思ったのもつかの間。VSCで開こうとすると「このファイルはバイナリかサポートされてないテキストエンコード…云々」。
え？と思ってMIMEタイプを調べてみるとなんと `charset=binary` 

```
$ file --mime toybox/1.fuze
toybox/1.fuze: text/plain; charset=binary
```

たしかに強引に開くとファイルの最後になんかある。ソースコードの部分は読めているので文字とバイト列が混在しているからバイナリと判定したと思われます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/144344/1547bf46-f62d-7f4c-2fe0-8253b30053ac.png)

まぁでも思考停止して、まずは普通にVSCでコード書いて動かしてみて動かなかったら謎の４文字をバイナリで追記すればじゃん、と思ったのですが結論として実行自体は問題なかったです。

確認したところ、FuzeEditorで保存するときに追加されるみたいでした。

# 気持ち悪いのでエディタ使わないで直接実行する方法を探してみた

「fuze commandline execute」とかで検索してみてもぜんぜん見つからないんですよね…ということはできないのかな。エディタ使いたくないなぁ…思ってコマンドがちゃがちゃ試していたら…

```
vagrant@vagrant:~/Desktop/fuze-basic/toybox$ fuze --help
?
Usage: fuze [-f] [-d] [-H] [-m mode] [-x xSize] [-y ySize] [-z bpp] [-l] [-D] <filename>
vagrant@vagrant:~/Desktop/fuze-bas
```
`--help` って解釈できなかったんだな…って、おぉぉ？… `filename` がある ❗️❗️❗️

おもむろに実行すると…

<img width="1203" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/144344/c12af93c-ae84-b2cd-b235-642231686136.png">

おお、実行できた！そして、謎のバイト列もつかない！
今後はこれで開発することにします🤓

# 所感

- コマンドラインから直接実行できるので、VSCでソース修正 -> Ubuntuで実行のサイクルが確立できた！
- 気持ち悪いバイト列ともオサラバ🙋🏻‍♂️
- `-x, -y, -mode`以外のオプションがなんなのか。調べたけど見つからない。キニシナイ！
- VSCのシンタックスハイライトが欲しい。。。
AWS東京リージョンの障害についてメモ

AWSの某AZで障害が起きた件で、Feedが騒がしかった。以下は私見。

- Qiitaその他の有益な情報が流れて見えない。鬱陶しいから早く沈静化してほしい。
- AWS利用者はSLAを読め。
 - もともとEC2, RDSで月間稼働率 100% は約束されていない。
 - SLAに満たなかった部分はサービスクレジットの請求を検討しろ。
 - https://aws.amazon.com/jp/compute/sla/
 - https://aws.amazon.com/jp/rds/sla/
- サービスの一時停止は起こるもの。
 - 想定していなかったのなら、想定しなかった方が残念。
- 障害のリスクを受容するか、回避するかは経営判断。
 - https://ja.wikipedia.org/wiki/%E3%83%AA%E3%82%B9%E3%82%AF%E3%83%9E%E3%83%8D%E3%82%B8%E3%83%A1%E3%83%B3%E3%83%88#%E3%83%AA%E3%82%B9%E3%82%AF%E5%AF%BE%E5%BF%9C
 - 開発者は複数AZを使って、高コストで高い信頼性のシステムを作ってもよい。
 - 単一AZで作って、低コストで低い信頼性のシステムを作ってもよい。
 - AWSでなくGCPで作ってもよい。
 - オンプレミスで作ってもよい。
- 経営判断に重要なことは３つ。
    - リスク発生率、発生時の深刻さ、システムの目的を考慮して、合理的かつ経済的な選択がされていること。
    - 品質水準が意識的に制御されていること。（高くても低くてもいい。意図的なら。）
    - 判断内容が経営陣の支持を得ていること。
RailsでTwitterAPI制限を取得する方法

# はじめに
こちらの記事では簡単にRubyOnRailsでTwitterのAPI制限値を取得していきたいと思います。初めてAPIを使ってみたい方にとってTwitterのAPIは使用しやすいものかな、と思っています。
しかし去年のちょうど今頃、TwitterAPIを使用するためにDeveloperアカウントを申請しなくてはならなくなりましたので、使えるようになるまでの敷居が高くなってしまいました・・・
つい最近個人でDeveloperアカウントを申請したのですが、比較的短い文章？で承認されましたので、いつか公開できればなと思っています^^

**こちらの記事は『Railsの環境構築』『Developerアカウントの取得』を前提としておりますのでご了承ください。**

# Gemfile
まずはGemfileに下記を記述します。
そして `bundle install` コマンドを打ってください。

```
source 'https://rubygems.org'
git_source(:github) { |repo| "https://github.com/#{repo}.git" }

ruby '2.4.2'
.
..
...
....(省略します)

gem 'twitter'

```

# Keyを記述し、API制限を取得する
ご自身で作成してあるいずれかのControllerに下記を記述してください。
TwitterDeveloper画面の `Apps > 自分のApp名 > Keys and tokens` から取得＆生成することができます^^
ここで取得しているAPIの種類は `/search/tweets` というもので、ツイートを検索する時に使用するものになります。他に指定できるAPIの種類はたくさんございますので、TwitterAPIのドキュメントを見てみてください。
https://developer.twitter.com/en/docs.html

```
class TopController < ApplicationController
  def index
    # Twitterのクライアントを作成する。
    client = Twitter::REST::Client.new do |config|
      config.consumer_key        = "**********"
      config.consumer_secret     = "**********"
      config.access_token        = "**********"
      config.access_token_secret = "**********"
    end

    # API制限を取得する
    rate_limit_status = client.__send__(:perform_get, '/1.1/application/rate_limit_status.json')
    p rate_limit_status[:resources][:search][:"/search/tweets"]
  end
end
```

# ログ
ログをみてみてください！
すると、制限が取得できているはずです^^

```
# ログ
{:limit=>180, :remaining=>180, :reset=>1566629720}
```

パラメータの詳細は、
`limit → 最大リクエスト数
remaining → リクエスト残数
reset → リセット時間`
です。
あと何回リクエストができるかは `remaining` を見れば良さそうですね。

またリセット時間はUNIX時間となっておりますので、日本時間に変換するためには

```
Time.at(rate_limit_status[:resources][:search][:"/search/tweets"][:reset])
```

で変換することができます！


# 終わりに
以上がTwitterのAPI制限を取得する方法になります。
私のQiitaでは、RubyOnRailsを中心に、どうすればRalisでWebサイトを構築できるか、本番環境にアップロードをするにはどうするかなどの記事を公開していきたいと思います。
プログラミングの勉強をしている方、独学で勉強している方など、少しでも助けになれればと思います^^
vim + ripgrep + fzf

# リポジトリ
[https://github.com/BurntSushi/ripgrep](https://github.com/BurntSushi/ripgrep)
# インストール
**mac**

```
$ brew install ripgrep
```

**CentOS**


# fzf
## リポジトリ
[https://github.com/junegunn/fzf](https://github.com/junegunn/fzf)
[https://github.com/junegunn/fzf.vim](https://github.com/junegunn/fzf.vim)

## インストール
**mac**

```
brew install fzf
```
**.vimrc**

```
" fzf
call dein#add('junegunn/fzf', { 'build': './install --all', 'merged': 0 })
call dein#add('junegunn/fzf.vim', { 'depends': 'fzf' })
```
```
:call dein#install()
```

# Ctags
mac

```
brew install --HEAD universal-ctags/universal-ctags/universal-ctags
```
【Spring Boot】SpringBootApplicationでちょっと試してみたいとき

SpringBootApplicationでちょっと試してみたい時、下記クラスのmainメソッドで試す事ができます。

````Spring公式サイトから引用.java
package hello;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;

@SpringBootApplication
public class Application {

	private static final Logger log = LoggerFactory.getLogger(Application.class);

	public static void main(String[] args) {
		SpringApplication.run(Application.class);
	}

	@Bean
	public CommandLineRunner demo(CustomerRepository repository) {
		return (args) -> {
			// save a couple of customers
			repository.save(new Customer("Jack", "Bauer"));
			repository.save(new Customer("Chloe", "O'Brian"));
			repository.save(new Customer("Kim", "Bauer"));
			repository.save(new Customer("David", "Palmer"));
			repository.save(new Customer("Michelle", "Dessler"));

			// fetch all customers
			log.info("Customers found with findAll():");
			log.info("-------------------------------");
			for (Customer customer : repository.findAll()) {
				log.info(customer.toString());
			}
			log.info("");

			// fetch an individual customer by ID
			repository.findById(1L)
				.ifPresent(customer -> {
					log.info("Customer found with findById(1L):");
					log.info("--------------------------------");
					log.info(customer.toString());
					log.info("");
				});

			// fetch customers by last name
			log.info("Customer found with findByLastName('Bauer'):");
			log.info("--------------------------------------------");
			repository.findByLastName("Bauer").forEach(bauer -> {
				log.info(bauer.toString());
			});
			log.info("");
		};
	}
}
FastlaneのコマンドをBitriseに組み込む(ios,ReactNative)

下記記事でReactNativeアプリのデプロイをFastlaneで自動化する手順を紹介しました。
[FastlaneでReactNativeのデプロイを自動化する(ios)](https://qiita.com/kenkono/items/a3eb4d1a83d8b1d70864)

今回はCICDツールとして有名な`Bitrise`を使用して、Githubにpushした際に、自動的にfastlaneが実行する仕組みを構築します。
android版はこちら↓
[FastlaneのコマンドをBitriseに組み込む(android,ReactNative)](https://qiita.com/kenkono/items/9e00eb3de49208e8892e)

# 事前準備
Bitriseに対象となるGithubのrepositoryを登録しておきます。
注意点として、SSHの公開鍵の登録ですが、repositry単体ではなく、Githubユーザーに対して登録するようにします。
repository単位で登録すると、fastlane実行の際に証明書を引っ張ってくる場所でエラーが発生します。

Bitrise
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/013be289-b728-e529-ad2a-cc3c90fc0e86.png)
GitHub
![Screen Shot 2019-08-24 at 15.48.47.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/1c1fb906-5e31-dc55-8c1b-bc40cbba4025.png)



# 環境変数の設定
下記の変数を追加します。
`GITHUB_USER_EMAIL`と`GITHUB_USER_NAME`は使用しているGithubの情報を入力します。
![Screen Shot 2019-08-24 at 15.27.52.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/2b97f355-943f-4e25-760c-0e85171a4aad.png)

# secretの設定
下記の変数を追加します。
- FASTLANE_USER = apple ID
- FASTLANE_PASSWORD = apple IDのパスワード
- MATCH_PASSWORD = githubのパスワード（repositoryにある証明書を取得するため）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/0ded784f-9753-7cfb-a60c-7c5aedf8f683.png)

# Workflowの設定
下記イベントを追加します。
基本的に追加した後に設定を変更する必要はありませんが、一部イベントは記述を書き換えます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/13b18dff-1556-79c5-0730-72061b3904f3.png)

### Script
script contentsを下記のようにします。

```
#!/usr/bin/env bash
# fail if any commands fails
set -e
# debug log
set -x

# Add github.com to known host 
ssh-keyscan -t rsa github.com >> ~/.ssh/known_hosts

# Configure Git user
git config --global user.name $GITHUB_USER_NAME
git config --global user.email $GITHUB_USER_EMAIL
```

### Run npm command

Working directory
$BITRISE_SOURCE_DIRを入力
The `npm` command with arguments to run
installを入力

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/ce56dc11-7a5a-357b-ce6c-34d2a10c7602.png)


### fastlane
fastlane lane
$FASTLANE_LANEを入力
Working directory
$FASTLANE_WORK_DIRを入力
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/16c7e051-ca67-4dd8-941c-ae85617f1c32.png)

# トリガーの設定

任意のブランチにpushした際に、どのwrokflowを実行するかを設定します。
workflowは先程設定したflowを選択します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/291139/d22f6df1-89d8-8f23-b614-e31bee46786b.png)

# 実行
指定したbranchにpushしますと、Bitriseが発動します。

# バージョン番号の自動インクリメントについて
fastlaneの設定でバージョン番号は自動的に上がるのですが、Bitriseのサーバ上で実行されるため手元のファイルでは更新されない問題が発生します。
下記記事でそれに対する対応法を記述しました。
[Bitriseのナンバリングを利用して、バージョンの自動インクリメントを実現(ReactNative, ios)](https://qiita.com/kenkono/items/e5a2be486840bb07b86c)
Vue.jsでフォローボタンと、フォロ数、フォロワー数の連携を実装する

![follow0830.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/91907/1ddf5b6e-d46b-9a1e-fa45-de1554f5a117.gif)

**フォロー機能はLaravelと、Vue.jsで実装してる**
フォローボタンと、フォロ数、フォロワー数の連携以外の部分は下記を見れば実装することができる。
https://www.youtube.com/watch?v=ImtZ5yENzgE

**フォロー機能については主に下記２点が大事と思う**
１．ユーザー登録機能がないとできない。
　　- Laravelの認証機能で簡単に実現できる
２．DBの設計では多対多であるユーザーテーブルと、プロファイルテーブルを持つことが必要。

#npmの準備
LaravelはVue.jsが標準搭載されていまして、前準備はNode.jsをインストールしてnpmの使用
ができるようにするだけ。

- node.jsとnpmのインストール

```ruby:
   sudo yum install nodejs npm --enablerepo=epel
```
- npmのバージョンアップ

```ruby:
   npm install -g npm 
```
- Vuexのインストール  
　コンポーネント間での通信（兄弟コンポーネント）を実現するのにVuexを必要とする。

```ruby:
   npm install vuex --save
```
- 依存パッケージをインストール 

```ruby:
   cd /path/to/laravel /* Laravelルートディレクトリへ移動 */
   npm install 
```
- フロントエンドのビルド

```ruby:
   cd /path/to/laravel /* Laravelルートディレクトリへ移動 */
   npm run watch
```

以上でLaravel上のVue.jsがちゃんと動くはず！


#ディレクトリの構成
- Laravelのresourcesディレクトリの構成

<img width="291" alt="スクリーンショット 2019-08-24 16.09.06.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/91907/a82b6e14-0095-bf7f-2e20-07dcbb7fdeb9.png">

- views/profiles/index.blade.phpはフォローボタンと、フォロ数、フォロワー数を表示する
- js/app.jsはVueコンストラクタからインスタンスを生成する
- js/components/follow-button.vueはフォローボタンの単一ファイルコンポーネント
- js/components/followers.vueはフォロワー数の単一ファイルコンポーネント
- js/components/following.vueはフォロー数の単一ファイルコンポーネント
- js/store/store.jsはアプリケーションの 状態（state） を保持するVuexを取り込む

ソースコードはgithubにアップする。後ろの部分にリンクを貼る。


#Vuex
スコープ関係で他コンポーネントにthisで参照する事ができないが、Vuexを使うことでコンポーネントの間で同一のデータを共有することが出来る。特に非親子コンポーネント間の通信はストアVuexを使わないと混雑になる。
**js/store/store.js**について詳しく説明する  
store.js
<img width="1440" alt="スクリーンショット 2019-08-24 16.58.58.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/91907/582aacc9-980c-0ea9-d412-1516e0613767.png">

15行目followUserメソッドはフォローボタンがクリックされた時のアクション、VuexではStoreの状態を変えるactionはすべてstore自身の中にないといけないため、フォローボタンのコンポーネントに書いていない。

１６行目axios.postはaxios(Promise)で非同期通信を行ってる。ここでサーバーにフォローと、フォローの解除を行う処理してる。

17行目はPromiseのthen()を使うコールバック処理、成功した場合は「true」を25行目.thenに渡して、フォローと、フォローの解除をした後のフォロ数、フォロワー数を数えてストアに反映させる。

**GitHub**
https://github.com/iwaoo/laravel_login
TOPPERS/ASPカーネルビルド用のDockerfile

[STM32CubeIDEでTOPPERS/ASPカーネルを動かす - 準備編](https://qiita.com/imagou/items/8e19ed77884af4fb4e71)を参考に構築をしました。これで環境の部分は簡単にできると思います。

ツッコミ・アドバイス色々お願いします。

```
# Pull base image.
FROM ubuntu:16.04

# Install
RUN apt update && DEBIAN_FRONTEND=noninteractive apt install -y build-essential gcc g++ cmake libgtest-dev google-mock \
    make fish wget git libboost-all-dev openssh-server libboost-regex1.58.0 libboost-regex1.58-dev lib32stdc++6 lib32ncurses5 lib32z1

# ARMコンパイラのインストール
RUN apt install -y gcc-arm-none-eabi gdb-arm-none-eabi

# ST-LINKのインストール
RUN apt install -y libusb-1.0
RUN git clone https://github.com/texane/stlink && cd stlink && make && \
    cd build/Release && make install && ldconfig

# mbed

# gmockのビルド
WORKDIR /usr/src/gmock/
RUN cmake . && make && ln -s /usr/src/gmock/*.a /usr/lib

# gtestのビルド
WORKDIR /usr/src/gtest/
RUN cmake . && make && ln -s /usr/src/gtest/*.a /usr/lib

# 起動シェルの変更
CMD ["/usr/bin/fish"]
```

あとはマウント設定などをシェル化しておけばだいぶ楽かなと。
MNCTF2017 情報照合☆★★

#問題

http://mnctf.info/mnctf2017/top.php

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/80e9ea9f-c284-a7c6-006f-802a331dda06.png)

#解いてみた

ハッシュリストをダウンロードして、中身を見てみると1000件もあります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/18855956-d09e-3a4f-dbbf-7974c6e63be7.png)

手作業で確認するのは現実的ではないですね。
リファレンスを見てみます。
英語は読めませんが、図がたくさんあったので意味は分かりました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/b41f7332-4b35-5233-0e6c-abc4d5494468.png)

とりあえず1リクエストで答えがもらえるわけではなく、まずはトークンをもらう必要があって、そのトークンとハッシュ値で検索すると答えがもらえる仕組みみたいです。

まぁpythonがやっぱりラクなんですかね。
とか思ったけどあえてのExcel VBAでやってみよう。

A列に検索するハッシュ値を保存して、トークンをB列に保存する。
ハッシュ値を検索した結果をC列に保存するようなプログラムです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/63454106-54c3-eff1-1af2-a79ec1ace85a.png)

これで実行してみます。

メモリが足りないのか

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/8457a503-bef0-d02c-cfcf-983edc3fa6be.png)

ここでずっととまったまま。。。
中で処理が動いていたらいいんですが。。。
どうやらメモリを開放しないといけないような気がします。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/1c288d16-dc51-8c63-7628-292b3ec2b8b7.png)

こんな感じでメモリ開放するようにして、再度実行です。
あまり変わりませんでした。
が、実は裏では動いているようで、数分ほっておくと一気に全部書き込まれました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/17681/9ea0f0fb-9860-728a-f00c-a6a2184c7724.png)

これが答えです。
bundle installでHTTPErrorにハマった話【Mac】

bundle installでHTTPErrorが発生し、色々な方法をトライしましたが解決せず、結局超単純な方法で解決したので書きます。

# 目次
1. 実施環境
2. 発生した問題
3. 試してダメだったこと
4. 試して解決したこと
5. 最後に

# 1. 実施環境
  * 実施日：2019/8/24
  * 端末：Mac Book Pro（2019/7/10購入）
  * OS：MacOS Mojave バージョン10.14.6
  * 通信環境: モバイルWi-Fi（UQ WiMAX）
  * Ruby: 2.6.3
  * Rails: 6.0.0
  * ターミナル: iTerm2 3.3.1

# 2. 発生した問題
rails6のbundle install時に以下のエラーが発生。

```
$ bundle install --path=vendor/bundle
Fetching source index from http://rubygems.org/

Retrying fetcher due to error (2/4): Bundler::HTTPError Could not fetch specs from http://rubygems.org/

Retrying fetcher due to error (3/4): Bundler::HTTPError Could not fetch specs from http://rubygems.org/

Retrying fetcher due to error (4/4): Bundler::HTTPError Could not fetch specs from http://rubygems.org/

Could not fetch specs from http://rubygems.org/
```

# 3. 試してダメだったこと
## 3-1. 5分待つ
いつの間にか直ってた、との記事を見つけたので待ってみました。

```
# 5分待つ
$ bundle install --path=vendor/bundle
#=> 同様のエラー発生。
```


## 3-2. モバイルWi-Fiを再起動する
通信環境の問題との記事を見つけたので、モバイルWi-Fiを再起動してみました。

```
# モバイルWi-Fiを再起動
$ bundle install --path=vendor/bundle
#=> 同様のエラー発生。
```

## 3-3. hostsファイルに追加
名前解決できていないことが原因との記事を見つけたので、hostsファイルに追記してみました。

```
$ host rubygems.org
rubygems.org has address 151.101.64.70
rubygems.org has address 151.101.0.70
rubygems.org has address 151.101.128.70
rubygems.org has address 151.101.192.70
rubygems.org has IPv6 address 2a04:4e42::70
rubygems.org mail is handled by 10 mxa.mailgun.org.
rubygems.org mail is handled by 10 mxb.mailgun.org.
$ sudo vi /etc/hosts
#=> 以下4行を追記
151.101.64.70 rubygems.org
151.101.0.70 rubygems.org
151.101.128.70 rubygems.org
151.101.192.70 rubygems.org
$ bundle install --path=vendor/bundle
#=> 同様のエラー発生。
```

## 3-4. httpsをhttpに変更
httpsをhttpに変更するとうまくいったと書かれた記事があったので試してみました。

```
$ vim Gemfile
#=> https://になっているところをhttp://に変更する。
## 変更前
source "https://rubygems.org"
## 変更後
source "http://rubygems.org"
$ bundle install --path=vendor/bundle
#=> 同様のエラー発生。
```

# 4. 試して解決したこと
PCを再起動したら何事もなかったかのように解決しました...！

```
# PC再起動
$ bundle install --path=vendor/bundle
Fetching gem metadata from https://rubygems.org/.............
Fetching gem metadata from https://rubygems.org/.
Resolving dependencies...
Fetching rake 12.3.3
~略~
```

# 5. 最後に
もしかしたらiTerm2再起動しても、解決したのかも...と思ってしまいました。
やっぱり、困ったらPC再起動ですね！
ご覧いただきありがとうございました。
LeetCode / Excel Sheet Column Title

（[ブログ記事](https://mhiro216.hatenablog.com/entry/2019/08/24/171325)からの転載）

[https://leetcode.com/problems/excel-sheet-column-title/]

Given a positive integer, return its corresponding column title as appear in an Excel sheet.

For example:

```
1 -> A
2 -> B
3 -> C
...
26 -> Z
27 -> AA
28 -> AB 
...
```

エクセルシートの列名をインデックスに読み換える問題です。実務で必要とされることが多そうな処理ですね。

#### 解答・解説

##### 解法1
まず、Discussionにとても素敵な整理表がありましたので共有します。
<img width="683" alt="スクリーンショット 2019-08-23 23.37.03.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/122973/f3d0cbe0-16ba-11fb-0134-c6daa414cd46.png">
列名とインデックスの対応はこのようになっています。

一の位は、nを26で割った時の余りに対応しています。割り切れた場合はZに対応します。
十の位は、nを26で割った時の商を、26で割った時の余りに対応しています。割り切れた場合はZに対応します。
百の位以上も同様です。

とすると、{1:'A', 2:'B', ... , 25:'Y', 0:'Z'} というような列名とインデックスの対応を格納した辞書を作成した上で、
nを26で割った余りを格納し、次はnを26で割った商を26で割った余りを格納し、、、を繰り返していけば良いように一瞬思えます。

ただ1つ落とし穴があって、この方法だと2桁以上のZZ, ZZZといったZのみから成る列名でうまくいきません。
例えば702は本来ZZですが、702/26の商は27・余りは0、27/26の商は1・余りは1で、AAZとなってしまいます。
nを26で割った時の商を次のループに回すのではなく、n-1を26で割った時の商をを次のループに回せば、うまくいきます。

```python
from string import ascii_uppercase

class Solution(object):
    def convertToTitle(self, n):
        """
        :type n: int
        :rtype: str
        """
        d = {0:'Z'}
        for i,s in enumerate(ascii_uppercase):
            d[i+1] = s
        result = []
        while n > 0:
            result.append(d[n%26])
            n = (n-1) // 26
        result.reverse()
        return ''.join(result)
```

nを26で割った時の余りの値を列名に対応させるのは、{1:'A', 2:'B', ... , 25:'Y', 0:'Z'} ではなく {0:'A', 1:'B', ... , 24:'Y', 25:'Z'} として、
n-1を26で割った時の余りの値を列名に対応させても良いので、コードをすっきりさせることができます。

```python
from string import ascii_uppercase

class Solution(object):
    def convertToTitle(self, n):
        """
        :type n: int
        :rtype: str
        """
        d = {}
        for i,s in enumerate(ascii_uppercase):
            d[i] = s
        result = []
        while n > 0:
            result.append(d[(n-1)%26])
            n = (n-1) // 26
        result.reverse()
        return ''.join(result)
```

##### 解法2
解法1ではstringライブラリを使いましたが、ord(s)でアスキーコードを取り出して数列を作り、chr(n)で文字に戻すことでA-Zの文字列から成るリストを作ることができます。

```python
class Solution(object):
    def convertToTitle(self, n):
        """
        :type n: int
        :rtype: str
        """
        capitals = [chr(x) for x in range(ord('A'), ord('Z')+1)]
        result = []
        while n > 0:
            result.append(capitals[(n-1)%26])
            n = (n-1) // 26
        result.reverse()
        return ''.join(result)
```
【salesforce】一覧

# レーニング内容一覧
## Classic、Visualforce、Apex、コントローラー
　　1. オブジェクト、タグ、アプリケーション作成
　　　[Classic基本知識ーオブジェクト、タグ、アプリケーション作成](https://qiita.com/training_zhang/items/9329e44288a72403aa75)
　　2. Visualforceページ作成
　　　[Classic基本知識ーVisualforceページ作成](https://qiita.com/training_zhang/items/ff00617d310cafb3236d)
　　3. タブと項目名の変更
　　　[Classic基本知識ータブと項目名の変更](https://qiita.com/training_zhang/items/8022ee4fa2c62e202af1)

## Lighting
　　1. Lightning入門
　　　[Lightning基本知識ーLightning入門](https://qiita.com/training_zhang/items/0da9e3d4a0ca3b57eea2)
　　2. Lightningクライアントコントローラー
　　　[Lightning基本知識ーLightningクライアントコントローラー](https://qiita.com/training_zhang/items/a2df87a2b488119720ac)
　　3. Lightningバックエンドコントローラー
　　　[Lightningバックエンドコントローラー](https://qiita.com/training_zhang/items/a8951bb3d69f075bb902)
　　4. Lightningコンポーネント間通信（イベント）
　　　[Lightningコンポーネント間通信（イベント）](https://qiita.com/training_zhang/items/477596ad002012034acf)

## トリガー、非同期処理、Test
　　1. トリガー
　　　[Apex トリガ](https://trailhead.salesforce.com/ja/content/learn/modules/apex_triggers)
　　2. 非同期処理
　　　[非同期 Apex](https://trailhead.salesforce.com/ja/content/learn/modules/asynchronous_apex)
　　3. Test
　　　[Apex テスト](https://trailhead.salesforce.com/ja/content/learn/modules/apex_testing)
Leetcode #833: Find And Replace in String

```swift
func findReplaceString(_ S: String, _ indexes: [Int], _ sources: [String], _ targets: [String]) -> String {
    var answer = [Character]()
    var str = Array(S)
    var  index = 0
    var i = 0
    let offsets = indexes.enumerated().sorted(by: {$0.element < $1.element}).map {$0.offset}
    let indexes = offsets.map {indexes[$0]}
    let sources = offsets.map {sources[$0]}
    let targets = offsets.map {targets[$0]}
    
    while i < str.count {
        if index >= indexes.count {
            answer += Array(str[i...])
            break
        }
        if i == indexes[index] {
            if str.count - indexes[index] < sources[index].count {
                index += 1
                continue
            }
            var possible = true
            for j in stride(from: 0, to: sources[index].count, by: 1) {
                if str[i+j] != Array(sources[index])[j] {
                    possible = false
                    break
                }
            }
            if possible {
                answer.append(contentsOf:Array(targets[index]))
                i += sources[index].count
            }
            index += 1
        } else {
            answer.append(str[i])
            i += 1
        }
    }
    return String(answer)
}
```
Rails5のAjax

[Rails Guide](https://railsguides.jp/working_with_javascript_in_rails.html)の説明を読んでもいまいちよくわからなかったので頭の整理をするために書いておく。

1. form_with, link_to, buttonなどでAjaxリクエストを送信
2. コントローラーの respond_toの中にformat.jsを書くと対応するxxxx.js.erbでJavascriptコードを作成する。

```users_controller.rb
def index
  @users = User.all
  respond_to do |format|
    format.js
  end
end
```
3. 返されたJavascriptによって元画面の書き換えが行われる。

```index.js.erb
# 実際はappendToではなくreplaceWithを使って書き換えるケースが多いと思う。
$("<%= escape_javascript(render @users) %>").appendTo("#users");
```

ちなみに `renders @users` は 対応する部分テンプレート(_user.html.erb)に受けとったデータを描画する。
Visual Studio Codeで選択したパス（ファイル、ディレクトリ）を既定のアプリで開く（Windows編）

VS Code のエディター画面で編集中のテキストに URL を貼り付けると、
![vscodelink.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/463374/0b088cdb-4dae-678c-338e-35cb8c83fac9.jpeg)
このようにリンク先を既定のブラウザで表示させることができます。

ローカルファイルやディレクトリへのパスはハイライトされませんが、いちいちエクスプローラーやブラウザにコピペするのも面倒です。`file:///C:/~` という表記で無理矢理リンクにすることはできますが、バイナリファイルやディレクトリを表示しようとするとエラーになってしまいます。[^1] どうにかしたい。

[^1]: バイナリファイルを既定のアプリで開きたい時には [Open](https://marketplace.visualstudio.com/items?itemName=sandcastle.vscode-open) 拡張機能がおすすめです。バイナリファイルを開くと「このファイルはバイナリか、サポートされていないテキストエンコードを使用しているため、エディターに表示できません。**このまま開きますか？**」と表示されます。強制的に表示した後、コマンドパレットからこの拡張機能を呼ぶと既定のアプリで表示させることができます。

## 選択したパス（ファイル、ディレクトリ）を既定のアプリで開くタスクを構成する

というわけで [Integrate with External Tools via Tasks](https://code.visualstudio.com/docs/editor/tasks) を参考にタスクを構成してみます。

.vscode ディレクトリに `tasks.json` を作成して、次のように記載してください：

```tasks.json
{
    "version": "2.0.0",
    "tasks": [
        {
            "label": "選択したリンクを既定のアプリで開く",
            "type": "shell",
            "command": "explorer ${selectedText}",
            "group": "none",
            "presentation": {
                "reveal": "never"
            },
            "problemMatcher": []
        }
    ]
}
```

このタスクを実行するとエディタで選択した中のテキストを `explorer.exe`に渡すので、既定のアプリで開いてくれます。カレントディレクトリはVS Codeのワーキングディレクトリになるので、プロジェクト内の相対パスでも開くことができますね。[^2]

[^2]: たとえば `.vscode\tasks.json` を選択してタスクを実行すると上記のファイルが開きます。便利！

## 参考リンク

* [【VSCode tips】VSCode で go buildする設定 【#1】](https://qiita.com/necomeshi/items/676ccb669d6e6102117b)
webarenaでubuntu その28

#概要

webarenaでubuntu18.04やってみた。
apache2.4やってみた。
rewriteやってみた。

#rewriteを有効に。

```
sudo a2enmod rewrite
```

#.htaccessを書く。

```
RewriteEngine On
RewriteRule ^(.*)\.html$ $1.php
```

以上。
create-react-appで始めるReactの起動まで

ターミナルを開き、コマンドを実行する

```sh
npx create-react-app my-app
cd my-app
```
npxを使用すれば、npm installでローカルやグローバルにパッケージを落とさなくてもパッケージを使用することができる。1回限りに使用したいときなどに便利。
create-react-appでreactのアプリケーションを生成、babelやwebpackなどのパッケージをインストールしてくれる。

インストールされたアプリケーションの構成は下記のようになる

```
my-app
├── README.md
├── node_modules
├── package.json
├── .gitignore
├── public
│   ├── favicon.ico
│   ├── index.html
│   └── manifest.json
└── src
    ├── App.css
    ├── App.js
    ├── App.test.js
    ├── index.css
    ├── index.js
    ├── logo.svg
    └── serviceWorker.js
```

my-app上で下記コマンドを実行する

```sh
npm start　my-app
```
下のような画面が[http://localhost:3000/](http://localhost:3000/)で立ち上がる
<img width="1239" alt="スクリーンショット 2019-08-21 23.02.03.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/484272/52cfad2d-ef8c-b70d-3aa5-ec79b0576737.png">

index.jsではAppというコンポーネントの出力をrootにレンダリングしている。

```index.js
ReactDOM.render(<App />, document.getElementById('root'));
```

レンダリング先はindex.htmlのrootになる。ReactはSPAのアプリケーションのため、レンダリング先はindex.htmlのみになる。

```
my-app
├── public
│   ├── index.html
```

```index.html
<div id="root"></div>
```

rootにレンダリングされるApp.jsの中身は下記の通り

```jsx:App.js
import React from 'react';
import logo from './logo.svg';
import './App.css';

function App() {
  return (
    <div className="App">
      <header className="App-header">
        <img src={logo} className="App-logo" alt="logo" />
        <p>
          Edit <code>src/App.js</code> and save to reload.
        </p>
        <a
          className="App-link"
          href="https://reactjs.org"
          target="_blank"
          rel="noopener noreferrer"
        >
          Learn React
        </a>
      </header>
    </div>
  );
}

export default App;
```

[http://localhost:3000/](http://localhost:3000/)でブラウザが立ちがり、App関数内のreturnの中身がレンダリングされる。
Windows 10 + PostgreSQL 10.10 に orafce を組込む

　タイトル通りにorafceを組込みたいのですが、WebからDLしたDLLでは、動いてくれない（```create extension orafce;```でエラー）ので自力でビルドし、実行確認までの備忘録になります。また、CMake も触ったことがないのでパスの指定が行えれば、問題ないと思ったのもあり、力業で作業を進めました。

# 準備するリソース
1. orafce 3.8 [ここからDL](https://github.com/orafce/orafce)
ビルドするソースになります。

2. Binaries from installer Version 10.10 (Win x86-64) [ここからDL](https://www.enterprisedb.com/download-postgresql-binaries)
orafceが使えることの確認のため、インストールせずに使える形式のものを使います。
3. icu4c-64_2-Win64-MSVC2017 [ここからDL](https://fossies.org/windows/misc/icu4c-64_2-Win64-MSVC2017.zip/)
orafceのビルドに使用します。

4. Visual Studio Community 2019
orafceをビルドするのに使用します。

# orafceのビルド
Visual Studio 2019を起動し、プロジェクトやソリューションを開くから、「ORF_HOME\msvc\orafce.2010.sln」を開く。

ORF_HOME は、DLしたorafceを解凍したディレクトリになります。

以下、orafceのビルドで発生したエラーの内容と対応を記載します。
### MSB8003	The VCToolsInstallDir property is not defined
ソリューション ⇒ プロパティ
構成 ⇒ 全般
プラットフォーム ツールセット
the build tools for windows7.1sdk
を
Visual Studio 2019 (v142)
に変更し、

ツール ⇒ ツールと機能を取得を選択
個別のコンポーネントタブを開く
MSVC v142 VS 2019 C++ X64/x86 ビルドツール（v14.22）にチェックマーク付けて追加インストールする。

### ヘッダーファイルが見つからない
変数「PG_HOME」は、PostgreSQLのバイナリー版を解凍したディレクトリになります。<br/>変数「ICU_HOME」は、ICUを解凍したディレクトリになります。

* postgres.h

ソリューションを右クリック ⇒ プロパティを選択
構成プロパティ ⇒ C/C++ ⇒ 全般の
追加のインクルードディレクトリで「PG_HOME\include\server」を設定する

* libintl.h

ソリューションを右クリック ⇒ プロパティを選択
構成プロパティ ⇒ C/C++ ⇒ 全般の
追加のインクルードディレクトリで「PG_HOME\include」を設定する

* netdb.h

ソリューションを右クリック ⇒ プロパティを選択
構成プロパティ ⇒ C/C++ ⇒ 全般の
追加のインクルードディレクトリで「PG_HOME\include\server\port\win32」を設定する

* dirent.h

ソリューションを右クリック ⇒ プロパティを選択
構成プロパティ ⇒ C/C++ ⇒ 全般の
追加のインクルードディレクトリで「PG_HOME\include\server\port\win32_msvc」を設定する

* unicode/ucol.h

ソリューションを右クリック ⇒ プロパティを選択
構成プロパティ ⇒ C/C++ ⇒ 全般の
追加のインクルードディレクトリで「ICU_HOME\include」を設定する


### ライブラリが見つからない

* postgres.lib

ソリューションを右クリック ⇒ プロパティを選択
構成プロパティ ⇒ リンカー ⇒ 全般の
追加ライブラリのディレクトリで「PG_HOME\lib」を設定する


# セットアップ

### orafce のファイルを PostgreSQL の配下に配置する

* ORF_HOME\msvc\bin\x64\10.3\lib\orafce.dll

PG_HOME\lib\ にコピーします。

* ORF_HOME\orafce.control

PG_HOME\share\extension\ にコピーします。

* ORF_HOME\orafce--3.8.sql

PG_HOME\share\extension\ にコピーします。

### PostgreSQL サーバの設定

コマンドプロンプトを開きパスを設定します。

```
set PG_HOME="postgresql-10.10-1-windows-x64-binariesを解凍したディレクトリ"
set PATH=%PG_HOME%\bin;%PATH%
```
データベースの初期化（データベースクラスタの作成）

```
>cd /d %PG_HOME%\bin
>initdb -D %PG_DATA%
```
PG_DATA は、データベースのデータを保存するディレクトリを指定します。

データベースサーバを起動

```
postgres -D %PG_DATA%
```

### orafce を確認するDBを作成する

```
set PG_HOME="postgresql-10.10-1-windows-x64-binariesを解凍したディレクトリ"
set PATH=%PG_HOME%\bin;%PATH%
>cd /d %PG_HOME%\bin
bin>psql -h 127.0.0.1 -p 5432 -d postgres
postgres=# CREATE ROLE admin LOGIN PASSWORD 'admin';
CREATE ROLE
postgres=# CREATE DATABASE testdb OWNER admin;
CREATE DATABASE
```
adminユーザは必要ありませんでした。initdb で Windowsユーザのロールが作成されていた。（後で知りました）


# 確認
A5 で接続し、下記コマンドで確認します。

```
create extension orafce;
select next_day(current_date, 'saturday');
```
HTTP PollingとWebSocket、それぞれのざっくりとした違い

# HTTP Polling
- 新着データの要求(Requset)に対し、データが存在した場合はすぐに応答(Response)を返しコネクションを切断する
- 新着データの要求に対し、データが存在しない場合もコネクションを切断する
- そのため、サーバーに対して定期的に要求(Request)を行う必要がある
- サーバー側からクライアントに直接送信することができない

# HTTP Long Polling
- 新着データの要求に対し、データが存在した場合にすぐに応答を返しコネクションを切断する
- 新着データの要求に対し、データが存在しない場合はサーバーとクライアント間のコネクションを維持したままとなる
- サーバー側で新着データを用意できたら応答を返しコネクションを切断する。その間、コネクションは維持されたまま
- 上記の定期的に要求を行うHTTP Pollingと比較すると、遅延が少ない
- コネクションを維持した状態で一定時間経過した場合には、切断し、再度要求を送り直す

# WebSocket
- 新着データの要求に対し、データが存在した場合にすぐに応答を返すが、コネクションは切断せず維持したままとなる
- 新着データの要求に対し、データが存在しない場合も、サーバーとクライアント間のコネクションを維持したままとなる
- サーバー側で新着データを用意できたら応答を返し、コネクションを維持し続ける
- 上記2つと比較すると、最初から最後まで繋ぎっぱなしで要求と応答を繰り返すことができる

# 参考になったページ
[WebSocketのキホン(SlideShare)](https://www.slideshare.net/You_Kinjoh/websocket-10621887)
[HTTP Long Pollingとは(Qiita)](https://qiita.com/kubocchi/items/efcf392862be24a3d06f)
[リアルタイムなwebアプリを実現する方法(ポーリング、Comet、Server Sent Events、WebSocket)(Qiita)](https://qiita.com/kimullaa/items/d49bd603be17b36f7495)
[Push技術(Wikipedia)](https://ja.wikipedia.org/wiki/Push%E6%8A%80%E8%A1%93#Long_polling)