カテゴリー: tech

  • ローカル環境でHTTPSサーバーを立ち上げる

    ローカル環境でHTTPSサーバーを立ち上げる

    OpenSSLとNode.jsの http-server モジュールを使って、ローカル環境でHTTPSサーバーを立ち上げる方法を説明。

    Subject Alternative Name (SAN) を設定する

    vim SAN.txt
    ---
    subjectAltName = DNS:sumito.jp
    

    この手順では、SANを指定するためのファイル SAN.txt を作成します。ここでは sumito.jp をSANとして指定していますが、適宜変更してください。

    秘密鍵と証明書の作成

    openssl genrsa -out server.key 2048
    openssl req -out server.csr -key server.key -new
    openssl x509 -req -days 3650 -signkey server.key -in server.csr -out server.crt -extfile SAN.txt
    

    この一連のコマンドで、2048ビットの秘密鍵 server.key と、その秘密鍵に基づく証明書署名リクエスト(CSR) server.csr を作成します。最後に、CSRと秘密鍵から、有効期限3650日の自己署名証明書 server.crt を作成しています。この際、先ほど作成した SAN.txt ファイルを使ってSANを設定しています。

    HTTPSサーバーの起動

    http-server -S -C server.crt -K server.key -p 443
    

    最後に、http-server コマンドを実行して、HTTPSサーバーを起動します。このコマンドでは、作成した server.crtserver.key を指定し、ポート443でリッスンするように指定しています。

    hosts に以下の通り記載します

    127.0.0.1       sumito.jp
    

    これで、ローカル環境でHTTPSサーバーが立ち上がりました。ブラウザで https://sumito.jp/ にアクセスすると、自己署名証明書の警告が出る場合がありますが、それを無視して進めばウェブサーバーにアクセスできます。

    注意点として、この方法で作成した証明書は自己署名なので、実際の運用環境では使えません。

    本番環境で使う場合は、認証局から発行された適切な証明書を取得する必要があります

  • Shell でjsonの配列の変数から value を抜き出す

    Shell でjsonの配列の変数から value を抜き出す

    キーが固定の場合

    以下は、シェルスクリプトでJSONデータを読み込み、jqコマンドを使用して同様の処理を行う例です。

    #!/bin/bash
    
    json='[{"name":"Worker","no":"123"}, {"name":"User","no":"456"}, {"name":"Organization","no":"789"}, {"name": "Position","no":"123"}, {"name": "PositionTranslation","no":"123"}]'
    
    echo "$json" | jq -c '.[]' | while read -r item; do
      name=$(echo "$item" | jq -r '.name')
      no=$(echo "$item" | jq -r '.no')
      
      echo "$name"
      echo "$no"
      echo "-----"
    done

    このスクリプトでは:

    1. json変数にJSONデータを文字列として格納します。
    2. echo "$json" | jq -c '.[]'を使用して、JSONデータをパイプでjqコマンドに渡し、各オブジェクトを個別の行に分割します。
    3. while read -r itemを使用して、各オブジェクトを1つずつ読み込みます。
    4. echo "$item" | jq -r '.name'echo "$item" | jq -r '.no'を使用して、各オブジェクトからnamenoの値を抽出します。
    5. 抽出した値とセパレーターを表示します。

    結果はこちらです

    Worker
    123
    -----
    User
    456
    -----
    Organization
    789
    -----
    Position
    123
    -----
    PositionTranslation
    123
    -----
    
    

    キーが固定でない場合(接頭辞が共通の場合)

    JSONデータのキーが一部共通している場合、jqコマンドの to_entriesselectmapを組み合わせて目的の値を取得することができます。以下は、public_ip で始まるキーに対応する値を取得する例です。

    #!/bin/bash
    
    json='{"public_ip01": "1.2.3.4", "public_ip02": "2.3.4.5", "public_ip03": "12.2.3.4"}'
    
    echo "$json" | jq -r 'to_entries | map(select(.key | startswith("public_ip")).value)'
    

    このスクリプトでは:

    1. json 変数にJSONデータを文字列として格納します。
    2. echo "$json" | jq -r 'to_entries | map(select(.key | startswith("public_ip")).value)' を使用して、JSONデータを jq コマンドに渡し、以下の処理を行います:
      • to_entries で、JSONオブジェクトをキーと値のペアの配列に変換します。
      • map(select(.key | startswith("public_ip"))) で、キーが "public_ip" で始まるエントリーのみを選択します。
      • .value で、選択されたエントリーの値のみを取得します。
    3. jq の出力は、選択された値の配列になります。

    このスクリプトを実行すると、以下のような結果が得られます

    "1.2.3.4" "2.3.4.5" "12.2.3.4"

    これにより、public_ip で始まるキーに対応する値が取得できました。必要に応じて、この出力を変数に格納したり、ループ処理で個別に処理したりすることができます。

  • SendGridのSMTPサーバーを使ったメール送信をシェルスクリプトで確認する

    SendGridのSMTPサーバーを使ったメール送信をシェルスクリプトで確認する

    SendGridのSMTPサーバーを使ったメール送信をシェルスクリプトで確認する方法

    SendGridは、メールの配信を専門とするクラウドベースのサービスであり、多くの開発者やビジネスに利用されています。SendGridのSMTPサーバーを利用することで、アプリケーションからメールを送信することができます。ここでは、シェルスクリプトを使ってSendGridのSMTPサーバー経由でメールを送信する方法を紹介します。

    SendGridを使うメリット

    • 高い配信率: SendGridは、高い配信率を実現するために、メールの配信に関する様々な技術を駆使しています。
    • スパムフィルタリング: SendGridは、スパムメールの送信を防ぐために、高度なスパムフィルタリング技術を採用しています。
    • 分析とトラッキング: SendGridは、メールの開封率やクリック率などの詳細な分析データを提供し、メールマーケティングのパフォーマンスを追跡することができます。
    • シンプルなインテグレーション: SendGridは、SMTPリレーやWebAPIなど、様々なインテグレーション方法を提供しており、開発者にとって使いやすいサービスになっています。

    必要なもの

    • SendGridのアカウント
    • SendGridのAPIキー

    シェルスクリプト

    以下のシェルスクリプトを使って、SendGridのSMTPサーバー経由でメールを送信できます。

    #!/bin/bash
    
    smtp_server="smtp.sendgrid.net"
    smtp_port=587
    smtp_username="apikey"
    smtp_password="SG.xxxxxxxx"
    
    from_address="from@hoge.jp"
    to_address="to@hoge.jp"
    
    subject="Bash SMTP テスト"
    body="mail test"
    
    message="From: $from_address
    To: $to_address
    Subject: $subject
    
    $body"
    
    # メッセージをファイルに書き出す
    echo "$message" > message.txt
    
    # SMTPサーバーに接続してメールを送信
    curl --ssl-reqd \
    --url "${smtp_server}:${smtp_port}" \
    --user "${smtp_username}:${smtp_password}" \
    --mail-from "${from_address}" \
    --mail-rcpt "${to_address}" \
    --upload-file message.txt
    
    # 一時ファイルを削除
    rm message.txt
    

    手順

    1. SendGridのアカウントを作成し、APIキーを取得します。
    2. シェルスクリプトの smtp_password の部分を、取得したAPIキーに置き換えます。
    3. from_addressto_address を、実際の送信元と送信先のメールアドレスに置き換えます。
    4. シェルスクリプトを実行します。
     chmod +x script_name.sh ./script_name.sh
    1. メールが送信されたことを確認します。

    解説

    このシェルスクリプトでは、curlコマンドを使ってSendGridのSMTPサーバーに接続し、PLAINタイプの認証を使ってメールを送信します。

    メッセージ本文は一時ファイルに書き出され、curlコマンドの --upload-file オプションを使ってSMTPサーバーに送信されます。メール送信後、一時ファイルは削除されます。

    SendGridを使ったメール送信のテストの重要性

    SendGridを使ってメール送信機能を実装する前に、実際にメールが送信できることを確認することは非常に重要です。以下のような理由から、メール送信のテストを行うことが推奨されます。

    • メールの配信設定の確認: SendGridの設定が正しく行われているかどうかを確認することができます。
    • メールの内容の確認: メールの件名や本文が意図した通りに表示されるかどうかを確認することができます。
    • エラーの早期発見: メール送信に関する問題を早期に発見し、修正することができます。

    シェルスクリプトを使ったメール送信のテストは、手軽に実行できる方法の一つであり、SendGridを使ったメール送信機能の実装前に行うことをお勧めします。

    まとめ

    シェルスクリプトを使うことで、SendGridのSMTPサーバー経由でメールを送信できることを確認しました。この方法は、SendGridを使ってメール送信機能を実装する前の動作確認に役立ちます。メール送信のテストを行うことで、メールの配信設定やメールの内容を確認し、エラーを早期に発見することができます。SendGridを使ったメール送信機能の実装では、このようなテストを行うことが重要です。

    SendGridは、高い配信率やスパムフィルタリング、分析とトラッキング機能など、多くのメリットを提供するサービスです。SendGridを使うことで、信頼性の高いメール配信を実現することができます。

  • GitHub Actionsを使ったDockerイメージのビルドとAmazon ECRへのデプロイ

    GitHub Actionsを使ったDockerイメージのビルドとAmazon ECRへのデプロイ

    GitHub Actionsを使ったDockerイメージのビルドとAmazon ECRへのデプロイ

    今回は、GitHub Actionsを使ってDockerイメージをビルドし、Amazon Elastic Container Registry (ECR)にデプロイする方法について解説します。GitHub Actionsを活用することで、コードの変更に応じて自動的にDockerイメージをビルドし、ECRにプッシュすることができます。

    GitHub Actionsとは

    GitHub Actionsは、GitHubに組み込まれた継続的インテグレーション・継続的デプロイメント(CI/CD)のためのプラットフォームです。ワークフローを定義することで、コードのビルド、テスト、デプロイなどを自動化できます。GitHub Actionsでは、YAMLファイルを使ってワークフローを定義し、GitHubリポジトリ内の`.github/workflows`ディレクトリに配置します。

    Amazon ECRとは

    Amazon Elastic Container Registry (ECR)は、AWSが提供するフルマネージド型のDockerコンテナレジストリサービスです。ECRを使用すると、Dockerイメージを安全に保存、管理、デプロイすることができます。ECRは、AWSの他のサービスとの統合が容易で、スケーラビリティと可用性に優れています。

    ワークフローの解説

    それでは、GitHub Actionsを使ってDockerイメージをビルドし、Amazon ECRにプッシュするワークフローを解説していきます。

        - name: Login to Amazon ECR
          uses: aws-actions/amazon-ecr-login@v1
        - name: Build and push to Amazon ECR
          uses: docker/build-push-action@v3
            with:
            context: .
            push: true
            tags: ${{ env.ECR_REPOSITORY }}:${{ env.GITHUB_SHA }}
            cache-from: type=gha
            cache-to: type=gha,mode=max

    1. Amazon ECRへのログイン

    最初のステップでは、`aws-actions/amazon-ecr-login@v1`アクションを使用してAmazon ECRにログインします。このアクションは、AWSの認証情報を使用してECRレジストリにアクセスするために必要なログイン処理を行います。これは、以下の`aws`コマンドに相当します:

    aws ecr get-login-password --region <region> | docker login --username AWS --password-stdin <ecr-registry>

    2. DockerイメージのビルドとECRへのプッシュ

    次のステップでは、`docker/build-push-action@v3`アクションを使用して、Dockerイメージのビルドとプッシュを行います。このアクションは、以下の`docker`コマンドに相当します:

    docker build -t <ecr-registry>/<repository>:<tag> . docker push <ecr-registry>/<repository>:<tag>

    `with`セクションでアクションの設定を行います:

    • `context: .`: Dockerfileが存在するディレクトリを指定します。ここでは、現在のディレクトリ(`.`)を指定しています。
    • `push: true`: ビルドしたイメージをレジストリにプッシュすることを指定します。
    • `tags: ${{ env.ECR_REPOSITORY }}:${{ env.GITHUB_SHA }}`: イメージにタグを付けます。ここでは、環境変数`ECR_REPOSITORY`(ECRリポジトリのURL)とGitHubのコミットハッシュ(`GITHUB_SHA`)を組み合わせたタグを使用しています。
    • `cache-from: type=gha`: キャッシュからイメージレイヤーを読み込むことを指定します。`type=gha`は、GitHub Actionsのキャッシュを使用することを示します。
    • `cache-to: type=gha,mode=max`: ビルドしたイメージレイヤーをキャッシュに保存することを指定します。`mode=max`は、キャッシュを最大限に活用することを示します。

    キャッシュの活用

    GitHub Actionsでは、キャッシュ機能を利用してビルドの効率化を図ることができます。`cache-from`と`cache-to`オプションを使用することで、以前のビルドで作成されたイメージレイヤーをキャッシュから読み込み、ビルド時間を短縮できます。また、ビルドしたイメージレイヤーをキャッシュに保存することで、次回以降のビルドでそれらのレイヤーを再利用できます。

    キャッシュ機能は、`docker`コマンドや`aws`コマンドには直接対応する機能がありませんが、GitHub Actionsではこの機能を活用してビルドの効率化を図ることができます。

    まとめ

    GitHub Actionsを使ってDockerイメージをビルドし、Amazon ECRにデプロイする方法について解説しました。GitHub Actionsのワークフローでは、`aws-actions/amazon-ecr-login@v1`アクションを使用してECRにログインし、`docker/build-push-action@v3`アクションを使用してDockerイメージのビルドとプッシュを行います。また、キャッシュ機能を活用することで、ビルドの効率化を図ることができます。

    GitHub Actionsを活用することで、コードの変更に応じて自動的にDockerイメージをビルドし、ECRにデプロイすることができます。これにより、開発者はコードの開発に専念でき、CI/CDパイプラインの管理を簡素化できます。

    ぜひ、GitHub Actionsを使ってDockerイメージのビルドとデプロイを自動化してみてください。開発の効率化と品質向上に役立つはずです。

  • AWSコマンドでCloudFrontのキャッシュを消す

    AWSコマンドでCloudFrontのキャッシュを消す

    AWSコマンドでCloudFrontのキャッシュを消す方法

    AWSコマンドラインインターフェース(CLI)を使用してCloudFrontのキャッシュを無効化(Invalidation)する方法を説明します。

    手順

    以下のコマンドを実行します。

    aws cloudfront create-invalidation --distribution-id <distribution-id> --paths "<path1>" "<path2>" ...

    パラメータの説明

    • <distribution-id>: キャッシュを無効化したいCloudFrontディストリビューションのIDを指定します。
    • "<path1>" "<path2>" ...: キャッシュを無効化したいオブジェクトのパス(複数可)を指定します。パスはダブルクォーテーションで囲みます。

    ディストリビューションIDがEDFDVBD6EXAMPLEで、/index.html/images/logo.jpgのキャッシュを無効化したい場合は、以下のようになります。

    aws cloudfront create-invalidation --distribution-id EDFDVBD6EXAMPLE --paths "/index.html" "/images/logo.jpg"

    すべてのオブジェクトのキャッシュを無効化したい場合は、"/*"を指定します。

    aws cloudfront create-invalidation --distribution-id EDFDVBD6EXAMPLE --paths "/*"

    注意点

    • Invalidationリクエストには料金がかかります。
    • Invalidationが完了するまでには数分かかる場合があります。
    • 無効化されたオブジェクトは、次のリクエスト時に再びキャッシュされます。

    これにより、指定したパスのオブジェクトのキャッシュが無効化され、次のリクエスト時に新しいバージョンのオブジェクトがCloudFrontにキャッシュされます。

    以上で、AWSコマンドを使用してCloudFrontのキャッシュを消す方法の説明を終わります。ご不明な点があればお気軽にお問い合わせください。

  • Resource handler returned message: “The runtime parameter of nodejs14.x is no longer supported for creating or updating AWS Lambda functions. We recommend you use the new runtime (nodejs20.x) while creating or updating functions.

    Resource handler returned message: “The runtime parameter of nodejs14.x is no longer supported for creating or updating AWS Lambda functions. We recommend you use the new runtime (nodejs20.x) while creating or updating functions.

    AWS CDKでLambdaランタイムのアップグレードエラーを解決する

    AWS Cloud Development Kit (CDK)を使用してサーバーレスアプリケーションをデプロイする際に、Lambdaランタイムのバージョンアップによるエラーに遭遇することがあります。本記事では、そのようなエラーの原因と解決策について説明します。

    問題の概要

    CDKでLambda関数をデプロイしようとしたところ、以下のようなエラーが発生しました。

    Resource handler returned message: "The runtime parameter of nodejs14.x is no longer supported for creating or updating AWS Lambda functions. We recommend you use the new runtime (nodejs20.x) while creating or updating functions. (Service: Lambda, Status Code: 400, Request ID: 9xxx)" (RequestToken: e3c5cxxxx, HandlerErrorCode: InvalidRequest)
    

    このエラーは、AWS LambdaがNode.js 14.xランタイムのサポートを終了し、Node.js 20.xへの移行を推奨しているために発生しています。

    原因の特定

    エラーの原因を特定するために、プロジェクトの依存関係を確認したところ、package.jsonファイルに@aws-cdk/coreなどのCDK v1のパッケージが含まれていました。

    "dependencies": {
      "@aws-cdk/core": "^1.x.x",
      // ...
    }

    CDK v1はNode.js 14.xをデフォルトのランタイムとして使用していたため、これが原因でLambda関数のランタイムがNode.js 14.xになっていたのです。

    解決策

    この問題を解決するには、以下の手順を実行します。

    1. package.jsonファイルから、CDK v1の古いモジュール(@aws-cdk/coreなど)を削除します。
    2. CDK v2の新しいモジュール(aws-cdk-lib)をpackage.jsonファイルの依存関係に追加します。
    "dependencies": {
      "aws-cdk-lib": "^2.x.x",
      // ...
    }
    1. CDKのコード内で、@aws-cdk/coreなどの古いモジュールをインポートしている箇所を、aws-cdk-libからのインポートに変更します。
    2. npm installを実行して、更新された依存関係をインストールします。
    npm install
    1. CDKアプリケーションを再度合成し、CloudFormationテンプレートを生成します。
    cdk synth
    1. 生成されたCloudFormationテンプレートを確認し、Lambda関数のランタイムがNode.js 20.xに更新されていることを確認します。
    2. CDKアプリケーションをデプロイします。
    cdk deploy

    これで、Lambda関数のランタイムがNode.js 20.xに更新され、エラーが解消されるはずです。

    予防策

    今回の問題を予防するには、以下の点に注意が必要です。

    1. CDKのバージョンを最新のものに保つ
      • CDKは常に進化しており、新しいバージョンではモジュールの構造や名前が変更されることがあります。定期的にCDKのバージョンを更新することで、最新のベストプラクティスに沿ったアプリケーションを構築できます。
    2. 依存関係を定期的に確認する
      • プロジェクトの依存関係に古いモジュールが含まれていないか、定期的に確認することが重要です。古いモジュールを使用し続けると、セキュリティの問題や非互換性の問題が発生する可能性があります。
    3. AWS公式ドキュメントを参照する
      • AWSのサービスは常に進化しており、サポートされるランタイムやベストプラクティスも変化します。定期的にAWS公式ドキュメントを確認し、最新の情報を把握することが重要です。

    まとめ

    AWS CDKを使用する際に、古いCDKバージョンの依存関係が含まれていることが原因で、Lambdaランタイムのバージョンアップによるエラーに遭遇することがあります。このようなエラーは、古いモジュールを削除し、新しいモジュールを使用することで解決できます。また、CDKとAWSのサービスの進化に合わせて、定期的にアプリケーションの依存関係を見直すことが重要です。

    本記事が、同様の問題に直面した開発者の助けになれば幸いです。

  • Git: 特定のファイルだけを別のブランチにマージする方法

    Git: 特定のファイルだけを別のブランチにマージする方法

    Git: 特定のファイルだけを別のブランチにマージする方法

    Gitを使用していると、あるブランチの特定のファイルだけを別のブランチにマージしたい場合があります。この記事では、そのような状況で役立つGitコマンドについて説明します。

    ステップバイステップガイド

    1. まず、マージ先のブランチ(例: developブランチ)をローカルに最新の状態に更新します。

      git checkout develop git pull origin develop
    2. 次に、新しいブランチを作成し、そのブランチに切り替えます。

      git checkout -b merge-specific-file
    3. マージ元のブランチ(例: features/new-featureブランチ)から特定のファイル(例: path/to/file.txt)を現在のブランチにコピーします。

      git checkout features/new-feature -- path/to/file.txt
    4. 変更をステージングしてコミットします。

      git add path/to/file.txt git commit -m "Merge specific file from features/new-feature"
    5. 新しいブランチをリモートリポジトリにプッシュします。

      git push -u origin merge-specific-file
    6. GitHubやGitLabなどのWebインターフェースを使用して、merge-specific-fileブランチからdevelopブランチへのプルリクエストを作成します。

    7. プルリクエストがレビューされ、承認されたら、マージを完了します。

    8. 最後に、ローカルのdevelopブランチを更新します。

      git checkout develop git pull origin develop

    以上のステップにより、特定のブランチの特定のファイルのみを別のブランチにマージするためのプルリクエストを作成できます。

    まとめ

    Gitの柔軟性により、様々な状況に対応できます。特定のファイルだけをマージする必要がある場合は、上記のステップに従うことで、簡単にその目的を達成できます。このテクニックを活用して、Gitワークフローをさらに効率化しましょう。

  • 【Athena】タイムスタンプと文字列の比較で起こるTYPE_MISMATCHエラーの解決方法

    【Athena】タイムスタンプと文字列の比較で起こるTYPE_MISMATCHエラーの解決方法

    【Athena】タイムスタンプと文字列の比較で起こるTYPE_MISMATCHエラーの解決方法

    1. はじめに

    データ分析においてAthenaは非常に強力なツールですが、クエリを書く際にデータ型の不一致によるエラーに遭遇することがあります。特にタイムスタンプと文字列の比較は、TYPE_MISMATCHエラーを引き起こしやすい事例の一つです。本記事では、このエラーの原因と解決方法を詳しく説明します。

    2. TYPE_MISMATCHエラーとは

    TYPE_MISMATCHエラーは、比較や演算を行う際に、データ型が一致しない場合に発生します。例えば、以下のようなエラーメッセージが表示されます。

    TYPE_MISMATCH: line 18:56: Cannot check if timestamp(3) with time zone is BETWEEN varchar(10) and timestamp(3) with time zone

    このメッセージは、タイムスタンプ型の値と文字列型の値を比較しようとしたために、エラーが発生したことを示しています。

    3. タイムスタンプと文字列の比較によるTYPE_MISMATCHエラー

    Athenaでは、タイムスタンプ型と文字列型は異なるデータ型として扱われます。タイムスタンプ型は日付と時刻を含む値を表現するのに対し、文字列型は文字の並びを表現します。そのため、これらの型を直接比較することはできません。

    以下は、タイムスタンプと文字列を比較しようとしてTYPE_MISMATCHエラーが発生する例です。

    SELECT * FROM table WHERE from_unixtime(timestamp/1000, 'Asia/Tokyo') BETWEEN '2024-03-01' AND now();

    ここでは、from_unixtime関数の結果がタイムスタンプ型なのに対し、'2024-03-01'は文字列型になっているため、比較ができずにエラーが発生しています。

    4. エラーを解決する方法

    TYPE_MISMATCHエラーを解決するには、比較する値のデータ型を一致させる必要があります。上記の例では、文字列をタイムスタンプ型に変換することで、エラーを解消できます。

    SELECT * FROM table WHERE from_unixtime(timestamp/1000, 'Asia/Tokyo') BETWEEN timestamp '2024-03-01 00:00:00' AND now();

    ここでは、timestampキーワードを使って文字列'2024-03-01 00:00:00'をタイムスタンプ型に明示的に変換しています。これにより、from_unixtime関数の結果と比較可能になり、エラーが解決されます。

    5. 他のTYPE_MISMATCHエラーの事例と対処法

    タイムスタンプと文字列の比較以外にも、整数型と文字列型、日付型と文字列型など、異なる型同士の比較によってTYPE_MISMATCHエラーが発生することがあります。

    例えば、整数型の値と文字列型の値を比較しようとすると、以下のようなエラーが発生します。

    TYPE_MISMATCH: line 3:22: Cannot check if integer is BETWEEN varchar(1) and varchar(1)

    この場合も、文字列を整数型に変換することでエラーを解決できます。

    SELECT * FROM table WHERE int_column BETWEEN cast('1' as integer) AND cast('100' as integer);

    同様に、日付型と文字列型の比較では、文字列を日付型に変換する必要があります。

    SELECT * FROM table WHERE date_column BETWEEN date '2024-03-01' AND date '2024-03-31';

    6. Athenaを使う上での型に関するベストプラクティス

    Athenaを効果的に使うには、データ型に関するいくつかのベストプラクティスを守ることが重要です。

    • 一貫したデータ型の使用: テーブル内の各列には、適切なデータ型を設定し、一貫して使用します。
    • 比較や演算前の型チェック: クエリを実行する前に、比較や演算に使用する値のデータ型を確認します。
    • 明示的な型変換の実施: 必要に応じて、cast関数やtimestampキーワードなどを使って明示的に型変換を行います。

    これらのプラクティスを守ることで、TYPE_MISMATCHエラーを未然に防ぎ、正しいクエリを書くことができます。

    7. まとめ

    本記事では、Athenaでタイムスタンプと文字列を比較する際に発生するTYPE_MISMATCHエラーについて説明しました。このエラーは、異なるデータ型同士を比較しようとすることで発生します。解決方法は、文字列をタイムスタンプ型に変換することです。

    また、整数型と文字列型、日付型と文字列型の比較でも同様のエラーが起こりうるため、適切な型変換が必要です。Athenaを使う際は、一貫したデータ型の使用、比較前の型チェック、明示的な型変換を心がけましょう。

    これらのポイントを理解し、実践することで、TYPE_MISMATCHエラーを避け、Athenaをより効果的にデータ分析に活用できるようになります。

    8. 参考資料

    以上が、WordPressのエディタにコピーしやすい形式で書き直した技術ブログ記事です。HTML タグを使ってマークアップしているので、そのままコピー&ペーストすれば、WordPressの記事として利用できるはずです。必要に応じて、画像やその他の要素を追加してカスタマイズしてください。

  • AWS S3とCloudFrontを使ってシングルページアプリケーション(SPA)を公開する

    AWS S3とCloudFrontを使ってシングルページアプリケーション(SPA)を公開する

    AWSを使用してウェブサイトを公開する際、S3とCloudFrontは非常に人気のある選択肢です。これらのサービスは、静的コンテンツの配信に優れており、シングルページアプリケーション(SPA)のようなモダンなウェブアプリケーションのホスティングに適しています。しかし、S3の静的ウェブサイトホスティングとCloudFrontを組み合わせる際には、いくつかの設定を理解しておく必要があります。

    S3の静的ウェブサイトホスティング

    Amazon S3は、静的ウェブサイトホスティングを簡単に行えるようにサポートしています。これにより、HTML、CSS、JavaScriptファイルなどの静的ファイルを保存し、ウェブサイトとして公開できます。S3バケットで静的ウェブサイトホスティングを有効にすると、デフォルトドキュメント(通常はindex.html)へのリクエストをサポートし、特定のパスが指定された場合に自動的にそのファイルを返すようになります。これはSPAの開発において重要な機能です。なぜなら、クライアントサイドでのルーティングを使って、異なるURLが同一のHTMLファイルによって処理されることが多いからです。

    例: http://example-bucket.s3-website-region.amazonaws.com/about のリクエストは、about ディレクトリにファイルが存在しなくても、自動的に index.html を返します。

    CloudFrontとS3の組み合わせ

    CloudFrontは、AWSが提供する高速コンテンツ配信ネットワーク(CDN)サービスで、世界中のエッジロケーションからコンテンツを迅速に配信できます。S3バケットをオリジンとしてCloudFrontディストリビューションを設定することで、ウェブサイトのロード時間を短縮し、セキュリティを強化することが可能です。

    しかし、CloudFrontを介してSPAを公開する際には、S3の静的ウェブサイトホスティングとは異なる挙動に注意する必要があります。特に、存在しないパスへのリクエストが来た場合、CloudFrontはデフォルトでindex.htmlにリダイレクトせず、404エラーを返すため、SPAのクライアントサイドルーティングが期待通りに機能しません。

    解決策: カスタムエラーレスポンスの設定

    この問題を解決するには、CloudFrontディストリビューションのカスタムエラーレスポンス設定を使用します。具体的には、404(NotFound)や403(Forbidden)のエラーが発生した場合に、index.htmlページを返し、HTTPステータスコード200を使用してレスポンスするように設定します。これにより、リクエストされたパスに対応するファイルがS3バケットに存在しない場合でも、クライアントサイドのJavaScriptがルーティングを処理できるようになります。

    AWS CDKを使用してこの設定を実装する例は以下の通りです。

    const distribution = new cloudfront.Distribution(this, 'SiteDistribution', {
      // その他の設定...
      errorResponses: [
        {
          httpStatus: 404,
          responseHttpStatus: 200,
          responsePagePath: '/index.html',
          ttl: Duration.seconds(0),
        },
        {
          httpStatus: 403,
          responseHttpStatus: 200,
          responsePagePath: '/index.html',
          ttl: Duration.seconds(0),
        }
      ],
    });
    

    この設定により、CloudFrontはS3と同様の挙動をするようになり、SPAのホスティングに適した環境を提供します。

    結論

    AWS S3とCloudFrontは、静的コンテンツやSPAの公開に強力な選択肢です。ただし、CloudFrontを介してSPAを公開する場合には、カスタムエラーレスポンスの設定を適切に行うことで、クライアントサイドルーティングを正しく機能させることが可能になります。この設定により、ユーザーにとってより快適なウェブサイト体験を提供することができます。

  • Ubuntuコンテナにおける利用可能なPHPの version について

    Ubuntuコンテナにおける利用可能なPHPの version について

    背景

    PHPは広く使用されているオープンソースの汎用スクリプト言語で、特にWeb開発に適しています。Dockerコンテナ内で異なるバージョンのPHPが利用できるかどうかは、開発やデプロイのプロセスに大きな影響を与える可能性があります。

    最近、異なるUbuntuコンテナでインストール可能なPHPのバージョンを深く掘り下げる必要がある状況に遭遇しました。

    発見プロセス

    当初、ubuntu:18.04ベースのDockerコンテナにPHPバージョン7.3以上をインストールしようとしました。ppa:ondrej/php を追加しても、7.2以上のバージョンのPHPをインストールすることができませんでした。

    私のプロジェクトの多くは、様々な依存関係やそれ以降のPHPバージョンで導入された機能により、少なくともPHP 7.3が必要だったため、この制限は大きな課題となりました。

    Ubuntu 18.04での実験

    ubuntu:18.04コンテナを使い、以下のコマンドを活用してPHP 7.3と8.0のインストールを試みました

    sudo add-apt-repository ppa:ondrej/php
    sudo apt-get update
    sudo apt-get install php7.3

    以下の様なエラーになりました

    E: Unable to locate package php7.3
    E: Couldn't find any package by glob 'php7.3'
    E: Couldn't find any package by regex 'php7.3'

    Ubuntu 20.04への乗り換え

    ubuntu:18.04で直面した課題に促され、Dockerコンテナをubuntu:20.04に切り替えることにしました。

    同じ手順を適用したところ、PHPバージョン7.3、7.4、そしてPHP 8.0まで問題なくインストールできました。

    分析

    このことにより、ベースイメージが利用可能なPHP の version に影響することが明確になりました。Ubuntu 18.04は古いLTSリリースであるため、時には複雑な設定を追加しなければ、7.2以上のPHPバージョンをネイティブにサポートしていません。

    対照的に、最新のLTSバージョンであるUbuntu 20.04は、ソフトウェアの互換性と可用性の進歩を反映して、新しいPHPバージョンをすぐにサポートしています。

    結論

    Docker環境でPHPを扱う開発者やDevOpsエンジニアにとって、ベースコンテナイメージとソフトウェアパッケージの可用性の関係を理解することは非常に重要です。

    PHPのバージョン7.3以降を使用する予定であれば、ubuntu:20.04コンテナを選択するのが、より簡単で効率的な選択かと思います。

    推奨事項

    • プロジェクトのセットアップを開始する前に、選択したUbuntuコンテナのバージョンとのPHPバージョンの互換性を必ず確認してください。
    • 新しいPHPバージョンのサポートが必要な場合は、Dockerコンテナを新しいUbuntuバージョンにアップグレードすることを検討してください。
    • UbuntuのリリースでサポートされているPHPのバージョンについて常に情報を入手し、スムーズな開発とデプロイを行いましょう。