diff --git a/internal/ent/role.go b/internal/ent/role.go new file mode 100644 index 0000000..5e5c87c --- /dev/null +++ b/internal/ent/role.go @@ -0,0 +1,140 @@ +// Code generated by ent, DO NOT EDIT. + +package ent + +import ( + "EnGin/internal/ent/role" + "fmt" + "strings" + + "entgo.io/ent" + "entgo.io/ent/dialect/sql" +) + +// Role is the model entity for the Role schema. +type Role struct { + config `json:"-"` + // ID of the ent. + ID int `json:"id,omitempty"` + // Code holds the value of the "code" field. + Code string `json:"code,omitempty"` + // Name holds the value of the "name" field. + Name string `json:"name,omitempty"` + // Edges holds the relations/edges for other nodes in the graph. + // The values are being populated by the RoleQuery when eager-loading is set. + Edges RoleEdges `json:"edges"` + selectValues sql.SelectValues +} + +// RoleEdges holds the relations/edges for other nodes in the graph. +type RoleEdges struct { + // Users holds the value of the users edge. + Users []*User `json:"users,omitempty"` + // loadedTypes holds the information for reporting if a + // type was loaded (or requested) in eager-loading or not. + loadedTypes [1]bool +} + +// UsersOrErr returns the Users value or an error if the edge +// was not loaded in eager-loading. +func (e RoleEdges) UsersOrErr() ([]*User, error) { + if e.loadedTypes[0] { + return e.Users, nil + } + return nil, &NotLoadedError{edge: "users"} +} + +// scanValues returns the types for scanning values from sql.Rows. +func (*Role) scanValues(columns []string) ([]any, error) { + values := make([]any, len(columns)) + for i := range columns { + switch columns[i] { + case role.FieldID: + values[i] = new(sql.NullInt64) + case role.FieldCode, role.FieldName: + values[i] = new(sql.NullString) + default: + values[i] = new(sql.UnknownType) + } + } + return values, nil +} + +// assignValues assigns the values that were returned from sql.Rows (after scanning) +// to the Role fields. +func (_m *Role) assignValues(columns []string, values []any) error { + if m, n := len(values), len(columns); m < n { + return fmt.Errorf("mismatch number of scan values: %d != %d", m, n) + } + for i := range columns { + switch columns[i] { + case role.FieldID: + value, ok := values[i].(*sql.NullInt64) + if !ok { + return fmt.Errorf("unexpected type %T for field id", value) + } + _m.ID = int(value.Int64) + case role.FieldCode: + if value, ok := values[i].(*sql.NullString); !ok { + return fmt.Errorf("unexpected type %T for field code", values[i]) + } else if value.Valid { + _m.Code = value.String + } + case role.FieldName: + if value, ok := values[i].(*sql.NullString); !ok { + return fmt.Errorf("unexpected type %T for field name", values[i]) + } else if value.Valid { + _m.Name = value.String + } + default: + _m.selectValues.Set(columns[i], values[i]) + } + } + return nil +} + +// Value returns the ent.Value that was dynamically selected and assigned to the Role. +// This includes values selected through modifiers, order, etc. +func (_m *Role) Value(name string) (ent.Value, error) { + return _m.selectValues.Get(name) +} + +// QueryUsers queries the "users" edge of the Role entity. +func (_m *Role) QueryUsers() *UserQuery { + return NewRoleClient(_m.config).QueryUsers(_m) +} + +// Update returns a builder for updating this Role. +// Note that you need to call Role.Unwrap() before calling this method if this Role +// was returned from a transaction, and the transaction was committed or rolled back. +func (_m *Role) Update() *RoleUpdateOne { + return NewRoleClient(_m.config).UpdateOne(_m) +} + +// Unwrap unwraps the Role entity that was returned from a transaction after it was closed, +// so that all future queries will be executed through the driver which created the transaction. +func (_m *Role) Unwrap() *Role { + _tx, ok := _m.config.driver.(*txDriver) + if !ok { + panic("ent: Role is not a transactional entity") + } + _m.config.driver = _tx.drv + return _m +} + +// String implements the fmt.Stringer. +func (_m *Role) String() string { + var builder strings.Builder + builder.WriteString("Role(") + builder.WriteString(fmt.Sprintf("id=%v, ", _m.ID)) + builder.WriteString("code=") + builder.WriteString(_m.Code) + builder.WriteString(", ") + builder.WriteString("name=") + builder.WriteString(_m.Name) + builder.WriteByte(')') + return builder.String() +} + +// Roles is a parsable slice of Role. +type Roles []*Role diff --git a/internal/ent/role/role.go b/internal/ent/role/role.go new file mode 100644 index 0000000..ae4a0a4 --- /dev/null +++ b/internal/ent/role/role.go @@ -0,0 +1,97 @@ +// Code generated by ent, DO NOT EDIT. + +package role + +import ( + "entgo.io/ent/dialect/sql" + "entgo.io/ent/dialect/sql/sqlgraph" +) + +const ( + // Label holds the string label denoting the role type in the database. + Label = "role" + // FieldID holds the string denoting the id field in the database. + FieldID = "id" + // FieldCode holds the string denoting the code field in the database. + FieldCode = "code" + // FieldName holds the string denoting the name field in the database. + FieldName = "name" + // EdgeUsers holds the string denoting the users edge name in mutations. + EdgeUsers = "users" + // Table holds the table name of the role in the database. + Table = "roles" + // UsersTable is the table that holds the users relation/edge. The primary key declared below. + UsersTable = "user_roles" + // UsersInverseTable is the table name for the User entity. + // It exists in this package in order to avoid circular dependency with the "user" package. + UsersInverseTable = "users" +) + +// Columns holds all SQL columns for role fields. +var Columns = []string{ + FieldID, + FieldCode, + FieldName, +} + +var ( + // UsersPrimaryKey and UsersColumn2 are the table columns denoting the + // primary key for the users relation (M2M). + UsersPrimaryKey = []string{"user_id", "role_id"} +) + +// ValidColumn reports if the column name is valid (part of the table columns). +func ValidColumn(column string) bool { + for i := range Columns { + if column == Columns[i] { + return true + } + } + return false +} + +var ( + // CodeValidator is a validator for the "code" field. It is called by the builders before save. + CodeValidator func(string) error + // NameValidator is a validator for the "name" field. It is called by the builders before save. + NameValidator func(string) error +) + +// OrderOption defines the ordering options for the Role queries. +type OrderOption func(*sql.Selector) + +// ByID orders the results by the id field. +func ByID(opts ...sql.OrderTermOption) OrderOption { + return sql.OrderByField(FieldID, opts...).ToFunc() +} + +// ByCode orders the results by the code field. +func ByCode(opts ...sql.OrderTermOption) OrderOption { + return sql.OrderByField(FieldCode, opts...).ToFunc() +} + +// ByName orders the results by the name field. +func ByName(opts ...sql.OrderTermOption) OrderOption { + return sql.OrderByField(FieldName, opts...).ToFunc() +} + +// ByUsersCount orders the results by users count. +func ByUsersCount(opts ...sql.OrderTermOption) OrderOption { + return func(s *sql.Selector) { + sqlgraph.OrderByNeighborsCount(s, newUsersStep(), opts...) + } +} + +// ByUsers orders the results by users terms. +func ByUsers(term sql.OrderTerm, terms ...sql.OrderTerm) OrderOption { + return func(s *sql.Selector) { + sqlgraph.OrderByNeighborTerms(s, newUsersStep(), append([]sql.OrderTerm{term}, terms...)...) + } +} +func newUsersStep() *sqlgraph.Step { + return sqlgraph.NewStep( + sqlgraph.From(Table, FieldID), + sqlgraph.To(UsersInverseTable, FieldID), + sqlgraph.Edge(sqlgraph.M2M, true, UsersTable, UsersPrimaryKey...), + ) +} diff --git a/internal/ent/role/where.go b/internal/ent/role/where.go new file mode 100644 index 0000000..e5f3342 --- /dev/null +++ b/internal/ent/role/where.go @@ -0,0 +1,233 @@ +// Code generated by ent, DO NOT EDIT. + +package role + +import ( + "EnGin/internal/ent/predicate" + + "entgo.io/ent/dialect/sql" + "entgo.io/ent/dialect/sql/sqlgraph" +) + +// ID filters vertices based on their ID field. +func ID(id int) predicate.Role { + return predicate.Role(sql.FieldEQ(FieldID, id)) +} + +// IDEQ applies the EQ predicate on the ID field. +func IDEQ(id int) predicate.Role { + return predicate.Role(sql.FieldEQ(FieldID, id)) +} + +// IDNEQ applies the NEQ predicate on the ID field. +func IDNEQ(id int) predicate.Role { + return predicate.Role(sql.FieldNEQ(FieldID, id)) +} + +// IDIn applies the In predicate on the ID field. +func IDIn(ids ...int) predicate.Role { + return predicate.Role(sql.FieldIn(FieldID, ids...)) +} + +// IDNotIn applies the NotIn predicate on the ID field. +func IDNotIn(ids ...int) predicate.Role { + return predicate.Role(sql.FieldNotIn(FieldID, ids...)) +} + +// IDGT applies the GT predicate on the ID field. +func IDGT(id int) predicate.Role { + return predicate.Role(sql.FieldGT(FieldID, id)) +} + +// IDGTE applies the GTE predicate on the ID field. +func IDGTE(id int) predicate.Role { + return predicate.Role(sql.FieldGTE(FieldID, id)) +} + +// IDLT applies the LT predicate on the ID field. +func IDLT(id int) predicate.Role { + return predicate.Role(sql.FieldLT(FieldID, id)) +} + +// IDLTE applies the LTE predicate on the ID field. +func IDLTE(id int) predicate.Role { + return predicate.Role(sql.FieldLTE(FieldID, id)) +} + +// Code applies equality check predicate on the "code" field. It's identical to CodeEQ. +func Code(v string) predicate.Role { + return predicate.Role(sql.FieldEQ(FieldCode, v)) +} + +// Name applies equality check predicate on the "name" field. It's identical to NameEQ. +func Name(v string) predicate.Role { + return predicate.Role(sql.FieldEQ(FieldName, v)) +} + +// CodeEQ applies the EQ predicate on the "code" field. +func CodeEQ(v string) predicate.Role { + return predicate.Role(sql.FieldEQ(FieldCode, v)) +} + +// CodeNEQ applies the NEQ predicate on the "code" field. +func CodeNEQ(v string) predicate.Role { + return predicate.Role(sql.FieldNEQ(FieldCode, v)) +} + +// CodeIn applies the In predicate on the "code" field. +func CodeIn(vs ...string) predicate.Role { + return predicate.Role(sql.FieldIn(FieldCode, vs...)) +} + +// CodeNotIn applies the NotIn predicate on the "code" field. +func CodeNotIn(vs ...string) predicate.Role { + return predicate.Role(sql.FieldNotIn(FieldCode, vs...)) +} + +// CodeGT applies the GT predicate on the "code" field. +func CodeGT(v string) predicate.Role { + return predicate.Role(sql.FieldGT(FieldCode, v)) +} + +// CodeGTE applies the GTE predicate on the "code" field. +func CodeGTE(v string) predicate.Role { + return predicate.Role(sql.FieldGTE(FieldCode, v)) +} + +// CodeLT applies the LT predicate on the "code" field. +func CodeLT(v string) predicate.Role { + return predicate.Role(sql.FieldLT(FieldCode, v)) +} + +// CodeLTE applies the LTE predicate on the "code" field. +func CodeLTE(v string) predicate.Role { + return predicate.Role(sql.FieldLTE(FieldCode, v)) +} + +// CodeContains applies the Contains predicate on the "code" field. +func CodeContains(v string) predicate.Role { + return predicate.Role(sql.FieldContains(FieldCode, v)) +} + +// CodeHasPrefix applies the HasPrefix predicate on the "code" field. +func CodeHasPrefix(v string) predicate.Role { + return predicate.Role(sql.FieldHasPrefix(FieldCode, v)) +} + +// CodeHasSuffix applies the HasSuffix predicate on the "code" field. +func CodeHasSuffix(v string) predicate.Role { + return predicate.Role(sql.FieldHasSuffix(FieldCode, v)) +} + +// CodeEqualFold applies the EqualFold predicate on the "code" field. +func CodeEqualFold(v string) predicate.Role { + return predicate.Role(sql.FieldEqualFold(FieldCode, v)) +} + +// CodeContainsFold applies the ContainsFold predicate on the "code" field. +func CodeContainsFold(v string) predicate.Role { + return predicate.Role(sql.FieldContainsFold(FieldCode, v)) +} + +// NameEQ applies the EQ predicate on the "name" field. +func NameEQ(v string) predicate.Role { + return predicate.Role(sql.FieldEQ(FieldName, v)) +} + +// NameNEQ applies the NEQ predicate on the "name" field. +func NameNEQ(v string) predicate.Role { + return predicate.Role(sql.FieldNEQ(FieldName, v)) +} + +// NameIn applies the In predicate on the "name" field. +func NameIn(vs ...string) predicate.Role { + return predicate.Role(sql.FieldIn(FieldName, vs...)) +} + +// NameNotIn applies the NotIn predicate on the "name" field. +func NameNotIn(vs ...string) predicate.Role { + return predicate.Role(sql.FieldNotIn(FieldName, vs...)) +} + +// NameGT applies the GT predicate on the "name" field. +func NameGT(v string) predicate.Role { + return predicate.Role(sql.FieldGT(FieldName, v)) +} + +// NameGTE applies the GTE predicate on the "name" field. +func NameGTE(v string) predicate.Role { + return predicate.Role(sql.FieldGTE(FieldName, v)) +} + +// NameLT applies the LT predicate on the "name" field. +func NameLT(v string) predicate.Role { + return predicate.Role(sql.FieldLT(FieldName, v)) +} + +// NameLTE applies the LTE predicate on the "name" field. +func NameLTE(v string) predicate.Role { + return predicate.Role(sql.FieldLTE(FieldName, v)) +} + +// NameContains applies the Contains predicate on the "name" field. +func NameContains(v string) predicate.Role { + return predicate.Role(sql.FieldContains(FieldName, v)) +} + +// NameHasPrefix applies the HasPrefix predicate on the "name" field. +func NameHasPrefix(v string) predicate.Role { + return predicate.Role(sql.FieldHasPrefix(FieldName, v)) +} + +// NameHasSuffix applies the HasSuffix predicate on the "name" field. +func NameHasSuffix(v string) predicate.Role { + return predicate.Role(sql.FieldHasSuffix(FieldName, v)) +} + +// NameEqualFold applies the EqualFold predicate on the "name" field. +func NameEqualFold(v string) predicate.Role { + return predicate.Role(sql.FieldEqualFold(FieldName, v)) +} + +// NameContainsFold applies the ContainsFold predicate on the "name" field. +func NameContainsFold(v string) predicate.Role { + return predicate.Role(sql.FieldContainsFold(FieldName, v)) +} + +// HasUsers applies the HasEdge predicate on the "users" edge. +func HasUsers() predicate.Role { + return predicate.Role(func(s *sql.Selector) { + step := sqlgraph.NewStep( + sqlgraph.From(Table, FieldID), + sqlgraph.Edge(sqlgraph.M2M, true, UsersTable, UsersPrimaryKey...), + ) + sqlgraph.HasNeighbors(s, step) + }) +} + +// HasUsersWith applies the HasEdge predicate on the "users" edge with a given conditions (other predicates). +func HasUsersWith(preds ...predicate.User) predicate.Role { + return predicate.Role(func(s *sql.Selector) { + step := newUsersStep() + sqlgraph.HasNeighborsWith(s, step, func(s *sql.Selector) { + for _, p := range preds { + p(s) + } + }) + }) +} + +// And groups predicates with the AND operator between them. +func And(predicates ...predicate.Role) predicate.Role { + return predicate.Role(sql.AndPredicates(predicates...)) +} + +// Or groups predicates with the OR operator between them. +func Or(predicates ...predicate.Role) predicate.Role { + return predicate.Role(sql.OrPredicates(predicates...)) +} + +// Not applies the not operator on the given predicate. +func Not(p predicate.Role) predicate.Role { + return predicate.Role(sql.NotPredicates(p)) +} diff --git a/internal/ent/role_create.go b/internal/ent/role_create.go new file mode 100644 index 0000000..6faf160 --- /dev/null +++ b/internal/ent/role_create.go @@ -0,0 +1,238 @@ +// Code generated by ent, DO NOT EDIT. + +package ent + +import ( + "EnGin/internal/ent/role" + "EnGin/internal/ent/user" + "context" + "errors" + "fmt" + + "entgo.io/ent/dialect/sql/sqlgraph" + "entgo.io/ent/schema/field" +) + +// RoleCreate is the builder for creating a Role entity. +type RoleCreate struct { + config + mutation *RoleMutation + hooks []Hook +} + +// SetCode sets the "code" field. +func (_c *RoleCreate) SetCode(v string) *RoleCreate { + _c.mutation.SetCode(v) + return _c +} + +// SetName sets the "name" field. +func (_c *RoleCreate) SetName(v string) *RoleCreate { + _c.mutation.SetName(v) + return _c +} + +// AddUserIDs adds the "users" edge to the User entity by IDs. +func (_c *RoleCreate) AddUserIDs(ids ...int) *RoleCreate { + _c.mutation.AddUserIDs(ids...) + return _c +} + +// AddUsers adds the "users" edges to the User entity. +func (_c *RoleCreate) AddUsers(v ...*User) *RoleCreate { + ids := make([]int, len(v)) + for i := range v { + ids[i] = v[i].ID + } + return _c.AddUserIDs(ids...) +} + +// Mutation returns the RoleMutation object of the builder. +func (_c *RoleCreate) Mutation() *RoleMutation { + return _c.mutation +} + +// Save creates the Role in the database. +func (_c *RoleCreate) Save(ctx context.Context) (*Role, error) { + return withHooks(ctx, _c.sqlSave, _c.mutation, _c.hooks) +} + +// SaveX calls Save and panics if Save returns an error. +func (_c *RoleCreate) SaveX(ctx context.Context) *Role { + v, err := _c.Save(ctx) + if err != nil { + panic(err) + } + return v +} + +// Exec executes the query. +func (_c *RoleCreate) Exec(ctx context.Context) error { + _, err := _c.Save(ctx) + return err +} + +// ExecX is like Exec, but panics if an error occurs. +func (_c *RoleCreate) ExecX(ctx context.Context) { + if err := _c.Exec(ctx); err != nil { + panic(err) + } +} + +// check runs all checks and user-defined validators on the builder. +func (_c *RoleCreate) check() error { + if _, ok := _c.mutation.Code(); !ok { + return &ValidationError{Name: "code", err: errors.New(`ent: missing required field "Role.code"`)} + } + if v, ok := _c.mutation.Code(); ok { + if err := role.CodeValidator(v); err != nil { + return &ValidationError{Name: "code", err: fmt.Errorf(`ent: validator failed for field "Role.code": %w`, err)} + } + } + if _, ok := _c.mutation.Name(); !ok { + return &ValidationError{Name: "name", err: errors.New(`ent: missing required field "Role.name"`)} + } + if v, ok := _c.mutation.Name(); ok { + if err := role.NameValidator(v); err != nil { + return &ValidationError{Name: "name", err: fmt.Errorf(`ent: validator failed for field "Role.name": %w`, err)} + } + } + return nil +} + +func (_c *RoleCreate) sqlSave(ctx context.Context) (*Role, error) { + if err := _c.check(); err != nil { + return nil, err + } + _node, _spec := _c.createSpec() + if err := sqlgraph.CreateNode(ctx, _c.driver, _spec); err != nil { + if sqlgraph.IsConstraintError(err) { + err = &ConstraintError{msg: err.Error(), wrap: err} + } + return nil, err + } + id := _spec.ID.Value.(int64) + _node.ID = int(id) + _c.mutation.id = &_node.ID + _c.mutation.done = true + return _node, nil +} + +func (_c *RoleCreate) createSpec() (*Role, *sqlgraph.CreateSpec) { + var ( + _node = &Role{config: _c.config} + _spec = sqlgraph.NewCreateSpec(role.Table, sqlgraph.NewFieldSpec(role.FieldID, field.TypeInt)) + ) + if value, ok := _c.mutation.Code(); ok { + _spec.SetField(role.FieldCode, field.TypeString, value) + _node.Code = value + } + if value, ok := _c.mutation.Name(); ok { + _spec.SetField(role.FieldName, field.TypeString, value) + _node.Name = value + } + if nodes := _c.mutation.UsersIDs(); len(nodes) > 0 { + edge := &sqlgraph.EdgeSpec{ + Rel: sqlgraph.M2M, + Inverse: true, + Table: role.UsersTable, + Columns: role.UsersPrimaryKey, + Bidi: false, + Target: &sqlgraph.EdgeTarget{ + IDSpec: sqlgraph.NewFieldSpec(user.FieldID, field.TypeInt), + }, + } + for _, k := range nodes { + edge.Target.Nodes = append(edge.Target.Nodes, k) + } + _spec.Edges = append(_spec.Edges, edge) + } + return _node, _spec +} + +// RoleCreateBulk is the builder for creating many Role entities in bulk. +type RoleCreateBulk struct { + config + err error + builders []*RoleCreate +} + +// Save creates the Role entities in the database. +func (_c *RoleCreateBulk) Save(ctx context.Context) ([]*Role, error) { + if _c.err != nil { + return nil, _c.err + } + specs := make([]*sqlgraph.CreateSpec, len(_c.builders)) + nodes := make([]*Role, len(_c.builders)) + mutators := make([]Mutator, len(_c.builders)) + for i := range _c.builders { + func(i int, root context.Context) { + builder := _c.builders[i] + var mut Mutator = MutateFunc(func(ctx context.Context, m Mutation) (Value, error) { + mutation, ok := m.(*RoleMutation) + if !ok { + return nil, fmt.Errorf("unexpected mutation type %T", m) + } + if err := builder.check(); err != nil { + return nil, err + } + builder.mutation = mutation + var err error + nodes[i], specs[i] = builder.createSpec() + if i < len(mutators)-1 { + _, err = mutators[i+1].Mutate(root, _c.builders[i+1].mutation) + } else { + spec := &sqlgraph.BatchCreateSpec{Nodes: specs} + // Invoke the actual operation on the latest mutation in the chain. + if err = sqlgraph.BatchCreate(ctx, _c.driver, spec); err != nil { + if sqlgraph.IsConstraintError(err) { + err = &ConstraintError{msg: err.Error(), wrap: err} + } + } + } + if err != nil { + return nil, err + } + mutation.id = &nodes[i].ID + if specs[i].ID.Value != nil { + id := specs[i].ID.Value.(int64) + nodes[i].ID = int(id) + } + mutation.done = true + return nodes[i], nil + }) + for i := len(builder.hooks) - 1; i >= 0; i-- { + mut = builder.hooks[i](mut) + } + mutators[i] = mut + }(i, ctx) + } + if len(mutators) > 0 { + if _, err := mutators[0].Mutate(ctx, _c.builders[0].mutation); err != nil { + return nil, err + } + } + return nodes, nil +} + +// SaveX is like Save, but panics if an error occurs. +func (_c *RoleCreateBulk) SaveX(ctx context.Context) []*Role { + v, err := _c.Save(ctx) + if err != nil { + panic(err) + } + return v +} + +// Exec executes the query. +func (_c *RoleCreateBulk) Exec(ctx context.Context) error { + _, err := _c.Save(ctx) + return err +} + +// ExecX is like Exec, but panics if an error occurs. +func (_c *RoleCreateBulk) ExecX(ctx context.Context) { + if err := _c.Exec(ctx); err != nil { + panic(err) + } +} diff --git a/internal/ent/role_delete.go b/internal/ent/role_delete.go new file mode 100644 index 0000000..add7463 --- /dev/null +++ b/internal/ent/role_delete.go @@ -0,0 +1,88 @@ +// Code generated by ent, DO NOT EDIT. + +package ent + +import ( + "EnGin/internal/ent/predicate" + "EnGin/internal/ent/role" + "context" + + "entgo.io/ent/dialect/sql" + "entgo.io/ent/dialect/sql/sqlgraph" + "entgo.io/ent/schema/field" +) + +// RoleDelete is the builder for deleting a Role entity. +type RoleDelete struct { + config + hooks []Hook + mutation *RoleMutation +} + +// Where appends a list predicates to the RoleDelete builder. +func (_d *RoleDelete) Where(ps ...predicate.Role) *RoleDelete { + _d.mutation.Where(ps...) + return _d +} + +// Exec executes the deletion query and returns how many vertices were deleted. +func (_d *RoleDelete) Exec(ctx context.Context) (int, error) { + return withHooks(ctx, _d.sqlExec, _d.mutation, _d.hooks) +} + +// ExecX is like Exec, but panics if an error occurs. +func (_d *RoleDelete) ExecX(ctx context.Context) int { + n, err := _d.Exec(ctx) + if err != nil { + panic(err) + } + return n +} + +func (_d *RoleDelete) sqlExec(ctx context.Context) (int, error) { + _spec := sqlgraph.NewDeleteSpec(role.Table, sqlgraph.NewFieldSpec(role.FieldID, field.TypeInt)) + if ps := _d.mutation.predicates; len(ps) > 0 { + _spec.Predicate = func(selector *sql.Selector) { + for i := range ps { + ps[i](selector) + } + } + } + affected, err := sqlgraph.DeleteNodes(ctx, _d.driver, _spec) + if err != nil && sqlgraph.IsConstraintError(err) { + err = &ConstraintError{msg: err.Error(), wrap: err} + } + _d.mutation.done = true + return affected, err +} + +// RoleDeleteOne is the builder for deleting a single Role entity. +type RoleDeleteOne struct { + _d *RoleDelete +} + +// Where appends a list predicates to the RoleDelete builder. +func (_d *RoleDeleteOne) Where(ps ...predicate.Role) *RoleDeleteOne { + _d._d.mutation.Where(ps...) + return _d +} + +// Exec executes the deletion query. +func (_d *RoleDeleteOne) Exec(ctx context.Context) error { + n, err := _d._d.Exec(ctx) + switch { + case err != nil: + return err + case n == 0: + return &NotFoundError{role.Label} + default: + return nil + } +} + +// ExecX is like Exec, but panics if an error occurs. +func (_d *RoleDeleteOne) ExecX(ctx context.Context) { + if err := _d.Exec(ctx); err != nil { + panic(err) + } +} diff --git a/internal/ent/role_query.go b/internal/ent/role_query.go new file mode 100644 index 0000000..b895339 --- /dev/null +++ b/internal/ent/role_query.go @@ -0,0 +1,637 @@ +// Code generated by ent, DO NOT EDIT. + +package ent + +import ( + "EnGin/internal/ent/predicate" + "EnGin/internal/ent/role" + "EnGin/internal/ent/user" + "context" + "database/sql/driver" + "fmt" + "math" + + "entgo.io/ent" + "entgo.io/ent/dialect/sql" + "entgo.io/ent/dialect/sql/sqlgraph" + "entgo.io/ent/schema/field" +) + +// RoleQuery is the builder for querying Role entities. +type RoleQuery struct { + config + ctx *QueryContext + order []role.OrderOption + inters []Interceptor + predicates []predicate.Role + withUsers *UserQuery + // intermediate query (i.e. traversal path). + sql *sql.Selector + path func(context.Context) (*sql.Selector, error) +} + +// Where adds a new predicate for the RoleQuery builder. +func (_q *RoleQuery) Where(ps ...predicate.Role) *RoleQuery { + _q.predicates = append(_q.predicates, ps...) + return _q +} + +// Limit the number of records to be returned by this query. +func (_q *RoleQuery) Limit(limit int) *RoleQuery { + _q.ctx.Limit = &limit + return _q +} + +// Offset to start from. +func (_q *RoleQuery) Offset(offset int) *RoleQuery { + _q.ctx.Offset = &offset + return _q +} + +// Unique configures the query builder to filter duplicate records on query. +// By default, unique is set to true, and can be disabled using this method. +func (_q *RoleQuery) Unique(unique bool) *RoleQuery { + _q.ctx.Unique = &unique + return _q +} + +// Order specifies how the records should be ordered. +func (_q *RoleQuery) Order(o ...role.OrderOption) *RoleQuery { + _q.order = append(_q.order, o...) + return _q +} + +// QueryUsers chains the current query on the "users" edge. +func (_q *RoleQuery) QueryUsers() *UserQuery { + query := (&UserClient{config: _q.config}).Query() + query.path = func(ctx context.Context) (fromU *sql.Selector, err error) { + if err := _q.prepareQuery(ctx); err != nil { + return nil, err + } + selector := _q.sqlQuery(ctx) + if err := selector.Err(); err != nil { + return nil, err + } + step := sqlgraph.NewStep( + sqlgraph.From(role.Table, role.FieldID, selector), + sqlgraph.To(user.Table, user.FieldID), + sqlgraph.Edge(sqlgraph.M2M, true, role.UsersTable, role.UsersPrimaryKey...), + ) + fromU = sqlgraph.SetNeighbors(_q.driver.Dialect(), step) + return fromU, nil + } + return query +} + +// First returns the first Role entity from the query. +// Returns a *NotFoundError when no Role was found. +func (_q *RoleQuery) First(ctx context.Context) (*Role, error) { + nodes, err := _q.Limit(1).All(setContextOp(ctx, _q.ctx, ent.OpQueryFirst)) + if err != nil { + return nil, err + } + if len(nodes) == 0 { + return nil, &NotFoundError{role.Label} + } + return nodes[0], nil +} + +// FirstX is like First, but panics if an error occurs. +func (_q *RoleQuery) FirstX(ctx context.Context) *Role { + node, err := _q.First(ctx) + if err != nil && !IsNotFound(err) { + panic(err) + } + return node +} + +// FirstID returns the first Role ID from the query. +// Returns a *NotFoundError when no Role ID was found. +func (_q *RoleQuery) FirstID(ctx context.Context) (id int, err error) { + var ids []int + if ids, err = _q.Limit(1).IDs(setContextOp(ctx, _q.ctx, ent.OpQueryFirstID)); err != nil { + return + } + if len(ids) == 0 { + err = &NotFoundError{role.Label} + return + } + return ids[0], nil +} + +// FirstIDX is like FirstID, but panics if an error occurs. +func (_q *RoleQuery) FirstIDX(ctx context.Context) int { + id, err := _q.FirstID(ctx) + if err != nil && !IsNotFound(err) { + panic(err) + } + return id +} + +// Only returns a single Role entity found by the query, ensuring it only returns one. +// Returns a *NotSingularError when more than one Role entity is found. +// Returns a *NotFoundError when no Role entities are found. +func (_q *RoleQuery) Only(ctx context.Context) (*Role, error) { + nodes, err := _q.Limit(2).All(setContextOp(ctx, _q.ctx, ent.OpQueryOnly)) + if err != nil { + return nil, err + } + switch len(nodes) { + case 1: + return nodes[0], nil + case 0: + return nil, &NotFoundError{role.Label} + default: + return nil, &NotSingularError{role.Label} + } +} + +// OnlyX is like Only, but panics if an error occurs. +func (_q *RoleQuery) OnlyX(ctx context.Context) *Role { + node, err := _q.Only(ctx) + if err != nil { + panic(err) + } + return node +} + +// OnlyID is like Only, but returns the only Role ID in the query. +// Returns a *NotSingularError when more than one Role ID is found. +// Returns a *NotFoundError when no entities are found. +func (_q *RoleQuery) OnlyID(ctx context.Context) (id int, err error) { + var ids []int + if ids, err = _q.Limit(2).IDs(setContextOp(ctx, _q.ctx, ent.OpQueryOnlyID)); err != nil { + return + } + switch len(ids) { + case 1: + id = ids[0] + case 0: + err = &NotFoundError{role.Label} + default: + err = &NotSingularError{role.Label} + } + return +} + +// OnlyIDX is like OnlyID, but panics if an error occurs. +func (_q *RoleQuery) OnlyIDX(ctx context.Context) int { + id, err := _q.OnlyID(ctx) + if err != nil { + panic(err) + } + return id +} + +// All executes the query and returns a list of Roles. +func (_q *RoleQuery) All(ctx context.Context) ([]*Role, error) { + ctx = setContextOp(ctx, _q.ctx, ent.OpQueryAll) + if err := _q.prepareQuery(ctx); err != nil { + return nil, err + } + qr := querierAll[[]*Role, *RoleQuery]() + return withInterceptors[[]*Role](ctx, _q, qr, _q.inters) +} + +// AllX is like All, but panics if an error occurs. +func (_q *RoleQuery) AllX(ctx context.Context) []*Role { + nodes, err := _q.All(ctx) + if err != nil { + panic(err) + } + return nodes +} + +// IDs executes the query and returns a list of Role IDs. +func (_q *RoleQuery) IDs(ctx context.Context) (ids []int, err error) { + if _q.ctx.Unique == nil && _q.path != nil { + _q.Unique(true) + } + ctx = setContextOp(ctx, _q.ctx, ent.OpQueryIDs) + if err = _q.Select(role.FieldID).Scan(ctx, &ids); err != nil { + return nil, err + } + return ids, nil +} + +// IDsX is like IDs, but panics if an error occurs. +func (_q *RoleQuery) IDsX(ctx context.Context) []int { + ids, err := _q.IDs(ctx) + if err != nil { + panic(err) + } + return ids +} + +// Count returns the count of the given query. +func (_q *RoleQuery) Count(ctx context.Context) (int, error) { + ctx = setContextOp(ctx, _q.ctx, ent.OpQueryCount) + if err := _q.prepareQuery(ctx); err != nil { + return 0, err + } + return withInterceptors[int](ctx, _q, querierCount[*RoleQuery](), _q.inters) +} + +// CountX is like Count, but panics if an error occurs. +func (_q *RoleQuery) CountX(ctx context.Context) int { + count, err := _q.Count(ctx) + if err != nil { + panic(err) + } + return count +} + +// Exist returns true if the query has elements in the graph. +func (_q *RoleQuery) Exist(ctx context.Context) (bool, error) { + ctx = setContextOp(ctx, _q.ctx, ent.OpQueryExist) + switch _, err := _q.FirstID(ctx); { + case IsNotFound(err): + return false, nil + case err != nil: + return false, fmt.Errorf("ent: check existence: %w", err) + default: + return true, nil + } +} + +// ExistX is like Exist, but panics if an error occurs. +func (_q *RoleQuery) ExistX(ctx context.Context) bool { + exist, err := _q.Exist(ctx) + if err != nil { + panic(err) + } + return exist +} + +// Clone returns a duplicate of the RoleQuery builder, including all associated steps. It can be +// used to prepare common query builders and use them differently after the clone is made. +func (_q *RoleQuery) Clone() *RoleQuery { + if _q == nil { + return nil + } + return &RoleQuery{ + config: _q.config, + ctx: _q.ctx.Clone(), + order: append([]role.OrderOption{}, _q.order...), + inters: append([]Interceptor{}, _q.inters...), + predicates: append([]predicate.Role{}, _q.predicates...), + withUsers: _q.withUsers.Clone(), + // clone intermediate query. + sql: _q.sql.Clone(), + path: _q.path, + } +} + +// WithUsers tells the query-builder to eager-load the nodes that are connected to +// the "users" edge. The optional arguments are used to configure the query builder of the edge. +func (_q *RoleQuery) WithUsers(opts ...func(*UserQuery)) *RoleQuery { + query := (&UserClient{config: _q.config}).Query() + for _, opt := range opts { + opt(query) + } + _q.withUsers = query + return _q +} + +// GroupBy is used to group vertices by one or more fields/columns. +// It is often used with aggregate functions, like: count, max, mean, min, sum. +// +// Example: +// +// var v []struct { +// Code string `json:"code,omitempty"` +// Count int `json:"count,omitempty"` +// } +// +// client.Role.Query(). +// GroupBy(role.FieldCode). +// Aggregate(ent.Count()). +// Scan(ctx, &v) +func (_q *RoleQuery) GroupBy(field string, fields ...string) *RoleGroupBy { + _q.ctx.Fields = append([]string{field}, fields...) + grbuild := &RoleGroupBy{build: _q} + grbuild.flds = &_q.ctx.Fields + grbuild.label = role.Label + grbuild.scan = grbuild.Scan + return grbuild +} + +// Select allows the selection one or more fields/columns for the given query, +// instead of selecting all fields in the entity. +// +// Example: +// +// var v []struct { +// Code string `json:"code,omitempty"` +// } +// +// client.Role.Query(). +// Select(role.FieldCode). +// Scan(ctx, &v) +func (_q *RoleQuery) Select(fields ...string) *RoleSelect { + _q.ctx.Fields = append(_q.ctx.Fields, fields...) + sbuild := &RoleSelect{RoleQuery: _q} + sbuild.label = role.Label + sbuild.flds, sbuild.scan = &_q.ctx.Fields, sbuild.Scan + return sbuild +} + +// Aggregate returns a RoleSelect configured with the given aggregations. +func (_q *RoleQuery) Aggregate(fns ...AggregateFunc) *RoleSelect { + return _q.Select().Aggregate(fns...) +} + +func (_q *RoleQuery) prepareQuery(ctx context.Context) error { + for _, inter := range _q.inters { + if inter == nil { + return fmt.Errorf("ent: uninitialized interceptor (forgotten import ent/runtime?)") + } + if trv, ok := inter.(Traverser); ok { + if err := trv.Traverse(ctx, _q); err != nil { + return err + } + } + } + for _, f := range _q.ctx.Fields { + if !role.ValidColumn(f) { + return &ValidationError{Name: f, err: fmt.Errorf("ent: invalid field %q for query", f)} + } + } + if _q.path != nil { + prev, err := _q.path(ctx) + if err != nil { + return err + } + _q.sql = prev + } + return nil +} + +func (_q *RoleQuery) sqlAll(ctx context.Context, hooks ...queryHook) ([]*Role, error) { + var ( + nodes = []*Role{} + _spec = _q.querySpec() + loadedTypes = [1]bool{ + _q.withUsers != nil, + } + ) + _spec.ScanValues = func(columns []string) ([]any, error) { + return (*Role).scanValues(nil, columns) + } + _spec.Assign = func(columns []string, values []any) error { + node := &Role{config: _q.config} + nodes = append(nodes, node) + node.Edges.loadedTypes = loadedTypes + return node.assignValues(columns, values) + } + for i := range hooks { + hooks[i](ctx, _spec) + } + if err := sqlgraph.QueryNodes(ctx, _q.driver, _spec); err != nil { + return nil, err + } + if len(nodes) == 0 { + return nodes, nil + } + if query := _q.withUsers; query != nil { + if err := _q.loadUsers(ctx, query, nodes, + func(n *Role) { n.Edges.Users = []*User{} }, + func(n *Role, e *User) { n.Edges.Users = append(n.Edges.Users, e) }); err != nil { + return nil, err + } + } + return nodes, nil +} + +func (_q *RoleQuery) loadUsers(ctx context.Context, query *UserQuery, nodes []*Role, init func(*Role), assign func(*Role, *User)) error { + edgeIDs := make([]driver.Value, len(nodes)) + byID := make(map[int]*Role) + nids := make(map[int]map[*Role]struct{}) + for i, node := range nodes { + edgeIDs[i] = node.ID + byID[node.ID] = node + if init != nil { + init(node) + } + } + query.Where(func(s *sql.Selector) { + joinT := sql.Table(role.UsersTable) + s.Join(joinT).On(s.C(user.FieldID), joinT.C(role.UsersPrimaryKey[0])) + s.Where(sql.InValues(joinT.C(role.UsersPrimaryKey[1]), edgeIDs...)) + columns := s.SelectedColumns() + s.Select(joinT.C(role.UsersPrimaryKey[1])) + s.AppendSelect(columns...) + s.SetDistinct(false) + }) + if err := query.prepareQuery(ctx); err != nil { + return err + } + qr := QuerierFunc(func(ctx context.Context, q Query) (Value, error) { + return query.sqlAll(ctx, func(_ context.Context, spec *sqlgraph.QuerySpec) { + assign := spec.Assign + values := spec.ScanValues + spec.ScanValues = func(columns []string) ([]any, error) { + values, err := values(columns[1:]) + if err != nil { + return nil, err + } + return append([]any{new(sql.NullInt64)}, values...), nil + } + spec.Assign = func(columns []string, values []any) error { + outValue := int(values[0].(*sql.NullInt64).Int64) + inValue := int(values[1].(*sql.NullInt64).Int64) + if nids[inValue] == nil { + nids[inValue] = map[*Role]struct{}{byID[outValue]: {}} + return assign(columns[1:], values[1:]) + } + nids[inValue][byID[outValue]] = struct{}{} + return nil + } + }) + }) + neighbors, err := withInterceptors[[]*User](ctx, query, qr, query.inters) + if err != nil { + return err + } + for _, n := range neighbors { + nodes, ok := nids[n.ID] + if !ok { + return fmt.Errorf(`unexpected "users" node returned %v`, n.ID) + } + for kn := range nodes { + assign(kn, n) + } + } + return nil +} + +func (_q *RoleQuery) sqlCount(ctx context.Context) (int, error) { + _spec := _q.querySpec() + _spec.Node.Columns = _q.ctx.Fields + if len(_q.ctx.Fields) > 0 { + _spec.Unique = _q.ctx.Unique != nil && *_q.ctx.Unique + } + return sqlgraph.CountNodes(ctx, _q.driver, _spec) +} + +func (_q *RoleQuery) querySpec() *sqlgraph.QuerySpec { + _spec := sqlgraph.NewQuerySpec(role.Table, role.Columns, sqlgraph.NewFieldSpec(role.FieldID, field.TypeInt)) + _spec.From = _q.sql + if unique := _q.ctx.Unique; unique != nil { + _spec.Unique = *unique + } else if _q.path != nil { + _spec.Unique = true + } + if fields := _q.ctx.Fields; len(fields) > 0 { + _spec.Node.Columns = make([]string, 0, len(fields)) + _spec.Node.Columns = append(_spec.Node.Columns, role.FieldID) + for i := range fields { + if fields[i] != role.FieldID { + _spec.Node.Columns = append(_spec.Node.Columns, fields[i]) + } + } + } + if ps := _q.predicates; len(ps) > 0 { + _spec.Predicate = func(selector *sql.Selector) { + for i := range ps { + ps[i](selector) + } + } + } + if limit := _q.ctx.Limit; limit != nil { + _spec.Limit = *limit + } + if offset := _q.ctx.Offset; offset != nil { + _spec.Offset = *offset + } + if ps := _q.order; len(ps) > 0 { + _spec.Order = func(selector *sql.Selector) { + for i := range ps { + ps[i](selector) + } + } + } + return _spec +} + +func (_q *RoleQuery) sqlQuery(ctx context.Context) *sql.Selector { + builder := sql.Dialect(_q.driver.Dialect()) + t1 := builder.Table(role.Table) + columns := _q.ctx.Fields + if len(columns) == 0 { + columns = role.Columns + } + selector := builder.Select(t1.Columns(columns...)...).From(t1) + if _q.sql != nil { + selector = _q.sql + selector.Select(selector.Columns(columns...)...) + } + if _q.ctx.Unique != nil && *_q.ctx.Unique { + selector.Distinct() + } + for _, p := range _q.predicates { + p(selector) + } + for _, p := range _q.order { + p(selector) + } + if offset := _q.ctx.Offset; offset != nil { + // limit is mandatory for offset clause. We start + // with default value, and override it below if needed. + selector.Offset(*offset).Limit(math.MaxInt32) + } + if limit := _q.ctx.Limit; limit != nil { + selector.Limit(*limit) + } + return selector +} + +// RoleGroupBy is the group-by builder for Role entities. +type RoleGroupBy struct { + selector + build *RoleQuery +} + +// Aggregate adds the given aggregation functions to the group-by query. +func (_g *RoleGroupBy) Aggregate(fns ...AggregateFunc) *RoleGroupBy { + _g.fns = append(_g.fns, fns...) + return _g +} + +// Scan applies the selector query and scans the result into the given value. +func (_g *RoleGroupBy) Scan(ctx context.Context, v any) error { + ctx = setContextOp(ctx, _g.build.ctx, ent.OpQueryGroupBy) + if err := _g.build.prepareQuery(ctx); err != nil { + return err + } + return scanWithInterceptors[*RoleQuery, *RoleGroupBy](ctx, _g.build, _g, _g.build.inters, v) +} + +func (_g *RoleGroupBy) sqlScan(ctx context.Context, root *RoleQuery, v any) error { + selector := root.sqlQuery(ctx).Select() + aggregation := make([]string, 0, len(_g.fns)) + for _, fn := range _g.fns { + aggregation = append(aggregation, fn(selector)) + } + if len(selector.SelectedColumns()) == 0 { + columns := make([]string, 0, len(*_g.flds)+len(_g.fns)) + for _, f := range *_g.flds { + columns = append(columns, selector.C(f)) + } + columns = append(columns, aggregation...) + selector.Select(columns...) + } + selector.GroupBy(selector.Columns(*_g.flds...)...) + if err := selector.Err(); err != nil { + return err + } + rows := &sql.Rows{} + query, args := selector.Query() + if err := _g.build.driver.Query(ctx, query, args, rows); err != nil { + return err + } + defer rows.Close() + return sql.ScanSlice(rows, v) +} + +// RoleSelect is the builder for selecting fields of Role entities. +type RoleSelect struct { + *RoleQuery + selector +} + +// Aggregate adds the given aggregation functions to the selector query. +func (_s *RoleSelect) Aggregate(fns ...AggregateFunc) *RoleSelect { + _s.fns = append(_s.fns, fns...) + return _s +} + +// Scan applies the selector query and scans the result into the given value. +func (_s *RoleSelect) Scan(ctx context.Context, v any) error { + ctx = setContextOp(ctx, _s.ctx, ent.OpQuerySelect) + if err := _s.prepareQuery(ctx); err != nil { + return err + } + return scanWithInterceptors[*RoleQuery, *RoleSelect](ctx, _s.RoleQuery, _s, _s.inters, v) +} + +func (_s *RoleSelect) sqlScan(ctx context.Context, root *RoleQuery, v any) error { + selector := root.sqlQuery(ctx) + aggregation := make([]string, 0, len(_s.fns)) + for _, fn := range _s.fns { + aggregation = append(aggregation, fn(selector)) + } + switch n := len(*_s.selector.flds); { + case n == 0 && len(aggregation) > 0: + selector.Select(aggregation...) + case n != 0 && len(aggregation) > 0: + selector.AppendSelect(aggregation...) + } + rows := &sql.Rows{} + query, args := selector.Query() + if err := _s.driver.Query(ctx, query, args, rows); err != nil { + return err + } + defer rows.Close() + return sql.ScanSlice(rows, v) +} diff --git a/internal/ent/role_update.go b/internal/ent/role_update.go new file mode 100644 index 0000000..9809207 --- /dev/null +++ b/internal/ent/role_update.go @@ -0,0 +1,442 @@ +// Code generated by ent, DO NOT EDIT. + +package ent + +import ( + "EnGin/internal/ent/predicate" + "EnGin/internal/ent/role" + "EnGin/internal/ent/user" + "context" + "errors" + "fmt" + + "entgo.io/ent/dialect/sql" + "entgo.io/ent/dialect/sql/sqlgraph" + "entgo.io/ent/schema/field" +) + +// RoleUpdate is the builder for updating Role entities. +type RoleUpdate struct { + config + hooks []Hook + mutation *RoleMutation +} + +// Where appends a list predicates to the RoleUpdate builder. +func (_u *RoleUpdate) Where(ps ...predicate.Role) *RoleUpdate { + _u.mutation.Where(ps...) + return _u +} + +// SetCode sets the "code" field. +func (_u *RoleUpdate) SetCode(v string) *RoleUpdate { + _u.mutation.SetCode(v) + return _u +} + +// SetNillableCode sets the "code" field if the given value is not nil. +func (_u *RoleUpdate) SetNillableCode(v *string) *RoleUpdate { + if v != nil { + _u.SetCode(*v) + } + return _u +} + +// SetName sets the "name" field. +func (_u *RoleUpdate) SetName(v string) *RoleUpdate { + _u.mutation.SetName(v) + return _u +} + +// SetNillableName sets the "name" field if the given value is not nil. +func (_u *RoleUpdate) SetNillableName(v *string) *RoleUpdate { + if v != nil { + _u.SetName(*v) + } + return _u +} + +// AddUserIDs adds the "users" edge to the User entity by IDs. +func (_u *RoleUpdate) AddUserIDs(ids ...int) *RoleUpdate { + _u.mutation.AddUserIDs(ids...) + return _u +} + +// AddUsers adds the "users" edges to the User entity. +func (_u *RoleUpdate) AddUsers(v ...*User) *RoleUpdate { + ids := make([]int, len(v)) + for i := range v { + ids[i] = v[i].ID + } + return _u.AddUserIDs(ids...) +} + +// Mutation returns the RoleMutation object of the builder. +func (_u *RoleUpdate) Mutation() *RoleMutation { + return _u.mutation +} + +// ClearUsers clears all "users" edges to the User entity. +func (_u *RoleUpdate) ClearUsers() *RoleUpdate { + _u.mutation.ClearUsers() + return _u +} + +// RemoveUserIDs removes the "users" edge to User entities by IDs. +func (_u *RoleUpdate) RemoveUserIDs(ids ...int) *RoleUpdate { + _u.mutation.RemoveUserIDs(ids...) + return _u +} + +// RemoveUsers removes "users" edges to User entities. +func (_u *RoleUpdate) RemoveUsers(v ...*User) *RoleUpdate { + ids := make([]int, len(v)) + for i := range v { + ids[i] = v[i].ID + } + return _u.RemoveUserIDs(ids...) +} + +// Save executes the query and returns the number of nodes affected by the update operation. +func (_u *RoleUpdate) Save(ctx context.Context) (int, error) { + return withHooks(ctx, _u.sqlSave, _u.mutation, _u.hooks) +} + +// SaveX is like Save, but panics if an error occurs. +func (_u *RoleUpdate) SaveX(ctx context.Context) int { + affected, err := _u.Save(ctx) + if err != nil { + panic(err) + } + return affected +} + +// Exec executes the query. +func (_u *RoleUpdate) Exec(ctx context.Context) error { + _, err := _u.Save(ctx) + return err +} + +// ExecX is like Exec, but panics if an error occurs. +func (_u *RoleUpdate) ExecX(ctx context.Context) { + if err := _u.Exec(ctx); err != nil { + panic(err) + } +} + +// check runs all checks and user-defined validators on the builder. +func (_u *RoleUpdate) check() error { + if v, ok := _u.mutation.Code(); ok { + if err := role.CodeValidator(v); err != nil { + return &ValidationError{Name: "code", err: fmt.Errorf(`ent: validator failed for field "Role.code": %w`, err)} + } + } + if v, ok := _u.mutation.Name(); ok { + if err := role.NameValidator(v); err != nil { + return &ValidationError{Name: "name", err: fmt.Errorf(`ent: validator failed for field "Role.name": %w`, err)} + } + } + return nil +} + +func (_u *RoleUpdate) sqlSave(ctx context.Context) (_node int, err error) { + if err := _u.check(); err != nil { + return _node, err + } + _spec := sqlgraph.NewUpdateSpec(role.Table, role.Columns, sqlgraph.NewFieldSpec(role.FieldID, field.TypeInt)) + if ps := _u.mutation.predicates; len(ps) > 0 { + _spec.Predicate = func(selector *sql.Selector) { + for i := range ps { + ps[i](selector) + } + } + } + if value, ok := _u.mutation.Code(); ok { + _spec.SetField(role.FieldCode, field.TypeString, value) + } + if value, ok := _u.mutation.Name(); ok { + _spec.SetField(role.FieldName, field.TypeString, value) + } + if _u.mutation.UsersCleared() { + edge := &sqlgraph.EdgeSpec{ + Rel: sqlgraph.M2M, + Inverse: true, + Table: role.UsersTable, + Columns: role.UsersPrimaryKey, + Bidi: false, + Target: &sqlgraph.EdgeTarget{ + IDSpec: sqlgraph.NewFieldSpec(user.FieldID, field.TypeInt), + }, + } + _spec.Edges.Clear = append(_spec.Edges.Clear, edge) + } + if nodes := _u.mutation.RemovedUsersIDs(); len(nodes) > 0 && !_u.mutation.UsersCleared() { + edge := &sqlgraph.EdgeSpec{ + Rel: sqlgraph.M2M, + Inverse: true, + Table: role.UsersTable, + Columns: role.UsersPrimaryKey, + Bidi: false, + Target: &sqlgraph.EdgeTarget{ + IDSpec: sqlgraph.NewFieldSpec(user.FieldID, field.TypeInt), + }, + } + for _, k := range nodes { + edge.Target.Nodes = append(edge.Target.Nodes, k) + } + _spec.Edges.Clear = append(_spec.Edges.Clear, edge) + } + if nodes := _u.mutation.UsersIDs(); len(nodes) > 0 { + edge := &sqlgraph.EdgeSpec{ + Rel: sqlgraph.M2M, + Inverse: true, + Table: role.UsersTable, + Columns: role.UsersPrimaryKey, + Bidi: false, + Target: &sqlgraph.EdgeTarget{ + IDSpec: sqlgraph.NewFieldSpec(user.FieldID, field.TypeInt), + }, + } + for _, k := range nodes { + edge.Target.Nodes = append(edge.Target.Nodes, k) + } + _spec.Edges.Add = append(_spec.Edges.Add, edge) + } + if _node, err = sqlgraph.UpdateNodes(ctx, _u.driver, _spec); err != nil { + if _, ok := err.(*sqlgraph.NotFoundError); ok { + err = &NotFoundError{role.Label} + } else if sqlgraph.IsConstraintError(err) { + err = &ConstraintError{msg: err.Error(), wrap: err} + } + return 0, err + } + _u.mutation.done = true + return _node, nil +} + +// RoleUpdateOne is the builder for updating a single Role entity. +type RoleUpdateOne struct { + config + fields []string + hooks []Hook + mutation *RoleMutation +} + +// SetCode sets the "code" field. +func (_u *RoleUpdateOne) SetCode(v string) *RoleUpdateOne { + _u.mutation.SetCode(v) + return _u +} + +// SetNillableCode sets the "code" field if the given value is not nil. +func (_u *RoleUpdateOne) SetNillableCode(v *string) *RoleUpdateOne { + if v != nil { + _u.SetCode(*v) + } + return _u +} + +// SetName sets the "name" field. +func (_u *RoleUpdateOne) SetName(v string) *RoleUpdateOne { + _u.mutation.SetName(v) + return _u +} + +// SetNillableName sets the "name" field if the given value is not nil. +func (_u *RoleUpdateOne) SetNillableName(v *string) *RoleUpdateOne { + if v != nil { + _u.SetName(*v) + } + return _u +} + +// AddUserIDs adds the "users" edge to the User entity by IDs. +func (_u *RoleUpdateOne) AddUserIDs(ids ...int) *RoleUpdateOne { + _u.mutation.AddUserIDs(ids...) + return _u +} + +// AddUsers adds the "users" edges to the User entity. +func (_u *RoleUpdateOne) AddUsers(v ...*User) *RoleUpdateOne { + ids := make([]int, len(v)) + for i := range v { + ids[i] = v[i].ID + } + return _u.AddUserIDs(ids...) +} + +// Mutation returns the RoleMutation object of the builder. +func (_u *RoleUpdateOne) Mutation() *RoleMutation { + return _u.mutation +} + +// ClearUsers clears all "users" edges to the User entity. +func (_u *RoleUpdateOne) ClearUsers() *RoleUpdateOne { + _u.mutation.ClearUsers() + return _u +} + +// RemoveUserIDs removes the "users" edge to User entities by IDs. +func (_u *RoleUpdateOne) RemoveUserIDs(ids ...int) *RoleUpdateOne { + _u.mutation.RemoveUserIDs(ids...) + return _u +} + +// RemoveUsers removes "users" edges to User entities. +func (_u *RoleUpdateOne) RemoveUsers(v ...*User) *RoleUpdateOne { + ids := make([]int, len(v)) + for i := range v { + ids[i] = v[i].ID + } + return _u.RemoveUserIDs(ids...) +} + +// Where appends a list predicates to the RoleUpdate builder. +func (_u *RoleUpdateOne) Where(ps ...predicate.Role) *RoleUpdateOne { + _u.mutation.Where(ps...) + return _u +} + +// Select allows selecting one or more fields (columns) of the returned entity. +// The default is selecting all fields defined in the entity schema. +func (_u *RoleUpdateOne) Select(field string, fields ...string) *RoleUpdateOne { + _u.fields = append([]string{field}, fields...) + return _u +} + +// Save executes the query and returns the updated Role entity. +func (_u *RoleUpdateOne) Save(ctx context.Context) (*Role, error) { + return withHooks(ctx, _u.sqlSave, _u.mutation, _u.hooks) +} + +// SaveX is like Save, but panics if an error occurs. +func (_u *RoleUpdateOne) SaveX(ctx context.Context) *Role { + node, err := _u.Save(ctx) + if err != nil { + panic(err) + } + return node +} + +// Exec executes the query on the entity. +func (_u *RoleUpdateOne) Exec(ctx context.Context) error { + _, err := _u.Save(ctx) + return err +} + +// ExecX is like Exec, but panics if an error occurs. +func (_u *RoleUpdateOne) ExecX(ctx context.Context) { + if err := _u.Exec(ctx); err != nil { + panic(err) + } +} + +// check runs all checks and user-defined validators on the builder. +func (_u *RoleUpdateOne) check() error { + if v, ok := _u.mutation.Code(); ok { + if err := role.CodeValidator(v); err != nil { + return &ValidationError{Name: "code", err: fmt.Errorf(`ent: validator failed for field "Role.code": %w`, err)} + } + } + if v, ok := _u.mutation.Name(); ok { + if err := role.NameValidator(v); err != nil { + return &ValidationError{Name: "name", err: fmt.Errorf(`ent: validator failed for field "Role.name": %w`, err)} + } + } + return nil +} + +func (_u *RoleUpdateOne) sqlSave(ctx context.Context) (_node *Role, err error) { + if err := _u.check(); err != nil { + return _node, err + } + _spec := sqlgraph.NewUpdateSpec(role.Table, role.Columns, sqlgraph.NewFieldSpec(role.FieldID, field.TypeInt)) + id, ok := _u.mutation.ID() + if !ok { + return nil, &ValidationError{Name: "id", err: errors.New(`ent: missing "Role.id" for update`)} + } + _spec.Node.ID.Value = id + if fields := _u.fields; len(fields) > 0 { + _spec.Node.Columns = make([]string, 0, len(fields)) + _spec.Node.Columns = append(_spec.Node.Columns, role.FieldID) + for _, f := range fields { + if !role.ValidColumn(f) { + return nil, &ValidationError{Name: f, err: fmt.Errorf("ent: invalid field %q for query", f)} + } + if f != role.FieldID { + _spec.Node.Columns = append(_spec.Node.Columns, f) + } + } + } + if ps := _u.mutation.predicates; len(ps) > 0 { + _spec.Predicate = func(selector *sql.Selector) { + for i := range ps { + ps[i](selector) + } + } + } + if value, ok := _u.mutation.Code(); ok { + _spec.SetField(role.FieldCode, field.TypeString, value) + } + if value, ok := _u.mutation.Name(); ok { + _spec.SetField(role.FieldName, field.TypeString, value) + } + if _u.mutation.UsersCleared() { + edge := &sqlgraph.EdgeSpec{ + Rel: sqlgraph.M2M, + Inverse: true, + Table: role.UsersTable, + Columns: role.UsersPrimaryKey, + Bidi: false, + Target: &sqlgraph.EdgeTarget{ + IDSpec: sqlgraph.NewFieldSpec(user.FieldID, field.TypeInt), + }, + } + _spec.Edges.Clear = append(_spec.Edges.Clear, edge) + } + if nodes := _u.mutation.RemovedUsersIDs(); len(nodes) > 0 && !_u.mutation.UsersCleared() { + edge := &sqlgraph.EdgeSpec{ + Rel: sqlgraph.M2M, + Inverse: true, + Table: role.UsersTable, + Columns: role.UsersPrimaryKey, + Bidi: false, + Target: &sqlgraph.EdgeTarget{ + IDSpec: sqlgraph.NewFieldSpec(user.FieldID, field.TypeInt), + }, + } + for _, k := range nodes { + edge.Target.Nodes = append(edge.Target.Nodes, k) + } + _spec.Edges.Clear = append(_spec.Edges.Clear, edge) + } + if nodes := _u.mutation.UsersIDs(); len(nodes) > 0 { + edge := &sqlgraph.EdgeSpec{ + Rel: sqlgraph.M2M, + Inverse: true, + Table: role.UsersTable, + Columns: role.UsersPrimaryKey, + Bidi: false, + Target: &sqlgraph.EdgeTarget{ + IDSpec: sqlgraph.NewFieldSpec(user.FieldID, field.TypeInt), + }, + } + for _, k := range nodes { + edge.Target.Nodes = append(edge.Target.Nodes, k) + } + _spec.Edges.Add = append(_spec.Edges.Add, edge) + } + _node = &Role{config: _u.config} + _spec.Assign = _node.assignValues + _spec.ScanValues = _node.scanValues + if err = sqlgraph.UpdateNode(ctx, _u.driver, _spec); err != nil { + if _, ok := err.(*sqlgraph.NotFoundError); ok { + err = &NotFoundError{role.Label} + } else if sqlgraph.IsConstraintError(err) { + err = &ConstraintError{msg: err.Error(), wrap: err} + } + return nil, err + } + _u.mutation.done = true + return _node, nil +} diff --git a/internal/middleware/bind.go b/internal/middleware/bind.go new file mode 100644 index 0000000..4eadf8a --- /dev/null +++ b/internal/middleware/bind.go @@ -0,0 +1,44 @@ +package middleware + +import ( + "EnGin/internal/utils/res" + + "github.com/gin-gonic/gin" +) + +func BindJsonMiddleware[T any](c *gin.Context) { + var cr T + err := c.ShouldBindJSON(&cr) + if err != nil { + res.FailWithError(err, c) + c.Abort() + return + } + c.Set("request", cr) +} + +func BindQueryMiddleware[T any](c *gin.Context) { + var cr T + err := c.ShouldBindQuery(&cr) + if err != nil { + res.FailWithError(err, c) + c.Abort() + return + } + c.Set("request", cr) +} + +func BindUriMiddleware[T any](c *gin.Context) { + var cr T + err := c.ShouldBindUri(&cr) + if err != nil { + res.FailWithError(err, c) + c.Abort() + return + } + c.Set("request", cr) +} + +func GetBind[T any](c *gin.Context) (cr T) { + return c.MustGet("request").(T) +} diff --git a/internal/middleware/limit.go b/internal/middleware/limit.go new file mode 100644 index 0000000..37658ea --- /dev/null +++ b/internal/middleware/limit.go @@ -0,0 +1,98 @@ +package middleware + +import ( + "EnGin/internal/db" + "EnGin/internal/utils/res" + "context" + "fmt" + "time" + + "github.com/gin-gonic/gin" +) + +// LimitConfig 限流配置 +type LimitConfig struct { + MaxRequest int // 最大请求数 + TimeWindow time.Duration // 时间窗口 + Message string // 提示信息 +} + +var ( + DefaultLimit = LimitConfig{ + MaxRequest: 100, + TimeWindow: 60 * time.Second, + Message: "请求过于频繁,请稍后重试", + } + + SearchLimit = LimitConfig{ + MaxRequest: 20, + TimeWindow: 60 * time.Second, + Message: "搜索过于频繁,请稍后重试", + } + + AuthLimit = LimitConfig{ + MaxRequest: 5, + TimeWindow: 60 * time.Second, + Message: "登录尝试过多,请稍后重试", + } + + PaymentLimit = LimitConfig{ + MaxRequest: 3, + TimeWindow: 60 * time.Second, + Message: "操作过于频繁,请稍后重试", + } +) + +// RateLimitMiddleware ip限流器 +func RateLimitMiddleware(c *gin.Context, config LimitConfig) { + ip := c.ClientIP() + key := fmt.Sprintf("rate_limit:%s", ip) + ctx := context.Background() + + // 获取当前计数 + count, err := db.Redis.Get(ctx, key).Int() + if err != nil && err.Error() != "redis: nil" { + // Redis 错误,放行请求(降级策略) + c.Next() + return + } + + // 检查是否超限 + if count >= config.MaxRequest { + res.FailWithMsg("请求过于频繁,请稍后重试", c) + c.Abort() + return + } + + // 增加计数 + pipe := db.Redis.Pipeline() + pipe.Incr(ctx, key) + pipe.Expire(ctx, key, config.TimeWindow) + _, err = pipe.Exec(ctx) + + if err != nil { + // Redis 错误,放行请求 + c.Next() + return + } + + c.Next() +} + +// 快捷方法 + +func DefaultRateLimit(c *gin.Context) { + RateLimitMiddleware(c, DefaultLimit) +} + +func SearchRateLimit(c *gin.Context) { + RateLimitMiddleware(c, SearchLimit) +} + +func AuthRateLimit(c *gin.Context) { + RateLimitMiddleware(c, AuthLimit) +} + +func PaymentRateLimit(c *gin.Context) { + RateLimitMiddleware(c, AuthLimit) +}