1" Test for commands that operate on the spellfile.
2
3source shared.vim
4source check.vim
5
6CheckFeature spell
7CheckFeature syntax
8
9func Test_spell_normal()
10  new
11  call append(0, ['1 good', '2 goood', '3 goood'])
12  set spell spellfile=./Xspellfile.add spelllang=en
13  let oldlang=v:lang
14  lang C
15
16  " Test for zg
17  1
18  norm! ]s
19  call assert_equal('2 goood', getline('.'))
20  norm! zg
21  1
22  let a=execute('unsilent :norm! ]s')
23  call assert_equal('1 good', getline('.'))
24  call assert_equal('search hit BOTTOM, continuing at TOP', a[1:])
25  let cnt=readfile('./Xspellfile.add')
26  call assert_equal('goood', cnt[0])
27
28  " Test for zw
29  2
30  norm! $zw
31  1
32  norm! ]s
33  call assert_equal('2 goood', getline('.'))
34  let cnt=readfile('./Xspellfile.add')
35  call assert_equal('#oood', cnt[0])
36  call assert_equal('goood/!', cnt[1])
37
38  " Test for :spellrare
39  spellrare rare
40  let cnt=readfile('./Xspellfile.add')
41  call assert_equal(['#oood', 'goood/!', 'rare/?'], cnt)
42
43  " Make sure :spellundo works for rare words.
44  spellundo rare
45  let cnt=readfile('./Xspellfile.add')
46  call assert_equal(['#oood', 'goood/!', '#are/?'], cnt)
47
48  " Test for zg in visual mode
49  let a=execute('unsilent :norm! V$zg')
50  call assert_equal("Word '2 goood' added to ./Xspellfile.add", a[1:])
51  1
52  norm! ]s
53  call assert_equal('3 goood', getline('.'))
54  let cnt=readfile('./Xspellfile.add')
55  call assert_equal('2 goood', cnt[3])
56  " Remove "2 good" from spellfile
57  2
58  let a=execute('unsilent norm! V$zw')
59  call assert_equal("Word '2 goood' added to ./Xspellfile.add", a[1:])
60  let cnt=readfile('./Xspellfile.add')
61  call assert_equal('2 goood/!', cnt[4])
62
63  " Test for zG
64  let a=execute('unsilent norm! V$zG')
65  call assert_match("Word '2 goood' added to .*", a)
66  let fname=matchstr(a, 'to\s\+\zs\f\+$')
67  let cnt=readfile(fname)
68  call assert_equal('2 goood', cnt[0])
69
70  " Test for zW
71  let a=execute('unsilent norm! V$zW')
72  call assert_match("Word '2 goood' added to .*", a)
73  let cnt=readfile(fname)
74  call assert_equal('# goood', cnt[0])
75  call assert_equal('2 goood/!', cnt[1])
76
77  " Test for zuW
78  let a=execute('unsilent norm! V$zuW')
79  call assert_match("Word '2 goood' removed from .*", a)
80  let cnt=readfile(fname)
81  call assert_equal('# goood', cnt[0])
82  call assert_equal('# goood/!', cnt[1])
83
84  " Test for zuG
85  let a=execute('unsilent norm! $zG')
86  call assert_match("Word 'goood' added to .*", a)
87  let cnt=readfile(fname)
88  call assert_equal('# goood', cnt[0])
89  call assert_equal('# goood/!', cnt[1])
90  call assert_equal('goood', cnt[2])
91  let a=execute('unsilent norm! $zuG')
92  let cnt=readfile(fname)
93  call assert_match("Word 'goood' removed from .*", a)
94  call assert_equal('# goood', cnt[0])
95  call assert_equal('# goood/!', cnt[1])
96  call assert_equal('#oood', cnt[2])
97  " word not found in wordlist
98  let a=execute('unsilent norm! V$zuG')
99  let cnt=readfile(fname)
100  call assert_match("", a)
101  call assert_equal('# goood', cnt[0])
102  call assert_equal('# goood/!', cnt[1])
103  call assert_equal('#oood', cnt[2])
104
105  " Test for zug
106  call delete('./Xspellfile.add')
107  2
108  let a=execute('unsilent norm! $zg')
109  let cnt=readfile('./Xspellfile.add')
110  call assert_equal('goood', cnt[0])
111  let a=execute('unsilent norm! $zug')
112  call assert_match("Word 'goood' removed from \./Xspellfile.add", a)
113  let cnt=readfile('./Xspellfile.add')
114  call assert_equal('#oood', cnt[0])
115  " word not in wordlist
116  let a=execute('unsilent norm! V$zug')
117  call assert_match('', a)
118  let cnt=readfile('./Xspellfile.add')
119  call assert_equal('#oood', cnt[0])
120
121  " Test for zuw
122  call delete('./Xspellfile.add')
123  2
124  let a=execute('unsilent norm! Vzw')
125  let cnt=readfile('./Xspellfile.add')
126  call assert_equal('2 goood/!', cnt[0])
127  let a=execute('unsilent norm! Vzuw')
128  call assert_match("Word '2 goood' removed from \./Xspellfile.add", a)
129  let cnt=readfile('./Xspellfile.add')
130  call assert_equal('# goood/!', cnt[0])
131  " word not in wordlist
132  let a=execute('unsilent norm! $zug')
133  call assert_match('', a)
134  let cnt=readfile('./Xspellfile.add')
135  call assert_equal('# goood/!', cnt[0])
136
137  " add second entry to spellfile setting
138  set spellfile=./Xspellfile.add,./Xspellfile2.add
139  call delete('./Xspellfile.add')
140  2
141  let a=execute('unsilent norm! $2zg')
142  let cnt=readfile('./Xspellfile2.add')
143  call assert_match("Word 'goood' added to ./Xspellfile2.add", a)
144  call assert_equal('goood', cnt[0])
145
146  " Test for :spellgood!
147  let temp = execute(':spe!0/0')
148  call assert_match('Invalid region', temp)
149  let spellfile = matchstr(temp, 'Invalid region nr in \zs.*\ze line \d: 0')
150  call assert_equal(['# goood', '# goood/!', '#oood', '0/0'], readfile(spellfile))
151
152  " Test for :spellrare!
153  :spellrare! raare
154  call assert_equal(['# goood', '# goood/!', '#oood', '0/0', 'raare/?'], readfile(spellfile))
155  call delete(spellfile)
156
157  " clean up
158  exe "lang" oldlang
159  call delete("./Xspellfile.add")
160  call delete("./Xspellfile2.add")
161  call delete("./Xspellfile.add.spl")
162  call delete("./Xspellfile2.add.spl")
163
164  " zux -> no-op
165  2
166  norm! $zux
167  call assert_equal([], glob('Xspellfile.add',0,1))
168  call assert_equal([], glob('Xspellfile2.add',0,1))
169
170  set spellfile= spell& spelllang&
171  bw!
172endfunc
173
174" Spell file content test. Write 'content' to the spell file prefixed by the
175" spell file header and then enable spell checking. If 'emsg' is not empty,
176" then check for error.
177func Spellfile_Test(content, emsg)
178  let splfile = './Xtest/spell/Xtest.utf-8.spl'
179  " Add the spell file header and version (VIMspell2)
180  let v = 0z56494D7370656C6C32 + a:content
181  call writefile(v, splfile, 'b')
182
183  " 'encoding' is set before each test to clear the previously loaded suggest
184  " file from memory.
185  set encoding=utf-8
186
187  set runtimepath=./Xtest
188  set spelllang=Xtest
189  if a:emsg != ''
190    call assert_fails('set spell', a:emsg)
191  else
192    " FIXME: With some invalid spellfile contents, there are no error
193    " messages. So don't know how to check for the test result.
194    set spell
195  endif
196  set nospell spelllang& rtp&
197endfunc
198
199" Test for spell file format errors.
200" The spell file format is described in spellfile.c
201func Test_spellfile_format_error()
202  let save_rtp = &rtp
203  call mkdir('Xtest/spell', 'p')
204  let splfile = './Xtest/spell/Xtest.utf-8.spl'
205
206  " empty spell file
207  call writefile([], splfile)
208  set runtimepath=./Xtest
209  set spelllang=Xtest
210  call assert_fails('set spell', 'E757:')
211  set nospell spelllang&
212
213  " invalid file ID
214  call writefile(0z56494D, splfile, 'b')
215  set runtimepath=./Xtest
216  set spelllang=Xtest
217  call assert_fails('set spell', 'E757:')
218  set nospell spelllang&
219
220  " missing version number
221  call writefile(0z56494D7370656C6C, splfile, 'b')
222  set runtimepath=./Xtest
223  set spelllang=Xtest
224  call assert_fails('set spell', 'E771:')
225  set nospell spelllang&
226
227  " invalid version number
228  call writefile(0z56494D7370656C6C7A, splfile, 'b')
229  set runtimepath=./Xtest
230  set spelllang=Xtest
231  call assert_fails('set spell', 'E772:')
232  set nospell spelllang&
233
234  " no sections
235  call Spellfile_Test(0z, 'E758:')
236
237  " missing section length
238  call Spellfile_Test(0z00, 'E758:')
239
240  " unsupported required section
241  call Spellfile_Test(0z7A0100000004, 'E770:')
242
243  " unsupported not-required section
244  call Spellfile_Test(0z7A0000000004, 'E758:')
245
246  " SN_REGION: invalid number of region names
247  call Spellfile_Test(0z0000000000FF, 'E759:')
248
249  " SN_CHARFLAGS: missing <charflagslen> length
250  call Spellfile_Test(0z010000000004, 'E758:')
251
252  " SN_CHARFLAGS: invalid <charflagslen> length
253  call Spellfile_Test(0z0100000000010201, '')
254
255  " SN_CHARFLAGS: charflagslen == 0 and folcharslen != 0
256  call Spellfile_Test(0z01000000000400000101, 'E759:')
257
258  " SN_CHARFLAGS: missing <folcharslen> length
259  call Spellfile_Test(0z01000000000100, 'E758:')
260
261  " SN_PREFCOND: invalid prefcondcnt
262  call Spellfile_Test(0z03000000000100, 'E759:')
263
264  " SN_PREFCOND: invalid condlen
265  call Spellfile_Test(0z0300000000020001, 'E759:')
266
267  " SN_REP: invalid repcount
268  call Spellfile_Test(0z04000000000100, 'E758:')
269
270  " SN_REP: missing rep
271  call Spellfile_Test(0z0400000000020004, 'E758:')
272
273  " SN_REP: zero repfromlen
274  call Spellfile_Test(0z040000000003000100, 'E759:')
275
276  " SN_REP: invalid reptolen
277  call Spellfile_Test(0z0400000000050001014101, '')
278
279  " SN_REP: zero reptolen
280  call Spellfile_Test(0z0400000000050001014100, 'E759:')
281
282  " SN_SAL: missing salcount
283  call Spellfile_Test(0z05000000000102, 'E758:')
284
285  " SN_SAL: missing salfromlen
286  call Spellfile_Test(0z050000000003080001, 'E758:')
287
288  " SN_SAL: missing saltolen
289  call Spellfile_Test(0z0500000000050400010161, 'E758:')
290
291  " SN_WORDS: non-NUL terminated word
292  call Spellfile_Test(0z0D000000000376696D, 'E758:')
293
294  " SN_WORDS: very long word
295  let v = eval('0z0D000000012C' .. repeat('41', 300))
296  call Spellfile_Test(v, 'E759:')
297
298  " SN_SOFO: missing sofofromlen
299  call Spellfile_Test(0z06000000000100, 'E758:')
300
301  " SN_SOFO: missing sofotolen
302  call Spellfile_Test(0z06000000000400016100, 'E758:')
303
304  " SN_SOFO: missing sofoto
305  call Spellfile_Test(0z0600000000050001610000, 'E759:')
306
307  " SN_SOFO: empty sofofrom and sofoto
308  call Spellfile_Test(0z06000000000400000000FF000000000000000000000000, '')
309
310  " SN_COMPOUND: compmax is less than 2
311  call Spellfile_Test(0z08000000000101, 'E759:')
312
313  " SN_COMPOUND: missing compsylmax and other options
314  call Spellfile_Test(0z0800000000020401, 'E759:')
315
316  " SN_COMPOUND: missing compoptions
317  call Spellfile_Test(0z080000000005040101, 'E758:')
318
319  " SN_COMPOUND: missing comppattern
320  call Spellfile_Test(0z08000000000704010100000001, 'E758:')
321
322  " SN_COMPOUND: incorrect comppatlen
323  call Spellfile_Test(0z080000000007040101000000020165, 'E758:')
324
325  " SN_INFO: missing info
326  call Spellfile_Test(0z0F0000000005040101, '')
327
328  " SN_MIDWORD: missing midword
329  call Spellfile_Test(0z0200000000040102, '')
330
331  " SN_MAP: missing midword
332  call Spellfile_Test(0z0700000000040102, '')
333
334  " SN_MAP: empty map string
335  call Spellfile_Test(0z070000000000FF000000000000000000000000, '')
336
337  " SN_MAP: duplicate multibyte character
338  call Spellfile_Test(0z070000000004DC81DC81, 'E783:')
339
340  " SN_SYLLABLE: missing SYLLABLE item
341  call Spellfile_Test(0z0900000000040102, '')
342
343  " SN_SYLLABLE: More than SY_MAXLEN size
344  let v = eval('0z090000000022612F' .. repeat('62', 32))
345  call Spellfile_Test(v, '')
346
347  " LWORDTREE: missing
348  call Spellfile_Test(0zFF, 'E758:')
349
350  " LWORDTREE: missing tree node
351  call Spellfile_Test(0zFF00000004, 'E758:')
352
353  " LWORDTREE: missing tree node value
354  call Spellfile_Test(0zFF0000000402, 'E758:')
355
356  " LWORDTREE: incorrect sibling node count
357  call Spellfile_Test(0zFF00000001040000000000000000, 'E759:')
358
359  " KWORDTREE: missing tree node
360  call Spellfile_Test(0zFF0000000000000004, 'E758:')
361
362  " PREFIXTREE: missing tree node
363  call Spellfile_Test(0zFF000000000000000000000004, 'E758:')
364
365  " PREFIXTREE: incorrect prefcondnr
366  call Spellfile_Test(0zFF000000000000000000000002010200000020, 'E759:')
367
368  " PREFIXTREE: invalid nodeidx
369  call Spellfile_Test(0zFF00000000000000000000000201010000, 'E759:')
370
371  let &rtp = save_rtp
372  call delete('Xtest', 'rf')
373endfunc
374
375" Test for format errors in suggest file
376func Test_sugfile_format_error()
377  let save_rtp = &rtp
378  call mkdir('Xtest/spell', 'p')
379  let splfile = './Xtest/spell/Xtest.utf-8.spl'
380  let sugfile = './Xtest/spell/Xtest.utf-8.sug'
381
382  " create an empty spell file with a suggest timestamp
383  call writefile(0z56494D7370656C6C320B00000000080000000000000044FF000000000000000000000000, splfile, 'b')
384
385  " 'encoding' is set before each test to clear the previously loaded suggest
386  " file from memory.
387
388  " empty suggest file
389  set encoding=utf-8
390  call writefile([], sugfile)
391  set runtimepath=./Xtest
392  set spelllang=Xtest
393  set spell
394  call assert_fails("let s = spellsuggest('abc')", 'E778:')
395  set nospell spelllang&
396
397  " zero suggest version
398  set encoding=utf-8
399  call writefile(0z56494D73756700, sugfile)
400  set runtimepath=./Xtest
401  set spelllang=Xtest
402  set spell
403  call assert_fails("let s = spellsuggest('abc')", 'E779:')
404  set nospell spelllang&
405
406  " unsupported suggest version
407  set encoding=utf-8
408  call writefile(0z56494D7375671F, sugfile)
409  set runtimepath=./Xtest
410  set spelllang=Xtest
411  set spell
412  call assert_fails("let s = spellsuggest('abc')", 'E780:')
413  set nospell spelllang&
414
415  " missing suggest timestamp
416  set encoding=utf-8
417  call writefile(0z56494D73756701, sugfile)
418  set runtimepath=./Xtest
419  set spelllang=Xtest
420  set spell
421  call assert_fails("let s = spellsuggest('abc')", 'E781:')
422  set nospell spelllang&
423
424  " incorrect suggest timestamp
425  set encoding=utf-8
426  call writefile(0z56494D7375670100000000000000FF, sugfile)
427  set runtimepath=./Xtest
428  set spelllang=Xtest
429  set spell
430  call assert_fails("let s = spellsuggest('abc')", 'E781:')
431  set nospell spelllang&
432
433  " missing suggest wordtree
434  set encoding=utf-8
435  call writefile(0z56494D737567010000000000000044, sugfile)
436  set runtimepath=./Xtest
437  set spelllang=Xtest
438  set spell
439  call assert_fails("let s = spellsuggest('abc')", 'E782:')
440  set nospell spelllang&
441
442  " invalid suggest word count in SUGTABLE
443  set encoding=utf-8
444  call writefile(0z56494D7375670100000000000000440000000022, sugfile)
445  set runtimepath=./Xtest
446  set spelllang=Xtest
447  set spell
448  call assert_fails("let s = spellsuggest('abc')", 'E782:')
449  set nospell spelllang&
450
451  " missing sugline in SUGTABLE
452  set encoding=utf-8
453  call writefile(0z56494D7375670100000000000000440000000000000005, sugfile)
454  set runtimepath=./Xtest
455  set spelllang=Xtest
456  set spell
457  call assert_fails("let s = spellsuggest('abc')", 'E782:')
458  set nospell spelllang&
459
460  let &rtp = save_rtp
461  call delete('Xtest', 'rf')
462endfunc
463
464" Test for using :mkspell to create a spell file from a list of words
465func Test_wordlist_dic()
466  " duplicate encoding
467  let lines =<< trim [END]
468    # This is an example word list
469
470    /encoding=latin1
471    /encoding=latin1
472    example
473  [END]
474  call writefile(lines, 'Xwordlist.dic')
475  let output = execute('mkspell Xwordlist.spl Xwordlist.dic')
476  call assert_match('Duplicate /encoding= line ignored in Xwordlist.dic line 4: /encoding=latin1', output)
477
478  " multiple encoding for a word
479  let lines =<< trim [END]
480    example
481    /encoding=latin1
482    example
483  [END]
484  call writefile(lines, 'Xwordlist.dic')
485  let output = execute('mkspell! Xwordlist.spl Xwordlist.dic')
486  call assert_match('/encoding= line after word ignored in Xwordlist.dic line 2: /encoding=latin1', output)
487
488  " unsupported encoding for a word
489  let lines =<< trim [END]
490    /encoding=Xtest
491    example
492  [END]
493  call writefile(lines, 'Xwordlist.dic')
494  let output = execute('mkspell! Xwordlist.spl Xwordlist.dic')
495  call assert_match('Conversion in Xwordlist.dic not supported: from Xtest to utf-8', output)
496
497  " duplicate region
498  let lines =<< trim [END]
499    /regions=usca
500    /regions=usca
501    example
502  [END]
503  call writefile(lines, 'Xwordlist.dic')
504  let output = execute('mkspell! Xwordlist.spl Xwordlist.dic')
505  call assert_match('Duplicate /regions= line ignored in Xwordlist.dic line 2: regions=usca', output)
506
507  " maximum regions
508  let lines =<< trim [END]
509    /regions=uscauscauscauscausca
510    example
511  [END]
512  call writefile(lines, 'Xwordlist.dic')
513  let output = execute('mkspell! Xwordlist.spl Xwordlist.dic')
514  call assert_match('Too many regions in Xwordlist.dic line 1: uscauscauscauscausca', output)
515
516  " unsupported '/' value
517  let lines =<< trim [END]
518    /test=abc
519    example
520  [END]
521  call writefile(lines, 'Xwordlist.dic')
522  let output = execute('mkspell! Xwordlist.spl Xwordlist.dic')
523  call assert_match('/ line ignored in Xwordlist.dic line 1: /test=abc', output)
524
525  " unsupported flag
526  let lines =<< trim [END]
527    example/+
528  [END]
529  call writefile(lines, 'Xwordlist.dic')
530  let output = execute('mkspell! Xwordlist.spl Xwordlist.dic')
531  call assert_match('Unrecognized flags in Xwordlist.dic line 1: +', output)
532
533  " non-ascii word
534  call writefile(["ʀʀ"], 'Xwordlist.dic')
535  let output = execute('mkspell! -ascii Xwordlist.spl Xwordlist.dic')
536  call assert_match('Ignored 1 words with non-ASCII characters', output)
537
538  " keep case of a word
539  let lines =<< trim [END]
540    example/=
541  [END]
542  call writefile(lines, 'Xwordlist.dic')
543  let output = execute('mkspell! Xwordlist.spl Xwordlist.dic')
544  call assert_match('Compressed keep-case:', output)
545
546  call delete('Xwordlist.spl')
547  call delete('Xwordlist.dic')
548endfunc
549
550" Test for the :mkspell command
551func Test_mkspell()
552  call assert_fails('mkspell Xtest_us.spl', 'E751:')
553  call assert_fails('mkspell a b c d e f g h i j k', 'E754:')
554
555  call writefile([], 'Xtest.spl')
556  call writefile([], 'Xtest.dic')
557  call assert_fails('mkspell Xtest.spl Xtest.dic', 'E13:')
558  call delete('Xtest.spl')
559  call delete('Xtest.dic')
560
561  call mkdir('Xtest.spl')
562  call assert_fails('mkspell! Xtest.spl Xtest.dic', 'E17:')
563  call delete('Xtest.spl', 'rf')
564
565  call assert_fails('mkspell en en_US abc_xyz', 'E755:')
566endfunc
567
568" Tests for :mkspell with a .dic and .aff file
569func Test_aff_file_format_error()
570  " FIXME: For some reason, the :mkspell command below doesn't fail on the
571  " MS-Windows CI build. Disable this test on MS-Windows for now.
572  CheckNotMSWindows
573
574  " No word count in .dic file
575  call writefile([], 'Xtest.dic')
576  call writefile([], 'Xtest.aff')
577  call assert_fails('mkspell! Xtest.spl Xtest', 'E760:')
578
579  " create a .dic file for the tests below
580  call writefile(['1', 'work'], 'Xtest.dic')
581
582  " Invalid encoding in .aff file
583  call writefile(['# comment', 'SET Xinvalidencoding'], 'Xtest.aff')
584  let output = execute('mkspell! Xtest.spl Xtest')
585  call assert_match('Conversion in Xtest.aff not supported: from xinvalidencoding', output)
586
587  " Invalid flag in .aff file
588  call writefile(['FLAG xxx'], 'Xtest.aff')
589  let output = execute('mkspell! Xtest.spl Xtest')
590  call assert_match('Invalid value for FLAG in Xtest.aff line 1: xxx', output)
591
592  " set FLAGS after using flag for an affix
593  call writefile(['SFX L Y 1', 'SFX L 0 re [^x]', 'FLAG long'], 'Xtest.aff')
594  let output = execute('mkspell! Xtest.spl Xtest')
595  call assert_match('FLAG after using flags in Xtest.aff line 3: long', output)
596
597  " INFO in affix file
598  let save_encoding = &encoding
599  call mkdir('Xrtp/spell', 'p')
600  call writefile(['1', 'work'], 'Xrtp/spell/Xtest.dic')
601  call writefile(['NAME klingon', 'VERSION 1.4', 'AUTHOR Spock'],
602        \ 'Xrtp/spell/Xtest.aff')
603  silent mkspell! Xrtp/spell/Xtest.utf-8.spl Xrtp/spell/Xtest
604  let save_rtp = &rtp
605  set runtimepath=./Xrtp
606  set spelllang=Xtest
607  set spell
608  let output = split(execute('spellinfo'), "\n")
609  call assert_equal("NAME klingon", output[1])
610  call assert_equal("VERSION 1.4", output[2])
611  call assert_equal("AUTHOR Spock", output[3])
612  let &rtp = save_rtp
613  call delete('Xrtp', 'rf')
614  set spell& spelllang& spellfile&
615  %bw!
616  " 'encoding' must be set again to clear the spell file in memory
617  let &encoding = save_encoding
618
619  " COMPOUNDFORBIDFLAG flag after PFX in an affix file
620  call writefile(['PFX L Y 1', 'PFX L 0 re x', 'COMPOUNDFLAG c', 'COMPOUNDFORBIDFLAG x'],
621        \ 'Xtest.aff')
622  let output = execute('mkspell! Xtest.spl Xtest')
623  call assert_match('Defining COMPOUNDFORBIDFLAG after PFX item may give wrong results in Xtest.aff line 4', output)
624
625  " COMPOUNDPERMITFLAG flag after PFX in an affix file
626  call writefile(['PFX L Y 1', 'PFX L 0 re x', 'COMPOUNDPERMITFLAG c'],
627        \ 'Xtest.aff')
628  let output = execute('mkspell! Xtest.spl Xtest')
629  call assert_match('Defining COMPOUNDPERMITFLAG after PFX item may give wrong results in Xtest.aff line 3', output)
630
631  " Wrong COMPOUNDRULES flag value in an affix file
632  call writefile(['COMPOUNDRULES a'], 'Xtest.aff')
633  let output = execute('mkspell! Xtest.spl Xtest')
634  call assert_match('Wrong COMPOUNDRULES value in Xtest.aff line 1: a', output)
635
636  " Wrong COMPOUNDWORDMAX flag value in an affix file
637  call writefile(['COMPOUNDWORDMAX 0'], 'Xtest.aff')
638  let output = execute('mkspell! Xtest.spl Xtest')
639  call assert_match('Wrong COMPOUNDWORDMAX value in Xtest.aff line 1: 0', output)
640
641  " Wrong COMPOUNDMIN flag value in an affix file
642  call writefile(['COMPOUNDMIN 0'], 'Xtest.aff')
643  let output = execute('mkspell! Xtest.spl Xtest')
644  call assert_match('Wrong COMPOUNDMIN value in Xtest.aff line 1: 0', output)
645
646  " Wrong COMPOUNDSYLMAX flag value in an affix file
647  call writefile(['COMPOUNDSYLMAX 0'], 'Xtest.aff')
648  let output = execute('mkspell! Xtest.spl Xtest')
649  call assert_match('Wrong COMPOUNDSYLMAX value in Xtest.aff line 1: 0', output)
650
651  " Wrong CHECKCOMPOUNDPATTERN flag value in an affix file
652  call writefile(['CHECKCOMPOUNDPATTERN 0'], 'Xtest.aff')
653  let output = execute('mkspell! Xtest.spl Xtest')
654  call assert_match('Wrong CHECKCOMPOUNDPATTERN value in Xtest.aff line 1: 0', output)
655
656  " Duplicate affix entry in an affix file
657  call writefile(['PFX L Y 1', 'PFX L 0 re x', 'PFX L Y 1', 'PFX L 0 re x'],
658        \ 'Xtest.aff')
659  let output = execute('mkspell! Xtest.spl Xtest')
660  call assert_match('Duplicate affix in Xtest.aff line 3: L', output)
661
662  " Duplicate affix entry in an affix file
663  call writefile(['PFX L Y 1', 'PFX L Y 1'], 'Xtest.aff')
664  let output = execute('mkspell! Xtest.spl Xtest')
665  call assert_match('Unrecognized or duplicate item in Xtest.aff line 2: PFX', output)
666
667  " Different combining flags in an affix file
668  call writefile(['PFX L Y 1', 'PFX L 0 re x', 'PFX L N 1'], 'Xtest.aff')
669  let output = execute('mkspell! Xtest.spl Xtest')
670  call assert_match('Different combining flag in continued affix block in Xtest.aff line 3', output)
671
672  " Try to reuse a affix used for BAD flag
673  call writefile(['BAD x', 'PFX x Y 1', 'PFX x 0 re x'], 'Xtest.aff')
674  let output = execute('mkspell! Xtest.spl Xtest')
675  call assert_match('Affix also used for BAD/RARE/KEEPCASE/NEEDAFFIX/NEEDCOMPOUND/NOSUGGEST in Xtest.aff line 2: x', output)
676
677  " Trailing characters in an affix entry
678  call writefile(['PFX L Y 1 Test', 'PFX L 0 re x'], 'Xtest.aff')
679  let output = execute('mkspell! Xtest.spl Xtest')
680  call assert_match('Trailing text in Xtest.aff line 1: Test', output)
681
682  " Trailing characters in an affix entry
683  call writefile(['PFX L Y 1', 'PFX L 0 re x Test'], 'Xtest.aff')
684  let output = execute('mkspell! Xtest.spl Xtest')
685  call assert_match('Trailing text in Xtest.aff line 2: Test', output)
686
687  " Incorrect combine flag in an affix entry
688  call writefile(['PFX L X 1', 'PFX L 0 re x'], 'Xtest.aff')
689  let output = execute('mkspell! Xtest.spl Xtest')
690  call assert_match('Expected Y or N in Xtest.aff line 1: X', output)
691
692  " Invalid count for REP item
693  call writefile(['REP a'], 'Xtest.aff')
694  let output = execute('mkspell! Xtest.spl Xtest')
695  call assert_match('Expected REP(SAL) count in Xtest.aff line 1', output)
696
697  " Trailing characters in REP item
698  call writefile(['REP 1', 'REP f ph test'], 'Xtest.aff')
699  let output = execute('mkspell! Xtest.spl Xtest')
700  call assert_match('Trailing text in Xtest.aff line 2: test', output)
701
702  " Invalid count for MAP item
703  call writefile(['MAP a'], 'Xtest.aff')
704  let output = execute('mkspell! Xtest.spl Xtest')
705  call assert_match('Expected MAP count in Xtest.aff line 1', output)
706
707  " Duplicate character in a MAP item
708  call writefile(['MAP 2', 'MAP xx', 'MAP yy'], 'Xtest.aff')
709  let output = execute('mkspell! Xtest.spl Xtest')
710  call assert_match('Duplicate character in MAP in Xtest.aff line 2', output)
711
712  " Use COMPOUNDSYLMAX without SYLLABLE
713  call writefile(['COMPOUNDSYLMAX 2'], 'Xtest.aff')
714  let output = execute('mkspell! Xtest.spl Xtest')
715  call assert_match('COMPOUNDSYLMAX used without SYLLABLE', output)
716
717  " Missing SOFOTO
718  call writefile(['SOFOFROM abcdef'], 'Xtest.aff')
719  let output = execute('mkspell! Xtest.spl Xtest')
720  call assert_match('Missing SOFOTO line in Xtest.aff', output)
721
722  " Length of SOFOFROM and SOFOTO differ
723  call writefile(['SOFOFROM abcde', 'SOFOTO ABCD'], 'Xtest.aff')
724  call assert_fails('mkspell! Xtest.spl Xtest', 'E759:')
725
726  " Both SAL and SOFOFROM/SOFOTO items
727  call writefile(['SOFOFROM abcd', 'SOFOTO ABCD', 'SAL CIA X'], 'Xtest.aff')
728  let output = execute('mkspell! Xtest.spl Xtest')
729  call assert_match('Both SAL and SOFO lines in Xtest.aff', output)
730
731  " use an alphabet flag when FLAG is num
732  call writefile(['FLAG num', 'SFX L Y 1', 'SFX L 0 re [^x]'], 'Xtest.aff')
733  let output = execute('mkspell! Xtest.spl Xtest')
734  call assert_match('Flag is not a number in Xtest.aff line 2: L', output)
735
736  " use number and alphabet flag when FLAG is num
737  call writefile(['FLAG num', 'SFX 4f Y 1', 'SFX 4f 0 re [^x]'], 'Xtest.aff')
738  let output = execute('mkspell! Xtest.spl Xtest')
739  call assert_match('Affix name too long in Xtest.aff line 2: 4f', output)
740
741  " use a single character flag when FLAG is long
742  call writefile(['FLAG long', 'SFX L Y 1', 'SFX L 0 re [^x]'], 'Xtest.aff')
743  let output = execute('mkspell! Xtest.spl Xtest')
744  call assert_match('Illegal flag in Xtest.aff line 2: L', output)
745
746  " missing character in UPP entry. The character table is used only in a
747  " non-utf8 encoding
748  call writefile(['FOL abc', 'LOW abc', 'UPP A'], 'Xtest.aff')
749  let save_encoding = &encoding
750  set encoding=cp949
751  call assert_fails('mkspell! Xtest.spl Xtest', 'E761:')
752  let &encoding = save_encoding
753
754  " character range doesn't match between FOL and LOW entries
755  call writefile(["FOL \u0102bc", 'LOW abc', 'UPP ABC'], 'Xtest.aff')
756  let save_encoding = &encoding
757  set encoding=cp949
758  call assert_fails('mkspell! Xtest.spl Xtest', 'E762:')
759  let &encoding = save_encoding
760
761  " character range doesn't match between FOL and UPP entries
762  call writefile(["FOL \u0102bc", "LOW \u0102bc", 'UPP ABC'], 'Xtest.aff')
763  let save_encoding = &encoding
764  set encoding=cp949
765  call assert_fails('mkspell! Xtest.spl Xtest', 'E762:')
766  let &encoding = save_encoding
767
768  " additional characters in LOW and UPP entries
769  call writefile(["FOL ab", "LOW abc", 'UPP ABC'], 'Xtest.aff')
770  let save_encoding = &encoding
771  set encoding=cp949
772  call assert_fails('mkspell! Xtest.spl Xtest', 'E761:')
773  let &encoding = save_encoding
774
775  " duplicate word in the .dic file
776  call writefile(['2', 'good', 'good', 'good'], 'Xtest.dic')
777  call writefile(['NAME vim'], 'Xtest.aff')
778  let output = execute('mkspell! Xtest.spl Xtest')
779  call assert_match('First duplicate word in Xtest.dic line 3: good', output)
780  call assert_match('2 duplicate word(s) in Xtest.dic', output)
781
782  call delete('Xtest.dic')
783  call delete('Xtest.aff')
784  call delete('Xtest.spl')
785  call delete('Xtest.sug')
786endfunc
787
788func Test_spell_add_word()
789  set spellfile=
790  call assert_fails('spellgood abc', 'E764:')
791
792  set spellfile=Xtest.utf-8.add
793  call assert_fails('2spellgood abc', 'E765:')
794
795  edit Xtest.utf-8.add
796  call setline(1, 'sample')
797  call assert_fails('spellgood abc', 'E139:')
798  set spellfile&
799  %bw!
800endfunc
801
802" When 'spellfile' is not set, adding a new good word will automatically set
803" the 'spellfile'
804func Test_init_spellfile()
805  let save_rtp = &rtp
806  let save_encoding = &encoding
807  call mkdir('Xrtp/spell', 'p')
808  call writefile(['vim'], 'Xrtp/spell/Xtest.dic')
809  silent mkspell Xrtp/spell/Xtest.utf-8.spl Xrtp/spell/Xtest.dic
810  set runtimepath=./Xrtp
811  set spelllang=Xtest
812  set spell
813  silent spellgood abc
814  call assert_equal('./Xrtp/spell/Xtest.utf-8.add', &spellfile)
815  call assert_equal(['abc'], readfile('Xrtp/spell/Xtest.utf-8.add'))
816  call assert_true(filereadable('Xrtp/spell/Xtest.utf-8.spl'))
817  set spell& spelllang& spellfile&
818  call delete('Xrtp', 'rf')
819  let &encoding = save_encoding
820  let &rtp = save_rtp
821  %bw!
822endfunc
823
824" Test for the 'mkspellmem' option
825func Test_mkspellmem_opt()
826  call assert_fails('set mkspellmem=1000', 'E474:')
827  call assert_fails('set mkspellmem=1000,', 'E474:')
828  call assert_fails('set mkspellmem=1000,50', 'E474:')
829  call assert_fails('set mkspellmem=1000,50,', 'E474:')
830  call assert_fails('set mkspellmem=1000,50,10,', 'E474:')
831  call assert_fails('set mkspellmem=1000,50,0', 'E474:')
832endfunc
833
834" vim: shiftwidth=2 sts=2 expandtab
835