🥕

【AWS】ExpressからS3objectを操作する

2023/08/17に公開

localのexpressから、amazonS3を操作するコードを解説します。

AWS側の設定

BucketとObjectの作成

テスト用にs3のリソースを作成しておきます。

実装

SDKインストール

aws-sdk-for-javascript-v3を使用します。
v3からは操作対象のサービス毎に必要なライブラリがあり、今回はS3用のライブラリをyarnでインストールします。

yarn add @aws-sdk/client-s3

awsConfig

awsのユーザー設定をawsConfigオブジェクトにまとめて使用します。
渡すのは下記の3つです

  • Region
  • AccessKey
  • SecretAccessKey
const dotenv = require("dotenv");
dotenv.config();

export const awsConfig = {
  region: process.env.REGION,
  credentials: {
    accessKeyId: process.env.AWS_ACCESS_KEY,
    secretAccessKey: process.env.AWS_SECRET_KEY,
  },
};

S3インスタンス生成

awsConfigと、インストールしたs3clientを利用して、s3データのオブジェクトを生成します。
以降でs3にローカルからアクセスする際は「s3Context」を利用するようにします。

import { S3Client } from "@aws-sdk/client-s3";
import { awsConfig } from "../config/aws";

export const s3Context = new S3Client(awsConfig);

ロジックの実装

GET, PUT毎にエンドポイントを用意し、S3Controllerにメソッドを用意してpostmanから叩く流れで動作検証を行います。

router

import express from "express";
const router = express.Router();
const { S3Controller } = require("../controller/S3Controller");

// S3Controllerクラスのインスタンス化
const s3 = new S3Controller();

// エンドポイントでメソッドを振り分ける
router.get("/s3GetObject", s3.getObject);
router.post("/s3PutObject", s3.putObject);

module.exports = router;

S3Controller

aws-sdk/client-s3から目的別にCommandオブジェクトが提供されているので、それを利用してS3を操作します。
requestから値を受け取り、それをCommandの引数に渡すことで指定のリソースを操作できる設計です。

import { Request, Response } from "express";
import {
  GetObjectCommand,
  PutObjectCommand,
} from "@aws-sdk/client-s3";
import { s3Context } from "../../lib/s3Client";
const dotenv = require("dotenv");
dotenv.config();

export class S3Controller {
  async getObject(req: Request, res: Response): Promise<void> {
    const { bucketName, objectName } = req.body;
    const command = new GetObjectCommand({
      Bucket: `${bucketName}`,
      Key: `${objectName}`,
    });
    try {
      const response = await s3Context.send(command);
      const str = await response.Body?.transformToString();
      res.send(str);
    } catch (error) {
      console.log(error);
    }
  }

  async putObject(req: Request, res: Response): Promise<void> {
    const { bucketName, objectName, body } = req.body;
    const command = new PutObjectCommand({
      Bucket: `${bucketName}`,
      Key: `${objectName}`,
      Body: `${body}`,
    });

    try {
      const response = await s3Context.send(command);
      res.status(201).json({
        message: "create s3 object",
        response,
      });
    } catch (error: any) {
      res.status(4001).json({
        message: error.message,
      });
    }
  }
}

動作検証

getObject

bucket名、object名をrequestに含めてhtmlファイルを取得

PutObject

bucket名、object名、bodyをrequestに含めて新規オブジェクトを作成

getObjectで新規オブジェクトを確認

Discussion