@@ -2,6 +2,7 @@ package transformers
22
33import (
44 "fmt"
5+ "strings"
56 "testing"
67
78 "github.com/nucleuscloud/neosync/worker/pkg/rng"
@@ -85,3 +86,177 @@ func Test_TransformFullNamelTransformer_NoOptions(t *testing.T) {
8586 assert .NoError (t , err )
8687 assert .NotEmpty (t , res )
8788}
89+
90+ func Test_TransformFullNamePreserveLengthSingleName (t * testing.T ) {
91+ t .Run ("single name with preserve length" , func (t * testing.T ) {
92+ randomizer := rng .New (1 )
93+ singleName := "John"
94+ expectedLength := int64 (len (singleName ))
95+
96+ // Debug: Let's see what splitEvenly returns
97+ firstname , lastname := splitEvenly (singleName )
98+ t .Logf ("splitEvenly('%s') = firstname: '%s' (len: %d), lastname: '%s' (len: %d)" ,
99+ singleName , firstname , len (firstname ), lastname , len (lastname ))
100+
101+ res , err := transformFullName (randomizer , singleName , true , maxCharacterLimit )
102+
103+ assert .NoError (t , err )
104+ assert .NotNil (t , res )
105+ t .Logf ("Input: '%s' (len: %d), Output: '%s' (len: %d)" ,
106+ singleName , len (singleName ), * res , len (* res ))
107+ assert .Equal (t , expectedLength , int64 (len (* res )), "The output should be the same length as the input" )
108+ assert .Contains (t , * res , " " , "Should contain a space between first and last name" )
109+ })
110+
111+ t .Run ("single name with preserve length via bloblang" , func (t * testing.T ) {
112+ singleName := "John"
113+ mapping := fmt .Sprintf (`root = transform_full_name(value:%q,preserve_length:true,max_length:%d)` , singleName , maxCharacterLimit )
114+ ex , err := bloblang .Parse (mapping )
115+ assert .NoError (t , err , "failed to parse the full name transformer" )
116+
117+ res , err := ex .Query (singleName )
118+ assert .NoError (t , err )
119+
120+ resStr , ok := res .(* string )
121+ if ! ok {
122+ t .Errorf ("Expected *string, got %T" , res )
123+ return
124+ }
125+
126+ assert .NotNil (t , resStr )
127+ t .Logf ("Bloblang Input: '%s' (len: %d), Output: '%s' (len: %d)" ,
128+ singleName , len (singleName ), * resStr , len (* resStr ))
129+ assert .Equal (t , len (singleName ), len (* resStr ), "Generated full name must be as long as input name" )
130+ assert .Contains (t , * resStr , " " , "Should contain a space between first and last name" )
131+ })
132+ }
133+
134+ func Test_TransformFullNamePreserveLengthShortLastName (t * testing.T ) {
135+ t .Run ("name with short last name" , func (t * testing.T ) {
136+ randomizer := rng .New (1 )
137+ nameWithShortLastName := "John A"
138+ expectedLength := int64 (len (nameWithShortLastName ))
139+
140+ res , err := transformFullName (randomizer , nameWithShortLastName , true , maxCharacterLimit )
141+
142+ assert .NoError (t , err )
143+ assert .NotNil (t , res )
144+ assert .Equal (t , expectedLength , int64 (len (* res )), "The output should be the same length as the input" )
145+ assert .Contains (t , * res , " " , "Should contain a space between first and last name" )
146+ })
147+ }
148+
149+ func Test_TransformFullNamePreserveLengthMultipleWords (t * testing.T ) {
150+ t .Run ("name with multiple words" , func (t * testing.T ) {
151+ randomizer := rng .New (1 )
152+ multiWordName := "John van der Berg"
153+ expectedLength := int64 (len (multiWordName ))
154+
155+ res , err := transformFullName (randomizer , multiWordName , true , maxCharacterLimit )
156+
157+ assert .NoError (t , err )
158+ assert .NotNil (t , res )
159+ assert .Equal (t , expectedLength , int64 (len (* res )), "The output should be the same length as the input" )
160+ assert .Contains (t , * res , " " , "Should contain spaces between name parts" )
161+ })
162+ }
163+
164+ func Test_TransformFullNamePreserveLengthEdgeCases (t * testing.T ) {
165+ t .Run ("very short name" , func (t * testing.T ) {
166+ randomizer := rng .New (1 )
167+ shortName := "A"
168+ expectedLength := int64 (len (shortName ))
169+
170+ res , err := transformFullName (randomizer , shortName , true , maxCharacterLimit )
171+
172+ assert .NoError (t , err )
173+ assert .NotNil (t , res )
174+ assert .Equal (t , expectedLength , int64 (len (* res )), "The output should be the same length as the input" )
175+ })
176+
177+ t .Run ("name with only spaces" , func (t * testing.T ) {
178+ randomizer := rng .New (1 )
179+ spaceName := " "
180+
181+ res , err := transformFullName (randomizer , spaceName , true , maxCharacterLimit )
182+
183+ assert .NoError (t , err )
184+ assert .NotNil (t , res )
185+ assert .Equal (t , int64 (len (spaceName )), int64 (len (* res )), "The output should be the same length as the input" )
186+ })
187+ }
188+
189+ func Test_SplitEvenly (t * testing.T ) {
190+ t .Run ("even number of words" , func (t * testing.T ) {
191+ first , last := splitEvenly ("John Smith" )
192+ assert .Equal (t , "John" , first )
193+ assert .Equal (t , "Smith" , last )
194+ })
195+
196+ t .Run ("odd number of words" , func (t * testing.T ) {
197+ first , last := splitEvenly ("John van der Berg" )
198+ assert .Equal (t , "John van" , first )
199+ assert .Equal (t , "der Berg" , last )
200+ })
201+
202+ t .Run ("single word" , func (t * testing.T ) {
203+ first , last := splitEvenly ("John" )
204+ assert .Equal (t , "John" , first )
205+ assert .Equal (t , "" , last )
206+ })
207+
208+ t .Run ("empty string" , func (t * testing.T ) {
209+ first , last := splitEvenly ("" )
210+ assert .Equal (t , "" , first )
211+ assert .Equal (t , "" , last )
212+ })
213+
214+ t .Run ("multiple spaces" , func (t * testing.T ) {
215+ first , last := splitEvenly ("John Smith" )
216+ assert .Equal (t , "John" , first )
217+ assert .Equal (t , "Smith" , last )
218+ })
219+ }
220+
221+ func Test_TransformFullNamePreserveLength_FirstNameFallback (t * testing.T ) {
222+ t .Run ("first name fallback to random string padding" , func (t * testing.T ) {
223+ randomizer := rng .New (1 )
224+ // Use a name with a length that is unlikely to exist in the corpus (e.g., 1 character)
225+ name := "A B"
226+ res , err := transformFullName (randomizer , name , true , maxCharacterLimit )
227+ assert .NoError (t , err )
228+ assert .NotNil (t , res )
229+ assert .Equal (t , len (name ), len (* res ), "Output should match input length" )
230+ assert .Contains (t , * res , " " , "Should contain a space" )
231+ // The first and last name parts should each be 1 character (plus the space)
232+ parts := strings .SplitN (* res , " " , 2 )
233+ if len (parts ) == 2 {
234+ assert .Len (t , parts [0 ], 1 , "First name part should be 1 char (padded if needed)" )
235+ assert .Len (t , parts [1 ], 1 , "Last name part should be 1 char (padded if needed)" )
236+ }
237+ })
238+ }
239+
240+ func Test_TransformFullNamePreserveLength_PadAndTruncate (t * testing.T ) {
241+ t .Run ("padding when generated name is shorter than input" , func (t * testing.T ) {
242+ randomizer := rng .New (1 )
243+ // Use a name with a length that is longer than typical generated names
244+ name := "John Smith ExtraLongName"
245+ res , err := transformFullName (randomizer , name , true , maxCharacterLimit )
246+ assert .NoError (t , err )
247+ assert .NotNil (t , res )
248+ assert .Equal (t , len (name ), len (* res ), "Output should match input length" )
249+ assert .Contains (t , * res , " " , "Should contain a space" )
250+ })
251+
252+ t .Run ("truncation when generated name is longer than input" , func (t * testing.T ) {
253+ randomizer := rng .New (1 )
254+ // Use a very short name so the generated name will be truncated
255+ name := "Jo Sm"
256+ res , err := transformFullName (randomizer , name , true , maxCharacterLimit )
257+ assert .NoError (t , err )
258+ assert .NotNil (t , res )
259+ assert .Equal (t , len (name ), len (* res ), "Output should match input length" )
260+ assert .Contains (t , * res , " " , "Should contain a space" )
261+ })
262+ }
0 commit comments