Commits
Diff
diff --git a/search/main.go b/search/main.go
index 4d351cb..4cd3f51 100644
--- a/search/main.go
+++ b/search/main.go
@@ -4,4 +4 @@ import (
- "fmt"
- "reflect"
- "regexp"
- "strconv"
+ "logc/parser"
@@ -11,19 +8,2 @@ import (
-func All(data []interface{}, filters, removes, replaces []string, replaceFile string) []interface{} {
- filter := [][]string{}
- for _, v := range filters {
- target, match := splitFilterString(v)
- filter = append(filter, []string{target, match})
- }
- // !ISSUE: Load file first
- replace := [][]string{}
- for _, v := range replaces {
- target, match, replacement := splitReplaceString(v)
- replace = append(replace, []string{target, match, replacement})
- }
-
- remove := []string{}
- for _, v := range removes {
- remove = append(remove, v)
- }
-
- grouped := []interface{}{}
+func Text(comments []parser.Comment, headers, query string) []parser.Comment {
+ headerFilter := []parser.Comment{}
@@ -31,2 +11 @@ func All(data []interface{}, filters, removes, replaces []string, replaceFile st
- for i := range data {
- val := reflect.ValueOf(data[i])
+ headerList := strings.Split(headers, ",")
@@ -34,27 +13,5 @@ func All(data []interface{}, filters, removes, replaces []string, replaceFile st
- if val.Kind() == reflect.Ptr && val.Elem().Kind() == reflect.Struct {
- // Already a pointer to struct
- removeFields(data[i], remove)
- m := filterFields(data[i], filter)
- if m {
- replaceFields(data[i], replace)
- grouped = append(grouped, data[i])
- }
- } else if val.Kind() == reflect.Struct {
- // It's a struct, we need to work with a pointer
- // Create a copy we can modify
- ptrToNewCopy := reflect.New(val.Type())
- ptrToNewCopy.Elem().Set(val)
-
- // Modify the copy
- removeFields(ptrToNewCopy.Interface(), remove)
- m := filterFields(ptrToNewCopy.Interface(), filter)
-
- if m {
- replaceFields(ptrToNewCopy.Interface(), replace)
- data[i] = ptrToNewCopy.Elem().Interface()
- grouped = append(grouped, data[i])
- }
- } else {
- fmt.Printf("Skipping element at index %d: not a struct or pointer to struct\n", i)
- }
- }
+ if headers == "" {
+ for _, v := range comments {
+ for i, h := range v.Headers {
+ if h[0] == '[' {
+ v.Headers[i] = h[strings.Index(h, "]")+1:]
@@ -62,42 +18,0 @@ func All(data []interface{}, filters, removes, replaces []string, replaceFile st
- return grouped
-}
-
-func removeFields(data interface{}, query []string) {
- val := reflect.ValueOf(data)
- if val.Kind() != reflect.Ptr || val.Elem().Kind() != reflect.Struct {
- fmt.Println("removeFields: data must be a pointer to a struct")
- return
- }
-
- val = val.Elem() // Get the struct value the pointer points to
- typ := val.Type()
-
- for i := 0; i < val.NumField(); i++ {
- field := val.Field(i)
- fieldType := typ.Field(i)
- name := fieldType.Name
-
- // Check if this field needs to be zeroed
- for _, v := range query {
- if strings.Contains(v, ".") {
- // Handle nested fields
- vs := strings.Split(v, ".")
- if strings.EqualFold(name, strings.TrimSpace(vs[0])) {
- remainingPath := strings.Join(vs[1:], ".")
-
- if field.Kind() == reflect.Ptr && !field.IsNil() && field.Elem().Kind() == reflect.Struct {
- // Field is a pointer to struct
- removeFields(field.Interface(), []string{remainingPath})
- } else if field.Kind() == reflect.Struct {
- if field.CanAddr() {
- // Field is a struct that we can get address of
- removeFields(field.Addr().Interface(), []string{remainingPath})
- }
- }
- }
- } else if strings.EqualFold(name, strings.TrimSpace(v)) {
- // Zero out this field
- if field.CanSet() {
- field.Set(reflect.Zero(field.Type()))
- } else {
- fmt.Printf("Cannot set field %s\n", name)
@@ -107,42 +22,29 @@ func removeFields(data interface{}, query []string) {
-
- // Recursively process nested structs (not already processed with dot notation)
- if field.Kind() == reflect.Ptr && !field.IsNil() && field.Elem().Kind() == reflect.Struct {
- removeFields(field.Interface(), query)
- } else if field.Kind() == reflect.Struct {
- if field.CanAddr() {
- removeFields(field.Addr().Interface(), query)
- }
- }
- }
-}
-
-func filterFields(data interface{}, query [][]string) bool {
- if len(query) == 0 {
- return true
- }
- val := reflect.ValueOf(data)
- // Ensure we're working with a pointer to a struct
- if val.Kind() != reflect.Ptr || val.Elem().Kind() != reflect.Struct {
- fmt.Println("filterFields: data must be a pointer to a struct")
- return false
- }
-
- val = val.Elem()
- typ := val.Type()
- matches := false
-
- for i := 0; i < val.NumField(); i++ {
- field := val.Field(i)
- fieldType := typ.Field(i)
- name := fieldType.Name
-
- for _, v := range query {
- key := v[0]
- exp := v[1]
- if strings.Contains(key, ".") {
- vs := strings.Split(key, ".")
-
- if strings.EqualFold(name, strings.TrimSpace(vs[0])) {
- if field.Kind() == reflect.Struct && field.CanAddr() {
- if filterFields(field.Addr().Interface(), [][]string{[]string{strings.Join(vs[1:], "."), exp}}) {
- matches = true
+ headerFilter = comments
+ } else {
+ for j, v := range comments {
+ match := false
+ headersAndTags := v.Headers
+ headersAndTags = append(headersAndTags, v.Tags...)
+ for _, h := range headersAndTags {
+ // !DEVMAN: This is the logic for pulling out optional headers
+ if len(h) > 0 && h[0] == '[' {
+ tags := strings.Split(h[1:strings.Index(h, "]")], ",")
+ m := false
+ for _, s := range tags {
+ b := false
+ for _, t := range headerList {
+ if s[0] == '!' {
+ if t == s[1:] {
+ m = true
+ b = true
+ break
+ } else {
+ m = false
+ }
+ } else if t == s {
+ m = true
+ } else if t == headersAndTags[0] {
+ m = true
+ }
+ }
+ if b {
@@ -152,30 +53,0 @@ func filterFields(data interface{}, query [][]string) bool {
- }
- } else if strings.EqualFold(name, strings.TrimSpace(key)) {
- str := []byte(fmt.Sprintf("%v", field.Interface()))
-
- matches, _ = regexp.Match(exp, str)
- if matches {
- break
- }
- }
- }
-
- if matches {
- break
- }
- }
- return matches
-}
-
-func replaceFields(data interface{}, query [][]string) bool {
- val := reflect.ValueOf(data)
-
- // Ensure we're working with a pointer to a struct
- if val.Kind() != reflect.Ptr || val.Elem().Kind() != reflect.Struct {
- fmt.Println("replaceFields: data must be a pointer to a struct")
- return false
- }
-
- val = val.Elem() // Get the value the pointer points to.
- typ := val.Type()
- matches := false // Track if any replacements were made
@@ -183,20 +55,6 @@ func replaceFields(data interface{}, query [][]string) bool {
- // Iterate over the fields of the struct.
- for i := 0; i < val.NumField(); i++ {
- field := val.Field(i) // The field's value.
- fieldType := typ.Field(i) // The field's type.
- name := fieldType.Name // The field's name.
-
- // Iterate over the query items.
- for _, v := range query {
- key := v[0]
- exp := v[1]
- rep := v[2]
- // Handle nested fields (e.g., "Nested.Field").
- if strings.Contains(key, ".") {
- parts := strings.Split(key, ".")
- if strings.EqualFold(name, strings.TrimSpace(parts[0])) {
- // Check if the field is a struct and addressable.
- if field.Kind() == reflect.Struct && field.CanAddr() {
- // Recursively call replaceFields on the nested struct.
- nestedQuery := [][]string{
- {strings.Join(parts[1:], "."), exp, rep}, // Pass the rest of the path.
+ if !m {
+ for i, k := range v.Headers {
+ if k == h {
+ comments[j].Headers[i] = ""
+ comments[j].Data[i] = ""
+ }
@@ -204,2 +62,6 @@ func replaceFields(data interface{}, query [][]string) bool {
- if replaceFields(field.Addr().Interface(), nestedQuery) {
- matches = true // Track if nested call made a replacement
+ } else {
+ // Remove the brackets if it matches
+ for i, k := range v.Headers {
+ if k == h {
+ comments[j].Headers[i] = h[strings.Index(h, "]")+1:]
+ }
@@ -208,10 +69,0 @@ func replaceFields(data interface{}, query [][]string) bool {
- }
- } else if strings.EqualFold(name, strings.TrimSpace(key)) && field.CanSet() {
- re, err := regexp.Compile(exp) // Compile the regex.
- if err != nil {
- fmt.Printf("replaceFields: invalid regex: %s, error: %v\n", exp, err)
- continue // Skip this query item if the regex is invalid.
- }
- if field.Kind() == reflect.Slice {
- sliceVal := reflect.ValueOf(field.Interface())
- newSlice := reflect.MakeSlice(field.Type(), sliceVal.Len(), sliceVal.Len())
@@ -219,14 +71 @@ func replaceFields(data interface{}, query [][]string) bool {
- for j := 0; j < sliceVal.Len(); j++ {
- sliceElem := sliceVal.Index(j)
- str := fmt.Sprintf("%v", sliceElem.Interface())
- newValueStr := re.ReplaceAllString(str, rep)
-
- newValue, err := convertStringToType(newValueStr, sliceElem.Kind())
- if err != nil {
- fmt.Printf("replaceFields: error converting '%s' to %s for slice element of field '%s': %v\n", newValueStr, sliceElem.Type(), name, err)
- continue // Skip on error, or handle as appropriate
- }
- newSlice.Index(j).Set(reflect.ValueOf(newValue).Convert(sliceElem.Type()))
- }
- field.Set(newSlice)
- matches = true
+ match = m
@@ -234,11 +73,4 @@ func replaceFields(data interface{}, query [][]string) bool {
- // Field name matches, and the field is settable.
- str := fmt.Sprintf("%v", field.Interface()) // Convert field value to string.
-
- newValueStr := re.ReplaceAllString(str, rep) // Apply the replacement.
-
- // Convert the new string value back to the field's original type.
- newValue, err := convertStringToType(newValueStr, field.Kind())
-
- if err != nil {
- fmt.Printf("replaceFields: error converting '%s' to %s for field '%s': %v\n", newValueStr, field.Type(), name, err)
- continue // Skip if conversion fails.
+ for _, t := range headerList {
+ if t == h && !match {
+ match = true
+ }
@@ -247,2 +78,0 @@ func replaceFields(data interface{}, query [][]string) bool {
- field.Set(reflect.ValueOf(newValue)) // Set the field's new value.
- matches = true // Indicate a replacement was made.
@@ -250,9 +79,0 @@ func replaceFields(data interface{}, query [][]string) bool {
- }
- }
- }
- return matches // Return whether any replacements occurred.
-}
-
-func splitFilterString(str string) (string, string) {
- var target, match string
- targetDone, matchDone := false, false
@@ -260,10 +80,0 @@ func splitFilterString(str string) (string, string) {
- escaped := false
- slashCount := 0
-
- for _, v := range str {
-
- if !targetDone {
- if v != 61 || (v == 61 && escaped) {
- target += string(v)
- } else if !escaped {
- targetDone = true
@@ -271,5 +82,4 @@ func splitFilterString(str string) (string, string) {
- } else if targetDone && !matchDone && slashCount == 1 {
- if v != 47 || (v == 47 && escaped) {
- match += string(v)
- } else {
- matchDone = true
+ if match {
+ v.Headers = removeEmpty(v.Headers)
+ v.Data = removeEmpty(v.Data)
+ headerFilter = append(headerFilter, v)
@@ -277,12 +86,0 @@ func splitFilterString(str string) (string, string) {
- } else if slashCount == 2 && targetDone && matchDone {
- break
- }
-
- if v == 47 && !escaped {
- slashCount++
- }
- if escaped {
- escaped = false
- }
- if v == 92 {
- escaped = true
@@ -291 +88,0 @@ func splitFilterString(str string) (string, string) {
- return target, match
@@ -293 +90 @@ func splitFilterString(str string) (string, string) {
-}
+ queryFilter := []parser.Comment{}
@@ -295,3 +92,7 @@ func splitFilterString(str string) (string, string) {
-func splitReplaceString(str string) (string, string, string) {
- var target, match, replace string
- targetDone, matchDone, replaceDone := false, false, false
+ if query == "" {
+ return headerFilter
+ } else {
+ lowerQuery := strings.ToLower(query)
+ for _, v := range headerFilter {
+ text := strings.Join(v.Data, " ")
+ text += strings.Join(v.Headers, " ")
@@ -299,24 +100 @@ func splitReplaceString(str string) (string, string, string) {
- escaped := false
- slashCount := 0
- for _, v := range str {
- if !targetDone {
- if v != 61 || (v == 61 && escaped) {
- target += string(v)
- } else if !escaped {
- targetDone = true
- }
- } else if targetDone && !matchDone && slashCount == 1 {
- if v != 47 || (v == 47 && escaped) {
- match += string(v)
- } else {
- matchDone = true
- }
- } else if targetDone && matchDone && !replaceDone && slashCount == 2 {
- if v != 47 || (v == 47 && escaped) {
- replace += string(v)
- } else {
- replaceDone = true
- }
- } else if slashCount == 3 && targetDone && matchDone && replaceDone {
- break
- }
+ text = strings.ToLower(text)
@@ -324,8 +102,3 @@ func splitReplaceString(str string) (string, string, string) {
- if v == 47 && !escaped {
- slashCount++
- }
- if escaped {
- escaped = false
- }
- if v == 92 {
- escaped = true
+ if strings.Contains(text, lowerQuery) {
+ queryFilter = append(queryFilter, v)
+ }
@@ -334,2 +107 @@ func splitReplaceString(str string) (string, string, string) {
- return target, match, replace
-
+ return queryFilter
@@ -338,54 +110,6 @@ func splitReplaceString(str string) (string, string, string) {
-func convertStringToType(s string, kind reflect.Kind) (interface{}, error) {
- switch kind {
- case reflect.String:
- return s, nil
- case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
- i, err := strconv.ParseInt(s, 10, 64)
- if err != nil {
- return nil, err
- }
- // Further convert to the specific integer type if necessary.
- switch kind {
- case reflect.Int8:
- return int8(i), nil
- case reflect.Int16:
- return int16(i), nil
- case reflect.Int32:
- return int32(i), nil
- case reflect.Int64:
- return i, nil
- case reflect.Int:
- return int(i), nil
- }
- return i, nil
- case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
- u, err := strconv.ParseUint(s, 10, 64)
- if err != nil {
- return nil, err
- }
- switch kind {
- case reflect.Uint8:
- return uint8(u), nil
- case reflect.Uint16:
- return uint16(u), nil
- case reflect.Uint32:
- return uint32(u), nil
- case reflect.Uint64:
- return u, nil
- case reflect.Uint:
- return uint(u), nil
- }
- return u, nil
- case reflect.Float32, reflect.Float64:
- f, err := strconv.ParseFloat(s, 64)
- if err != nil {
- return nil, err
- }
- if kind == reflect.Float32 {
- return float32(f), nil
- }
- return f, nil
- case reflect.Bool:
- b, err := strconv.ParseBool(s)
- if err != nil {
- return nil, err
+func removeEmpty(input []string) []string {
+ // Create a new slice to hold non-empty strings
+ nonEmpty := []string{}
+ for _, str := range input {
+ if str != "" { // Check if the string is not empty
+ nonEmpty = append(nonEmpty, str)
@@ -393,3 +116,0 @@ func convertStringToType(s string, kind reflect.Kind) (interface{}, error) {
- return b, nil
- default:
- return nil, fmt.Errorf("unsupported type: %v", kind)
@@ -396,0 +118 @@ func convertStringToType(s string, kind reflect.Kind) (interface{}, error) {
+ return nonEmpty
package search
import (
"fmt"
"reflect"
"regexp"
"strconv"
"strings"
)
func All(data []interface{}, filters, removes, replaces []string, replaceFile string) []interface{} {
filter := [][]string{}
for _, v := range filters {
target, match := splitFilterString(v)
filter = append(filter, []string{target, match})
}
// !ISSUE: Load file first
replace := [][]string{}
for _, v := range replaces {
target, match, replacement := splitReplaceString(v)
replace = append(replace, []string{target, match, replacement})
}
remove := []string{}
for _, v := range removes {
remove = append(remove, v)
}
grouped := []interface{}{}
for i := range data {
val := reflect.ValueOf(data[i])
if val.Kind() == reflect.Ptr && val.Elem().Kind() == reflect.Struct {
// Already a pointer to struct
removeFields(data[i], remove)
m := filterFields(data[i], filter)
if m {
replaceFields(data[i], replace)
grouped = append(grouped, data[i])
}
} else if val.Kind() == reflect.Struct {
// It's a struct, we need to work with a pointer
// Create a copy we can modify
ptrToNewCopy := reflect.New(val.Type())
ptrToNewCopy.Elem().Set(val)
// Modify the copy
removeFields(ptrToNewCopy.Interface(), remove)
m := filterFields(ptrToNewCopy.Interface(), filter)
if m {
replaceFields(ptrToNewCopy.Interface(), replace)
data[i] = ptrToNewCopy.Elem().Interface()
grouped = append(grouped, data[i])
}
} else {
fmt.Printf("Skipping element at index %d: not a struct or pointer to struct\n", i)
}
}
return grouped
}
func removeFields(data interface{}, query []string) {
val := reflect.ValueOf(data)
if val.Kind() != reflect.Ptr || val.Elem().Kind() != reflect.Struct {
fmt.Println("removeFields: data must be a pointer to a struct")
return
}
val = val.Elem() // Get the struct value the pointer points to
typ := val.Type()
for i := 0; i < val.NumField(); i++ {
field := val.Field(i)
fieldType := typ.Field(i)
name := fieldType.Name
// Check if this field needs to be zeroed
for _, v := range query {
if strings.Contains(v, ".") {
// Handle nested fields
vs := strings.Split(v, ".")
if strings.EqualFold(name, strings.TrimSpace(vs[0])) {
remainingPath := strings.Join(vs[1:], ".")
if field.Kind() == reflect.Ptr && !field.IsNil() && field.Elem().Kind() == reflect.Struct {
// Field is a pointer to struct
removeFields(field.Interface(), []string{remainingPath})
} else if field.Kind() == reflect.Struct {
if field.CanAddr() {
// Field is a struct that we can get address of
removeFields(field.Addr().Interface(), []string{remainingPath})
}
}
}
} else if strings.EqualFold(name, strings.TrimSpace(v)) {
// Zero out this field
if field.CanSet() {
field.Set(reflect.Zero(field.Type()))
} else {
fmt.Printf("Cannot set field %s\n", name)
}
}
}
// Recursively process nested structs (not already processed with dot notation)
if field.Kind() == reflect.Ptr && !field.IsNil() && field.Elem().Kind() == reflect.Struct {
removeFields(field.Interface(), query)
} else if field.Kind() == reflect.Struct {
if field.CanAddr() {
removeFields(field.Addr().Interface(), query)
}
}
}
}
func filterFields(data interface{}, query [][]string) bool {
if len(query) == 0 {
return true
}
val := reflect.ValueOf(data)
// Ensure we're working with a pointer to a struct
if val.Kind() != reflect.Ptr || val.Elem().Kind() != reflect.Struct {
fmt.Println("filterFields: data must be a pointer to a struct")
return false
}
val = val.Elem()
typ := val.Type()
matches := false
for i := 0; i < val.NumField(); i++ {
field := val.Field(i)
fieldType := typ.Field(i)
name := fieldType.Name
for _, v := range query {
key := v[0]
exp := v[1]
if strings.Contains(key, ".") {
vs := strings.Split(key, ".")
if strings.EqualFold(name, strings.TrimSpace(vs[0])) {
if field.Kind() == reflect.Struct && field.CanAddr() {
if filterFields(field.Addr().Interface(), [][]string{[]string{strings.Join(vs[1:], "."), exp}}) {
matches = true
break
}
}
}
} else if strings.EqualFold(name, strings.TrimSpace(key)) {
str := []byte(fmt.Sprintf("%v", field.Interface()))
matches, _ = regexp.Match(exp, str)
if matches {
break
}
}
}
if matches {
break
}
}
return matches
}
func replaceFields(data interface{}, query [][]string) bool {
val := reflect.ValueOf(data)
// Ensure we're working with a pointer to a struct
if val.Kind() != reflect.Ptr || val.Elem().Kind() != reflect.Struct {
fmt.Println("replaceFields: data must be a pointer to a struct")
return false
}
val = val.Elem() // Get the value the pointer points to.
typ := val.Type()
matches := false // Track if any replacements were made
// Iterate over the fields of the struct.
for i := 0; i < val.NumField(); i++ {
field := val.Field(i) // The field's value.
fieldType := typ.Field(i) // The field's type.
name := fieldType.Name // The field's name.
// Iterate over the query items.
for _, v := range query {
key := v[0]
exp := v[1]
rep := v[2]
// Handle nested fields (e.g., "Nested.Field").
if strings.Contains(key, ".") {
parts := strings.Split(key, ".")
if strings.EqualFold(name, strings.TrimSpace(parts[0])) {
// Check if the field is a struct and addressable.
if field.Kind() == reflect.Struct && field.CanAddr() {
// Recursively call replaceFields on the nested struct.
nestedQuery := [][]string{
{strings.Join(parts[1:], "."), exp, rep}, // Pass the rest of the path.
}
if replaceFields(field.Addr().Interface(), nestedQuery) {
matches = true // Track if nested call made a replacement
}
}
}
} else if strings.EqualFold(name, strings.TrimSpace(key)) && field.CanSet() {
re, err := regexp.Compile(exp) // Compile the regex.
if err != nil {
fmt.Printf("replaceFields: invalid regex: %s, error: %v\n", exp, err)
continue // Skip this query item if the regex is invalid.
}
if field.Kind() == reflect.Slice {
sliceVal := reflect.ValueOf(field.Interface())
newSlice := reflect.MakeSlice(field.Type(), sliceVal.Len(), sliceVal.Len())
for j := 0; j < sliceVal.Len(); j++ {
sliceElem := sliceVal.Index(j)
str := fmt.Sprintf("%v", sliceElem.Interface())
newValueStr := re.ReplaceAllString(str, rep)
newValue, err := convertStringToType(newValueStr, sliceElem.Kind())
if err != nil {
fmt.Printf("replaceFields: error converting '%s' to %s for slice element of field '%s': %v\n", newValueStr, sliceElem.Type(), name, err)
continue // Skip on error, or handle as appropriate
}
newSlice.Index(j).Set(reflect.ValueOf(newValue).Convert(sliceElem.Type()))
}
field.Set(newSlice)
matches = true
} else {
// Field name matches, and the field is settable.
str := fmt.Sprintf("%v", field.Interface()) // Convert field value to string.
newValueStr := re.ReplaceAllString(str, rep) // Apply the replacement.
// Convert the new string value back to the field's original type.
newValue, err := convertStringToType(newValueStr, field.Kind())
if err != nil {
fmt.Printf("replaceFields: error converting '%s' to %s for field '%s': %v\n", newValueStr, field.Type(), name, err)
continue // Skip if conversion fails.
}
field.Set(reflect.ValueOf(newValue)) // Set the field's new value.
matches = true // Indicate a replacement was made.
}
}
}
}
return matches // Return whether any replacements occurred.
}
func splitFilterString(str string) (string, string) {
var target, match string
targetDone, matchDone := false, false
escaped := false
slashCount := 0
for _, v := range str {
if !targetDone {
if v != 61 || (v == 61 && escaped) {
target += string(v)
} else if !escaped {
targetDone = true
}
} else if targetDone && !matchDone && slashCount == 1 {
if v != 47 || (v == 47 && escaped) {
match += string(v)
} else {
matchDone = true
}
} else if slashCount == 2 && targetDone && matchDone {
break
}
if v == 47 && !escaped {
slashCount++
}
if escaped {
escaped = false
}
if v == 92 {
escaped = true
}
}
return target, match
}
func splitReplaceString(str string) (string, string, string) {
var target, match, replace string
targetDone, matchDone, replaceDone := false, false, false
escaped := false
slashCount := 0
for _, v := range str {
if !targetDone {
if v != 61 || (v == 61 && escaped) {
target += string(v)
} else if !escaped {
targetDone = true
}
} else if targetDone && !matchDone && slashCount == 1 {
if v != 47 || (v == 47 && escaped) {
match += string(v)
} else {
matchDone = true
}
} else if targetDone && matchDone && !replaceDone && slashCount == 2 {
if v != 47 || (v == 47 && escaped) {
replace += string(v)
} else {
replaceDone = true
}
} else if slashCount == 3 && targetDone && matchDone && replaceDone {
break
}
if v == 47 && !escaped {
slashCount++
}
if escaped {
escaped = false
}
if v == 92 {
escaped = true
}
}
return target, match, replace
}
func convertStringToType(s string, kind reflect.Kind) (interface{}, error) {
switch kind {
case reflect.String:
return s, nil
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
i, err := strconv.ParseInt(s, 10, 64)
if err != nil {
return nil, err
}
// Further convert to the specific integer type if necessary.
switch kind {
case reflect.Int8:
return int8(i), nil
case reflect.Int16:
return int16(i), nil
case reflect.Int32:
return int32(i), nil
case reflect.Int64:
return i, nil
case reflect.Int:
return int(i), nil
}
return i, nil
case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
u, err := strconv.ParseUint(s, 10, 64)
if err != nil {
return nil, err
}
switch kind {
case reflect.Uint8:
return uint8(u), nil
case reflect.Uint16:
return uint16(u), nil
case reflect.Uint32:
return uint32(u), nil
case reflect.Uint64:
return u, nil
case reflect.Uint:
return uint(u), nil
}
return u, nil
case reflect.Float32, reflect.Float64:
f, err := strconv.ParseFloat(s, 64)
if err != nil {
return nil, err
}
if kind == reflect.Float32 {
return float32(f), nil
}
return f, nil
case reflect.Bool:
b, err := strconv.ParseBool(s)
if err != nil {
return nil, err
}
return b, nil
default:
return nil, fmt.Errorf("unsupported type: %v", kind)
}
}