Example #1
0
// Internal control command.
// SlaveOf can change the replication settings of a slave on the fly.
func (c *CtrlContext) SlaveOf(host string) error {
	call := c.cli.newCall(proto.CmdSlaveOf, nil)
	if call.err != nil {
		return call.err
	}

	var p ctrl.PkgSlaveOf
	p.ClientReq = true
	p.MasterAddr = host

	pkg, err := ctrl.Encode(call.cmd, c.dbId, call.seq, &p)
	if err != nil {
		c.cli.errCall(call, err)
		return err
	}

	call.pkg = pkg
	c.cli.sending <- call

	r, err := (<-call.Done).Reply()
	if err != nil {
		return err
	}

	t := r.(*ctrl.PkgSlaveOf)
	if t.ErrMsg != "" {
		return errors.New(t.ErrMsg)
	}
	return nil
}
Example #2
0
func (slv *slave) SendSlaveOfToMaster() error {
	slv.mtx.Lock()
	var mi = slv.mi
	var cli = slv.cli
	slv.mtx.Unlock()

	if cli == nil {
		return nil
	}

	var err error
	var pkg []byte
	if mi.Migration {
		var p ctrl.PkgMigrate
		p.ClientReq = false
		p.MasterAddr = mi.MasterAddr
		p.SlaveAddr = mi.SlaveAddr
		p.SlotId = mi.SlotId

		pkg, err = ctrl.Encode(proto.CmdMigrate, 0, 0, &p)
		if err != nil {
			return err
		}
	} else {
		lastSeq, valid := slv.bin.GetMasterSeq()
		if !valid {
			slv.mc.SetStatus(ctrl.SlaveNeedClear)
			// Any better solution?
			log.Fatalf("Slave lastSeq %d is out of sync, please clear old data! "+
				"(Restart may fix this issue)", lastSeq)
		}

		var p ctrl.PkgSlaveOf
		p.ClientReq = false
		p.MasterAddr = mi.MasterAddr
		p.SlaveAddr = mi.SlaveAddr
		p.LastSeq = lastSeq
		log.Printf("Connect to master %s with lastSeq %d\n",
			mi.MasterAddr, p.LastSeq)

		pkg, err = ctrl.Encode(proto.CmdSlaveOf, 0, 0, &p)
		if err != nil {
			return err
		}
	}

	cli.AddResp(pkg)
	return slv.mc.SetStatus(ctrl.SlaveFullSync)
}