基于fabric的校园征信系统——链代码的设计与实现

  • 链代码的设计
  • 链代码的实现

链代码的设计

我们已经完成了组织节点的部署,接下来我么就要针对项目来设计相应的链代码,也就是设计想要存入区块中的数据的数据结构。在Fabric账本中数据都是以key,value的形式进行存放的,key为string类型,value可以为json格式,所以它可以很简单也可以很复杂,具体针对实际情况进行设计。
       对于我们校园征信的项目,为减轻编程工作量,我们简化数据内容,以unionchannel为例,通道中中至少要保存以下数据:

数据内容参考高校学生档案管理规范:太原理工大学学生诚信档案管理办法
       如图所示学生征信档案内容包含学生基本信息,学校记录信息,第三方征信平台信息。前两项数据应由学校维护,后者应由加入联盟链的第三方的征信机构维护,加入联盟的企业可通过身份证号进行档案的查询,所以该数据放在unionchannel的账本中由三方共同维护和使用。其他各组织的不公开数据由各自channel中的账本进行读写和维护。
       在链码中对应的结构体声明如下:
       学生基本信息应包含学生姓名,性别,籍贯,出生日期,民族,身份证号,入学日期,毕业日期,学校名称,专业名称

// 学生基本信息
type StuInfo struct {StuName         string `json:"stuname"`    // 学生姓名 StuSex          string `json:"stusex"` // 学生性别NativePlace     string `json:"nativeplace"`    //籍贯 Birthday        string `json:"birthday"`  // 出生日期Nation          string `json:"nation"`  // 民族IDNum           string `json:"idnum"` // 身份证号AdmissionDate   string `json:"admissiondate"` // 入学日期GraduationTime  string `json:"graduationtime"` // 毕业日期SchName         string `json:"schname"` // 学校名称SubName         string `json:"subname"` // 专业名称
}

学校记录信息应包含学生绩点,在校优良记录,在校不良记录,助学贷款信息,毕业评语。

// 学校记录信息
type SchInfo struct {StuGPA            string `json:"stugpa"`    // 学生绩点 ExcellentRecord   string `json:"excellentrecord"` // 优良记录BadRecord         string `json:"badrecord"`    //不良记录 StuLoan           string `json:"stuloan"`  // 助学贷款记录GraduationComment string `json:"graduationcomment"`  // 毕业评价}

第三方征信机构信息应包含银行卡透支情况,花呗逾期情况,滴滴欠款情况,芝麻信用积分。

// 征信机构信息
type CreInfo struct {BankOverdraft       string `json:"bankoverdraft"`    // 信用卡透支记录 AntCreditPayOverDue string `json:"antcreditpayoverdue"` // 花呗逾期记录DidiTaxiArrears     string `json:"diditaxiarrears"`    //滴滴欠款记录 SesameCredit        string `json:"sesamecredit"`  // 芝麻信用积分}

将三个信息结构体封装到StuCreInfo结构体当中

// 学生征信档案
type StuCreInfo struct {StuInfo     StuInfo `json:"stuinfo"`    // 学生基本信息 SchInfo     SchInfo `json:"schinfo"` // 学校记录信息CreInfo     CreInfo `json:"creinfo"`    //征信机构信息
}

为了降低复杂程度,我们将数据类型都设置成string类型,其他组织各自channel中要存储的数据同样参考组织实际需要进行设计,与unionchannel类似。

链代码的实现

每个链码程序都必须实现链码接口 ,接口中的方法会在响应传来的交易时被调用。Init方法会在链码接收到instantiate(实例化)或者upgrade(升级)交易时被调用,执行必要的初始化操作,包括初始化应用的状态;Invoke方法会在响应调用交易时被调用以执行交易。
       链码在开发过程中需要实现链码接口,交易的类型决定了哪个接口函数将会被调用,如instantiate和upgrade类型会调用链码的Init接口,而invoke类型的交易则调用链码的Invoke接口。链码的接口定义如下:

type Chaincode interface {Init(stub ChaincodeStubInterface) pb.ResponseInvoke(stub ChaincodeStubInterface) pb.Response
}

shim.ChaincodeStubInterface接口用于访问及修改账本,并实现链码之间的互相调用,为编写链码的业务逻辑提供了大量实用的方法。
       链码的必要结构如下:

package main//引入必要的包
import(
"github.com/hyperledger/fabric/core/chaincode/shim"
pb"github.com/hyperledger/fabric/protos/peer"
)//声明一个结构体
type SimpleChaincode struct {}//为结构体添加Init方法
func (t *SimpleChaincode) Init(stub shim.ChaincodeStubInterface) pb.Response{//在该方法中实现链码初始化或升级时的处理逻辑//编写时可灵活使用stub中的API
}//为结构体添加Invoke方法
func (t *SimpleChaincode) Invoke(stub shim.ChaincodeStubInterface) pb.Response{//在该方法中实现链码运行中被调用或查询时的处理逻辑//编写时可灵活使用stub中的API
}//主函数,需要调用shim.Start( )方法
func main() {err:=shim.Start(new(SimpleChaincode))if err != nil {fmt.Printf("Error starting Simple chaincode: %s", err)}
}

接下来我们来实现项目的链代码:

package union
import("encoding/json""fmt""github.com/hyperledger/fabric/core/chaincode/shim""github.com/hyperledger/fabric/protos/peer"
)//学生征信链代码
type Unionchaincode struct{}
// 学生基本信息
type StuInfo struct {StuName         string `json:"stuname"`    // 学生姓名StuSex          string `json:"stusex"` // 学生性别NativePlace     string `json:"nativeplace"`    //籍贯Birthday        string `json:"birthday"`  // 出生日期Nation          string `json:"nation"`  // 民族IDNum           string `json:"idnum"` // 身份证号AdmissionDate   string `json:"admissiondate"` // 入学日期GraduationTime  string `json:"graduationtime"` // 毕业日期SchName         string `json:"schname"` // 学校名称SubName         string `json:"subname"` // 专业名称
}
// 学校记录信息
type SchInfo struct {StuGPA            string `json:"stugpa"`    // 学生绩点ExcellentRecord   string `json:"excellentrecord"` // 优良记录BadRecord         string `json:"badrecord"`    //不良记录StuLoan           string `json:"stuloan"`  // 助学贷款记录GraduationComment string `json:"graduationcomment"`  // 毕业评价}
// 征信机构信息
type CreInfo struct {BankOverdraft       string `json:"bankoverdraft"`    // 信用卡透支记录AntCreditPayOverDue string `json:"antcreditpayoverdue"` // 花呗逾期记录DidiTaxiArrears     string `json:"diditaxiarrears"`    //滴滴欠款记录SesameCredit        string `json:"sesamecredit"`  // 芝麻信用积分}
// 学生征信档案
type StuCreInfo struct {StuInfo     StuInfo `json:"stuinfo"`    // 学生基本信息SchInfo     SchInfo `json:"schinfo"` // 学校记录信息CreInfo     CreInfo `json:"creinfo"`    //征信机构信息
}
//Init函数
func (this *Unionchaincode) Init(stub shim.ChaincodeStubInterface) peer.Response{return shim.Success([]byte(""))
}//Invoke函数
func (this *Unionchaincode) Invoke(stub shim.ChaincodeStubInterface) peer.Response{// 通过函数名匹配对应的链代码函数调用function, params := stub.GetFunctionAndParameters()if function == "addStuInfo" {// 添加学生基本信息return this.addStuInfo(stub, params)} else if function == "getStuInfo" {// 获取学生基本信息return this.getStuInfo(stub, params)} else if function == "addSchInfo" {// 添加学校填写信息return this.addSchInfo(stub, params)} else if function == "getSchInfo" {// 获取学校填写信息return this.getSchInfo(stub, params)} else if function == "addCreInfo" {// 添加征信机构信息return this.addCreInfo(stub, params)} else if function == "getCreInfo" {// 获取征信机构信息return this.getCreInfo(stub, params)}// 没有任何函数被匹配到,返回错误消息fmt.Println("==== fn = ", function)return shim.Error("Received unknow function invocation")
}//main函数
func main() {err:=shim.Start(new(Unionchaincode))if err != nil {fmt.Printf("Error starting Union chaincode: %s", err)}
}
//StuInfo中的IDNum作为key
func (this *Unionchaincode) addStuInfo(stub shim.ChaincodeStubInterface, params []string) peer.Response{//定义一个学生档案结构体var stucreinfo StuCreInfo//判断参数个数是否正确if len(params) !=10 {return shim.Error("Incorrect number oof arguments.")}//判断身份证号是否为空if params[5] == "" {return shim.Error("IdNum can't be empty.")}//将传入的参数分别赋值给key和及结构体key := params[5]stucreinfo.StuInfo.StuName = params[0]stucreinfo.StuInfo.StuSex = params[1]stucreinfo.StuInfo.NativePlace = params[2]stucreinfo.StuInfo.Birthday = params[3]stucreinfo.StuInfo.Nation = params[4]stucreinfo.StuInfo.IDNum = params[5]stucreinfo.StuInfo.AdmissionDate = params[6]stucreinfo.StuInfo.GraduationTime = params[7]stucreinfo.StuInfo.SchName = params[8]stucreinfo.StuInfo.SubName = params[9]//将结构体转换为json格式stucreinfobytes,  err := json.Marshal(stucreinfo)if err != nil {shim.Error(err.Error())}//将key,value上传到链上err = stub.PutState(key, stucreinfobytes)if err != nil {shim.Error(err.Error())}return shim.Success([]byte("addStuInfo: OK"))
}
func (this *Unionchaincode) getStuInfo(stub shim.ChaincodeStubInterface, params []string) peer.Response {//判断参数个数是否正确if len(params) != 1 {return shim.Error("Incorrect number of arguments.")}//将参数赋值给keykey := params[0]//获取历史信息迭代器resultIterator, err := stub.GetHistoryForKey(key)if err != nil {shim.Error(err.Error())}var stuInfo StuInfo//释放迭代器defer resultIterator.Close()//遍历结果集if resultIterator.HasNext() {var stuCreInfo StuCreInforesponse, err := resultIterator.Next()if err != nil {return shim.Error(err.Error())}err = json.Unmarshal(response.Value, &stuCreInfo)if err != nil {shim.Error(err.Error())}if stuCreInfo.StuInfo.IDNum != "" {stuInfo = stuCreInfo.StuInfo}}stuInfobytes, err := json.Marshal(stuInfo)if err != nil {return shim.Error(err.Error())}//返回StuInfo的json格式数据return shim.Success(stuInfobytes)
}

以上代码是学生基本信息的添加与查询,其他信息的功能实现与其类似,这里不再赘述。链代码的设计和已经完成,那么Fabric端的相关工作已经完成,在后续我们将进行后端的业务逻辑的代码编写以及fabric-sdk-go的应用。

混子日记——校园征信项目3相关推荐

  1. 混子日记——校园征信项目1

    基于fabric的校园征信系统--前期环境准备 阿里云服务器配置 需求分析 诚信档案建立的必要性及目前的痛点 利用联盟链的思想解决现阶段问题 项目架构设计 Hyperledger fabric 交易流 ...

  2. 社交数据在征信领域的应用探索

    由51CTO举办的WOT"互联网+"时代大数据技术峰会上,来自腾讯数据挖掘高级工程师刘黎春做了以<社交数据在征信领域的应用探索>为主题的演讲,主要内容由社交征信背景.腾 ...

  3. 征信3.0时代,你准备好了么

    征信3.0时代,你准备好了么 征信3.0时代即将来临,你准备好了么? 当前征信主要竞品汇总 征信的公司分为两类:个人征信及企业征信. 目前的从事企业征信行业的公司主要有天创信用.量化派.启信宝.BBD ...

  4. 《惢客创业日记》2021.07.26-31(周日)惢客与征信的区别(上)

    今天,在日记中分享一下我在<惢客>书中关于惢客与征信区别的上半部分内容. 很多人听到惢客这个"证明诚信"的项目,第一个反应就是征信.其实,惢客与目前的征信体系还是有一定 ...

  5. 《惢客创业日记》2021.08.06-09(周五)惢客与征信的区别(下)

    这两天,没啥关于惢客的事儿,正好把我写的<惢客>书中"惢客与征信的区别"下半部分分享一下. 3.在"诚信辨识度"上的差异分析 [差异点]:征信(目前 ...

  6. 招标 | 近期隐私计算项目招标中标22(复旦大学、金控征信、联通、中讯邮电、农村商业银行、普陀公共数据等)

    1.复旦大学上海医学院基于隐私计算的健康医疗科研数据协作平台开发服务采购 项目名称:复旦大学上海医学院基于隐私计算的健康医疗科研数据协作平台开发服务 项目编号:2102027091 公告日期:2022 ...

  7. 《区块链原理、设计与应用》一3.3 征信和权属管理

    3.3 征信和权属管理 1.?征信管理 征信管理是一个巨大的潜在市场,据称超过千亿规模,也是目前大数据应用领域最有前途的方向之一. 目前,与征信相关的大量有效数据集中在少数机构手中.由于这些数据太过敏 ...

  8. 大数据征信应用与启示 ——以美国互联网金融公司 ZestFinance为例

    首页 干货教程 大数据动向 大数据应用 数据可视化 数据分析 投资并购 企业专区 注册 登录 大数据征信应用与启示 --以美国互联网金融公司 ZestFinance为例 蝙蝠侠 2014-10-29 ...

  9. 拖欠水费可能影响个人征信,大家怎么看?

    一直以来征信报告所记录的个人信息都相对比较少,旧版征信报告主要记录的是个人贷款,信用卡以及一些司法信息.但这些信息并不能全面的反映一个人的信用情况,因为很多人根本就没有贷款或者信用卡,所以大家就没法判 ...

最新文章

  1. CTFshow 命令执行 web53
  2. myeclipse自动生成hibernate映射文件的过程
  3. 写了人生中第一个完整模块的用例
  4. 基于任务编程_如何理解任何编程任务
  5. asp无组件上传图片 动态保存文件名 upload.inc逐句翻译
  6. 【转载】linux进程控制-exec系列 exec系统调用
  7. 非root用户安装mysql_linux非root用户安装5.7.27版本mysql
  8. Qt 之 QQ系统表情(四)
  9. 保持简单:纪念丹尼斯•里奇
  10. Linux : SSHD服务
  11. logisim 数码管输出设计
  12. 香橙派装php_香橙派Orange Pi 3电脑开发板如何安装安卓系统
  13. RuntimeError: size mismatch
  14. 抖音SEO,抖音seo优化
  15. Ubuntu14.04+cuda6.5+opencv2.4.9+caffe配置记录
  16. oem是代工还是贴牌_OEM贴牌和ODM贴牌的区别
  17. 毕业季--写给大学毕业生的一番话
  18. 怎么做期货可以每天都赚钱?都有哪些技巧和方法?
  19. FilterChain 过滤器链和拦截路径
  20. Windows 下 Gambit 启动脚本

热门文章

  1. 用ptp4l和phc2sys实现系统时钟同步
  2. 今年十八,喜欢SQL注入
  3. python实现长视频分割为短视频
  4. linux搭建seafile_CentOS7+seafile搭建私有云盘测试过程记录
  5. 常见P2P协议之BitTorrent 分析
  6. 水晶球 | 贪心、排序
  7. 1.决策树C4.5算法
  8. 2020软考信息系统项目管理师_项目管理(上) 视频培训教程-任铄-专题视频课程
  9. IDEA VUE使用JavaScript表达式
  10. Lecture 1: Probability Models and Axioms