feat: upd deps & image attaching to course

This commit is contained in:
Sergey Yarkov 2021-10-24 17:57:56 +03:00
parent 98a67f1744
commit 987fafd440
14 changed files with 367 additions and 343 deletions

View File

@ -23,7 +23,11 @@
"Database": "database", "Database": "database",
"Contracts": "contracts" "Contracts": "contracts"
}, },
"preloads": ["./routes/index", "./start/kernel", "./start/event"], "preloads": [
"./routes/index",
"./start/kernel",
"./start/event"
],
"providers": [ "providers": [
"./providers/AppProvider", "./providers/AppProvider",
"./providers/CloudinaryProvider", "./providers/CloudinaryProvider",
@ -32,9 +36,12 @@
"@adonisjs/auth", "@adonisjs/auth",
"@adonisjs/redis", "@adonisjs/redis",
"@adonisjs/mail", "@adonisjs/mail",
"@adonisjs/view" "@adonisjs/view",
"@adonisjs/attachment-lite"
],
"aceProviders": [
"@adonisjs/repl"
], ],
"aceProviders": ["@adonisjs/repl"],
"metaFiles": [ "metaFiles": [
{ {
"pattern": "resources/views/**/*.edge", "pattern": "resources/views/**/*.edge",

1
.gitignore vendored
View File

@ -5,3 +5,4 @@ coverage
.DS_STORE .DS_STORE
.env .env
tmp tmp
uploads

View File

@ -1,39 +0,0 @@
import { HttpContextContract } from '@ioc:Adonis/Core/HttpContext';
import { Exception, inject, Ioc } from '@adonisjs/core/build/standalone';
/**
* Services
*/
import AssetsService from 'App/Services/AssetsService';
import BaseController from '../BaseController';
@inject()
export default class AssetsController extends BaseController {
private assetsService: AssetsService;
constructor(assetsService: AssetsService) {
super();
this.assetsService = assetsService;
}
/**
* Send background image of course
* GET /assets/images/courses/:fileName
*/
public async serveCourseImage(ctx: HttpContextContract) {
const result = await this.assetsService.getCourseImagePath(ctx.params.fileName);
if (typeof result !== 'string') {
if (!result.success && result.error) {
throw new Exception(result.message, result.status, result.error.code);
}
return this.sendResponse(ctx, result.data, result.message, result.status);
}
return this.sendFile(ctx, result);
}
}
new Ioc().make(AssetsController);

View File

@ -13,18 +13,18 @@ import {
ManyToMany, ManyToMany,
manyToMany, manyToMany,
} from '@ioc:Adonis/Lucid/Orm'; } from '@ioc:Adonis/Lucid/Orm';
import { attachment, AttachmentContract } from '@ioc:Adonis/Addons/AttachmentLite';
import Category from 'App/Models/Category'; import Category from 'App/Models/Category';
import Lesson from 'App/Models/Lesson'; import Lesson from 'App/Models/Lesson';
import User from 'App/Models/User'; import User from 'App/Models/User';
import CourseStatusEnum from 'App/Datatypes/Enums/CourseStatusEnum'; import CourseStatusEnum from 'App/Datatypes/Enums/CourseStatusEnum';
// import Image from './Image';
export default class Course extends BaseModel { export default class Course extends BaseModel {
@column({ isPrimary: true }) @column({ isPrimary: true })
public id: string; public id: string;
@column() @attachment({ folder: 'images/courses', preComputeUrl: true })
public bg_image_path: string; public image: AttachmentContract | null;
@column() @column()
public title: string; public title: string;
@ -46,11 +46,6 @@ export default class Course extends BaseModel {
}) })
public category: BelongsTo<typeof Category>; public category: BelongsTo<typeof Category>;
// @belongsTo(() => Image, {
// foreignKey: 'bg_image_id',
// })
// public image: BelongsTo<typeof Image>;
@belongsTo(() => User, { @belongsTo(() => User, {
foreignKey: 'teacher_id', foreignKey: 'teacher_id',
}) })

View File

@ -1,8 +1,10 @@
/* eslint-disable @typescript-eslint/naming-convention */ /* eslint-disable @typescript-eslint/naming-convention */
import Database from '@ioc:Adonis/Lucid/Database';
import { Attachment } from '@ioc:Adonis/Addons/AttachmentLite';
/** /**
* Datatypes * Datatypes
*/ */
import Database from '@ioc:Adonis/Lucid/Database';
import CourseStatusEnum from 'App/Datatypes/Enums/CourseStatusEnum'; import CourseStatusEnum from 'App/Datatypes/Enums/CourseStatusEnum';
/** /**
@ -183,14 +185,19 @@ export default class CourseRepository {
/** /**
* Create new course * Create new course
*/ */
const course = await this.Course.create({ const course = new this.Course();
bg_image_path: data.image?.filePath,
title: data.title, course.title = data.title;
description: data.description, course.description = data.description;
status: data.status, course.status = data.status;
teacher_id: data.teacher_id, course.teacher_id = data.teacher_id;
category_id: data.category_id, course.category_id = data.category_id;
});
if (data.image) {
course.image = Attachment.fromFile(data.image);
}
await course.save();
return course; return course;
} }

View File

@ -1,47 +0,0 @@
import { inject, Ioc } from '@adonisjs/core/build/standalone';
import Application from '@ioc:Adonis/Core/Application';
/**
* Datatypes
*/
import IResponse from 'App/Datatypes/Interfaces/IResponse';
import HttpStatusEnum from 'App/Datatypes/Enums/HttpStatusEnum';
/**
* Reposirories
*/
import ImageRepository from 'App/Repositories/ImageRepository';
@inject()
export default class AssetsService {
private imageRepository: ImageRepository;
constructor(imageRepository: ImageRepository) {
this.imageRepository = imageRepository;
}
/**
*
* @param name Image name
* @returns Pathname
*/
public async getCourseImagePath(name: string): Promise<IResponse | string> {
const image = await this.imageRepository.getByFileName(name);
if (!image) {
return {
success: false,
status: HttpStatusEnum.NOT_FOUND,
message: 'Image not found.',
data: {},
error: {
code: 'E_NOT_FOUND',
},
};
}
return Application.tmpPath(`uploads/images/courses/${image.name}`);
}
}
new Ioc().make(AssetsService);

View File

@ -42,7 +42,7 @@ const driveConfig: DriveConfig = {
*/ */
local: { local: {
driver: 'local', driver: 'local',
visibility: 'public', visibility: 'private',
/* /*
|-------------------------------------------------------------------------- |--------------------------------------------------------------------------
@ -53,7 +53,7 @@ const driveConfig: DriveConfig = {
| files. | files.
| |
*/ */
root: Application.tmpPath('uploads'), root: Application.makePath('uploads'),
/* /*
|-------------------------------------------------------------------------- |--------------------------------------------------------------------------

View File

@ -16,33 +16,27 @@ import LessonContent from 'App/Models/LessonContent';
import Role from 'App/Models/Role'; import Role from 'App/Models/Role';
import User from 'App/Models/User'; import User from 'App/Models/User';
const makeFakeUser = (faker: Faker.FakerStatic) => {
return {
first_name: faker.name.firstName(),
last_name: faker.name.lastName(),
login: `${faker.lorem.word(12)}${faker.datatype.number(100)}`,
email: faker.internet.exampleEmail(),
password: '123456',
};
};
export const ContactFactory = Factory.define(Contact, ({ faker }) => { export const ContactFactory = Factory.define(Contact, ({ faker }) => {
return { return {
phone_number: faker.phone.phoneNumber(), phone_number: faker.phone.phoneNumber(),
}; };
}).build(); }).build();
export const UserFactory = Factory.define(User, ({ faker }) => { export const UserFactory = Factory.define(User, ({ faker }) => makeFakeUser(faker))
return {
first_name: faker.name.firstName(),
last_name: faker.name.lastName(),
login: `${faker.lorem.word(12)}${faker.datatype.number(100)}`,
email: faker.internet.exampleEmail(),
password: '123456',
};
})
.relation('contacts', () => ContactFactory) .relation('contacts', () => ContactFactory)
.build(); .build();
export const TeacherFactory = Factory.define(User, ({ faker }) => { export const TeacherFactory = Factory.define(User, ({ faker }) => makeFakeUser(faker))
return {
first_name: faker.name.firstName(),
last_name: faker.name.lastName(),
login: `${faker.lorem.word(12)}${faker.datatype.number(100)}`,
email: faker.internet.exampleEmail(),
password: '123456',
};
})
.relation('contacts', () => ContactFactory) .relation('contacts', () => ContactFactory)
.after('create', async (_, user: User) => { .after('create', async (_, user: User) => {
/** /**

View File

@ -11,11 +11,11 @@ export default class Courses extends BaseSchema {
public async up() { public async up() {
this.schema.createTable(this.tableName, table => { this.schema.createTable(this.tableName, table => {
table.string('id', 21).primary(); table.string('id', 21).primary();
table.string('bg_image_path'); table.json('image');
table.string('title').notNullable(); table.string('title').notNullable();
table.string('description').notNullable(); table.string('description').notNullable();
table.string('teacher_id', 21).unsigned().references('users.id').onDelete('CASCADE'); table.string('teacher_id', 21).unsigned().references('users.id').notNullable().onDelete('CASCADE');
table.string('category_id', 21).unsigned().references('categories.id').onDelete('CASCADE'); table.string('category_id', 21).unsigned().references('categories.id').notNullable().onDelete('CASCADE');
table table
.enu('status', Object.values(CourseStatusEnum), { .enu('status', Object.values(CourseStatusEnum), {
useNative: true, useNative: true,

545
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -32,14 +32,15 @@
"youch-terminal": "^1.1.1" "youch-terminal": "^1.1.1"
}, },
"dependencies": { "dependencies": {
"@adonisjs/auth": "^8.0.9", "@adonisjs/attachment-lite": "^1.0.1",
"@adonisjs/core": "^5.3.2", "@adonisjs/auth": "^8.0.10",
"@adonisjs/drive": "^2.0.6", "@adonisjs/core": "^5.4.0",
"@adonisjs/lucid": "^16.0.2", "@adonisjs/drive": "^2.0.7",
"@adonisjs/lucid": "^16.2.1",
"@adonisjs/mail": "^7.2.4", "@adonisjs/mail": "^7.2.4",
"@adonisjs/redis": "^7.0.9", "@adonisjs/redis": "^7.0.9",
"@adonisjs/repl": "^3.1.6", "@adonisjs/repl": "^3.1.7",
"@adonisjs/view": "^6.1.0", "@adonisjs/view": "^6.1.1",
"cloudinary": "^1.26.3", "cloudinary": "^1.26.3",
"luxon": "^1.28.0", "luxon": "^1.28.0",
"nanoid": "^3.1.25", "nanoid": "^3.1.25",

View File

@ -1,10 +0,0 @@
import Route from '@ioc:Adonis/Core/Route';
Route.group(() => {
/**
* Serve background image for course
*/
Route.get('/images/courses/:fileName', 'Api/AssetsController.serveCourseImage').as('serve.course.image');
})
.prefix('assets')
.as('assets');

View File

@ -26,9 +26,4 @@ Route.group(() => {
* Api routes * Api routes
*/ */
require('./api'); require('./api');
/**
* Serve assets
*/
require('./assets');
}); });

View File

@ -33,7 +33,8 @@
"@adonisjs/auth", "@adonisjs/auth",
"@adonisjs/redis", "@adonisjs/redis",
"@adonisjs/mail", "@adonisjs/mail",
"@adonisjs/view" "@adonisjs/view",
"@adonisjs/attachment-lite"
] ]
} }
} }