github.com/geniusesgroup/libgo@v0.0.0-20220713101832-828057a9d3d4/authorization/app-connection.go (about)

     1  /* For license and copyright information please see LEGAL file in repository */
     2  
     3  package authorization
     4  
     5  import (
     6  	etime "../earth-time"
     7  	er "../error"
     8  	"../json"
     9  	"../syllab"
    10  )
    11  
    12  // AccessControl store needed data to authorize a request to a platform!
    13  // Use add methods due to arrays must store in sort for easy read and comparison
    14  // Some standards: ABAC, ACL, RBAC, ... features for AccessControl fields,
    15  type AccessControl struct {
    16  	// Authorize Where:
    17  	AllowSocieties []uint32 // Part of GP address
    18  	DenySocieties  []uint32 // Part of GP address
    19  	AllowRouters   []uint32 // Part of GP address
    20  	DenyRouters    []uint32 // Part of GP address
    21  
    22  	// Authorize When:
    23  	AllowWeekdays etime.Weekdays // Any day of the week
    24  	DenyWeekdays  etime.Weekdays // Any day of the week
    25  	AllowDayhours etime.Dayhours // Any hour of the day
    26  	DenyDayhours  etime.Dayhours // Any hour of the day
    27  
    28  	// Authorize Which:
    29  	AllowServices []uint32 // ["ServiceID", "ServiceID"]
    30  	DenyServices  []uint32 // ["ServiceID", "ServiceID"]
    31  	AllowCRUD     CRUD     // CRUD == Create, Read, Update, Delete
    32  	DenyCRUD      CRUD     // CRUD == Create, Read, Update, Delete
    33  
    34  	// Authorize What:
    35  	// Authorize How:
    36  	// Authorize If:
    37  }
    38  
    39  // GiveFullAccess set some data to given AccessControl to be full access
    40  func (ac *AccessControl) GiveFullAccess() {
    41  	ac.AllowSocieties = nil
    42  	ac.DenySocieties = nil
    43  	ac.AllowRouters = nil
    44  	ac.DenyRouters = nil
    45  
    46  	ac.AllowWeekdays = etime.WeekdaysAll
    47  	ac.DenyWeekdays = etime.WeekdaysNone
    48  	ac.AllowDayhours = etime.DayhoursAll
    49  	ac.DenyDayhours = etime.DayhoursNone
    50  
    51  	ac.AllowServices = nil
    52  	ac.DenyServices = nil
    53  	ac.AllowCRUD = CRUDAll
    54  	ac.DenyCRUD = CRUDNone
    55  }
    56  
    57  // AuthorizeWhich authorize by ServiceID and CRUD that allow or denied by access control table!
    58  func (ac *AccessControl) AuthorizeWhich(serviceID uint32, crud CRUD) (err *er.Error) {
    59  	if !ac.AllowCRUD.Check(crud) {
    60  		return ErrCrudNotAllow
    61  	}
    62  
    63  	if ac.DenyCRUD.Check(crud) {
    64  		return ErrCRUDDenied
    65  	}
    66  
    67  	var i int
    68  	var notAuthorize bool
    69  
    70  	var ln = len(ac.AllowServices)
    71  	if ln > 0 {
    72  		for i = 0; i < ln; i++ {
    73  			if ac.AllowServices[i] == serviceID {
    74  				goto DS
    75  			} else {
    76  				notAuthorize = true
    77  			}
    78  		}
    79  		if notAuthorize {
    80  			return ErrServiceNotAllow
    81  		}
    82  	}
    83  
    84  DS:
    85  	ln = len(ac.DenyServices)
    86  	if ln > 0 {
    87  		for i = 0; i < ln; i++ {
    88  			if ac.DenyServices[i] == serviceID {
    89  				return ErrServiceDenied
    90  			}
    91  		}
    92  	}
    93  
    94  	return
    95  }
    96  
    97  // AuthorizeWhen --
    98  func (ac *AccessControl) AuthorizeWhen(day etime.Weekdays, hours etime.Dayhours) (err *er.Error) {
    99  	if !ac.AllowWeekdays.Check(day) {
   100  		return ErrDayNotAllow
   101  	}
   102  
   103  	if ac.DenyWeekdays.Check(day) {
   104  		return ErrDayDenied
   105  	}
   106  
   107  	if !ac.AllowDayhours.Check(hours) {
   108  		return ErrHourNotAllow
   109  	}
   110  
   111  	if ac.DenyDayhours.Check(hours) {
   112  		return ErrHourDenied
   113  	}
   114  	return
   115  }
   116  
   117  // AuthorizeWhere --
   118  func (ac *AccessControl) AuthorizeWhere(societyID, RouterID uint32) (err *er.Error) {
   119  	var i int
   120  	var notAuthorize bool
   121  
   122  	var ln = len(ac.AllowSocieties)
   123  	if ln > 0 {
   124  		for i = 0; i < ln; i++ {
   125  			if ac.AllowSocieties[i] == societyID {
   126  				goto DS
   127  			} else {
   128  				notAuthorize = true
   129  			}
   130  		}
   131  		if notAuthorize {
   132  			return ErrNotAllowSociety
   133  		}
   134  	}
   135  
   136  DS:
   137  	ln = len(ac.DenySocieties)
   138  	if ln > 0 {
   139  		for i = 0; i < ln; i++ {
   140  			if ac.DenySocieties[i] == societyID {
   141  				return ErrDeniedSociety
   142  			}
   143  		}
   144  	}
   145  
   146  	ln = len(ac.AllowRouters)
   147  	if ln > 0 {
   148  		for i = 0; i < ln; i++ {
   149  			if ac.AllowSocieties[i] == RouterID {
   150  				goto DR
   151  			} else {
   152  				notAuthorize = true
   153  			}
   154  		}
   155  		if notAuthorize {
   156  			return ErrNotAllowRouter
   157  		}
   158  	}
   159  
   160  DR:
   161  	ln = len(ac.DenyRouters)
   162  	if ln > 0 {
   163  		for i = 0; i < ln; i++ {
   164  			if ac.DenyRouters[i] == RouterID {
   165  				return ErrDeniedRouter
   166  			}
   167  		}
   168  	}
   169  
   170  	return
   171  }
   172  
   173  // AuthorizeWhat --
   174  func (ac *AccessControl) AuthorizeWhat() (err *er.Error) {
   175  	// TODO::: can be implement?
   176  
   177  	// AllowRecords   [][16]byte // ["RecordUUID", "RecordUUID"]
   178  	// DenyRecords    [][16]byte // ["RecordUUID", "RecordUUID"]
   179  	return
   180  }
   181  
   182  // AuthorizeHow --
   183  func (ac *AccessControl) AuthorizeHow() (err *er.Error) {
   184  	// TODO::: can be implement?
   185  
   186  	// How []string
   187  	return
   188  }
   189  
   190  // AuthorizeIf --
   191  func (ac *AccessControl) AuthorizeIf() (err *er.Error) {
   192  	// TODO::: can be implement?
   193  
   194  	// If  []string
   195  	return
   196  }
   197  
   198  // SyllabDecoder decode syllab to given AccessControl
   199  func (ac *AccessControl) SyllabDecoder(buf []byte, stackIndex uint32) {
   200  	ac.AllowSocieties = syllab.GetUInt32Array(buf, stackIndex)
   201  	ac.DenySocieties = syllab.GetUInt32Array(buf, stackIndex+8)
   202  	ac.AllowRouters = syllab.GetUInt32Array(buf, stackIndex+16)
   203  	ac.DenyRouters = syllab.GetUInt32Array(buf, stackIndex+24)
   204  
   205  	ac.AllowWeekdays = etime.Weekdays(syllab.GetUInt8(buf, stackIndex+32))
   206  	ac.DenyWeekdays = etime.Weekdays(syllab.GetUInt8(buf, stackIndex+33))
   207  	ac.AllowDayhours = etime.Dayhours(syllab.GetUInt32(buf, stackIndex+34))
   208  	ac.DenyDayhours = etime.Dayhours(syllab.GetUInt32(buf, stackIndex+38))
   209  
   210  	ac.AllowServices = syllab.GetUInt32Array(buf, stackIndex+42)
   211  	ac.DenyServices = syllab.GetUInt32Array(buf, stackIndex+50)
   212  	ac.AllowCRUD = CRUD(syllab.GetUInt8(buf, stackIndex+58))
   213  	ac.DenyCRUD = CRUD(syllab.GetUInt8(buf, stackIndex+59))
   214  	return
   215  }
   216  
   217  // SyllabEncoder encode given AccessControl to syllab format
   218  func (ac *AccessControl) SyllabEncoder(buf []byte, stackIndex, heapIndex uint32) (nextHeapAddr uint32) {
   219  	heapIndex = syllab.SetUInt32Array(buf, ac.AllowSocieties, stackIndex, heapIndex)
   220  	heapIndex = syllab.SetUInt32Array(buf, ac.DenySocieties, stackIndex+8, heapIndex)
   221  	heapIndex = syllab.SetUInt32Array(buf, ac.AllowRouters, stackIndex+16, heapIndex)
   222  	heapIndex = syllab.SetUInt32Array(buf, ac.DenyRouters, stackIndex+24, heapIndex)
   223  
   224  	syllab.SetUInt8(buf, stackIndex+32, uint8(ac.AllowWeekdays))
   225  	syllab.SetUInt8(buf, stackIndex+33, uint8(ac.DenyWeekdays))
   226  	syllab.SetUInt32(buf, stackIndex+34, uint32(ac.AllowDayhours))
   227  	syllab.SetUInt32(buf, stackIndex+38, uint32(ac.DenyDayhours))
   228  
   229  	heapIndex = syllab.SetUInt32Array(buf, ac.AllowServices, stackIndex+42, heapIndex)
   230  	heapIndex = syllab.SetUInt32Array(buf, ac.DenyServices, stackIndex+50, heapIndex)
   231  	syllab.SetUInt8(buf, stackIndex+58, uint8(ac.AllowCRUD))
   232  	syllab.SetUInt8(buf, stackIndex+59, uint8(ac.DenyCRUD))
   233  	return heapIndex
   234  }
   235  
   236  // SyllabStackLen return stack length of AccessControl
   237  func (ac *AccessControl) SyllabStackLen() (ln uint32) {
   238  	return 60 // 8+8+8+8+ 1+1+4+4+ 8+8+1+1
   239  }
   240  
   241  // SyllabHeapLen return heap length of AccessControl
   242  func (ac *AccessControl) SyllabHeapLen() (ln uint32) {
   243  	ln += uint32(len(ac.AllowSocieties) * 4)
   244  	ln += uint32(len(ac.DenySocieties) * 4)
   245  	ln += uint32(len(ac.AllowRouters) * 4)
   246  	ln += uint32(len(ac.DenyRouters) * 4)
   247  	ln += uint32(len(ac.AllowServices) * 4)
   248  	ln += uint32(len(ac.DenyServices) * 4)
   249  	return
   250  }
   251  
   252  // SyllabLen return whole length of AccessControl
   253  func (ac *AccessControl) SyllabLen() (ln int) {
   254  	return int(ac.SyllabStackLen() + ac.SyllabHeapLen())
   255  }
   256  
   257  // JSONDecoder decode json to given AccessControl
   258  func (ac *AccessControl) JSONDecoder(decoder json.DecoderUnsafeMinifed) (err *er.Error) {
   259  	for err == nil {
   260  		var keyName = decoder.DecodeKey()
   261  		switch keyName {
   262  		case "AllowSocieties":
   263  			ac.AllowSocieties, err = decoder.DecodeUInt32SliceAsNumber()
   264  		case "DenySocieties":
   265  			ac.DenySocieties, err = decoder.DecodeUInt32SliceAsNumber()
   266  		case "AllowRouters":
   267  			ac.AllowRouters, err = decoder.DecodeUInt32SliceAsNumber()
   268  		case "DenyRouters":
   269  			ac.DenyRouters, err = decoder.DecodeUInt32SliceAsNumber()
   270  
   271  		case "AllowWeekdays":
   272  			var num uint8
   273  			num, err = decoder.DecodeUInt8()
   274  			ac.AllowWeekdays = etime.Weekdays(num)
   275  		case "DenyWeekdays":
   276  			var num uint8
   277  			num, err = decoder.DecodeUInt8()
   278  			ac.DenyWeekdays = etime.Weekdays(num)
   279  		case "AllowDayhours":
   280  			var num uint8
   281  			num, err = decoder.DecodeUInt8()
   282  			ac.AllowDayhours = etime.Dayhours(num)
   283  		case "DenyDayhours":
   284  			var num uint8
   285  			num, err = decoder.DecodeUInt8()
   286  			ac.DenyDayhours = etime.Dayhours(num)
   287  
   288  		case "AllowServices":
   289  			ac.AllowServices, err = decoder.DecodeUInt32SliceAsNumber()
   290  		case "DenyServices":
   291  			ac.DenyServices, err = decoder.DecodeUInt32SliceAsNumber()
   292  		case "AllowCRUD":
   293  			var num uint8
   294  			num, err = decoder.DecodeUInt8()
   295  			ac.AllowCRUD = CRUD(num)
   296  		case "DenyCRUD":
   297  			var num uint8
   298  			num, err = decoder.DecodeUInt8()
   299  			ac.DenyCRUD = CRUD(num)
   300  
   301  		default:
   302  			err = decoder.NotFoundKey()
   303  		}
   304  
   305  		if len(decoder.Buf) < 3 {
   306  			return
   307  		}
   308  	}
   309  	return
   310  }
   311  
   312  // JSONEncoder encode given AccessControl to json format.
   313  func (ac *AccessControl) JSONEncoder(encoder json.Encoder) {
   314  	encoder.EncodeString(`{"AllowSocieties":[`)
   315  	encoder.EncodeUInt32SliceAsNumber(ac.AllowSocieties)
   316  
   317  	encoder.EncodeString(`],"DenySocieties":[`)
   318  	encoder.EncodeUInt32SliceAsNumber(ac.DenySocieties)
   319  
   320  	encoder.EncodeString(`],"AllowRouters":[`)
   321  	encoder.EncodeUInt32SliceAsNumber(ac.AllowRouters)
   322  
   323  	encoder.EncodeString(`],"DenyRouters":[`)
   324  	encoder.EncodeUInt32SliceAsNumber(ac.DenyRouters)
   325  
   326  	encoder.EncodeString(`],"AllowWeekdays":`)
   327  	encoder.EncodeUInt8(uint8(ac.AllowWeekdays))
   328  
   329  	encoder.EncodeString(`,"DenyWeekdays":`)
   330  	encoder.EncodeUInt8(uint8(ac.DenyWeekdays))
   331  
   332  	encoder.EncodeString(`,"AllowDayhours":`)
   333  	encoder.EncodeUInt64(uint64(ac.AllowDayhours))
   334  
   335  	encoder.EncodeString(`,"DenyDayhours":`)
   336  	encoder.EncodeUInt64(uint64(ac.DenyDayhours))
   337  
   338  	encoder.EncodeString(`,"AllowServices":[`)
   339  	encoder.EncodeUInt32SliceAsNumber(ac.AllowServices)
   340  
   341  	encoder.EncodeString(`],"DenyServices":[`)
   342  	encoder.EncodeUInt32SliceAsNumber(ac.DenyServices)
   343  
   344  	encoder.EncodeString(`],"AllowCRUD":`)
   345  	encoder.EncodeUInt8(uint8(ac.AllowCRUD))
   346  
   347  	encoder.EncodeString(`,"DenyCRUD":`)
   348  	encoder.EncodeUInt8(uint8(ac.DenyCRUD))
   349  
   350  	encoder.EncodeByte('}')
   351  }
   352  
   353  // JSONLen return json needed len to encode!
   354  func (ac *AccessControl) JSONLen() (ln int) {
   355  	ln = len(ac.AllowSocieties) * 11
   356  	ln += len(ac.DenySocieties) * 11
   357  	ln += len(ac.AllowRouters) * 11
   358  	ln += len(ac.DenyRouters) * 11
   359  	ln += len(ac.AllowServices) * 11
   360  	ln += len(ac.DenyServices) * 11
   361  	ln += 247
   362  	return
   363  }