lrf402788946 4 jaren geleden
bovenliggende
commit
bbfc12777f

+ 59 - 0
app/controller/.admin.js

@@ -0,0 +1,59 @@
+module.exports = {
+  create: {
+    requestBody: [
+      "!name",
+      "!phone",
+      "!passwd",
+      "remark",
+    ],
+  },
+  destroy: {
+    params: ["!id"],
+    service: "delete",
+  },
+  update: {
+    params: ["!id"],
+    requestBody: [
+      "name",
+      "phone",
+      "remark",
+    ],
+  },
+  show: {
+    parameters: {
+      params: ["!id"],
+    },
+    service: "fetch",
+  },
+  index: {
+    parameters: {
+      query: {
+        name: "%name%",
+        phone: "phone",
+        "create_time@start": "create_time@start",
+        "create_time@end": "create_time@end",
+      },
+      // options: {
+      //   "meta.state": 0 // 默认条件
+      // },
+    },
+    service: "query",
+    options: {
+      query: ["skip", "limit"],
+      sort: ["meta.createdAt"],
+      desc: true,
+      count: true,
+    },
+  },
+  //修改密码
+  password: {
+    params: ["!id"],
+    requestBody: ["passwd"],
+    service: "password",
+  },
+  // 登陆
+  login: {
+    requestBody: ["code_phone", "passwd"],
+    service: "login",
+  }
+};

+ 87 - 0
app/controller/.expert.js

@@ -0,0 +1,87 @@
+module.exports = {
+  create: {
+    requestBody: [
+      "code",
+      "education",
+      "school",
+      "birthDate",
+      "qqwx",
+      "email",
+      "company",
+      "zwzc",
+      "expertise",
+      "img_path",
+      "workexperience",
+      "scientific",
+      "undertakingproject",
+      "scienceaward",
+      "social",
+      "status",
+      "remark",
+      'name',
+      'phone',
+      'addr',
+      'office_phone',
+      'profession',
+    ],
+  },
+  destroy: {
+    params: ["!id"],
+    service: "delete",
+  },
+  update: {
+    params: ["!id"],
+    requestBody: [
+      "education",
+      "school",
+      "birthDate",
+      "qqwx",
+      "email",
+      "company",
+      "zwzc",
+      "expertise",
+      "img_path",
+      "workexperience",
+      "scientific",
+      "undertakingproject",
+      "scienceaward",
+      "social",
+      "status",
+      "remark",
+      'name',
+      'phone',
+      'addr',
+      'office_phone',
+      'profession',
+    ],
+  },
+  show: {
+    parameters: {
+      params: ["!user_id"],
+    },
+    service: "fetch",
+  },
+  index: {
+    parameters: {
+      query: {
+        name: "%name%",
+        phone: "phone",
+        code: "code",
+        company: "company",
+        status: "status",
+        "create_time@start": "create_time@start",
+        "create_time@end": "create_time@end",
+      },
+      options: {
+        isdel: "0", // 默认条件
+      },
+    },
+    service: "query",
+    options: {
+      query: ["skip", "limit"],
+      sort: ["meta.createdAt"],
+      desc: true,
+      count: true,
+    },
+  },
+};

+ 1 - 1
app/controller/.news.js

@@ -38,7 +38,7 @@ module.exports = {
     parameters: {
       query: {
         user_id: "user_id",
-        column_name: "%column_name%",
+        column_name: "column_name",
         title: "%title%",
         origin: "origin",
         "release_time@start": "release_time@start",

+ 77 - 0
app/controller/.patent.js

@@ -0,0 +1,77 @@
+module.exports = {
+  create: {
+    requestBody: [
+      "create_number",
+      "create_date",
+      "success_number",
+      "success_date",
+      "name",
+      "inventor",
+      "address",
+      "apply_personal",
+      "term",
+      "type",
+      "agent_personal",
+      "agent",
+      "abstract",
+      "img_url",
+      "origin",
+    ],
+  },
+  destroy: {
+    params: ["!id"],
+    service: "delete",
+  },
+  update: {
+    params: ["!id"],
+    requestBody: [
+      "create_number",
+      "create_date",
+      "success_number",
+      "success_date",
+      "name",
+      "inventor",
+      "address",
+      "apply_personal",
+      "term",
+      "type",
+      "agent_personal",
+      "agent",
+      "abstract",
+      "img_url",
+      "origin",
+    ],
+  },
+  show: {
+    parameters: {
+      params: ["!id"],
+    },
+    service: "fetch",
+  },
+  index: {
+    parameters: {
+      query: {
+        create_number: "create_number",
+        create_date: "create_date",
+        create_number: "create_number",
+        success_date: "success_date",
+        name: "%name%",
+        inventor: "inventor",
+        address: "address",
+        apply_personal: "%apply_personal%",
+        term: "term",
+        type: "type",
+        agent_personal: "agent_personal",
+        agent: "agent",
+        origin: "%origin%",
+      },
+    },
+    service: "query",
+    options: {
+      query: ["skip", "limit"],
+      sort: ["meta.createdAt"],
+      desc: true,
+      count: true,
+    },
+  },
+};

+ 110 - 0
app/controller/.product.js

@@ -0,0 +1,110 @@
+module.exports = {
+  create: {
+    requestBody: [
+      "name",
+      "contacts",
+      "phone",
+      "qqwx",
+      "email",
+      "type",
+      "status",
+      "user_id",
+      "field",
+      "cooperation",
+      "company",
+      "condition",
+      "image",
+      "expect",
+      "demand",
+      "budget",
+      "requirementdesc",
+      "present",
+      "achievestatus",
+      "achieveown",
+      "achievesource",
+      "intentionprice",
+      "patent",
+      "roadshow",
+      "achievebrief",
+      "features",
+      "team",
+      "messattribute",
+      "informationdesc",
+      "coreelements",
+      "priceinfo",
+      "remark",
+    ],
+  },
+  destroy: {
+    params: ["!id"],
+    service: "delete",
+  },
+  update: {
+    params: ["!id"],
+    requestBody: [
+      "name",
+      "contacts",
+      "phone",
+      "qqwx",
+      "email",
+      "type",
+      "status",
+      "user_id",
+      "field",
+      "cooperation",
+      "company",
+      "condition",
+      "image",
+      "expect",
+      "demand",
+      "budget",
+      "requirementdesc",
+      "present",
+      "achievestatus",
+      "achieveown",
+      "achievesource",
+      "intentionprice",
+      "patent",
+      "roadshow",
+      "achievebrief",
+      "features",
+      "team",
+      "messattribute",
+      "informationdesc",
+      "coreelements",
+      "priceinfo",
+      "remark",
+    ],
+  },
+  show: {
+    parameters: {
+      params: ["!id"],
+    },
+    service: "fetch",
+  },
+  index: {
+    parameters: {
+      query: {
+        name: "%name%",
+        code:"code",
+        qqwx: "qqwx",
+        type: "type",
+        status: "status",
+        user_id: "user_id",
+        company: "company",
+        "create_time@start": "create_time@start",
+        "create_time@end": "create_time@end",
+      },
+      // options: {
+      //   "meta.state": 0 // 默认条件
+      // },
+    },
+    service: "query",
+    options: {
+      query: ["skip", "limit"],
+      sort: ["meta.createdAt"],
+      desc: true,
+      count: true,
+    },
+  },
+};

+ 64 - 0
app/controller/.road_show.js

@@ -0,0 +1,64 @@
+module.exports = {
+  create: {
+    requestBody: [
+      "user_id",
+      "dock_id",
+      "title",
+      "brief",
+      "origin",
+      "publish_time",
+      "content",
+      "picture",
+      "filepath",
+      "remark"
+    ],
+  },
+  destroy: {
+    params: ["!id"],
+    service: "delete",
+  },
+  update: {
+    params: ["!id"],
+    requestBody: [
+      "user_id",
+      "dock_id",
+      "title",
+      "brief",
+      "origin",
+      "publish_time",
+      "content",
+      "picture",
+      "filepath",
+      "remark"
+    ],
+  },
+  show: {
+    parameters: {
+      params: ["!id"],
+    },
+    service: "fetch",
+  },
+  index: {
+    parameters: {
+      query: {
+        dock_id:"dock_id",
+        title:"%title%",
+        origin:"origin",
+        "publish_time@start":"publish_time@start",
+        "publish_time@end":"publish_time@end",
+        "create_time@start": "create_time@start",
+        "create_time@end": "create_time@end",
+      },
+      // options: {
+      //   "meta.state": 0 // 默认条件
+      // },
+    },
+    service: "query",
+    options: {
+      query: ["skip", "limit"],
+      sort: ["meta.createdAt"],
+      desc: true,
+      count: true,
+    },
+  },
+};

+ 13 - 0
app/controller/admin.js

@@ -0,0 +1,13 @@
+'use strict';
+const meta = require('./.admin.js');
+const Controller = require('egg').Controller;
+const { CrudController } = require('naf-framework-mongoose/lib/controller');
+
+// 管理员
+class AdminController extends Controller {
+  constructor(ctx) {
+    super(ctx);
+    this.service = this.ctx.service.admin;
+  }
+}
+module.exports = CrudController(AdminController, meta);

+ 17 - 0
app/controller/expert.js

@@ -0,0 +1,17 @@
+'use strict';
+const meta = require('./.expert.js');
+const Controller = require('egg').Controller;
+const { CrudController } = require('naf-framework-mongoose/lib/controller');
+
+// 专家
+class ExpertController extends Controller {
+  constructor(ctx) {
+    super(ctx);
+    this.service = this.ctx.service.expert;
+  }
+  // async index() {
+  //   const { data, total } = await this.service.query(this.ctx.query);
+  //   this.ctx.ok({ data, total });
+  // }
+}
+module.exports = CrudController(ExpertController, meta);

+ 16 - 0
app/controller/patent.js

@@ -0,0 +1,16 @@
+'use strict';
+
+const _ = require('lodash');
+const meta = require('./.patent.js');
+const Controller = require('egg').Controller;
+const { CrudController } = require('naf-framework-mongoose/lib/controller');
+
+// 专利表
+class PatentController extends Controller {
+  constructor(ctx) {
+    super(ctx);
+    this.service = this.ctx.service.patent;
+  }
+}
+
+module.exports = CrudController(PatentController, meta);

+ 17 - 0
app/controller/product.js

@@ -0,0 +1,17 @@
+'use strict';
+const meta = require('./.product.js');
+const Controller = require('egg').Controller;
+const { CrudController } = require('naf-framework-mongoose/lib/controller');
+
+// 产品
+class ProductController extends Controller {
+  constructor(ctx) {
+    super(ctx);
+    this.service = this.ctx.service.product;
+  }
+  // async index() {
+  //   const { data, total } = await this.service.query(this.ctx.query);
+  //   this.ctx.ok({ data, total });
+  // }
+}
+module.exports = CrudController(ProductController, meta);

+ 13 - 0
app/controller/road_show.js

@@ -0,0 +1,13 @@
+'use strict';
+const meta = require('./.road_show.js');
+const Controller = require('egg').Controller;
+const { CrudController } = require('naf-framework-mongoose/lib/controller');
+
+// 项目路演
+class Road_showController extends Controller {
+  constructor(ctx) {
+    super(ctx);
+    this.service = this.ctx.service.roadShow;
+  }
+}
+module.exports = CrudController(Road_showController, meta);

+ 22 - 0
app/model/admin.js

@@ -0,0 +1,22 @@
+'use strict';
+const Schema = require('mongoose').Schema;
+const moment = require('moment');
+const metaPlugin = require('naf-framework-mongoose/lib/model/meta-plugin');
+const { ObjectId } = require('mongoose').Types;
+const { Secret } = require('naf-framework-mongoose/lib/model/schema');
+// 管理员表
+const admin = {
+  name: { type: String }, // 名称
+  phone: { type: String }, // 手机
+  passwd: { type: Secret, select: false }, // 注册密码
+  remark: { type: String },
+  create_time: { type: String, default: moment(new Date()).format('YYYY-MM-DD HH:mm:ss') },
+};
+const schema = new Schema(admin, { toJSON: { virtuals: true } });
+schema.index({ id: 1 });
+schema.index({ 'meta.createdAt': 1 });
+schema.plugin(metaPlugin);
+module.exports = app => {
+  const { mongoose } = app;
+  return mongoose.model('Admin', schema, 'admin');
+};

+ 48 - 0
app/model/expert.js

@@ -0,0 +1,48 @@
+'use strict';
+const Schema = require('mongoose').Schema;
+const moment = require('moment');
+const metaPlugin = require('naf-framework-mongoose/lib/model/meta-plugin');
+const { Secret } = require('naf-framework-mongoose/lib/model/schema');
+const { ObjectId } = require('mongoose').Types;
+
+// 专家表
+const expert = {
+  user_id: { type: ObjectId }, // 关联的personal的id
+  // user
+  name: { type: String, required: true }, // 用户名
+  phone: { type: String, required: false, maxLength: 200 }, // 电话号码
+  addr: { type: String, required: false, maxLength: 500 }, // 地址
+  office_phone: { type: String, required: false, maxLength: 500 }, // 办公电话
+  profession: { type: String, required: false, maxLength: 500 }, // 所属行业
+
+  education: { type: String, required: false, maxLength: 200 }, // 最高学历
+  school: { type: String, required: false, maxLength: 200 }, // 毕业院校
+  birthDate: { type: String, required: false, maxLength: 200 }, // 出生日期
+  qqwx: { type: String, required: false, maxLength: 200 }, // qq&微信
+  email: { type: String, required: false, maxLength: 200 }, // 邮箱
+  company: { type: String, required: false, maxLength: 500 }, // 单位名称
+  zwzc: { type: String, required: false, maxLength: 200 }, // 职务职称
+  expertise: { type: String, required: false, maxLength: 200 }, // 擅长领域
+  img_path: { type: String, required: false }, // 头像图片
+  workexperience: { type: String, required: false, maxLength: 500 }, // 工作经历
+  scientific: { type: String, required: false, maxLength: 300 }, // 科研综述
+  undertakingproject: { type: String, required: false, maxLength: 200 }, // 承担项目
+  scienceaward: { type: String, required: false, maxLength: 200 }, // 科技奖励
+  social: { type: String, required: false, maxLength: 200 }, // 社会任职
+  // status: { type: String, required: false, default: '0', maxLength: 200 }, // 审核状态,0-注册,1-通过,2-拒绝
+
+  isdel: { type: String, required: false, default: '0' }, // 0=>未删除;1=>已删除
+  remark: { type: String, maxLength: 200 },
+  create_time: { type: String, default: moment().format('YYYY-MM-DD HH:mm:ss') },
+};
+const schema = new Schema(expert, { toJSON: { virtuals: true } });
+schema.index({ id: 1 });
+schema.index({ phone: 1 });
+schema.index({ code: 1 });
+schema.index({ status: 1 });
+schema.index({ 'meta.createdAt': 1 });
+schema.plugin(metaPlugin);
+module.exports = app => {
+  const { mongoose } = app;
+  return mongoose.model('Expert', schema, 'expert');
+};

+ 1 - 1
app/model/news.js

@@ -12,7 +12,7 @@ const news = {
   origin: { type: String }, // 来源
   content: { type: String }, // 内容
   image: { type: Array }, // 图片
-  fileUrl: { type: String }, // 附件
+  fileUrl: { type: Array }, // 附件
 
   remark: { type: String },
   create_time: { type: String, default: moment(new Date()).format('YYYY-MM-DD HH:mm:ss') },

+ 31 - 0
app/model/patent.js

@@ -0,0 +1,31 @@
+'use strict';
+const Schema = require('mongoose').Schema;
+const metaPlugin = require('naf-framework-mongoose/lib/model/meta-plugin');
+// 专利表
+const PatentSchema = {
+  create_number: { type: String, required: false }, // 申请号
+  create_date: { type: String, required: false }, // 申请日
+  success_number: { type: String, required: false }, // 公开(公告)号
+  success_date: { type: String, required: false }, //  公开(公告)日
+  name: { type: String, required: false }, // 标题
+  inventor: { type: String, required: false }, // 发明人
+  address: { type: String, required: false }, // 发明人地址
+  apply_personal: { type: String, required: false }, // 申请人
+  term: { type: String, required: false }, // 专利有效性
+  type: { type: String, required: false }, // 专利类型
+  agent_personal: { type: String, required: false }, // 代理人
+  agent: { type: String, required: false }, // 代理机构
+  abstract: { type: String, required: false }, // 摘要
+  img_url: { type: Array, required: false }, // 图片
+  origin: { type: String }, // 数据来源(手写的)
+};
+
+const schema = new Schema(PatentSchema, { toJSON: { virtuals: true } });
+schema.index({ id: 1 });
+schema.index({ 'meta.createdAt': 1 });
+schema.plugin(metaPlugin);
+
+module.exports = app => {
+  const { mongoose } = app;
+  return mongoose.model('Patent', schema, 'patent');
+};

+ 71 - 0
app/model/product.js

@@ -0,0 +1,71 @@
+'use strict';
+const Schema = require('mongoose').Schema;
+const moment = require('moment');
+const metaPlugin = require('naf-framework-mongoose/lib/model/meta-plugin');
+// 产品图片表
+const file = new Schema({
+  name: { type: String, required: true, maxLength: 500 }, // 图片名
+  url: { type: String, required: true, maxLength: 500 }, // 图片路径
+});
+// 专利信息
+const patents = new Schema({
+  patentinfo: { type: String, required: false, maxLength: 200 }, // 专利信息,
+  patentstatus: { type: String, required: false, maxLength: 200 }, // 专利状态,
+});
+// 产品表
+const product = {
+  name: { type: String, required: false, maxLength: 200 }, // 名称
+  contacts: { type: String, required: false, maxLength: 200 }, // 联系人
+  phone: { type: String, required: false, maxLength: 11 }, // 联系电话
+  qqwx: { type: String, required: false, maxLength: 200 }, // qq&微信
+  email: { type: String, required: false, maxLength: 200 }, // 邮箱
+  type: { type: String, required: false, maxLength: 200 }, // 类型: 0-科技需求;1-技术成果;2-商务服务
+  status: { type: String, required: false, maxLength: 200, default: '0' }, // 状态(0:草稿 1:审核中 2:审核通过 3:审核拒绝)
+  user_id: { type: String, required: false, maxLength: 500 }, // 创建人id
+  // 共同字段
+  field: { type: String, required: false, maxLength: 500 }, // 所属领域
+  cooperation: { type: String, required: false, maxLength: 500 }, // 合作方式
+  company: { type: String, required: false, maxLength: 500 }, // 企业名称
+  condition: { type: String, required: false, maxLength: 500 }, // 合作条件及要求
+  image: { type: [ file ] }, // 图片,产品图片都为此字段
+  expect: { type: String, required: false, maxLength: 500 }, // 预期, 所有的预期都合并为此字段
+  demand: { type: String, required: false, maxLength: 200 }, // 需求程度:技术的需求紧急程度和服务的需求程度改为此字段
+
+  // 技术需求字段
+  budget: { type: String, required: false, maxLength: 300 }, // 投资预算
+  requirementdesc: { type: String, required: false, maxLength: 500 }, // 需求说明
+  present: { type: String, required: false, maxLength: 500 }, // 需求现状
+
+  // 技术成果字段
+  achievestatus: { type: String, required: false, maxLength: 200 }, // 成果状态
+  achieveown: { type: String, required: false, maxLength: 200 }, // 成果权属
+  achievesource: { type: String, required: false, maxLength: 200 }, // 成果来源
+  intentionprice: { type: String, required: false, maxLength: 200 }, // 意向价格
+  patent: { type: [ patents ] },
+  roadshow: { type: Array, required: false, maxLength: 200 }, // 项目路演
+  achievebrief: { type: String, required: false, maxLength: 500 }, // 成果简介
+  features: { type: String, required: false, maxLength: 500 }, // 技术特点
+  team: { type: String, required: false, maxLength: 500 }, // 技术团队
+
+  // 商务需求
+  messattribute: { type: String, required: false, maxLength: 200 }, // 信息属性
+  informationdesc: { type: String, required: false, maxLength: 500 }, // 信息描述
+  coreelements: { type: String, required: false, maxLength: 500 }, // 核心要素
+  priceinfo: { type: String, required: false, maxLength: 500 }, // 价格信息
+
+  remark: { type: String, maxLength: 200 },
+  create_time: { type: String, default: moment().format('YYYY-MM-DD HH:mm:ss') },
+};
+const schema = new Schema(product, { toJSON: { virtuals: true } });
+schema.index({ id: 1 });
+schema.index({ name: 1 });
+schema.index({ qqwx: 1 });
+schema.index({ type: 1 });
+schema.index({ status: 1 });
+schema.index({ company: 1 });
+schema.index({ 'meta.createdAt': 1 });
+schema.plugin(metaPlugin);
+module.exports = app => {
+  const { mongoose } = app;
+  return mongoose.model('Product', schema, 'product');
+};

+ 32 - 0
app/model/road_show.js

@@ -0,0 +1,32 @@
+'use strict';
+const Schema = require('mongoose').Schema;
+const moment = require('moment');
+const metaPlugin = require('naf-framework-mongoose/lib/model/meta-plugin');
+const { Secret } = require('naf-framework-mongoose/lib/model/schema');
+const { ObjectId } = require('mongoose').Types;
+// 项目路演表
+const road_show = {
+  user_id: { type: ObjectId },
+  dock_id: { type: ObjectId }, // 展会id(暂不用)
+  title: { type: String, required: false, maxLength: 500 }, // 标题
+  brief: { type: String, maxLength: 100 }, // 简介
+  origin: { type: String, required: false, maxLength: 500, default: '网站管理员' }, // 来源
+  publish_time: { type: String, required: false, maxLength: 500 }, // 发布时间
+  content: { type: String, required: false }, // 正文
+  picture: { type: String, required: false }, // 图片路径
+  filepath: { type: String, required: false }, // 文件路径
+  remark: { type: String, maxLength: 200 },
+  create_time: { type: String, default: moment().format('YYYY-MM-DD HH:mm:ss') },
+};
+const schema = new Schema(road_show, { toJSON: { virtuals: true } });
+schema.index({ id: 1 });
+schema.index({ dock_id: 1 });
+schema.index({ title: 1 });
+schema.index({ origin: 1 });
+schema.index({ publish_time: 1 });
+schema.index({ 'meta.createdAt': 1 });
+schema.plugin(metaPlugin);
+module.exports = app => {
+  const { mongoose } = app;
+  return mongoose.model('Road_show', schema, 'road_show');
+};

+ 5 - 0
app/router.js

@@ -7,4 +7,9 @@ module.exports = app => {
   const { router, controller } = app;
   router.get('/', controller.home.index);
   require('./router/news')(app); // 新闻
+  require('./router/product')(app); // 产品
+  require('./router/patent')(app); // 专利
+  require('./router/road_show')(app); // 路演
+  require('./router/expert')(app); // 专家
+  require('./router/admin')(app); // 管理员
 };

+ 11 - 0
app/router/admin.js

@@ -0,0 +1,11 @@
+'use strict';
+
+
+module.exports = app => {
+  const { router, controller } = app;
+  const prefix = 'admin';
+  router.post(prefix, `/${prefix}/login`, controller[prefix].login);
+  router.post(prefix, `/${prefix}/password/:id`, controller[prefix].password);
+  router.resources(prefix, `/${prefix}`, controller[prefix]); // index、create、show、destroy
+  router.post(prefix, `/${prefix}/update/:id`, controller[prefix].update);
+};

+ 9 - 0
app/router/expert.js

@@ -0,0 +1,9 @@
+'use strict';
+
+
+module.exports = app => {
+  const { router, controller } = app;
+  const prefix = 'expert';
+  router.resources(prefix, `/${prefix}`, controller[prefix]); // index、create、show、destroy
+  router.post(prefix, `/${prefix}/update/:id`, controller[prefix].update);
+};

+ 9 - 0
app/router/patent.js

@@ -0,0 +1,9 @@
+'use strict';
+
+
+module.exports = app => {
+  const { router, controller } = app;
+  const prefix = 'product';
+  router.resources(prefix, `/${prefix}`, controller[prefix]); // index、create、show、destroy
+  router.post(prefix, `/${prefix}/update/:id`, controller[prefix].update);
+};

+ 9 - 0
app/router/product.js

@@ -0,0 +1,9 @@
+'use strict';
+
+
+module.exports = app => {
+  const { router, controller } = app;
+  const prefix = 'patent';
+  router.resources(prefix, `/${prefix}`, controller[prefix]); // index、create、show、destroy
+  router.post(prefix, `/${prefix}/update/:id`, controller[prefix].update);
+};

+ 9 - 0
app/router/road_show.js

@@ -0,0 +1,9 @@
+'use strict';
+
+
+module.exports = app => {
+  const { router, controller } = app;
+  const prefix = 'roadShow';
+  router.resources(prefix, `/${prefix}`, controller[prefix]); // index、create、show、destroy
+  router.post(prefix, `/${prefix}/update/:id`, controller[prefix].update);
+};

+ 58 - 0
app/service/admin.js

@@ -0,0 +1,58 @@
+'use strict';
+const { CrudService } = require('naf-framework-mongoose/lib/service');
+const { BusinessError, ErrorCode } = require('naf-core').Error;
+const { ObjectId } = require('mongoose').Types;
+const _ = require('lodash');
+const jwt = require('jsonwebtoken');
+
+
+// 管理员
+class AdminService extends CrudService {
+  constructor(ctx) {
+    super(ctx, 'admin');
+    this.model = this.ctx.model.Admin;
+  }
+  /**
+   * 创建用户
+   * @param {Object} params 用户信息
+   */
+  async create({ passwd, ...data }) {
+    data.passwd = { secret: passwd };
+    const { phone } = data;
+    // 检查手机号
+    const num = await this.model.count({ phone });
+    if (num > 0) throw new BusinessError(ErrorCode.DATA_EXISTED, '已有管理员');
+    const res = await this.model.create(data);
+    return res;
+  }
+  /**
+   * 修改密码
+   * @param {Object} {id,passwd} 用户id和密码
+   */
+  async password({ id, passwd }) {
+    const object = await this.model.findById(id);
+    if (!object) throw new BusinessError(ErrorCode.DATA_NOT_EXIST, '未找到用户的信息');
+    object.passwd = { secret: passwd };
+    await object.save();
+  }
+  /**
+   * 管理员登陆
+   * @param {Object} params 登陆信息
+   * @property code_phone code或者是phone
+   * @property passwd 密码
+   */
+  async login({ code_phone, passwd }) {
+    const object = await this.model.findOne({ $or: [{ code: code_phone }, { phone: code_phone }] }, '+passwd');
+    if (!object) throw new BusinessError(ErrorCode.DATA_NOT_EXIST, '未找到用户的信息');
+    const { passwd: op } = object;
+    const { secret } = op;
+    if (secret !== passwd) throw new BusinessError(ErrorCode.BAD_PASSWORD, '密码错误');
+    const data = _.omit(JSON.parse(JSON.stringify(object)), [ 'meta', 'passwd', '__v' ]);
+    const { secret: secrets } = this.config.jwt;
+    const token = jwt.sign(data, secrets);
+    return token;
+  }
+
+}
+
+module.exports = AdminService;

+ 15 - 0
app/service/expert.js

@@ -0,0 +1,15 @@
+'use strict';
+const { CrudService } = require('naf-framework-mongoose/lib/service');
+const { BusinessError, ErrorCode } = require('naf-core').Error;
+const _ = require('lodash');
+const assert = require('assert');
+
+// 专家
+class ExpertService extends CrudService {
+  constructor(ctx) {
+    super(ctx, 'expert');
+    this.model = this.ctx.model.Expert;
+  }
+}
+
+module.exports = ExpertService;

+ 16 - 0
app/service/patent.js

@@ -0,0 +1,16 @@
+'use strict';
+
+const assert = require('assert');
+const moment = require('moment');
+const { CrudService } = require('naf-framework-mongoose/lib/service');
+const { BusinessError, ErrorCode } = require('naf-core').Error;
+
+class PatentService extends CrudService {
+  constructor(ctx) {
+    super(ctx, 'patent');
+    this.model = this.ctx.model.Patent;
+  }
+
+}
+
+module.exports = PatentService;

+ 84 - 0
app/service/product.js

@@ -0,0 +1,84 @@
+'use strict';
+const { CrudService } = require('naf-framework-mongoose/lib/service');
+const { ObjectId } = require('mongoose').Types;
+// 产品
+class ProductService extends CrudService {
+  constructor(ctx) {
+    super(ctx, 'product');
+    this.model = this.ctx.model.Product;
+  }
+  // async query({ skip = 0, limit = 0, ...query } = {}) {
+  //   if (query.name) {
+  //     query['%name%'] = query.name;
+  //     delete query.name;
+  //   }
+  //   query = this.ctx.service.util.util.dealQuery(query);
+  //   const { code, company, ...oq } = query;
+  //   let res = [];
+  //   let total = 0;
+  //   if (!code) {
+  //     if (!company) {
+  //       res = await this.model.find(query).skip(parseInt(skip)).limit(parseInt(limit));
+  //       total = await this.model.count(query);
+  //     } else {
+  //     // 处理company特殊的情况
+  //       let nquery = {};
+  //       if (company === '中科系') nquery.company = [ '中科院长春分院', '中国科学院东北地理与农业生态研究所', '中国科学院长春应用化学研究所', '中科院长春光学精密机械与物理研究所' ];
+  //       else if (company === '其他')nquery.company = { $nin: [ '中科院长春分院', '中国科学院东北地理与农业生态研究所', '中国科学院长春应用化学研究所', '中科院长春光学精密机械与物理研究所', '吉林大学', '长春工业大学' ] };
+  //       else nquery.company = company;
+  //       nquery = { ...oq, ...nquery };
+  //       res = await this.model.find(nquery).skip(parseInt(skip)).limit(parseInt(limit));
+  //       total = await this.model.count(nquery);
+  //     }
+
+  //   } else {
+  //     // 使用code查出个人,专家,机构下的产品,skip和limit限制的是最后产品,而不是角色那部分
+  //     let pl = await this.personal.find({ code }, '_id');
+  //     if (pl.length > 0)pl = JSON.parse(JSON.stringify(pl));
+  //     let el = await this.expert.find({ code }, '_id');
+  //     if (el.length > 0)el = JSON.parse(JSON.stringify(el));
+  //     let ol = await this.organization.find({ code }, '_id');
+  //     if (ol.length > 0)ol = JSON.parse(JSON.stringify(ol));
+  //     const ids = pl.map(i => i._id).concat(el.map(i => i._id).concat(ol.map(i => i._id)));
+  //     if (ids.length > 0) {
+  //       res = await this.model.find({ ...oq, user_id: ids }).skip(parseInt(skip)).limit(parseInt(limit));
+  //       total = await this.model.count({ ...oq, user_id: ids });
+  //     }
+  //   }
+  //   return { data: res, total };
+  // }
+
+  async indexQuery() {
+    // product,limit=>6;status=>2;type=>0/1/2
+    // 科技需求
+    const require = await this.getSample('model', 6, { type: '0', status: '2' });
+    // 技术成果
+    const achieve = await this.getSample('model', 6, { type: '1', status: '2' });
+    // 商务服务
+    const serve = await this.getSample('model', 5, { type: '2', status: '2' });
+    // 专利:patent limit=>6
+    const patent = await this.getSample('patent');
+    // 专家:expert:limit=>8
+    const expert = await this.getSample('expert', 8);
+    // 专家需要姓名
+    const ids = expert.map(i => i.user_id);
+    const personal = await this.personal.find({ _id: ids }, 'name');
+    for (const exp of expert) {
+      const r = await personal.find(f => ObjectId(f._id).equals(exp.user_id));
+      if (r) exp.name = r.name;
+    }
+    // 路演:roadShow:limit=>5
+    const roadShow = await this.getSample('roadShow', 5);
+    return { require, achieve, serve, patent, expert, roadShow };
+  }
+
+  async getSample(model, limit = 6, match = {}) {
+    const res = await this[model].aggregate([
+      { $match: match },
+      { $sample: { size: parseInt(limit) } },
+    ]);
+    return res;
+  }
+}
+
+module.exports = ProductService;

+ 16 - 0
app/service/road_show.js

@@ -0,0 +1,16 @@
+'use strict';
+const { CrudService } = require('naf-framework-mongoose/lib/service');
+const { BusinessError, ErrorCode } = require('naf-core').Error;
+const { ObjectId } = require('mongoose').Types;
+const _ = require('lodash');
+const assert = require('assert');
+
+// 项目路演
+class Road_showService extends CrudService {
+  constructor(ctx) {
+    super(ctx, 'road_show');
+    this.model = this.ctx.model.RoadShow;
+  }
+}
+
+module.exports = Road_showService;

+ 6 - 0
config/config.default.js

@@ -1,6 +1,7 @@
 /* eslint valid-jsdoc: "off" */
 
 'use strict';
+const { jwt } = require('./config.secret');
 
 /**
  * @param {Egg.EggAppInfo} appInfo app info
@@ -22,6 +23,11 @@ module.exports = appInfo => {
   const userConfig = {
     // myAppName: 'egg',
   };
+  config.jwt = {
+    ...jwt,
+    expiresIn: '1d',
+    issuer: 'test',
+  };
   config.cluster = {
     listen: {
       port: 9201,

+ 7 - 0
config/config.secret.js

@@ -0,0 +1,7 @@
+'use strict';
+
+module.exports = {
+  jwt: {
+    secret: 'Ziyouyanfa!@#',
+  },
+};

+ 2 - 1
package.json

@@ -8,9 +8,10 @@
   },
   "dependencies": {
     "egg": "^2.15.1",
-    "egg-scripts": "^2.11.0",
     "egg-naf-amqp": "0.0.13",
     "egg-redis": "^2.4.0",
+    "egg-scripts": "^2.11.0",
+    "jsonwebtoken": "^8.5.1",
     "lodash": "^4.17.15",
     "moment": "^2.24.0",
     "naf-framework-mongoose": "^0.6.11"