go gin multipart 画像保存
公式通りに進めていけばそんなに難しくなかったけど、忘れないうちにアウトプット
今回はreactでaxios使用してサーバー側に送りました。 商品を名前や詳細と同時に画像を保存する処理です。(validationとかはまだ) ginにはSaveUploadFileという関数が用意されています。引数にそのファイルとディレクトリを指定あげればapp内に保存されます。
ItemController
func Store(c *gin.Context) { var item domain.Item err := c.Bind(&item) if err != nil { c.String(http.StatusBadRequest, "Request is failed: "+err.Error()) return } //商品画像とリレーション紐づけるのでidの返り値を貰う。 id := repository.SaveItem(&item) //同じファイル名が重複しないようにランダム値に変更 file, _ := c.FormFile("image") fileName := filepath.Ext(file.Filename) newFileName := uuid.New().String() + fileName filePath := "./public/images/" //ここはいらないかも if f, exist := os.Stat(filePath); os.IsNotExist(exist) || !f.IsDir() { c.AbortWithStatusJSON(http.StatusInternalServerError, gin.H{ "message": "error. could not find dir", }) } //ここでディレクトリに保存、公式参照 er := c.SaveUploadedFile(file, filePath + newFileName) if er != nil { c.AbortWithStatusJSON(http.StatusInternalServerError, gin.H{ "message": "Unable to save the file", }) return } //ファイル情報をDBに保存 repository.SaveItemImage(newFileName, id) c.JSON(http.StatusCreated, gin.H{ "name": item.Name, "detail": item.Detail, }) }
ItemImageRepository
//ここは結構シンプルです func SaveItemImage(fileName string, id uint) { fmt.Println() filePath := "/public/images/" db := database.GormConnect() var data domain.ItemImage data.ItemId = id data.File_name = fileName data.Path = filePath + fileName now := time.Now() data.CreatedAt = now data.UpdatedAt = now db.Create(&data) }
とりあえず動くことは動きます。 まだまだこれで運用には程遠いと思いますので、この後は例外処理とか入れてハンドリング予定