1 ;; erlang.el --- Major modes for editing and running Erlang
2 ;; The contents of this file are subject to the Erlang Public License,
3 ;; Version 1.1, (the "License"); you may not use this file except in
4 ;; compliance with the License. You should have received a copy of the
5 ;; Erlang Public License along with this software. If not, it can be
6 ;; retrieved via the world wide web at http://www.erlang.org/.
8 ;; Software distributed under the License is distributed on an "AS IS"
9 ;; basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
10 ;; the License for the specific language governing rights and limitations
13 ;; The Initial Developer of the Original Code is Ericsson Utvecklings AB.
14 ;; All Rights Reserved.
19 '(("If" "if" erlang-skel-if
)
20 ("Case" "case" erlang-skel-case
)
21 ("Receive" "receive" erlang-skel-receive
)
22 ("Receive After" "after" erlang-skel-receive-after
)
23 ("Receive Loop" "loop" erlang-skel-receive-loop
)
24 ("Module" "module" erlang-skel-module
)
25 ("Author" "author" erlang-skel-author
)
26 ("Function" "function" erlang-skel-function
)
28 ("Small Header" "small-header"
29 erlang-skel-small-header erlang-skel-header
)
30 ("Normal Header" "normal-header"
31 erlang-skel-normal-header erlang-skel-header
)
32 ("Large Header" "large-header"
33 erlang-skel-large-header erlang-skel-header
)
35 ("Small Server" "small-server"
36 erlang-skel-small-server erlang-skel-header
)
38 ("Application" "application"
39 erlang-skel-application erlang-skel-header
)
40 ("Supervisor" "supervisor"
41 erlang-skel-supervisor erlang-skel-header
)
42 ("supervisor_bridge" "supervisor-bridge"
43 erlang-skel-supervisor-bridge erlang-skel-header
)
44 ("gen_server" "generic-server"
45 erlang-skel-generic-server erlang-skel-header
)
46 ("gen_event" "gen-event"
47 erlang-skel-gen-event erlang-skel-header
)
49 erlang-skel-gen-fsm erlang-skel-header
)
50 ("Library module" "gen-lib"
51 erlang-skel-lib erlang-skel-header
)
52 ("Corba callback" "gen-corba-cb"
53 erlang-skel-corba-callback erlang-skel-header
)
54 ("Erlang test suite TS frontend" "ts-test-suite"
55 erlang-skel-ts-test-suite erlang-skel-header
)
56 ("Erlang test suite CT frontend" "ct-test-suite"
57 erlang-skel-ct-test-suite erlang-skel-header
)
59 "*Description of all skeleton templates.
60 Both functions and menu entries will be created.
62 Each entry in `erlang-skel' should be a list with three or four
63 elements, or the empty list.
65 The first element is the name which shows up in the menu. The second
66 is the `tempo' identifier (The string \"erlang-\" will be added in
67 front of it). The third is the skeleton descriptor, a variable
68 containing `tempo' attributes as described in the function
69 `tempo-define-template'. The optional fourth elements denotes a
70 function which should be called when the menu is selected.
72 Functions corresponding to every template will be created. The name
73 of the function will be `tempo-template-erlang-X' where `X' is the
74 tempo identifier as specified in the second argument of the elements
77 A list with zero elements means that the a horizontal line should
78 be placed in the menu.")
80 ;; In XEmacs `user-mail-address' returns "x@y.z (Foo Bar)" ARGH!
81 ;; What's wrong with that? RFC 822 says it's legal. [sverkerw]
82 ;; This needs to use the customized value. If that's not sane, things like
83 ;; add-log will lose anyhow. Avoid it if there _is_ a paren.
84 (defvar erlang-skel-mail-address
85 (if (or (not user-mail-address
) (string-match "(" user-mail-address
))
86 (concat (user-login-name) "@"
87 (or (and (boundp 'mail-host-address
)
91 "Mail address of the user.")
93 ;; Expression templates:
94 (defvar erlang-skel-case
95 '((erlang-skel-skip-blank) o
>
96 "case " p
" of" n
> p
"_ ->" n
> p
"ok" n
> "end" p
)
97 "*The skeleton of a `case' expression.
98 Please see the function `tempo-define-template'.")
100 (defvar erlang-skel-if
101 '((erlang-skel-skip-blank) o
>
102 "if" n
> p
" ->" n
> p
"ok" n
> "end" p
)
103 "The skeleton of an `if' expression.
104 Please see the function `tempo-define-template'.")
106 (defvar erlang-skel-receive
107 '((erlang-skel-skip-blank) o
>
108 "receive" n
> p
"_ ->" n
> p
"ok" n
> "end" p
)
109 "*The skeleton of a `receive' expression.
110 Please see the function `tempo-define-template'.")
112 (defvar erlang-skel-receive-after
113 '((erlang-skel-skip-blank) o
>
114 "receive" n
> p
"_ ->" n
> p
"ok" n
> "after " p
"T ->" n
>
116 "*The skeleton of a `receive' expression with an `after' clause.
117 Please see the function `tempo-define-template'.")
119 (defvar erlang-skel-receive-loop
120 '(& o
"loop(" p
") ->" n
> "receive" n
> p
"_ ->" n
>
121 "loop(" p
")" n
> "end.")
122 "*The skeleton of a simple `receive' loop.
123 Please see the function `tempo-define-template'.")
126 (defvar erlang-skel-function
127 '((erlang-skel-separator 2)
131 (erlang-skel-separator 2))
132 "*The template of a function skeleton.
133 Please see the function `tempo-define-template'.")
136 ;; Attribute templates
138 (defvar erlang-skel-module
140 (erlang-add-quotes-if-needed (erlang-get-module-from-file-name))
142 "*The skeleton of a `module' attribute.
143 Please see the function `tempo-define-template'.")
145 (defvar erlang-skel-author
146 '(& "-author('" erlang-skel-mail-address
"')." n
)
147 "*The skeleton of a `author' attribute.
148 Please see the function `tempo-define-template'.")
150 (defvar erlang-skel-vc nil
151 "*The skeleton template to generate a version control attribute.
152 The default is to insert nothing. Example of usage:
154 (setq erlang-skel-vc '(& \"-rcs(\\\"$\Id: $ \\\").\") n)
156 Please see the function `tempo-define-template'.")
158 (defvar erlang-skel-export
159 '(& "-export([" n
> "])." n
)
160 "*The skeleton of an `export' attribute.
161 Please see the function `tempo-define-template'.")
163 (defvar erlang-skel-import
164 '(& "%%-import(Module, [Function/Arity, ...])." n
)
165 "*The skeleton of an `import' attribute.
166 Please see the function `tempo-define-template'.")
168 (defvar erlang-skel-compile nil
169 ;; '(& "%%-compile(export_all)." n)
170 "*The skeleton of a `compile' attribute.
171 Please see the function `tempo-define-template'.")
174 ;; Comment templates.
176 (defvar erlang-skel-date-function
'erlang-skel-dd-mmm-yyyy
177 "*Function which returns date string.
178 Look in the module `time-stamp' for a battery of functions.")
180 (defvar erlang-skel-copyright-comment
181 (if (boundp '*copyright-organization
*)
182 '(& "%%% @copyright (C) " (format-time-string "%Y") ", "
183 *copyright-organization
* n
)
184 '(& "%%% @copyright (C) " (format-time-string "%Y") ", "
186 "*The template for a copyright line in the header, normally empty.
187 This variable should be bound to a `tempo' template, for example:
188 '(& \"%%% Copyright (C) 2000, Yoyodyne, Inc.\" n)
189 Please see the function `tempo-define-template'.")
191 (defvar erlang-skel-created-comment
192 '(& "%%% Created : " (funcall erlang-skel-date-function
) " by "
193 (user-full-name) " <" erlang-skel-mail-address
">" n
)
194 "*The template for the \"Created:\" comment line.")
196 (defvar erlang-skel-author-comment
197 '(& "%%% @author " (user-full-name) " <" erlang-skel-mail-address
">" n
)
198 "*The template for creating the \"Author:\" line in the header.
199 Please see the function `tempo-define-template'.")
201 (defvar erlang-skel-small-header
202 '(o (erlang-skel-include erlang-skel-module
)
203 ;; erlang-skel-author)
205 (erlang-skel-include erlang-skel-compile
206 ;; erlang-skel-export
208 "*The template of a small header without any comments.
209 Please see the function `tempo-define-template'.")
211 (defvar erlang-skel-normal-header
212 '(o (erlang-skel-include erlang-skel-author-comment
)
213 (erlang-skel-include erlang-skel-copyright-comment
)
217 (erlang-skel-include erlang-skel-created-comment
) n
218 (erlang-skel-include erlang-skel-small-header
) n
)
219 "*The template of a normal header.
220 Please see the function `tempo-define-template'.")
222 (defvar erlang-skel-large-header
223 '(o (erlang-skel-separator)
224 (erlang-skel-include erlang-skel-author-comment
)
225 (erlang-skel-include erlang-skel-copyright-comment
)
229 (erlang-skel-include erlang-skel-created-comment
)
230 (erlang-skel-separator)
231 (erlang-skel-include erlang-skel-small-header
) )
232 "*The template of a large header.
233 Please see the function `tempo-define-template'.")
237 (defvar erlang-skel-small-server
238 '((erlang-skel-include erlang-skel-large-header
)
239 "-export([start/0,init/1])." n n n
240 "start() ->" n
> "spawn(" (erlang-get-module-from-file-name)
241 ", init, [self()])." n n
250 "*Template of a small server.
251 Please see the function `tempo-define-template'.")
253 ;; Behaviour templates.
254 (defvar erlang-skel-application
255 '((erlang-skel-include erlang-skel-large-header
)
256 "-behaviour(application)." n n
257 "%% Application callbacks" n
258 "-export([start/2, stop/1])." n n
259 (erlang-skel-double-separator 2)
260 "%% Application callbacks" n
261 (erlang-skel-double-separator 2)
262 (erlang-skel-separator 2)
264 "%% This function is called whenever an application" n
265 "%% is started using application:start/1,2, and should start the processes" n
266 "%% of the application. If the application is structured according to the" n
267 "%% OTP design principles as a supervision tree, this means starting the" n
268 "%% top supervisor of the tree." n
270 "%% @spec start(Type, StartArgs) -> {ok, Pid} |" n
271 "%% {ok, Pid, State} |" n
272 "%% {error, Reason}." n
274 (erlang-skel-separator 2)
275 "start(_Type, StartArgs) ->" n
>
276 "case 'TopSupervisor':start_link(StartArgs) of" n
>
283 (erlang-skel-separator 2)
285 "%% This function is called whenever an application" n
286 "%% has stopped. It is intended to be the opposite of Module:start/2 and" n
287 "%% should do any necessary cleaning up. The return value is ignored." n
289 "%% @spec stop(State) -> void()." n
291 (erlang-skel-separator 2)
295 (erlang-skel-double-separator 2)
296 "%% Internal functions" n
297 (erlang-skel-double-separator 2)
299 "*The template of an application behaviour.
300 Please see the function `tempo-define-template'.")
302 (defvar erlang-skel-supervisor
303 '((erlang-skel-include erlang-skel-large-header
)
304 "-behaviour(supervisor)." n n
307 "-export([start_link/0])." n n
309 "%% Supervisor callbacks" n
310 "-export([init/1])." n n
312 "-define(SERVER, ?MODULE)." n n
314 (erlang-skel-double-separator 2)
316 (erlang-skel-double-separator 2)
317 (erlang-skel-separator 2)
319 "%% Starts the supervisor" n
321 "%% @spec start_link() -> {ok,Pid} | ignore | {error,Error}." n
323 (erlang-skel-separator 2)
325 "supervisor:start_link({local, ?SERVER}, ?MODULE, [])." n
327 (erlang-skel-double-separator 2)
328 "%% Supervisor callbacks" n
329 (erlang-skel-double-separator 2)
330 (erlang-skel-separator 2)
332 "%% Whenever a supervisor is started using" n
333 "%% supervisor:start_link/[2,3], this function is called by the new process" n
334 "%% to find out about restart strategy, maximum restart frequency and child" n
335 "%% specifications." n
337 "%% @spec init(Args) -> {ok, {SupFlags, [ChildSpec]}} |" n
339 "%% {error, Reason}." n
341 (erlang-skel-separator 2)
343 "AChild = {'AName',{'AModule',start_link,[]}," n
>
344 "permanent,2000,worker,['AModule']}," n
>
345 "{ok,{{one_for_all,0,1}, [AChild]}}." n
347 (erlang-skel-double-separator 2)
348 "%% Internal functions" n
349 (erlang-skel-double-separator 2)
351 "*The template of an supervisor behaviour.
352 Please see the function `tempo-define-template'.")
354 (defvar erlang-skel-supervisor-bridge
355 '((erlang-skel-include erlang-skel-large-header
)
356 "-behaviour(supervisor_bridge)." n n
359 "-export([start_link/0])." n n
361 "%% supervisor_bridge callbacks" n
362 "-export([init/1, terminate/2])." n n
364 "-define(SERVER, ?MODULE)." n n
366 "-record(state, {})." n n
368 (erlang-skel-double-separator 2)
370 (erlang-skel-double-separator 2)
371 (erlang-skel-separator 2)
373 "%% Starts the supervisor bridge" n
375 "%% @spec start_link() -> {ok,Pid} | ignore | {error,Error}." n
377 (erlang-skel-separator 2)
379 "supervisor_bridge:start_link({local, ?SERVER}, ?MODULE, [])." n
381 (erlang-skel-double-separator 2)
382 "%% supervisor_bridge callbacks" n
383 (erlang-skel-double-separator 2)
384 (erlang-skel-separator 2)
386 "%% Creates a supervisor_bridge process, linked to the calling" n
387 "%% process, which calls Module:init/1 to start the subsystem. To ensure a" n
388 "%% synchronized start-up procedure, this function does not return until" n
389 "%% Module:init/1 has returned." n
391 "%% @spec init(Args) -> {ok, Pid, State} |" n
393 "%% {error, Reason}." n
395 (erlang-skel-separator 2)
397 "case 'AModule':start_link() of" n
>
399 "{ok, Pid, #state{}};" n
>
404 (erlang-skel-separator 2)
406 "%% This function is called by the supervisor_bridge when it is" n
407 "%% about to terminate. It should be the opposite of Module:init/1 and stop" n
408 "%% the subsystem and do any necessary cleaning up.The return value is ignored." n
410 "%% @spec terminate(Reason, State) -> void()." n
412 (erlang-skel-separator 2)
413 "terminate(Reason, State) ->" n
>
414 "'AModule':stop()," n
>
417 (erlang-skel-double-separator 2)
418 "%% Internal functions" n
419 (erlang-skel-double-separator 2)
421 "*The template of an supervisor_bridge behaviour.
422 Please see the function `tempo-define-template'.")
424 (defvar erlang-skel-generic-server
425 '((erlang-skel-include erlang-skel-large-header
)
426 "-behaviour(gen_server)." n n
429 "-export([start_link/0])." n n
431 "%% gen_server callbacks" n
432 "-export([init/1, handle_call/3, handle_cast/2, "
434 "terminate/2, code_change/3])." n n
436 "-define(SERVER, ?MODULE). " n n
438 "-record(state, {})." n n
440 (erlang-skel-double-separator 2)
442 (erlang-skel-double-separator 2)
443 (erlang-skel-separator 2)
445 "%% Starts the server" n
447 "%% @spec start_link() -> {ok,Pid} | ignore | {error,Error}." n
449 (erlang-skel-separator 2)
451 "gen_server:start_link({local, ?SERVER}, ?MODULE, [], [])." n
453 (erlang-skel-double-separator 2)
454 "%% gen_server callbacks" n
455 (erlang-skel-double-separator 2)
457 (erlang-skel-separator 2)
459 "%% Initiates the server" n
461 "%% @spec init(Args) -> {ok, State} |" n
462 "%% {ok, State, Timeout} |" n
464 "%% {stop, Reason}." n
466 (erlang-skel-separator 2)
470 (erlang-skel-separator 2)
472 "%% Handling call messages" n
474 "%% @spec handle_call(Request, From, State) -> {reply, Reply, State} |" n
475 "%% {reply, Reply, State, Timeout} |" n
476 "%% {noreply, State} |" n
477 "%% {noreply, State, Timeout} |" n
478 "%% {stop, Reason, Reply, State} |" n
479 "%% {stop, Reason, State}." n
481 (erlang-skel-separator 2)
482 "handle_call(_Request, _From, State) ->" n
>
484 "{reply, Reply, State}." n
486 (erlang-skel-separator 2)
488 "%% Handling cast messages" n
490 "%% @spec handle_cast(Msg, State) -> {noreply, State} |" n
491 "%% {noreply, State, Timeout} |" n
492 "%% {stop, Reason, State}." n
495 (erlang-skel-separator 2)
496 "handle_cast(_Msg, State) ->" n
>
497 "{noreply, State}." n
499 (erlang-skel-separator 2)
501 "%% Handling all non call/cast messages" n
503 "%% @spec handle_info(Info, State) -> {noreply, State} |" n
504 "%% {noreply, State, Timeout} |" n
505 "%% {stop, Reason, State}." n
507 (erlang-skel-separator 2)
508 "handle_info(_Info, State) ->" n
>
509 "{noreply, State}." n
511 (erlang-skel-separator 2)
513 "%% This function is called by a gen_server when it is about to" n
514 "%% terminate. It should be the opposite of Module:init/1 and do any necessary" n
515 "%% cleaning up. When it returns, the gen_server terminates with Reason." n
516 "%% The return value is ignored." n
518 "%% @spec terminate(Reason, State) -> void()." n
520 (erlang-skel-separator 2)
521 "terminate(_Reason, _State) ->" n
>
524 (erlang-skel-separator 2)
526 "%% Convert process state when code is changed" n
528 "%% @spec code_change(OldVsn, State, Extra) -> {ok, NewState}." n
530 (erlang-skel-separator 2)
531 "code_change(_OldVsn, State, _Extra) ->" n
>
534 (erlang-skel-double-separator 2)
535 "%%% Internal functions" n
536 (erlang-skel-double-separator 2)
538 "*The template of a generic server.
539 Please see the function `tempo-define-template'.")
541 (defvar erlang-skel-gen-event
542 '((erlang-skel-include erlang-skel-large-header
)
543 "-behaviour(gen_event)." n
546 "-export([start_link/0, add_handler/0])." n n
548 "%% gen_event callbacks" n
549 "-export([init/1, handle_event/2, handle_call/2, " n
>
550 "handle_info/2, terminate/2, code_change/3])." n n
552 "-record(state, {})." n n
554 (erlang-skel-double-separator 2)
555 "%% gen_event callbacks" n
556 (erlang-skel-double-separator 2)
557 (erlang-skel-separator 2)
559 "%% Creates an event manager." n
561 "%% @spec start_link() -> {ok,Pid} | {error,Error}." n
563 (erlang-skel-separator 2)
565 "gen_event:start_link({local, ?SERVER})." n
567 (erlang-skel-separator 2)
569 "%% Adds an event handler" n
571 "%% @spec add_handler() -> ok | {'EXIT',Reason} | term()." n
573 (erlang-skel-separator 2)
574 "add_handler() ->" n
>
575 "gen_event:add_handler(?SERVER, ?MODULE, [])." n
577 (erlang-skel-double-separator 2)
578 "%% gen_event callbacks" n
579 (erlang-skel-double-separator 2)
580 (erlang-skel-separator 2)
582 "%% Whenever a new event handler is added to an event manager," n
583 "%% this function is called to initialize the event handler." n
585 "%% @spec init(Args) -> {ok, State}." n
587 (erlang-skel-separator 2)
591 (erlang-skel-separator 2)
593 "%% Whenever an event manager receives an event sent using" n
594 "%% gen_event:notify/2 or gen_event:sync_notify/2, this function is called for" n
595 "%% each installed event handler to handle the event." n
597 "%% @spec handle_event(Event, State) -> {ok, State} |" n
598 "%% {swap_handler, Args1, State1, Mod2, Args2} |"n
599 "%% remove_handler." n
601 (erlang-skel-separator 2)
602 "handle_event(_Event, State) ->" n
>
605 (erlang-skel-separator 2)
607 "%% Whenever an event manager receives a request sent using" n
608 "%% gen_event:call/3,4, this function is called for the specified event" n
609 "%% handler to handle the request." n
611 "%% @spec handle_call(Request, State) -> {ok, Reply, State} |" n
612 "%% {swap_handler, Reply, Args1, State1," n
613 "%% Mod2, Args2} |" n
614 "%% {remove_handler, Reply}." n
616 (erlang-skel-separator 2)
617 "handle_call(_Request, State) ->" n
>
619 "{ok, Reply, State}." n
621 (erlang-skel-separator 2)
623 "%% This function is called for each installed event handler when" n
624 "%% an event manager receives any other message than an event or a synchronous" n
625 "%% request (or a system message)." n
627 "%% @spec handle_info(Info, State) -> {ok, State} |" n
628 "%% {swap_handler, Args1, State1, Mod2, Args2} |" n
629 "%% remove_handler." n
631 (erlang-skel-separator 2)
632 "handle_info(_Info, State) ->" n
>
635 (erlang-skel-separator 2)
637 "%% Whenever an event handler is deleted from an event manager," n
638 "%% this function is called. It should be the opposite of Module:init/1 and" n
639 "%% do any necessary cleaning up." n
641 "%% @spec terminate(Reason, State) -> void()." n
643 (erlang-skel-separator 2)
644 "terminate(_Reason, _State) ->" n
>
647 (erlang-skel-separator 2)
649 "%% Convert process state when code is changed" n
651 "%% @spec code_change(OldVsn, State, Extra) -> {ok, NewState}." n
653 (erlang-skel-separator 2)
654 "code_change(_OldVsn, State, _Extra) ->" n
>
657 (erlang-skel-double-separator 2)
658 "%%% Internal functions" n
659 (erlang-skel-double-separator 2)
661 "*The template of a gen_event.
662 Please see the function `tempo-define-template'.")
664 (defvar erlang-skel-gen-fsm
665 '((erlang-skel-include erlang-skel-large-header
)
666 "-behaviour(gen_fsm)." n n
669 "-export([start_link/0])." n n
671 "%% gen_fsm callbacks" n
672 "-export([init/1, state_name/2, state_name/3, handle_event/3," n
>
673 "handle_sync_event/4, handle_info/3, terminate/3, code_change/4])." n n
675 "-record(state, {})." n n
677 (erlang-skel-double-separator 2)
679 (erlang-skel-double-separator 2)
680 (erlang-skel-separator 2)
682 "%% Creates a gen_fsm process which calls Module:init/1 to" n
683 "%% initialize. To ensure a synchronized start-up procedure, this function" n
684 "%% does not return until Module:init/1 has returned." n
686 "%% @spec start_link() -> ok,Pid} | ignore | {error,Error}." n
688 (erlang-skel-separator 2)
690 "gen_fsm:start_link({local, ?SERVER}, ?MODULE, [], [])." n
692 (erlang-skel-double-separator 2)
693 "%% gen_fsm callbacks" n
694 (erlang-skel-double-separator 2)
695 (erlang-skel-separator 2)
697 "%% Whenever a gen_fsm is started using gen_fsm:start/[3,4] or" n
698 "%% gen_fsm:start_link/3,4, this function is called by the new process to " n
701 "%% @spec init(Args) -> {ok, StateName, State} |" n
702 "%% {ok, StateName, State, Timeout} |" n
704 "%% {stop, StopReason}." n
706 (erlang-skel-separator 2)
708 "{ok, state_name, #state{}}." n
710 (erlang-skel-separator 2)
712 "%% There should be one instance of this function for each possible" n
713 "%% state name. Whenever a gen_fsm receives an event sent using" n
714 "%% gen_fsm:send_event/2, the instance of this function with the same name as" n
715 "%% the current state name StateName is called to handle the event. It is also" n
716 "%% called if a timeout occurs." n
718 "%% @spec state_name(Event, State) -> {next_state, NextStateName, NextState}|" n
719 "%% {next_state, NextStateName," n
720 "%% NextState, Timeout} |" n
721 "%% {stop, Reason, NewState}." n
723 (erlang-skel-separator 2)
724 "state_name(_Event, State) ->" n
>
725 "{next_state, state_name, State}." n
727 (erlang-skel-separator 2)
729 "%% There should be one instance of this function for each" n
730 "%% possible state name. Whenever a gen_fsm receives an event sent using" n
731 "%% gen_fsm:sync_send_event/2,3, the instance of this function with the same" n
732 "%% name as the current state name StateName is called to handle the event." n
734 "%% @spec state_name(Event, From, State) -> {next_state, NextStateName, NextState} |"n
735 "%% {next_state, NextStateName," n
736 "%% NextState, Timeout} |" n
737 "%% {reply, Reply, NextStateName, NextState}|" n
738 "%% {reply, Reply, NextStateName," n
739 "%% NextState, Timeout} |" n
740 "%% {stop, Reason, NewState}|" n
741 "%% {stop, Reason, Reply, NewState}." n
743 (erlang-skel-separator 2)
744 "state_name(_Event, _From, State) ->" n
>
746 "{reply, Reply, state_name, State}." n
748 (erlang-skel-separator 2)
750 "%% Whenever a gen_fsm receives an event sent using" n
751 "%% gen_fsm:send_all_state_event/2, this function is called to handle" n
754 "%% @spec handle_event(Event, StateName, State) -> {next_state, NextStateName," n
756 "%% {next_state, NextStateName," n
757 "%% NextState, Timeout} |" n
758 "%% {stop, Reason, NewState}." n
760 (erlang-skel-separator 2)
761 "handle_event(_Event, StateName, State) ->" n
>
762 "{next_state, StateName, State}." n
764 (erlang-skel-separator 2)
766 "%% Whenever a gen_fsm receives an event sent using" n
767 "%% gen_fsm:sync_send_all_state_event/2,3, this function is called to handle" n
770 "%% @spec handle_sync_event(Event, From, StateName," n
771 "%% State) -> {next_state, NextStateName, NextState} |" n
772 "%% {next_state, NextStateName, NextState," n
774 "%% {reply, Reply, NextStateName, NextState}|" n
775 "%% {reply, Reply, NextStateName, NextState," n
777 "%% {stop, Reason, NewState} |" n
778 "%% {stop, Reason, Reply, NewState}." n
780 (erlang-skel-separator 2)
781 "handle_sync_event(Event, From, StateName, State) ->" n
>
783 "{reply, Reply, StateName, State}." n
785 (erlang-skel-separator 2)
787 "%% This function is called by a gen_fsm when it receives any" n
788 "%% other message than a synchronous or asynchronous event" n
789 "%% (or a system message)." n
791 "%% @spec handle_info(Info,StateName,State)-> {next_state, NextStateName, NextState}|" n
792 "%% {next_state, NextStateName, NextState," n
794 "%% {stop, Reason, NewState}." n
796 (erlang-skel-separator 2)
797 "handle_info(_Info, StateName, State) ->" n
>
798 "{next_state, StateName, State}." n
800 (erlang-skel-separator 2)
802 "%% This function is called by a gen_fsm when it is about" n
803 "%% to terminate. It should be the opposite of Module:init/1 and do any" n
804 "%% necessary cleaning up. When it returns, the gen_fsm terminates with" n
805 "%% Reason. The return value is ignored." n
807 "%% @spec terminate(Reason, StateName, State) -> void()." n
809 (erlang-skel-separator 2)
810 "terminate(_Reason, _StateName, _State) ->" n
>
813 (erlang-skel-separator 2)
815 "%% Convert process state when code is changed" n
817 "%% @spec code_change(OldVsn, StateName, State, Extra) -> {ok, StateName, NewState}." n
819 (erlang-skel-separator 2)
820 "code_change(_OldVsn, StateName, State, _Extra) ->" n
>
821 "{ok, StateName, State}." n
823 (erlang-skel-double-separator 2)
824 "%%% Internal functions" n
825 (erlang-skel-double-separator 2)
827 "*The template of a gen_fsm.
828 Please see the function `tempo-define-template'.")
830 (defvar erlang-skel-lib
831 '((erlang-skel-include erlang-skel-large-header
)
836 (erlang-skel-double-separator 2)
838 (erlang-skel-double-separator 2)
839 (erlang-skel-separator 2)
843 (erlang-skel-separator 2)
845 (erlang-skel-double-separator 2)
846 "%% Internal functions" n
847 (erlang-skel-double-separator 2)
849 "*The template of a library module.
850 Please see the function `tempo-define-template'.")
852 (defvar erlang-skel-corba-callback
853 '((erlang-skel-include erlang-skel-large-header
)
854 "%% Include files" n n
859 "%% Corba callbacks" n
860 "-export([init/1, terminate/2, code_change/3])." n n
862 "-record(state, {})." n n
864 (erlang-skel-double-separator 2)
865 "%% Corba callbacks" n
866 (erlang-skel-double-separator 2)
867 (erlang-skel-separator 2)
869 "%% Initiates the server" n
871 "%% @spec init(Args) -> {ok, State} |" n
872 "%% {ok, State, Timeout} |" n
874 "%% {stop, Reason}." n
876 (erlang-skel-separator 2)
880 (erlang-skel-separator 2)
882 "%% Shutdown the server" n
884 "%% @spec terminate(Reason, State) -> void()." n
886 (erlang-skel-separator 2)
887 "terminate(_Reason, _State) ->" n
>
890 (erlang-skel-separator 2)
892 "%% Convert process state when code is changed" n
894 "%% @spec code_change(OldVsn, State, Extra) -> {ok, NewState}." n
896 (erlang-skel-separator 2)
897 "code_change(_OldVsn, State, _Extra) ->" n
>
900 (erlang-skel-double-separator 2)
901 "%% Internal functions" n
902 (erlang-skel-double-separator 2)
904 "*The template of a library module.
905 Please see the function `tempo-define-template'.")
907 (defvar erlang-skel-ts-test-suite
908 '((erlang-skel-include erlang-skel-large-header
)
909 "%% Note: This directive should only be used in test suites." n
910 "-compile(export_all)." n n
912 "-include(\"test_server.hrl\")." n n
914 "%% Test server callback functions" n
915 (erlang-skel-separator 2)
917 "%% Config - [tuple()]" n
918 "%% A list of key/value pairs, holding the test case configuration." n
919 "%% Initiation before the whole suite" n
921 "%% Note: This function is free to add any key/value pairs to the Config" n
922 "%% variable, but should NOT alter/remove any existing entries." n
924 "%% @spec init_per_suite(Config) -> Config." n
926 (erlang-skel-separator 2)
927 "init_per_suite(Config) ->" n
>
930 (erlang-skel-separator 2)
932 "%% Config - [tuple()]" n
933 "%% A list of key/value pairs, holding the test case configuration." n
934 "%% Cleanup after the whole suite" n
936 "%% @spec end_per_suite(Config) -> _." n
938 (erlang-skel-separator 2)
939 "end_per_suite(_Config) ->" n
>
942 (erlang-skel-separator 2)
945 "%% Name of the test case that is about to be run." n
946 "%% Config - [tuple()]" n
947 "%% A list of key/value pairs, holding the test case configuration." n
949 "%% Initiation before each test case" n
951 "%% Note: This function is free to add any key/value pairs to the Config" n
952 "%% variable, but should NOT alter/remove any existing entries." n
954 "%% @spec init_per_testcase(TestCase, Config) -> Config." n
956 (erlang-skel-separator 2)
957 "init_per_testcase(_TestCase, Config) ->" n
>
960 (erlang-skel-separator 2)
963 "%% Name of the test case that is about to be run." n
964 "%% Config - [tuple()]" n
965 "%% A list of key/value pairs, holding the test case configuration." n
966 "%% Cleanup after each test case" n
968 "%% @spec end_per_testcase(TestCase, Config) -> _." n
970 (erlang-skel-separator 2)
971 "end_per_testcase(_TestCase, _Config) ->" n
>
974 (erlang-skel-separator 2)
976 "%% Clause - atom() - suite | doc" n
977 "%% TestCases - [Case]" n
979 "%% Name of a test case." n
980 "%% Returns a list of all test cases in this test suite" n
982 "%% @spec all(Clause) -> TestCases." n
984 (erlang-skel-separator 2)
986 "[\"Describe the main purpose of this suite\"];" n n
990 "%% Test cases starts here." n
991 (erlang-skel-separator 2)
992 "test_case(doc) ->" n
>
993 "[\"Describe the main purpose of test case\"];" n n
994 "test_case(suite) ->" n
>
996 "test_case(Config) when is_list(Config) ->" n
>
999 "*The template of a library module.
1000 Please see the function `tempo-define-template'.")
1002 (defvar erlang-skel-ct-test-suite
1003 '((erlang-skel-include erlang-skel-large-header
)
1004 "-suite_defaults([{timetrap, {minutes, 10}}])." n n
1006 "%% Note: This directive should only be used in test suites." n
1007 "-compile(export_all)." n n
1009 "-include(\"ct.hrl\")." n n
1011 "%% Test server callback functions" n
1012 (erlang-skel-separator 2)
1014 "%% Config - [tuple()]" n
1015 "%% A list of key/value pairs, holding the test case configuration." n
1016 "%% Initiation before the whole suite" n
1018 "%% Note: This function is free to add any key/value pairs to the Config" n
1019 "%% variable, but should NOT alter/remove any existing entries." n
1021 "%% @spec init_per_suite(Config) -> Config." n
1023 (erlang-skel-separator 2)
1024 "init_per_suite(Config) ->" n
>
1027 (erlang-skel-separator 2)
1029 "%% Config - [tuple()]" n
1030 "%% A list of key/value pairs, holding the test case configuration." n
1031 "%% Cleanup after the whole suite" n
1033 "%% @spec end_per_suite(Config) -> _." n
1035 (erlang-skel-separator 2)
1036 "end_per_suite(_Config) ->" n
>
1039 (erlang-skel-separator 2)
1041 "%% Case - atom()" n
1042 "%% Name of the test case that is about to be run." n
1043 "%% Config - [tuple()]" n
1044 "%% A list of key/value pairs, holding the test case configuration." n
1046 "%% Initiation before each test case" n
1048 "%% Note: This function is free to add any key/value pairs to the Config" n
1049 "%% variable, but should NOT alter/remove any existing entries." n
1050 "%% Initiation before each test case" n
1052 "%% @spec init_per_testcase(TestCase, Config) -> Config." n
1054 (erlang-skel-separator 2)
1055 "init_per_testcase(_TestCase, Config) ->" n
>
1058 (erlang-skel-separator 2)
1060 "%% Case - atom()" n
1061 "%% Name of the test case that is about to be run." n
1062 "%% Config - [tuple()]" n
1063 "%% A list of key/value pairs, holding the test case configuration." n
1064 "%% Cleanup after each test case" n
1066 "%% @spec end_per_testcase(TestCase, Config) -> _." n
1068 (erlang-skel-separator 2)
1069 "end_per_testcase(_TestCase, _Config) ->" n
>
1072 (erlang-skel-separator 2)
1074 "%% TestCases - [Case]" n
1075 "%% Case - atom()" n
1076 "%% Name of a test case." n
1077 "%% Returns a list of all test cases in this test suite" n
1079 "%% @spec all() -> TestCases." n
1081 (erlang-skel-separator 2)
1085 "%% Test cases starts here." n
1086 (erlang-skel-separator 2)
1087 "test_case() ->" n
>
1088 "[{doc, \"Describe the main purpose of this test case\"}]." n n
1089 "test_case(Config) when is_list(Config) ->" n
>
1092 "*The template of a library module.
1093 Please see the function `tempo-define-template'.")
1097 ;; This code is based on the package `tempo' which is part of modern
1098 ;; Emacsen. (GNU Emacs 19.25 (?) and XEmacs 19.14.)
1100 (defun erlang-skel-init ()
1101 "Generate the skeleton functions and menu items.
1102 The variable `erlang-skel' contains the name and descriptions of
1105 The skeleton routines are based on the `tempo' package. Should this
1106 package not be present, this function does nothing."
1111 (if (featurep 'tempo
)
1112 (let ((skel erlang-skel
)
1115 (cond ((null (car skel
))
1116 (setq menu
(cons nil menu
)))
1118 (funcall (symbol-function 'tempo-define-template
)
1119 (concat "erlang-" (nth 1 (car skel
)))
1120 ;; The tempo template used contains an `include'
1121 ;; function call only, hence changes to the
1122 ;; variables describing the templates take effect
1124 (list (list 'erlang-skel-include
(nth 2 (car skel
))))
1126 (setq menu
(cons (erlang-skel-make-menu-item
1127 (car skel
)) menu
))))
1128 (setq skel
(cdr skel
)))
1129 (setq erlang-menu-skel-items
1130 (list nil
(list "Skeletons" (nreverse menu
))))
1131 (setq erlang-menu-items
1132 (erlang-menu-add-above 'erlang-menu-skel-items
1133 'erlang-menu-version-items
1135 (erlang-menu-init))))
1137 (defun erlang-skel-make-menu-item (skel)
1138 (let ((func (intern (concat "tempo-template-erlang-" (nth 1 skel
)))))
1139 (cond ((null (nth 3 skel
))
1140 (list (car skel
) func
))
1146 (list 'quote
(nth 3 skel
))
1147 (list 'quote func
))))))))
1149 ;; Functions designed to be added to the skeleton menu.
1150 ;; (Not normally used)
1151 (defun erlang-skel-insert (func)
1152 "Insert skeleton generated by FUNC and goto first tempo mark."
1153 (save-excursion (funcall func
))
1154 (funcall (symbol-function 'tempo-forward-mark
)))
1156 (defun erlang-skel-header (func)
1157 "Insert the header generated by FUNC at the beginning of the buffer."
1158 (goto-char (point-min))
1159 (save-excursion (funcall func
))
1160 (funcall (symbol-function 'tempo-forward-mark
)))
1163 ;; Functions used inside the skeleton descriptions.
1164 (defun erlang-skel-skip-blank ()
1165 (skip-chars-backward " \t")
1168 (defun erlang-skel-include (&rest args
)
1169 "Include a template inside another template.
1171 Example of use, assuming that `erlang-skel-func' is defined:
1173 (defvar foo-skeleton '(\"%%% New function:\"
1174 (erlang-skel-include erlang-skel-func)))
1176 Technically, this function returns the `tempo' attribute`(l ...)' which
1177 can contain other `tempo' attributes. Please see the function
1178 `tempo-define-template' for a description of the `(l ...)' attribute."
1182 (setq entry
(car args
))
1184 (setq res
(cons (car entry
) res
))
1185 (setq entry
(cdr entry
)))
1186 (setq args
(cdr args
)))
1187 (cons 'l
(nreverse res
))))
1189 (defun erlang-skel-separator (&optional percent
)
1190 "Return a comment separator."
1191 (let ((percent (or percent
3)))
1192 (concat (make-string percent ?%
)
1193 (make-string (- 70 percent
) ?-
)
1196 (defun erlang-skel-double-separator (&optional percent
)
1197 "Return a comment separator."
1198 (let ((percent (or percent
3)))
1199 (concat (make-string percent ?%
)
1200 (make-string (- 70 percent
) ?
=)
1203 (defun erlang-skel-dd-mmm-yyyy ()
1204 "Return the current date as a string in \"DD Mon YYYY\" form.
1205 The first character of DD is space if the value is less than 10."
1206 (let ((date (current-time-string)))
1208 (string-to-int (substring date
8 10))
1209 (substring date
4 7)
1210 (substring date -
4))))
1213 ;; coding: iso-8859-1
1216 ;;; erlang.el ends here