// 开发合同.docx 生成脚本
// 标准 Word 排版：A4、宋体、清晰的层级
const {
  Document, Packer, Paragraph, TextRun, Table, TableRow, TableCell,
  AlignmentType, HeadingLevel, BorderStyle, WidthType, ShadingType,
  PageNumber, Footer, Header, LevelFormat
} = require('docx');
const fs = require('fs');

// 边框样式
const noBorder = { style: BorderStyle.NONE, size: 0, color: "FFFFFF" };
const tableBorders = {
  top: { style: BorderStyle.SINGLE, size: 6, color: "000000" },
  bottom: { style: BorderStyle.SINGLE, size: 6, color: "000000" },
  left: { style: BorderStyle.SINGLE, size: 6, color: "000000" },
  right: { style: BorderStyle.SINGLE, size: 6, color: "000000" },
  insideHorizontal: { style: BorderStyle.SINGLE, size: 4, color: "000000" },
  insideVertical: { style: BorderStyle.SINGLE, size: 4, color: "000000" },
};

// 标题段落（一级）
function h1(text) {
  return new Paragraph({
    heading: HeadingLevel.HEADING_1,
    spacing: { before: 360, after: 200 },
    children: [new TextRun({ text, bold: true, size: 32, font: "SimSun" })],
  });
}

// 标题段落（二级）
function h2(text) {
  return new Paragraph({
    heading: HeadingLevel.HEADING_2,
    spacing: { before: 240, after: 120 },
    children: [new TextRun({ text, bold: true, size: 28, font: "SimSun" })],
  });
}

// 正文段落
function p(text, opts = {}) {
  return new Paragraph({
    spacing: { line: 360, before: 80, after: 80, lineRule: "auto" },
    alignment: opts.align || AlignmentType.JUSTIFIED,
    indent: opts.indent ? { firstLine: opts.indent } : undefined,
    children: [new TextRun({ text, size: 24, font: "SimSun" })],
  });
}

// 粗体段落
function pBold(text, opts = {}) {
  return new Paragraph({
    spacing: { line: 360, before: 80, after: 80, lineRule: "auto" },
    alignment: opts.align || AlignmentType.LEFT,
    children: [new TextRun({ text, bold: true, size: 24, font: "SimSun" })],
  });
}

// 空行
function empty() {
  return new Paragraph({ children: [new TextRun({ text: "" })] });
}

// 居中粗体大标题
function bigTitle(text) {
  return new Paragraph({
    alignment: AlignmentType.CENTER,
    spacing: { before: 200, after: 400 },
    children: [new TextRun({ text, bold: true, size: 44, font: "SimHei" })],
  });
}

// 表格单元格
function cell(text, opts = {}) {
  return new TableCell({
    borders: tableBorders,
    width: { size: opts.width || 2000, type: WidthType.DXA },
    shading: opts.header ? { fill: "E7E6E6", type: ShadingType.CLEAR, color: "auto" } : undefined,
    margins: { top: 100, bottom: 100, left: 120, right: 120 },
    children: [new Paragraph({
      alignment: opts.align || AlignmentType.LEFT,
      spacing: { line: 300, before: 0, after: 0 },
      children: [new TextRun({
        text: String(text),
        bold: !!opts.header,
        size: 24,
        font: "SimSun",
      })],
    })],
  });
}

// 创建表格
function makeTable(rows, colWidths) {
  return new Table({
    width: { size: colWidths.reduce((a, b) => a + b, 0), type: WidthType.DXA },
    columnWidths: colWidths,
    rows: rows.map((row, i) => new TableRow({
      children: row.map((text, j) => cell(text, { width: colWidths[j], header: i === 0 })),
    })),
  });
}

// ==================== 内容 ====================

const children = [];

// 大标题
children.push(bigTitle("36仓体直流电瓶车充电柜"));
children.push(bigTitle("开发合同"));

// 合同信息
children.push(p("合同编号：_______________", { align: AlignmentType.LEFT }));
children.push(p("签订地点：_______________", { align: AlignmentType.LEFT }));
children.push(p("签订日期：______年______月______日", { align: AlignmentType.LEFT }));
children.push(empty());

// 第一条
children.push(h1("第一条  合同双方"));
children.push(pBold("甲方（委托方）："));
children.push(p("公司名称：____________________________________"));
children.push(p("法定代表人：________________"));
children.push(p("地址：____________________________________"));
children.push(p("联系人：________________  联系电话：________________"));
children.push(empty());
children.push(pBold("乙方（开发方）："));
children.push(p("公司名称：____________________________________"));
children.push(p("法定代表人：________________"));
children.push(p("地址：____________________________________"));
children.push(p("联系人：________________  联系电话：________________"));

// 第二条
children.push(h1("第二条  项目概述"));
children.push(p("1. 项目名称：36仓体直流电瓶车充电柜开发项目。"));
children.push(p("2. 项目目标：开发充电柜配套的柜控主板、仓控主板、嵌入式固件、后台管理系统及微信小程序。"));
children.push(p("3. 开发周期：合同生效后12周。"));
children.push(p("4. 交付成果：详见第五条及附件。"));

// 第三条
children.push(h1("第三条  开发内容"));
children.push(makeTable(
  [
    ["序号", "开发内容", "详见附件"],
    ["1", "柜控主板硬件设计开发", "附件一"],
    ["2", "仓控主板硬件设计开发", "附件一"],
    ["3", "嵌入式固件开发（柜控板+仓控板）", "附件一"],
    ["4", "后台管理系统开发", "附件二"],
    ["5", "微信小程序开发", "附件二"],
    ["6", "通讯协议栈开发实现", "附件三"],
  ],
  [1000, 5360, 3000]
));
children.push(empty());
children.push(p("乙方负责主板设计、元器件采购、焊接调试及联调支持。柜体、电源及外部器件由甲方提供。本合同不交付任何源代码。"));

// 第四条
children.push(h1("第四条  开发阶段"));
children.push(makeTable(
  [
    ["阶段", "时间", "交付物"],
    ["M1 方案定稿", "第1-2周", "原理图、PCB、BOM、协议文档"],
    ["M2 开发完成", "第3-6周", "硬件样板、固件、后台、小程序"],
    ["M3 联调完成", "第7-9周", "集成测试报告"],
    ["M4 验收交付", "第10-12周", "完整成品、技术文档"],
  ],
  [2500, 2000, 4860]
));
children.push(empty());
children.push(p("付款方式：______________________________________________________________________"));

// 第五条
children.push(h1("第五条  交付与验收"));
children.push(p("交付物清单及验收标准详见附件三。整机验收时乙方到甲方现场完成联调，验收所需柜体及电源由甲方提供。"));

// 第六条
children.push(h1("第六条  知识产权"));
children.push(p("1. 乙方在本合同履行过程中产生的全部技术成果（包括但不限于源代码、设计图纸、技术文档等）的知识产权归甲乙双方共同所有。"));
children.push(p("2. 任何一方均有权在自身业务范围内自由使用上述技术成果，无需征得另一方同意或另行支付费用。"));

// 第七条
children.push(h1("第七条  保密条款"));
children.push(p("1. 双方对合同履行过程中知悉的对方商业秘密、技术秘密负有保密义务。"));
children.push(p("2. 保密期限自合同生效之日起3年。"));
children.push(p("3. 未经对方书面同意，不得向第三方披露任何与本合同相关的信息。"));

// 第八条
children.push(h1("第八条  质保与维护"));
children.push(p("1. 硬件质保期自验收通过之日起12个月，质保期内免费维修或更换。"));
children.push(p("2. 软件质保期自验收通过之日起6个月，质保期内免费修复Bug。"));
children.push(p("3. 质保期外的维护服务费用由双方另行协商。"));

// 第九条
children.push(h1("第九条  违约责任"));
children.push(p("1. 甲方逾期付款的，每逾期一日按应付未付金额的千分之三支付违约金。"));
children.push(p("2. 乙方逾期交付的，每逾期一日按合同总金额的千分之三支付违约金。"));
children.push(p("3. 任何一方违反知识产权或保密条款的，应赔偿对方全部损失。"));

// 第十条
children.push(h1("第十条  合同总金额"));
children.push(p("合同总金额：人民币____________元（大写：__________________________）。"));

// 第十一条
children.push(h1("第十一条  争议解决"));
children.push(p("本合同履行过程中发生争议的，双方应协商解决；协商不成的，提交合同签订地人民法院诉讼解决。"));

// 第十二条
children.push(h1("第十二条  其他"));
children.push(p("1. 本合同一式两份，甲乙双方各执一份，具有同等法律效力。"));
children.push(p("2. 本合同附件为合同的组成部分，与本合同具有同等法律效力。"));
children.push(p("3. 未尽事宜，双方可另行签订补充协议。"));

// 签章区
children.push(empty());
children.push(empty());
children.push(pBold("甲方（盖章）：__________________________"));
children.push(p("授权代表签字：________________________"));
children.push(p("日期：______年______月______日"));
children.push(empty());
children.push(pBold("乙方（盖章）：__________________________"));
children.push(p("授权代表签字：________________________"));
children.push(p("日期：______年______月______日"));

// ==================== 生成文档 ====================

const doc = new Document({
  creator: "CodeBuddy",
  title: "36仓体直流电瓶车充电柜开发合同",
  styles: {
    default: {
      document: { run: { font: "SimSun", size: 24 } },
    },
    paragraphStyles: [
      {
        id: "Heading1", name: "Heading 1", basedOn: "Normal", next: "Normal", quickFormat: true,
        run: { size: 32, bold: true, font: "SimHei" },
        paragraph: { spacing: { before: 360, after: 200 }, outlineLevel: 0 },
      },
      {
        id: "Heading2", name: "Heading 2", basedOn: "Normal", next: "Normal", quickFormat: true,
        run: { size: 28, bold: true, font: "SimHei" },
        paragraph: { spacing: { before: 240, after: 120 }, outlineLevel: 1 },
      },
    ],
  },
  sections: [{
    properties: {
      page: {
        size: { width: 11906, height: 16838 }, // A4
        margin: { top: 1440, right: 1440, bottom: 1440, left: 1440 },
      },
    },
    footers: {
      default: new Footer({
        children: [new Paragraph({
          alignment: AlignmentType.CENTER,
          children: [
            new TextRun({ text: "第 ", size: 20, font: "SimSun" }),
            new TextRun({ children: [PageNumber.CURRENT], size: 20, font: "SimSun" }),
            new TextRun({ text: " 页 / 共 ", size: 20, font: "SimSun" }),
            new TextRun({ children: [PageNumber.TOTAL_PAGES], size: 20, font: "SimSun" }),
            new TextRun({ text: " 页", size: 20, font: "SimSun" }),
          ],
        })],
      }),
    },
    children,
  }],
});

Packer.toBuffer(doc).then(buffer => {
  fs.writeFileSync("开发合同.docx", buffer);
  console.log("OK: 开发合同.docx 已生成 (" + buffer.length + " bytes)");
});
