Skip to content

Commit

Permalink
Merge pull request #20 from ashbeelghouri/0.5
Browse files Browse the repository at this point in the history
Logs
  • Loading branch information
ashbeelghouri authored Jul 1, 2024
2 parents 3c99e5c + 221d0bf commit c2daf86
Show file tree
Hide file tree
Showing 5 changed files with 147 additions and 56 deletions.
7 changes: 4 additions & 3 deletions Basic_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,14 @@ import (
)

func TestV2Validate(t *testing.T) {
schematics, err := v2.LoadJsonSchemaFile("test-data/schema/direct/v2/example-1.json")
schematics, err := v2.LoadJsonSchemaFile("test-data/schema/direct/v2/example-2.json")
if err != nil {
t.Error(err)
}
schematics.Logging.PrintDebugLogs = true
schematics.Logging.PrintErrorLogs = true
schematics.Validators.RegisterValidator("NewFun", NewFun)
content, err := os.ReadFile("test-data/data/direct/v2/example.json")
content, err := os.ReadFile("test-data/data/direct/v2/example-3.json")
if err != nil {
t.Error(err)
}
Expand All @@ -25,7 +27,6 @@ func TestV2Validate(t *testing.T) {
errs := schematics.Validate(jsonData)
log.Println(errs.GetStrings("en", "%data\n"))
}

func NewFun(i interface{}, attr map[string]interface{}) error {
log.Println(i)
log.Println(attr)
Expand Down
61 changes: 30 additions & 31 deletions data/v0/schema.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,6 @@ import (
"strings"
)

var Logs utils.Logger

type TargetKey string

type Schematics struct {
Expand Down Expand Up @@ -42,6 +40,7 @@ type Field struct {
Operators map[string]Constant `json:"operators"`
L10n map[string]interface{} `json:"l10n"`
AdditionalInformation map[string]interface{} `json:"additional_information"`
logging utils.Logger
}

type Constant struct {
Expand All @@ -51,31 +50,30 @@ type Constant struct {
}

func (s *Schematics) Configs() {
Logs = s.Logging
if s.Logging.PrintDebugLogs {
log.Println("debugger is on")
}
if s.Logging.PrintErrorLogs {
log.Println("error logging is on")
}
s.Validators.Logger = Logs
s.Operators.Logger = Logs
s.Validators.Logger = s.Logging
s.Operators.Logger = s.Logging
}

func (s *Schematics) LoadJsonSchemaFile(path string) error {
s.Configs()
content, err := os.ReadFile(path)
if err != nil {
Logs.ERROR("Failed to load schema file", err)
s.Logging.ERROR("Failed to load schema file", err)
return err
}
var schema Schema
err = json.Unmarshal(content, &schema)
if err != nil {
Logs.ERROR("Failed to unmarshall schema file", err)
s.Logging.ERROR("Failed to unmarshall schema file", err)
return err
}
Logs.DEBUG("Schema Loaded From File: ", schema)
s.Logging.DEBUG("Schema Loaded From File: ", schema)
s.Schema = schema
s.Validators.BasicValidators()
s.Operators.LoadBasicOperations()
Expand All @@ -91,16 +89,16 @@ func (s *Schematics) LoadJsonSchemaFile(path string) error {
func (s *Schematics) LoadMap(schemaMap interface{}) error {
JSON, err := json.Marshal(schemaMap)
if err != nil {
Logs.ERROR("Schema should be valid json map[string]interface", err)
s.Logging.ERROR("Schema should be valid json map[string]interface", err)
return err
}
var schema Schema
err = json.Unmarshal(JSON, &schema)
if err != nil {
Logs.ERROR("Invalid Schema", err)
s.Logging.ERROR("Invalid Schema", err)
return err
}
Logs.DEBUG("Schema Loaded From MAP: ", schema)
s.Logging.DEBUG("Schema Loaded From MAP: ", schema)
s.Schema = schema
s.Validators.BasicValidators()
s.Operators.LoadBasicOperations()
Expand All @@ -124,15 +122,15 @@ func (f *Field) Validate(value interface{}, allValidators map[string]validators.
}
for name, constants := range f.Validators {
err.Validator = name
Logs.DEBUG("Validator: ", name, constants)
f.logging.DEBUG("Validator: ", name, constants)
if name != "" {
Logs.DEBUG("Name of the validator is not given: ", name)
f.logging.DEBUG("Name of the validator is not given: ", name)
err.Validator = name
}
if f.IsRequired && value == nil {
err.Validator = "Required"
err.AddMessage("en", "this is a required field")
Logs.DEBUG("Field is required but value is null")
f.logging.DEBUG("Field is required but value is null")
return &err
}

Expand All @@ -142,25 +140,25 @@ func (f *Field) Validate(value interface{}, allValidators map[string]validators.

var fn validators.Validator
fn, exists := allValidators[name]
Logs.DEBUG("function exists? ", exists)
f.logging.DEBUG("function exists? ", exists)
if !exists {
Logs.ERROR("function not found", name)
f.logging.ERROR("function not found", name)
err.AddMessage("en", "validator not registered")
return &err
}

fnError := fn(value, constants.Attributes)
Logs.DEBUG("fnError: ", fnError)
f.logging.DEBUG("fnError: ", fnError)
if fnError != nil {
if constants.Error != "" {
Logs.DEBUG("Custom Error is Defined", constants.Error)
f.logging.DEBUG("Custom Error is Defined", constants.Error)
err.AddMessage("en", constants.Error)
}

if f.L10n != nil {
for locale, msg := range f.L10n {
if msg != nil {
Logs.DEBUG("L10n: ", locale, msg)
f.logging.DEBUG("L10n: ", locale, msg)
err.AddMessage(locale, msg.(string))
}
}
Expand Down Expand Up @@ -212,37 +210,38 @@ func (s *Schematics) Validate(jsonData interface{}) *errorHandler.Errors {
}

func (s *Schematics) ValidateObject(jsonData *map[string]interface{}, id *string) *errorHandler.Errors {
Logs.DEBUG("validating the object")
s.Logging.DEBUG("validating the object")
var errorMessages errorHandler.Errors
var baseError errorHandler.Error
flatData := *s.makeFlat(*jsonData)
Logs.DEBUG("here after flat data --> ", flatData)
s.Logging.DEBUG("here after flat data --> ", flatData)
uniqueID := ""

if id != nil {
uniqueID = *id
}
Logs.DEBUG("after unique id")
s.Logging.DEBUG("after unique id")
var missingFromDependants []string
for target, field := range s.Schema.Fields {
field.logging = s.Logging
baseError.Validator = "is-required"
matchingKeys := utils.FindMatchingKeys(flatData, string(target))
Logs.DEBUG("matching keys --> ", matchingKeys)
s.Logging.DEBUG("matching keys --> ", matchingKeys)
if len(matchingKeys) == 0 {
if field.IsRequired {
baseError.AddMessage("en", "this field is required")
errorMessages.AddError(string(target), baseError)
}
continue
}
Logs.DEBUG("after is required --> ", matchingKeys)
s.Logging.DEBUG("after is required --> ", matchingKeys)
// check for dependencies
if len(field.DependsOn) > 0 {
missing := false
for _, d := range field.DependsOn {
matchDependsOn := utils.FindMatchingKeys(flatData, d)
if !(utils.StringInStrings(string(target), missingFromDependants) == false && len(matchDependsOn) > 0) {
Logs.DEBUG("matched depends on", matchDependsOn)
s.Logging.DEBUG("matched depends on", matchDependsOn)
baseError.Validator = "depends-on"
baseError.AddMessage("en", "this field depends on other values which do not exists")
errorMessages.AddError(string(target), baseError)
Expand All @@ -258,7 +257,7 @@ func (s *Schematics) ValidateObject(jsonData *map[string]interface{}, id *string

for key, value := range matchingKeys {
validationError := field.Validate(value, s.Validators.ValidationFns, &uniqueID)
Logs.DEBUG(validationError)
s.Logging.DEBUG(validationError)
if validationError != nil {
errorMessages.AddError(key, *validationError)
}
Expand All @@ -273,7 +272,7 @@ func (s *Schematics) ValidateObject(jsonData *map[string]interface{}, id *string
}

func (s *Schematics) ValidateArray(jsonData []map[string]interface{}) *errorHandler.Errors {
Logs.DEBUG("validating the array")
s.Logging.DEBUG("validating the array")
var errs errorHandler.Errors
i := 0
for _, d := range jsonData {
Expand All @@ -289,7 +288,7 @@ func (s *Schematics) ValidateArray(jsonData []map[string]interface{}) *errorHand
id := arrayId.(string)
errorMessages = s.ValidateObject(&d, &id)
if errorMessages.HasErrors() {
Logs.ERROR("has errors", errorMessages.GetStrings("en", "%data\n"))
s.Logging.ERROR("has errors", errorMessages.GetStrings("en", "%data\n"))
errs.MergeErrors(errorMessages)
}
i = i + 1
Expand All @@ -307,7 +306,7 @@ func (f *Field) Operate(value interface{}, allOperations map[string]operators.Op
for operationName, operationConstants := range f.Operators {
customValidator, exists := allOperations[operationName]
if !exists {
Logs.ERROR("This operation does not exists in basic or custom operators", operationName)
f.logging.ERROR("This operation does not exists in basic or custom operators", operationName)
return nil
}
result := customValidator(value, operationConstants.Attributes)
Expand All @@ -324,15 +323,15 @@ func (s *Schematics) Operate(data interface{}) (interface{}, *errorHandler.Error
baseError.Validator = "operate-on-schema"
bytes, err := json.Marshal(data)
if err != nil {
Logs.ERROR("[operate] error converting the data into bytes", err)
s.Logging.ERROR("[operate] error converting the data into bytes", err)
baseError.AddMessage("en", "data is not valid json")
errorMessages.AddError("whole-data", baseError)
return nil, &errorMessages
}

dataType, item := utils.IsValidJson(bytes)
if item == nil {
Logs.ERROR("[operate] error occurred when checking if this data is an array or object")
s.Logging.ERROR("[operate] error occurred when checking if this data is an array or object")
baseError.AddMessage("en", "can not convert the data into json")
errorMessages.AddError("whole-data", baseError)
return nil, &errorMessages
Expand Down
30 changes: 8 additions & 22 deletions data/v2/schema.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,12 +7,9 @@ import (
"github.com/ashbeelghouri/jsonschematics/operators"
"github.com/ashbeelghouri/jsonschematics/utils"
"github.com/ashbeelghouri/jsonschematics/validators"
"log"
"os"
)

var Logs utils.Logger

type Schematics struct {
Schema Schema
Validators validators.Validators
Expand Down Expand Up @@ -49,30 +46,15 @@ type Component struct {
L10n map[string]interface{} `json:"l10n"`
}

func (s *Schematics) Configs() {
Logs = s.Logging
if s.Logging.PrintDebugLogs {
log.Println("debugger is on")
}
if s.Logging.PrintErrorLogs {
log.Println("error logging is on")
}
s.Validators.Logger = Logs
s.Operators.Logger = Logs
}

func LoadJsonSchemaFile(path string) (*v0.Schematics, error) {
var s Schematics
s.Configs()
content, err := os.ReadFile(path)
if err != nil {
Logs.ERROR("Failed to load schema file", err)
return nil, err
}
var schema Schema
err = json.Unmarshal(content, &schema)
if err != nil {
Logs.ERROR("Failed to unmarshall schema file", err)
return nil, err
}
s.Schema = schema
Expand All @@ -86,16 +68,13 @@ func LoadJsonSchemaFile(path string) (*v0.Schematics, error) {

func LoadMap(schemaMap interface{}) (*v0.Schematics, error) {
var s Schematics
s.Configs()
jsonBytes, err := json.Marshal(schemaMap)
if err != nil {
Logs.ERROR("Schema should be valid json map[string]interface", err)
return nil, err
}
var schema Schema
err = json.Unmarshal(jsonBytes, &schema)
if err != nil {
Logs.ERROR("Failed to unmarshall schema file", err)
return nil, err
}
s.Schema = schema
Expand All @@ -104,7 +83,13 @@ func LoadMap(schemaMap interface{}) (*v0.Schematics, error) {

func transformSchematics(s Schematics) *v0.Schematics {
var baseSchematics v0.Schematics
baseSchematics.Logging = s.Logging
if s.Logging.PrintDebugLogs {
baseSchematics.Logging.PrintDebugLogs = true
}
if s.Logging.PrintErrorLogs {
baseSchematics.Logging.PrintErrorLogs = true
}

baseSchematics.ArrayIdKey = s.ArrayIdKey
baseSchematics.Separator = s.Separator
baseSchematics.Validators.BasicValidators()
Expand All @@ -117,6 +102,7 @@ func transformSchema(schema Schema) *v0.Schema {
var baseSchema v0.Schema
baseSchema.Version = schema.Version
baseSchema.Fields = make(map[v0.TargetKey]v0.Field)

for _, field := range schema.Fields {
baseSchema.Fields[v0.TargetKey(field.TargetKey)] = v0.Field{
DependsOn: field.DependsOn,
Expand Down
60 changes: 60 additions & 0 deletions test-data/data/direct/v2/example-3.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
{
"name": "iphone 15 - Blue - 128",
"phone": [
{
"label": "home",
"hidden": false,
"number": "+971523906401"
}
],
"Search": {
"tags": [
"iphone",
"15",
"blue",
"phone"
]
},
"saleor": {
"channelID": "",
"productID": "",
"variantID": "",
"warehouseID": ""
},
"features": [
{
"name": "Color",
"value": "Blue",
"additional_data": {}
},
{
"name": "Storage",
"value": "128",
"additional_data": {}
},
{
"name": "Height",
"value": "5.81 in",
"additional_data": {}
},
{
"name": "Width",
"value": "71.6 in",
"additional_data": {}
},
{
"name": "Depth",
"value": "0.31 in",
"additional_data": {}
},
{
"name": "Weight",
"value": "171 g",
"additional_data": {}
}
],
"quantity": 1,
"product_id": "2688f465-689c-4c55-9e77-c8c932e4043d",
"category_id": "10749d14-89b6-4c4a-a03c-873ecb1d3cb3",
"description": "Iphone 15, color is blue and have 256 GB of storage"
}
Loading

0 comments on commit c2daf86

Please sign in to comment.