fix(image):

This commit is contained in:
pakintada@gmail.com 2024-06-03 10:12:16 +07:00
parent 2b8745679f
commit 040c3c7751
6 changed files with 459 additions and 437 deletions

2
.gitignore vendored
View file

@ -4,3 +4,5 @@ server/services/logger/serverlog.log
server/cofffeemachineConfig server/cofffeemachineConfig
node_modules node_modules
server/cofffeemachineConfig.diff server/cofffeemachineConfig.diff
**/.env
nginx_cfg/

3
client/.gitignore vendored
View file

@ -1,7 +1,8 @@
# See http://help.github.com/ignore-files/ for more about ignoring files. # See http://help.github.com/ignore-files/ for more about ignoring files.
# Compiled output # Compiled output
/dist /dist/client/
/dist/client.zip
/tmp /tmp
/out-tsc /out-tsc
/bazel-out /bazel-out

View file

@ -1,372 +1,376 @@
import { CommonModule, DatePipe } from '@angular/common'; import { CommonModule, DatePipe } from "@angular/common";
import { Component, EventEmitter, OnInit } from '@angular/core'; import { Component, EventEmitter, OnInit } from "@angular/core";
import { FormBuilder, FormsModule, ReactiveFormsModule } from '@angular/forms'; import { FormBuilder, FormsModule, ReactiveFormsModule } from "@angular/forms";
import { ActivatedRoute, Router, RouterLink } from '@angular/router'; import { ActivatedRoute, Router, RouterLink } from "@angular/router";
import { Observable, first, map } from 'rxjs'; import { Observable, first, map } from "rxjs";
import { RecipeService } from 'src/app/core/services/recipe.service'; import { RecipeService } from "src/app/core/services/recipe.service";
import { ConfirmModal } from 'src/app/shared/modal/confirm/confirm-modal.component'; import { ConfirmModal } from "src/app/shared/modal/confirm/confirm-modal.component";
import { animate, style, transition, trigger } from '@angular/animations'; import { animate, style, transition, trigger } from "@angular/animations";
import { RecipeListComponent } from './recipe-list/recipe-list.component'; import { RecipeListComponent } from "./recipe-list/recipe-list.component";
import { import {
Recipe01, Recipe01,
RecipeDetail, RecipeDetail,
RecipeDetailMat, RecipeDetailMat,
Topping, Topping,
ToppingSet, ToppingSet,
} from 'src/app/core/models/recipe.model'; } from "src/app/core/models/recipe.model";
import { ActionRecord } from 'src/app/shared/actionRecord/actionRecord'; import { ActionRecord } from "src/app/shared/actionRecord/actionRecord";
import { UserService } from 'src/app/core/services/user.service'; import { UserService } from "src/app/core/services/user.service";
import { UserPermissions } from 'src/app/core/auth/userPermissions'; import { UserPermissions } from "src/app/core/auth/userPermissions";
import { ToppingService } from 'src/app/core/services/topping.service'; import { ToppingService } from "src/app/core/services/topping.service";
import { copy, transformToTSV } from 'src/app/shared/helpers/copy'; import { copy, transformToTSV } from "src/app/shared/helpers/copy";
import { isEqual } from 'lodash'; import { isEqual } from "lodash";
import { environment } from 'src/environments/environment'; import { environment } from "src/environments/environment";
@Component({ @Component({
selector: 'app-recipe-details', selector: "app-recipe-details",
templateUrl: './recipe-details.component.html', templateUrl: "./recipe-details.component.html",
standalone: true, standalone: true,
animations: [ animations: [
trigger('inOutAnimation', [ trigger("inOutAnimation", [
transition(':enter', [ transition(":enter", [
style({ opacity: 0 }), style({ opacity: 0 }),
animate('1s ease-out', style({ opacity: 1 })), animate("1s ease-out", style({ opacity: 1 })),
]), ]),
]), ]),
], ],
imports: [ imports: [
CommonModule, CommonModule,
RouterLink, RouterLink,
ReactiveFormsModule, ReactiveFormsModule,
ConfirmModal, ConfirmModal,
DatePipe, DatePipe,
RecipeListComponent, RecipeListComponent,
FormsModule, FormsModule,
], ],
}) })
export class RecipeDetailsComponent implements OnInit { export class RecipeDetailsComponent implements OnInit {
title: string = 'Recipe Detail'; title: string = "Recipe Detail";
recipeDetail$!: Observable<RecipeDetail>; recipeDetail$!: Observable<RecipeDetail>;
isLoaded: boolean = false; isLoaded: boolean = false;
isMatLoaded: boolean = false; isMatLoaded: boolean = false;
actionRecord: ActionRecord<RecipeDetail | RecipeDetailMat> = actionRecord: ActionRecord<RecipeDetail | RecipeDetailMat> =
new ActionRecord(); new ActionRecord();
recipeOriginalDetail!: typeof this.recipeDetailForm.value; recipeOriginalDetail!: typeof this.recipeDetailForm.value;
commit_msg: string = ''; commit_msg: string = "";
// //
department: string = this._route.parent!.snapshot.params['department']; department: string = this._route.parent!.snapshot.params["department"];
constructor( constructor(
private _formBuilder: FormBuilder, private _formBuilder: FormBuilder,
private _route: ActivatedRoute, private _route: ActivatedRoute,
private _router: Router, private _router: Router,
private _recipeService: RecipeService, private _recipeService: RecipeService,
private _toppingService: ToppingService, private _toppingService: ToppingService,
private _userService: UserService private _userService: UserService,
) {} ) {}
productCode!: any; productCode!: any;
changedProductCode: string | undefined = undefined; changedProductCode: string | undefined = undefined;
recipeDetailForm = this._formBuilder.group({ recipeDetailForm = this._formBuilder.group({
productCode: '', productCode: "",
name: '', name: "",
otherName: '', otherName: "",
description: '', description: "",
otherDescription: '', otherDescription: "",
lastModified: Date(), lastModified: Date(),
price: 0, price: 0,
isUse: false, isUse: false,
isShow: false, isShow: false,
disable: false, disable: false,
}); });
repl = []; repl = [];
tpl = []; tpl = [];
toppingSet: ToppingSet[] | null = null; toppingSet: ToppingSet[] | null = null;
submenus: Recipe01[] | null = null; submenus: Recipe01[] | null = null;
rawRecipe: {} | undefined | null = undefined; rawRecipe: {} | undefined | null = undefined;
async ngOnInit() { async ngOnInit() {
this.productCode = this._route.snapshot.params['productCode']; this.productCode = this._route.snapshot.params["productCode"];
this.recipeDetail$ = ( this.recipeDetail$ = (
await this._recipeService.getRecipeDetail(this.productCode) await this._recipeService.getRecipeDetail(this.productCode)
).pipe(first()); ).pipe(first());
this.recipeDetail$.subscribe((detail) => { this.recipeDetail$.subscribe((detail) => {
console.log('Recipe Detail', detail); console.log("Recipe Detail", detail);
// transform lastChange aka lastUpdated to type `Date` // transform lastChange aka lastUpdated to type `Date`
if(detail.lastUpdated){ if (detail.lastUpdated) {
console.log("Date ", detail.lastUpdated, typeof detail.lastUpdated) console.log("Date ", detail.lastUpdated, typeof detail.lastUpdated);
} }
this.recipeDetailForm.patchValue(detail); this.recipeDetailForm.patchValue(detail);
console.log("from recipeDetailForm", this.recipeDetailForm); console.log("from recipeDetailForm", this.recipeDetailForm);
this.recipeDetailForm.get('lastModified')?.setValue(detail.lastUpdated.toString()); this.recipeDetailForm
.get("lastModified")
this.isLoaded = true; ?.setValue(detail.lastUpdated.toString());
this.recipeOriginalDetail = { ...this.recipeDetailForm.getRawValue() };
}); this.isLoaded = true;
this.recipeOriginalDetail = { ...this.recipeDetailForm.getRawValue() };
this._recipeService });
.getSubMenus(
await this._recipeService.getCurrentCountry(), this._recipeService
this._recipeService.getCurrentFile(), .getSubMenus(
this.productCode await this._recipeService.getCurrentCountry(),
) this._recipeService.getCurrentFile(),
.subscribe((data) => { this.productCode,
console.log('Submenus', data); )
this.submenus = data; .subscribe((data) => {
}); console.log("Submenus", data);
this.submenus = data;
this.recipeDetailForm.valueChanges.subscribe(this.onRecipeDetailFormChange); });
( this.recipeDetailForm.valueChanges.subscribe(this.onRecipeDetailFormChange);
await this._toppingService.getToppingsOfRecipe(
this.department, (
this._recipeService.getCurrentFile(), await this._toppingService.getToppingsOfRecipe(
this.productCode this.department,
) this._recipeService.getCurrentFile(),
).subscribe((data) => { this.productCode,
this.toppingSet = data; )
// console.log('Toppings', data); ).subscribe((data) => {
}); this.toppingSet = data;
// console.log('Toppings', data);
// get full raw value of this recipe });
(
await this._recipeService.getRawRecipeOfProductCode( // get full raw value of this recipe
this.department, (
this._recipeService.getCurrentFile(), await this._recipeService.getRawRecipeOfProductCode(
this.productCode this.department,
) this._recipeService.getCurrentFile(),
).subscribe((data) => { this.productCode,
console.log('Raw Recipe', data); )
this.rawRecipe = data; ).subscribe((data) => {
}); console.log("Raw Recipe", data);
this.rawRecipe = data;
// snap recipe detail form value });
this.actionRecord.registerOnAddAction((currAction, allAction) => { // snap recipe detail form value
if (currAction.type === 'recipeListData') {
switch (currAction.action) { this.actionRecord.registerOnAddAction((currAction, allAction) => {
case 'add': if (currAction.type === "recipeListData") {
break; switch (currAction.action) {
case 'delete': case "add":
break; break;
} case "delete":
} break;
console.log('Action Record', allAction); }
}); }
} console.log("Action Record", allAction);
});
showConfirmSaveModal: EventEmitter<boolean> = new EventEmitter<boolean>(); }
showConfirmCloseModal: EventEmitter<boolean> = new EventEmitter<boolean>();
showConfirmSaveModal: EventEmitter<boolean> = new EventEmitter<boolean>();
confirmSave = { showConfirmCloseModal: EventEmitter<boolean> = new EventEmitter<boolean>();
title: 'The changes detected!',
message: 'Do you want to save changes?', confirmSave = {
confirmCallBack: async () => { title: "The changes detected!",
console.log('confirm save'); message: "Do you want to save changes?",
confirmCallBack: async () => {
// get username console.log("confirm save");
let username: string = '';
// get username
username = this._userService.getCurrentUser()!.name; let username: string = "";
// diff with rawValue, then send username = this._userService.getCurrentUser()!.name;
let to_send = { // diff with rawValue, then send
edit_by: username,
commit_msg: this.commit_msg, let to_send = {
productCode: edit_by: username,
this.changedProductCode == undefined commit_msg: this.commit_msg,
? this.productCode productCode:
: this.changedProductCode, this.changedProductCode == undefined
name: ? this.productCode
this.recipeDetailForm.getRawValue().name != : this.changedProductCode,
this.recipeOriginalDetail.name name:
? this.recipeDetailForm.getRawValue().name this.recipeDetailForm.getRawValue().name !=
: this.recipeOriginalDetail.name, this.recipeOriginalDetail.name
otherName: ? this.recipeDetailForm.getRawValue().name
this.recipeDetailForm.getRawValue().otherName != : this.recipeOriginalDetail.name,
this.recipeOriginalDetail.otherName otherName:
? this.recipeDetailForm.getRawValue().otherName this.recipeDetailForm.getRawValue().otherName !=
: this.recipeOriginalDetail.otherName, this.recipeOriginalDetail.otherName
description: ? this.recipeDetailForm.getRawValue().otherName
this.recipeDetailForm.getRawValue().description != : this.recipeOriginalDetail.otherName,
this.recipeOriginalDetail.description description:
? this.recipeDetailForm.getRawValue().description this.recipeDetailForm.getRawValue().description !=
: this.recipeOriginalDetail.description, this.recipeOriginalDetail.description
otherDescription: ? this.recipeDetailForm.getRawValue().description
this.recipeDetailForm.getRawValue().otherDescription != : this.recipeOriginalDetail.description,
this.recipeOriginalDetail.otherDescription otherDescription:
? this.recipeDetailForm.getRawValue().otherDescription this.recipeDetailForm.getRawValue().otherDescription !=
: this.recipeOriginalDetail.otherDescription, this.recipeOriginalDetail.otherDescription
LastChange: new Date(), ? this.recipeDetailForm.getRawValue().otherDescription
price: : this.recipeOriginalDetail.otherDescription,
this.recipeDetailForm.getRawValue().price != LastChange: new Date(),
this.recipeOriginalDetail.price price:
? this.recipeDetailForm.getRawValue().price this.recipeDetailForm.getRawValue().price !=
: this.recipeOriginalDetail.price, this.recipeOriginalDetail.price
isUse: (this.rawRecipe as any).isUse, ? this.recipeDetailForm.getRawValue().price
isShow: (this.rawRecipe as any).isShow, : this.recipeOriginalDetail.price,
disable: (this.rawRecipe as any).disable, isUse: (this.rawRecipe as any).isUse,
recipes: [...(this.repl.length <= 0 ? [] : this.repl)], isShow: (this.rawRecipe as any).isShow,
SubMenu: [...(this.rawRecipe! as any).SubMenu!], disable: (this.rawRecipe as any).disable,
ToppingSet: [...(this.rawRecipe as any).ToppingSet], recipes: [...(this.repl.length <= 0 ? [] : this.repl)],
}; SubMenu: [...(this.rawRecipe! as any).SubMenu!],
console.log('pre to_send', to_send); ToppingSet: [...(this.rawRecipe as any).ToppingSet],
};
this.concatNoEditKeyToMap(this.rawRecipe, to_send); console.log("pre to_send", to_send);
console.log('to_send', to_send); this.concatNoEditKeyToMap(this.rawRecipe, to_send);
this._recipeService.editChanges(
await this._recipeService.getCurrentCountry(this.department), console.log("to_send", to_send);
this._recipeService.getCurrentFile(), this._recipeService.editChanges(
{ await this._recipeService.getCurrentCountry(this.department),
...to_send, this._recipeService.getCurrentFile(),
} {
); ...to_send,
console.log('Sending changes'); },
void this._router );
.navigate(['/' + this.department + '/recipes']) console.log("Sending changes");
.then(() => { void this._router
window.location.reload(); .navigate(["/" + this.department + "/recipes"])
}); .then(() => {
}, window.location.reload();
}; });
},
onKeyUpCommitMsg(e: any) { };
this.commit_msg = e.target.value;
} onKeyUpCommitMsg(e: any) {
this.commit_msg = e.target.value;
confirmClose = { }
title: 'The changes will be lost!',
message: 'Do you want to close without saving?', confirmClose = {
confirmCallBack: () => { title: "The changes will be lost!",
console.log('confirm close'); message: "Do you want to close without saving?",
this._router.navigate(['/' + this.department + '/recipes']); confirmCallBack: () => {
}, console.log("confirm close");
}; this._router.navigate(["/" + this.department + "/recipes"]);
},
onPressConfirmSave() { };
if (this.isValueChanged) {
this.showConfirmSaveModal.emit(true); onPressConfirmSave() {
} else { if (this.isValueChanged) {
this._router.navigate(['/' + this.department + '/recipes']); this.showConfirmSaveModal.emit(true);
} } else {
} this._router.navigate(["/" + this.department + "/recipes"]);
}
onPressConfirmClose() { }
if (this.isValueChanged) {
this.showConfirmCloseModal.emit(true); onPressConfirmClose() {
} else { if (this.isValueChanged) {
this._router.navigate(['/' + this.department + '/recipes']); this.showConfirmCloseModal.emit(true);
} } else {
} this._router.navigate(["/" + this.department + "/recipes"]);
}
isValueChanged: boolean = false; }
onRecipeDetailFormChange(recipeDetail: typeof this.recipeDetailForm.value) { isValueChanged: boolean = false;
// console.log('Recipe Detail Form Changed', recipeDetail);
} onRecipeDetailFormChange(recipeDetail: typeof this.recipeDetailForm.value) {
// console.log('Recipe Detail Form Changed', recipeDetail);
onRecipeListFormChange(repl: unknown[]) { }
console.log('Recipe List Form Changed', repl);
this.tpl = repl[0] as never[]; onRecipeListFormChange(repl: unknown[]) {
this.repl = repl[1] as never[]; console.log("Recipe List Form Changed", repl);
this.tpl = repl[0] as never[];
console.log('Recipe List Form Changed', this.repl, this.tpl); this.repl = repl[1] as never[];
for (let ti = 0; ti < this.tpl.length; ti++) {
// check at the same index console.log("Recipe List Form Changed", this.repl, this.tpl);
if (!isEqual(this.tpl[ti][0], (this.rawRecipe as any).ToppingSet[ti])) { for (let ti = 0; ti < this.tpl.length; ti++) {
console.log( // check at the same index
'topping list changed', if (!isEqual(this.tpl[ti][0], (this.rawRecipe as any).ToppingSet[ti])) {
ti, console.log(
this.tpl[ti][0], "topping list changed",
(this.rawRecipe as any).ToppingSet[ti] ti,
); this.tpl[ti][0],
// update raw recipe (this.rawRecipe as any).ToppingSet[ti],
(this.rawRecipe as any).ToppingSet[ti] = this.tpl[ti][0]; );
console.log( // update raw recipe
'after update topping', (this.rawRecipe as any).ToppingSet[ti] = this.tpl[ti][0];
(this.rawRecipe as any).ToppingSet[ti] console.log(
); "after update topping",
} (this.rawRecipe as any).ToppingSet[ti],
} );
}
// console.log('Recipe List Form Changed', this.repl, this.tpl); }
this.isValueChanged ||= repl != undefined;
} // console.log('Recipe List Form Changed', this.repl, this.tpl);
this.isValueChanged ||= repl != undefined;
onToppingListChange(tpl: unknown[]) { }
// console.log('Topping List Form Changed', tpl);
this.tpl = tpl as never[]; onToppingListChange(tpl: unknown[]) {
this.isValueChanged ||= tpl != undefined; // console.log('Topping List Form Changed', tpl);
} this.tpl = tpl as never[];
this.isValueChanged ||= tpl != undefined;
isEditable() { }
return this._userService
.getCurrentUser()! isEditable() {
.permissions.includes(UserPermissions.EDITOR); return this._userService
} .getCurrentUser()!
.permissions.includes(UserPermissions.EDITOR);
onProductCodeChange(event: any) { }
if (event.target.value != '') {
this.changedProductCode = event.target.value; onProductCodeChange(event: any) {
} if (event.target.value != "") {
} this.changedProductCode = event.target.value;
}
// Submenus }
selectedSubProductCode: string | undefined = undefined;
hasSubmenu = () => this.submenus != null && this.submenus!.length > 0; // Submenus
listSubMenuProductcodes = () => selectedSubProductCode: string | undefined = undefined;
this.submenus!.map((recipe) => recipe.productCode); hasSubmenu = () => this.submenus != null && this.submenus!.length > 0;
listSubMenuProductcodes = () =>
selectSubmenu(productCode: string) { this.submenus!.map((recipe) => recipe.productCode);
void this._router.navigate([
'/' + this.department + '/recipes/' + productCode, selectSubmenu(productCode: string) {
]); void this._router.navigate([
} "/" + this.department + "/recipes/" + productCode,
]);
// concat remaining unused keys }
concatNoEditKeyToMap(source: any, target: any) {
for (const key of Object.keys(source)) { // concat remaining unused keys
if (!Object.keys(target).includes(key)) { concatNoEditKeyToMap(source: any, target: any) {
target[key] = source[key]; for (const key of Object.keys(source)) {
} if (!Object.keys(target).includes(key)) {
} target[key] = source[key];
} }
}
recipePrice = () => }
this.rawRecipe != undefined &&
this.rawRecipe != null && recipePrice = () =>
Object.keys(this.rawRecipe as any).includes('cashPrice') this.rawRecipe != undefined &&
? (this.rawRecipe as any).cashPrice this.rawRecipe != null &&
: 0; Object.keys(this.rawRecipe as any).includes("cashPrice")
? (this.rawRecipe as any).cashPrice
// image path : 0;
imagePath = (productCode: string) => {
const filename = this._recipeService.getCurrentFile(); // image path
imagePath = (productCode: string) => {
return environment.api + const filename = this._recipeService.getCurrentFile();
'/recipes/' +
this.department + return (
'/' + environment.api +
filename + "/recipes/" +
'/' + this.department +
productCode + "/" +
'/image'; filename +
}; "/" +
} productCode +
"/image"
);
};
}

View file

@ -189,7 +189,7 @@ var (
func NewData(taoLogger *logger.TaoLogger, redisClient *RedisCli) *Data { func NewData(taoLogger *logger.TaoLogger, redisClient *RedisCli) *Data {
allRecipeFiles := helpers.ScanRecipeFiles(helpers.LoadCountrySettings()) allRecipeFiles := helpers.ScanRecipeFiles(helpers.LoadCountrySettings())
fmt.Println(allRecipeFiles) // fmt.Println(allRecipeFiles)
defaultFile := "coffeethai02_600.json" defaultFile := "coffeethai02_600.json"

View file

@ -801,49 +801,70 @@ func (rr *RecipeRouter) getImageOfProductCode(w http.ResponseWriter, r *http.Req
// img_dir := "taobin_project/image/page_drink_picture2_n/" // img_dir := "taobin_project/image/page_drink_picture2_n/"
// new img dir // new img dir
img_dir := "cofffeemachineConfig/" + countryID + "/.img/" // img_dir := "cofffeemachineConfig/" + countryID + "/.img/"
fullPath := img_dir + uriName // fullPath := img_dir + uriName
rr.taoLogger.Log.Debug("RecipeRouter.getImageOfProductCode", zap.Any("fullPath", fullPath)) // rr.taoLogger.Log.Debug("RecipeRouter.getImageOfProductCode", zap.Any("fullPath", fullPath))
// check if image file exists // check if image file exists
if _, err := os.Stat(fullPath); os.IsNotExist(err) { // if _, err := os.Stat(fullPath); os.IsNotExist(err) {
http.Error(w, "Image not found", http.StatusNotFound) // http.Error(w, "Image not found", http.StatusNotFound)
return // return
} // }
// TODO: get from cache // TODO: get from cache
var imgResult image.Image var imgResult image.Image
// try cache // try cache
img, err := rr.cache_db.GetCacheImage(fullPath) // img, err := rr.cache_db.GetCacheImage(fullPath)
// if err != nil {
// // read image
// imgFile, err := os.Open(fullPath)
// if err != nil {
// http.Error(w, err.Error(), http.StatusNotFound)
// return
// }
// defer imgFile.Close()
// thisImage, err := png.Decode(imgFile)
// if err != nil {
// http.Error(w, err.Error(), http.StatusNotFound)
// return
// }
// imgResult = thisImage
// // set cache
// err = rr.cache_db.SetImageToCache(fullPath, thisImage)
// if err != nil {
// rr.taoLogger.Log.Debug("CacheImage.SetError", zap.Any("error", err))
// }
// } else {
// imgResult = img
// rr.taoLogger.Log.Debug("CacheImage.OK", zap.Any("status", imgResult))
// }
// New: try load from another server
//
cli := http.Client{}
resp, err := cli.Get("http://localhost:36527/image/" + uriName)
if err != nil { if err != nil {
// read image rr.taoLogger.Log.Debug("ImgGetFromFastErr", zap.Any("Error", err.Error()))
imgFile, err := os.Open(fullPath) http.Error(w, err.Error(), http.StatusNotFound)
if err != nil {
http.Error(w, err.Error(), http.StatusNotFound)
return
}
defer imgFile.Close()
thisImage, err := png.Decode(imgFile)
if err != nil {
http.Error(w, err.Error(), http.StatusNotFound)
return
}
imgResult = thisImage
// set cache
err = rr.cache_db.SetImageToCache(fullPath, thisImage)
if err != nil {
rr.taoLogger.Log.Debug("CacheImage.SetError", zap.Any("error", err))
}
} else {
imgResult = img
rr.taoLogger.Log.Debug("CacheImage.OK", zap.Any("status", imgResult))
} }
rr.taoLogger.Log.Debug("GetImageFromFast", zap.Int("Code", resp.StatusCode));
img_data, err := png.Decode(resp.Body)
if err != nil {
rr.taoLogger.Log.Error("ReadFromFastRespErr", zap.Any("Error", err.Error()))
}
resp.Body.Close()
imgResult = img_data
// write image // write image
png.Encode(w, imgResult) png.Encode(w, imgResult)
} }

View file

@ -3,9 +3,7 @@ package logger
import ( import (
"os" "os"
"recipe-manager/config" "recipe-manager/config"
"time"
"github.com/natefinch/lumberjack"
"go.uber.org/zap" "go.uber.org/zap"
"go.uber.org/zap/zapcore" "go.uber.org/zap/zapcore"
) )
@ -22,36 +20,32 @@ func (tl *TaoLogger) initConfig() *zap.Logger {
return lvl >= zap.InfoLevel || tl.enableDebug return lvl >= zap.InfoLevel || tl.enableDebug
}) })
logCore := zapcore.NewTee( productionConfig := zap.NewProductionEncoderConfig()
zapcore.NewCore(zapcore.NewJSONEncoder(zapcore.EncoderConfig{ productionConfig.EncodeTime = zapcore.ISO8601TimeEncoder
TimeKey: "timestamp",
LevelKey: "level", // fileEncoder := zapcore.NewJSONEncoder(productionConfig)
NameKey: "logger", consoleEncoder := zapcore.NewConsoleEncoder(productionConfig)
CallerKey: "caller",
MessageKey: "message", // logCore := zapcore.NewTee(
StacktraceKey: "error", // zapcore.NewCore(zapcore.NewJSONEncoder(productionConfig),
EncodeLevel: zapcore.LowercaseLevelEncoder, // zapcore.NewCore(zapcore.NewConsoleEncoder(zapcore.EncoderConfig{
EncodeTime: zapcore.TimeEncoderOfLayout(time.DateTime), // TimeKey: "timestamp",
}), zapcore.AddSync(&lumberjack.Logger{ // LevelKey: "level",
Filename: "services/logger/serverlog.log", // NameKey: "logger",
MaxSize: 5, // megabytes // CallerKey: "caller",
MaxAge: 28, //days // MessageKey: "message",
LocalTime: true, // StacktraceKey: "error",
Compress: true, // EncodeLevel: zapcore.CapitalColorLevelEncoder,
}), enableDebugMode), // EncodeTime: zapcore.ISO8601TimeEncoder,
zapcore.NewCore(zapcore.NewConsoleEncoder(zapcore.EncoderConfig{ // }), zapcore.AddSync(os.Stdout), enableDebugMode),
TimeKey: "timestamp", // )
LevelKey: "level",
NameKey: "logger", core := zapcore.NewTee(
CallerKey: "caller", // zapcore.NewCore(fileEncoder, zapcore.AddSync(), enableDebugMode),
MessageKey: "message", zapcore.NewCore(consoleEncoder, zapcore.AddSync(os.Stdout), enableDebugMode),
StacktraceKey: "error",
EncodeLevel: zapcore.CapitalColorLevelEncoder,
EncodeTime: zapcore.ISO8601TimeEncoder,
}), zapcore.AddSync(os.Stdout), enableDebugMode),
) )
return zap.New(logCore) return zap.New(core)
} }
func NewTaoLogger(cfg *config.ServerConfig) *TaoLogger { func NewTaoLogger(cfg *config.ServerConfig) *TaoLogger {