Open18

daily memo

ピン留めされたアイテム

目的
日々の技術的な学びをメモしておくことで、記事の材料としたい

2022-05-09

  • vscodeスクリーンキャストモード

  • sqlのview参照時は、create view時の記載したsqlが実行されるイメージ?

    • 以下の通り、viewを参照するたびに記載されているsqlが実行されていることがわかる。
-- テストデータ作成参考: https://goodbyegangster.hatenablog.com/entry/2019/05/06/111009
create table random (code int);
insert into random (code)
    select (random() * 100) from generate_series(1, 10);

CREATE OR REPLACE VIEW view_test as
select * from random
UNION ALL
select * from random
;
 select * from view_test ;
 code
------
   94
   89
   88
    7
   44
    7
   14
   21
   64
   54
   94
   89
   88
    7
   44
    7
   14
   21
   64
   54
(20 rows)

-- 新たにデータを10件投入してみる。
insert into random (code)
    select (random() * 100) from generate_series(1, 10);

 select * from view_test ;
 code
------
   94
   89
   88
    7
   44
    7
   14
   21
   64
   54
   28
   88
   41
   18
   14
   70
   73
   15
    1
   66
   94
   89
   88
    7
   44
    7
   14
   21
   64
   54
   28
   88
   41
   18
   14
   70
   73
   15
    1
   66
(40 rows)

2022-05-10

  • psql
  • docker-compose volume mountで パッケージデータが消失してしまう問題は以下の解決策で回避できる。
    • 解決策1: docker-compose run <サービス名> <パッケージinstallコマンド>
    • 解決策2: docker-compose.ymlにentrypointを記載する
    • 解決策3: docker-compose volumeを追加してmountする

まずは現象の確認

# https://zenn.dev/gakin/scraps/4cc16e7761d1ef 「Dockerfileを修正」まで構築
rm -rf node_modules/
# コンテナ再ビルド
docker-compose up -d --build
docker-compose ps
              Name                             Command               State    Ports
-----------------------------------------------------------------------------------
nodedev_node-dev_1   docker-entrypoint.sh /bin/ ...   Exit 1
# ログ確認→ moduleがなくてコケている。
docker-compose logs
Attaching to nodedev_node-dev_1
node-dev_1  |
node-dev_1  | > app@1.0.0 dev /app
node-dev_1  | > npx ts-node-dev --respawn src/app.ts
node-dev_1  |
npx: installed 52 in 8.128s
node-dev_1  | Cannot find module 'typescript

解決策1: docker-compose run <パッケージinstallコマンド>

docker-compose run node-dev npm install
# node_moduleが作成されている。
ls
Dockerfile  docker-compose.yml  node_modules  package-lock.json  package.json  src  tsconfig.json

# コンテナ起動する
docker-compose up -d

# コンテナログを確認→hello worldが表示されていることを確認
docker-compoe logs -f 

Hello, world!

解決策2: docker-compose.ymlにentrypointを記載する

version: '3'
services:
  node-dev:
    build: 
      context: .
      dockerfile: Dockerfile
    tty: true
    volumes:
      - .:/app
    entrypoint: >
      /bin/sh -c "
        npm install && npm run dev
      "

rm -rf node_modules/
# コンテナ起動
docker-compose up -d
# コンテナログ確認→問題なく実行できていることを確認
docker-compose logs -f
 > app@1.0.0 dev /app
 > npx ts-node-dev --respawn src/app.ts

 [INFO] 11:43:18 ts-node-dev ver. 1.1.8 (using ts-node ver. 9.1.1, typescript ver. 4.6.4)
 Hello, world!

解決策3: docker-compose volumeを追加してmountする

version: '3'
services:
  node-dev:
    build: 
      context: .
      dockerfile: Dockerfile
    tty: true
    volumes:
      - .:/app
      - node_modules-volumes:/app/node_modules/
volumes:
    node_modules-volumes:

2022-05-11

2022-05-14

  • vscode
    • 拡張機能: vsnote
      • vscodeでノートとかをかけ、tagで管理ができる。gitのリポジトリを保存先にしておけば、commitやpushをvscodeのパレット上から実行できる
    • 拡張機能: pastimage
      • スクショとかした画像をmarkdownに保存できる。vsnoteでmarkdownを保存する
  • Github
gh auth login
# public repo list
gh repo list --visibility public --limit 100
# public→privateに変更する
gh repo edit <repo-name> --visibility private

2022-05-15

"[markdown]":  {
    "editor.wordWrap": "on",
    "editor.quickSuggestions": true,
    "editor.snippetSuggestions": "top"
}
markdown.json
"details_tag": {
		"prefix": "ghdetail",
		"body": [
			"<details>",
			"<summary>$1</summary>",
			"",
			"",
			"</details>"
		],
		"description": "gh_details_tag"
}

2022-05-17

import sqlalchemy as sa
from sqlalchemy.orm import scoped_session
from sqlalchemy.ext.declarative import declarative_base

engine = sa.create_engine(
    sa.engine.url.URL.create(
        drivername="mysql+pymysql", # or postgresql
        username=db_user,  # e.g. "my-database-user"
        password=db_pass,  # e.g. "my-database-password"
        host=db_hostname,  # e.g. "127.0.0.1"
        port=db_port,  # e.g. 3306
        database=db_name,  # e.g. "my-database-name"
    )
)
session = scoped_session(
    sessionmaker(
        autocommit = False,
        autoflush = False,
        bind = engine
    )
)

Base = declarative_base()
class User(Base):
    """
    ユーザモデル
    """
    __tablename__ = 'users'
    id = Column('id', Integer, primary_key = True)
    name = Column('name', String(200))
    age = Column('age', Integer)
    email = Column('email', String(100))


engine = test_session.get_bind()
engine.execute(f'TRUNCATE TABLE {User.__tablename__}')
  • postgres
    • 接続中のセッションを切断する
    • pg_terminate_backend関数を使うとセッションを切断することができる
    • pg_stat_activityビューを使って現在接続中のプロセスを確認
    • 参考: https://qiita.com/iewori/items/0461f2c0e9e8ce0fd1ee
SELECT 
    pg_terminate_backend(pid) 
FROM 
    pg_stat_activity 
WHERE 
    -- don't kill my own connection!
    pid <> pg_backend_pid()
    -- don't kill the connections to other databases
    AND datname = 'database_name'
;

2022-05-18

  • sqlalchemy
    • engine, sessionの動作確認方法
コード
# 参考:https://dev.classmethod.jp/articles/sqlalchemy-connection-pooling/
import sqlalchemy as sa 
from sqlalchemy.orm import scoped_session, sessionmaker
from sqlalchemy.pool import QueuePool
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy import Column, Integer, String, ForeignKey
from sqlalchemy.dialects.mysql import TIMESTAMP as Timestamp

from .base import Base

# database_source_nameの作成
dsn = sa.engine.url.URL(
        drivername="mysql+pymysql", # or postgresql
        username="root",  # e.g. "my-database-user"
        password="pass",  # e.g. "my-database-password"
        host="mysql",  # e.g. "127.0.0.1"
        port=3306,  # e.g. 3306
        database="gg",  # e.g. "my-database-name"
    )

engine = sa.create_engine(
    dsn
)
session = scoped_session(
    sessionmaker(
        bind=engine
    )
)

# model定義
Base = declarative_base()
class User(Base):
    __tablename__ = "user"
    user_id = Column(String, primary_key=True, nullable=False)

# 確認: session作成時のpool情報確認 → この時点ではクエリが発行されていないので、poolの数は0のまま
session_engine.get_bind().pool.status()

# 確認:クエリ実行→クエリ実行すると connection数が増える. mysql側でconnection数が増えることを確認
session_engine.query(User).all()
session_engine.query(User).first()
session_engine.get_bind().pool.status()
# 'Pool size: 5  Connections in pool: 0 Current Overflow: -4 Current Checked out connections: 1'

# 確認: sessionを閉じてもconnection数が減らないことを確認する。→ checkoutされた checkout connecction が poolに戻されるだけ
session_engine.close()
session_engine.get_bind().pool.status()
# 'Pool size: 5  Connections in pool: 1 Current Overflow: -4 Current Checked out connections: 0'

session_engine.get_bind().dispose()
version: "2"
services:
    containerA:
        image: yauritux/busybox-curl
        tty: true
    containerB:
        image: nginx
動作確認

containerAからcontianerBへ通信する方法を見てみる。

# コンテナ起動
docker-compose up -d
# コンテナログイン
docker-compose exec containerA sh
# コンテナ内で動作確認

curl http://<docker-compose サービス名>

curl http://containerB

nginxのhtmlが取得できた。

<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
    body {
        width: 35em;
        margin: 0 auto;
        font-family: Tahoma, Verdana, Arial, sans-serif;
    }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>

ping <docker-compose サービス名> ※docker-composeはサービス名で名前解決できる

ping containerB

PING containerB (****): 56 data bytes
64 bytes from ****: seq=0 ttl=64 time=0.727 ms
64 bytes from ****: seq=1 ttl=64 time=0.118 ms

2022-05-19


command: mysqld --character-set-server=utf8 --collation-server=utf8_general_ci --wait_timeout=10

2022-05-20

domain=
backlog_api_key=

# プロジェクト一覧取得
curl -sS -X GET "https://${domain}.backlog.jp/api/v2/projects?apiKey=${backlog_api_key}"

2022-05-23

  • gcp
    • gcloudコマンド環境 in docker
ファイルの中身
Dockerfile
FROM gcr.io/google.com/cloudsdktool/cloud-sdk:370.0.0-alpine

RUN apk add --no-cache jq vim

WORKDIR /app

COPY service_account.json ./

RUN gcloud components install kubectl -q

RUN gcloud auth activate-service-account --key-file ./service_account.json && \
    gcloud config set project <projects-name> && \
    gcloud config set compute/zone <zone-name> && \
    gcloud container clusters get-credentials <credentials-name>

COPY kubeconfig-context ./

RUN KUBECONFIG=~/.kube/config:./kubeconfig-context kubectl config view --flatten > newkubeconfig && \
    cp newkubeconfig ~/.kube/config
docker-compose.yml
version: "3"
services:
  gcloud:
    build: .
    entrypoint:
      sleep  infinity
    volumes: 
      - "./:/app"
  • cloudsql proxy in docker
ファイルの中身
version: "3"
services:
  mysql:
    image: mysql:5.7
    command: mysqld --character-set-server=utf8 --collation-server=utf8_general_ci
    environment:
      MYSQL_ROOT_PASSWORD: ${MYSQL_PASSWORD}
      TZ: "Asia/Tokyo"
  cloudsqlproxy:
    image: gcr.io/cloudsql-docker/gce-proxy:1.23.0
    volumes:
      - ./cloudsqlproxy/:/secrets/cloudsql/
    command:
      [
        ./cloud_sql_proxy,
	-instances=INSTANCE_CONNECTION_NAME=tcp:0.0.0.0:1234,
        -credential_file=/secrets/cloudsql/service_account.json
      ]

2022-05-24

win2lin () { f="${1/C://c}"; printf '%s\n' "${f//\\//}"; }

$ file='C:\Users\abcd\Downloads\testingFile.log'
$ win2lin "$file"
/c/Users/abcd/Downloads/testingFile.log
$ 
$ file='C:\Users\pqrs\Documents\foobar'
$ win2lin "$file"
/c/Users/pqrs/Documents/foobar

2022-05-25

2022-05-29

  • 早期continue, break
    • ループ中の分岐処理は早期continue,breakを使うといい
result = 0
for i in range(1, 10):
    for j in range(1,10):
        if i == j:
            pass
        else:
            result += i*j
 
print(result)

# good
result = 0
for i in range(1, 10):
    for j in range(1,10):
        if i == j: continue
        result += i*j
print(result)
  • interface

    • 分岐処理を書くときは一度interfaceが使えるかどうか検討する
  • postgres

    • SELECT jsonb_pretty('{"a": 1, "b": 2, "c": 3}') as result

2022-06-13

  • gcloud
    • dns list取得
    • dns update
# dns list
gcloud dns record-sets list --zone=<zone名>
# dns update (全部書き換える)
gcloud dns record-sets update <FQDN> --rrdatas=<IPアドレス> --type=A --ttl=30 --zone=<zone名>

DB_DRIVER=postgresql
DB_USER=postgres
DB_PASS=password
DB_HOST=postgres
# DB_DRIVER=mysql
# DB_USER=mysql+pymysql
# DB_PASS=password
# DB_HOST=mysql
DB_NAME=test

# テーブル全部作る場合
sqlacodegen ${DB_DRIVER}://${DB_USER}:${DB_PASS}@${DB_HOST}/${DB_NAME} --outfile output.py

# 特定table郡から作るばあい
sqlacodegen ${DB_DRIVER}://${DB_USER}:${DB_PASS}@${DB_HOST}/${DB_NAME} --outfile output.py --tables <table名1>,<table名2>
ログインするとコメントできます