react go实现用户历史登录列表页面

refer: http://ip-api.com/

1.首先需要创建一个保存用户历史的登录的表,然后连接go

2.在用户登录的时候,获取用户的IP IP位置,在后端直接处理数据即可(不需要在前端传递数据)

(1)增加路由:

Go 复制代码
apiv1.POST("/history_login_logs", v1.AddHistoryLoginLog)

(2)在model里增加(例如:models/history_login_logs.go)

Go 复制代码
 func AddHistoryLoginLog(user_id int, ip_address string, ip_location string, login_at time.Time) bool {
    db.Create(&HistoryLoginLogs{
      UserId:    user_id,
      IpAddress: ip_address,
      IpLocation:   ip_location,
      LoginAt: login_at,
    })

    return true
  }

(3) 在登录后的方法中增加(需要引入

Go 复制代码
import(
  "time"
  "io/ioutil"
  "fmt"
  "encoding/json"
)

type Location struct {
  Status      string  `json:"status"`
    Country     string  `json:"country"`
    CountryCode string  `json:"countryCode"`
    Region      string  `json:"region"`
    RegionName  string  `json:"regionName"`
    City        string  `json:"city"`
    Zip         string  `json:"zip"`
    Lat         float64 `json:"lat"`
    Lon         float64 `json:"lon"`
    Timezone    string  `json:"timezone"`
    Isp         string  `json:"isp"`
    Org         string  `json:"org"`
    As          string  `json:"as"`
    Query       string  `json:"query"`
}

...
ipAddress := c.ClientIP()
fmt.Println("== ip_address:", ipAddress)
resp, err := http.Get("http://ip-api.com/json/" + ipAddress + "?lang=zh-CN")
if err != nil {
  fmt.Println("Error:", err)
    return
}

defer resp.Body.Close()

  body, err := ioutil.ReadAll(resp.Body)
  if err != nil {
    fmt.Println("Error:", err)
      return
  }

  var location Location
err = json.Unmarshal(body, &location)
  if err != nil {
    fmt.Println("Error:", err)
      return
  }

fmt.Println("=== Location:", location)
City := location.City

  currentTime := time.Now()
models.AddHistoryLoginLog(user.ID, ipAddress, City, currentTime)
...

(4)增加action (例如:routers/api/v1/history_login_log.go)(需要引入import "net/http" "time" "fmt")

Go 复制代码
type AddHistoryLoginLogRequest struct {
    UserID     int    `json:"user_id" binding:"required"`
      IPAddress  string `json:"ip_address" binding:"required"`
      City string `json:"ip_location" binding:"required"`
      CurrentTime time.Time `json:"login_at" binding:"required"`
  }

func AddHistoryLoginLog(c *gin.Context) {
  var request AddHistoryLoginLogRequest
    if err := c.ShouldBindJSON(&request); err != nil {
      fmt.Println("== err: ", err)
        return
    }

  models.AddHistoryLoginLog(request.UserID, request.IPAddress, request.City, request.CurrentTime)

}

3.在前端写一个展示的列表页面即可。(登录时间写现在的时间即可。)

例如:src/pages/HistoryLoginLog/index.jsx

Go 复制代码
import React, { Component } from 'react'
import { Table } from 'antd';
import axios from 'axios'
import Config from '@/settings'
import { getToken, removeToken } from '@/utils/auth'

const columns = [
  {
    title: '登录名',
    dataIndex: 'user_id',
    key: 'user_id',
    render: text => <a>{text}</a>,
  },
  {
    title: '登陆时间',
    dataIndex: 'login_at',
    key: 'login_at',
    // 这里是进行时间的处理,转换为北京时间,格式为:2023/08/16 21:40
    render: text => {
      const dateObj = new Date(text);
      const localizedDate = dateObj.toLocaleString('zh-CN', {
        timeZone: 'Asia/Shanghai',
        year: 'numeric',
        month: '2-digit',
        day: '2-digit',
        hour: '2-digit',
        minute: '2-digit',
      });
      return <span>{localizedDate}</span>;
    },
  },
  {
    title: '登陆ip',
    dataIndex: 'ip_address',
    key: 'ip_address',
  },
  {
    title: '登陆位置',
    dataIndex: 'ip_location',
    key: 'ip_locatio',
  }
];

export default class CalculationPlan extends Component {
  state = {
    data: [],
    loading: true,
  }

  async fetchData() {
    try {
      const response = await axios.get(`${Config.BASE_URL}/api/v1/history_login_logs?token=${getToken()}`)
      if (response.data.message == "ok") {
        const sortedData = response.data.data.sort((a, b) => new Date(b.id) - new Date(a.id));
        this.setState({
          data: sortedData,
          loading: false,
        })
      }
    } catch (error) {
      console.error(error)
      removeToken()
      window.location.href = '/'
    }
  }

  componentDidMount() {
    this.fetchData()
  }

  render() {
    const { data, loading } = this.state

    return (
        <Table columns={columns} dataSource={data} loading={loading} />
    )
  }
}
相关推荐
小羊没烦恼!2 小时前
T-SQL查询高级—SQL Server索引中的碎片和填充因子
开发语言·前端·javascript·数据库·后端·python·web安全
定栓2 小时前
Webpack迁到Vite第一节:模块系统迁移:require → import
运维·前端·webpack
土豆.exe2 小时前
chunked 编码的行尾:Go、h11 与 Tomcat 各错在哪一处
开发语言·网络安全·golang·tomcat
小熊在忙fpga2 小时前
N32G430芯片的flash表示
前端·javascript·html
Data analyse4562 小时前
App埋点版本兼容的字段迁移校验
大数据·运维·服务器·前端·数据库·数据分析
todoitbo2 小时前
本来只想给内网开个口子,Natapp 却多给了一道防护
前端·javascript·vue.js·内网穿透·网络防护·natapp
会灭火的程序员3 小时前
SuperMap AgentX Server智能体接入WEB应用技术文档
前端·supermap·agentx·agentx server
CRMEB3 小时前
商品 SKU 设计,从简单规格到多规格踩过什么
java·前端·数据库·开源
Chloe.Zz3 小时前
一篇入门Agent
开发语言·前端·javascript
java1234_小锋3 小时前
【技术专题】HTML5 网页技术 - HTML5 表格标签
前端·html·html5