FuelPHPでDUPLICATE KEY UPDATE

なるべくDBへのアクセスを減らして、テーブルにレコードが存在しないときはInsert、テーブルに登録済みの場合は商品名を更新したいときなどに使う。

  • 更新前
id title
1 foo
2 bar

<?php
        $data = [
            0 => ['id' => 1, 'name' => 'hoge'],
            1 => ['id' => 2, 'name' => 'fuga']
        ];

        $query = \DB::insert('products')
            ->columns(
                ['id', 'title']);

        foreach ($data as $item) {
            $query->values(
                [
                    $item->id,
                    $item->title,
                ]);
        }

        \DB::query($query->compile() . "ON DUPLICATE KEY UPDATE `title` =VALUES(`title`), `updated_at` = NOW()")->execute();

  • 更新後
id title
1 hoge
2 fuga

UPDATEされるのは、UNIQUEインデックスまたはPRIMARY KEYに重複した値を発生させる行が挿入された場合のみ。
idがUNIQUEかPRIMARY KEYではない場合は、INSERTされることになる。

手を動かしながら2週間で学ぶ AWS 基本から応用まで Day6

Day6 ELBを用いてWebレイヤの可用性を高める

AWSの設計の考え方

基本的に、単一障害点(single point of failure、SPOF)を作らない=冗長化すること

・DB層はRDSで、master - slave構成で障害に備える。
・Web層はELBを使う。

Elastic Load Balancing は受信したアプリケーションまたはネットワークトラフィックを、Amazon EC2 インスタンス、コンテナ、IP アドレス、複数のアベイラビリティーゾーンなど、複数のターゲットに分散させる。

・ELBの主要機能
https://aws.amazon.com/jp/elasticloadbalancing/features/#compare

  1. 負荷分散
    EC2の負荷を見て、負荷が均等になるようにリクエストを分散する

  2. ヘルスチェック
    正しい動きをしているインスタンスのみにリクエストを振る

  3. Auto Scaling
    条件を決めてEC2の数を増減させる

ALB Application Load Balancer
アプリケーション層

NLB Network Load Balancer
ネットワーク層

負荷分散とヘルスチェック

  • EC2インスタンスのAMIを作成する
    Web-1aをコピーする
    アクション→イメージ→イメージの作成

RDSインスタンスを起動させておく

  • VPC
    EC2を作成したときに自動的にパブリックのIPを割り当てるようにする
    public-subuet-1a
    public-subuet-1c
    自動割当IP設定の変更→パブリック IPv4 アドレスの自動割り当てを有効にする

  • EC2インスタンス Web-1aを起動する

  • AMIからweb-1cを作成する
    サブネット:public-subnet-1c
    タグ:Name Web-1c
    セキュリティグループ:Web-sg
    インスタンスの作成

/var/www/html/index.phpの中身をWeb-1aとWeb-1cのインスタンスで中身を変えておく

  • ロードバランサーの設定 EC2→ロードバランサー→作成→ALB
    スキーム:インターネット向け
    IPアドレスタイプ:ipv4
    リスナー:HTTP
    アベイラビリティーゾーン
    ap-north-1a public-subnet-1a
    ap-north-1c public-subnet-1c

  • セキュリティグループの設定
    新しいセキュリティグループを設定する
    セキュリティグループ名:ELB-sg
    タイプ:HTTP
    プロトコル:TCP
    ポート:80
    ソース:カスタム 0.0.0.0/0, ::/0

  • ルーティングの設定
    ターゲットグループの設定:デフォルト
    ヘルスチェック:しきい値を低くする

  • ターゲットの登録
    起動済みのWeb-1a, Web-1cを選択→登録済みを押して追加

作成

ロードバランサーが起動後
ターゲットグループ→登録済みターゲットがhealtyになっていることを確認
ロードバランサーDNS名をコピーしてアクセスすると、Web-1a/Web-1cのどちらかに割り振られることがわかる

Web-1aのapacheを止めてみる

sudo service httpd stop

ロードバランサーのステータスがunhealthyになり、Web-1cにのみ割り振られるようになる

オートスケーリング

EC2→AUTO SCALING→起動設定→起動設定の作成
AMIの選択:マイAMI
起動設定の作成:デフォルト
セキュリティグループ:Web-sgを選択
作成

  • Auto Scalingグループの作成
    グループサイズ:開始時2インスタンス
    サブネット:public-1a,public-1c

  • 高度な詳細
    ロードバランシング:一つまたは複数のロードバランサーからトラフィックを受信する
    ターゲットグループ:さっきつくったターゲットグループを選択
    自動起動したインスタンスがターゲットグループに紐付けられるようになる
    ヘルスチェック:ELBの単位で行う
    スケーリングポリシーの設定

  • Auto Scalingグループの作成
    スケーリングポリシーを使用して、このグループのキャパシティを調整する
    スケーリングの範囲:2~4
    グループサイズの増加→新しいアラームの作成
    しきい値の設定
    アクションを設定:インスタンスを2追加
    作成
    f:id:kyamashiro:20190118222744p:plain インスタンスにAutoScalingで作成したインスタンスが2つ作成されている
    f:id:kyamashiro:20190117235214p:plain ロードバランシングのターゲットグループにもAutoScalingで作成したインスタンスが2つ登録されている

  • AutoScalingで作成したインスタンスに負荷をかける

yes > /dev/null &

負荷が設定したCPU使用率40%を超えるとインスタンスが2つ増え、Auto Scalingグループの作成で設定したインスタンスが最大4つになる。

ELBの設計ポイント

  1. AZをまたがったサーバ配置
    AZの障害があっても他のAZが正常なら動作できる

  2. アプリケーションをステートレスに構築する
    どのWebに振られても問題なく動作できるようにする セッションなどをElastic Cacheに保存するなど、あるインスタンスから別のインスタンスに振られても問題なくアプリケーションが動作するように設計する

手を動かしながら2週間で学ぶ AWS 基本から応用まで Day5

Day5 リレーショナルDBのマネージドサービスRDSを使う

RDSについて

Master - Slave構成が容易

リードレプリカ
Master - Reprica
更新はMaster 参照系はレプリカ
Masterのみの構成だとDBがボトルネックになってスループットが落ちる

Amazon RDSの作成

RDS→サブネットグループ→DBサブネットグループの作成
DBインスタンスをどのサブネットで起動するか設定する

名前・説明を入力・VPCグループを選択

サブネットの追加
「このVPCに関連するすべてのサブネットを追加する」を選択すると、VPCのサブネットがすべて追加される

privateのサブネットを追加する
アベイラビリティーゾーン
ap-northeast-1a
サブネット
10.0.21.0

アベイラビリティーゾーン
ap-northeast-1c
サブネット
10.0.22.0

パラメータグループの作成
デフォルトのものが定義されて使えるが、変更することができない
変更する場合はパラメータグループで設定する

パラメータグループファミリー:mysql5.7

グループ名:mysql57-parameter-group

RDS→データベースの作成→MySQL

RDS 無料利用枠の対象オプションのみを有効化
Master - Slave構成にするのでチェックを外す
ユースケース:開発/テスト用

DB 詳細の指定
DBエンジンのバージョン:5.7系

インスタンスのクラスを選択
マルチAZ配置
[x] 別のゾーンにレプリカを作成します
ストレージタイプ:汎用
ストレージ割当:20

DBインスタンスの識別子を入力

  • 詳細設定 ネットワーク&セキュリティ
    VPCを選択
    サブネットグループ
    前に作ったprivateサブネット
    パブリックアクセシビリティ:いいえ

アベイラビリティーゾーン:指定なし
Master - Slave構成で作成したいので

VPCセキュリティグループ:DB-sg
前回作成したweb-sgからの接続のみ許可するDB-sgを設定する
Defaultを消す

データベースの設定
データベースの名前:空白
ポート:3306

IAM DB認証:無効化

バックアップ
バックアップウィンドウ
どの時間帯にバックアップするのかを選択できる

拡張モニタリング:無効にする

ログのエクスポート:チェックなし

データベースの作成

RDSにつなぐ

EC2インスタンスWeb-1a DB-1aを起動
Web-1aのインスタンスにログイン

ssh -i key-pair.pem ec2-user@Web-1aのIPv4  
mysql -h RDSのエンドポイント -u root -p  

データベースの作成

create database simple_blog;  
use simple_blog;  

テーブル作成・データInsert  
create table posts (id int not null primary key, title varchar(100), detail varchar(1000), image varchar(1000));  

insert into posts values (1, "XXXX-RDS", "XXXXXXXXXX", "./img/img1.jpeg");  

insert into posts values (2, "YYYY-RDS", "YYYYYYYYYY", "./img/img2.jpeg");  

# 設定変更
sudo vim /var/www/html/index.php  

$dbh = new PDO('mysql:host=RDSのエンドポイントにする;dbname=simple_blog', "root", "password");  

スナップショットの取得とリストア

RDS→インスタンスの操作→スナップショットの取得
スナップショットのアクション→スナップショットのアクション→スナップショットの復元
RDSインスタンスが新しく作られる、セキュリティグループがデフォルトになっているので変更する。

シングル構成にする

Master - Slave構成だとインスタンスの停止ができない
RDS→DBインスタンスの変更→マルチAZ配置:いいえ
シングル構成になるのでRDSインスタンスの停止ができるようになる

『「納品」をなくせば、うまくいく』を読んだ

 

「納品」をなくせばうまくいく

「納品」をなくせばうまくいく

 

 

『「納品」をなくせば、うまくいく』を読んだ。

 

e-words.jp

 

受託開発という形式を取る以上、仕様を決めていかにスケジュール通りに作るかということになる。スケジュールが伸びると、クライアントがそれを受け入れて伸びた分のコストを支払ってくれるのなら問題はないが、そうではないのなら開発する側の利益が減ることになる。

一括請負では最初に要件定義と見積もりをして、作るものと金額を決めてから開発を始めるので、開発会社が利益を確保するためには、当初に見積もった予算の範囲に収まるように、なるべくコストを抑えることが大事になってきます。p.22

仕組み的にそうなっているので、「言われたことだけやる=言われた以外のことをやらない」というのがベストという思考になってきている。

この機能はどういう目的で誰が使うのかと疑問に思っても、作ればお金がもらえるので、もやもやしたまま言われたとおりに作ることになる。

結局、大して価値がないものを作っているということになる。悲しい。