CREATE TABLE "verification" (
"id" text PRIMARY KEY NOT NULL,
"user_id" text NOT NULL,
"identifier" text NOT NULL,
"value" boolean DEFAULT false,
"expires_at" timestamp DEFAULT now() + INTERVAL '+ 7 days' NOT NULL,
"created_at" timestamp DEFAULT now() NOT NULL,
"updated_at" timestamp DEFAULT now() NOT NULL
);
import { createId } from "@paralleldrive/cuid2";
import { sql } from "drizzle-orm";
import { boolean, pgTable, text, timestamp } from "drizzle-orm/pg-core";
import { user } from "./user";
export const verification = pgTable("verification", {
id: text()
.$defaultFn(() => createId())
.primaryKey(),
userId: text('user_id').notNull().references(() => user.id, { onDelete: 'cascade' }),
identifier: text('identifier').notNull(),
value: boolean('value').default(false),
expiresAt: timestamp('expires_at')
.default(
sql`now() + INTERVAL '+ 7 days'`
)
.notNull(),
createdAt: timestamp('created_at').defaultNow().notNull(),
updatedAt: timestamp('updated_at').defaultNow().notNull()
});
//...
export const verificationDto = {
//...
createVerification: async (userId: string) => {
const newVerification = await db
.insert(table.verification)
.values({
userId,
identifier: createId()
})
.returning()
return newVerification[0]
}
//...
}
//...
export const auth = new Elysia({ name: 'auth' })
//...
.post("/signup", async ({ body, jwtAuth, error }) => {
//...
const newUser = await userDTO.createUser({
role: body.role,
email: body.email,
password: await Bun.password.hash(body.password)
});
const token = await jwtAuth.sign({ id: newUser.id });
const { password, ...user } = newUser
await verificationDto.createVerification(user.id);
//...
return {
token,
user,
//...
}
}, { body: registerBody })
//...
.col {
overflow: hidden; чтоб урезать линии границ блоков с закруглениями
// пунктиры 1го и последнего одинаковы для десктопа и мобилки
&:first-of-type {
&:after {}
}
&:last-of-type {
&:before {}
}
@media(max-width: мобилка) {
&:nth-of-type( последовательности подбираем ) {
&:before, &:after {}
}
}
@media(min-width: десктоп) {
&:nth-of-type( последовательности подбираем ) {
&:before, &:after {}
}
}
}
const app = new Vue({
router,
store,
i18n,
render: h => h(App)
}).$mount('#app')
// вместо vue use ajax, где ajax - объект с install, в котором объявляется новое св-во / прототип
app.$ajax = new Ajax()
store.$app = app
class AlertCaller {
constructor(options) {
this.state = {
children: options.textError
}
this._render();
}
_render() {
ReactDOM.render(
<Alert {...this.state} />,
document.getElementById("alerts")
);
}
destroy() {
ReactDOM.unmountComponentAtNode(this._container);
}
}
<svg><use/ xlink:href='path/to/sprite.svg#icon-name'><svg>
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"><symbol fill="none" viewBox="0 0 18 18" id="archive" xmlns="http://www.w3.org/2000/svg"><path d="M9 0v10.42m0 0L6.143 7.676M9 10.42l2.857-2.742M6 5H4.5L1 12m0 0v5h16v-5M1 12h4a1 1 0 011 1 1 1 0 001 1h4a1 1 0 001-1 1 1 0 011-1h4m0 0l-3.5-7H12"/></symbol>
...
const gulp = require('gulp'),
cheerio = require('gulp-cheerio'),
svgmin = require('gulp-svgmin'),
replace = require('gulp-replace'),
util = require('gulp-util'),
notify = require('gulp-notify'),
svgSprite = require('gulp-svg-sprite'),
path = require('path');
let dest = path.join('src', 'assets', 'icons');
let svgConfig = {
mode: {
symbol:{
sprite: "../sprite.svg"
}
}
};
gulp.task('sprite', function() {
gulp.src("**/*.svg", {cwd: path.join(dest, 'exported')})
.pipe(svgSprite(svgConfig))
.pipe(cheerio({
run: function ($) {
$('[stroke]').removeAttr('stroke');
$('[viewBox]').attr('viewBox', '0 0 18 18');
return
},
parserOptions: {xmlMode: true}
}))
.pipe(replace('>', '>'))
.on('error', function(err) {
util.log(err);
})
.on('error', notify.onError('sprite compiling error!'))
.pipe(gulp.dest(dest))
});
.block {
$parent: &;
&--active {
#{$parent}__component {display: block}
}
&__component {
display: none;
}
}