handleStringCast handles casts to the string types that may have length restrictions. Returns an error if other types are passed in. Will always return the correct string, even on error, as some contexts may ignore the error.
(input string, targetType *pgtypes.DoltgresType)
| 31 | // handleStringCast handles casts to the string types that may have length restrictions. Returns an error if other types |
| 32 | // are passed in. Will always return the correct string, even on error, as some contexts may ignore the error. |
| 33 | func handleStringCast(input string, targetType *pgtypes.DoltgresType) (string, error) { |
| 34 | tm := targetType.GetAttTypMod() |
| 35 | switch targetType.ID { |
| 36 | case pgtypes.BpChar.ID: |
| 37 | if tm == -1 { |
| 38 | return input, nil |
| 39 | } |
| 40 | maxChars, err := pgtypes.GetTypModFromCharLength("char", tm) |
| 41 | if err != nil { |
| 42 | return "", err |
| 43 | } |
| 44 | length := uint32(maxChars) |
| 45 | str, runeLength := truncateString(input, length) |
| 46 | if runeLength > length { |
| 47 | return input, cerrors.Wrap(pgtypes.ErrCastOutOfRange, fmt.Sprintf("value too long for type %s", targetType.String())) |
| 48 | } else if runeLength < length { |
| 49 | return str + strings.Repeat(" ", int(length-runeLength)), nil |
| 50 | } else { |
| 51 | return str, nil |
| 52 | } |
| 53 | case pgtypes.InternalChar.ID: |
| 54 | str, _ := truncateString(input, pgtypes.InternalCharLength) |
| 55 | return str, nil |
| 56 | case pgtypes.Name.ID: |
| 57 | // Name seems to never throw an error, regardless of the context or how long the input is |
| 58 | str, _ := truncateString(input, uint32(targetType.TypLength)) |
| 59 | return str, nil |
| 60 | case pgtypes.VarChar.ID: |
| 61 | if tm == -1 { |
| 62 | return input, nil |
| 63 | } |
| 64 | length := uint32(pgtypes.GetCharLengthFromTypmod(tm)) |
| 65 | str, runeLength := truncateString(input, length) |
| 66 | if runeLength > length { |
| 67 | return input, cerrors.Wrap(pgtypes.ErrCastOutOfRange, fmt.Sprintf("value too long for type %s", targetType.String())) |
| 68 | } else { |
| 69 | return str, nil |
| 70 | } |
| 71 | default: |
| 72 | return "", cerrors.Errorf("internal cast called to handle non-string type") |
| 73 | } |
| 74 | } |
| 75 | |
| 76 | // truncateString returns a string that has been truncated to the given length. Uses the rune count rather than the |
| 77 | // byte count. Returns the input string if it's smaller than the length. Also returns the rune count of the string. |
no test coverage detected