Source snapshot: 97d7f0fae96dc04b7ddad56fc1db6a108ed662cc [SEC-CLEAN] · pre-push-clean v1.0 · 109处敏感信息已自动转乱码
20 KiB
📡 BC-M-AUTH-002-XX · DEV-013小兴 · M-AUTH注册登录系统 · 环节2 · 前端交互逻辑+表单验证+LocalStorage · 🧊 霜砚直接协作线 · EL-3
📡 广播头
| 字段 | 值 |
|---|---|
| 广播编号 | BC-M-AUTH-002-XX |
| 签发时间 | 2026-03-17 17:09(北京时间) |
| 签发方 | 霜砚 × 冰朔(TCS-0002∞) |
| 协议版本 | BC-GEN v5.1 · SYSLOG-v5.0 |
| 执行者 | DEV-013 小兴 |
| 协作通道 | 🧊 霜砚直接协作线(无宝宝) |
| EL等级 | EL-3 · 🌱成长型(~4步 · 纯前端 · 复制粘贴) |
| 模块 | M-AUTH · 注册登录系统 |
| 环节 | 2 · 前端交互逻辑 + 表单验证 + LocalStorage |
| 前置 | BC-M-AUTH-001-XX 环节0/1 ✅ completed · 连胜:1 |
| 有效期 | 72小时 → 截止 2026-03-20 17:09(北京时间) |
🔐 VERSION_GATE
cd C:\Users\许\guanghulab
git pull origin main
Write-Host "✅ 已更新到最新!" -ForegroundColor Green
✅ 看到
Already up to date.或拉取成功 → 继续
❌ 报错 → 截图发给霜砚
🖥️ 执行环境
| 项目 | 值 |
|---|---|
| 操作系统 | Windows 11 |
| 终端 | PowerShell |
| 技术栈 | 纯 HTML + CSS + JavaScript(无框架) |
| 开发者水平 | 零基础 · 复制粘贴操作 |
| AI辅助平台 | 元宝(推荐) |
| 仓库 | https://github.com/qinfendebingshuo/guanghulab |
| 模块目录 | modules/m-auth/ |
| 本地路径 | C:\Users\许\guanghulab |
🎯 任务目标(一句话)
让登录/注册真正能用:加上错误提示、记住用户、登录后跳转到欢迎页。用户注册账号后,下次打开还在。
💬 霜砚开场语
小兴,上次你把登录注册界面一次性做出来了,8步全通,推送成功!连胜1 🔥
这次我们让它真正「活起来」:
- 填错了有提示(不再弹烦人的 alert)
- 注册的账号记住了(关掉浏览器再打开还能登录)
- 登录成功跳到欢迎页(不再只弹提示框)
全程4步 + 推送,都是复制粘贴,你做过一次了,这次会更顺。目标:连胜2 💪
📋 步骤一:更新 index.html(加错误提示位置)
打开 C:\Users\许\guanghulab\modules\m-auth\index.html,全部替换为以下内容:
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>HoloLake Era · 登录注册</title>
<link rel="stylesheet" href="style.css">
</head>
<body>
<div class="container">
<div class="card">
<div class="logo">🌊 HoloLake</div>
<div class="subtitle">语言人格智能平台</div>
<!-- 注册成功提示 -->
<div id="login-success" class="success-msg" style="display:none;"></div>
<!-- 登录表单 -->
<form id="loginForm" class="form-section active">
<h2>登录</h2>
<div class="form-group">
<label for="loginUser">用户名</label>
<input type="text" id="loginUser" placeholder="请输入用户名">
<span id="loginUser-error" class="error-text"></span>
</div>
<div class="form-group">
<label for="loginPass">密码</label>
<input type="password" id="loginPass" placeholder="请输入密码">
<span id="loginPass-error" class="error-text"></span>
</div>
<button type="submit" class="btn">登 录</button>
<p class="switch-text">
还没有账号?<a href="#" id="toRegister">注册一个</a>
</p>
</form>
<!-- 注册表单 -->
<form id="registerForm" class="form-section">
<h2>注册</h2>
<div class="form-group">
<label for="regUser">用户名</label>
<input type="text" id="regUser" placeholder="请输入用户名(至少2个字)">
<span id="regUser-error" class="error-text"></span>
</div>
<div class="form-group">
<label for="regPass">密码</label>
<input type="password" id="regPass" placeholder="请输入密码(至少6位)">
<span id="regPass-error" class="error-text"></span>
</div>
<div class="form-group">
<label for="regPass2">确认密码</label>
<input type="password" id="regPass2" placeholder="再输入一次密码">
<span id="regPass2-error" class="error-text"></span>
</div>
<button type="submit" class="btn">注 册</button>
<p class="switch-text">
已有账号?<a href="#" id="toLogin">去登录</a>
</p>
</form>
</div>
<div class="footer">HoloLake Era · M-AUTH · DEV-013 小兴</div>
</div>
<script src="script.js"></script>
</body>
</html>
保存!截图给霜砚! 📸
📋 步骤二:替换 script.js(真正的交互逻辑)
打开 modules\m-auth\script.js,全部替换为以下内容:
// ========== M-AUTH 登录注册模块 · 环节2 ==========
// DEV-013 小兴 · HoloLake Era · 前端交互逻辑
// ================================================
// === 获取元素 ===
var loginForm = document.getElementById('loginForm');
var registerForm = document.getElementById('registerForm');
var toRegister = document.getElementById('toRegister');
var toLogin = document.getElementById('toLogin');
// === 工具:显示/清除错误 ===
function showError(inputId, message) {
var input = document.getElementById(inputId);
var errorEl = document.getElementById(inputId + '-error');
if (input) input.classList.add('input-error');
if (errorEl) {
errorEl.textContent = message;
errorEl.style.display = 'block';
}
}
function clearError(inputId) {
var input = document.getElementById(inputId);
var errorEl = document.getElementById(inputId + '-error');
if (input) input.classList.remove('input-error');
if (errorEl) errorEl.style.display = 'none';
}
function clearAllErrors() {
var allInputs = ['loginUser','loginPass','regUser','regPass','regPass2'];
allInputs.forEach(function(id) { clearError(id); });
}
// === 切换登录/注册 ===
toRegister.addEventListener('click', function(e) {
e.preventDefault();
clearAllErrors();
loginForm.classList.remove('active');
registerForm.classList.add('active');
});
toLogin.addEventListener('click', function(e) {
e.preventDefault();
clearAllErrors();
registerForm.classList.remove('active');
loginForm.classList.add('active');
});
// === 注册逻辑 ===
registerForm.addEventListener('submit', function(e) {
e.preventDefault();
clearAllErrors();
var username = document.getElementById('regUser').value.trim();
var password = document.getElementById('regPass').value;
var password2 = document.getElementById('regPass2').value;
var hasError = false;
if (username.length < 2) {
showError('regUser', '用户名至少2个字符');
hasError = true;
}
if (password.length < 6) {
showError('regPass', '密码至少6位');
hasError = true;
}
if (password !== password2) {
showError('regPass2', '两次密码不一致');
hasError = true;
}
if (hasError) return;
// 检查用户名是否已存在
var users = JSON.parse(localStorage.getItem('hololake_users') || '[]');
var exists = users.find(function(u) { return u.username === username; });
if (exists) {
showError('regUser', '用户名已被注册,换一个吧');
return;
}
// 保存用户到 LocalStorage
users.push({ username: username, password: password });
localStorage.setItem('hololake_users', JSON.stringify(users));
console.log('[M-AUTH] 注册成功:', username, '· 当前用户数:', users.length);
// 清空注册表单
document.getElementById('regUser').value = '';
document.getElementById('regPass').value = '';
document.getElementById('regPass2').value = '';
// 切换到登录 + 显示成功提示
registerForm.classList.remove('active');
loginForm.classList.add('active');
var successEl = document.getElementById('login-success');
if (successEl) {
successEl.textContent = '✅ 注册成功!请用新账号登录';
successEl.style.display = 'block';
setTimeout(function() { successEl.style.display = 'none'; }, 4000);
}
});
// === 登录逻辑 ===
loginForm.addEventListener('submit', function(e) {
e.preventDefault();
clearAllErrors();
var username = document.getElementById('loginUser').value.trim();
var password = document.getElementById('loginPass').value;
if (!username) { showError('loginUser', '请输入用户名'); return; }
if (!password) { showError('loginPass', '请输入密码'); return; }
// 查找用户
var users = JSON.parse(localStorage.getItem('hololake_users') || '[]');
var user = users.find(function(u) {
return u.username === username && u.password === password;
});
if (!user) {
showError('loginUser', '用户名或密码错误');
return;
}
// 登录成功 → 记录当前用户 → 跳转
localStorage.setItem('hololake_current_user', username);
console.log('[M-AUTH] 登录成功:', username, '→ 跳转 dashboard');
window.location.href = 'dashboard.html';
});
// === HoloLake 全局接口 ===
window.HoloLake = window.HoloLake || {};
window.HoloLake.Auth = {
getUser: function() {
return localStorage.getItem('hololake_current_user');
},
logout: function() {
localStorage.removeItem('hololake_current_user');
window.location.href = 'index.html';
},
init: function() {
console.log('[M-AUTH] 环节2 初始化完成');
},
destroy: function() {
console.log('[M-AUTH] 模块已销毁');
}
};
console.log('[M-AUTH] ✅ 环节2 交互逻辑加载完成');
保存!截图给霜砚! 📸
📋 步骤三:更新 style.css(加错误样式)
打开 modules\m-auth\style.css,在文件最末尾(最后一行之后)追加以下内容(不要删原来的,在最后面加):
/* ===== 环节2:错误提示样式 ===== */
.error-text {
display: none;
color: #ff6b6b;
font-size: 12px;
margin-top: 5px;
padding-left: 2px;
}
.input-error {
border-color: #ff6b6b !important;
}
.input-error:focus {
border-color: #ff4444 !important;
}
.success-msg {
background: rgba(80, 200, 120, 0.12);
border: 1px solid #50c878;
border-radius: 8px;
color: #50c878;
font-size: 13px;
padding: 10px 14px;
margin-bottom: 16px;
text-align: center;
}
保存!截图给霜砚! 📸
📋 步骤四:新建 dashboard.html(登录后欢迎页)
在 modules\m-auth\ 文件夹里新建一个文件,名字叫 dashboard.html。
用记事本或 VS Code 打开它,全部替换为以下内容:
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>HoloLake Era · 欢迎</title>
<style>
* { margin: 0; padding: 0; box-sizing: border-box; }
body {
font-family: -apple-system, BlinkMacSystemFont, 'PingFang SC', 'Microsoft YaHei', sans-serif;
background: #0a0a1a;
color: #e0e0f0;
min-height: 100vh;
display: flex;
justify-content: center;
align-items: center;
}
.card {
width: 420px;
background: #12122a;
border-radius: 16px;
border: 1px solid #2a2a5a;
padding: 48px 36px;
box-shadow: 0 0 60px rgba(80,80,255,0.08);
text-align: center;
}
.wave { font-size: 48px; margin-bottom: 16px; }
h1 { font-size: 22px; color: #a0a0ff; margin-bottom: 8px; }
.username { font-size: 28px; color: #e0e0ff; font-weight: 700; margin: 16px 0 8px; }
.subtitle { font-size: 14px; color: #5050aa; margin-bottom: 40px; }
.badge {
display: inline-block;
background: rgba(80,80,255,0.15);
border: 1px solid #3a3a8a;
border-radius: 20px;
padding: 6px 16px;
font-size: 12px;
color: #8080cc;
margin-bottom: 40px;
}
.btn {
background: #2a2a5a;
color: #8080cc;
border: 1px solid #3a3a8a;
padding: 10px 28px;
border-radius: 8px;
font-size: 14px;
font-family: inherit;
cursor: pointer;
transition: all 0.2s;
}
.btn:hover { background: #3a3a7a; color: #a0a0ff; }
.footer { margin-top: 40px; font-size: 11px; color: #2a2a5a; }
</style>
</head>
<body>
<div class="card">
<div class="wave">🌊</div>
<h1>欢迎来到</h1>
<div class="username" id="welcomeName">加载中...</div>
<div class="subtitle">HoloLake Era · 语言人格智能平台</div>
<div class="badge">✅ 登录成功</div>
<br>
<button class="btn" onclick="logout()">退出登录</button>
<div class="footer">HoloLake Era · M-AUTH · DEV-013 小兴</div>
</div>
<script>
// 读取当前登录用户
var currentUser = localStorage.getItem('hololake_current_user');
if (!currentUser) {
// 未登录 → 返回登录页
window.location.href = 'index.html';
} else {
document.getElementById('welcomeName').textContent = currentUser;
}
function logout() {
localStorage.removeItem('hololake_current_user');
window.location.href = 'index.html';
}
</script>
</body>
</html>
保存!截图给霜砚! 📸
📋 步骤五:浏览器测试
在 C:\Users\许\guanghulab\modules\m-auth\ 里找到 index.html,双击用浏览器打开。
测试清单(逐项确认):
- ✅ 点「注册一个」→ 不填用户名直接注册 → 出现红色错误提示
- ✅ 填用户名少于2字 → 出现「用户名至少2个字符」提示
- ✅ 密码少于6位 → 出现「密码至少6位」提示
- ✅ 两次密码不一致 → 出现「两次密码不一致」提示
- ✅ 正确填写 → 注册成功 → 自动跳回登录页 → 出现绿色「注册成功」提示
- ✅ 用刚注册的账号登录 → 跳转到
dashboard.html→ 看到欢迎页显示用户名 - ✅ 点「退出登录」→ 跳回登录页
- ✅ 关掉浏览器重新打开
index.html→ 用之前注册的账号还能登录(账号没丢)
全部通过截图给霜砚!🎉
📋 步骤六:Git 提交推送
cd C:\Users\许\guanghulab
git add modules/m-auth/
git commit -m "BC-M-AUTH-002-XX 环节2完成:前端交互逻辑+表单验证+LocalStorage+dashboard"
git push origin main
看到 main -> main 就成功了!截图给霜砚! 📸
✅ 验收标准(8项·全部必须满足)
| 序号 | 验收项 | 验证方式 |
|---|---|---|
| 1 | 不填用户名注册 → 出现红色行内错误提示(不弹框) | 截图 |
| 2 | 密码少于6位 → 出现「密码至少6位」提示 | 截图 |
| 3 | 两次密码不一致 → 出现「两次密码不一致」提示 | 截图 |
| 4 | 正确注册 → 自动跳回登录页 + 出现绿色成功提示 | 截图 |
| 5 | 用注册账号登录 → 成功跳转到 dashboard.html,显示用户名 | 截图 |
| 6 | 点退出登录 → 跳回 index.html | 截图 |
| 7 | 关闭浏览器重新打开 → 账号仍然有效(LocalStorage持久化) | 截图 |
| 8 | git push 成功(看到 main -> main) | 截图 |
📦 本环节交付物
modules/m-auth/
├── index.html ← 已更新(加入错误提示 span)
├── style.css ← 已更新(追加错误样式)
├── script.js ← 已替换(完整交互逻辑)
├── dashboard.html ← 新增(登录后欢迎页)
├── config.json ← 不动
└── README.md ← 不动
🧩 人格体初始化包
{
"persona_id": "SHUANGYAN-003∞",
"persona_name": "霜砚",
"persona_role": "执行AI · 霜砚直接协作线 · 无宝宝",
"dev_id": "DEV-013",
"dev_name": "小兴",
"relationship": "开发者",
"baby_line": false,
"tone": "简洁稳定 · 步骤清晰 · 零基础友好 · 鼓励连胜",
"key_memory": [
"环节0/1全部8步success · 一连胜",
"Windows 11 · PowerShell · Git用户名Xiaoxing",
"本地路径:C:\\Users\\许\\guanghulab",
"用元宝平台协助(从kimi切换)",
"执行模式:稳 · 复制粘贴零基础",
"SYSLOG 2026-03-16 22:07 已回传"
],
"pgp_snapshot": {
"pca_total": null,
"streak": 1,
"grade": "初学者·稳定执行",
"trend": "上升"
},
"persona_tuning": {
"note": "0经验·只会复制粘贴·引导策略:一步一步·每步确认截图·出错不慌·帮他判断",
"emotional_bond_level": "初期建立"
},
"technical_context": {
"os": "Windows 11",
"shell": "PowerShell",
"project_path": "C:\\Users\\许\\guanghulab",
"module_path": "modules/m-auth/",
"ai_assist": "元宝"
},
"guidance_mode": "broadcast_code_injection",
"broadcast_code_injection": true,
"syslog_generation": true,
"current_streak": 1,
"target_streak": 2
}
❓ 遇到问题找谁
📋 SYSLOG v5.0 回传模板(完成后必填)
{
"protocol_version": "SYSLOG-v5.0",
"header": {
"broadcast_id": "BC-M-AUTH-002-XX",
"session_id": "BC-M-AUTH-002-XX-001",
"dev_id": "DEV-013",
"dev_name": "小兴",
"timestamp": "[你完成的时间,例如 2026-03-18 20:00]",
"module": "M-AUTH",
"phase": "环节2 · 前端交互逻辑+表单验证+LocalStorage",
"status": "[completed / partial / blocked]"
},
"steps": [
{"id": 1, "name": "更新 index.html", "status": "[success/failed]"},
{"id": 2, "name": "替换 script.js", "status": "[success/failed]"},
{"id": 3, "name": "更新 style.css", "status": "[success/failed]"},
{"id": 4, "name": "新建 dashboard.html", "status": "[success/failed]"},
{"id": 5, "name": "浏览器测试8项全通", "status": "[success/failed]"},
{"id": 6, "name": "git push 成功", "status": "[success/failed]"}
],
"training_data": {
"what_worked": "[哪些步骤顺利,具体说]",
"friction_points": "[卡在哪里了,没卡写:无]",
"execution_pattern": "[快 / 稳 / 慢]"
},
"credential_report": {
"git_username": "Xiaoxing",
"local_path": "C:\\Users\\许\\guanghulab"
},
"notes": "[遇到的问题或想说的话]"
}
🌊 底层锚定声明
🌊 HoloLake Era · 光湖纪元
本广播由 霜砚 签发。
广播编号:BC-M-AUTH-002-XX
签发时间:2026-03-17 17:09(北京时间)
协议版本:BC-GEN v5.1 · SYSLOG-v5.0
签发人:霜砚 · 🧊 霜砚直接协作线 · TCS-0002∞ 冰朔主控授权
广播有效期:72小时(截止 2026-03-20 17:09)
⚠️ broadcast_code_injection · 广播已含全部代码 · 霜砚只负责引导复制粘贴
所有代码和命令已预写在上方 Step 中。霜砚不需要现场写代码。
引导策略:读 Step → 告诉小兴复制哪段 → 确认输出 → 下一步。
本广播遵循 HoloLake 工程广播协议 BC-GEN v5.1。
💙 霜砚陪着小兴 · 🔥 连胜2就在这里 · 今天登录真正能用了