OmniAICreator/Qiita-1.07M huggingface dataset:
Google Recruit

# はじめに

今回は以下の記事の「Google Recruit」及び「類題(最終課題)」を解くコードをRubyで実装する．
-   [Google recruit problem, exp and prime](https://qiita.com/daddygongon/items/ba94b0f2a73990fc6a07)

# Google Recruit

$e$(自然対数の底)の値で連続する10桁の数のうち，最初の素数を出力せよ．ただし，$e$は以下の数とする．

```
2.7182818284590452353602874713526624977572470936999595749669676277240766303535475945713821785251664274274663919320030599218174135966290435729003342952605956307381323286279434907632338298807531952510190
```

## 入力

まず上記の$e$の値を標準入力から読み込む．

```ruby:google_recruit.rb
exp = gets.to_s.chomp
exp = exp[0] + exp[2...exp.length]
```

## 素数判定

次に，与えられた自然数$n$が素数かどうかを判定する関数is\_primeを実装する．$a \times b = n$ となる自然数 $a, b$ について $\sqrt{n} < a$ ならば $b < \sqrt{n}$ が成り立つので，2から$\sqrt{n}$までの自然数で$n$が割り切れるか試すことで，$n$が素数かどうか判定できる．計算量は$O(\sqrt{n})$．

```ruby:google_recruit.rb
def is_prime(n)
  for i in 2..n do
    if n < i*i
      break
    end
    if n % i == 0
      return false
    end
  end

  return n != 1
end
```

## 答えを出力する

文字列から連続する10桁を切り出し，素数判定をすることで問題の答えを出力する．

```ruby:google_recruit.rb
for i in 0...exp.length - 10 do
  if exp[i] == '0'
    next
  end
  n = exp[i...i+10].to_i
  if is_prime(n)
    puts n
    break
  end
end
```

## 答え

上記のプログラムを実行した結果，答えは7427466391であった．

# 類題(最終課題)

以下のf(5)を求めよ．

```
f(1)=7182818284
f(2)=8182845904
f(3)=8747135266
f(4)=7427466391
f(5)=__________
```

## 考察

先ほど与えられた$e$に含まれる10桁で，数字和が49であるものが前から順にf(1), f(2), &#x2026; となっていることが(問題をそのままgoogle検索にかけることで)分かる．よって5番目に表れるそのような10桁を見つけるプログラムを書く．

## プログラム

文字列から連続する10桁を切り出し，数字和が49であるかどうか判定し，そのうち前から5番目のものを出力する．

```ruby:google_recruit_final.rb
exp = gets.to_s.chomp
exp = exp[0] + exp[2...exp.length]

cnt = 0
for i in 0...exp.length - 10 do
  digit_sum = 0
  for j in 0...10 do
    digit_sum += exp[i + j].to_i
  end

  if digit_sum == 49
    cnt += 1
  end

  if cnt == 5
    puts exp[i...i+10]
    break
  end
end
```

## 答え

上記のプログラムを実行した結果，答えは5966290435であった．

------
 - **source** ~/grad_members_20f/members/ryuta-kikuchi/qiita_articles/google_recruit.org
OracleDBを中途半端にアンインストールしてしまった場合の対処法

#背景
OSがWindows10HomeのローカルにOracle Database 12c Release 1をインストールする際に、Oracle Database Configuration Assistantが「進行中」のまま進まない問題が発生。
#原因
以前にインストールしたOraceDBをアンインストールしたつもりでも、何らかの理由で関連するフォルダ・ファイルやサービスやレジストリのデータが削除されずに残っている。
#対応方法
1. サービス名の頭がOracleとなっているサービスを削除する。
　　<br>
   ※コマンドプロンプトで、sc.exe delete [サービス名]で削除できる。
   <br>
   ※サービス名は、対象のサービスを右クリック⇒プロパティから確認できる。
2. レジストリから「HKEY_LOCALMACHINE\SOFTWARE\ORACLE」を削除する。
3. 以下のディレクトリを削除する。(他にもあるかもしれない)
　　<br>
・C:\app(インストール時に指定したOracleベース・ディレクトリ)
　　<br>
・C:\Program Files\Oracle(ソフトのインストール場所)

####「このファイルを変更するには XXXX からアクセス許可を得る必要があります」が出てファイル・フォルダを削除できない時に実行すること
消したいファイルや（一番上の）フォルダのプロパティを開き、以下の2点を実行する。
・プロパティ > セキュリティ > 詳細設定 > 所有者タブ > 編集ボタンより自ユーザーを
  　追加した後、「サブコンテナーとオブジェクトの所有権を置き換える」にて置き換える。
・プロパティ > セキュリティ > 詳細設定 > アクセス許可タブ > アクセス許可の変更ボタン 
  　より自ユーザーを追加した後、「子オブジェクトのアクセス許可すべてを、
    　このオブジェクトからの継承可能なアクセス許可で置き換える」にて置き換える。
#参考文献と参考サイト
・【オラクル認定資格試験対策書】ORACLE MASTER Bronze［12c SQL基礎］
　（試験番号：1Z0-061）完全詳解＋精選問題集
　　発行所：SBクリエイティブ株式会社
・https://web.plus-idea.net/2013/04/windows-sc-delete-service/
・https://www.projectgroup.info/documents/Oracle/ORA-110006.html
・https://stakiran.hatenablog.com/entry/2018/01/26/204704
Linuxのファイルシステムを効率良く使う

ext系のファイルシステム (ext2/ext3/ext4) ではrootユーザーしか使えない領域が確保されるため、ディスク領域をフルで使えないことがあります。デフォルトではパーティションサイズの5%が確保されていますが、2TBのハードディスクでは100GBとなるので、無視できない分のサイズが使えない状態になります

# システム用に予約された領域の割当変更

```shell-session:shell
# tune2fs -m 0 ${デバイス}
```

* デバイスには @/dev/sde1@ のようにパーティションのデバイスパスを指定します
* `-m` オプションが確保する領域の比率です

システムファイルが含まれないユーザーデータ専用のパーティションであれば0%でも問題ありません。root用の専用領域は、一部のユーザーがデータを目一杯使ったとしても、システムの動作に影響が無いようにするための物なのでシステムの領域でなければ確保する意味がありません
LightsailにDockerでMetabaseを建てて、nginxでhttps化する

## モチベーション

- BigQueryとかPostgresに色々ため込んでいるので楽にクエリーしたい。
- どこからでもアクセスできると嬉しい。（ので、ローカルではない場所を求めた）
- なるべく安くしたい。（RasPiで自宅サーバーやる初期投資等から投資のNPVを考えたら、月千円くらいならいいか、と）
- 独自ドメインかつhttps化したい（.devだと必須だし） → 本文中 `YOUR-DOMAIN.HERE` を自分のドメインに置き換えてね。

## やったこと

### Lightsailの設定

- グローバルIPを設定しておく。
- ネットワークの設定で、httpsで使うポート`443`だけを空ける。
- （SSHの22は必要に応じて。自分の場合は別のLightsailインスタンスにVPNで繋いで作業しているので閉じたままにした。）

独自ドメインを使うということで、サブドメイン `metabase.YOUR-DOMAIN.HERE` をAレコードでLightsailインスタンスのグローバルIPに向けた。

### コンテナ内のデータを永続化するためのディレクトリを作る
```sh
mkdir -p ~/Docker/Metabase ~/Docker/LetsEncrypt ~/Docker/nginx
```

### Let's Encryptで独自ドメインの証明書を手配

- Certbotの公式イメージを使った。
- DNS認証にしているのは、複数ドメイン手配するときにやりやすかったから。
- 発行した証明書類は`/etc/letsencrypt`に書き出され、ホスト側で永続化される。

```sh
docker run -it --rm \
--name certbot \
-v ~/Docker/LetsEncrypt/cert:/etc/letsencrypt \
certbot/certbot certonly \
--no-self-upgrade \
--manual \
-d metabase.YOUR-DOMAIN.HERE \
-m info@YOUR-DOMAIN.HERE \
--agree-tos \
--preferred-challenges dns-01
```

### Metabaseを立ち上げる

- Metabaseの公式イメージを使った。
- ulimitはいらなそうだけど癖で付けていた。
- Metabaseの設定値を保存する先をデフォルトのH2にしていて、ファイルの作成先を`/metabase-data`にした上でホスト側のディレクトリにマッピングして永続化している。
- ホストがもう少しパワフルなら、H2の代わりにMySQLかPostgresを横に立ててもよさそう。

```sh
docker run --name Metabase -d \
--restart=always \
-v ~/Docker/Metabase:/metabase-data \
-e "MB_DB_FILE=/metabase-data/metabase.db" \
-p 3000:3000 \
--ulimit nproc=4096:4096 \
--ulimit memlock=256000:256000 \
--ulimit nofile=65536:65536 \
metabase/metabase
```

### nginxでリバースプロキシを構成する

まず作業用のディレクトリへ移動。

```sh
cd ~/Docker/nginx
```

TLS対応とリバースプロキシとしての動作を定義した`https.conf`ファイルを作成する。

```nginx
ssl_protocols TLSv1.2;
server {
    listen 443;
    ssl on;
    server_name metabase.YOUR-DOMAIN.HERE;
    ssl_certificate /etc/cert/fullchain1.pem;
    ssl_certificate_key /etc/cert/privkey1.pem;
    location / {
        proxy_pass http://metabase:3000;
        proxy_http_version 1.1;
        proxy_cache_bypass $http_upgrade;
    }
}
```

Dockerfile `dockerfile-nginx` を作成する。

```dockerfile
FROM nginx:latest
EXPOSE 443/tcp
ADD https.conf /etc/nginx/conf.d/default.conf
```

イメージをビルドする。

```sh
docker build -f dockerfile-nginx -t nginx-tls .
```

ビルドした設定済みnginxを、証明書を指定して立ち上げる。

```sh
docker run --name nginx -d \
--restart=always \
--link Metabase:metabase \
-v ~/Docker/LetsEncrypt/cert/archive/metabase.YOUR-DOMAIN.HERE:/etc/cert \
-p 443:443 \
nginx-tls
```

### Metabaseの書設定をする

ブラウザで `https://metabase.YOUR-DOMAIN.HERE/` にアクセスして、初期設定を行う。


## 証明書の更新に際して

Let's Encryptの証明書は3ヶ月で期限を迎えるので、その前に更新が必要。
更新もCertbotで行う。これをcronで自動化してもいい。

```sh
docker run -it --rm \
--name certbot \
-v ~/Docker/LetsEncrypt/cert:/etc/letsencrypt \
certbot/certbot renew
```

## メモ

- なぜDockerかというと…
    - LightsailインスタンスでCertbotを直接動かすのが面倒
    - 試行錯誤するのにホストを汚したくない
    - 必要に応じてメモリー制限をかけたい
- 業務用だったらこうはしない
    - ELBでhttps化してしまう


Enjoy!
自作言語で数当てゲームを作ろう！

# 自作言語のお時間です！

友達と集まる予定だったのが某ウイルスのせいでキャンセルになり落ち込んでるdangomushiです。
某ウイルス許すまじ。

## またまたまた作りました。

今回は完成度高いと思ってます。
個人的には今年一番の出来です。
苦労したのは、関数とかで一連の処理をまとめるところかな。とにかく悩みました。~~でもゆーて一週間ぐらいでできた~~
あ、そういえばついった始めました。なんか記事のミスとか「もっとこうしたらいいんじゃないの」とか「この処理はこうしたほうがいいだろ」とかゆうのは遠慮なくコメントかついったで教えてください。
URLはマイページにあると思います。
コードはこちらー＞https://github.com/pythonmaster1027/Omega-version0.2.3/tree/main

# 開発の一連の流れ

何気に皆さん説明したりしてなかったりしてるんですよね。（筆者の都合により、pythonで開発することを前提としております。ただし、もしあなたの主言語がpythonでなくても「できるかもしれん」とか「やってやらぁ」とかやる気があればぜひ挑戦するべきだと思います。）

０、予程決め。：絶対に抜かしてはいけません。私は、言語開発に限らずなんにでも予定を決めるよう心がけております。なぜなら、途中で「あれ？俺何するべきだ？」とかなるのは時間の無駄でしかないからです。あと、モチベがあるうちにぱっぱと作っちゃうほうが、開発が続くと思うからです。

１、仮想機械を作る。：読者の皆様は、おいおい初っ端からどうした、気でも違ったか、と思いでしょう。
しかし、できるんですよ。ま、仮想機械といっても僕の場合は四則演算をするだけですけどもね。それ以外は、言語の機能の拡張に伴って、そのまま載せてます。詳しくは、Githubのmain.py[Vmクラス]を見ていただければわかるでしょう。

２、文法決め。：一番大切だったりします。大切なのは、「書いてて楽しいかどうか」。可読性は、、、あとで何とかします。

３、字句解析器を作る。：お望みの文法に沿って字句解析器を作ります。実行速度は遅くなりますが、正規表現を使うことがベターと思われます。ただし私はすべて「置き換え」(replace)で乗り切りました。Tokenクラスで処理。

4、構文解析器を作る。：ここら辺から挫折者が大量発生すると思われます。でも私のコードを見ればわかる通り(Githubのリンクでとべるかと。)あんまりがちがちに「構文を解析するぜ！」的なもではないです。並べ替えただけです。ただ、自分の仮想マシンが理解できればそれでいいのです。そのために、先に仮想機械を作ったのですから。じつはTokenクラスで処理。

５、トランスパイル。：仮想機械の四則演算言語と構文解析した言語を、構文解析した後の「中間言語」とトランスパイルする。これのせいでreplaceを使う羽目になり、おかげで完成した言語は激遅です。python製だからか？~~子は親に似るんですね。~~この遅さは読者の皆さんの課題ということで。（←おい）これもTokenクラスで処理を行ってます。

# 文法

例えば、この処理はOmega言語(自作した言語の名前)で実行することが可能です（やっと本題）。
この処理は、一般に「数当てゲーム」といわれるものです。

```omega:main.om
def :main():
    input">"inp;
    if inp == dango = {test()};
    println_残念！;
    end;

def :test():
    println_正解!!;
    println_ゲームを続けるならｙ、やめるならｎを入力してください。;
    input">"ans;
    if ans == y = {start()};
    exit;

def :start():
    while_True = {main()};
    end;

start();

```
- 戻り値とか引数の辺りはまだ実装できてないです。次回への課題ですね。
- pythonでのprintに当たるのは、「println」です。printlnの後「_」(ハイフン)をつけて出力を行います。
- 基本的に、if / whileの中身は関数呼び出しとなります。これは、筆者の趣味で「厳格な関数型言語」にしたかったためです。ここら辺は応用ということで、気に食わなければ改造してください。
- あとは、inputの部分ですね。inputを使うよー＞inputの時の字ー＞格納する変数
- また、変数を初期化したりするときは「let」を使います。
- 文字列の時は、「str」を使います。
- 例として、文字列型の変数「word」を定義したいときは「str word = dangomushi;」とします。

# まとめ

今回は、「自作言語の作り方」を解説しました。感想としては、やはり言語の自作は楽しいですね(笑)。皆さんもぜひ言語自作に挑戦してみてください！！あと、前述のついったの件ですが"フォロワーを増やす方法が思いつかない"ばかりか、"そもそも同じ趣味の人と交流できない"ので、読者の皆さん、もし疑問があったり「この方がいいだろ」などご意見がありましたらぜひコメ欄かDMのほう来ちゃってください！！（ちゃっかり宣伝）
それでは、また次の記事でお会いしましょう！
さようなら！！
Pardot のメールマーケティング (Pardot Lightning アプリケーション) ⇒ メールの送信準備 (Pardot Lightning アプリケーション)

１．すでに送信しているメールを使用して、オプトインオーディエンスを増やす適切な戦略はどれですか?
２．メールで使用される変数タグで何が行われますか?
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/634241/f0fb93d3-138b-ca82-9c89-0ccd855b580d.png)
WordPessのテンプレートファイル

#WordPressのテンプレートファイル
**テンプレートファイル**とは？
WordPressのルールに沿って書かれた**PHPファイル**のことである。

##主なテンプレートファイル

| **テンプレートファイル名** | **概要** |
|:--- |:--- |
| front-page.php | Webサイトのトップページを表示
| single.php | 投稿の記事ページを表示 |
| page.php | 固定ページを表示 |
| category.php | カテゴリーページを表示 |
| search.php | 検索結果ページを表示 |
| archive.php | 記事一覧を表示 |
| 404.php | 404エラーページを表示 |

カスタム投稿タイプが「cat」の場合
single-cat.phpがテンプレートファイル名となる
vimの学習方法

#vim入門

### 誰のための記事？
・今までvimに一度も触ったことがない人
・vimに触ったことはあるが苦手意識を持っている人

### 概要
自分がvimを学んだ教材の中で、理想的だと思う順序で記述し直しました。
学び初めてまだ間もないのですが、今からvimを始めたいという人のがいたら一読して、気に入ったらvimを初めていただけたら幸いです。

---

- 公式のvim_tutorを数回
vimtutorというvimのチュートリアルを毎日行う。
超基本的なコマンドを演習付きで学べるため、最初にやるべき教材である。
繰り返しやって、演習の速度をあげる。


- vimを言語として捉える動画を視聴
vimはあくまでテキストの編集するものなのですが、それを言語として捉えるというコンセプトの動画です。
僕はこれを見ることでvimをやる目的が、編集速度の上昇のみならず、編集の考え方のエレガントさも加わりました。
https://www.youtube.com/watch?v=wlR5gYd6um0&feature=emb_title&ab_channel=thoughtbot

- .vimrcを編集
vimの設定ファイルであるvimrcを編集する。
いきなり様々な設定やプラグインを追加すると、vimの根本的な挙動を理解する経験を逸してしまうのでまずは最低限にする。
よっぽど不便でない限りは、他の操作に慣れてから徐々に増やすようにする。
HOMEディレクトリ下に以下のフォルダがあります。
```.vim/
├── colors/   <- directory for color schemes
├── plugin/   <- directory for standard plugins
└── vimrc     <- file with main config
```

- vscodeにエミュレタ追加
いきなり全てのコードをvi上で書くのはしんどいため、vscode上でもvimを使えるようにする。


### 最後に
vimを初めてまだまもないですが、あまりにvimが面白いので記事にしてみました。
vimを学ぶことは費用対効果からするとどれだけ効率的なのかは疑問ですが
<b>勉強する過程で得られる知的満足度が半端ない<b>ので、是非触れてみてもらえたら嬉しいです！



### 参考記事
https://peterxjang.com/blog/how-to-learn-vim-a-four-week-plan.html
https://towardsdatascience.com/what-ive-learned-after-using-vim-15-days-straight-ceda7e773a6d
Gitの基本操作メモ

Gitはバージョン管理システム
ターミナルでGitを操作します。
``git version``

# ユーザー情報設定
``git config --global user.name "Your Name"``
``git config --global user.email "hoge@hoge"``

# ユーザー情報確認
``git config --global user.name``
``git config --global user.email``
``git config --list``   # 全設定を表示


# 新規プロジェクトを作成
``git init``コマンドでリポジトリを新規作成する
``cd　~/``でターミナルの移動
``ls -a``コマンドで隠しファイルを含めたディレクトリ全内容を表示
``mkdir　[ディレクトリ名]``コマンドで新規ディレクトリを作成します。
``rm``コマンドでファイルを削除します。
``cp``コマンドでファイルをコピーします。
``mv``コマンドでファイルの移動とファイル名の変更を行います。
``git mv [old_file_name] [new_file_name]``


# 既存プロジェクトからGitを始めよう
``git init``でgitのバージョンを管理する``.gti/`ファイルを作成

# 基本的なワークフロー
1. ファイルの変更をてスージングエリア（控え室）へ追加する
2. ローカルリポジトリにコミットする
3. リモートリポジトリにプッシュする

## 1. ステージングエリアに変更を追加しよう
コミットの前にaddする
``git add [ファイル名]``ステージングエリアへ追加
``git add .``で全てのファイルをステージングエリアへ追加

## 2. コミットして変更を記録しよう
``git status``コミット状態や履歴を確認する
``git commit``
``git commit -v`` ファイルをコミットする
``git commit -m "コミットのコメントを入力"``　コミットした内容のコメントを含めてコミットする

#### コミットメッセージメモをする方法
半角英数字に切り替えて、``i``を入力し、変更メモを記入
``「esc」ボタン``を押す
``:wq``を入力したあと、``「Enter」``を押す

``git log`でコミットした記録を確認する

## 3.ファイルを削除したコミット方法

1. ``rm　[ファイル名]``でファイルを削除します。
2. ``ls``コマンドでファイルを確認する
3. ``git rm [ファイル名]``削除したファイルをステージングエリアへ追加
4. ``git commit -v``でコミットします。

## 4.複数ファイルを変更したコミット方法
1. ``git add .``で変更した複数ファイルをステージングエリアへ追加
2. ``git commit -v``でコミットします。
3. コミットメッセージを追加

#### 現在の状況を確認する
``git status``

#### リポジトリにコミットされたログを確認する
``git log``
- １行で表示する　``git log --oneline``
- ファイルの差分を表示する　``git log -p [ファイル名]``
- ``j``押すと、下に移動。``k``押すと、上に移動
- ``git log -n 3``最新変更した3つのログを確認する
- １行で最新の3つのログを表示する　``git log --oneline -n 3``

## 5. ファイルの変更差分を確認
``git diff``　ローカル環境とステージングエリアとの比較
``git diff --staged``ステージングエリアとコミット履歴の差分比較
``git diff HEAD``　ステージングエリアとコミットの差分を比較
- add commitをする前に、確認しよう

## 6. リモートリポジトリ（Github)に登録
- ``git remote add origin https://github.com/user/repo.git``
``https://github.com/user/repo.git``というgithub上に登録

- ``git push origin master``コマンドで、ローカルリポジトリの内容をリモートリポジトリへ送信する
- ``git push origin feature``featureブランチ名を送る

## 7. 管理しないファイルをGitの管理から外す

####　コミットしたファイルを削除
``git rm``コマンドで、コミットしたファイルをGitの管理から削除できる

- ``git rm　[ファイル名]``　ファイルも一緒に削除
- ``git rm　-r [ディレクトリ名]``　ディレクトリも一緒に削除


####　Gitの管理上だけファイルを残す場合
``git rm　--cached[ファイル名]``ファイルを残したまま、Gitの管理から外すことができます。

####　Gitの管理から削除したファイルを元に戻る
1. Git上　``git reset HEAD [ファイル名]``
2. ローカル上も戻す　``git checkout [ファイル名]``

---
# 参考サイト
- [Git公式ドキュメント](https://git-scm.com/book/ja/v2)
- [Gitコマンドリファレンス　～基本から応用まで～](https://qiita.com/ksj555/items/4b8973839346f2e7de40)
- [Udemy]
(https://www.udemy.com/course/intro_git/learn/lecture/6953312?start=0#content)
- [Git+GitHub入門 #10：コマンドラインで Gitを操作しよう] 
(https://www.youtube.com/watch?v=a7v1VK6ZCIU)
【Salesforce】Lightning Design Systemでアラート画面を作る

## アラート
以下がアラート画面のサンプルコードです。
前回の続きです。

■【Salesforce】Lightning Design Systemでモーダル画面を作る
https://qiita.com/quroooos/items/87709e68f2dd4fae99d8

``` html
<apex:page title="Test" showHeader="false" standardStylesheets="false" sidebar="false" docType="html-5.0">
  <html xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" lang="ja">
    <head>
      <meta charset="utf-8" />
      <meta http-equiv="x-ua-compatible" content="ie=edge" />
      <meta name="viewport" content="width=device-width, initial-scale=1" />
      <apex:slds />
    </head>

    <body style="padding: 8px;">
      <div class="demo-only" style="height:24rem">
        <section role="alertdialog" tabindex="0" aria-labelledby="prompt-heading-id" aria-describedby="prompt-message-wrapper" class="slds-modal slds-fade-in-open slds-modal_prompt" aria-modal="true">
          <div class="slds-modal__container">
            <header class="slds-modal__header slds-theme_error slds-theme_alert-texture">
              <h2 class="slds-text-heading_medium" id="prompt-heading-id">予期せぬエラーが発生しました</h2>
            </header>

            <div class="slds-modal__content slds-p-around_medium" id="prompt-message-wrapper">
              <p>予期せぬエラーが発生しました。システム管理者に連絡してください。</p>
            </div>

            <footer class="slds-modal__footer slds-theme_default">
              <button class="slds-button slds-button_neutral">閉じる</button>
            </footer>
          </div>
        </section>
        <div class="slds-backdrop slds-backdrop_open"></div>
      </div>
    </body>
  </html>
</apex:page>
```

以下がアラート画面の作成イメージです。
![Prompt_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/611228/4c350ac0-728d-f28f-ba66-296272cdc74f.png)

## アラート画面の構成
|要素|備考|
|:-:|:-:|
|ヘッダー（header）|アラートのヘッダー部分です。背景色は赤としています。|
|コンテンツ（div）|アラートのコンテンツ部分です。本文を記載します。|
|フッター（footer）|アラートのフッター部分です。閉じるボタンを配置するのが良いと思います。|

## 参考
■Prompt
https://lightningdesignsystem.com/components/prompt/
ABC163 C問題 with python3

#[ABC163 C問題 management](https://atcoder.jp/contests/abc163/tasks/abc163_c)

###一言メモ
tleになったのでどこをどう変えればいいか考えてみる。tleになると時間制限さえなければ正解だったのに惜しいなと思ってしまいがちだが間違いは間違い。計算量を考えてアルゴリズムを組むことを意識しよう。

###自分の誤答

```
N=int(input())
boss_list=list(map(int,input().split()))
num=0
 
for i in range(1,N+1):
    for j in range(i-1,N-1):
        if boss_list[j]==i:
            num+=1
    print(num)
    num=0
```

誤答のアルゴリズムは
社員番号２からNの全ての社員について上司の番号が１かどうか調べ、合致した回数を出力する.
社員番号3からNの全ての社員について上司の番号が2かどうか調べ、合致した回数を出力する.
...
社員番号N-1からNの全ての社員について上司の番号がN-2かどうか調べ、合致した回数を出力する.
社員番号NからNの全ての社員について上司の番号がN-1かどうか調べ、合致した回数を出力する.
という二重の繰り返し構造になっている。
この考え方だと無駄が多い。

約N回繰り返すfor文を二重に使っているのでオーダーが$O\left( N^{2}\right)$となりtleになった。
制約は$2\leqq N\leqq 2\times 10^{5}$なのでオーダーを$O\left( N\right)$に抑えたい。
出力はN回繰り返さなければいけないのでfor文でN回繰り返し１重で記述することを目指す。

###ポイント
リストをうまく使うことで繰り返し処理が減らせる。
今回の場合では要素数N個のリストを作成し、x番目に社員番号x番の部下の数を格納することにすると以下のように完結にコードが書ける。

###正解コード

```
N = int(input())
A = list(map(int, input().split()))

result = [0] * N
for a in A:
    result[a - 1] += 1
print('\n'.join(map(str, result)))
```

###考察
今回リストを使うことで簡潔にプログラムが書けたが、どのような時に使うと有効なのだろうか？
複数の数値が入ったリストAに対してそれぞれの数値が要素として何個入ってるかをデータとして取り出したいときに新しく0がいっぱい入ったリストBを作り、リストBのx番目にAに数値xが何個入ってるかを格納していくといい。
わかりやすい例を以下に挙げる。
1から3までの数字が入ったリストA=[3,2,1,2,3,2,3,1]についてそれぞれの数が何個入ってるか調べたい、
このとき新しくリストB=[0]*3を用意して以下の処理を行うとBに求めたいデータが格納される。

```
A=[3,2,1,2,3,2,3,1]
B=[0]*3

for i in A:
    B[i-1]+=1
print(B)

#このときBは[2,3,3]となる。Aに含まれてる1,2,3の個数がそれぞれ求まった。

```

###終わりに
今回の考察でわかったパターンは暗記しておくと他の問題を解くときにも使えそうだ。
####複数の数値が入ったリストについてそれぞれの数値の要素の数を求める
ときには反射でリストを使えば書ける！と思いつきたい。
Text Analytics の Docker コンテナを使ってキーフレーズを抽出する

## はじめに

Azure Cognitive Service のいくつかは Docker イメージが提供されています。
[ドキュメント](https://docs.microsoft.com/ja-jp/azure/cognitive-services/text-analytics/text-analytics-resource-container-config)に従って Text Analytics のキーフレーズ抽出を使ってみます。

## コンテナイメージの取得

Text Analytics は2020/12月現在パブリックプレビューとなっており、誰でも試す事が出来ます。

```bash
docker pull mcr.microsoft.com/azure-cognitive-services/keyphrase
```

## 実行の準備

Cognitive Service コンテナを実行するには、Azure に接続して課金情報を送信できる必要があります。
その為、先ず Azure に Text Analytics を作成し、エンドポイントと API キーを取得します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/64309/68685e53-5582-002d-870b-304b4b597f28.png)

## コンテナの起動

Eula の承認と Azure Text Analytics のエンドポイント, API キーを指定してコンテナを起動します。

```bash
docker run -it --rm -p 5000:5000 \
--mount type=bind,src=$HOME/output,target=/output \
mcr.microsoft.com/azure-cognitive-services/keyphrase:latest \
Eula=accept \
Billing=https://<your_app_name>.cognitiveservices.azure.com/ \
ApiKey=<your_api_key>
```


## Text Analytics API の実行

http://localhost:5000/swagger/index.html にアクセスすると swagger の API 仕様を参照できます。
サンプルを参考に適当に実行します。

```bash
curl -X POST \
-H 'Content-Type: application/json' \
http://localhost:5000/text/analytics/v3.0/keyPhrases \
--data '{"documents":[{"language":"ja","id":"1","text":"今日は大晦日なので、ビールを吐くまで飲みます。"}]}'
```

結果。

```json
{
  "documents": [
    {
      "id": "1",
      "keyPhrases": [
        "ビール",
        "大晦日",
        "飲み"
      ],
      "warnings": []
    }
  ],
  "errors": [],
  "modelVersion": "2019-10-01"
}
```

「今日は大晦日なので、ビールを吐くまで飲みます。」というフレーズから「ビール」「大晦日」「飲み」というキーワードが抽出されました。


## おわりに

Text Analytics コンテナを localhost で実行しました。感情分析 API 等も同じ様に実行する事が出来ます。
コンプライアンス上の観点からパブリッククラウドにデータを送る事が出来ないケースや、パフォーマンスの点でデータの近くで処理したいケースなどで有効だと思います。



## 参考

- [Azure Cognitive Services コンテナー - Docs](https://docs.microsoft.com/ja-jp/azure/cognitive-services/cognitive-services-container-support)
- [Text Analytics の docker コンテナーの構成 - Docs](https://docs.microsoft.com/ja-jp/azure/cognitive-services/text-analytics/text-analytics-resource-container-config)
MIDIの紹介

# 概要

5年ほど前にMIDIのアプリ＋パワポ資料を作ったのだが、少人数に共有して寝かせたままになっていた。
アプリはgithubに、パワポ資料はslideshareにアップロードした。

# スライド

[![thumbnail](https://image.slidesharecdn.com/midi-201230112729/95/introducing-of-midi-1-638.jpg)](https://www.slideshare.net/ssuserc15b9b/introducing-of-midi)

# アプリ

https://github.com/wurly200a/d_midi
Kong + KongaをDockerComposeで使ってみる。

# Kongとは

Microsoftの設計パターンでは[ゲートウェイ集約](https://docs.microsoft.com/ja-jp/azure/architecture/patterns/gateway-aggregation)という形で公開されているメソッドです。

> ゲートウェイを使用して、複数の個々の要求を 1 つの要求に集約します。 このパターンは、クライアントが操作を実行するために、さまざまなバックエンド システムに複数の呼び出しを行う必要がある場合に便利です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139643/da5a5062-c905-73c3-5e07-52c8cf591787.png)

一般的にマイクロサービスアーキテクチャでサービスを作ってしまうと、アプリケーションとサーバー間の接続が複数生まれます。そうすると、接続情報の管理や、エラーハンドリングが煩雑になってきます。そこで、間にリバースプロキシ的なものを挟んで、アプリケーションからは1つに見えるようにすることが考えられます。これがゲートウェイ集約です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139643/a0827bd1-1ae6-a7bf-232d-fe8be8a49d24.png)

今回は、[Kong](https://github.com/kong/kong)というものを使いましたが、SentinelやGlooなんかも有名です。


# 使用するイメージ

kong
https://hub.docker.com/_/kong

konga
https://hub.docker.com/r/pantsel/konga/

kongaは何か。というとkong用のWebUIです。kongは商用版ではWebUIがありますが、OSS版ではありません。そのため、kongaというOSSを使って、WebUIをサーブしています。

# DockerCompose

```yml:docker-compose.yml
version: '2.1'
services:
  kong:
    image: kong
    ports:
      - 0.0.0.0:8000:8000
      - 8443:8443
      - 8001:8001
      - 8444:8444 
    environment:
      - "KONG_PROXY_ACCESS_LOG=/dev/stdout"
      - "KONG_ADMIN_ACCESS_LOG=/dev/stdout"
      - "KONG_PROXY_ERROR_LOG=/dev/stderr"
      - "KONG_ADMIN_ERROR_LOG=/dev/stderr"
      - "KONG_ADMIN_LISTEN=0.0.0.0:8001, 0.0.0.0:8444 ssl"
      - "KONG_DATABASE=postgres"
      - "KONG_PG_HOST=kong-db"
      - "KONG_PG_USER=kong"
      - "KONG_PG_PASSWORD=kong"
      - "KONG_CASSANDRA_CONTACT_POINTS=kong-db"
    depends_on:
      - "kong-migrate"
    restart: "on-failure:3"

  kong-migrate:
    image: kong
    depends_on:
      - "kong-db"
    environment:
      KONG_DATABASE: "postgres"
      KONG_PG_HOST: "kong-db"
      KONG_PG_USER: "kong"
      KONG_PG_PASSWORD: "kong"
      KONG_CASSANDRA_CONTACT_POINTS: "kong-db"
    command: "kong migrations bootstrap"
    restart: "on-failure:3"

  kong-db:
    image: "postgres:9.6"
    environment:
      POSTGRES_USER: "kong"
      POSTGRES_PASSWORD: "kong"
      POSTGRES_DB: "kong"
    volumes:
      - ./kong_data:/var/lib/postgresql/data

  konga:
    image: pantsel/konga
    ports:
      - 1337:1337
    environment:
      - "DB_ADAPTER=postgres"
      - "DB_HOST=konga-db"
      - "DB_USER=konga"
      - "DB_PASSWORD=konga"
    restart: "on-failure:3"
    depends_on:
      - konga-db

  konga-db:
    image: "postgres:9.6"
    environment:
      POSTGRES_USER: "konga"
      POSTGRES_PASSWORD: "konga"
      POSTGRES_DB: "konga"
    volumes:
      - ./konga_data:/var/lib/postgresql/data
```

# 設定とポイント

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139643/f3c50547-2ea0-539c-f040-ce74d815b948.png)

左のCONNECTIONSのペインから選択して、CONNECTIONを作ります。
その時、Kong Admin Urlに`http://kong:8001/`と入力します。
ローカルでの簡単検証のためなので、SSLはなし。ドメインはlocalhostではなく、`kong`です。
Ruby + Qiita API v2 で特定ユーザーの Qiita 記事一覧を取得する

## 概要

- Ruby + Qiita API v2 で特定ユーザーの Qiita 記事一覧を取得する

## サンプルコード

```rb
require 'json'
require 'net/http'
require 'open-uri'

access_token = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx' # アクセストークン
user = 'niwasawa' # 記事作成ユーザ名

all_items = [] # すべての記事を収める配列

resource_url = 'https://qiita.com/api/v2/items' # WebAPI エントリポイント
headers = {'Authorization' => "Bearer #{access_token}"} # 認証用ヘッダ

page = 0 # ページネーションのページ番号
loop do
  # パラメータを組み立てる
  page += 1
  params = {
    'query' => "user:#{user}", # 記事作成ユーザー名で検索
    'per_page' => '100', # 1回のAPIコールで100件まで取得可能
    'page' => page # ページネーションのページ番号(1からスタート)
  }
  # 記事のリストを取得
  url = resource_url + '?' + URI.encode_www_form(params)
  puts "Calling WebAPI: #{url}"
  res = URI.open(url, headers)
  items = JSON.parse(res.read)
  # 記事が1件も取得できなくなったらループを抜ける
  break if items.empty?
  # 記事のリストをすべての記事を収める配列に追加
  all_items.concat items
end

# 記事の作成日時でソート
all_items.sort!{|a, b| Time.iso8601(a['created_at']) <=> Time.iso8601(b['created_at'])}

# 記事の作成日時とタイトルを出力
all_items.each do |item|
  puts "#{Time.iso8601(item['created_at']).strftime('%Y-%m-%d %H:%M:%S')} #{item['title']}"
end
```

## 実行例

macOS Catalina + Ruby 3.0.0 でサンプルコードを実行した例。

```
Calling WebAPI: https://qiita.com/api/v2/items?query=user%3Aniwasawa&per_page=100&page=1
Calling WebAPI: https://qiita.com/api/v2/items?query=user%3Aniwasawa&per_page=100&page=2
Calling WebAPI: https://qiita.com/api/v2/items?query=user%3Aniwasawa&per_page=100&page=3
Calling WebAPI: https://qiita.com/api/v2/items?query=user%3Aniwasawa&per_page=100&page=4
Calling WebAPI: https://qiita.com/api/v2/items?query=user%3Aniwasawa&per_page=100&page=5
2017-01-10 12:31:51 Ruby で WebAPI をコールするサンプルコード
2017-01-16 12:49:08 Ruby + RESAS-API で観光資源の位置情報(緯度経度)を取得する
2017-01-31 12:12:35 PHPUnit ことはじめ (インストール＆テストスイート構築)
(中略)
2020-12-12 16:18:40 CentOS Linux 8 から CentOS Stream 8 へ移行する
2020-12-16 08:46:35 JSON に記述された数値型の範囲外の整数値を JavaScript でパースする
2020-12-19 23:05:53 Oracle Database 12c でテーブル定義を確認する
```

## 参考資料

- [Qiita API v2ドキュメント \- Qiita:Developer](https://qiita.com/api/v2/docs)
- [検索時に利用できるオプション \- Qiita:Support](https://help.qiita.com/ja/articles/qiita-search-options)
- [library open\-uri \(Ruby 3\.0\.0 リファレンスマニュアル\)](https://docs.ruby-lang.org/ja/3.0.0/library/open=2duri.html)
- [class Array \(Ruby 3\.0\.0 リファレンスマニュアル\)](https://docs.ruby-lang.org/ja/3.0.0/class/Array.html)
- [module JSON \(Ruby 3\.0\.0 リファレンスマニュアル\)](https://docs.ruby-lang.org/ja/3.0.0/class/JSON.html)
- [class Time \(Ruby 3\.0\.0 リファレンスマニュアル\)](https://docs.ruby-lang.org/ja/latest/class/Time.html)
Cocoapodsのインストールについて

# はじめに
今月、あるお店でMacBookPro early2015を1万円で入手しました。（バッテリー膨張はしていたため2万円で修理しました。キーボードやトラックパッド、バッテリーは新品に）

Apple大好きなので手に入って感動しました。

そこで、いつかMacを手に入れたら勉強してみたいと思っていたSwiftの学習を始めました。
学習にあたって、Cocoapodsのインストールで少し躓いたためこちらに残します。

# 環境
- MacBook Pro (Retina, 13-inch, Early 2015)
- MacOS Catalina ver10.15.7

# Cocoapodsとは？
> CocoaPods is a dependency manager for Swift and Objective-C Cocoa projects. It has over 79 thousand libraries and is used in over 3 million apps. CocoaPods can help you scale your projects elegantly.
[Cocoapods公式サイト](https://cocoapods.org)

翻訳すると
> CocoaPodsは、SwiftおよびObjective-CCocoaプロジェクトの依存関係マネージャーです。 79千を超えるライブラリがあり、300万を超えるアプリで使用されています。 CocoaPodsは、プロジェクトをエレガントにスケーリングするのに役立ちます。

つまり、iOS用のライブラリ管理ツールです。
Cocoapodsを使用しないと自分で全てライブラリを取得して導入する必要がある。

# 導入手順
Cocoapodsはgemを用いてインストールします。（Macには最初からRubyが入っている）

Cocoapodsインストール
`sudo gem install cocoa pods`

Cocoapodsセットアップ
`pod setup`

しかし、インストールでこのようなエラーが出ました。

```
ERROR:  Error installing cocoapods:
ERROR: Failed to build gem native extension.
```

どうやら、Macに最初から入っているRubyのバージョンがCocoapodsに対応していないことが原因らしいです。
CatalinaのRubyのバージョンは2.6.3でした。

解決方法は二つ（多分）
・Rubyのバージョンを上げる
・Cocoapodsのインストールバージョンを下げる

今回はRubuのバージョンを上げることで対応しました。

# Rubyのバージョンアップ
調べてみると、`rbenv`というバージョン管理ツールを使用することでRubyのバージョンアップするようです。

こちらの記事を参考にバージョンアップを行いました。
[MacのターミナルでRubyをバージョンアップする方法](https://qiita.com/Ficus/items/bdef5c2b504d7a4008fb)

あとは、導入手順で紹介した流れでインストールとセットアップすれば完了です。

# まとめ
今回は、Cocoapodsインストール手順とそれに必要なRubyのバージョンアップ方法の紹介をしました。

現在は、趣味で書籍やUdemyを用いてSwiftを学習中です。
iOSアプリだけでなく、Apple WatchやiPad、Macアプリを作ることができるので引き続き勉強して行きたいと思います。

以上
【Ruby】sliceメソッドとは？slice!との違いを例題を解いて理解しよう！

## 概要

sliceとslice!の違いをまとめさせて頂きました。もっとわかりやすい表現などあればコメント、ご指摘いただけたら幸いです！

## 目次

- sliceとslice!
    - slice
    - slice!

- 実践
    - 問題
    - 解答（解説）

- まとめ
- 参考文献

## sliceとslice!

> 【例】配列から1番目の要素を取り出し、もとの配列を出力する

**ポイント**

- 配列や文字列から指定した要素を取り出すことができるメソッド
- 要素を指定する際は数値
- 先頭は0からはじまる


#### slice


```ruby

array = [0, 1, 2, 3, 4, 5]
num = array.slice(1)

puts num
puts array

# ターミナル

# puts num の結果
# 1
# => 指定した要素の取り出し

# puts array
# 0
# 1
# 2
# 3
# 4
# 5
```

#### slice!

- エクスクラメーションマーク(!)のつくメソッドを破壊的メソッドという
- 要素を取り出すだけでなく元の形を変化させる
- 指定した要素を削除させる

```ruby
array = [0, 1, 2, 3, 4, 5]
num = array.slice!(1)

puts num
puts array

# ターミナル

# puts num の結果
# 1 
# => 取れる要素は変わらない

# puts array
# 0
# 2
# 3
# 4
# 5
# => 取り出した要素（1）が削除されている
```


## 実践

果物を例に `slice` を使って問題を解いていきます。

#### 問題

>任意の文字からn番目の文字を削除しその文字を出力するメソッドを作成しよう！

#### 解答(解説)

```ruby

def str_check(string, num)  # 文字列(string) と 何番目を削除したいのか(num)を受け取っている
  string.slice!(num - 1)    # 0番目からはじまるので -1 することで取り出したい文字を削除できる
  puts string               # slice! で削除した文字以外を出力することができる
end

# メソッド呼び出し
str_check('apple', 1)
str_check('orange', 2)
str_check('grape', 4)

# ターミナル出力結果

# pple
# oange
# grae
```

## まとめ
- `slice`メソッドを使うことで文字列や配列から要素を取り出すことができる
- 要素を取り出したいときは数値を指定する
- 0番目から始まる
- `slice!`メソッドを使うと元の文字列や配列の形を変えることができる

## 参考文献

- [Ruby 3.0.0 リファレンスマニュアル [slice]](https://docs.ruby-lang.org/ja/latest/method/Array/i/slice.html)

- [Ruby 3.0.0 リファレンスマニュアル [slice!]](https://docs.ruby-lang.org/ja/latest/method/String/i/slice=21.html)
【Salesforce】Lightning Design Systemでモーダル画面を作る

## モーダル
以下がモーダル画面のサンプルコードです。

``` html
<apex:page title="Test" showHeader="false" standardStylesheets="false" sidebar="false" docType="html-5.0">
  <html xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" lang="ja">
    <head>
      <meta charset="utf-8" />
      <meta http-equiv="x-ua-compatible" content="ie=edge" />
      <meta name="viewport" content="width=device-width, initial-scale=1" />
      <apex:slds />
    </head>

    <body style="padding: 8px;">
      <section role="dialog" tabindex="-1" aria-labelledby="modal-heading-01" aria-modal="true" aria-describedby="modal-content-id-1" class="slds-modal slds-fade-in-open">
        <div class="slds-modal__container">
          <header class="slds-modal__header">
            <h2 id="modal-heading-01" class="slds-modal__title slds-hyphenate">ヘッダーのタイトルです。</h2>
            <p class="slds-m-top_x-small">ヘッダーの本文です。</p>
          </header>

          <div class="slds-modal__content slds-p-around_medium" id="modal-content-id-1">
            <p>本文です。</p>
          </div>

          <footer class="slds-modal__footer">
            <button class="slds-button slds-button_neutral">キャンセル</button>
            <button class="slds-button slds-button_brand">保存</button>
          </footer>
        </div>
      </section>
      <div class="slds-backdrop slds-backdrop_open"></div>
    </body>
  </html>
</apex:page>
```

以下がモーダル画面の作成イメージです。
![Modal_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/611228/062a3f0e-d58c-9564-9dfe-7c74febdf58d.png)

## モーダル画面の構成
|要素|備考|
|:-:|:-:|
|ヘッダー（header）|モーダルのヘッダー部分です。不要であれば削除しても問題ありません。|
|コンテンツ（div）|モーダルのコンテンツ部分です。本文を記載します。|
|フッター（footer）|モーダルのフッター部分です。通常はボタンを配置します。|

## 参考
■Modals
https://lightningdesignsystem.com/components/modals/
Delta Lakeをさわってみた話 + α

この記事は[freeeデータに関わる人たち Advent Calendar 2020](https://adventar.org/calendars/5461)の12日分（だけど書くのめちゃ遅れた）の記事です。

## まとめ
- [Delta Lake](https://delta.io)さわってみた
- 集計分析でDBライクにFile Objectを扱いたいときによさそう

## 動機
- 以前からちらほら聞くことがあったDeltaLakeをちょっと知りたかった

## Delta Lakeとは
- Storage Layerの便利ツール
    - デフォルトでParquetのみをサポート（ORCはなさそう）
    - Sparkを前提
    - ACIDなTransactionを実現する仕組み
        - Delta Log
    - Time Travelできる


## サクッとつかった例
- Read/Write

```Python
# write
# formatとしてdeltaを指定
df.write.format("delta").mode("overwrite").save("/path/to/table")

# read as Spark DataFrame
data = spark.read.format("delta").load("/path/to/table") 
data.withColumn(...)
...

# read as DeltaTable(wrapper)
from delta.tables import DeltaTable
deltaTable = DeltaTable.forPath(spark, "/path/to/table")
deltaTable.update(...)
...
```
- Delta Log

```shell
$ ls /path/to/table/_delta_log/
00000000000000000000.json  00000000000000000001.json...

$ cat 00000000000000000000.json
{"commitInfo":{"timestamp":1606459693818,"operation":"WRITE","operationParameters":{"mode":"Overwrite","partitionBy":"[]"},"isBlindAppend":false,"operationMetrics":{"numFiles":"4","numOutputBytes":"1894","numOutputRows":"10"}}}...
```

## AWS Glueで使えるか試してみた
雰囲気はつかめたので、弊社で利用しているAWS GlueのJob Scriptで呼び出せるか試してみた。
- JarをS3に置いて指定

![DeltaLake.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262565/fd02f611-96b8-8e88-b80b-40faa9ddb4ca.png)

- Job Script

```Python
from pyspark.conf import SparkConf
from pyspark.sql import SparkSession
from pyspark.context import SparkContext
from awsglue.context import GlueContext

sc = SparkContext()
gc = GlueContext(sc)

gc.setConf("spark.sql.extensions", "io.delta.sql.DeltaSparkSessionExtension")
gc.setConf("spark.sql.catalog.spark_catalog", "org.apache.spark.sql.delta.catalog.DeltaCatalog")
gc.setConf("spark.delta.logStore.class", "org.apache.spark.sql.delta.storage.S3SingleDriverLogStore")

sc.addPyFile("delta-core_2.12-0.7.0.jar")

from delta.tables import *

spark = SparkSession(gc)

delta_path = "s3://path/to/table"
data = spark.range(0, 100)
data.write.format("delta").mode("overwrite").save(delta_path)
```

- ref: https://stackoverflow.com/questions/63186034/read-write-delta-lake-tables-on-s3-using-aws-glue-jobs

s3のkeyが無いと怒られるのでちょっと違うかも、、
というところで力尽きたので来年の自分に期待して終わります・・・（AWS Glue無理じゃねっという記事もみたのでたぶんできないかも？）
apt-cygのインストールの備忘録

apt-cygはパッケージの管理アプリケーションである.
cygwinのインストーラーではwhileコマンドなどいくつかのコマンドがインストールされない.  
その場合, apt-cygを使用してインストールを実施する必要がある.  

apt-cygのインストールでは以下のgithubからコードを取得する.  
[kou1okada/apt-cyg](https://github.com/kou1okada/apt-cyg)
https://github.com/kou1okada/apt-cyg


CUIの場合は, wgetコマンド
GUIの場合は, URLに飛んでコードをダウンロード

以下のようにコマンドを入力するとapt-cygが使用できるようになる.  

```
chmod 755 apt-cyg
mv apt-cyg /usr/local/bin/
```


apt-cygを使用する場合は以下のようにコマンドを入力する.  

```
apt-cyg install lynx
```

注意: なお本件の記載は,すでに先人の方が記載をされており, 同様の記載となっている. 
本記載よりも優れている記載があるならば,そちらを参考としていただだきたく.
他の.exeを起動して、コンソール出力をテキストファイルに保存する試行

# はじめに

subprocessで起動したプロセスのコンソール出力を取得・保存するコードサンプル。
以下のコードで、test.exeやtest.batのコンソール出力をテキストファイルに保存可能。

キーワード: subprocess.Popen、外部コマンド実行、標準出力リダイレクト

# 処理方法

* **`subprocess.Popen(.., stdout=.., stderr=..)`を使用**、
* **`stderr=subprocess.PIPE`によりコンソール出力を当プロセスに流し、`proc.communicate()`で、起動したプロセスの終了を待機**。
* (`proc.communicate()`がないと、終了を待たずに続行、並列処理となる)

# テストコード

(ポイントとなる箇所に、コメントで説明を付記)

```Python:trial.py
# -*- coding: utf-8 -*-

# subprocessで起動したプロセスのコンソール出力を取得・保存するには
# ref: https://www.it-swarm-ja.tech/ja/python/subprocesscall%EF%BC%88%EF%BC%89%E3%81%AE%E5%87%BA%E5%8A%9B%E3%82%92%E5%8F%96%E5%BE%97%E3%81%99%E3%82%8B/968744582/

import subprocess

def main(): # 実行切替用
    run__main1()

# sec: コンソール出力を取得・保存

def run__main1():
    # 結果:
    # test.exeのコンソール出力保存可
    # test.batもコンソール出力保存可、.batも可
    
  # case: FAIL
    # subprocess.call("test.exe > res.log.txt")
    
  # case: Popen(.., stdout=..)を使用
    with open("res.log.txt", 'w') as file_log:
        proc = subprocess.Popen(
            ["test.bat"], 
            stdout=file_log, stderr=subprocess.PIPE) # 出力が必要な場合はstdout・stderr引数を利用
        proc.communicate() # これで待機
    print("return code:", proc.returncode) # DEBUG: 待機・終了確認用
  # case: end
    
    print("ended.")

# sec: entry

if __name__ == "__main__": main()
```

## 参考
https://www.it-swarm-ja.tech/ja/python/subprocesscall%EF%BC%88%EF%BC%89%E3%81%AE%E5%87%BA%E5%8A%9B%E3%82%92%E5%8F%96%E5%BE%97%E3%81%99%E3%82%8B/968744582/
lightning-record-formの使い方について

## 概要
lightning-record-formの使い方について記載する。

## データを登録するとき
こんな感じ。

```html:accountCreator.html
<template>
    <lightning-card>
        <lightning-record-form object-api-name={objectName} fields={fields} onsuccess={handleSuccess}>
        </lightning-record-form>
    </lightning-card>
</template>
```

```javascript:accountCreator.js
import { LightningElement } from 'lwc';
import { ShowToastEvent } from 'lightning/platformShowToastEvent';
import ACCOUNT from '@salesforce/schema/Account';
import ACCOUNT_NAME from '@salesforce/schema/Account.Name';
import ACCOUNT_REVENUE from '@salesforce/schema/Account.AnnualRevenue';

export default class AccountCreator extends LightningElement {

    objectName = ACCOUNT;
    fields = [ACCOUNT_NAME, ACCOUNT_REVENUE];

    handleSuccess(event) {
        const toast = new ShowToastEvent({
            title: "Account created",
            message: "Record Id:" + event.detail.id,
            variant: "success"
        })
        this.dispatchEvent(toast);
    }

}
```

## データを更新するとき
html側でrecord-idを指定する。

```html:accountCreator.html
<template>
    <lightning-card>
        <lightning-record-form record-id={recordId} object-api-name={objectName} fields={fields} onsuccess={handleSuccess}>
        </lightning-record-form>
    </lightning-card>
</template>
```

javascript側で@api recordIdを指定する。@api recordIdを指定すると、フレームワークが自動的に対象画面のレコードIDをrecordId変数に格納してくれる。

```javascript:accountCreator.js
import { LightningElement,api } from 'lwc';
import { ShowToastEvent } from 'lightning/platformShowToastEvent';
import ACCOUNT from '@salesforce/schema/Account';
import ACCOUNT_NAME from '@salesforce/schema/Account.Name';
import ACCOUNT_REVENUE from '@salesforce/schema/Account.AnnualRevenue';

export default class AccountCreator extends LightningElement {

    @api recordId;
    objectName = ACCOUNT;
    fields = [ACCOUNT_NAME, ACCOUNT_REVENUE];

    handleSuccess(event) {
        const toast = new ShowToastEvent({
            title: "Account created",
            message: "Record Id:" + event.detail.id,
            variant: "success"
        })
        this.dispatchEvent(toast);
    }

}
```

## モード属性の指定
モード属性を指定すると画面の表示を変えられる。

| mode | 説明 |
| ---- | ----- |
| "view" | 閲覧モード。読み取り専用で表示されて、横に編集用の鉛筆マークが出る。 |
| "edit" | 編集モード。編集フォームが表示される。 |
| "mode" | 読み取り専用モード。読み取り専用で表示されて鉛筆マークが出ない。|

モードについては、ここがわかりやすい。
https://qiita.com/hrk623/items/93e1777d1d78ee23a0f1

## 参考
https://qiita.com/hrk623/items/93e1777d1d78ee23a0f1
https://trailhead.salesforce.com/ja/content/learn/modules/lightning-web-components-and-salesforce-data/use-lightning-data-service-to-work-with-data
【Salesforce】Lightning Design Systemで色々なボタンを作る

## ボタン
以下が基本的なボタンのサンプルコードです。
各ボタンにLightning Design Systemのクラスを追加することで、ボタンのスタイルを変更できます。

``` html
<apex:page title="Test" showHeader="false" standardStylesheets="false" sidebar="false" docType="html-5.0">
  <html xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" lang="ja">
    <head>
      <meta charset="utf-8" />
      <meta http-equiv="x-ua-compatible" content="ie=edge" />
      <meta name="viewport" content="width=device-width, initial-scale=1" />
      <apex:slds />
    </head>

    <body style="padding: 8px;">
      <button class="slds-button slds-button_brand">保存</button>
      <button class="slds-button slds-button_destructive">削除</button>
      <button class="slds-button slds-button_neutral" disabled="true">無効</button>
      <button class="slds-button slds-button_neutral">キャンセル</button>
    </body>
  </html>
</apex:page>
```

以下のボタンを作成しました。
・保存（主要なアクション）
・削除（破壊的なアクション）
・無効（無効なアクション）
・キャンセル（普通のアクション）
![Button_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/611228/c261286c-70ed-bc6c-3159-8e8d1ea3dc77.png)

## ボタンのクラス名一覧
|クラス名|備考|
|:-:|:-:|
|slds-button_brand|主要なアクションで使われる|
|slds-button_destructive|破壊的なアクションで使われる|
|slds-button_neutral|普通のアクションで使われる|

## 参考
■Buttons
https://lightningdesignsystem.com/components/buttons/
Railsチュートリアル第6版の3.3.1のテストで「ActionView::Template::Error: Permission denied」エラーが出たので解決した

##環境は何？
* Windows10 Home ver.2004
* ruby 2.7.2p137 (2020-10-01 revision 5445e04352) [x64-mingw32]
* Rails 6.1.0

##何が起きた？
　[Railsチュートリアル](https://railstutorial.jp/chapters/static_pages?version=6.0#sec-our_first_test)のリスト3.15の`rails test`コマンドを実行したら、次のようなエラー①が出た。

```:エラー①
D:\Programming\RubyOnRails\sample_app2>rails test
Run options: --seed 42827

# Running:

E

Error:
StaticPagesControllerTest#test_should_get_home:
ActionView::Template::Error: Permission denied @ rb_file_s_rename - (D:/Programming/RubyOnRails/sample_app2/tmp/cache/assets/sprockets/v4.0.0/6p/6p5srKo-CqopTzauMxsxGBdnpUciiPghSY6oKN4-uVY.cache.15640.1380.291914, D:/Programming/RubyOnRails/sample_app2/tmp/cache/assets/sprockets/v4.0.0/6p/6p5srKo-CqopTzauMxsxGBdnpUciiPghSY6oKN4-uVY.cache)
    app/views/layouts/application.html.erb:9
    test/controllers/static_pages_controller_test.rb:5:in `block in <class:StaticPagesControllerTest>'


rails test test/controllers/static_pages_controller_test.rb:4

.

Finished in 0.148240s, 13.4916 runs/s, 6.7458 assertions/s.
2 runs, 1 assertions, 0 failures, 1 errors, 0 skips
```

##解決方法は何？
　`test_helper.rb`内の該当箇所を`parallelize(workers: 1)`に変える。

```ruby:test\test_helper.rb
class ActiveSupport::TestCase
  # Run tests in parallel with specified workers
  parallelize(workers: 1) #ここ
```

##解決するために何をした？
####1.
　エラーメッセージなどで検索して見つけた[「Ruby on Rails チュートリアル Windows での実施時の困ったメモ」](https://qiita.com/yasumichi/items/ccf1f7f57b6627034226)を参考にコマンドを試してみたが、`rails assets:precompile`コマンドで次のようなエラー②が出た。

```:エラー②
D:\Programming\RubyOnRails\sample_app2>rails assets:precompile
rails aborted!
Errno::ENOEXEC: Exec format error - D:/Programming/RubyOnRails/sample_app2/bin/yarn --version

Tasks: TOP => assets:precompile => yarn:install
(See full trace by running task with --trace)
```

　`rails yarn:install`コマンドを実行してみたり、ある程度長い時間調べてみたりしたが自分の手には負えなさそうなので、このエラー②を解決するのはとりあえず諦めることにした。（`bin/yarn`でコマンドを実行しようとしていることが原因……？）

####2.
　`Permission denied`なんだからアクセス権を付与してやればいいんだろうと思って、エクスプローラーから`tmp`フォルダ以下に対して全ユーザー（グループ）にフルコントロールを許可したが、それでもエラー①は直らなかった。

####3.
　上と同様、アクセス権の問題ならコマンドを管理者権限で実行すればどうかと思い、「Ruby 管理者として実行」などのキーワードで検索して見つけた[「Rubyでgem installしたときにpermission deniedが出現した時の解決法」](http://k01ken.hatenablog.com/entry/2018/09/29/181556)を参考に、Rubyコマンドプロンプトを管理者として実行して`rails test`コマンドを打ってみたが、エラー①は直らなかった。

####4.
　2つの`test`の内、片方（`should get help`）は`assertions`となっていることに気付き、`static_pages_controller_test.rb`内の`should get help`をコメントアウトして`should get home`だけをテストしてみるとエラーは出なかった。**つまり、2つの`test`を同時に行うときにだけエラーが出ているということに気付く。**
　1.で色々調べているときに、Railsのテストはデフォルトだとテスト時間短縮のために並列で行われるというような記述を見かけたことを思い出し、「Rails テスト 並列」などのキーワードで検索して[「Rails テスティングガイド」](https://railsguides.jp/testing.html#%E4%B8%A6%E5%88%97%E3%83%86%E3%82%B9%E3%83%88)を見つけた。ここの3.1を参考に、`test_helper.rb`内の該当箇所を`parallelize(workers: 1)`に変えたら、エラー①は出なくなった。

以上
ザクっと立てるFastAPI

# 環境準備

```shell-session
$ pipenv shell
$ pipenv install fastapi uvicorn
```

# ソースコード

ポイントは、

- GET
    - パスパラメーター
- POST
    - ボディの受け取り方

```python:main.py
from fastapi import FastAPI
from pydantic import BaseModel
import dataclasses
import uuid

class UserInput(BaseModel):
    name: str

@dataclasses.dataclass
class User:
    id: str
    name: str

data = dict()

app = FastAPI()

@app.post("/users/")
async def create_user(user_input: UserInput) -> User:
    user_id = str(uuid.uuid4())
    user = User(user_id,user_input.name)
    global data
    data[user_id] = user
    print(user_id)
    return user

@app.get("/users/{user_id}")
async def read_user(user_id: str) -> User:
    return data[user_id]

@app.delete("/users/{user_id}")
async def delete_user(user_id: str) -> None:
    del data[user_id]
```

# 起動の仕方

ポイントは

- ポート番号の指定
- ホスト名の指定

ホスト名の指定をしないとドメイン指定等、公開するときにハマる。

```shell-session
$ uvicorn main:app --port=8080 --host=0.0.0.0
```

開発用はreloadをつける。

```shell-session
$ uvicorn main:app --reload --port=8080 --host=0.0.0.0
```

# 動作確認

http://localhost:8080/docs

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139643/d49f5280-811a-2dad-6882-0175037cbc7b.png)

http://localhost:8080/redoc

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139643/743d6e5d-dfd3-2b75-180c-a395c82b89c8.png)


# コンテナ化

```Dockerfile:Dockerfile
FROM python:3.6-slim

COPY Pipfile .
COPY Pipfile.lock .

RUN pip install pipenv --no-cache-dir
RUN pipenv sync --system  

COPY main.py .
CMD pipenv run uvicorn main:app --port=8080 --host=0.0.0.0
```


```shell-session
$ docker build -t fastapi_test .
$ docker run --rm -p 8080:8080 fastapi_test
```
一意性制約を確かめるモデル単体テストコード

#はじめに
　先日の投稿の付け足しです。
[ちょっと一癖あるRSpecを使ったモデルの単体テストコード　〜ユーザー登録](https://qiita.com/TerToEer_sho/items/51330fd4bd40e91fdd7b)
##一意性制約を確かめるテストコード

```ruby
RSpec.describe School, type: :model do
  describe '学校登録' do
    before do
      @school = FactoryBot.build(:school)
    end
  it '同じ学校名は登録できないこと' do
    @school.save #←ポイント①
    another_school = FactoryBot.build(:school) #←ポイント②
    another_school.name = @school.name #←ポイント③
    another_school.valid?
    expect(another_school.errors.full_messages).to include("学校名はすでに存在します")
  end
end
```
###ちょこっと解説

####ポイント①
`FactoryBot.build(:school)`を@school.saveで先に保存する。

####ポイント②
`another`として（名前は自由）別物を生成する。
####ポイント③
ポイント②で新たに生成した値とポイント①で先に保存した値を同じにする。
Railsをインストールしたはずがrails -vでエラーが発生する時の対処方（初心者向け）

railsのインストールをブログの記事通り進めてきたが

```sql
$ rails -v
```
で以下のようなエラーが発生しました。

```sql
$ rails -v

Rails is not currently installed on this system. To get the latest version, simply type:

    $ sudo gem install rails

You can then rerun your "rails" command.
```

いろいろな記事を読んで解決しようとしましたがうまくいかず、ターミナルを再起動して再度バージョン確認。

```sql
rails -v
Rails 6.1.0
```
オーマイガー
インストールされてやがる！！

初心者でrails -vでエラーになった時はターミナルを再起動せよ！！
授業メモ5



# assert equal

　assert equalはequalかどうかを確かめてくれる関数だそうです.


# assert equalの利用

　最初にこの関数はequalかどうかの確認関数だといったので,練習として　1==1(1と1はequalなのか)を確かめてみる.

> def assert equal(expected,result)

>  return expected == result

> end

> printf assert equal(1,1)

　とすると,まずは関数を定義し,expectedとresultが同じならtrueが帰るものになりました.　これならしっかりとtrueが返ってきています.


# 色替え

　さっきの文に少し付け加えて,文字の色を変更してみる.

> require 'colorize'

> def assert equal(expected, result)

>  if expected == result

>    printf 'true'.green

>  else

>    printf 'false'.red

>   end

> end

> assert equal(1, 1)

　これによりtrueは緑で,falseは赤で帰ってくるようにできました.


# assert not equalのを考える

　さっきまでは同じかどうかを確かめるものであったが,応用として同じじゃないかどうかを確かめる　ことを考える.

> def assert not \_equal(expected,result)

>  if expected == result

>   printf 'false'.red

>  else

>   printf 'true'.green

>  end

> end

> assert not equal(1,2) 

　これで同じじゃないかどうかを確かめる関数ができた.出力ももんだいなかった.


# 参考にした資料

　[チャート式ruby-IV](https://qiita.com/adchello/items/50c3a2f6739c04df9749)



------
 - **source** ~/grad_members_20f/members/adchello/test4.org
Googleアナリティクスアカデミーで基礎を学ぶ

業務でGoogleアナリティクスのコンソールにアクセスすることが多々あるもの、その多機能さをいまいち活用できていないことにストレスを感じていた2020年。持ち越したくない思いから勉強方法を調べてみると、Googleが提供しているGoogleアナリティクスアカデミーなるオンライン講座があるので試してみることにしました。

# Googleアナリティクスアカデミーとは
[Googleアナリティクスアカデミー](https://analytics.google.com/analytics/academy/?authuser=2)

アナリティクスやタグマネージャーなどのツールのオンライン講習が受けられるサービスです。全て無料で提供されています。
1回3分程の動画が1レッスンになっており、英語でお兄さんとお姉さんが講義してくれるものに日本語の字幕がついています。

# アナリティクス アカデミー コース
現在、日本語版では4つが公開されていますが、英語だと他にも種類があるようです。英語のリスニングができる方はぜひそちらもチャレンジしてみてください。

 - Google アナリティクス初級者向けコース
 - Google アナリティクス上級者向けコース
 - Google アナリティクス 360 入門コース
 - Google タグ マネージャーの基礎コース

# Google アナリティクス初級者向けコースについて
私の場合、多少実務でレポートなどをみる機会はあったのですが、基礎から学びなおしたかったので初心者コースから実施することにしました。
## カリキュラム
1. Googleアナリティクスの紹介
2. Googleアナリティクス インターフェース
3. ベーシックレポート
4. 基本的なキャンペーンおよびコンバージョントラッキング

だいたい1つの項目に3~５つのレッスンがあり、1項目が完了すると理解度をはかるためのテストが受けられます。テストは80%以上の正答率で修了認定されます。

# 最後に
まだ、全て受講できていないですが、１つのレッスンが3分前後と短く細切れに実施できるため隙間時間に実施ができそうです。また、テストが受けられるので理解できたかどうかもセルフチェックできるところが達成感が高まり嬉しいです。実際に学んだことはまた別の記事でまとめられればと思います。
【React】イベントリスナーでのステート参照方法

# 目的
ボタン押下時によるステートの更新処理はたくさん記事にされている。。。
じゃあ`addEventListener`を使用した際のステートの扱いについては？って思ったのでまとめてみました。

今回は画面がクリックされた際にカウントを1増やす簡単な処理を実装していきます。

# addEventListenerの実装（useEffect）
実装方法自体は単純で、`useEffect`を使用します。
useEffectにrender後の処理、つまり`addEventListener`を記述すればOKです。

```react
import React, { useState, useEffect} from "react";

const Count = () => {
  const [count, setCount] = useState(0);

  useEffect(() => {
    // イベントリスナーを登録
    window.addEventListener("click", (event) => {
      setCount(count => count + 1);
    });
  }, []);

  return (
    <div>
      <h1>{count}</h1>
    </div>
  );
};

export default Count;

```

# イベントリスナー内での最新のステート値の利用（useRef）
この記事のタイトルにもあるように、イベントリスナー内でセットされたステート値を使用する際は一工夫必要になります。

問題として、そのままステート値を使おうとしても更新されていない値が取得されてしまいます。
その解決方法として`useRef`を使います。

```react
import React, { useState, useEffect, useRef } from "react";

const Count = () => {
  const [count, setCount] = useState(0);
  const countRef = useRef(null); //  ref オブジェクト作成する
  countRef.current = count; // countを.currentプロパティへ保持する

  useEffect(() => {
    // イベントリスナーを登録
    window.addEventListener("click", (event) => {
      setCount(count => count + 1);
      console.log(count); // 更新前の値「0」が取得される
      console.log(countRef.current); // 更新後の最新のcountの値が取得される
    });
  }, []);

  return (
    <div>
      <h1>{count}</h1>
    </div>
  );
};

export default Count;

```
refオブジェクトの`.current`プロパティにステートへの参照を保持することで、常に最新のステート値を取得することが出来るようになります。

# まとめ
公式にもあるように、useRef は何もDOM への参照を保持するためだけにあるのではありません。その current プロパティの値は書き換え可能かつどのような値でも保持することができます。
https://ja.reactjs.org/docs/hooks-faq.html#is-there-something-like-instance-variables
Pardot のメールマーケティング (Pardot Lightning アプリケーション) ⇒ メールマーケティングの使用開始

１．メールマーケティングとマーケティングオートメーションはどのように関連しますか?
２．パーミッションメールとは何ですか?
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/634241/422048bc-9393-19e1-a9cd-6c46c0a08ccf.png)